OSDN Git Service

a11a71b6c2e6b356bf45d21f4a5827a1c358f1ca
[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
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 ;; w -- print the operand as if it's a "word" (HImode) even if it isn't.
42 ;; s -- print a shift double count, followed by the assemblers argument
43 ;;      delimiter.
44 ;; b -- print the QImode name of the register for the indicated operand.
45 ;;      %b0 would print %al if operands[0] is reg 0.
46 ;; w --  likewise, print the HImode name of the register.
47 ;; k --  likewise, print the SImode name of the register.
48 ;; q --  likewise, print the DImode name of the register.
49 ;; x --  likewise, print the V4SFmode name of the register.
50 ;; t --  likewise, print the V8SFmode name of the register.
51 ;; h -- print the QImode name for a "high" register, either ah, bh, ch or dh.
52 ;; y -- print "st(0)" instead of "st" as a register.
53 ;; d -- print duplicated register operand for AVX instruction.
54 ;; D -- print condition for SSE cmp instruction.
55 ;; P -- if PIC, print an @PLT suffix.
56 ;; p -- print raw symbol name.
57 ;; X -- don't print any sort of PIC '@' suffix for a symbol.
58 ;; & -- print some in-use local-dynamic symbol name.
59 ;; H -- print a memory address offset by 8; used for sse high-parts
60 ;; Y -- print condition for XOP pcom* instruction.
61 ;; + -- print a branch hint as 'cs' or 'ds' prefix
62 ;; ; -- print a semicolon (after prefixes due to bug in older gas).
63 ;; @ -- print a segment register of thread base pointer load
64
65 ;; UNSPEC usage:
66
67 (define_c_enum "unspec" [
68   ;; Relocation specifiers
69   UNSPEC_GOT
70   UNSPEC_GOTOFF
71   UNSPEC_GOTPCREL
72   UNSPEC_GOTTPOFF
73   UNSPEC_TPOFF
74   UNSPEC_NTPOFF
75   UNSPEC_DTPOFF
76   UNSPEC_GOTNTPOFF
77   UNSPEC_INDNTPOFF
78   UNSPEC_PLTOFF
79   UNSPEC_MACHOPIC_OFFSET
80   UNSPEC_PCREL
81
82   ;; Prologue support
83   UNSPEC_STACK_ALLOC
84   UNSPEC_SET_GOT
85   UNSPEC_REG_SAVE
86   UNSPEC_DEF_CFA
87   UNSPEC_SET_RIP
88   UNSPEC_SET_GOT_OFFSET
89   UNSPEC_MEMORY_BLOCKAGE
90   UNSPEC_STACK_CHECK
91
92   ;; TLS support
93   UNSPEC_TP
94   UNSPEC_TLS_GD
95   UNSPEC_TLS_LD_BASE
96   UNSPEC_TLSDESC
97   UNSPEC_TLS_IE_SUN
98
99   ;; Other random patterns
100   UNSPEC_SCAS
101   UNSPEC_FNSTSW
102   UNSPEC_SAHF
103   UNSPEC_PARITY
104   UNSPEC_FSTCW
105   UNSPEC_ADD_CARRY
106   UNSPEC_FLDCW
107   UNSPEC_REP
108   UNSPEC_LD_MPIC        ; load_macho_picbase
109   UNSPEC_TRUNC_NOOP
110   UNSPEC_DIV_ALREADY_SPLIT
111   UNSPEC_CALL_NEEDS_VZEROUPPER
112   UNSPEC_PAUSE
113
114   ;; For SSE/MMX support:
115   UNSPEC_FIX_NOTRUNC
116   UNSPEC_MASKMOV
117   UNSPEC_MOVMSK
118   UNSPEC_MOVNT
119   UNSPEC_MOVU
120   UNSPEC_RCP
121   UNSPEC_RSQRT
122   UNSPEC_SFENCE
123   UNSPEC_PFRCP
124   UNSPEC_PFRCPIT1
125   UNSPEC_PFRCPIT2
126   UNSPEC_PFRSQRT
127   UNSPEC_PFRSQIT1
128   UNSPEC_MFENCE
129   UNSPEC_LFENCE
130   UNSPEC_PSADBW
131   UNSPEC_LDDQU
132   UNSPEC_MS_TO_SYSV_CALL
133
134   ;; Generic math support
135   UNSPEC_COPYSIGN
136   UNSPEC_IEEE_MIN       ; not commutative
137   UNSPEC_IEEE_MAX       ; not commutative
138
139   ;; x87 Floating point
140   UNSPEC_SIN
141   UNSPEC_COS
142   UNSPEC_FPATAN
143   UNSPEC_FYL2X
144   UNSPEC_FYL2XP1
145   UNSPEC_FRNDINT
146   UNSPEC_FIST
147   UNSPEC_F2XM1
148   UNSPEC_TAN
149   UNSPEC_FXAM
150
151   ;; x87 Rounding
152   UNSPEC_FRNDINT_FLOOR
153   UNSPEC_FRNDINT_CEIL
154   UNSPEC_FRNDINT_TRUNC
155   UNSPEC_FRNDINT_MASK_PM
156   UNSPEC_FIST_FLOOR
157   UNSPEC_FIST_CEIL
158
159   ;; x87 Double output FP
160   UNSPEC_SINCOS_COS
161   UNSPEC_SINCOS_SIN
162   UNSPEC_XTRACT_FRACT
163   UNSPEC_XTRACT_EXP
164   UNSPEC_FSCALE_FRACT
165   UNSPEC_FSCALE_EXP
166   UNSPEC_FPREM_F
167   UNSPEC_FPREM_U
168   UNSPEC_FPREM1_F
169   UNSPEC_FPREM1_U
170
171   UNSPEC_C2_FLAG
172   UNSPEC_FXAM_MEM
173
174   ;; SSP patterns
175   UNSPEC_SP_SET
176   UNSPEC_SP_TEST
177   UNSPEC_SP_TLS_SET
178   UNSPEC_SP_TLS_TEST
179
180   ;; SSSE3
181   UNSPEC_PSHUFB
182   UNSPEC_PSIGN
183   UNSPEC_PALIGNR
184
185   ;; For SSE4A support
186   UNSPEC_EXTRQI
187   UNSPEC_EXTRQ
188   UNSPEC_INSERTQI
189   UNSPEC_INSERTQ
190
191   ;; For SSE4.1 support
192   UNSPEC_BLENDV
193   UNSPEC_INSERTPS
194   UNSPEC_DP
195   UNSPEC_MOVNTDQA
196   UNSPEC_MPSADBW
197   UNSPEC_PHMINPOSUW
198   UNSPEC_PTEST
199   UNSPEC_ROUND
200
201   ;; For SSE4.2 support
202   UNSPEC_CRC32
203   UNSPEC_PCMPESTR
204   UNSPEC_PCMPISTR
205
206   ;; For FMA4 support
207   UNSPEC_FMADDSUB
208   UNSPEC_XOP_UNSIGNED_CMP
209   UNSPEC_XOP_TRUEFALSE
210   UNSPEC_XOP_PERMUTE
211   UNSPEC_FRCZ
212
213   ;; For AES support
214   UNSPEC_AESENC
215   UNSPEC_AESENCLAST
216   UNSPEC_AESDEC
217   UNSPEC_AESDECLAST
218   UNSPEC_AESIMC
219   UNSPEC_AESKEYGENASSIST
220
221   ;; For PCLMUL support
222   UNSPEC_PCLMUL
223
224   ;; For AVX support
225   UNSPEC_PCMP
226   UNSPEC_VPERMIL
227   UNSPEC_VPERMIL2
228   UNSPEC_VPERMIL2F128
229   UNSPEC_CAST
230   UNSPEC_VTESTP
231   UNSPEC_VCVTPH2PS
232   UNSPEC_VCVTPS2PH
233
234   ;; For AVX2 support
235   UNSPEC_VPERMSI
236   UNSPEC_VPERMDF
237   UNSPEC_VPERMSF
238   UNSPEC_VPERMDI
239   UNSPEC_VPERMTI
240   UNSPEC_GATHER
241
242   ;; For BMI support
243   UNSPEC_BEXTR
244
245   ;; For RDRAND support
246   UNSPEC_RDRAND
247
248   ;; For BMI2 support
249   UNSPEC_PDEP
250   UNSPEC_PEXT
251 ])
252
253 (define_c_enum "unspecv" [
254   UNSPECV_BLOCKAGE
255   UNSPECV_STACK_PROBE
256   UNSPECV_PROBE_STACK_RANGE
257   UNSPECV_EMMS
258   UNSPECV_LDMXCSR
259   UNSPECV_STMXCSR
260   UNSPECV_FEMMS
261   UNSPECV_CLFLUSH
262   UNSPECV_ALIGN
263   UNSPECV_MONITOR
264   UNSPECV_MWAIT
265   UNSPECV_CMPXCHG
266   UNSPECV_XCHG
267   UNSPECV_LOCK
268   UNSPECV_PROLOGUE_USE
269   UNSPECV_CLD
270   UNSPECV_NOPS
271   UNSPECV_VZEROALL
272   UNSPECV_VZEROUPPER
273   UNSPECV_RDTSC
274   UNSPECV_RDTSCP
275   UNSPECV_RDPMC
276   UNSPECV_LLWP_INTRINSIC
277   UNSPECV_SLWP_INTRINSIC
278   UNSPECV_LWPVAL_INTRINSIC
279   UNSPECV_LWPINS_INTRINSIC
280   UNSPECV_RDFSBASE
281   UNSPECV_RDGSBASE
282   UNSPECV_WRFSBASE
283   UNSPECV_WRGSBASE
284   UNSPECV_SPLIT_STACK_RETURN
285 ])
286
287 ;; Constants to represent rounding modes in the ROUND instruction
288 (define_constants
289   [(ROUND_FLOOR                 0x1)
290    (ROUND_CEIL                  0x2)
291    (ROUND_TRUNC                 0x3)
292    (ROUND_MXCSR                 0x4)
293    (ROUND_NO_EXC                0x8)
294   ])
295
296 ;; Constants to represent pcomtrue/pcomfalse variants
297 (define_constants
298   [(PCOM_FALSE                  0)
299    (PCOM_TRUE                   1)
300    (COM_FALSE_S                 2)
301    (COM_FALSE_P                 3)
302    (COM_TRUE_S                  4)
303    (COM_TRUE_P                  5)
304   ])
305
306 ;; Constants used in the XOP pperm instruction
307 (define_constants
308   [(PPERM_SRC                   0x00)   /* copy source */
309    (PPERM_INVERT                0x20)   /* invert source */
310    (PPERM_REVERSE               0x40)   /* bit reverse source */
311    (PPERM_REV_INV               0x60)   /* bit reverse & invert src */
312    (PPERM_ZERO                  0x80)   /* all 0's */
313    (PPERM_ONES                  0xa0)   /* all 1's */
314    (PPERM_SIGN                  0xc0)   /* propagate sign bit */
315    (PPERM_INV_SIGN              0xe0)   /* invert & propagate sign */
316    (PPERM_SRC1                  0x00)   /* use first source byte */
317    (PPERM_SRC2                  0x10)   /* use second source byte */
318    ])
319
320 ;; Registers by name.
321 (define_constants
322   [(AX_REG                       0)
323    (DX_REG                       1)
324    (CX_REG                       2)
325    (BX_REG                       3)
326    (SI_REG                       4)
327    (DI_REG                       5)
328    (BP_REG                       6)
329    (SP_REG                       7)
330    (ST0_REG                      8)
331    (ST1_REG                      9)
332    (ST2_REG                     10)
333    (ST3_REG                     11)
334    (ST4_REG                     12)
335    (ST5_REG                     13)
336    (ST6_REG                     14)
337    (ST7_REG                     15)
338    (FLAGS_REG                   17)
339    (FPSR_REG                    18)
340    (FPCR_REG                    19)
341    (XMM0_REG                    21)
342    (XMM1_REG                    22)
343    (XMM2_REG                    23)
344    (XMM3_REG                    24)
345    (XMM4_REG                    25)
346    (XMM5_REG                    26)
347    (XMM6_REG                    27)
348    (XMM7_REG                    28)
349    (MM0_REG                     29)
350    (MM1_REG                     30)
351    (MM2_REG                     31)
352    (MM3_REG                     32)
353    (MM4_REG                     33)
354    (MM5_REG                     34)
355    (MM6_REG                     35)
356    (MM7_REG                     36)
357    (R8_REG                      37)
358    (R9_REG                      38)
359    (R10_REG                     39)
360    (R11_REG                     40)
361    (R12_REG                     41)
362    (R13_REG                     42)
363    (XMM8_REG                    45)
364    (XMM9_REG                    46)
365    (XMM10_REG                   47)
366    (XMM11_REG                   48)
367    (XMM12_REG                   49)
368    (XMM13_REG                   50)
369    (XMM14_REG                   51)
370    (XMM15_REG                   52)
371   ])
372
373 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
374 ;; from i386.c.
375
376 ;; In C guard expressions, put expressions which may be compile-time
377 ;; constants first.  This allows for better optimization.  For
378 ;; example, write "TARGET_64BIT && reload_completed", not
379 ;; "reload_completed && TARGET_64BIT".
380
381 \f
382 ;; Processor type.
383 (define_attr "cpu" "none,pentium,pentiumpro,geode,k6,athlon,k8,core2,corei7,
384                     atom,generic64,amdfam10,bdver1,bdver2,btver1"
385   (const (symbol_ref "ix86_schedule")))
386
387 ;; A basic instruction type.  Refinements due to arguments to be
388 ;; provided in other attributes.
389 (define_attr "type"
390   "other,multi,
391    alu,alu1,negnot,imov,imovx,lea,
392    incdec,ishift,ishiftx,ishift1,rotate,rotatex,rotate1,imul,imulx,idiv,
393    icmp,test,ibr,setcc,icmov,
394    push,pop,call,callv,leave,
395    str,bitmanip,
396    fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint,
397    sselog,sselog1,sseiadd,sseiadd1,sseishft,sseishft1,sseimul,
398    sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,ssecvt1,sseicvt,ssediv,sseins,
399    ssemuladd,sse4arg,lwp,
400    mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft"
401   (const_string "other"))
402
403 ;; Main data type used by the insn
404 (define_attr "mode"
405   "unknown,none,QI,HI,SI,DI,TI,OI,SF,DF,XF,TF,V8SF,V4DF,V4SF,V2DF,V2SF,V1DF"
406   (const_string "unknown"))
407
408 ;; The CPU unit operations uses.
409 (define_attr "unit" "integer,i387,sse,mmx,unknown"
410   (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint")
411            (const_string "i387")
412          (eq_attr "type" "sselog,sselog1,sseiadd,sseiadd1,sseishft,sseishft1,sseimul,
413                           sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,
414                           ssecvt1,sseicvt,ssediv,sseins,ssemuladd,sse4arg")
415            (const_string "sse")
416          (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft")
417            (const_string "mmx")
418          (eq_attr "type" "other")
419            (const_string "unknown")]
420          (const_string "integer")))
421
422 ;; The (bounding maximum) length of an instruction immediate.
423 (define_attr "length_immediate" ""
424   (cond [(eq_attr "type" "incdec,setcc,icmov,str,lea,other,multi,idiv,leave,
425                           bitmanip,imulx")
426            (const_int 0)
427          (eq_attr "unit" "i387,sse,mmx")
428            (const_int 0)
429          (eq_attr "type" "alu,alu1,negnot,imovx,ishift,ishiftx,ishift1,
430                           rotate,rotatex,rotate1,imul,icmp,push,pop")
431            (symbol_ref "ix86_attr_length_immediate_default (insn, true)")
432          (eq_attr "type" "imov,test")
433            (symbol_ref "ix86_attr_length_immediate_default (insn, false)")
434          (eq_attr "type" "call")
435            (if_then_else (match_operand 0 "constant_call_address_operand" "")
436              (const_int 4)
437              (const_int 0))
438          (eq_attr "type" "callv")
439            (if_then_else (match_operand 1 "constant_call_address_operand" "")
440              (const_int 4)
441              (const_int 0))
442          ;; We don't know the size before shorten_branches.  Expect
443          ;; the instruction to fit for better scheduling.
444          (eq_attr "type" "ibr")
445            (const_int 1)
446          ]
447          (symbol_ref "/* Update immediate_length and other attributes! */
448                       gcc_unreachable (),1")))
449
450 ;; The (bounding maximum) length of an instruction address.
451 (define_attr "length_address" ""
452   (cond [(eq_attr "type" "str,other,multi,fxch")
453            (const_int 0)
454          (and (eq_attr "type" "call")
455               (match_operand 0 "constant_call_address_operand" ""))
456              (const_int 0)
457          (and (eq_attr "type" "callv")
458               (match_operand 1 "constant_call_address_operand" ""))
459              (const_int 0)
460          ]
461          (symbol_ref "ix86_attr_length_address_default (insn)")))
462
463 ;; Set when length prefix is used.
464 (define_attr "prefix_data16" ""
465   (cond [(eq_attr "type" "ssemuladd,sse4arg,sseiadd1,ssecvt1")
466            (const_int 0)
467          (eq_attr "mode" "HI")
468            (const_int 1)
469          (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF,TI"))
470            (const_int 1)
471         ]
472         (const_int 0)))
473
474 ;; Set when string REP prefix is used.
475 (define_attr "prefix_rep" ""
476   (cond [(eq_attr "type" "ssemuladd,sse4arg,sseiadd1,ssecvt1")
477            (const_int 0)
478          (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF"))
479            (const_int 1)
480         ]
481         (const_int 0)))
482
483 ;; Set when 0f opcode prefix is used.
484 (define_attr "prefix_0f" ""
485   (if_then_else
486     (ior (eq_attr "type" "imovx,setcc,icmov,bitmanip")
487          (eq_attr "unit" "sse,mmx"))
488     (const_int 1)
489     (const_int 0)))
490
491 ;; Set when REX opcode prefix is used.
492 (define_attr "prefix_rex" ""
493   (cond [(not (match_test "TARGET_64BIT"))
494            (const_int 0)
495          (and (eq_attr "mode" "DI")
496               (and (eq_attr "type" "!push,pop,call,callv,leave,ibr")
497                    (eq_attr "unit" "!mmx")))
498            (const_int 1)
499          (and (eq_attr "mode" "QI")
500               (match_test "x86_extended_QIreg_mentioned_p (insn)"))
501            (const_int 1)
502          (match_test "x86_extended_reg_mentioned_p (insn)")
503            (const_int 1)
504          (and (eq_attr "type" "imovx")
505               (match_operand:QI 1 "ext_QIreg_operand" ""))
506            (const_int 1)
507         ]
508         (const_int 0)))
509
510 ;; There are also additional prefixes in 3DNOW, SSSE3.
511 ;; ssemuladd,sse4arg default to 0f24/0f25 and DREX byte,
512 ;; sseiadd1,ssecvt1 to 0f7a with no DREX byte.
513 ;; 3DNOW has 0f0f prefix, SSSE3 and SSE4_{1,2} 0f38/0f3a.
514 (define_attr "prefix_extra" ""
515   (cond [(eq_attr "type" "ssemuladd,sse4arg")
516            (const_int 2)
517          (eq_attr "type" "sseiadd1,ssecvt1")
518            (const_int 1)
519         ]
520         (const_int 0)))
521
522 ;; Prefix used: original, VEX or maybe VEX.
523 (define_attr "prefix" "orig,vex,maybe_vex"
524   (if_then_else (eq_attr "mode" "OI,V8SF,V4DF")
525     (const_string "vex")
526     (const_string "orig")))
527
528 ;; VEX W bit is used.
529 (define_attr "prefix_vex_w" "" (const_int 0))
530
531 ;; The length of VEX prefix
532 ;; Only instructions with 0f prefix can have 2 byte VEX prefix,
533 ;; 0f38/0f3a prefixes can't.  In i386.md 0f3[8a] is
534 ;; still prefix_0f 1, with prefix_extra 1.
535 (define_attr "length_vex" ""
536   (if_then_else (and (eq_attr "prefix_0f" "1")
537                      (eq_attr "prefix_extra" "0"))
538     (if_then_else (eq_attr "prefix_vex_w" "1")
539       (symbol_ref "ix86_attr_length_vex_default (insn, true, true)")
540       (symbol_ref "ix86_attr_length_vex_default (insn, true, false)"))
541     (if_then_else (eq_attr "prefix_vex_w" "1")
542       (symbol_ref "ix86_attr_length_vex_default (insn, false, true)")
543       (symbol_ref "ix86_attr_length_vex_default (insn, false, false)"))))
544
545 ;; Set when modrm byte is used.
546 (define_attr "modrm" ""
547   (cond [(eq_attr "type" "str,leave")
548            (const_int 0)
549          (eq_attr "unit" "i387")
550            (const_int 0)
551          (and (eq_attr "type" "incdec")
552               (and (not (match_test "TARGET_64BIT"))
553                    (ior (match_operand:SI 1 "register_operand" "")
554                         (match_operand:HI 1 "register_operand" ""))))
555            (const_int 0)
556          (and (eq_attr "type" "push")
557               (not (match_operand 1 "memory_operand" "")))
558            (const_int 0)
559          (and (eq_attr "type" "pop")
560               (not (match_operand 0 "memory_operand" "")))
561            (const_int 0)
562          (and (eq_attr "type" "imov")
563               (and (not (eq_attr "mode" "DI"))
564                    (ior (and (match_operand 0 "register_operand" "")
565                              (match_operand 1 "immediate_operand" ""))
566                         (ior (and (match_operand 0 "ax_reg_operand" "")
567                                   (match_operand 1 "memory_displacement_only_operand" ""))
568                              (and (match_operand 0 "memory_displacement_only_operand" "")
569                                   (match_operand 1 "ax_reg_operand" ""))))))
570            (const_int 0)
571          (and (eq_attr "type" "call")
572               (match_operand 0 "constant_call_address_operand" ""))
573              (const_int 0)
574          (and (eq_attr "type" "callv")
575               (match_operand 1 "constant_call_address_operand" ""))
576              (const_int 0)
577          (and (eq_attr "type" "alu,alu1,icmp,test")
578               (match_operand 0 "ax_reg_operand" ""))
579              (symbol_ref "(get_attr_length_immediate (insn) <= (get_attr_mode (insn) != MODE_QI))")
580          ]
581          (const_int 1)))
582
583 ;; The (bounding maximum) length of an instruction in bytes.
584 ;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences.
585 ;; Later we may want to split them and compute proper length as for
586 ;; other insns.
587 (define_attr "length" ""
588   (cond [(eq_attr "type" "other,multi,fistp,frndint")
589            (const_int 16)
590          (eq_attr "type" "fcmp")
591            (const_int 4)
592          (eq_attr "unit" "i387")
593            (plus (const_int 2)
594                  (plus (attr "prefix_data16")
595                        (attr "length_address")))
596          (ior (eq_attr "prefix" "vex")
597               (and (eq_attr "prefix" "maybe_vex")
598                    (match_test "TARGET_AVX")))
599            (plus (attr "length_vex")
600                  (plus (attr "length_immediate")
601                        (plus (attr "modrm")
602                              (attr "length_address"))))]
603          (plus (plus (attr "modrm")
604                      (plus (attr "prefix_0f")
605                            (plus (attr "prefix_rex")
606                                  (plus (attr "prefix_extra")
607                                        (const_int 1)))))
608                (plus (attr "prefix_rep")
609                      (plus (attr "prefix_data16")
610                            (plus (attr "length_immediate")
611                                  (attr "length_address")))))))
612
613 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
614 ;; `store' if there is a simple memory reference therein, or `unknown'
615 ;; if the instruction is complex.
616
617 (define_attr "memory" "none,load,store,both,unknown"
618   (cond [(eq_attr "type" "other,multi,str,lwp")
619            (const_string "unknown")
620          (eq_attr "type" "lea,fcmov,fpspc")
621            (const_string "none")
622          (eq_attr "type" "fistp,leave")
623            (const_string "both")
624          (eq_attr "type" "frndint")
625            (const_string "load")
626          (eq_attr "type" "push")
627            (if_then_else (match_operand 1 "memory_operand" "")
628              (const_string "both")
629              (const_string "store"))
630          (eq_attr "type" "pop")
631            (if_then_else (match_operand 0 "memory_operand" "")
632              (const_string "both")
633              (const_string "load"))
634          (eq_attr "type" "setcc")
635            (if_then_else (match_operand 0 "memory_operand" "")
636              (const_string "store")
637              (const_string "none"))
638          (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp")
639            (if_then_else (ior (match_operand 0 "memory_operand" "")
640                               (match_operand 1 "memory_operand" ""))
641              (const_string "load")
642              (const_string "none"))
643          (eq_attr "type" "ibr")
644            (if_then_else (match_operand 0 "memory_operand" "")
645              (const_string "load")
646              (const_string "none"))
647          (eq_attr "type" "call")
648            (if_then_else (match_operand 0 "constant_call_address_operand" "")
649              (const_string "none")
650              (const_string "load"))
651          (eq_attr "type" "callv")
652            (if_then_else (match_operand 1 "constant_call_address_operand" "")
653              (const_string "none")
654              (const_string "load"))
655          (and (eq_attr "type" "alu1,negnot,ishift1,sselog1")
656               (match_operand 1 "memory_operand" ""))
657            (const_string "both")
658          (and (match_operand 0 "memory_operand" "")
659               (match_operand 1 "memory_operand" ""))
660            (const_string "both")
661          (match_operand 0 "memory_operand" "")
662            (const_string "store")
663          (match_operand 1 "memory_operand" "")
664            (const_string "load")
665          (and (eq_attr "type"
666                  "!alu1,negnot,ishift1,
667                    imov,imovx,icmp,test,bitmanip,
668                    fmov,fcmp,fsgn,
669                    sse,ssemov,ssecmp,ssecomi,ssecvt,ssecvt1,sseicvt,sselog1,
670                    sseiadd1,mmx,mmxmov,mmxcmp,mmxcvt")
671               (match_operand 2 "memory_operand" ""))
672            (const_string "load")
673          (and (eq_attr "type" "icmov,ssemuladd,sse4arg")
674               (match_operand 3 "memory_operand" ""))
675            (const_string "load")
676         ]
677         (const_string "none")))
678
679 ;; Indicates if an instruction has both an immediate and a displacement.
680
681 (define_attr "imm_disp" "false,true,unknown"
682   (cond [(eq_attr "type" "other,multi")
683            (const_string "unknown")
684          (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1")
685               (and (match_operand 0 "memory_displacement_operand" "")
686                    (match_operand 1 "immediate_operand" "")))
687            (const_string "true")
688          (and (eq_attr "type" "alu,ishift,ishiftx,rotate,rotatex,imul,idiv")
689               (and (match_operand 0 "memory_displacement_operand" "")
690                    (match_operand 2 "immediate_operand" "")))
691            (const_string "true")
692         ]
693         (const_string "false")))
694
695 ;; Indicates if an FP operation has an integer source.
696
697 (define_attr "fp_int_src" "false,true"
698   (const_string "false"))
699
700 ;; Defines rounding mode of an FP operation.
701
702 (define_attr "i387_cw" "trunc,floor,ceil,mask_pm,uninitialized,any"
703   (const_string "any"))
704
705 ;; Define attribute to classify add/sub insns that consumes carry flag (CF)
706 (define_attr "use_carry" "0,1" (const_string "0"))
707
708 ;; Define attribute to indicate unaligned ssemov insns
709 (define_attr "movu" "0,1" (const_string "0"))
710
711 ;; Used to control the "enabled" attribute on a per-instruction basis.
712 (define_attr "isa" "base,sse2,sse2_noavx,sse3,sse4,sse4_noavx,noavx,avx,bmi2"
713   (const_string "base"))
714
715 (define_attr "enabled" ""
716   (cond [(eq_attr "isa" "sse2") (symbol_ref "TARGET_SSE2")
717          (eq_attr "isa" "sse2_noavx")
718            (symbol_ref "TARGET_SSE2 && !TARGET_AVX")
719          (eq_attr "isa" "sse3") (symbol_ref "TARGET_SSE3")
720          (eq_attr "isa" "sse4") (symbol_ref "TARGET_SSE4_1")
721          (eq_attr "isa" "sse4_noavx")
722            (symbol_ref "TARGET_SSE4_1 && !TARGET_AVX")
723          (eq_attr "isa" "avx") (symbol_ref "TARGET_AVX")
724          (eq_attr "isa" "noavx") (symbol_ref "!TARGET_AVX")
725          (eq_attr "isa" "bmi2") (symbol_ref "TARGET_BMI2")
726         ]
727         (const_int 1)))
728
729 ;; Describe a user's asm statement.
730 (define_asm_attributes
731   [(set_attr "length" "128")
732    (set_attr "type" "multi")])
733
734 (define_code_iterator plusminus [plus minus])
735
736 (define_code_iterator sat_plusminus [ss_plus us_plus ss_minus us_minus])
737
738 ;; Base name for define_insn
739 (define_code_attr plusminus_insn
740   [(plus "add") (ss_plus "ssadd") (us_plus "usadd")
741    (minus "sub") (ss_minus "sssub") (us_minus "ussub")])
742
743 ;; Base name for insn mnemonic.
744 (define_code_attr plusminus_mnemonic
745   [(plus "add") (ss_plus "adds") (us_plus "addus")
746    (minus "sub") (ss_minus "subs") (us_minus "subus")])
747 (define_code_attr plusminus_carry_mnemonic
748   [(plus "adc") (minus "sbb")])
749
750 ;; Mark commutative operators as such in constraints.
751 (define_code_attr comm [(plus "%") (ss_plus "%") (us_plus "%")
752                         (minus "") (ss_minus "") (us_minus "")])
753
754 ;; Mapping of max and min
755 (define_code_iterator maxmin [smax smin umax umin])
756
757 ;; Mapping of signed max and min
758 (define_code_iterator smaxmin [smax smin])
759
760 ;; Mapping of unsigned max and min
761 (define_code_iterator umaxmin [umax umin])
762
763 ;; Base name for integer and FP insn mnemonic
764 (define_code_attr maxmin_int [(smax "maxs") (smin "mins")
765                               (umax "maxu") (umin "minu")])
766 (define_code_attr maxmin_float [(smax "max") (smin "min")])
767
768 ;; Mapping of logic operators
769 (define_code_iterator any_logic [and ior xor])
770 (define_code_iterator any_or [ior xor])
771
772 ;; Base name for insn mnemonic.
773 (define_code_attr logic [(and "and") (ior "or") (xor "xor")])
774
775 ;; Mapping of shift-right operators
776 (define_code_iterator any_shiftrt [lshiftrt ashiftrt])
777
778 ;; Base name for define_insn
779 (define_code_attr shiftrt_insn [(lshiftrt "lshr") (ashiftrt "ashr")])
780
781 ;; Base name for insn mnemonic.
782 (define_code_attr shiftrt [(lshiftrt "shr") (ashiftrt "sar")])
783
784 ;; Mapping of rotate operators
785 (define_code_iterator any_rotate [rotate rotatert])
786
787 ;; Base name for define_insn
788 (define_code_attr rotate_insn [(rotate "rotl") (rotatert "rotr")])
789
790 ;; Base name for insn mnemonic.
791 (define_code_attr rotate [(rotate "rol") (rotatert "ror")])
792
793 ;; Mapping of abs neg operators
794 (define_code_iterator absneg [abs neg])
795
796 ;; Base name for x87 insn mnemonic.
797 (define_code_attr absneg_mnemonic [(abs "abs") (neg "chs")])
798
799 ;; Used in signed and unsigned widening multiplications.
800 (define_code_iterator any_extend [sign_extend zero_extend])
801
802 ;; Prefix for insn menmonic.
803 (define_code_attr sgnprefix [(sign_extend "i") (zero_extend "")])
804
805 ;; Prefix for define_insn
806 (define_code_attr u [(sign_extend "") (zero_extend "u")])
807 (define_code_attr s [(sign_extend "s") (zero_extend "u")])
808
809 ;; All integer modes.
810 (define_mode_iterator SWI1248x [QI HI SI DI])
811
812 ;; All integer modes without QImode.
813 (define_mode_iterator SWI248x [HI SI DI])
814
815 ;; All integer modes without QImode and HImode.
816 (define_mode_iterator SWI48x [SI DI])
817
818 ;; All integer modes without SImode and DImode.
819 (define_mode_iterator SWI12 [QI HI])
820
821 ;; All integer modes without DImode.
822 (define_mode_iterator SWI124 [QI HI SI])
823
824 ;; All integer modes without QImode and DImode.
825 (define_mode_iterator SWI24 [HI SI])
826
827 ;; Single word integer modes.
828 (define_mode_iterator SWI [QI HI SI (DI "TARGET_64BIT")])
829
830 ;; Single word integer modes without QImode.
831 (define_mode_iterator SWI248 [HI SI (DI "TARGET_64BIT")])
832
833 ;; Single word integer modes without QImode and HImode.
834 (define_mode_iterator SWI48 [SI (DI "TARGET_64BIT")])
835
836 ;; All math-dependant single and double word integer modes.
837 (define_mode_iterator SDWIM [(QI "TARGET_QIMODE_MATH")
838                              (HI "TARGET_HIMODE_MATH")
839                              SI DI (TI "TARGET_64BIT")])
840
841 ;; Math-dependant single word integer modes.
842 (define_mode_iterator SWIM [(QI "TARGET_QIMODE_MATH")
843                             (HI "TARGET_HIMODE_MATH")
844                             SI (DI "TARGET_64BIT")])
845
846 ;; Math-dependant integer modes without DImode.
847 (define_mode_iterator SWIM124 [(QI "TARGET_QIMODE_MATH")
848                                (HI "TARGET_HIMODE_MATH")
849                                SI])
850
851 ;; Math-dependant single word integer modes without QImode.
852 (define_mode_iterator SWIM248 [(HI "TARGET_HIMODE_MATH")
853                                SI (DI "TARGET_64BIT")])
854
855 ;; Double word integer modes.
856 (define_mode_iterator DWI [(DI "!TARGET_64BIT")
857                            (TI "TARGET_64BIT")])
858
859 ;; Double word integer modes as mode attribute.
860 (define_mode_attr DWI [(SI "DI") (DI "TI")])
861 (define_mode_attr dwi [(SI "di") (DI "ti")])
862
863 ;; Half mode for double word integer modes.
864 (define_mode_iterator DWIH [(SI "!TARGET_64BIT")
865                             (DI "TARGET_64BIT")])
866
867 ;; Instruction suffix for integer modes.
868 (define_mode_attr imodesuffix [(QI "b") (HI "w") (SI "l") (DI "q")])
869
870 ;; Pointer size prefix for integer modes (Intel asm dialect)
871 (define_mode_attr iptrsize [(QI "BYTE")
872                             (HI "WORD")
873                             (SI "DWORD")
874                             (DI "QWORD")])
875
876 ;; Register class for integer modes.
877 (define_mode_attr r [(QI "q") (HI "r") (SI "r") (DI "r")])
878
879 ;; Immediate operand constraint for integer modes.
880 (define_mode_attr i [(QI "n") (HI "n") (SI "e") (DI "e")])
881
882 ;; General operand constraint for word modes.
883 (define_mode_attr g [(QI "qmn") (HI "rmn") (SI "rme") (DI "rme")])
884
885 ;; Immediate operand constraint for double integer modes.
886 (define_mode_attr di [(SI "nF") (DI "e")])
887
888 ;; Immediate operand constraint for shifts.
889 (define_mode_attr S [(QI "I") (HI "I") (SI "I") (DI "J") (TI "O")])
890
891 ;; General operand predicate for integer modes.
892 (define_mode_attr general_operand
893         [(QI "general_operand")
894          (HI "general_operand")
895          (SI "x86_64_general_operand")
896          (DI "x86_64_general_operand")
897          (TI "x86_64_general_operand")])
898
899 ;; General sign/zero extend operand predicate for integer modes.
900 (define_mode_attr general_szext_operand
901         [(QI "general_operand")
902          (HI "general_operand")
903          (SI "x86_64_szext_general_operand")
904          (DI "x86_64_szext_general_operand")])
905
906 ;; Immediate operand predicate for integer modes.
907 (define_mode_attr immediate_operand
908         [(QI "immediate_operand")
909          (HI "immediate_operand")
910          (SI "x86_64_immediate_operand")
911          (DI "x86_64_immediate_operand")])
912
913 ;; Nonmemory operand predicate for integer modes.
914 (define_mode_attr nonmemory_operand
915         [(QI "nonmemory_operand")
916          (HI "nonmemory_operand")
917          (SI "x86_64_nonmemory_operand")
918          (DI "x86_64_nonmemory_operand")])
919
920 ;; Operand predicate for shifts.
921 (define_mode_attr shift_operand
922         [(QI "nonimmediate_operand")
923          (HI "nonimmediate_operand")
924          (SI "nonimmediate_operand")
925          (DI "shiftdi_operand")
926          (TI "register_operand")])
927
928 ;; Operand predicate for shift argument.
929 (define_mode_attr shift_immediate_operand
930         [(QI "const_1_to_31_operand")
931          (HI "const_1_to_31_operand")
932          (SI "const_1_to_31_operand")
933          (DI "const_1_to_63_operand")])
934
935 ;; Input operand predicate for arithmetic left shifts.
936 (define_mode_attr ashl_input_operand
937         [(QI "nonimmediate_operand")
938          (HI "nonimmediate_operand")
939          (SI "nonimmediate_operand")
940          (DI "ashldi_input_operand")
941          (TI "reg_or_pm1_operand")])
942
943 ;; SSE and x87 SFmode and DFmode floating point modes
944 (define_mode_iterator MODEF [SF DF])
945
946 ;; All x87 floating point modes
947 (define_mode_iterator X87MODEF [SF DF XF])
948
949 ;; SSE instruction suffix for various modes
950 (define_mode_attr ssemodesuffix
951   [(SF "ss") (DF "sd")
952    (V8SF "ps") (V4DF "pd")
953    (V4SF "ps") (V2DF "pd")
954    (V16QI "b") (V8HI "w") (V4SI "d") (V2DI "q")
955    (V32QI "b") (V16HI "w") (V8SI "d") (V4DI "q")])
956
957 ;; SSE vector suffix for floating point modes
958 (define_mode_attr ssevecmodesuffix [(SF "ps") (DF "pd")])
959
960 ;; SSE vector mode corresponding to a scalar mode
961 (define_mode_attr ssevecmode
962   [(QI "V16QI") (HI "V8HI") (SI "V4SI") (DI "V2DI") (SF "V4SF") (DF "V2DF")])
963
964 ;; Instruction suffix for REX 64bit operators.
965 (define_mode_attr rex64suffix [(SI "") (DI "{q}")])
966
967 ;; This mode iterator allows :P to be used for patterns that operate on
968 ;; pointer-sized quantities.  Exactly one of the two alternatives will match.
969 (define_mode_iterator P [(SI "Pmode == SImode") (DI "Pmode == DImode")])
970
971 ;; This mode iterator allows :PTR to be used for patterns that operate on
972 ;; ptr_mode sized quantities.
973 (define_mode_iterator PTR
974   [(SI "ptr_mode == SImode") (DI "ptr_mode == DImode")])
975 \f
976 ;; Scheduling descriptions
977
978 (include "pentium.md")
979 (include "ppro.md")
980 (include "k6.md")
981 (include "athlon.md")
982 (include "bdver1.md")
983 (include "geode.md")
984 (include "atom.md")
985 (include "core2.md")
986
987 \f
988 ;; Operand and operator predicates and constraints
989
990 (include "predicates.md")
991 (include "constraints.md")
992
993 \f
994 ;; Compare and branch/compare and store instructions.
995
996 (define_expand "cbranch<mode>4"
997   [(set (reg:CC FLAGS_REG)
998         (compare:CC (match_operand:SDWIM 1 "nonimmediate_operand" "")
999                     (match_operand:SDWIM 2 "<general_operand>" "")))
1000    (set (pc) (if_then_else
1001                (match_operator 0 "ordered_comparison_operator"
1002                 [(reg:CC FLAGS_REG) (const_int 0)])
1003                (label_ref (match_operand 3 "" ""))
1004                (pc)))]
1005   ""
1006 {
1007   if (MEM_P (operands[1]) && MEM_P (operands[2]))
1008     operands[1] = force_reg (<MODE>mode, operands[1]);
1009   ix86_expand_branch (GET_CODE (operands[0]),
1010                       operands[1], operands[2], operands[3]);
1011   DONE;
1012 })
1013
1014 (define_expand "cstore<mode>4"
1015   [(set (reg:CC FLAGS_REG)
1016         (compare:CC (match_operand:SWIM 2 "nonimmediate_operand" "")
1017                     (match_operand:SWIM 3 "<general_operand>" "")))
1018    (set (match_operand:QI 0 "register_operand" "")
1019         (match_operator 1 "ordered_comparison_operator"
1020           [(reg:CC FLAGS_REG) (const_int 0)]))]
1021   ""
1022 {
1023   if (MEM_P (operands[2]) && MEM_P (operands[3]))
1024     operands[2] = force_reg (<MODE>mode, operands[2]);
1025   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
1026                      operands[2], operands[3]);
1027   DONE;
1028 })
1029
1030 (define_expand "cmp<mode>_1"
1031   [(set (reg:CC FLAGS_REG)
1032         (compare:CC (match_operand:SWI48 0 "nonimmediate_operand" "")
1033                     (match_operand:SWI48 1 "<general_operand>" "")))])
1034
1035 (define_insn "*cmp<mode>_ccno_1"
1036   [(set (reg FLAGS_REG)
1037         (compare (match_operand:SWI 0 "nonimmediate_operand" "<r>,?m<r>")
1038                  (match_operand:SWI 1 "const0_operand" "")))]
1039   "ix86_match_ccmode (insn, CCNOmode)"
1040   "@
1041    test{<imodesuffix>}\t%0, %0
1042    cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
1043   [(set_attr "type" "test,icmp")
1044    (set_attr "length_immediate" "0,1")
1045    (set_attr "mode" "<MODE>")])
1046
1047 (define_insn "*cmp<mode>_1"
1048   [(set (reg FLAGS_REG)
1049         (compare (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
1050                  (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m")))]
1051   "ix86_match_ccmode (insn, CCmode)"
1052   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
1053   [(set_attr "type" "icmp")
1054    (set_attr "mode" "<MODE>")])
1055
1056 (define_insn "*cmp<mode>_minus_1"
1057   [(set (reg FLAGS_REG)
1058         (compare
1059           (minus:SWI (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
1060                      (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m"))
1061           (const_int 0)))]
1062   "ix86_match_ccmode (insn, CCGOCmode)"
1063   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
1064   [(set_attr "type" "icmp")
1065    (set_attr "mode" "<MODE>")])
1066
1067 (define_insn "*cmpqi_ext_1"
1068   [(set (reg FLAGS_REG)
1069         (compare
1070           (match_operand:QI 0 "general_operand" "Qm")
1071           (subreg:QI
1072             (zero_extract:SI
1073               (match_operand 1 "ext_register_operand" "Q")
1074               (const_int 8)
1075               (const_int 8)) 0)))]
1076   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1077   "cmp{b}\t{%h1, %0|%0, %h1}"
1078   [(set_attr "type" "icmp")
1079    (set_attr "mode" "QI")])
1080
1081 (define_insn "*cmpqi_ext_1_rex64"
1082   [(set (reg FLAGS_REG)
1083         (compare
1084           (match_operand:QI 0 "register_operand" "Q")
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   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1091   "cmp{b}\t{%h1, %0|%0, %h1}"
1092   [(set_attr "type" "icmp")
1093    (set_attr "mode" "QI")])
1094
1095 (define_insn "*cmpqi_ext_2"
1096   [(set (reg FLAGS_REG)
1097         (compare
1098           (subreg:QI
1099             (zero_extract:SI
1100               (match_operand 0 "ext_register_operand" "Q")
1101               (const_int 8)
1102               (const_int 8)) 0)
1103           (match_operand:QI 1 "const0_operand" "")))]
1104   "ix86_match_ccmode (insn, CCNOmode)"
1105   "test{b}\t%h0, %h0"
1106   [(set_attr "type" "test")
1107    (set_attr "length_immediate" "0")
1108    (set_attr "mode" "QI")])
1109
1110 (define_expand "cmpqi_ext_3"
1111   [(set (reg:CC FLAGS_REG)
1112         (compare:CC
1113           (subreg:QI
1114             (zero_extract:SI
1115               (match_operand 0 "ext_register_operand" "")
1116               (const_int 8)
1117               (const_int 8)) 0)
1118           (match_operand:QI 1 "immediate_operand" "")))])
1119
1120 (define_insn "*cmpqi_ext_3_insn"
1121   [(set (reg FLAGS_REG)
1122         (compare
1123           (subreg:QI
1124             (zero_extract:SI
1125               (match_operand 0 "ext_register_operand" "Q")
1126               (const_int 8)
1127               (const_int 8)) 0)
1128           (match_operand:QI 1 "general_operand" "Qmn")))]
1129   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1130   "cmp{b}\t{%1, %h0|%h0, %1}"
1131   [(set_attr "type" "icmp")
1132    (set_attr "modrm" "1")
1133    (set_attr "mode" "QI")])
1134
1135 (define_insn "*cmpqi_ext_3_insn_rex64"
1136   [(set (reg FLAGS_REG)
1137         (compare
1138           (subreg:QI
1139             (zero_extract:SI
1140               (match_operand 0 "ext_register_operand" "Q")
1141               (const_int 8)
1142               (const_int 8)) 0)
1143           (match_operand:QI 1 "nonmemory_operand" "Qn")))]
1144   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1145   "cmp{b}\t{%1, %h0|%h0, %1}"
1146   [(set_attr "type" "icmp")
1147    (set_attr "modrm" "1")
1148    (set_attr "mode" "QI")])
1149
1150 (define_insn "*cmpqi_ext_4"
1151   [(set (reg FLAGS_REG)
1152         (compare
1153           (subreg:QI
1154             (zero_extract:SI
1155               (match_operand 0 "ext_register_operand" "Q")
1156               (const_int 8)
1157               (const_int 8)) 0)
1158           (subreg:QI
1159             (zero_extract:SI
1160               (match_operand 1 "ext_register_operand" "Q")
1161               (const_int 8)
1162               (const_int 8)) 0)))]
1163   "ix86_match_ccmode (insn, CCmode)"
1164   "cmp{b}\t{%h1, %h0|%h0, %h1}"
1165   [(set_attr "type" "icmp")
1166    (set_attr "mode" "QI")])
1167
1168 ;; These implement float point compares.
1169 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
1170 ;; which would allow mix and match FP modes on the compares.  Which is what
1171 ;; the old patterns did, but with many more of them.
1172
1173 (define_expand "cbranchxf4"
1174   [(set (reg:CC FLAGS_REG)
1175         (compare:CC (match_operand:XF 1 "nonmemory_operand" "")
1176                     (match_operand:XF 2 "nonmemory_operand" "")))
1177    (set (pc) (if_then_else
1178               (match_operator 0 "ix86_fp_comparison_operator"
1179                [(reg:CC FLAGS_REG)
1180                 (const_int 0)])
1181               (label_ref (match_operand 3 "" ""))
1182               (pc)))]
1183   "TARGET_80387"
1184 {
1185   ix86_expand_branch (GET_CODE (operands[0]),
1186                       operands[1], operands[2], operands[3]);
1187   DONE;
1188 })
1189
1190 (define_expand "cstorexf4"
1191   [(set (reg:CC FLAGS_REG)
1192         (compare:CC (match_operand:XF 2 "nonmemory_operand" "")
1193                     (match_operand:XF 3 "nonmemory_operand" "")))
1194    (set (match_operand:QI 0 "register_operand" "")
1195               (match_operator 1 "ix86_fp_comparison_operator"
1196                [(reg:CC FLAGS_REG)
1197                 (const_int 0)]))]
1198   "TARGET_80387"
1199 {
1200   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
1201                      operands[2], operands[3]);
1202   DONE;
1203 })
1204
1205 (define_expand "cbranch<mode>4"
1206   [(set (reg:CC FLAGS_REG)
1207         (compare:CC (match_operand:MODEF 1 "cmp_fp_expander_operand" "")
1208                     (match_operand:MODEF 2 "cmp_fp_expander_operand" "")))
1209    (set (pc) (if_then_else
1210               (match_operator 0 "ix86_fp_comparison_operator"
1211                [(reg:CC FLAGS_REG)
1212                 (const_int 0)])
1213               (label_ref (match_operand 3 "" ""))
1214               (pc)))]
1215   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
1216 {
1217   ix86_expand_branch (GET_CODE (operands[0]),
1218                       operands[1], operands[2], operands[3]);
1219   DONE;
1220 })
1221
1222 (define_expand "cstore<mode>4"
1223   [(set (reg:CC FLAGS_REG)
1224         (compare:CC (match_operand:MODEF 2 "cmp_fp_expander_operand" "")
1225                     (match_operand:MODEF 3 "cmp_fp_expander_operand" "")))
1226    (set (match_operand:QI 0 "register_operand" "")
1227               (match_operator 1 "ix86_fp_comparison_operator"
1228                [(reg:CC FLAGS_REG)
1229                 (const_int 0)]))]
1230   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
1231 {
1232   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
1233                      operands[2], operands[3]);
1234   DONE;
1235 })
1236
1237 (define_expand "cbranchcc4"
1238   [(set (pc) (if_then_else
1239               (match_operator 0 "comparison_operator"
1240                [(match_operand 1 "flags_reg_operand" "")
1241                 (match_operand 2 "const0_operand" "")])
1242               (label_ref (match_operand 3 "" ""))
1243               (pc)))]
1244   ""
1245 {
1246   ix86_expand_branch (GET_CODE (operands[0]),
1247                       operands[1], operands[2], operands[3]);
1248   DONE;
1249 })
1250
1251 (define_expand "cstorecc4"
1252   [(set (match_operand:QI 0 "register_operand" "")
1253               (match_operator 1 "comparison_operator"
1254                [(match_operand 2 "flags_reg_operand" "")
1255                 (match_operand 3 "const0_operand" "")]))]
1256   ""
1257 {
1258   ix86_expand_setcc (operands[0], GET_CODE (operands[1]),
1259                      operands[2], operands[3]);
1260   DONE;
1261 })
1262
1263
1264 ;; FP compares, step 1:
1265 ;; Set the FP condition codes.
1266 ;;
1267 ;; CCFPmode     compare with exceptions
1268 ;; CCFPUmode    compare with no exceptions
1269
1270 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
1271 ;; used to manage the reg stack popping would not be preserved.
1272
1273 (define_insn "*cmpfp_0"
1274   [(set (match_operand:HI 0 "register_operand" "=a")
1275         (unspec:HI
1276           [(compare:CCFP
1277              (match_operand 1 "register_operand" "f")
1278              (match_operand 2 "const0_operand" ""))]
1279         UNSPEC_FNSTSW))]
1280   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1281    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1282   "* return output_fp_compare (insn, operands, false, false);"
1283   [(set_attr "type" "multi")
1284    (set_attr "unit" "i387")
1285    (set (attr "mode")
1286      (cond [(match_operand:SF 1 "" "")
1287               (const_string "SF")
1288             (match_operand:DF 1 "" "")
1289               (const_string "DF")
1290            ]
1291            (const_string "XF")))])
1292
1293 (define_insn_and_split "*cmpfp_0_cc"
1294   [(set (reg:CCFP FLAGS_REG)
1295         (compare:CCFP
1296           (match_operand 1 "register_operand" "f")
1297           (match_operand 2 "const0_operand" "")))
1298    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1299   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1300    && TARGET_SAHF && !TARGET_CMOVE
1301    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1302   "#"
1303   "&& reload_completed"
1304   [(set (match_dup 0)
1305         (unspec:HI
1306           [(compare:CCFP (match_dup 1)(match_dup 2))]
1307         UNSPEC_FNSTSW))
1308    (set (reg:CC FLAGS_REG)
1309         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1310   ""
1311   [(set_attr "type" "multi")
1312    (set_attr "unit" "i387")
1313    (set (attr "mode")
1314      (cond [(match_operand:SF 1 "" "")
1315               (const_string "SF")
1316             (match_operand:DF 1 "" "")
1317               (const_string "DF")
1318            ]
1319            (const_string "XF")))])
1320
1321 (define_insn "*cmpfp_xf"
1322   [(set (match_operand:HI 0 "register_operand" "=a")
1323         (unspec:HI
1324           [(compare:CCFP
1325              (match_operand:XF 1 "register_operand" "f")
1326              (match_operand:XF 2 "register_operand" "f"))]
1327           UNSPEC_FNSTSW))]
1328   "TARGET_80387"
1329   "* return output_fp_compare (insn, operands, false, false);"
1330   [(set_attr "type" "multi")
1331    (set_attr "unit" "i387")
1332    (set_attr "mode" "XF")])
1333
1334 (define_insn_and_split "*cmpfp_xf_cc"
1335   [(set (reg:CCFP FLAGS_REG)
1336         (compare:CCFP
1337           (match_operand:XF 1 "register_operand" "f")
1338           (match_operand:XF 2 "register_operand" "f")))
1339    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1340   "TARGET_80387
1341    && TARGET_SAHF && !TARGET_CMOVE"
1342   "#"
1343   "&& reload_completed"
1344   [(set (match_dup 0)
1345         (unspec:HI
1346           [(compare:CCFP (match_dup 1)(match_dup 2))]
1347         UNSPEC_FNSTSW))
1348    (set (reg:CC FLAGS_REG)
1349         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1350   ""
1351   [(set_attr "type" "multi")
1352    (set_attr "unit" "i387")
1353    (set_attr "mode" "XF")])
1354
1355 (define_insn "*cmpfp_<mode>"
1356   [(set (match_operand:HI 0 "register_operand" "=a")
1357         (unspec:HI
1358           [(compare:CCFP
1359              (match_operand:MODEF 1 "register_operand" "f")
1360              (match_operand:MODEF 2 "nonimmediate_operand" "fm"))]
1361           UNSPEC_FNSTSW))]
1362   "TARGET_80387"
1363   "* return output_fp_compare (insn, operands, false, false);"
1364   [(set_attr "type" "multi")
1365    (set_attr "unit" "i387")
1366    (set_attr "mode" "<MODE>")])
1367
1368 (define_insn_and_split "*cmpfp_<mode>_cc"
1369   [(set (reg:CCFP FLAGS_REG)
1370         (compare:CCFP
1371           (match_operand:MODEF 1 "register_operand" "f")
1372           (match_operand:MODEF 2 "nonimmediate_operand" "fm")))
1373    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1374   "TARGET_80387
1375    && TARGET_SAHF && !TARGET_CMOVE"
1376   "#"
1377   "&& reload_completed"
1378   [(set (match_dup 0)
1379         (unspec:HI
1380           [(compare:CCFP (match_dup 1)(match_dup 2))]
1381         UNSPEC_FNSTSW))
1382    (set (reg:CC FLAGS_REG)
1383         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1384   ""
1385   [(set_attr "type" "multi")
1386    (set_attr "unit" "i387")
1387    (set_attr "mode" "<MODE>")])
1388
1389 (define_insn "*cmpfp_u"
1390   [(set (match_operand:HI 0 "register_operand" "=a")
1391         (unspec:HI
1392           [(compare:CCFPU
1393              (match_operand 1 "register_operand" "f")
1394              (match_operand 2 "register_operand" "f"))]
1395           UNSPEC_FNSTSW))]
1396   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1397    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1398   "* return output_fp_compare (insn, operands, false, true);"
1399   [(set_attr "type" "multi")
1400    (set_attr "unit" "i387")
1401    (set (attr "mode")
1402      (cond [(match_operand:SF 1 "" "")
1403               (const_string "SF")
1404             (match_operand:DF 1 "" "")
1405               (const_string "DF")
1406            ]
1407            (const_string "XF")))])
1408
1409 (define_insn_and_split "*cmpfp_u_cc"
1410   [(set (reg:CCFPU FLAGS_REG)
1411         (compare:CCFPU
1412           (match_operand 1 "register_operand" "f")
1413           (match_operand 2 "register_operand" "f")))
1414    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1415   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1416    && TARGET_SAHF && !TARGET_CMOVE
1417    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1418   "#"
1419   "&& reload_completed"
1420   [(set (match_dup 0)
1421         (unspec:HI
1422           [(compare:CCFPU (match_dup 1)(match_dup 2))]
1423         UNSPEC_FNSTSW))
1424    (set (reg:CC FLAGS_REG)
1425         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1426   ""
1427   [(set_attr "type" "multi")
1428    (set_attr "unit" "i387")
1429    (set (attr "mode")
1430      (cond [(match_operand:SF 1 "" "")
1431               (const_string "SF")
1432             (match_operand:DF 1 "" "")
1433               (const_string "DF")
1434            ]
1435            (const_string "XF")))])
1436
1437 (define_insn "*cmpfp_<mode>"
1438   [(set (match_operand:HI 0 "register_operand" "=a")
1439         (unspec:HI
1440           [(compare:CCFP
1441              (match_operand 1 "register_operand" "f")
1442              (match_operator 3 "float_operator"
1443                [(match_operand:SWI24 2 "memory_operand" "m")]))]
1444           UNSPEC_FNSTSW))]
1445   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1446    && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
1447    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1448   "* return output_fp_compare (insn, operands, false, false);"
1449   [(set_attr "type" "multi")
1450    (set_attr "unit" "i387")
1451    (set_attr "fp_int_src" "true")
1452    (set_attr "mode" "<MODE>")])
1453
1454 (define_insn_and_split "*cmpfp_<mode>_cc"
1455   [(set (reg:CCFP FLAGS_REG)
1456         (compare:CCFP
1457           (match_operand 1 "register_operand" "f")
1458           (match_operator 3 "float_operator"
1459             [(match_operand:SWI24 2 "memory_operand" "m")])))
1460    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1461   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1462    && TARGET_SAHF && !TARGET_CMOVE
1463    && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
1464    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1465   "#"
1466   "&& reload_completed"
1467   [(set (match_dup 0)
1468         (unspec:HI
1469           [(compare:CCFP
1470              (match_dup 1)
1471              (match_op_dup 3 [(match_dup 2)]))]
1472         UNSPEC_FNSTSW))
1473    (set (reg:CC FLAGS_REG)
1474         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1475   ""
1476   [(set_attr "type" "multi")
1477    (set_attr "unit" "i387")
1478    (set_attr "fp_int_src" "true")
1479    (set_attr "mode" "<MODE>")])
1480
1481 ;; FP compares, step 2
1482 ;; Move the fpsw to ax.
1483
1484 (define_insn "x86_fnstsw_1"
1485   [(set (match_operand:HI 0 "register_operand" "=a")
1486         (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))]
1487   "TARGET_80387"
1488   "fnstsw\t%0"
1489   [(set (attr "length")
1490         (symbol_ref "ix86_attr_length_address_default (insn) + 2"))
1491    (set_attr "mode" "SI")
1492    (set_attr "unit" "i387")])
1493
1494 ;; FP compares, step 3
1495 ;; Get ax into flags, general case.
1496
1497 (define_insn "x86_sahf_1"
1498   [(set (reg:CC FLAGS_REG)
1499         (unspec:CC [(match_operand:HI 0 "register_operand" "a")]
1500                    UNSPEC_SAHF))]
1501   "TARGET_SAHF"
1502 {
1503 #ifndef HAVE_AS_IX86_SAHF
1504   if (TARGET_64BIT)
1505     return ASM_BYTE "0x9e";
1506   else
1507 #endif
1508   return "sahf";
1509 }
1510   [(set_attr "length" "1")
1511    (set_attr "athlon_decode" "vector")
1512    (set_attr "amdfam10_decode" "direct")
1513    (set_attr "bdver1_decode" "direct")
1514    (set_attr "mode" "SI")])
1515
1516 ;; Pentium Pro can do steps 1 through 3 in one go.
1517 ;; comi*, ucomi*, fcomi*, ficomi*, fucomi*
1518 ;; (these i387 instructions set flags directly)
1519 (define_insn "*cmpfp_i_mixed"
1520   [(set (reg:CCFP FLAGS_REG)
1521         (compare:CCFP (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, false);"
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_i_sse"
1549   [(set (reg:CCFP FLAGS_REG)
1550         (compare:CCFP (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, false);"
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_i_i387"
1572   [(set (reg:CCFP FLAGS_REG)
1573         (compare:CCFP (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, false);"
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" "double")])
1591
1592 (define_insn "*cmpfp_iu_mixed"
1593   [(set (reg:CCFPU FLAGS_REG)
1594         (compare:CCFPU (match_operand 0 "register_operand" "f,x")
1595                        (match_operand 1 "nonimmediate_operand" "f,xm")))]
1596   "TARGET_MIX_SSE_I387
1597    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1598    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1599   "* return output_fp_compare (insn, operands, true, true);"
1600   [(set_attr "type" "fcmp,ssecomi")
1601    (set_attr "prefix" "orig,maybe_vex")
1602    (set (attr "mode")
1603      (if_then_else (match_operand:SF 1 "" "")
1604         (const_string "SF")
1605         (const_string "DF")))
1606    (set (attr "prefix_rep")
1607         (if_then_else (eq_attr "type" "ssecomi")
1608                       (const_string "0")
1609                       (const_string "*")))
1610    (set (attr "prefix_data16")
1611         (cond [(eq_attr "type" "fcmp")
1612                  (const_string "*")
1613                (eq_attr "mode" "DF")
1614                  (const_string "1")
1615               ]
1616               (const_string "0")))
1617    (set_attr "athlon_decode" "vector")
1618    (set_attr "amdfam10_decode" "direct")
1619    (set_attr "bdver1_decode" "double")])
1620
1621 (define_insn "*cmpfp_iu_sse"
1622   [(set (reg:CCFPU FLAGS_REG)
1623         (compare:CCFPU (match_operand 0 "register_operand" "x")
1624                        (match_operand 1 "nonimmediate_operand" "xm")))]
1625   "TARGET_SSE_MATH
1626    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1627    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1628   "* return output_fp_compare (insn, operands, true, true);"
1629   [(set_attr "type" "ssecomi")
1630    (set_attr "prefix" "maybe_vex")
1631    (set (attr "mode")
1632      (if_then_else (match_operand:SF 1 "" "")
1633         (const_string "SF")
1634         (const_string "DF")))
1635    (set_attr "prefix_rep" "0")
1636    (set (attr "prefix_data16")
1637         (if_then_else (eq_attr "mode" "DF")
1638                       (const_string "1")
1639                       (const_string "0")))
1640    (set_attr "athlon_decode" "vector")
1641    (set_attr "amdfam10_decode" "direct")
1642    (set_attr "bdver1_decode" "double")])
1643
1644 (define_insn "*cmpfp_iu_387"
1645   [(set (reg:CCFPU FLAGS_REG)
1646         (compare:CCFPU (match_operand 0 "register_operand" "f")
1647                        (match_operand 1 "register_operand" "f")))]
1648   "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1649    && TARGET_CMOVE
1650    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1651    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1652   "* return output_fp_compare (insn, operands, true, true);"
1653   [(set_attr "type" "fcmp")
1654    (set (attr "mode")
1655      (cond [(match_operand:SF 1 "" "")
1656               (const_string "SF")
1657             (match_operand:DF 1 "" "")
1658               (const_string "DF")
1659            ]
1660            (const_string "XF")))
1661    (set_attr "athlon_decode" "vector")
1662    (set_attr "amdfam10_decode" "direct")
1663    (set_attr "bdver1_decode" "direct")])
1664 \f
1665 ;; Push/pop instructions.
1666
1667 (define_insn "*push<mode>2"
1668   [(set (match_operand:DWI 0 "push_operand" "=<")
1669         (match_operand:DWI 1 "general_no_elim_operand" "riF*o"))]
1670   ""
1671   "#"
1672   [(set_attr "type" "multi")
1673    (set_attr "mode" "<MODE>")])
1674
1675 (define_split
1676   [(set (match_operand:TI 0 "push_operand" "")
1677         (match_operand:TI 1 "general_operand" ""))]
1678   "TARGET_64BIT && reload_completed
1679    && !SSE_REG_P (operands[1])"
1680   [(const_int 0)]
1681   "ix86_split_long_move (operands); DONE;")
1682
1683 (define_insn "*pushdi2_rex64"
1684   [(set (match_operand:DI 0 "push_operand" "=<,!<")
1685         (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
1686   "TARGET_64BIT"
1687   "@
1688    push{q}\t%1
1689    #"
1690   [(set_attr "type" "push,multi")
1691    (set_attr "mode" "DI")])
1692
1693 ;; Convert impossible pushes of immediate to existing instructions.
1694 ;; First try to get scratch register and go through it.  In case this
1695 ;; fails, push sign extended lower part first and then overwrite
1696 ;; upper part by 32bit move.
1697 (define_peephole2
1698   [(match_scratch:DI 2 "r")
1699    (set (match_operand:DI 0 "push_operand" "")
1700         (match_operand:DI 1 "immediate_operand" ""))]
1701   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1702    && !x86_64_immediate_operand (operands[1], DImode)"
1703   [(set (match_dup 2) (match_dup 1))
1704    (set (match_dup 0) (match_dup 2))])
1705
1706 ;; We need to define this as both peepholer and splitter for case
1707 ;; peephole2 pass is not run.
1708 ;; "&& 1" is needed to keep it from matching the previous pattern.
1709 (define_peephole2
1710   [(set (match_operand:DI 0 "push_operand" "")
1711         (match_operand:DI 1 "immediate_operand" ""))]
1712   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1713    && !x86_64_immediate_operand (operands[1], DImode) && 1"
1714   [(set (match_dup 0) (match_dup 1))
1715    (set (match_dup 2) (match_dup 3))]
1716 {
1717   split_double_mode (DImode, &operands[1], 1, &operands[2], &operands[3]);
1718
1719   operands[1] = gen_lowpart (DImode, operands[2]);
1720   operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1721                                                    GEN_INT (4)));
1722 })
1723
1724 (define_split
1725   [(set (match_operand:DI 0 "push_operand" "")
1726         (match_operand:DI 1 "immediate_operand" ""))]
1727   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
1728                     ? epilogue_completed : reload_completed)
1729    && !symbolic_operand (operands[1], DImode)
1730    && !x86_64_immediate_operand (operands[1], DImode)"
1731   [(set (match_dup 0) (match_dup 1))
1732    (set (match_dup 2) (match_dup 3))]
1733 {
1734   split_double_mode (DImode, &operands[1], 1, &operands[2], &operands[3]);
1735
1736   operands[1] = gen_lowpart (DImode, operands[2]);
1737   operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1738                                                    GEN_INT (4)));
1739 })
1740
1741 (define_split
1742   [(set (match_operand:DI 0 "push_operand" "")
1743         (match_operand:DI 1 "general_operand" ""))]
1744   "!TARGET_64BIT && reload_completed
1745    && !(MMX_REG_P (operands[1]) || SSE_REG_P (operands[1]))"
1746   [(const_int 0)]
1747   "ix86_split_long_move (operands); DONE;")
1748
1749 (define_insn "*pushsi2"
1750   [(set (match_operand:SI 0 "push_operand" "=<")
1751         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1752   "!TARGET_64BIT"
1753   "push{l}\t%1"
1754   [(set_attr "type" "push")
1755    (set_attr "mode" "SI")])
1756
1757 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1758 ;; "push a byte/word".  But actually we use pushl, which has the effect
1759 ;; of rounding the amount pushed up to a word.
1760
1761 ;; For TARGET_64BIT we always round up to 8 bytes.
1762 (define_insn "*push<mode>2_rex64"
1763   [(set (match_operand:SWI124 0 "push_operand" "=X")
1764         (match_operand:SWI124 1 "nonmemory_no_elim_operand" "r<i>"))]
1765   "TARGET_64BIT"
1766   "push{q}\t%q1"
1767   [(set_attr "type" "push")
1768    (set_attr "mode" "DI")])
1769
1770 (define_insn "*push<mode>2"
1771   [(set (match_operand:SWI12 0 "push_operand" "=X")
1772         (match_operand:SWI12 1 "nonmemory_no_elim_operand" "rn"))]
1773   "!TARGET_64BIT"
1774   "push{l}\t%k1"
1775   [(set_attr "type" "push")
1776    (set_attr "mode" "SI")])
1777
1778 (define_insn "*push<mode>2_prologue"
1779   [(set (match_operand:P 0 "push_operand" "=<")
1780         (match_operand:P 1 "general_no_elim_operand" "r<i>*m"))
1781    (clobber (mem:BLK (scratch)))]
1782   ""
1783   "push{<imodesuffix>}\t%1"
1784   [(set_attr "type" "push")
1785    (set_attr "mode" "<MODE>")])
1786
1787 (define_insn "*pop<mode>1"
1788   [(set (match_operand:P 0 "nonimmediate_operand" "=r*m")
1789         (match_operand:P 1 "pop_operand" ">"))]
1790   ""
1791   "pop{<imodesuffix>}\t%0"
1792   [(set_attr "type" "pop")
1793    (set_attr "mode" "<MODE>")])
1794
1795 (define_insn "*pop<mode>1_epilogue"
1796   [(set (match_operand:P 0 "nonimmediate_operand" "=r*m")
1797         (match_operand:P 1 "pop_operand" ">"))
1798    (clobber (mem:BLK (scratch)))]
1799   ""
1800   "pop{<imodesuffix>}\t%0"
1801   [(set_attr "type" "pop")
1802    (set_attr "mode" "<MODE>")])
1803 \f
1804 ;; Move instructions.
1805
1806 (define_expand "movoi"
1807   [(set (match_operand:OI 0 "nonimmediate_operand" "")
1808         (match_operand:OI 1 "general_operand" ""))]
1809   "TARGET_AVX"
1810   "ix86_expand_move (OImode, operands); DONE;")
1811
1812 (define_expand "movti"
1813   [(set (match_operand:TI 0 "nonimmediate_operand" "")
1814         (match_operand:TI 1 "nonimmediate_operand" ""))]
1815   "TARGET_64BIT || TARGET_SSE"
1816 {
1817   if (TARGET_64BIT)
1818     ix86_expand_move (TImode, operands);
1819   else if (push_operand (operands[0], TImode))
1820     ix86_expand_push (TImode, operands[1]);
1821   else
1822     ix86_expand_vector_move (TImode, operands);
1823   DONE;
1824 })
1825
1826 ;; This expands to what emit_move_complex would generate if we didn't
1827 ;; have a movti pattern.  Having this avoids problems with reload on
1828 ;; 32-bit targets when SSE is present, but doesn't seem to be harmful
1829 ;; to have around all the time.
1830 (define_expand "movcdi"
1831   [(set (match_operand:CDI 0 "nonimmediate_operand" "")
1832         (match_operand:CDI 1 "general_operand" ""))]
1833   ""
1834 {
1835   if (push_operand (operands[0], CDImode))
1836     emit_move_complex_push (CDImode, operands[0], operands[1]);
1837   else
1838     emit_move_complex_parts (operands[0], operands[1]);
1839   DONE;
1840 })
1841
1842 (define_expand "mov<mode>"
1843   [(set (match_operand:SWI1248x 0 "nonimmediate_operand" "")
1844         (match_operand:SWI1248x 1 "general_operand" ""))]
1845   ""
1846   "ix86_expand_move (<MODE>mode, operands); DONE;")
1847
1848 (define_insn "*mov<mode>_xor"
1849   [(set (match_operand:SWI48 0 "register_operand" "=r")
1850         (match_operand:SWI48 1 "const0_operand" ""))
1851    (clobber (reg:CC FLAGS_REG))]
1852   "reload_completed"
1853   "xor{l}\t%k0, %k0"
1854   [(set_attr "type" "alu1")
1855    (set_attr "mode" "SI")
1856    (set_attr "length_immediate" "0")])
1857
1858 (define_insn "*mov<mode>_or"
1859   [(set (match_operand:SWI48 0 "register_operand" "=r")
1860         (match_operand:SWI48 1 "const_int_operand" ""))
1861    (clobber (reg:CC FLAGS_REG))]
1862   "reload_completed
1863    && operands[1] == constm1_rtx"
1864   "or{<imodesuffix>}\t{%1, %0|%0, %1}"
1865   [(set_attr "type" "alu1")
1866    (set_attr "mode" "<MODE>")
1867    (set_attr "length_immediate" "1")])
1868
1869 (define_insn "*movoi_internal_avx"
1870   [(set (match_operand:OI 0 "nonimmediate_operand" "=x,x,m")
1871         (match_operand:OI 1 "vector_move_operand" "C,xm,x"))]
1872   "TARGET_AVX && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1873 {
1874   switch (which_alternative)
1875     {
1876     case 0:
1877       return standard_sse_constant_opcode (insn, operands[1]);
1878     case 1:
1879     case 2:
1880       if (misaligned_operand (operands[0], OImode)
1881           || misaligned_operand (operands[1], OImode))
1882         return "vmovdqu\t{%1, %0|%0, %1}";
1883       else
1884         return "vmovdqa\t{%1, %0|%0, %1}";
1885     default:
1886       gcc_unreachable ();
1887     }
1888 }
1889   [(set_attr "type" "sselog1,ssemov,ssemov")
1890    (set_attr "prefix" "vex")
1891    (set_attr "mode" "OI")])
1892
1893 (define_insn "*movti_internal_rex64"
1894   [(set (match_operand:TI 0 "nonimmediate_operand" "=!r,o,x,x,xm")
1895         (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
1896   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1897 {
1898   switch (which_alternative)
1899     {
1900     case 0:
1901     case 1:
1902       return "#";
1903     case 2:
1904       return standard_sse_constant_opcode (insn, operands[1]);
1905     case 3:
1906     case 4:
1907       /* TDmode values are passed as TImode on the stack.  Moving them
1908          to stack may result in unaligned memory access.  */
1909       if (misaligned_operand (operands[0], TImode)
1910           || misaligned_operand (operands[1], TImode))
1911         {
1912           if (get_attr_mode (insn) == MODE_V4SF)
1913             return "%vmovups\t{%1, %0|%0, %1}";
1914           else
1915             return "%vmovdqu\t{%1, %0|%0, %1}";
1916         }
1917       else
1918         {
1919           if (get_attr_mode (insn) == MODE_V4SF)
1920             return "%vmovaps\t{%1, %0|%0, %1}";
1921           else
1922             return "%vmovdqa\t{%1, %0|%0, %1}";
1923         }
1924     default:
1925       gcc_unreachable ();
1926     }
1927 }
1928   [(set_attr "type" "*,*,sselog1,ssemov,ssemov")
1929    (set_attr "prefix" "*,*,maybe_vex,maybe_vex,maybe_vex")
1930    (set (attr "mode")
1931         (cond [(eq_attr "alternative" "2,3")
1932                  (if_then_else
1933                    (match_test "optimize_function_for_size_p (cfun)")
1934                    (const_string "V4SF")
1935                    (const_string "TI"))
1936                (eq_attr "alternative" "4")
1937                  (if_then_else
1938                    (ior (match_test "TARGET_SSE_TYPELESS_STORES")
1939                         (match_test "optimize_function_for_size_p (cfun)"))
1940                    (const_string "V4SF")
1941                    (const_string "TI"))]
1942                (const_string "DI")))])
1943
1944 (define_split
1945   [(set (match_operand:TI 0 "nonimmediate_operand" "")
1946         (match_operand:TI 1 "general_operand" ""))]
1947   "reload_completed
1948    && !SSE_REG_P (operands[0]) && !SSE_REG_P (operands[1])"
1949   [(const_int 0)]
1950   "ix86_split_long_move (operands); DONE;")
1951
1952 (define_insn "*movti_internal_sse"
1953   [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
1954         (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
1955   "TARGET_SSE && !TARGET_64BIT
1956    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1957 {
1958   switch (which_alternative)
1959     {
1960     case 0:
1961       return standard_sse_constant_opcode (insn, operands[1]);
1962     case 1:
1963     case 2:
1964       /* TDmode values are passed as TImode on the stack.  Moving them
1965          to stack may result in unaligned memory access.  */
1966       if (misaligned_operand (operands[0], TImode)
1967           || misaligned_operand (operands[1], TImode))
1968         {
1969           if (get_attr_mode (insn) == MODE_V4SF)
1970             return "%vmovups\t{%1, %0|%0, %1}";
1971           else
1972             return "%vmovdqu\t{%1, %0|%0, %1}";
1973         }
1974       else
1975         {
1976           if (get_attr_mode (insn) == MODE_V4SF)
1977             return "%vmovaps\t{%1, %0|%0, %1}";
1978           else
1979             return "%vmovdqa\t{%1, %0|%0, %1}";
1980         }
1981     default:
1982       gcc_unreachable ();
1983     }
1984 }
1985   [(set_attr "type" "sselog1,ssemov,ssemov")
1986    (set_attr "prefix" "maybe_vex")
1987    (set (attr "mode")
1988         (cond [(ior (not (match_test "TARGET_SSE2"))
1989                     (match_test "optimize_function_for_size_p (cfun)"))
1990                  (const_string "V4SF")
1991                (and (eq_attr "alternative" "2")
1992                     (match_test "TARGET_SSE_TYPELESS_STORES"))
1993                  (const_string "V4SF")]
1994               (const_string "TI")))])
1995
1996 (define_insn "*movdi_internal_rex64"
1997   [(set (match_operand:DI 0 "nonimmediate_operand"
1998           "=r,r  ,r,m ,!o,*y,m*y,?*y,?r ,?*Ym,*x,m ,*x,*x,?r ,?*Yi,?*x,?*Ym")
1999         (match_operand:DI 1 "general_operand"
2000           "Z ,rem,i,re,n ,C ,*y ,m  ,*Ym,r   ,C ,*x,*x,m ,*Yi,r   ,*Ym,*x"))]
2001   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2002 {
2003   switch (get_attr_type (insn))
2004     {
2005     case TYPE_SSECVT:
2006       if (SSE_REG_P (operands[0]))
2007         return "movq2dq\t{%1, %0|%0, %1}";
2008       else
2009         return "movdq2q\t{%1, %0|%0, %1}";
2010
2011     case TYPE_SSEMOV:
2012       if (get_attr_mode (insn) == MODE_TI)
2013         return "%vmovdqa\t{%1, %0|%0, %1}";
2014       /* Handle broken assemblers that require movd instead of movq.  */
2015       if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
2016         return "%vmovd\t{%1, %0|%0, %1}";
2017       else
2018         return "%vmovq\t{%1, %0|%0, %1}";
2019
2020     case TYPE_MMXMOV:
2021       /* Handle broken assemblers that require movd instead of movq.  */
2022       if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
2023         return "movd\t{%1, %0|%0, %1}";
2024       else
2025         return "movq\t{%1, %0|%0, %1}";
2026
2027     case TYPE_SSELOG1:
2028       return standard_sse_constant_opcode (insn, operands[1]);
2029
2030     case TYPE_MMX:
2031       return "pxor\t%0, %0";
2032
2033     case TYPE_MULTI:
2034       return "#";
2035
2036     case TYPE_LEA:
2037       return "lea{q}\t{%a1, %0|%0, %a1}";
2038
2039     default:
2040       gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
2041       if (get_attr_mode (insn) == MODE_SI)
2042         return "mov{l}\t{%k1, %k0|%k0, %k1}";
2043       else if (which_alternative == 2)
2044         return "movabs{q}\t{%1, %0|%0, %1}";
2045       else
2046         return "mov{q}\t{%1, %0|%0, %1}";
2047     }
2048 }
2049   [(set (attr "type")
2050      (cond [(eq_attr "alternative" "4")
2051               (const_string "multi")
2052             (eq_attr "alternative" "5")
2053               (const_string "mmx")
2054             (eq_attr "alternative" "6,7,8,9")
2055               (const_string "mmxmov")
2056             (eq_attr "alternative" "10")
2057               (const_string "sselog1")
2058             (eq_attr "alternative" "11,12,13,14,15")
2059               (const_string "ssemov")
2060             (eq_attr "alternative" "16,17")
2061               (const_string "ssecvt")
2062             (match_operand 1 "pic_32bit_operand" "")
2063               (const_string "lea")
2064            ]
2065            (const_string "imov")))
2066    (set (attr "modrm")
2067      (if_then_else
2068        (and (eq_attr "alternative" "2") (eq_attr "type" "imov"))
2069          (const_string "0")
2070          (const_string "*")))
2071    (set (attr "length_immediate")
2072      (if_then_else
2073        (and (eq_attr "alternative" "2") (eq_attr "type" "imov"))
2074          (const_string "8")
2075          (const_string "*")))
2076    (set (attr "prefix_rex")
2077      (if_then_else (eq_attr "alternative" "8,9")
2078        (const_string "1")
2079        (const_string "*")))
2080    (set (attr "prefix_data16")
2081      (if_then_else (eq_attr "alternative" "11")
2082        (const_string "1")
2083        (const_string "*")))
2084    (set (attr "prefix")
2085      (if_then_else (eq_attr "alternative" "10,11,12,13,14,15")
2086        (const_string "maybe_vex")
2087        (const_string "orig")))
2088    (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,DI,TI,DI,TI,DI,DI,DI,DI,DI")])
2089
2090 ;; Reload patterns to support multi-word load/store
2091 ;; with non-offsetable address.
2092 (define_expand "reload_noff_store"
2093   [(parallel [(match_operand 0 "memory_operand" "=m")
2094               (match_operand 1 "register_operand" "r")
2095               (match_operand:DI 2 "register_operand" "=&r")])]
2096   "TARGET_64BIT"
2097 {
2098   rtx mem = operands[0];
2099   rtx addr = XEXP (mem, 0);
2100
2101   emit_move_insn (operands[2], addr);
2102   mem = replace_equiv_address_nv (mem, operands[2]);
2103
2104   emit_insn (gen_rtx_SET (VOIDmode, mem, operands[1]));
2105   DONE;
2106 })
2107
2108 (define_expand "reload_noff_load"
2109   [(parallel [(match_operand 0 "register_operand" "=r")
2110               (match_operand 1 "memory_operand" "m")
2111               (match_operand:DI 2 "register_operand" "=r")])]
2112   "TARGET_64BIT"
2113 {
2114   rtx mem = operands[1];
2115   rtx addr = XEXP (mem, 0);
2116
2117   emit_move_insn (operands[2], addr);
2118   mem = replace_equiv_address_nv (mem, operands[2]);
2119
2120   emit_insn (gen_rtx_SET (VOIDmode, operands[0], mem));
2121   DONE;
2122 })
2123
2124 ;; Convert impossible stores of immediate to existing instructions.
2125 ;; First try to get scratch register and go through it.  In case this
2126 ;; fails, move by 32bit parts.
2127 (define_peephole2
2128   [(match_scratch:DI 2 "r")
2129    (set (match_operand:DI 0 "memory_operand" "")
2130         (match_operand:DI 1 "immediate_operand" ""))]
2131   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2132    && !x86_64_immediate_operand (operands[1], DImode)"
2133   [(set (match_dup 2) (match_dup 1))
2134    (set (match_dup 0) (match_dup 2))])
2135
2136 ;; We need to define this as both peepholer and splitter for case
2137 ;; peephole2 pass is not run.
2138 ;; "&& 1" is needed to keep it from matching the previous pattern.
2139 (define_peephole2
2140   [(set (match_operand:DI 0 "memory_operand" "")
2141         (match_operand:DI 1 "immediate_operand" ""))]
2142   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2143    && !x86_64_immediate_operand (operands[1], DImode) && 1"
2144   [(set (match_dup 2) (match_dup 3))
2145    (set (match_dup 4) (match_dup 5))]
2146   "split_double_mode (DImode, &operands[0], 2, &operands[2], &operands[4]);")
2147
2148 (define_split
2149   [(set (match_operand:DI 0 "memory_operand" "")
2150         (match_operand:DI 1 "immediate_operand" ""))]
2151   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2152                     ? epilogue_completed : reload_completed)
2153    && !symbolic_operand (operands[1], DImode)
2154    && !x86_64_immediate_operand (operands[1], DImode)"
2155   [(set (match_dup 2) (match_dup 3))
2156    (set (match_dup 4) (match_dup 5))]
2157   "split_double_mode (DImode, &operands[0], 2, &operands[2], &operands[4]);")
2158
2159 (define_insn "*movdi_internal"
2160   [(set (match_operand:DI 0 "nonimmediate_operand"
2161           "=r  ,o  ,*y,m*y,*y,*x,m ,*x,*x,*x,m ,*x,*x,?*x,?*Ym")
2162         (match_operand:DI 1 "general_operand"
2163           "riFo,riF,C ,*y ,m ,C ,*x,*x,m ,C ,*x,*x,m ,*Ym,*x"))]
2164   "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2165 {
2166   switch (get_attr_type (insn))
2167     {
2168     case TYPE_SSECVT:
2169       if (SSE_REG_P (operands[0]))
2170         return "movq2dq\t{%1, %0|%0, %1}";
2171       else
2172         return "movdq2q\t{%1, %0|%0, %1}";
2173
2174     case TYPE_SSEMOV:
2175       switch (get_attr_mode (insn))
2176         {
2177         case MODE_TI:
2178           return "%vmovdqa\t{%1, %0|%0, %1}";
2179         case MODE_DI:
2180            return "%vmovq\t{%1, %0|%0, %1}";
2181         case MODE_V4SF:
2182           return "movaps\t{%1, %0|%0, %1}";
2183         case MODE_V2SF:
2184           return "movlps\t{%1, %0|%0, %1}";
2185         default:
2186           gcc_unreachable ();
2187         }
2188
2189     case TYPE_MMXMOV:
2190       return "movq\t{%1, %0|%0, %1}";
2191
2192     case TYPE_SSELOG1:
2193       return standard_sse_constant_opcode (insn, operands[1]);
2194
2195     case TYPE_MMX:
2196       return "pxor\t%0, %0";
2197
2198     case TYPE_MULTI:
2199       return "#";
2200
2201     default:
2202       gcc_unreachable ();
2203     }
2204 }
2205   [(set (attr "isa")
2206      (cond [(eq_attr "alternative" "5,6,7,8,13,14")
2207               (const_string "sse2")
2208             (eq_attr "alternative" "9,10,11,12")
2209               (const_string "noavx")
2210            ]
2211            (const_string "*")))
2212    (set (attr "type")
2213      (cond [(eq_attr "alternative" "0,1")
2214               (const_string "multi")
2215             (eq_attr "alternative" "2")
2216               (const_string "mmx")
2217             (eq_attr "alternative" "3,4")
2218               (const_string "mmxmov")
2219             (eq_attr "alternative" "5,9")
2220               (const_string "sselog1")
2221             (eq_attr "alternative" "13,14")
2222               (const_string "ssecvt")
2223            ]
2224            (const_string "ssemov")))
2225    (set (attr "prefix")
2226      (if_then_else (eq_attr "alternative" "5,6,7,8")
2227        (const_string "maybe_vex")
2228        (const_string "orig")))
2229    (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF,DI,DI")])
2230
2231 (define_split
2232   [(set (match_operand:DI 0 "nonimmediate_operand" "")
2233         (match_operand:DI 1 "general_operand" ""))]
2234   "!TARGET_64BIT && reload_completed
2235    && !(MMX_REG_P (operands[0]) || SSE_REG_P (operands[0]))
2236    && !(MMX_REG_P (operands[1]) || SSE_REG_P (operands[1]))"
2237   [(const_int 0)]
2238   "ix86_split_long_move (operands); DONE;")
2239
2240 (define_insn "*movsi_internal"
2241   [(set (match_operand:SI 0 "nonimmediate_operand"
2242                         "=r,m ,*y,*y,?rm,?*y,*x,*x,?r ,m ,?*Yi,*x")
2243         (match_operand:SI 1 "general_operand"
2244                         "g ,re,C ,*y,*y ,rm ,C ,*x,*Yi,*x,r   ,m "))]
2245   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
2246 {
2247   switch (get_attr_type (insn))
2248     {
2249     case TYPE_SSELOG1:
2250       return standard_sse_constant_opcode (insn, operands[1]);
2251
2252     case TYPE_SSEMOV:
2253       switch (get_attr_mode (insn))
2254         {
2255         case MODE_TI:
2256           return "%vmovdqa\t{%1, %0|%0, %1}";
2257         case MODE_V4SF:
2258           return "%vmovaps\t{%1, %0|%0, %1}";
2259         case MODE_SI:
2260           return "%vmovd\t{%1, %0|%0, %1}";
2261         case MODE_SF:
2262           return "%vmovss\t{%1, %0|%0, %1}";
2263         default:
2264           gcc_unreachable ();
2265         }
2266
2267     case TYPE_MMX:
2268       return "pxor\t%0, %0";
2269
2270     case TYPE_MMXMOV:
2271       if (get_attr_mode (insn) == MODE_DI)
2272         return "movq\t{%1, %0|%0, %1}";
2273       return "movd\t{%1, %0|%0, %1}";
2274
2275     case TYPE_LEA:
2276       return "lea{l}\t{%a1, %0|%0, %a1}";
2277
2278     default:
2279       gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
2280       return "mov{l}\t{%1, %0|%0, %1}";
2281     }
2282 }
2283   [(set (attr "type")
2284      (cond [(eq_attr "alternative" "2")
2285               (const_string "mmx")
2286             (eq_attr "alternative" "3,4,5")
2287               (const_string "mmxmov")
2288             (eq_attr "alternative" "6")
2289               (const_string "sselog1")
2290             (eq_attr "alternative" "7,8,9,10,11")
2291               (const_string "ssemov")
2292             (match_operand 1 "pic_32bit_operand" "")
2293               (const_string "lea")
2294            ]
2295            (const_string "imov")))
2296    (set (attr "prefix")
2297      (if_then_else (eq_attr "alternative" "0,1,2,3,4,5")
2298        (const_string "orig")
2299        (const_string "maybe_vex")))
2300    (set (attr "prefix_data16")
2301      (if_then_else (and (eq_attr "type" "ssemov") (eq_attr "mode" "SI"))
2302        (const_string "1")
2303        (const_string "*")))
2304    (set (attr "mode")
2305      (cond [(eq_attr "alternative" "2,3")
2306               (const_string "DI")
2307             (eq_attr "alternative" "6,7")
2308               (if_then_else
2309                 (not (match_test "TARGET_SSE2"))
2310                 (const_string "V4SF")
2311                 (const_string "TI"))
2312             (and (eq_attr "alternative" "8,9,10,11")
2313                  (not (match_test "TARGET_SSE2")))
2314               (const_string "SF")
2315            ]
2316            (const_string "SI")))])
2317
2318 (define_insn "*movhi_internal"
2319   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
2320         (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
2321   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
2322 {
2323   switch (get_attr_type (insn))
2324     {
2325     case TYPE_IMOVX:
2326       /* movzwl is faster than movw on p2 due to partial word stalls,
2327          though not as fast as an aligned movl.  */
2328       return "movz{wl|x}\t{%1, %k0|%k0, %1}";
2329     default:
2330       if (get_attr_mode (insn) == MODE_SI)
2331         return "mov{l}\t{%k1, %k0|%k0, %k1}";
2332       else
2333         return "mov{w}\t{%1, %0|%0, %1}";
2334     }
2335 }
2336   [(set (attr "type")
2337      (cond [(match_test "optimize_function_for_size_p (cfun)")
2338               (const_string "imov")
2339             (and (eq_attr "alternative" "0")
2340                  (ior (not (match_test "TARGET_PARTIAL_REG_STALL"))
2341                       (not (match_test "TARGET_HIMODE_MATH"))))
2342               (const_string "imov")
2343             (and (eq_attr "alternative" "1,2")
2344                  (match_operand:HI 1 "aligned_operand" ""))
2345               (const_string "imov")
2346             (and (match_test "TARGET_MOVX")
2347                  (eq_attr "alternative" "0,2"))
2348               (const_string "imovx")
2349            ]
2350            (const_string "imov")))
2351     (set (attr "mode")
2352       (cond [(eq_attr "type" "imovx")
2353                (const_string "SI")
2354              (and (eq_attr "alternative" "1,2")
2355                   (match_operand:HI 1 "aligned_operand" ""))
2356                (const_string "SI")
2357              (and (eq_attr "alternative" "0")
2358                   (ior (not (match_test "TARGET_PARTIAL_REG_STALL"))
2359                        (not (match_test "TARGET_HIMODE_MATH"))))
2360                (const_string "SI")
2361             ]
2362             (const_string "HI")))])
2363
2364 ;; Situation is quite tricky about when to choose full sized (SImode) move
2365 ;; over QImode moves.  For Q_REG -> Q_REG move we use full size only for
2366 ;; partial register dependency machines (such as AMD Athlon), where QImode
2367 ;; moves issue extra dependency and for partial register stalls machines
2368 ;; that don't use QImode patterns (and QImode move cause stall on the next
2369 ;; instruction).
2370 ;;
2371 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
2372 ;; register stall machines with, where we use QImode instructions, since
2373 ;; partial register stall can be caused there.  Then we use movzx.
2374 (define_insn "*movqi_internal"
2375   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
2376         (match_operand:QI 1 "general_operand"      " q,qn,qm,q,rn,qm,qn"))]
2377   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
2378 {
2379   switch (get_attr_type (insn))
2380     {
2381     case TYPE_IMOVX:
2382       gcc_assert (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]));
2383       return "movz{bl|x}\t{%1, %k0|%k0, %1}";
2384     default:
2385       if (get_attr_mode (insn) == MODE_SI)
2386         return "mov{l}\t{%k1, %k0|%k0, %k1}";
2387       else
2388         return "mov{b}\t{%1, %0|%0, %1}";
2389     }
2390 }
2391   [(set (attr "type")
2392      (cond [(and (eq_attr "alternative" "5")
2393                  (not (match_operand:QI 1 "aligned_operand" "")))
2394               (const_string "imovx")
2395             (match_test "optimize_function_for_size_p (cfun)")
2396               (const_string "imov")
2397             (and (eq_attr "alternative" "3")
2398                  (ior (not (match_test "TARGET_PARTIAL_REG_STALL"))
2399                       (not (match_test "TARGET_QIMODE_MATH"))))
2400               (const_string "imov")
2401             (eq_attr "alternative" "3,5")
2402               (const_string "imovx")
2403             (and (match_test "TARGET_MOVX")
2404                  (eq_attr "alternative" "2"))
2405               (const_string "imovx")
2406            ]
2407            (const_string "imov")))
2408    (set (attr "mode")
2409       (cond [(eq_attr "alternative" "3,4,5")
2410                (const_string "SI")
2411              (eq_attr "alternative" "6")
2412                (const_string "QI")
2413              (eq_attr "type" "imovx")
2414                (const_string "SI")
2415              (and (eq_attr "type" "imov")
2416                   (and (eq_attr "alternative" "0,1")
2417                        (and (match_test "TARGET_PARTIAL_REG_DEPENDENCY")
2418                             (and (not (match_test "optimize_function_for_size_p (cfun)"))
2419                                  (not (match_test "TARGET_PARTIAL_REG_STALL"))))))
2420                (const_string "SI")
2421              ;; Avoid partial register stalls when not using QImode arithmetic
2422              (and (eq_attr "type" "imov")
2423                   (and (eq_attr "alternative" "0,1")
2424                        (and (match_test "TARGET_PARTIAL_REG_STALL")
2425                             (not (match_test "TARGET_QIMODE_MATH")))))
2426                (const_string "SI")
2427            ]
2428            (const_string "QI")))])
2429
2430 ;; Stores and loads of ax to arbitrary constant address.
2431 ;; We fake an second form of instruction to force reload to load address
2432 ;; into register when rax is not available
2433 (define_insn "*movabs<mode>_1"
2434   [(set (mem:SWI1248x (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2435         (match_operand:SWI1248x 1 "nonmemory_operand" "a,er"))]
2436   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
2437   "@
2438    movabs{<imodesuffix>}\t{%1, %P0|%P0, %1}
2439    mov{<imodesuffix>}\t{%1, %a0|%a0, %1}"
2440   [(set_attr "type" "imov")
2441    (set_attr "modrm" "0,*")
2442    (set_attr "length_address" "8,0")
2443    (set_attr "length_immediate" "0,*")
2444    (set_attr "memory" "store")
2445    (set_attr "mode" "<MODE>")])
2446
2447 (define_insn "*movabs<mode>_2"
2448   [(set (match_operand:SWI1248x 0 "register_operand" "=a,r")
2449         (mem:SWI1248x (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2450   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
2451   "@
2452    movabs{<imodesuffix>}\t{%P1, %0|%0, %P1}
2453    mov{<imodesuffix>}\t{%a1, %0|%0, %a1}"
2454   [(set_attr "type" "imov")
2455    (set_attr "modrm" "0,*")
2456    (set_attr "length_address" "8,0")
2457    (set_attr "length_immediate" "0")
2458    (set_attr "memory" "load")
2459    (set_attr "mode" "<MODE>")])
2460
2461 (define_insn "*swap<mode>"
2462   [(set (match_operand:SWI48 0 "register_operand" "+r")
2463         (match_operand:SWI48 1 "register_operand" "+r"))
2464    (set (match_dup 1)
2465         (match_dup 0))]
2466   ""
2467   "xchg{<imodesuffix>}\t%1, %0"
2468   [(set_attr "type" "imov")
2469    (set_attr "mode" "<MODE>")
2470    (set_attr "pent_pair" "np")
2471    (set_attr "athlon_decode" "vector")
2472    (set_attr "amdfam10_decode" "double")
2473    (set_attr "bdver1_decode" "double")])
2474
2475 (define_insn "*swap<mode>_1"
2476   [(set (match_operand:SWI12 0 "register_operand" "+r")
2477         (match_operand:SWI12 1 "register_operand" "+r"))
2478    (set (match_dup 1)
2479         (match_dup 0))]
2480   "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
2481   "xchg{l}\t%k1, %k0"
2482   [(set_attr "type" "imov")
2483    (set_attr "mode" "SI")
2484    (set_attr "pent_pair" "np")
2485    (set_attr "athlon_decode" "vector")
2486    (set_attr "amdfam10_decode" "double")
2487    (set_attr "bdver1_decode" "double")])
2488
2489 ;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL
2490 ;; is disabled for AMDFAM10
2491 (define_insn "*swap<mode>_2"
2492   [(set (match_operand:SWI12 0 "register_operand" "+<r>")
2493         (match_operand:SWI12 1 "register_operand" "+<r>"))
2494    (set (match_dup 1)
2495         (match_dup 0))]
2496   "TARGET_PARTIAL_REG_STALL"
2497   "xchg{<imodesuffix>}\t%1, %0"
2498   [(set_attr "type" "imov")
2499    (set_attr "mode" "<MODE>")
2500    (set_attr "pent_pair" "np")
2501    (set_attr "athlon_decode" "vector")])
2502
2503 (define_expand "movstrict<mode>"
2504   [(set (strict_low_part (match_operand:SWI12 0 "nonimmediate_operand" ""))
2505         (match_operand:SWI12 1 "general_operand" ""))]
2506   ""
2507 {
2508   if (TARGET_PARTIAL_REG_STALL && optimize_function_for_speed_p (cfun))
2509     FAIL;
2510   if (GET_CODE (operands[0]) == SUBREG
2511       && GET_MODE_CLASS (GET_MODE (SUBREG_REG (operands[0]))) != MODE_INT)
2512     FAIL;
2513   /* Don't generate memory->memory moves, go through a register */
2514   if (MEM_P (operands[0]) && MEM_P (operands[1]))
2515     operands[1] = force_reg (<MODE>mode, operands[1]);
2516 })
2517
2518 (define_insn "*movstrict<mode>_1"
2519   [(set (strict_low_part
2520           (match_operand:SWI12 0 "nonimmediate_operand" "+<r>m,<r>"))
2521         (match_operand:SWI12 1 "general_operand" "<r>n,m"))]
2522   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
2523    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2524   "mov{<imodesuffix>}\t{%1, %0|%0, %1}"
2525   [(set_attr "type" "imov")
2526    (set_attr "mode" "<MODE>")])
2527
2528 (define_insn "*movstrict<mode>_xor"
2529   [(set (strict_low_part (match_operand:SWI12 0 "register_operand" "+<r>"))
2530         (match_operand:SWI12 1 "const0_operand" ""))
2531    (clobber (reg:CC FLAGS_REG))]
2532   "reload_completed"
2533   "xor{<imodesuffix>}\t%0, %0"
2534   [(set_attr "type" "alu1")
2535    (set_attr "mode" "<MODE>")
2536    (set_attr "length_immediate" "0")])
2537
2538 (define_insn "*mov<mode>_extv_1"
2539   [(set (match_operand:SWI24 0 "register_operand" "=R")
2540         (sign_extract:SWI24 (match_operand 1 "ext_register_operand" "Q")
2541                             (const_int 8)
2542                             (const_int 8)))]
2543   ""
2544   "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
2545   [(set_attr "type" "imovx")
2546    (set_attr "mode" "SI")])
2547
2548 (define_insn "*movqi_extv_1_rex64"
2549   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2550         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
2551                          (const_int 8)
2552                          (const_int 8)))]
2553   "TARGET_64BIT"
2554 {
2555   switch (get_attr_type (insn))
2556     {
2557     case TYPE_IMOVX:
2558       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
2559     default:
2560       return "mov{b}\t{%h1, %0|%0, %h1}";
2561     }
2562 }
2563   [(set (attr "type")
2564      (if_then_else (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2565                         (match_test "TARGET_MOVX"))
2566         (const_string "imovx")
2567         (const_string "imov")))
2568    (set (attr "mode")
2569      (if_then_else (eq_attr "type" "imovx")
2570         (const_string "SI")
2571         (const_string "QI")))])
2572
2573 (define_insn "*movqi_extv_1"
2574   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
2575         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
2576                          (const_int 8)
2577                          (const_int 8)))]
2578   "!TARGET_64BIT"
2579 {
2580   switch (get_attr_type (insn))
2581     {
2582     case TYPE_IMOVX:
2583       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
2584     default:
2585       return "mov{b}\t{%h1, %0|%0, %h1}";
2586     }
2587 }
2588   [(set (attr "type")
2589      (if_then_else (and (match_operand:QI 0 "register_operand" "")
2590                         (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2591                              (match_test "TARGET_MOVX")))
2592         (const_string "imovx")
2593         (const_string "imov")))
2594    (set (attr "mode")
2595      (if_then_else (eq_attr "type" "imovx")
2596         (const_string "SI")
2597         (const_string "QI")))])
2598
2599 (define_insn "*mov<mode>_extzv_1"
2600   [(set (match_operand:SWI48 0 "register_operand" "=R")
2601         (zero_extract:SWI48 (match_operand 1 "ext_register_operand" "Q")
2602                             (const_int 8)
2603                             (const_int 8)))]
2604   ""
2605   "movz{bl|x}\t{%h1, %k0|%k0, %h1}"
2606   [(set_attr "type" "imovx")
2607    (set_attr "mode" "SI")])
2608
2609 (define_insn "*movqi_extzv_2_rex64"
2610   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2611         (subreg:QI
2612           (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2613                            (const_int 8)
2614                            (const_int 8)) 0))]
2615   "TARGET_64BIT"
2616 {
2617   switch (get_attr_type (insn))
2618     {
2619     case TYPE_IMOVX:
2620       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
2621     default:
2622       return "mov{b}\t{%h1, %0|%0, %h1}";
2623     }
2624 }
2625   [(set (attr "type")
2626      (if_then_else (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2627                         (match_test "TARGET_MOVX"))
2628         (const_string "imovx")
2629         (const_string "imov")))
2630    (set (attr "mode")
2631      (if_then_else (eq_attr "type" "imovx")
2632         (const_string "SI")
2633         (const_string "QI")))])
2634
2635 (define_insn "*movqi_extzv_2"
2636   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
2637         (subreg:QI
2638           (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2639                            (const_int 8)
2640                            (const_int 8)) 0))]
2641   "!TARGET_64BIT"
2642 {
2643   switch (get_attr_type (insn))
2644     {
2645     case TYPE_IMOVX:
2646       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
2647     default:
2648       return "mov{b}\t{%h1, %0|%0, %h1}";
2649     }
2650 }
2651   [(set (attr "type")
2652      (if_then_else (and (match_operand:QI 0 "register_operand" "")
2653                         (ior (not (match_operand:QI 0 "QIreg_operand" ""))
2654                              (match_test "TARGET_MOVX")))
2655         (const_string "imovx")
2656         (const_string "imov")))
2657    (set (attr "mode")
2658      (if_then_else (eq_attr "type" "imovx")
2659         (const_string "SI")
2660         (const_string "QI")))])
2661
2662 (define_expand "mov<mode>_insv_1"
2663   [(set (zero_extract:SWI48 (match_operand 0 "ext_register_operand" "")
2664                             (const_int 8)
2665                             (const_int 8))
2666         (match_operand:SWI48 1 "nonmemory_operand" ""))])
2667
2668 (define_insn "*mov<mode>_insv_1_rex64"
2669   [(set (zero_extract:SWI48x (match_operand 0 "ext_register_operand" "+Q")
2670                              (const_int 8)
2671                              (const_int 8))
2672         (match_operand:SWI48x 1 "nonmemory_operand" "Qn"))]
2673   "TARGET_64BIT"
2674   "mov{b}\t{%b1, %h0|%h0, %b1}"
2675   [(set_attr "type" "imov")
2676    (set_attr "mode" "QI")])
2677
2678 (define_insn "*movsi_insv_1"
2679   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2680                          (const_int 8)
2681                          (const_int 8))
2682         (match_operand:SI 1 "general_operand" "Qmn"))]
2683   "!TARGET_64BIT"
2684   "mov{b}\t{%b1, %h0|%h0, %b1}"
2685   [(set_attr "type" "imov")
2686    (set_attr "mode" "QI")])
2687
2688 (define_insn "*movqi_insv_2"
2689   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2690                          (const_int 8)
2691                          (const_int 8))
2692         (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
2693                      (const_int 8)))]
2694   ""
2695   "mov{b}\t{%h1, %h0|%h0, %h1}"
2696   [(set_attr "type" "imov")
2697    (set_attr "mode" "QI")])
2698 \f
2699 ;; Floating point push instructions.
2700
2701 (define_insn "*pushtf"
2702   [(set (match_operand:TF 0 "push_operand" "=<,<,<")
2703         (match_operand:TF 1 "general_no_elim_operand" "x,Fo,*r"))]
2704   "TARGET_SSE2"
2705 {
2706   /* This insn should be already split before reg-stack.  */
2707   gcc_unreachable ();
2708 }
2709   [(set_attr "type" "multi")
2710    (set_attr "unit" "sse,*,*")
2711    (set_attr "mode" "TF,SI,SI")])
2712
2713 ;; %%% Kill this when call knows how to work this out.
2714 (define_split
2715   [(set (match_operand:TF 0 "push_operand" "")
2716         (match_operand:TF 1 "sse_reg_operand" ""))]
2717   "TARGET_SSE2 && reload_completed"
2718   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -16)))
2719    (set (mem:TF (reg:P SP_REG)) (match_dup 1))])
2720
2721 (define_insn "*pushxf"
2722   [(set (match_operand:XF 0 "push_operand" "=<,<")
2723         (match_operand:XF 1 "general_no_elim_operand" "f,ro"))]
2724   "optimize_function_for_speed_p (cfun)"
2725 {
2726   /* This insn should be already split before reg-stack.  */
2727   gcc_unreachable ();
2728 }
2729   [(set_attr "type" "multi")
2730    (set_attr "unit" "i387,*")
2731    (set_attr "mode" "XF,SI")])
2732
2733 ;; Size of pushxf is 3 (for sub) + 2 (for fstp) + memory operand size.
2734 ;; Size of pushxf using integer instructions is 3+3*memory operand size
2735 ;; Pushing using integer instructions is longer except for constants
2736 ;; and direct memory references (assuming that any given constant is pushed
2737 ;; only once, but this ought to be handled elsewhere).
2738
2739 (define_insn "*pushxf_nointeger"
2740   [(set (match_operand:XF 0 "push_operand" "=<,<")
2741         (match_operand:XF 1 "general_no_elim_operand" "f,*rFo"))]
2742   "optimize_function_for_size_p (cfun)"
2743 {
2744   /* This insn should be already split before reg-stack.  */
2745   gcc_unreachable ();
2746 }
2747   [(set_attr "type" "multi")
2748    (set_attr "unit" "i387,*")
2749    (set_attr "mode" "XF,SI")])
2750
2751 ;; %%% Kill this when call knows how to work this out.
2752 (define_split
2753   [(set (match_operand:XF 0 "push_operand" "")
2754         (match_operand:XF 1 "fp_register_operand" ""))]
2755   "reload_completed"
2756   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
2757    (set (mem:XF (reg:P SP_REG)) (match_dup 1))]
2758   "operands[2] = GEN_INT (-GET_MODE_SIZE (XFmode));")
2759
2760 (define_insn "*pushdf_rex64"
2761   [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2762         (match_operand:DF 1 "general_no_elim_operand" "f,Yd*rFm,x"))]
2763   "TARGET_64BIT"
2764 {
2765   /* This insn should be already split before reg-stack.  */
2766   gcc_unreachable ();
2767 }
2768   [(set_attr "type" "multi")
2769    (set_attr "unit" "i387,*,*")
2770    (set_attr "mode" "DF,DI,DF")])
2771
2772 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2773 ;; Size of pushdf using integer instructions is 2+2*memory operand size
2774 ;; On the average, pushdf using integers can be still shorter.
2775
2776 (define_insn "*pushdf"
2777   [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2778         (match_operand:DF 1 "general_no_elim_operand" "f,Yd*rFo,x"))]
2779   "!TARGET_64BIT"
2780 {
2781   /* This insn should be already split before reg-stack.  */
2782   gcc_unreachable ();
2783 }
2784   [(set_attr "isa" "*,*,sse2")
2785    (set_attr "type" "multi")
2786    (set_attr "unit" "i387,*,*")
2787    (set_attr "mode" "DF,DI,DF")])
2788
2789 ;; %%% Kill this when call knows how to work this out.
2790 (define_split
2791   [(set (match_operand:DF 0 "push_operand" "")
2792         (match_operand:DF 1 "any_fp_register_operand" ""))]
2793   "reload_completed"
2794   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -8)))
2795    (set (mem:DF (reg:P SP_REG)) (match_dup 1))])
2796
2797 (define_insn "*pushsf_rex64"
2798   [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2799         (match_operand:SF 1 "nonmemory_no_elim_operand" "f,rF,x"))]
2800   "TARGET_64BIT"
2801 {
2802   /* Anything else should be already split before reg-stack.  */
2803   gcc_assert (which_alternative == 1);
2804   return "push{q}\t%q1";
2805 }
2806   [(set_attr "type" "multi,push,multi")
2807    (set_attr "unit" "i387,*,*")
2808    (set_attr "mode" "SF,DI,SF")])
2809
2810 (define_insn "*pushsf"
2811   [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2812         (match_operand:SF 1 "general_no_elim_operand" "f,rFm,x"))]
2813   "!TARGET_64BIT"
2814 {
2815   /* Anything else should be already split before reg-stack.  */
2816   gcc_assert (which_alternative == 1);
2817   return "push{l}\t%1";
2818 }
2819   [(set_attr "type" "multi,push,multi")
2820    (set_attr "unit" "i387,*,*")
2821    (set_attr "mode" "SF,SI,SF")])
2822
2823 ;; %%% Kill this when call knows how to work this out.
2824 (define_split
2825   [(set (match_operand:SF 0 "push_operand" "")
2826         (match_operand:SF 1 "any_fp_register_operand" ""))]
2827   "reload_completed"
2828   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
2829    (set (mem:SF (reg:P SP_REG)) (match_dup 1))]
2830   "operands[2] = GEN_INT (-GET_MODE_SIZE (<P:MODE>mode));")
2831
2832 (define_split
2833   [(set (match_operand:SF 0 "push_operand" "")
2834         (match_operand:SF 1 "memory_operand" ""))]
2835   "reload_completed
2836    && (operands[2] = find_constant_src (insn))"
2837   [(set (match_dup 0) (match_dup 2))])
2838
2839 (define_split
2840   [(set (match_operand 0 "push_operand" "")
2841         (match_operand 1 "general_operand" ""))]
2842   "reload_completed
2843    && (GET_MODE (operands[0]) == TFmode
2844        || GET_MODE (operands[0]) == XFmode
2845        || GET_MODE (operands[0]) == DFmode)
2846    && !ANY_FP_REG_P (operands[1])"
2847   [(const_int 0)]
2848   "ix86_split_long_move (operands); DONE;")
2849 \f
2850 ;; Floating point move instructions.
2851
2852 (define_expand "movtf"
2853   [(set (match_operand:TF 0 "nonimmediate_operand" "")
2854         (match_operand:TF 1 "nonimmediate_operand" ""))]
2855   "TARGET_SSE2"
2856 {
2857   ix86_expand_move (TFmode, operands);
2858   DONE;
2859 })
2860
2861 (define_expand "mov<mode>"
2862   [(set (match_operand:X87MODEF 0 "nonimmediate_operand" "")
2863         (match_operand:X87MODEF 1 "general_operand" ""))]
2864   ""
2865   "ix86_expand_move (<MODE>mode, operands); DONE;")
2866
2867 (define_insn "*movtf_internal"
2868   [(set (match_operand:TF 0 "nonimmediate_operand" "=x,m,x,?*r ,!o")
2869         (match_operand:TF 1 "general_operand"      "xm,x,C,*roF,F*r"))]
2870   "TARGET_SSE2
2871    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
2872    && (!can_create_pseudo_p ()
2873        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2874        || GET_CODE (operands[1]) != CONST_DOUBLE
2875        || (optimize_function_for_size_p (cfun)
2876            && standard_sse_constant_p (operands[1])
2877            && !memory_operand (operands[0], TFmode))
2878        || (!TARGET_MEMORY_MISMATCH_STALL
2879            && memory_operand (operands[0], TFmode)))"
2880 {
2881   switch (which_alternative)
2882     {
2883     case 0:
2884     case 1:
2885       /* Handle misaligned load/store since we
2886          don't have movmisaligntf pattern. */
2887       if (misaligned_operand (operands[0], TFmode)
2888           || misaligned_operand (operands[1], TFmode))
2889         {
2890           if (get_attr_mode (insn) == MODE_V4SF)
2891             return "%vmovups\t{%1, %0|%0, %1}";
2892           else
2893             return "%vmovdqu\t{%1, %0|%0, %1}";
2894         }
2895       else
2896         {
2897           if (get_attr_mode (insn) == MODE_V4SF)
2898             return "%vmovaps\t{%1, %0|%0, %1}";
2899           else
2900             return "%vmovdqa\t{%1, %0|%0, %1}";
2901         }
2902
2903     case 2:
2904       return standard_sse_constant_opcode (insn, operands[1]);
2905
2906     case 3:
2907     case 4:
2908         return "#";
2909
2910     default:
2911       gcc_unreachable ();
2912     }
2913 }
2914   [(set_attr "type" "ssemov,ssemov,sselog1,*,*")
2915    (set_attr "prefix" "maybe_vex,maybe_vex,maybe_vex,*,*")
2916    (set (attr "mode")
2917         (cond [(eq_attr "alternative" "0,2")
2918                  (if_then_else
2919                    (match_test "optimize_function_for_size_p (cfun)")
2920                    (const_string "V4SF")
2921                    (const_string "TI"))
2922                (eq_attr "alternative" "1")
2923                  (if_then_else
2924                    (ior (match_test "TARGET_SSE_TYPELESS_STORES")
2925                         (match_test "optimize_function_for_size_p (cfun)"))
2926                    (const_string "V4SF")
2927                    (const_string "TI"))]
2928                (const_string "DI")))])
2929
2930 ;; Possible store forwarding (partial memory) stall in alternative 4.
2931 (define_insn "*movxf_internal"
2932   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,?Yx*r ,!o")
2933         (match_operand:XF 1 "general_operand"      "fm,f,G,Yx*roF,FYx*r"))]
2934   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2935    && (!can_create_pseudo_p ()
2936        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2937        || GET_CODE (operands[1]) != CONST_DOUBLE
2938        || (optimize_function_for_size_p (cfun)
2939            && standard_80387_constant_p (operands[1]) > 0
2940            && !memory_operand (operands[0], XFmode))
2941        || (!TARGET_MEMORY_MISMATCH_STALL
2942            && memory_operand (operands[0], XFmode)))"
2943 {
2944   switch (which_alternative)
2945     {
2946     case 0:
2947     case 1:
2948       return output_387_reg_move (insn, operands);
2949
2950     case 2:
2951       return standard_80387_constant_opcode (operands[1]);
2952
2953     case 3:
2954     case 4:
2955       return "#";
2956
2957     default:
2958       gcc_unreachable ();
2959     }
2960 }
2961   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2962    (set_attr "mode" "XF,XF,XF,SI,SI")])
2963
2964 (define_insn "*movdf_internal_rex64"
2965   [(set (match_operand:DF 0 "nonimmediate_operand"
2966                 "=f,m,f,?r,?m,?r,!o,x,x,x,m,Yi,r ")
2967         (match_operand:DF 1 "general_operand"
2968                 "fm,f,G,rm,r ,F ,F ,C,x,m,x,r ,Yi"))]
2969   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))
2970    && (!can_create_pseudo_p ()
2971        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2972        || GET_CODE (operands[1]) != CONST_DOUBLE
2973        || (optimize_function_for_size_p (cfun)
2974            && ((!(TARGET_SSE2 && TARGET_SSE_MATH)
2975                 && standard_80387_constant_p (operands[1]) > 0)
2976                || (TARGET_SSE2 && TARGET_SSE_MATH
2977                    && standard_sse_constant_p (operands[1]))))
2978        || memory_operand (operands[0], DFmode))"
2979 {
2980   switch (which_alternative)
2981     {
2982     case 0:
2983     case 1:
2984       return output_387_reg_move (insn, operands);
2985
2986     case 2:
2987       return standard_80387_constant_opcode (operands[1]);
2988
2989     case 3:
2990     case 4:
2991       return "mov{q}\t{%1, %0|%0, %1}";
2992
2993     case 5:
2994       return "movabs{q}\t{%1, %0|%0, %1}";
2995
2996     case 6:
2997       return "#";
2998
2999     case 7:
3000       return standard_sse_constant_opcode (insn, operands[1]);
3001
3002     case 8:
3003     case 9:
3004     case 10:
3005       switch (get_attr_mode (insn))
3006         {
3007         case MODE_V2DF:
3008           if (!TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL)
3009             return "%vmovapd\t{%1, %0|%0, %1}";
3010         case MODE_V4SF:
3011           return "%vmovaps\t{%1, %0|%0, %1}";
3012
3013         case MODE_DI:
3014           return "%vmovq\t{%1, %0|%0, %1}";
3015         case MODE_DF:
3016           if (TARGET_AVX && REG_P (operands[0]) && REG_P (operands[1]))
3017             return "vmovsd\t{%1, %0, %0|%0, %0, %1}";
3018           return "%vmovsd\t{%1, %0|%0, %1}";
3019         case MODE_V1DF:
3020           return "%vmovlpd\t{%1, %d0|%d0, %1}";
3021         case MODE_V2SF:
3022           return "%vmovlps\t{%1, %d0|%d0, %1}";
3023         default:
3024           gcc_unreachable ();
3025         }
3026
3027     case 11:
3028     case 12:
3029       /* Handle broken assemblers that require movd instead of movq.  */
3030       return "%vmovd\t{%1, %0|%0, %1}";
3031
3032     default:
3033       gcc_unreachable();
3034     }
3035 }
3036   [(set (attr "type")
3037         (cond [(eq_attr "alternative" "0,1,2")
3038                  (const_string "fmov")
3039                (eq_attr "alternative" "3,4,5")
3040                  (const_string "imov")
3041                (eq_attr "alternative" "6")
3042                  (const_string "multi")
3043                (eq_attr "alternative" "7")
3044                  (const_string "sselog1")
3045               ]
3046               (const_string "ssemov")))
3047    (set (attr "modrm")
3048      (if_then_else
3049        (and (eq_attr "alternative" "5") (eq_attr "type" "imov"))
3050          (const_string "0")
3051          (const_string "*")))
3052    (set (attr "length_immediate")
3053      (if_then_else
3054        (and (eq_attr "alternative" "5") (eq_attr "type" "imov"))
3055          (const_string "8")
3056          (const_string "*")))
3057    (set (attr "prefix")
3058      (if_then_else (eq_attr "alternative" "0,1,2,3,4,5,6")
3059        (const_string "orig")
3060        (const_string "maybe_vex")))
3061    (set (attr "prefix_data16")
3062      (if_then_else (eq_attr "mode" "V1DF")
3063        (const_string "1")
3064        (const_string "*")))
3065    (set (attr "mode")
3066         (cond [(eq_attr "alternative" "0,1,2")
3067                  (const_string "DF")
3068                (eq_attr "alternative" "3,4,5,6,11,12")
3069                  (const_string "DI")
3070
3071                /* xorps is one byte shorter.  */
3072                (eq_attr "alternative" "7")
3073                  (cond [(match_test "optimize_function_for_size_p (cfun)")
3074                           (const_string "V4SF")
3075                         (match_test "TARGET_SSE_LOAD0_BY_PXOR")
3076                           (const_string "TI")
3077                        ]
3078                        (const_string "V2DF"))
3079
3080                /* For architectures resolving dependencies on
3081                   whole SSE registers use APD move to break dependency
3082                   chains, otherwise use short move to avoid extra work.
3083
3084                   movaps encodes one byte shorter.  */
3085                (eq_attr "alternative" "8")
3086                  (cond
3087                    [(match_test "optimize_function_for_size_p (cfun)")
3088                       (const_string "V4SF")
3089                     (match_test "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3090                       (const_string "V2DF")
3091                    ]
3092                    (const_string "DF"))
3093                /* For architectures resolving dependencies on register
3094                   parts we may avoid extra work to zero out upper part
3095                   of register.  */
3096                (eq_attr "alternative" "9")
3097                  (if_then_else
3098                    (match_test "TARGET_SSE_SPLIT_REGS")
3099                    (const_string "V1DF")
3100                    (const_string "DF"))
3101               ]
3102               (const_string "DF")))])
3103
3104 ;; Possible store forwarding (partial memory) stall in alternative 4.
3105 (define_insn "*movdf_internal"
3106   [(set (match_operand:DF 0 "nonimmediate_operand"
3107                 "=f,m,f,?Yd*r ,!o   ,x,x,x,m,*x,*x,*x,m")
3108         (match_operand:DF 1 "general_operand"
3109                 "fm,f,G,Yd*roF,FYd*r,C,x,m,x,C ,*x,m ,*x"))]
3110   "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3111    && (!can_create_pseudo_p ()
3112        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
3113        || GET_CODE (operands[1]) != CONST_DOUBLE
3114        || (optimize_function_for_size_p (cfun)
3115            && ((!(TARGET_SSE2 && TARGET_SSE_MATH)
3116                 && standard_80387_constant_p (operands[1]) > 0)
3117                || (TARGET_SSE2 && TARGET_SSE_MATH
3118                    && standard_sse_constant_p (operands[1])))
3119            && !memory_operand (operands[0], DFmode))
3120        || (!TARGET_MEMORY_MISMATCH_STALL
3121            && memory_operand (operands[0], DFmode)))"
3122 {
3123   switch (which_alternative)
3124     {
3125     case 0:
3126     case 1:
3127       return output_387_reg_move (insn, operands);
3128
3129     case 2:
3130       return standard_80387_constant_opcode (operands[1]);
3131
3132     case 3:
3133     case 4:
3134       return "#";
3135
3136     case 5:
3137     case 9:
3138       return standard_sse_constant_opcode (insn, operands[1]);
3139
3140     case 6:
3141     case 7:
3142     case 8:
3143     case 10:
3144     case 11:
3145     case 12:
3146       switch (get_attr_mode (insn))
3147         {
3148         case MODE_V2DF:
3149           if (!TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL)
3150             return "%vmovapd\t{%1, %0|%0, %1}";
3151         case MODE_V4SF:
3152           return "%vmovaps\t{%1, %0|%0, %1}";
3153
3154         case MODE_DI:
3155           return "%vmovq\t{%1, %0|%0, %1}";
3156         case MODE_DF:
3157           if (TARGET_AVX && REG_P (operands[0]) && REG_P (operands[1]))
3158             return "vmovsd\t{%1, %0, %0|%0, %0, %1}";
3159           return "%vmovsd\t{%1, %0|%0, %1}";
3160         case MODE_V1DF:
3161           return "%vmovlpd\t{%1, %d0|%d0, %1}";
3162         case MODE_V2SF:
3163           return "%vmovlps\t{%1, %d0|%d0, %1}";
3164         default:
3165           gcc_unreachable ();
3166         }
3167
3168     default:
3169       gcc_unreachable ();
3170     }
3171 }
3172   [(set (attr "isa")
3173      (if_then_else (eq_attr "alternative" "5,6,7,8")
3174        (const_string "sse2")
3175        (const_string "*")))
3176    (set (attr "type")
3177         (cond [(eq_attr "alternative" "0,1,2")
3178                  (const_string "fmov")
3179                (eq_attr "alternative" "3,4")
3180                  (const_string "multi")
3181                (eq_attr "alternative" "5,9")
3182                  (const_string "sselog1")
3183               ]
3184               (const_string "ssemov")))
3185    (set (attr "prefix")
3186      (if_then_else (eq_attr "alternative" "0,1,2,3,4")
3187        (const_string "orig")
3188        (const_string "maybe_vex")))
3189    (set (attr "prefix_data16")
3190      (if_then_else (eq_attr "mode" "V1DF")
3191        (const_string "1")
3192        (const_string "*")))
3193    (set (attr "mode")
3194         (cond [(eq_attr "alternative" "0,1,2")
3195                  (const_string "DF")
3196                (eq_attr "alternative" "3,4")
3197                  (const_string "SI")
3198
3199                /* For SSE1, we have many fewer alternatives.  */
3200                (not (match_test "TARGET_SSE2"))
3201                  (if_then_else
3202                    (eq_attr "alternative" "5,6,9,10")
3203                    (const_string "V4SF")
3204                    (const_string "V2SF"))
3205
3206                /* xorps is one byte shorter.  */
3207                (eq_attr "alternative" "5,9")
3208                  (cond [(match_test "optimize_function_for_size_p (cfun)")
3209                           (const_string "V4SF")
3210                         (match_test "TARGET_SSE_LOAD0_BY_PXOR")
3211                           (const_string "TI")
3212                        ]
3213                        (const_string "V2DF"))
3214
3215                /* For architectures resolving dependencies on
3216                   whole SSE registers use APD move to break dependency
3217                   chains, otherwise use short move to avoid extra work.
3218
3219                   movaps encodes one byte shorter.  */
3220                (eq_attr "alternative" "6,10")
3221                  (cond
3222                    [(match_test "optimize_function_for_size_p (cfun)")
3223                       (const_string "V4SF")
3224                     (match_test "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3225                       (const_string "V2DF")
3226                    ]
3227                    (const_string "DF"))
3228                /* For architectures resolving dependencies on register
3229                   parts we may avoid extra work to zero out upper part
3230                   of register.  */
3231                (eq_attr "alternative" "7,11")
3232                  (if_then_else
3233                    (match_test "TARGET_SSE_SPLIT_REGS")
3234                    (const_string "V1DF")
3235                    (const_string "DF"))
3236               ]
3237               (const_string "DF")))])
3238
3239 (define_insn "*movsf_internal"
3240   [(set (match_operand:SF 0 "nonimmediate_operand"
3241           "=f,m,f,?r ,?m,x,x,x,m,!*y,!m,!*y,?Yi,?r,!*Ym,!r")
3242         (match_operand:SF 1 "general_operand"
3243           "fm,f,G,rmF,Fr,C,x,m,x,m  ,*y,*y ,r  ,Yi,r   ,*Ym"))]
3244   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
3245    && (!can_create_pseudo_p ()
3246        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
3247        || GET_CODE (operands[1]) != CONST_DOUBLE
3248        || (optimize_function_for_size_p (cfun)
3249            && ((!TARGET_SSE_MATH
3250                 && standard_80387_constant_p (operands[1]) > 0)
3251                || (TARGET_SSE_MATH
3252                    && standard_sse_constant_p (operands[1]))))
3253        || memory_operand (operands[0], SFmode))"
3254 {
3255   switch (which_alternative)
3256     {
3257     case 0:
3258     case 1:
3259       return output_387_reg_move (insn, operands);
3260
3261     case 2:
3262       return standard_80387_constant_opcode (operands[1]);
3263
3264     case 3:
3265     case 4:
3266       return "mov{l}\t{%1, %0|%0, %1}";
3267
3268     case 5:
3269       return standard_sse_constant_opcode (insn, operands[1]);
3270
3271     case 6:
3272       if (get_attr_mode (insn) == MODE_V4SF)
3273         return "%vmovaps\t{%1, %0|%0, %1}";
3274       if (TARGET_AVX)
3275         return "vmovss\t{%1, %0, %0|%0, %0, %1}";
3276
3277     case 7:
3278     case 8:
3279       return "%vmovss\t{%1, %0|%0, %1}";
3280
3281     case 9:
3282     case 10:
3283     case 14:
3284     case 15:
3285       return "movd\t{%1, %0|%0, %1}";
3286
3287     case 11:
3288       return "movq\t{%1, %0|%0, %1}";
3289
3290     case 12:
3291     case 13:
3292       return "%vmovd\t{%1, %0|%0, %1}";
3293
3294     default:
3295       gcc_unreachable ();
3296     }
3297 }
3298   [(set (attr "type")
3299         (cond [(eq_attr "alternative" "0,1,2")
3300                  (const_string "fmov")
3301                (eq_attr "alternative" "3,4")
3302                  (const_string "multi")
3303                (eq_attr "alternative" "5")
3304                  (const_string "sselog1")
3305                (eq_attr "alternative" "9,10,11,14,15")
3306                  (const_string "mmxmov")
3307               ]
3308               (const_string "ssemov")))
3309    (set (attr "prefix")
3310      (if_then_else (eq_attr "alternative" "5,6,7,8,12,13")
3311        (const_string "maybe_vex")
3312        (const_string "orig")))
3313    (set (attr "mode")
3314         (cond [(eq_attr "alternative" "3,4,9,10")
3315                  (const_string "SI")
3316                (eq_attr "alternative" "5")
3317                  (if_then_else
3318                    (and (and (match_test "TARGET_SSE_LOAD0_BY_PXOR")
3319                              (match_test "TARGET_SSE2"))
3320                         (not (match_test "optimize_function_for_size_p (cfun)")))
3321                    (const_string "TI")
3322                    (const_string "V4SF"))
3323                /* For architectures resolving dependencies on
3324                   whole SSE registers use APS move to break dependency
3325                   chains, otherwise use short move to avoid extra work.
3326
3327                   Do the same for architectures resolving dependencies on
3328                   the parts.  While in DF mode it is better to always handle
3329                   just register parts, the SF mode is different due to lack
3330                   of instructions to load just part of the register.  It is
3331                   better to maintain the whole registers in single format
3332                   to avoid problems on using packed logical operations.  */
3333                (eq_attr "alternative" "6")
3334                  (if_then_else
3335                    (ior (match_test "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3336                         (match_test "TARGET_SSE_SPLIT_REGS"))
3337                    (const_string "V4SF")
3338                    (const_string "SF"))
3339                (eq_attr "alternative" "11")
3340                  (const_string "DI")]
3341                (const_string "SF")))])
3342
3343 (define_split
3344   [(set (match_operand 0 "any_fp_register_operand" "")
3345         (match_operand 1 "memory_operand" ""))]
3346   "reload_completed
3347    && (GET_MODE (operands[0]) == TFmode
3348        || GET_MODE (operands[0]) == XFmode
3349        || GET_MODE (operands[0]) == DFmode
3350        || GET_MODE (operands[0]) == SFmode)
3351    && (operands[2] = find_constant_src (insn))"
3352   [(set (match_dup 0) (match_dup 2))]
3353 {
3354   rtx c = operands[2];
3355   int r = REGNO (operands[0]);
3356
3357   if ((SSE_REGNO_P (r) && !standard_sse_constant_p (c))
3358       || (FP_REGNO_P (r) && standard_80387_constant_p (c) < 1))
3359     FAIL;
3360 })
3361
3362 (define_split
3363   [(set (match_operand 0 "any_fp_register_operand" "")
3364         (float_extend (match_operand 1 "memory_operand" "")))]
3365   "reload_completed
3366    && (GET_MODE (operands[0]) == TFmode
3367        || GET_MODE (operands[0]) == XFmode
3368        || GET_MODE (operands[0]) == DFmode)
3369    && (operands[2] = find_constant_src (insn))"
3370   [(set (match_dup 0) (match_dup 2))]
3371 {
3372   rtx c = operands[2];
3373   int r = REGNO (operands[0]);
3374
3375   if ((SSE_REGNO_P (r) && !standard_sse_constant_p (c))
3376       || (FP_REGNO_P (r) && standard_80387_constant_p (c) < 1))
3377     FAIL;
3378 })
3379
3380 ;; Split the load of -0.0 or -1.0 into fldz;fchs or fld1;fchs sequence
3381 (define_split
3382   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
3383         (match_operand:X87MODEF 1 "immediate_operand" ""))]
3384   "reload_completed
3385    && (standard_80387_constant_p (operands[1]) == 8
3386        || standard_80387_constant_p (operands[1]) == 9)"
3387   [(set (match_dup 0)(match_dup 1))
3388    (set (match_dup 0)
3389         (neg:X87MODEF (match_dup 0)))]
3390 {
3391   REAL_VALUE_TYPE r;
3392
3393   REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
3394   if (real_isnegzero (&r))
3395     operands[1] = CONST0_RTX (<MODE>mode);
3396   else
3397     operands[1] = CONST1_RTX (<MODE>mode);
3398 })
3399
3400 (define_split
3401   [(set (match_operand 0 "nonimmediate_operand" "")
3402         (match_operand 1 "general_operand" ""))]
3403   "reload_completed
3404    && (GET_MODE (operands[0]) == TFmode
3405        || GET_MODE (operands[0]) == XFmode
3406        || GET_MODE (operands[0]) == DFmode)
3407    && !(ANY_FP_REG_P (operands[0]) || ANY_FP_REG_P (operands[1]))"
3408   [(const_int 0)]
3409   "ix86_split_long_move (operands); DONE;")
3410
3411 (define_insn "swapxf"
3412   [(set (match_operand:XF 0 "register_operand" "+f")
3413         (match_operand:XF 1 "register_operand" "+f"))
3414    (set (match_dup 1)
3415         (match_dup 0))]
3416   "TARGET_80387"
3417 {
3418   if (STACK_TOP_P (operands[0]))
3419     return "fxch\t%1";
3420   else
3421     return "fxch\t%0";
3422 }
3423   [(set_attr "type" "fxch")
3424    (set_attr "mode" "XF")])
3425
3426 (define_insn "*swap<mode>"
3427   [(set (match_operand:MODEF 0 "fp_register_operand" "+f")
3428         (match_operand:MODEF 1 "fp_register_operand" "+f"))
3429    (set (match_dup 1)
3430         (match_dup 0))]
3431   "TARGET_80387 || reload_completed"
3432 {
3433   if (STACK_TOP_P (operands[0]))
3434     return "fxch\t%1";
3435   else
3436     return "fxch\t%0";
3437 }
3438   [(set_attr "type" "fxch")
3439    (set_attr "mode" "<MODE>")])
3440 \f
3441 ;; Zero extension instructions
3442
3443 (define_expand "zero_extendsidi2"
3444   [(set (match_operand:DI 0 "nonimmediate_operand" "")
3445         (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
3446   ""
3447 {
3448   if (!TARGET_64BIT)
3449     {
3450       emit_insn (gen_zero_extendsidi2_1 (operands[0], operands[1]));
3451       DONE;
3452     }
3453 })
3454
3455 (define_insn "*zero_extendsidi2_rex64"
3456   [(set (match_operand:DI 0 "nonimmediate_operand"  "=r,o,?*Ym,?*y,?*Yi,*x")
3457         (zero_extend:DI
3458          (match_operand:SI 1 "nonimmediate_operand" "rm,0,r   ,m  ,r   ,m")))]
3459   "TARGET_64BIT"
3460   "@
3461    mov\t{%k1, %k0|%k0, %k1}
3462    #
3463    movd\t{%1, %0|%0, %1}
3464    movd\t{%1, %0|%0, %1}
3465    %vmovd\t{%1, %0|%0, %1}
3466    %vmovd\t{%1, %0|%0, %1}"
3467   [(set_attr "type" "imovx,imov,mmxmov,mmxmov,ssemov,ssemov")
3468    (set_attr "prefix" "orig,*,orig,orig,maybe_vex,maybe_vex")
3469    (set_attr "prefix_0f" "0,*,*,*,*,*")
3470    (set_attr "mode" "SI,DI,DI,DI,TI,TI")])
3471
3472 (define_split
3473   [(set (match_operand:DI 0 "memory_operand" "")
3474         (zero_extend:DI (match_dup 0)))]
3475   "TARGET_64BIT"
3476   [(set (match_dup 4) (const_int 0))]
3477   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3478
3479 ;; %%% Kill me once multi-word ops are sane.
3480 (define_insn "zero_extendsidi2_1"
3481   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?o,?*Ym,?*y,?*Yi,*x")
3482         (zero_extend:DI
3483          (match_operand:SI 1 "nonimmediate_operand" "0,rm,r ,r   ,m  ,r   ,m")))
3484    (clobber (reg:CC FLAGS_REG))]
3485   "!TARGET_64BIT"
3486   "@
3487    #
3488    #
3489    #
3490    movd\t{%1, %0|%0, %1}
3491    movd\t{%1, %0|%0, %1}
3492    %vmovd\t{%1, %0|%0, %1}
3493    %vmovd\t{%1, %0|%0, %1}"
3494   [(set_attr "isa" "*,*,*,*,*,*,sse2")
3495    (set_attr "type" "multi,multi,multi,mmxmov,mmxmov,ssemov,ssemov")
3496    (set_attr "prefix" "*,*,*,orig,orig,maybe_vex,maybe_vex")
3497    (set_attr "mode" "SI,SI,SI,DI,DI,TI,TI")])
3498
3499 (define_split
3500   [(set (match_operand:DI 0 "register_operand" "")
3501         (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3502    (clobber (reg:CC FLAGS_REG))]
3503   "!TARGET_64BIT && reload_completed
3504    && true_regnum (operands[0]) == true_regnum (operands[1])"
3505   [(set (match_dup 4) (const_int 0))]
3506   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3507
3508 (define_split
3509   [(set (match_operand:DI 0 "nonimmediate_operand" "")
3510         (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3511    (clobber (reg:CC FLAGS_REG))]
3512   "!TARGET_64BIT && reload_completed
3513    && !(MMX_REG_P (operands[0]) || SSE_REG_P (operands[0]))"
3514   [(set (match_dup 3) (match_dup 1))
3515    (set (match_dup 4) (const_int 0))]
3516   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3517
3518 (define_insn "zero_extend<mode>di2"
3519   [(set (match_operand:DI 0 "register_operand" "=r")
3520         (zero_extend:DI
3521          (match_operand:SWI12 1 "nonimmediate_operand" "<r>m")))]
3522   "TARGET_64BIT"
3523   "movz{<imodesuffix>l|x}\t{%1, %k0|%k0, %1}"
3524   [(set_attr "type" "imovx")
3525    (set_attr "mode" "SI")])
3526
3527 (define_expand "zero_extendhisi2"
3528   [(set (match_operand:SI 0 "register_operand" "")
3529         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
3530   ""
3531 {
3532   if (TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun))
3533     {
3534       operands[1] = force_reg (HImode, operands[1]);
3535       emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
3536       DONE;
3537     }
3538 })
3539
3540 (define_insn_and_split "zero_extendhisi2_and"
3541   [(set (match_operand:SI 0 "register_operand" "=r")
3542         (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
3543    (clobber (reg:CC FLAGS_REG))]
3544   "TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
3545   "#"
3546   "&& reload_completed"
3547   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
3548               (clobber (reg:CC FLAGS_REG))])]
3549   ""
3550   [(set_attr "type" "alu1")
3551    (set_attr "mode" "SI")])
3552
3553 (define_insn "*zero_extendhisi2_movzwl"
3554   [(set (match_operand:SI 0 "register_operand" "=r")
3555         (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3556   "!TARGET_ZERO_EXTEND_WITH_AND
3557    || optimize_function_for_size_p (cfun)"
3558   "movz{wl|x}\t{%1, %0|%0, %1}"
3559   [(set_attr "type" "imovx")
3560    (set_attr "mode" "SI")])
3561
3562 (define_expand "zero_extendqi<mode>2"
3563   [(parallel
3564     [(set (match_operand:SWI24 0 "register_operand" "")
3565           (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "")))
3566      (clobber (reg:CC FLAGS_REG))])])
3567
3568 (define_insn "*zero_extendqi<mode>2_and"
3569   [(set (match_operand:SWI24 0 "register_operand" "=r,?&q")
3570         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3571    (clobber (reg:CC FLAGS_REG))]
3572   "TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
3573   "#"
3574   [(set_attr "type" "alu1")
3575    (set_attr "mode" "<MODE>")])
3576
3577 ;; When source and destination does not overlap, clear destination
3578 ;; first and then do the movb
3579 (define_split
3580   [(set (match_operand:SWI24 0 "register_operand" "")
3581         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "")))
3582    (clobber (reg:CC FLAGS_REG))]
3583   "reload_completed
3584    && (TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun))
3585    && ANY_QI_REG_P (operands[0])
3586    && (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]))
3587    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3588   [(set (strict_low_part (match_dup 2)) (match_dup 1))]
3589 {
3590   operands[2] = gen_lowpart (QImode, operands[0]);
3591   ix86_expand_clear (operands[0]);
3592 })
3593
3594 (define_insn "*zero_extendqi<mode>2_movzbl_and"
3595   [(set (match_operand:SWI24 0 "register_operand" "=r,r")
3596         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3597    (clobber (reg:CC FLAGS_REG))]
3598   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun)"
3599   "#"
3600   [(set_attr "type" "imovx,alu1")
3601    (set_attr "mode" "<MODE>")])
3602
3603 ;; For the movzbl case strip only the clobber
3604 (define_split
3605   [(set (match_operand:SWI24 0 "register_operand" "")
3606         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "")))
3607    (clobber (reg:CC FLAGS_REG))]
3608   "reload_completed
3609    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))
3610    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3611   [(set (match_dup 0)
3612         (zero_extend:SWI24 (match_dup 1)))])
3613
3614 ; zero extend to SImode to avoid partial register stalls
3615 (define_insn "*zero_extendqi<mode>2_movzbl"
3616   [(set (match_operand:SWI24 0 "register_operand" "=r")
3617         (zero_extend:SWI24 (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3618   "reload_completed
3619    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))"
3620   "movz{bl|x}\t{%1, %k0|%k0, %1}"
3621   [(set_attr "type" "imovx")
3622    (set_attr "mode" "SI")])
3623
3624 ;; Rest is handled by single and.
3625 (define_split
3626   [(set (match_operand:SWI24 0 "register_operand" "")
3627         (zero_extend:SWI24 (match_operand:QI 1 "register_operand" "")))
3628    (clobber (reg:CC FLAGS_REG))]
3629   "reload_completed
3630    && true_regnum (operands[0]) == true_regnum (operands[1])"
3631   [(parallel [(set (match_dup 0) (and:SWI24 (match_dup 0) (const_int 255)))
3632               (clobber (reg:CC FLAGS_REG))])])
3633 \f
3634 ;; Sign extension instructions
3635
3636 (define_expand "extendsidi2"
3637   [(set (match_operand:DI 0 "register_operand" "")
3638         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))]
3639   ""
3640 {
3641   if (!TARGET_64BIT)
3642     {
3643       emit_insn (gen_extendsidi2_1 (operands[0], operands[1]));
3644       DONE;
3645     }
3646 })
3647
3648 (define_insn "*extendsidi2_rex64"
3649   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3650         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3651   "TARGET_64BIT"
3652   "@
3653    {cltq|cdqe}
3654    movs{lq|x}\t{%1, %0|%0, %1}"
3655   [(set_attr "type" "imovx")
3656    (set_attr "mode" "DI")
3657    (set_attr "prefix_0f" "0")
3658    (set_attr "modrm" "0,1")])
3659
3660 (define_insn "extendsidi2_1"
3661   [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3662         (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3663    (clobber (reg:CC FLAGS_REG))
3664    (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3665   "!TARGET_64BIT"
3666   "#")
3667
3668 ;; Extend to memory case when source register does die.
3669 (define_split
3670   [(set (match_operand:DI 0 "memory_operand" "")
3671         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3672    (clobber (reg:CC FLAGS_REG))
3673    (clobber (match_operand:SI 2 "register_operand" ""))]
3674   "(reload_completed
3675     && dead_or_set_p (insn, operands[1])
3676     && !reg_mentioned_p (operands[1], operands[0]))"
3677   [(set (match_dup 3) (match_dup 1))
3678    (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3679               (clobber (reg:CC FLAGS_REG))])
3680    (set (match_dup 4) (match_dup 1))]
3681   "split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);")
3682
3683 ;; Extend to memory case when source register does not die.
3684 (define_split
3685   [(set (match_operand:DI 0 "memory_operand" "")
3686         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3687    (clobber (reg:CC FLAGS_REG))
3688    (clobber (match_operand:SI 2 "register_operand" ""))]
3689   "reload_completed"
3690   [(const_int 0)]
3691 {
3692   split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);
3693
3694   emit_move_insn (operands[3], operands[1]);
3695
3696   /* Generate a cltd if possible and doing so it profitable.  */
3697   if ((optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
3698       && true_regnum (operands[1]) == AX_REG
3699       && true_regnum (operands[2]) == DX_REG)
3700     {
3701       emit_insn (gen_ashrsi3_cvt (operands[2], operands[1], GEN_INT (31)));
3702     }
3703   else
3704     {
3705       emit_move_insn (operands[2], operands[1]);
3706       emit_insn (gen_ashrsi3_cvt (operands[2], operands[2], GEN_INT (31)));
3707     }
3708   emit_move_insn (operands[4], operands[2]);
3709   DONE;
3710 })
3711
3712 ;; Extend to register case.  Optimize case where source and destination
3713 ;; registers match and cases where we can use cltd.
3714 (define_split
3715   [(set (match_operand:DI 0 "register_operand" "")
3716         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3717    (clobber (reg:CC FLAGS_REG))
3718    (clobber (match_scratch:SI 2 ""))]
3719   "reload_completed"
3720   [(const_int 0)]
3721 {
3722   split_double_mode (DImode, &operands[0], 1, &operands[3], &operands[4]);
3723
3724   if (true_regnum (operands[3]) != true_regnum (operands[1]))
3725     emit_move_insn (operands[3], operands[1]);
3726
3727   /* Generate a cltd if possible and doing so it profitable.  */
3728   if ((optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
3729       && true_regnum (operands[3]) == AX_REG
3730       && true_regnum (operands[4]) == DX_REG)
3731     {
3732       emit_insn (gen_ashrsi3_cvt (operands[4], operands[3], GEN_INT (31)));
3733       DONE;
3734     }
3735
3736   if (true_regnum (operands[4]) != true_regnum (operands[1]))
3737     emit_move_insn (operands[4], operands[1]);
3738
3739   emit_insn (gen_ashrsi3_cvt (operands[4], operands[4], GEN_INT (31)));
3740   DONE;
3741 })
3742
3743 (define_insn "extend<mode>di2"
3744   [(set (match_operand:DI 0 "register_operand" "=r")
3745         (sign_extend:DI
3746          (match_operand:SWI12 1 "nonimmediate_operand" "<r>m")))]
3747   "TARGET_64BIT"
3748   "movs{<imodesuffix>q|x}\t{%1, %0|%0, %1}"
3749   [(set_attr "type" "imovx")
3750    (set_attr "mode" "DI")])
3751
3752 (define_insn "extendhisi2"
3753   [(set (match_operand:SI 0 "register_operand" "=*a,r")
3754         (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3755   ""
3756 {
3757   switch (get_attr_prefix_0f (insn))
3758     {
3759     case 0:
3760       return "{cwtl|cwde}";
3761     default:
3762       return "movs{wl|x}\t{%1, %0|%0, %1}";
3763     }
3764 }
3765   [(set_attr "type" "imovx")
3766    (set_attr "mode" "SI")
3767    (set (attr "prefix_0f")
3768      ;; movsx is short decodable while cwtl is vector decoded.
3769      (if_then_else (and (eq_attr "cpu" "!k6")
3770                         (eq_attr "alternative" "0"))
3771         (const_string "0")
3772         (const_string "1")))
3773    (set (attr "modrm")
3774      (if_then_else (eq_attr "prefix_0f" "0")
3775         (const_string "0")
3776         (const_string "1")))])
3777
3778 (define_insn "*extendhisi2_zext"
3779   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3780         (zero_extend:DI
3781          (sign_extend:SI
3782           (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3783   "TARGET_64BIT"
3784 {
3785   switch (get_attr_prefix_0f (insn))
3786     {
3787     case 0:
3788       return "{cwtl|cwde}";
3789     default:
3790       return "movs{wl|x}\t{%1, %k0|%k0, %1}";
3791     }
3792 }
3793   [(set_attr "type" "imovx")
3794    (set_attr "mode" "SI")
3795    (set (attr "prefix_0f")
3796      ;; movsx is short decodable while cwtl is vector decoded.
3797      (if_then_else (and (eq_attr "cpu" "!k6")
3798                         (eq_attr "alternative" "0"))
3799         (const_string "0")
3800         (const_string "1")))
3801    (set (attr "modrm")
3802      (if_then_else (eq_attr "prefix_0f" "0")
3803         (const_string "0")
3804         (const_string "1")))])
3805
3806 (define_insn "extendqisi2"
3807   [(set (match_operand:SI 0 "register_operand" "=r")
3808         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3809   ""
3810   "movs{bl|x}\t{%1, %0|%0, %1}"
3811    [(set_attr "type" "imovx")
3812     (set_attr "mode" "SI")])
3813
3814 (define_insn "*extendqisi2_zext"
3815   [(set (match_operand:DI 0 "register_operand" "=r")
3816         (zero_extend:DI
3817           (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3818   "TARGET_64BIT"
3819   "movs{bl|x}\t{%1, %k0|%k0, %1}"
3820    [(set_attr "type" "imovx")
3821     (set_attr "mode" "SI")])
3822
3823 (define_insn "extendqihi2"
3824   [(set (match_operand:HI 0 "register_operand" "=*a,r")
3825         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3826   ""
3827 {
3828   switch (get_attr_prefix_0f (insn))
3829     {
3830     case 0:
3831       return "{cbtw|cbw}";
3832     default:
3833       return "movs{bw|x}\t{%1, %0|%0, %1}";
3834     }
3835 }
3836   [(set_attr "type" "imovx")
3837    (set_attr "mode" "HI")
3838    (set (attr "prefix_0f")
3839      ;; movsx is short decodable while cwtl is vector decoded.
3840      (if_then_else (and (eq_attr "cpu" "!k6")
3841                         (eq_attr "alternative" "0"))
3842         (const_string "0")
3843         (const_string "1")))
3844    (set (attr "modrm")
3845      (if_then_else (eq_attr "prefix_0f" "0")
3846         (const_string "0")
3847         (const_string "1")))])
3848 \f
3849 ;; Conversions between float and double.
3850
3851 ;; These are all no-ops in the model used for the 80387.
3852 ;; So just emit moves.
3853
3854 ;; %%% Kill these when call knows how to work out a DFmode push earlier.
3855 (define_split
3856   [(set (match_operand:DF 0 "push_operand" "")
3857         (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3858   "reload_completed"
3859   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -8)))
3860    (set (mem:DF (reg:P SP_REG)) (float_extend:DF (match_dup 1)))])
3861
3862 (define_split
3863   [(set (match_operand:XF 0 "push_operand" "")
3864         (float_extend:XF (match_operand:MODEF 1 "fp_register_operand" "")))]
3865   "reload_completed"
3866   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
3867    (set (mem:XF (reg:P SP_REG)) (float_extend:XF (match_dup 1)))]
3868   "operands[2] = GEN_INT (-GET_MODE_SIZE (XFmode));")
3869
3870 (define_expand "extendsfdf2"
3871   [(set (match_operand:DF 0 "nonimmediate_operand" "")
3872         (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
3873   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3874 {
3875   /* ??? Needed for compress_float_constant since all fp constants
3876      are TARGET_LEGITIMATE_CONSTANT_P.  */
3877   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3878     {
3879       if ((!TARGET_SSE2 || TARGET_MIX_SSE_I387)
3880           && standard_80387_constant_p (operands[1]) > 0)
3881         {
3882           operands[1] = simplify_const_unary_operation
3883             (FLOAT_EXTEND, DFmode, operands[1], SFmode);
3884           emit_move_insn_1 (operands[0], operands[1]);
3885           DONE;
3886         }
3887       operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3888     }
3889 })
3890
3891 /* For converting SF(xmm2) to DF(xmm1), use the following code instead of
3892    cvtss2sd:
3893       unpcklps xmm2,xmm2   ; packed conversion might crash on signaling NaNs
3894       cvtps2pd xmm2,xmm1
3895    We do the conversion post reload to avoid producing of 128bit spills
3896    that might lead to ICE on 32bit target.  The sequence unlikely combine
3897    anyway.  */
3898 (define_split
3899   [(set (match_operand:DF 0 "register_operand" "")
3900         (float_extend:DF
3901           (match_operand:SF 1 "nonimmediate_operand" "")))]
3902   "TARGET_USE_VECTOR_FP_CONVERTS
3903    && optimize_insn_for_speed_p ()
3904    && reload_completed && SSE_REG_P (operands[0])"
3905    [(set (match_dup 2)
3906          (float_extend:V2DF
3907            (vec_select:V2SF
3908              (match_dup 3)
3909              (parallel [(const_int 0) (const_int 1)]))))]
3910 {
3911   operands[2] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
3912   operands[3] = simplify_gen_subreg (V4SFmode, operands[0], DFmode, 0);
3913   /* Use movss for loading from memory, unpcklps reg, reg for registers.
3914      Try to avoid move when unpacking can be done in source.  */
3915   if (REG_P (operands[1]))
3916     {
3917       /* If it is unsafe to overwrite upper half of source, we need
3918          to move to destination and unpack there.  */
3919       if ((ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
3920            || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 4)
3921           && true_regnum (operands[0]) != true_regnum (operands[1]))
3922         {
3923           rtx tmp = gen_rtx_REG (SFmode, true_regnum (operands[0]));
3924           emit_move_insn (tmp, operands[1]);
3925         }
3926       else
3927         operands[3] = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
3928       emit_insn (gen_vec_interleave_lowv4sf (operands[3], operands[3],
3929                                              operands[3]));
3930     }
3931   else
3932     emit_insn (gen_vec_setv4sf_0 (operands[3],
3933                                   CONST0_RTX (V4SFmode), operands[1]));
3934 })
3935
3936 (define_insn "*extendsfdf2_mixed"
3937   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m,x")
3938         (float_extend:DF
3939           (match_operand:SF 1 "nonimmediate_operand" "fm,f,xm")))]
3940   "TARGET_SSE2 && TARGET_MIX_SSE_I387"
3941 {
3942   switch (which_alternative)
3943     {
3944     case 0:
3945     case 1:
3946       return output_387_reg_move (insn, operands);
3947
3948     case 2:
3949       return "%vcvtss2sd\t{%1, %d0|%d0, %1}";
3950
3951     default:
3952       gcc_unreachable ();
3953     }
3954 }
3955   [(set_attr "type" "fmov,fmov,ssecvt")
3956    (set_attr "prefix" "orig,orig,maybe_vex")
3957    (set_attr "mode" "SF,XF,DF")])
3958
3959 (define_insn "*extendsfdf2_sse"
3960   [(set (match_operand:DF 0 "nonimmediate_operand" "=x")
3961         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
3962   "TARGET_SSE2 && TARGET_SSE_MATH"
3963   "%vcvtss2sd\t{%1, %d0|%d0, %1}"
3964   [(set_attr "type" "ssecvt")
3965    (set_attr "prefix" "maybe_vex")
3966    (set_attr "mode" "DF")])
3967
3968 (define_insn "*extendsfdf2_i387"
3969   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
3970         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3971   "TARGET_80387"
3972   "* return output_387_reg_move (insn, operands);"
3973   [(set_attr "type" "fmov")
3974    (set_attr "mode" "SF,XF")])
3975
3976 (define_expand "extend<mode>xf2"
3977   [(set (match_operand:XF 0 "nonimmediate_operand" "")
3978         (float_extend:XF (match_operand:MODEF 1 "general_operand" "")))]
3979   "TARGET_80387"
3980 {
3981   /* ??? Needed for compress_float_constant since all fp constants
3982      are TARGET_LEGITIMATE_CONSTANT_P.  */
3983   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3984     {
3985       if (standard_80387_constant_p (operands[1]) > 0)
3986         {
3987           operands[1] = simplify_const_unary_operation
3988             (FLOAT_EXTEND, XFmode, operands[1], <MODE>mode);
3989           emit_move_insn_1 (operands[0], operands[1]);
3990           DONE;
3991         }
3992       operands[1] = validize_mem (force_const_mem (<MODE>mode, operands[1]));
3993     }
3994 })
3995
3996 (define_insn "*extend<mode>xf2_i387"
3997   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3998         (float_extend:XF
3999           (match_operand:MODEF 1 "nonimmediate_operand" "fm,f")))]
4000   "TARGET_80387"
4001   "* return output_387_reg_move (insn, operands);"
4002   [(set_attr "type" "fmov")
4003    (set_attr "mode" "<MODE>,XF")])
4004
4005 ;; %%% This seems bad bad news.
4006 ;; This cannot output into an f-reg because there is no way to be sure
4007 ;; of truncating in that case.  Otherwise this is just like a simple move
4008 ;; insn.  So we pretend we can output to a reg in order to get better
4009 ;; register preferencing, but we really use a stack slot.
4010
4011 ;; Conversion from DFmode to SFmode.
4012
4013 (define_expand "truncdfsf2"
4014   [(set (match_operand:SF 0 "nonimmediate_operand" "")
4015         (float_truncate:SF
4016           (match_operand:DF 1 "nonimmediate_operand" "")))]
4017   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4018 {
4019   if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387)
4020     ;
4021   else if (flag_unsafe_math_optimizations)
4022     ;
4023   else
4024     {
4025       enum ix86_stack_slot slot = (virtuals_instantiated
4026                                    ? SLOT_TEMP
4027                                    : SLOT_VIRTUAL);
4028       rtx temp = assign_386_stack_local (SFmode, slot);
4029       emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp));
4030       DONE;
4031     }
4032 })
4033
4034 /* For converting DF(xmm2) to SF(xmm1), use the following code instead of
4035    cvtsd2ss:
4036       unpcklpd xmm2,xmm2   ; packed conversion might crash on signaling NaNs
4037       cvtpd2ps xmm2,xmm1
4038    We do the conversion post reload to avoid producing of 128bit spills
4039    that might lead to ICE on 32bit target.  The sequence unlikely combine
4040    anyway.  */
4041 (define_split
4042   [(set (match_operand:SF 0 "register_operand" "")
4043         (float_truncate:SF
4044           (match_operand:DF 1 "nonimmediate_operand" "")))]
4045   "TARGET_USE_VECTOR_FP_CONVERTS
4046    && optimize_insn_for_speed_p ()
4047    && reload_completed && SSE_REG_P (operands[0])"
4048    [(set (match_dup 2)
4049          (vec_concat:V4SF
4050            (float_truncate:V2SF
4051              (match_dup 4))
4052            (match_dup 3)))]
4053 {
4054   operands[2] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
4055   operands[3] = CONST0_RTX (V2SFmode);
4056   operands[4] = simplify_gen_subreg (V2DFmode, operands[0], SFmode, 0);
4057   /* Use movsd for loading from memory, unpcklpd for registers.
4058      Try to avoid move when unpacking can be done in source, or SSE3
4059      movddup is available.  */
4060   if (REG_P (operands[1]))
4061     {
4062       if (!TARGET_SSE3
4063           && true_regnum (operands[0]) != true_regnum (operands[1])
4064           && (ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
4065               || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 8))
4066         {
4067           rtx tmp = simplify_gen_subreg (DFmode, operands[0], SFmode, 0);
4068           emit_move_insn (tmp, operands[1]);
4069           operands[1] = tmp;
4070         }
4071       else if (!TARGET_SSE3)
4072         operands[4] = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
4073       emit_insn (gen_vec_dupv2df (operands[4], operands[1]));
4074     }
4075   else
4076     emit_insn (gen_sse2_loadlpd (operands[4],
4077                                  CONST0_RTX (V2DFmode), operands[1]));
4078 })
4079
4080 (define_expand "truncdfsf2_with_temp"
4081   [(parallel [(set (match_operand:SF 0 "" "")
4082                    (float_truncate:SF (match_operand:DF 1 "" "")))
4083               (clobber (match_operand:SF 2 "" ""))])])
4084
4085 (define_insn "*truncdfsf_fast_mixed"
4086   [(set (match_operand:SF 0 "nonimmediate_operand"   "=fm,x")
4087         (float_truncate:SF
4088           (match_operand:DF 1 "nonimmediate_operand" "f  ,xm")))]
4089   "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations"
4090 {
4091   switch (which_alternative)
4092     {
4093     case 0:
4094       return output_387_reg_move (insn, operands);
4095     case 1:
4096       return "%vcvtsd2ss\t{%1, %d0|%d0, %1}";
4097     default:
4098       gcc_unreachable ();
4099     }
4100 }
4101   [(set_attr "type" "fmov,ssecvt")
4102    (set_attr "prefix" "orig,maybe_vex")
4103    (set_attr "mode" "SF")])
4104
4105 ;; Yes, this one doesn't depend on flag_unsafe_math_optimizations,
4106 ;; because nothing we do here is unsafe.
4107 (define_insn "*truncdfsf_fast_sse"
4108   [(set (match_operand:SF 0 "nonimmediate_operand"   "=x")
4109         (float_truncate:SF
4110           (match_operand:DF 1 "nonimmediate_operand" "xm")))]
4111   "TARGET_SSE2 && TARGET_SSE_MATH"
4112   "%vcvtsd2ss\t{%1, %d0|%d0, %1}"
4113   [(set_attr "type" "ssecvt")
4114    (set_attr "prefix" "maybe_vex")
4115    (set_attr "mode" "SF")])
4116
4117 (define_insn "*truncdfsf_fast_i387"
4118   [(set (match_operand:SF 0 "nonimmediate_operand"   "=fm")
4119         (float_truncate:SF
4120           (match_operand:DF 1 "nonimmediate_operand" "f")))]
4121   "TARGET_80387 && flag_unsafe_math_optimizations"
4122   "* return output_387_reg_move (insn, operands);"
4123   [(set_attr "type" "fmov")
4124    (set_attr "mode" "SF")])
4125
4126 (define_insn "*truncdfsf_mixed"
4127   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,x ,?f,?x,?*r")
4128         (float_truncate:SF
4129           (match_operand:DF 1 "nonimmediate_operand" "f ,xm,f ,f ,f")))
4130    (clobber (match_operand:SF 2 "memory_operand"     "=X,X ,m ,m ,m"))]
4131   "TARGET_MIX_SSE_I387"
4132 {
4133   switch (which_alternative)
4134     {
4135     case 0:
4136       return output_387_reg_move (insn, operands);
4137     case 1:
4138       return "%vcvtsd2ss\t{%1, %d0|%d0, %1}";
4139
4140     default:
4141       return "#";
4142     }
4143 }
4144   [(set_attr "isa" "*,sse2,*,*,*")
4145    (set_attr "type" "fmov,ssecvt,multi,multi,multi")
4146    (set_attr "unit" "*,*,i387,i387,i387")
4147    (set_attr "prefix" "orig,maybe_vex,orig,orig,orig")
4148    (set_attr "mode" "SF")])
4149
4150 (define_insn "*truncdfsf_i387"
4151   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,?f,?x,?*r")
4152         (float_truncate:SF
4153           (match_operand:DF 1 "nonimmediate_operand" "f ,f ,f ,f")))
4154    (clobber (match_operand:SF 2 "memory_operand"     "=X,m ,m ,m"))]
4155   "TARGET_80387"
4156 {
4157   switch (which_alternative)
4158     {
4159     case 0:
4160       return output_387_reg_move (insn, operands);
4161
4162     default:
4163       return "#";
4164     }
4165 }
4166   [(set_attr "type" "fmov,multi,multi,multi")
4167    (set_attr "unit" "*,i387,i387,i387")
4168    (set_attr "mode" "SF")])
4169
4170 (define_insn "*truncdfsf2_i387_1"
4171   [(set (match_operand:SF 0 "memory_operand" "=m")
4172         (float_truncate:SF
4173           (match_operand:DF 1 "register_operand" "f")))]
4174   "TARGET_80387
4175    && !(TARGET_SSE2 && TARGET_SSE_MATH)
4176    && !TARGET_MIX_SSE_I387"
4177   "* return output_387_reg_move (insn, operands);"
4178   [(set_attr "type" "fmov")
4179    (set_attr "mode" "SF")])
4180
4181 (define_split
4182   [(set (match_operand:SF 0 "register_operand" "")
4183         (float_truncate:SF
4184          (match_operand:DF 1 "fp_register_operand" "")))
4185    (clobber (match_operand 2 "" ""))]
4186   "reload_completed"
4187   [(set (match_dup 2) (match_dup 1))
4188    (set (match_dup 0) (match_dup 2))]
4189   "operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1]));")
4190
4191 ;; Conversion from XFmode to {SF,DF}mode
4192
4193 (define_expand "truncxf<mode>2"
4194   [(parallel [(set (match_operand:MODEF 0 "nonimmediate_operand" "")
4195                    (float_truncate:MODEF
4196                      (match_operand:XF 1 "register_operand" "")))
4197               (clobber (match_dup 2))])]
4198   "TARGET_80387"
4199 {
4200   if (flag_unsafe_math_optimizations)
4201     {
4202       rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (<MODE>mode);
4203       emit_insn (gen_truncxf<mode>2_i387_noop (reg, operands[1]));
4204       if (reg != operands[0])
4205         emit_move_insn (operands[0], reg);
4206       DONE;
4207     }
4208   else
4209     {
4210       enum ix86_stack_slot slot = (virtuals_instantiated
4211                                    ? SLOT_TEMP
4212                                    : SLOT_VIRTUAL);
4213       operands[2] = assign_386_stack_local (<MODE>mode, slot);
4214     }
4215 })
4216
4217 (define_insn "*truncxfsf2_mixed"
4218   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f,?x,?*r")
4219         (float_truncate:SF
4220           (match_operand:XF 1 "register_operand"   "f ,f ,f ,f")))
4221    (clobber (match_operand:SF 2 "memory_operand"   "=X,m ,m ,m"))]
4222   "TARGET_80387"
4223 {
4224   gcc_assert (!which_alternative);
4225   return output_387_reg_move (insn, operands);
4226 }
4227   [(set_attr "type" "fmov,multi,multi,multi")
4228    (set_attr "unit" "*,i387,i387,i387")
4229    (set_attr "mode" "SF")])
4230
4231 (define_insn "*truncxfdf2_mixed"
4232   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f,?x,?*r")
4233         (float_truncate:DF
4234           (match_operand:XF 1 "register_operand"   "f ,f ,f  ,f")))
4235    (clobber (match_operand:DF 2 "memory_operand"   "=X,m ,m  ,m"))]
4236   "TARGET_80387"
4237 {
4238   gcc_assert (!which_alternative);
4239   return output_387_reg_move (insn, operands);
4240 }
4241   [(set_attr "isa" "*,*,sse2,*")
4242    (set_attr "type" "fmov,multi,multi,multi")
4243    (set_attr "unit" "*,i387,i387,i387")
4244    (set_attr "mode" "DF")])
4245
4246 (define_insn "truncxf<mode>2_i387_noop"
4247   [(set (match_operand:MODEF 0 "register_operand" "=f")
4248         (float_truncate:MODEF
4249           (match_operand:XF 1 "register_operand" "f")))]
4250   "TARGET_80387 && flag_unsafe_math_optimizations"
4251   "* return output_387_reg_move (insn, operands);"
4252   [(set_attr "type" "fmov")
4253    (set_attr "mode" "<MODE>")])
4254
4255 (define_insn "*truncxf<mode>2_i387"
4256   [(set (match_operand:MODEF 0 "memory_operand" "=m")
4257         (float_truncate:MODEF
4258           (match_operand:XF 1 "register_operand" "f")))]
4259   "TARGET_80387"
4260   "* return output_387_reg_move (insn, operands);"
4261   [(set_attr "type" "fmov")
4262    (set_attr "mode" "<MODE>")])
4263
4264 (define_split
4265   [(set (match_operand:MODEF 0 "register_operand" "")
4266         (float_truncate:MODEF
4267           (match_operand:XF 1 "register_operand" "")))
4268    (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4269   "TARGET_80387 && reload_completed"
4270   [(set (match_dup 2) (float_truncate:MODEF (match_dup 1)))
4271    (set (match_dup 0) (match_dup 2))])
4272
4273 (define_split
4274   [(set (match_operand:MODEF 0 "memory_operand" "")
4275         (float_truncate:MODEF
4276           (match_operand:XF 1 "register_operand" "")))
4277    (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4278   "TARGET_80387"
4279   [(set (match_dup 0) (float_truncate:MODEF (match_dup 1)))])
4280 \f
4281 ;; Signed conversion to DImode.
4282
4283 (define_expand "fix_truncxfdi2"
4284   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4285                    (fix:DI (match_operand:XF 1 "register_operand" "")))
4286               (clobber (reg:CC FLAGS_REG))])]
4287   "TARGET_80387"
4288 {
4289   if (TARGET_FISTTP)
4290    {
4291      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4292      DONE;
4293    }
4294 })
4295
4296 (define_expand "fix_trunc<mode>di2"
4297   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4298                    (fix:DI (match_operand:MODEF 1 "register_operand" "")))
4299               (clobber (reg:CC FLAGS_REG))])]
4300   "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))"
4301 {
4302   if (TARGET_FISTTP
4303       && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4304    {
4305      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4306      DONE;
4307    }
4308   if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))
4309    {
4310      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4311      emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1]));
4312      if (out != operands[0])
4313         emit_move_insn (operands[0], out);
4314      DONE;
4315    }
4316 })
4317
4318 ;; Signed conversion to SImode.
4319
4320 (define_expand "fix_truncxfsi2"
4321   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4322                    (fix:SI (match_operand:XF 1 "register_operand" "")))
4323               (clobber (reg:CC FLAGS_REG))])]
4324   "TARGET_80387"
4325 {
4326   if (TARGET_FISTTP)
4327    {
4328      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4329      DONE;
4330    }
4331 })
4332
4333 (define_expand "fix_trunc<mode>si2"
4334   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4335                    (fix:SI (match_operand:MODEF 1 "register_operand" "")))
4336               (clobber (reg:CC FLAGS_REG))])]
4337   "TARGET_80387 || SSE_FLOAT_MODE_P (<MODE>mode)"
4338 {
4339   if (TARGET_FISTTP
4340       && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4341    {
4342      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4343      DONE;
4344    }
4345   if (SSE_FLOAT_MODE_P (<MODE>mode))
4346    {
4347      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4348      emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1]));
4349      if (out != operands[0])
4350         emit_move_insn (operands[0], out);
4351      DONE;
4352    }
4353 })
4354
4355 ;; Signed conversion to HImode.
4356
4357 (define_expand "fix_trunc<mode>hi2"
4358   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4359                    (fix:HI (match_operand:X87MODEF 1 "register_operand" "")))
4360               (clobber (reg:CC FLAGS_REG))])]
4361   "TARGET_80387
4362    && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))"
4363 {
4364   if (TARGET_FISTTP)
4365    {
4366      emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1]));
4367      DONE;
4368    }
4369 })
4370
4371 ;; Unsigned conversion to SImode.
4372
4373 (define_expand "fixuns_trunc<mode>si2"
4374   [(parallel
4375     [(set (match_operand:SI 0 "register_operand" "")
4376           (unsigned_fix:SI
4377             (match_operand:MODEF 1 "nonimmediate_operand" "")))
4378      (use (match_dup 2))
4379      (clobber (match_scratch:<ssevecmode> 3 ""))
4380      (clobber (match_scratch:<ssevecmode> 4 ""))])]
4381   "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4382 {
4383   enum machine_mode mode = <MODE>mode;
4384   enum machine_mode vecmode = <ssevecmode>mode;
4385   REAL_VALUE_TYPE TWO31r;
4386   rtx two31;
4387
4388   if (optimize_insn_for_size_p ())
4389     FAIL;
4390
4391   real_ldexp (&TWO31r, &dconst1, 31);
4392   two31 = const_double_from_real_value (TWO31r, mode);
4393   two31 = ix86_build_const_vector (vecmode, true, two31);
4394   operands[2] = force_reg (vecmode, two31);
4395 })
4396
4397 (define_insn_and_split "*fixuns_trunc<mode>_1"
4398   [(set (match_operand:SI 0 "register_operand" "=&x,&x")
4399         (unsigned_fix:SI
4400           (match_operand:MODEF 3 "nonimmediate_operand" "xm,xm")))
4401    (use (match_operand:<ssevecmode> 4  "nonimmediate_operand" "m,x"))
4402    (clobber (match_scratch:<ssevecmode> 1 "=x,&x"))
4403    (clobber (match_scratch:<ssevecmode> 2 "=x,x"))]
4404   "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH
4405    && optimize_function_for_speed_p (cfun)"
4406   "#"
4407   "&& reload_completed"
4408   [(const_int 0)]
4409 {
4410   ix86_split_convert_uns_si_sse (operands);
4411   DONE;
4412 })
4413
4414 ;; Unsigned conversion to HImode.
4415 ;; Without these patterns, we'll try the unsigned SI conversion which
4416 ;; is complex for SSE, rather than the signed SI conversion, which isn't.
4417
4418 (define_expand "fixuns_trunc<mode>hi2"
4419   [(set (match_dup 2)
4420         (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "")))
4421    (set (match_operand:HI 0 "nonimmediate_operand" "")
4422         (subreg:HI (match_dup 2) 0))]
4423   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
4424   "operands[2] = gen_reg_rtx (SImode);")
4425
4426 ;; When SSE is available, it is always faster to use it!
4427 (define_insn "fix_trunc<mode>di_sse"
4428   [(set (match_operand:DI 0 "register_operand" "=r,r")
4429         (fix:DI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4430   "TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode)
4431    && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4432   "%vcvtt<ssemodesuffix>2si{q}\t{%1, %0|%0, %1}"
4433   [(set_attr "type" "sseicvt")
4434    (set_attr "prefix" "maybe_vex")
4435    (set_attr "prefix_rex" "1")
4436    (set_attr "mode" "<MODE>")
4437    (set_attr "athlon_decode" "double,vector")
4438    (set_attr "amdfam10_decode" "double,double")
4439    (set_attr "bdver1_decode" "double,double")])
4440
4441 (define_insn "fix_trunc<mode>si_sse"
4442   [(set (match_operand:SI 0 "register_operand" "=r,r")
4443         (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4444   "SSE_FLOAT_MODE_P (<MODE>mode)
4445    && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4446   "%vcvtt<ssemodesuffix>2si\t{%1, %0|%0, %1}"
4447   [(set_attr "type" "sseicvt")
4448    (set_attr "prefix" "maybe_vex")
4449    (set_attr "mode" "<MODE>")
4450    (set_attr "athlon_decode" "double,vector")
4451    (set_attr "amdfam10_decode" "double,double")
4452    (set_attr "bdver1_decode" "double,double")])
4453
4454 ;; Shorten x87->SSE reload sequences of fix_trunc?f?i_sse patterns.
4455 (define_peephole2
4456   [(set (match_operand:MODEF 0 "register_operand" "")
4457         (match_operand:MODEF 1 "memory_operand" ""))
4458    (set (match_operand:SWI48x 2 "register_operand" "")
4459         (fix:SWI48x (match_dup 0)))]
4460   "TARGET_SHORTEN_X87_SSE
4461    && !(TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ())
4462    && peep2_reg_dead_p (2, operands[0])"
4463   [(set (match_dup 2) (fix:SWI48x (match_dup 1)))])
4464
4465 ;; Avoid vector decoded forms of the instruction.
4466 (define_peephole2
4467   [(match_scratch:DF 2 "x")
4468    (set (match_operand:SWI48x 0 "register_operand" "")
4469         (fix:SWI48x (match_operand:DF 1 "memory_operand" "")))]
4470   "TARGET_SSE2 && TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ()"
4471   [(set (match_dup 2) (match_dup 1))
4472    (set (match_dup 0) (fix:SWI48x (match_dup 2)))])
4473
4474 (define_peephole2
4475   [(match_scratch:SF 2 "x")
4476    (set (match_operand:SWI48x 0 "register_operand" "")
4477         (fix:SWI48x (match_operand:SF 1 "memory_operand" "")))]
4478   "TARGET_AVOID_VECTOR_DECODE && optimize_insn_for_speed_p ()"
4479   [(set (match_dup 2) (match_dup 1))
4480    (set (match_dup 0) (fix:SWI48x (match_dup 2)))])
4481
4482 (define_insn_and_split "fix_trunc<mode>_fisttp_i387_1"
4483   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
4484         (fix:SWI248x (match_operand 1 "register_operand" "")))]
4485   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4486    && TARGET_FISTTP
4487    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4488          && (TARGET_64BIT || <MODE>mode != DImode))
4489         && TARGET_SSE_MATH)
4490    && can_create_pseudo_p ()"
4491   "#"
4492   "&& 1"
4493   [(const_int 0)]
4494 {
4495   if (memory_operand (operands[0], VOIDmode))
4496     emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1]));
4497   else
4498     {
4499       operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4500       emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0],
4501                                                             operands[1],
4502                                                             operands[2]));
4503     }
4504   DONE;
4505 }
4506   [(set_attr "type" "fisttp")
4507    (set_attr "mode" "<MODE>")])
4508
4509 (define_insn "fix_trunc<mode>_i387_fisttp"
4510   [(set (match_operand:SWI248x 0 "memory_operand" "=m")
4511         (fix:SWI248x (match_operand 1 "register_operand" "f")))
4512    (clobber (match_scratch:XF 2 "=&1f"))]
4513   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4514    && TARGET_FISTTP
4515    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4516          && (TARGET_64BIT || <MODE>mode != DImode))
4517         && TARGET_SSE_MATH)"
4518   "* return output_fix_trunc (insn, operands, true);"
4519   [(set_attr "type" "fisttp")
4520    (set_attr "mode" "<MODE>")])
4521
4522 (define_insn "fix_trunc<mode>_i387_fisttp_with_temp"
4523   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "=m,?r")
4524         (fix:SWI248x (match_operand 1 "register_operand" "f,f")))
4525    (clobber (match_operand:SWI248x 2 "memory_operand" "=X,m"))
4526    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
4527   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4528    && TARGET_FISTTP
4529    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4530         && (TARGET_64BIT || <MODE>mode != DImode))
4531         && TARGET_SSE_MATH)"
4532   "#"
4533   [(set_attr "type" "fisttp")
4534    (set_attr "mode" "<MODE>")])
4535
4536 (define_split
4537   [(set (match_operand:SWI248x 0 "register_operand" "")
4538         (fix:SWI248x (match_operand 1 "register_operand" "")))
4539    (clobber (match_operand:SWI248x 2 "memory_operand" ""))
4540    (clobber (match_scratch 3 ""))]
4541   "reload_completed"
4542   [(parallel [(set (match_dup 2) (fix:SWI248x (match_dup 1)))
4543               (clobber (match_dup 3))])
4544    (set (match_dup 0) (match_dup 2))])
4545
4546 (define_split
4547   [(set (match_operand:SWI248x 0 "memory_operand" "")
4548         (fix:SWI248x (match_operand 1 "register_operand" "")))
4549    (clobber (match_operand:SWI248x 2 "memory_operand" ""))
4550    (clobber (match_scratch 3 ""))]
4551   "reload_completed"
4552   [(parallel [(set (match_dup 0) (fix:SWI248x (match_dup 1)))
4553               (clobber (match_dup 3))])])
4554
4555 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4556 ;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control
4557 ;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG
4558 ;; clobbering insns can be used. Look at emit_i387_cw_initialization ()
4559 ;; function in i386.c.
4560 (define_insn_and_split "*fix_trunc<mode>_i387_1"
4561   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
4562         (fix:SWI248x (match_operand 1 "register_operand" "")))
4563    (clobber (reg:CC FLAGS_REG))]
4564   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4565    && !TARGET_FISTTP
4566    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4567          && (TARGET_64BIT || <MODE>mode != DImode))
4568    && can_create_pseudo_p ()"
4569   "#"
4570   "&& 1"
4571   [(const_int 0)]
4572 {
4573   ix86_optimize_mode_switching[I387_TRUNC] = 1;
4574
4575   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
4576   operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
4577   if (memory_operand (operands[0], VOIDmode))
4578     emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1],
4579                                          operands[2], operands[3]));
4580   else
4581     {
4582       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4583       emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1],
4584                                                      operands[2], operands[3],
4585                                                      operands[4]));
4586     }
4587   DONE;
4588 }
4589   [(set_attr "type" "fistp")
4590    (set_attr "i387_cw" "trunc")
4591    (set_attr "mode" "<MODE>")])
4592
4593 (define_insn "fix_truncdi_i387"
4594   [(set (match_operand:DI 0 "memory_operand" "=m")
4595         (fix:DI (match_operand 1 "register_operand" "f")))
4596    (use (match_operand:HI 2 "memory_operand" "m"))
4597    (use (match_operand:HI 3 "memory_operand" "m"))
4598    (clobber (match_scratch:XF 4 "=&1f"))]
4599   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4600    && !TARGET_FISTTP
4601    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4602   "* return output_fix_trunc (insn, operands, false);"
4603   [(set_attr "type" "fistp")
4604    (set_attr "i387_cw" "trunc")
4605    (set_attr "mode" "DI")])
4606
4607 (define_insn "fix_truncdi_i387_with_temp"
4608   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4609         (fix:DI (match_operand 1 "register_operand" "f,f")))
4610    (use (match_operand:HI 2 "memory_operand" "m,m"))
4611    (use (match_operand:HI 3 "memory_operand" "m,m"))
4612    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
4613    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
4614   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4615    && !TARGET_FISTTP
4616    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4617   "#"
4618   [(set_attr "type" "fistp")
4619    (set_attr "i387_cw" "trunc")
4620    (set_attr "mode" "DI")])
4621
4622 (define_split
4623   [(set (match_operand:DI 0 "register_operand" "")
4624         (fix:DI (match_operand 1 "register_operand" "")))
4625    (use (match_operand:HI 2 "memory_operand" ""))
4626    (use (match_operand:HI 3 "memory_operand" ""))
4627    (clobber (match_operand:DI 4 "memory_operand" ""))
4628    (clobber (match_scratch 5 ""))]
4629   "reload_completed"
4630   [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
4631               (use (match_dup 2))
4632               (use (match_dup 3))
4633               (clobber (match_dup 5))])
4634    (set (match_dup 0) (match_dup 4))])
4635
4636 (define_split
4637   [(set (match_operand:DI 0 "memory_operand" "")
4638         (fix:DI (match_operand 1 "register_operand" "")))
4639    (use (match_operand:HI 2 "memory_operand" ""))
4640    (use (match_operand:HI 3 "memory_operand" ""))
4641    (clobber (match_operand:DI 4 "memory_operand" ""))
4642    (clobber (match_scratch 5 ""))]
4643   "reload_completed"
4644   [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
4645               (use (match_dup 2))
4646               (use (match_dup 3))
4647               (clobber (match_dup 5))])])
4648
4649 (define_insn "fix_trunc<mode>_i387"
4650   [(set (match_operand:SWI24 0 "memory_operand" "=m")
4651         (fix:SWI24 (match_operand 1 "register_operand" "f")))
4652    (use (match_operand:HI 2 "memory_operand" "m"))
4653    (use (match_operand:HI 3 "memory_operand" "m"))]
4654   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4655    && !TARGET_FISTTP
4656    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4657   "* return output_fix_trunc (insn, operands, false);"
4658   [(set_attr "type" "fistp")
4659    (set_attr "i387_cw" "trunc")
4660    (set_attr "mode" "<MODE>")])
4661
4662 (define_insn "fix_trunc<mode>_i387_with_temp"
4663   [(set (match_operand:SWI24 0 "nonimmediate_operand" "=m,?r")
4664         (fix:SWI24 (match_operand 1 "register_operand" "f,f")))
4665    (use (match_operand:HI 2 "memory_operand" "m,m"))
4666    (use (match_operand:HI 3 "memory_operand" "m,m"))
4667    (clobber (match_operand:SWI24 4 "memory_operand" "=X,m"))]
4668   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4669    && !TARGET_FISTTP
4670    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4671   "#"
4672   [(set_attr "type" "fistp")
4673    (set_attr "i387_cw" "trunc")
4674    (set_attr "mode" "<MODE>")])
4675
4676 (define_split
4677   [(set (match_operand:SWI24 0 "register_operand" "")
4678         (fix:SWI24 (match_operand 1 "register_operand" "")))
4679    (use (match_operand:HI 2 "memory_operand" ""))
4680    (use (match_operand:HI 3 "memory_operand" ""))
4681    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
4682   "reload_completed"
4683   [(parallel [(set (match_dup 4) (fix:SWI24 (match_dup 1)))
4684               (use (match_dup 2))
4685               (use (match_dup 3))])
4686    (set (match_dup 0) (match_dup 4))])
4687
4688 (define_split
4689   [(set (match_operand:SWI24 0 "memory_operand" "")
4690         (fix:SWI24 (match_operand 1 "register_operand" "")))
4691    (use (match_operand:HI 2 "memory_operand" ""))
4692    (use (match_operand:HI 3 "memory_operand" ""))
4693    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
4694   "reload_completed"
4695   [(parallel [(set (match_dup 0) (fix:SWI24 (match_dup 1)))
4696               (use (match_dup 2))
4697               (use (match_dup 3))])])
4698
4699 (define_insn "x86_fnstcw_1"
4700   [(set (match_operand:HI 0 "memory_operand" "=m")
4701         (unspec:HI [(reg:HI FPCR_REG)] UNSPEC_FSTCW))]
4702   "TARGET_80387"
4703   "fnstcw\t%0"
4704   [(set (attr "length")
4705         (symbol_ref "ix86_attr_length_address_default (insn) + 2"))
4706    (set_attr "mode" "HI")
4707    (set_attr "unit" "i387")
4708    (set_attr "bdver1_decode" "vector")])
4709
4710 (define_insn "x86_fldcw_1"
4711   [(set (reg:HI FPCR_REG)
4712         (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
4713   "TARGET_80387"
4714   "fldcw\t%0"
4715   [(set (attr "length")
4716         (symbol_ref "ix86_attr_length_address_default (insn) + 2"))
4717    (set_attr "mode" "HI")
4718    (set_attr "unit" "i387")
4719    (set_attr "athlon_decode" "vector")
4720    (set_attr "amdfam10_decode" "vector")
4721    (set_attr "bdver1_decode" "vector")])
4722 \f
4723 ;; Conversion between fixed point and floating point.
4724
4725 ;; Even though we only accept memory inputs, the backend _really_
4726 ;; wants to be able to do this between registers.
4727
4728 (define_expand "floathi<mode>2"
4729   [(set (match_operand:X87MODEF 0 "register_operand" "")
4730         (float:X87MODEF (match_operand:HI 1 "nonimmediate_operand" "")))]
4731   "TARGET_80387
4732    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4733        || TARGET_MIX_SSE_I387)")
4734
4735 ;; Pre-reload splitter to add memory clobber to the pattern.
4736 (define_insn_and_split "*floathi<mode>2_1"
4737   [(set (match_operand:X87MODEF 0 "register_operand" "")
4738         (float:X87MODEF (match_operand:HI 1 "register_operand" "")))]
4739   "TARGET_80387
4740    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4741        || TARGET_MIX_SSE_I387)
4742    && can_create_pseudo_p ()"
4743   "#"
4744   "&& 1"
4745   [(parallel [(set (match_dup 0)
4746               (float:X87MODEF (match_dup 1)))
4747    (clobber (match_dup 2))])]
4748   "operands[2] = assign_386_stack_local (HImode, SLOT_TEMP);")
4749
4750 (define_insn "*floathi<mode>2_i387_with_temp"
4751   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
4752         (float:X87MODEF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))
4753   (clobber (match_operand:HI 2 "memory_operand" "=m,m"))]
4754   "TARGET_80387
4755    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4756        || TARGET_MIX_SSE_I387)"
4757   "#"
4758   [(set_attr "type" "fmov,multi")
4759    (set_attr "mode" "<MODE>")
4760    (set_attr "unit" "*,i387")
4761    (set_attr "fp_int_src" "true")])
4762
4763 (define_insn "*floathi<mode>2_i387"
4764   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
4765         (float:X87MODEF (match_operand:HI 1 "memory_operand" "m")))]
4766   "TARGET_80387
4767    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4768        || TARGET_MIX_SSE_I387)"
4769   "fild%Z1\t%1"
4770   [(set_attr "type" "fmov")
4771    (set_attr "mode" "<MODE>")
4772    (set_attr "fp_int_src" "true")])
4773
4774 (define_split
4775   [(set (match_operand:X87MODEF 0 "register_operand" "")
4776         (float:X87MODEF (match_operand:HI 1 "register_operand" "")))
4777    (clobber (match_operand:HI 2 "memory_operand" ""))]
4778   "TARGET_80387
4779    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4780        || TARGET_MIX_SSE_I387)
4781    && reload_completed"
4782   [(set (match_dup 2) (match_dup 1))
4783    (set (match_dup 0) (float:X87MODEF (match_dup 2)))])
4784
4785 (define_split
4786   [(set (match_operand:X87MODEF 0 "register_operand" "")
4787         (float:X87MODEF (match_operand:HI 1 "memory_operand" "")))
4788    (clobber (match_operand:HI 2 "memory_operand" ""))]
4789    "TARGET_80387
4790     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4791         || TARGET_MIX_SSE_I387)
4792     && reload_completed"
4793   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))])
4794
4795 (define_expand "float<SWI48x:mode><X87MODEF:mode>2"
4796   [(set (match_operand:X87MODEF 0 "register_operand" "")
4797         (float:X87MODEF
4798           (match_operand:SWI48x 1 "nonimmediate_operand" "")))]
4799   "TARGET_80387
4800    || ((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4801        && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)"
4802 {
4803   if (!((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4804         && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
4805       && !X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode))
4806     {
4807       rtx reg = gen_reg_rtx (XFmode);
4808       rtx (*insn)(rtx, rtx);
4809
4810       emit_insn (gen_float<SWI48x:mode>xf2 (reg, operands[1]));
4811
4812       if (<X87MODEF:MODE>mode == SFmode)
4813         insn = gen_truncxfsf2;
4814       else if (<X87MODEF:MODE>mode == DFmode)
4815         insn = gen_truncxfdf2;
4816       else
4817         gcc_unreachable ();
4818
4819       emit_insn (insn (operands[0], reg));
4820       DONE;
4821     }
4822 })
4823
4824 ;; Pre-reload splitter to add memory clobber to the pattern.
4825 (define_insn_and_split "*float<SWI48x:mode><X87MODEF:mode>2_1"
4826   [(set (match_operand:X87MODEF 0 "register_operand" "")
4827         (float:X87MODEF (match_operand:SWI48x 1 "register_operand" "")))]
4828   "((TARGET_80387
4829      && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)
4830      && (!((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4831            && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
4832          || TARGET_MIX_SSE_I387))
4833     || ((<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4834         && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
4835         && ((<SWI48x:MODE>mode == SImode
4836              && TARGET_SSE2 && TARGET_USE_VECTOR_CONVERTS
4837              && optimize_function_for_speed_p (cfun)
4838              && flag_trapping_math)
4839             || !(TARGET_INTER_UNIT_CONVERSIONS
4840                  || optimize_function_for_size_p (cfun)))))
4841    && can_create_pseudo_p ()"
4842   "#"
4843   "&& 1"
4844   [(parallel [(set (match_dup 0) (float:X87MODEF (match_dup 1)))
4845               (clobber (match_dup 2))])]
4846 {
4847   operands[2] = assign_386_stack_local (<SWI48x:MODE>mode, SLOT_TEMP);
4848
4849   /* Avoid store forwarding (partial memory) stall penalty
4850      by passing DImode value through XMM registers.  */
4851   if (<SWI48x:MODE>mode == DImode && !TARGET_64BIT
4852       && TARGET_80387 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
4853       && optimize_function_for_speed_p (cfun))
4854     {
4855       emit_insn (gen_floatdi<X87MODEF:mode>2_i387_with_xmm (operands[0],
4856                                                             operands[1],
4857                                                             operands[2]));
4858       DONE;
4859     }
4860 })
4861
4862 (define_insn "*floatsi<mode>2_vector_mixed_with_temp"
4863   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x,x")
4864         (float:MODEF
4865           (match_operand:SI 1 "nonimmediate_operand" "m,?r,r,m,!x")))
4866    (clobber (match_operand:SI 2 "memory_operand" "=X,m,m,X,m"))]
4867   "TARGET_SSE2 && TARGET_MIX_SSE_I387
4868    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4869   "#"
4870   [(set_attr "type" "fmov,multi,sseicvt,sseicvt,sseicvt")
4871    (set_attr "mode" "<MODE>,<MODE>,<MODE>,<MODE>,<ssevecmode>")
4872    (set_attr "unit" "*,i387,*,*,*")
4873    (set_attr "athlon_decode" "*,*,double,direct,double")
4874    (set_attr "amdfam10_decode" "*,*,vector,double,double")
4875    (set_attr "bdver1_decode" "*,*,double,direct,double")
4876    (set_attr "fp_int_src" "true")])
4877
4878 (define_insn "*floatsi<mode>2_vector_mixed"
4879   [(set (match_operand:MODEF 0 "register_operand" "=f,x")
4880         (float:MODEF (match_operand:SI 1 "memory_operand" "m,m")))]
4881   "TARGET_SSE2 && TARGET_MIX_SSE_I387
4882    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4883   "@
4884    fild%Z1\t%1
4885    #"
4886   [(set_attr "type" "fmov,sseicvt")
4887    (set_attr "mode" "<MODE>,<ssevecmode>")
4888    (set_attr "unit" "i387,*")
4889    (set_attr "athlon_decode" "*,direct")
4890    (set_attr "amdfam10_decode" "*,double")
4891    (set_attr "bdver1_decode" "*,direct")
4892    (set_attr "fp_int_src" "true")])
4893
4894 (define_insn "*float<SWI48x:mode><MODEF:mode>2_mixed_with_temp"
4895   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x")
4896         (float:MODEF
4897           (match_operand:SWI48x 1 "nonimmediate_operand" "m,?r,r,m")))
4898    (clobber (match_operand:SWI48x 2 "memory_operand" "=X,m,m,X"))]
4899   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4900    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387"
4901   "#"
4902   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4903    (set_attr "mode" "<MODEF:MODE>")
4904    (set_attr "unit" "*,i387,*,*")
4905    (set_attr "athlon_decode" "*,*,double,direct")
4906    (set_attr "amdfam10_decode" "*,*,vector,double")
4907    (set_attr "bdver1_decode" "*,*,double,direct")
4908    (set_attr "fp_int_src" "true")])
4909
4910 (define_split
4911   [(set (match_operand:MODEF 0 "register_operand" "")
4912         (float:MODEF (match_operand:SWI48x 1 "register_operand" "")))
4913    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
4914   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4915    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4916    && TARGET_INTER_UNIT_CONVERSIONS
4917    && reload_completed
4918    && (SSE_REG_P (operands[0])
4919        || (GET_CODE (operands[0]) == SUBREG
4920            && SSE_REG_P (operands[0])))"
4921   [(set (match_dup 0) (float:MODEF (match_dup 1)))])
4922
4923 (define_split
4924   [(set (match_operand:MODEF 0 "register_operand" "")
4925         (float:MODEF (match_operand:SWI48x 1 "register_operand" "")))
4926    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
4927   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4928    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4929    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
4930    && reload_completed
4931    && (SSE_REG_P (operands[0])
4932        || (GET_CODE (operands[0]) == SUBREG
4933            && SSE_REG_P (operands[0])))"
4934   [(set (match_dup 2) (match_dup 1))
4935    (set (match_dup 0) (float:MODEF (match_dup 2)))])
4936
4937 (define_insn "*float<SWI48x:mode><MODEF:mode>2_mixed_interunit"
4938   [(set (match_operand:MODEF 0 "register_operand" "=f,x,x")
4939         (float:MODEF
4940           (match_operand:SWI48x 1 "nonimmediate_operand" "m,r,m")))]
4941   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4942    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4943    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
4944   "@
4945    fild%Z1\t%1
4946    %vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}
4947    %vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
4948   [(set_attr "type" "fmov,sseicvt,sseicvt")
4949    (set_attr "prefix" "orig,maybe_vex,maybe_vex")
4950    (set_attr "mode" "<MODEF:MODE>")
4951    (set (attr "prefix_rex")
4952      (if_then_else
4953        (and (eq_attr "prefix" "maybe_vex")
4954             (match_test "<SWI48x:MODE>mode == DImode"))
4955        (const_string "1")
4956        (const_string "*")))
4957    (set_attr "unit" "i387,*,*")
4958    (set_attr "athlon_decode" "*,double,direct")
4959    (set_attr "amdfam10_decode" "*,vector,double")
4960    (set_attr "bdver1_decode" "*,double,direct")
4961    (set_attr "fp_int_src" "true")])
4962
4963 (define_insn "*float<SWI48x:mode><MODEF:mode>2_mixed_nointerunit"
4964   [(set (match_operand:MODEF 0 "register_operand" "=f,x")
4965         (float:MODEF
4966           (match_operand:SWI48x 1 "memory_operand" "m,m")))]
4967   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
4968    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4969    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
4970   "@
4971    fild%Z1\t%1
4972    %vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
4973   [(set_attr "type" "fmov,sseicvt")
4974    (set_attr "prefix" "orig,maybe_vex")
4975    (set_attr "mode" "<MODEF:MODE>")
4976    (set (attr "prefix_rex")
4977      (if_then_else
4978        (and (eq_attr "prefix" "maybe_vex")
4979             (match_test "<SWI48x:MODE>mode == DImode"))
4980        (const_string "1")
4981        (const_string "*")))
4982    (set_attr "athlon_decode" "*,direct")
4983    (set_attr "amdfam10_decode" "*,double")
4984    (set_attr "bdver1_decode" "*,direct")
4985    (set_attr "fp_int_src" "true")])
4986
4987 (define_insn "*floatsi<mode>2_vector_sse_with_temp"
4988   [(set (match_operand:MODEF 0 "register_operand" "=x,x,x")
4989         (float:MODEF
4990           (match_operand:SI 1 "nonimmediate_operand" "r,m,!x")))
4991    (clobber (match_operand:SI 2 "memory_operand" "=m,X,m"))]
4992   "TARGET_SSE2 && TARGET_SSE_MATH
4993    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
4994   "#"
4995   [(set_attr "type" "sseicvt")
4996    (set_attr "mode" "<MODE>,<MODE>,<ssevecmode>")
4997    (set_attr "athlon_decode" "double,direct,double")
4998    (set_attr "amdfam10_decode" "vector,double,double")
4999    (set_attr "bdver1_decode" "double,direct,double")
5000    (set_attr "fp_int_src" "true")])
5001
5002 (define_insn "*floatsi<mode>2_vector_sse"
5003   [(set (match_operand:MODEF 0 "register_operand" "=x")
5004         (float:MODEF (match_operand:SI 1 "memory_operand" "m")))]
5005   "TARGET_SSE2 && TARGET_SSE_MATH
5006    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)"
5007   "#"
5008   [(set_attr "type" "sseicvt")
5009    (set_attr "mode" "<MODE>")
5010    (set_attr "athlon_decode" "direct")
5011    (set_attr "amdfam10_decode" "double")
5012    (set_attr "bdver1_decode" "direct")
5013    (set_attr "fp_int_src" "true")])
5014
5015 (define_split
5016   [(set (match_operand:MODEF 0 "register_operand" "")
5017         (float:MODEF (match_operand:SI 1 "register_operand" "")))
5018    (clobber (match_operand:SI 2 "memory_operand" ""))]
5019   "TARGET_SSE2 && TARGET_SSE_MATH
5020    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5021    && reload_completed
5022    && (SSE_REG_P (operands[0])
5023        || (GET_CODE (operands[0]) == SUBREG
5024            && SSE_REG_P (operands[0])))"
5025   [(const_int 0)]
5026 {
5027   rtx op1 = operands[1];
5028
5029   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5030                                      <MODE>mode, 0);
5031   if (GET_CODE (op1) == SUBREG)
5032     op1 = SUBREG_REG (op1);
5033
5034   if (GENERAL_REG_P (op1) && TARGET_INTER_UNIT_MOVES)
5035     {
5036       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5037       emit_insn (gen_sse2_loadld (operands[4],
5038                                   CONST0_RTX (V4SImode), operands[1]));
5039     }
5040   /* We can ignore possible trapping value in the
5041      high part of SSE register for non-trapping math. */
5042   else if (SSE_REG_P (op1) && !flag_trapping_math)
5043     operands[4] = simplify_gen_subreg (V4SImode, operands[1], SImode, 0);
5044   else
5045     {
5046       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5047       emit_move_insn (operands[2], operands[1]);
5048       emit_insn (gen_sse2_loadld (operands[4],
5049                                   CONST0_RTX (V4SImode), operands[2]));
5050     }
5051   emit_insn
5052     (gen_sse2_cvtdq2<ssevecmodesuffix> (operands[3], operands[4]));
5053   DONE;
5054 })
5055
5056 (define_split
5057   [(set (match_operand:MODEF 0 "register_operand" "")
5058         (float:MODEF (match_operand:SI 1 "memory_operand" "")))
5059    (clobber (match_operand:SI 2 "memory_operand" ""))]
5060   "TARGET_SSE2 && TARGET_SSE_MATH
5061    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5062    && reload_completed
5063    && (SSE_REG_P (operands[0])
5064        || (GET_CODE (operands[0]) == SUBREG
5065            && SSE_REG_P (operands[0])))"
5066   [(const_int 0)]
5067 {
5068   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5069                                      <MODE>mode, 0);
5070   operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5071
5072   emit_insn (gen_sse2_loadld (operands[4],
5073                               CONST0_RTX (V4SImode), operands[1]));
5074   emit_insn
5075     (gen_sse2_cvtdq2<ssevecmodesuffix> (operands[3], operands[4]));
5076   DONE;
5077 })
5078
5079 (define_split
5080   [(set (match_operand:MODEF 0 "register_operand" "")
5081         (float:MODEF (match_operand:SI 1 "register_operand" "")))]
5082   "TARGET_SSE2 && TARGET_SSE_MATH
5083    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5084    && reload_completed
5085    && (SSE_REG_P (operands[0])
5086        || (GET_CODE (operands[0]) == SUBREG
5087            && SSE_REG_P (operands[0])))"
5088   [(const_int 0)]
5089 {
5090   rtx op1 = operands[1];
5091
5092   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5093                                      <MODE>mode, 0);
5094   if (GET_CODE (op1) == SUBREG)
5095     op1 = SUBREG_REG (op1);
5096
5097   if (GENERAL_REG_P (op1))
5098     {
5099       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5100       if (TARGET_INTER_UNIT_MOVES)
5101         emit_insn (gen_sse2_loadld (operands[4],
5102                                     CONST0_RTX (V4SImode), operands[1]));
5103       else
5104         {
5105           operands[5] = ix86_force_to_memory (GET_MODE (operands[1]),
5106                                               operands[1]);
5107           emit_insn (gen_sse2_loadld (operands[4],
5108                                       CONST0_RTX (V4SImode), operands[5]));
5109           ix86_free_from_memory (GET_MODE (operands[1]));
5110         }
5111     }
5112   /* We can ignore possible trapping value in the
5113      high part of SSE register for non-trapping math. */
5114   else if (SSE_REG_P (op1) && !flag_trapping_math)
5115     operands[4] = simplify_gen_subreg (V4SImode, operands[1], SImode, 0);
5116   else
5117     gcc_unreachable ();
5118   emit_insn
5119     (gen_sse2_cvtdq2<ssevecmodesuffix> (operands[3], operands[4]));
5120   DONE;
5121 })
5122
5123 (define_split
5124   [(set (match_operand:MODEF 0 "register_operand" "")
5125         (float:MODEF (match_operand:SI 1 "memory_operand" "")))]
5126   "TARGET_SSE2 && TARGET_SSE_MATH
5127    && TARGET_USE_VECTOR_CONVERTS && optimize_function_for_speed_p (cfun)
5128    && reload_completed
5129    && (SSE_REG_P (operands[0])
5130        || (GET_CODE (operands[0]) == SUBREG
5131            && SSE_REG_P (operands[0])))"
5132   [(const_int 0)]
5133 {
5134   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5135                                      <MODE>mode, 0);
5136   operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5137
5138   emit_insn (gen_sse2_loadld (operands[4],
5139                               CONST0_RTX (V4SImode), operands[1]));
5140   emit_insn
5141     (gen_sse2_cvtdq2<ssevecmodesuffix> (operands[3], operands[4]));
5142   DONE;
5143 })
5144
5145 (define_insn "*float<SWI48x:mode><MODEF:mode>2_sse_with_temp"
5146   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
5147         (float:MODEF
5148           (match_operand:SWI48x 1 "nonimmediate_operand" "r,m")))
5149   (clobber (match_operand:SWI48x 2 "memory_operand" "=m,X"))]
5150   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5151    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH"
5152   "#"
5153   [(set_attr "type" "sseicvt")
5154    (set_attr "mode" "<MODEF:MODE>")
5155    (set_attr "athlon_decode" "double,direct")
5156    (set_attr "amdfam10_decode" "vector,double")
5157    (set_attr "bdver1_decode" "double,direct")
5158    (set_attr "fp_int_src" "true")])
5159
5160 (define_insn "*float<SWI48x:mode><MODEF:mode>2_sse_interunit"
5161   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
5162         (float:MODEF
5163           (match_operand:SWI48x 1 "nonimmediate_operand" "r,m")))]
5164   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5165    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5166    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
5167   "%vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
5168   [(set_attr "type" "sseicvt")
5169    (set_attr "prefix" "maybe_vex")
5170    (set_attr "mode" "<MODEF:MODE>")
5171    (set (attr "prefix_rex")
5172      (if_then_else
5173        (and (eq_attr "prefix" "maybe_vex")
5174             (match_test "<SWI48x:MODE>mode == DImode"))
5175        (const_string "1")
5176        (const_string "*")))
5177    (set_attr "athlon_decode" "double,direct")
5178    (set_attr "amdfam10_decode" "vector,double")
5179    (set_attr "bdver1_decode" "double,direct")
5180    (set_attr "fp_int_src" "true")])
5181
5182 (define_split
5183   [(set (match_operand:MODEF 0 "register_operand" "")
5184         (float:MODEF (match_operand:SWI48x 1 "nonimmediate_operand" "")))
5185    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5186   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5187    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5188    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
5189    && reload_completed
5190    && (SSE_REG_P (operands[0])
5191        || (GET_CODE (operands[0]) == SUBREG
5192            && SSE_REG_P (operands[0])))"
5193   [(set (match_dup 0) (float:MODEF (match_dup 1)))])
5194
5195 (define_insn "*float<SWI48x:mode><MODEF:mode>2_sse_nointerunit"
5196   [(set (match_operand:MODEF 0 "register_operand" "=x")
5197         (float:MODEF
5198           (match_operand:SWI48x 1 "memory_operand" "m")))]
5199   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5200    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5201    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))"
5202   "%vcvtsi2<MODEF:ssemodesuffix><SWI48x:rex64suffix>\t{%1, %d0|%d0, %1}"
5203   [(set_attr "type" "sseicvt")
5204    (set_attr "prefix" "maybe_vex")
5205    (set_attr "mode" "<MODEF:MODE>")
5206    (set (attr "prefix_rex")
5207      (if_then_else
5208        (and (eq_attr "prefix" "maybe_vex")
5209             (match_test "<SWI48x:MODE>mode == DImode"))
5210        (const_string "1")
5211        (const_string "*")))
5212    (set_attr "athlon_decode" "direct")
5213    (set_attr "amdfam10_decode" "double")
5214    (set_attr "bdver1_decode" "direct")
5215    (set_attr "fp_int_src" "true")])
5216
5217 (define_split
5218   [(set (match_operand:MODEF 0 "register_operand" "")
5219         (float:MODEF (match_operand:SWI48x 1 "register_operand" "")))
5220    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5221   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5222    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5223    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_function_for_size_p (cfun))
5224    && reload_completed
5225    && (SSE_REG_P (operands[0])
5226        || (GET_CODE (operands[0]) == SUBREG
5227            && SSE_REG_P (operands[0])))"
5228   [(set (match_dup 2) (match_dup 1))
5229    (set (match_dup 0) (float:MODEF (match_dup 2)))])
5230
5231 (define_split
5232   [(set (match_operand:MODEF 0 "register_operand" "")
5233         (float:MODEF (match_operand:SWI48x 1 "memory_operand" "")))
5234    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5235   "(<SWI48x:MODE>mode != DImode || TARGET_64BIT)
5236    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5237    && reload_completed
5238    && (SSE_REG_P (operands[0])
5239        || (GET_CODE (operands[0]) == SUBREG
5240            && SSE_REG_P (operands[0])))"
5241   [(set (match_dup 0) (float:MODEF (match_dup 1)))])
5242
5243 (define_insn "*float<SWI48x:mode><X87MODEF:mode>2_i387_with_temp"
5244   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5245         (float:X87MODEF
5246           (match_operand:SWI48x 1 "nonimmediate_operand" "m,?r")))
5247   (clobber (match_operand:SWI48x 2 "memory_operand" "=X,m"))]
5248   "TARGET_80387
5249    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)"
5250   "@
5251    fild%Z1\t%1
5252    #"
5253   [(set_attr "type" "fmov,multi")
5254    (set_attr "mode" "<X87MODEF:MODE>")
5255    (set_attr "unit" "*,i387")
5256    (set_attr "fp_int_src" "true")])
5257
5258 (define_insn "*float<SWI48x:mode><X87MODEF:mode>2_i387"
5259   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
5260         (float:X87MODEF
5261           (match_operand:SWI48x 1 "memory_operand" "m")))]
5262   "TARGET_80387
5263    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)"
5264   "fild%Z1\t%1"
5265   [(set_attr "type" "fmov")
5266    (set_attr "mode" "<X87MODEF:MODE>")
5267    (set_attr "fp_int_src" "true")])
5268
5269 (define_split
5270   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5271         (float:X87MODEF (match_operand:SWI48x 1 "register_operand" "")))
5272    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5273   "TARGET_80387
5274    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)
5275    && reload_completed"
5276   [(set (match_dup 2) (match_dup 1))
5277    (set (match_dup 0) (float:X87MODEF (match_dup 2)))])
5278
5279 (define_split
5280   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5281         (float:X87MODEF (match_operand:SWI48x 1 "memory_operand" "")))
5282    (clobber (match_operand:SWI48x 2 "memory_operand" ""))]
5283   "TARGET_80387
5284    && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, <SWI48x:MODE>mode)
5285    && reload_completed"
5286   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))])
5287
5288 ;; Avoid store forwarding (partial memory) stall penalty
5289 ;; by passing DImode value through XMM registers.  */
5290
5291 (define_insn "floatdi<X87MODEF:mode>2_i387_with_xmm"
5292   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5293         (float:X87MODEF
5294           (match_operand:DI 1 "nonimmediate_operand" "m,?r")))
5295    (clobber (match_scratch:V4SI 3 "=X,x"))
5296    (clobber (match_scratch:V4SI 4 "=X,x"))
5297    (clobber (match_operand:DI 2 "memory_operand" "=X,m"))]
5298   "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5299    && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5300    && !TARGET_64BIT && optimize_function_for_speed_p (cfun)"
5301   "#"
5302   [(set_attr "type" "multi")
5303    (set_attr "mode" "<X87MODEF:MODE>")
5304    (set_attr "unit" "i387")
5305    (set_attr "fp_int_src" "true")])
5306
5307 (define_split
5308   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5309         (float:X87MODEF (match_operand:DI 1 "register_operand" "")))
5310    (clobber (match_scratch:V4SI 3 ""))
5311    (clobber (match_scratch:V4SI 4 ""))
5312    (clobber (match_operand:DI 2 "memory_operand" ""))]
5313   "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5314    && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5315    && !TARGET_64BIT && optimize_function_for_speed_p (cfun)
5316    && reload_completed"
5317   [(set (match_dup 2) (match_dup 3))
5318    (set (match_dup 0) (float:X87MODEF (match_dup 2)))]
5319 {
5320   /* The DImode arrived in a pair of integral registers (e.g. %edx:%eax).
5321      Assemble the 64-bit DImode value in an xmm register.  */
5322   emit_insn (gen_sse2_loadld (operands[3], CONST0_RTX (V4SImode),
5323                               gen_rtx_SUBREG (SImode, operands[1], 0)));
5324   emit_insn (gen_sse2_loadld (operands[4], CONST0_RTX (V4SImode),
5325                               gen_rtx_SUBREG (SImode, operands[1], 4)));
5326   emit_insn (gen_vec_interleave_lowv4si (operands[3], operands[3],
5327                                          operands[4]));
5328
5329   operands[3] = gen_rtx_REG (DImode, REGNO (operands[3]));
5330 })
5331
5332 (define_split
5333   [(set (match_operand:X87MODEF 0 "fp_register_operand" "")
5334         (float:X87MODEF (match_operand:DI 1 "memory_operand" "")))
5335    (clobber (match_scratch:V4SI 3 ""))
5336    (clobber (match_scratch:V4SI 4 ""))
5337    (clobber (match_operand:DI 2 "memory_operand" ""))]
5338   "TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5339    && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5340    && !TARGET_64BIT && optimize_function_for_speed_p (cfun)
5341    && reload_completed"
5342   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))])
5343
5344 ;; Avoid store forwarding (partial memory) stall penalty by extending
5345 ;; SImode value to DImode through XMM register instead of pushing two
5346 ;; SImode values to stack. Note that even !TARGET_INTER_UNIT_MOVES
5347 ;; targets benefit from this optimization. Also note that fild
5348 ;; loads from memory only.
5349
5350 (define_insn "*floatunssi<mode>2_1"
5351   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5352         (unsigned_float:X87MODEF
5353           (match_operand:SI 1 "nonimmediate_operand" "x,m")))
5354    (clobber (match_operand:DI 2 "memory_operand" "=m,m"))
5355    (clobber (match_scratch:SI 3 "=X,x"))]
5356   "!TARGET_64BIT
5357    && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5358    && TARGET_SSE"
5359   "#"
5360   [(set_attr "type" "multi")
5361    (set_attr "mode" "<MODE>")])
5362
5363 (define_split
5364   [(set (match_operand:X87MODEF 0 "register_operand" "")
5365         (unsigned_float:X87MODEF
5366           (match_operand:SI 1 "register_operand" "")))
5367    (clobber (match_operand:DI 2 "memory_operand" ""))
5368    (clobber (match_scratch:SI 3 ""))]
5369   "!TARGET_64BIT
5370    && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5371    && TARGET_SSE
5372    && reload_completed"
5373   [(set (match_dup 2) (match_dup 1))
5374    (set (match_dup 0)
5375         (float:X87MODEF (match_dup 2)))]
5376   "operands[1] = simplify_gen_subreg (DImode, operands[1], SImode, 0);")
5377
5378 (define_split
5379   [(set (match_operand:X87MODEF 0 "register_operand" "")
5380         (unsigned_float:X87MODEF
5381           (match_operand:SI 1 "memory_operand" "")))
5382    (clobber (match_operand:DI 2 "memory_operand" ""))
5383    (clobber (match_scratch:SI 3 ""))]
5384   "!TARGET_64BIT
5385    && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5386    && TARGET_SSE
5387    && reload_completed"
5388   [(set (match_dup 2) (match_dup 3))
5389    (set (match_dup 0)
5390         (float:X87MODEF (match_dup 2)))]
5391 {
5392   emit_move_insn (operands[3], operands[1]);
5393   operands[3] = simplify_gen_subreg (DImode, operands[3], SImode, 0);
5394 })
5395
5396 (define_expand "floatunssi<mode>2"
5397   [(parallel
5398      [(set (match_operand:X87MODEF 0 "register_operand" "")
5399            (unsigned_float:X87MODEF
5400              (match_operand:SI 1 "nonimmediate_operand" "")))
5401       (clobber (match_dup 2))
5402       (clobber (match_scratch:SI 3 ""))])]
5403   "!TARGET_64BIT
5404    && ((TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode)
5405         && TARGET_SSE)
5406        || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
5407 {
5408   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5409     {
5410       ix86_expand_convert_uns_si<mode>_sse (operands[0], operands[1]);
5411       DONE;
5412     }
5413   else
5414     {
5415       enum ix86_stack_slot slot = (virtuals_instantiated
5416                                    ? SLOT_TEMP
5417                                    : SLOT_VIRTUAL);
5418       operands[2] = assign_386_stack_local (DImode, slot);
5419     }
5420 })
5421
5422 (define_expand "floatunsdisf2"
5423   [(use (match_operand:SF 0 "register_operand" ""))
5424    (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5425   "TARGET_64BIT && TARGET_SSE_MATH"
5426   "x86_emit_floatuns (operands); DONE;")
5427
5428 (define_expand "floatunsdidf2"
5429   [(use (match_operand:DF 0 "register_operand" ""))
5430    (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5431   "(TARGET_64BIT || TARGET_KEEPS_VECTOR_ALIGNED_STACK)
5432    && TARGET_SSE2 && TARGET_SSE_MATH"
5433 {
5434   if (TARGET_64BIT)
5435     x86_emit_floatuns (operands);
5436   else
5437     ix86_expand_convert_uns_didf_sse (operands[0], operands[1]);
5438   DONE;
5439 })
5440 \f
5441 ;; Add instructions
5442
5443 (define_expand "add<mode>3"
5444   [(set (match_operand:SDWIM 0 "nonimmediate_operand" "")
5445         (plus:SDWIM (match_operand:SDWIM 1 "nonimmediate_operand" "")
5446                     (match_operand:SDWIM 2 "<general_operand>" "")))]
5447   ""
5448   "ix86_expand_binary_operator (PLUS, <MODE>mode, operands); DONE;")
5449
5450 (define_insn_and_split "*add<dwi>3_doubleword"
5451   [(set (match_operand:<DWI> 0 "nonimmediate_operand" "=r,o")
5452         (plus:<DWI>
5453           (match_operand:<DWI> 1 "nonimmediate_operand" "%0,0")
5454           (match_operand:<DWI> 2 "<general_operand>" "ro<di>,r<di>")))
5455    (clobber (reg:CC FLAGS_REG))]
5456   "ix86_binary_operator_ok (PLUS, <DWI>mode, operands)"
5457   "#"
5458   "reload_completed"
5459   [(parallel [(set (reg:CC FLAGS_REG)
5460                    (unspec:CC [(match_dup 1) (match_dup 2)]
5461                               UNSPEC_ADD_CARRY))
5462               (set (match_dup 0)
5463                    (plus:DWIH (match_dup 1) (match_dup 2)))])
5464    (parallel [(set (match_dup 3)
5465                    (plus:DWIH
5466                      (match_dup 4)
5467                      (plus:DWIH
5468                        (ltu:DWIH (reg:CC FLAGS_REG) (const_int 0))
5469                        (match_dup 5))))
5470               (clobber (reg:CC FLAGS_REG))])]
5471   "split_double_mode (<DWI>mode, &operands[0], 3, &operands[0], &operands[3]);")
5472
5473 (define_insn "*add<mode>3_cc"
5474   [(set (reg:CC FLAGS_REG)
5475         (unspec:CC
5476           [(match_operand:SWI48 1 "nonimmediate_operand" "%0,0")
5477            (match_operand:SWI48 2 "<general_operand>" "r<i>,rm")]
5478           UNSPEC_ADD_CARRY))
5479    (set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r")
5480         (plus:SWI48 (match_dup 1) (match_dup 2)))]
5481   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5482   "add{<imodesuffix>}\t{%2, %0|%0, %2}"
5483   [(set_attr "type" "alu")
5484    (set_attr "mode" "<MODE>")])
5485
5486 (define_insn "addqi3_cc"
5487   [(set (reg:CC FLAGS_REG)
5488         (unspec:CC
5489           [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
5490            (match_operand:QI 2 "general_operand" "qn,qm")]
5491           UNSPEC_ADD_CARRY))
5492    (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
5493         (plus:QI (match_dup 1) (match_dup 2)))]
5494   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5495   "add{b}\t{%2, %0|%0, %2}"
5496   [(set_attr "type" "alu")
5497    (set_attr "mode" "QI")])
5498
5499 (define_insn_and_split "*lea_1"
5500   [(set (match_operand:SI 0 "register_operand" "=r")
5501         (subreg:SI (match_operand:DI 1 "lea_address_operand" "p") 0))]
5502   "TARGET_64BIT"
5503   "lea{l}\t{%a1, %0|%0, %a1}"
5504   "&& reload_completed && ix86_avoid_lea_for_addr (insn, operands)"
5505   [(const_int 0)]
5506 {
5507   ix86_split_lea_for_addr (operands, SImode);
5508   DONE;
5509 }
5510   [(set_attr "type" "lea")
5511    (set_attr "mode" "SI")])
5512
5513 (define_insn_and_split "*lea<mode>_2"
5514   [(set (match_operand:SWI48 0 "register_operand" "=r")
5515         (match_operand:SWI48 1 "lea_address_operand" "p"))]
5516   ""
5517   "lea{<imodesuffix>}\t{%a1, %0|%0, %a1}"
5518   "reload_completed && ix86_avoid_lea_for_addr (insn, operands)"
5519   [(const_int 0)]
5520 {
5521   ix86_split_lea_for_addr (operands, <MODE>mode);
5522   DONE;
5523 }
5524   [(set_attr "type" "lea")
5525    (set_attr "mode" "<MODE>")])
5526
5527 (define_insn "*lea_3_zext"
5528   [(set (match_operand:DI 0 "register_operand" "=r")
5529         (zero_extend:DI
5530           (subreg:SI (match_operand:DI 1 "lea_address_operand" "p") 0)))]
5531   "TARGET_64BIT"
5532   "lea{l}\t{%a1, %k0|%k0, %a1}"
5533   [(set_attr "type" "lea")
5534    (set_attr "mode" "SI")])
5535
5536 (define_insn "*lea_4_zext"
5537   [(set (match_operand:DI 0 "register_operand" "=r")
5538         (zero_extend:DI
5539           (match_operand:SI 1 "lea_address_operand" "p")))]
5540   "TARGET_64BIT"
5541   "lea{l}\t{%a1, %k0|%k0, %a1}"
5542   [(set_attr "type" "lea")
5543    (set_attr "mode" "SI")])
5544
5545 (define_insn "*lea_5_zext"
5546   [(set (match_operand:DI 0 "register_operand" "=r")
5547         (and:DI
5548           (subreg:DI (match_operand:SI 1 "lea_address_operand" "p") 0)
5549           (match_operand:DI 2 "const_32bit_mask" "n")))]
5550   "TARGET_64BIT"
5551   "lea{l}\t{%a1, %k0|%k0, %a1}"
5552   [(set_attr "type" "lea")
5553    (set_attr "mode" "SI")])
5554
5555 (define_insn "*lea_6_zext"
5556   [(set (match_operand:DI 0 "register_operand" "=r")
5557         (and:DI
5558           (match_operand:DI 1 "lea_address_operand" "p")
5559           (match_operand:DI 2 "const_32bit_mask" "n")))]
5560   "TARGET_64BIT"
5561   "lea{l}\t{%a1, %k0|%k0, %a1}"
5562   [(set_attr "type" "lea")
5563    (set_attr "mode" "SI")])
5564
5565 (define_insn "*add<mode>_1"
5566   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=r,rm,r,r")
5567         (plus:SWI48
5568           (match_operand:SWI48 1 "nonimmediate_operand" "%0,0,r,r")
5569           (match_operand:SWI48 2 "x86_64_general_operand" "rme,re,0,le")))
5570    (clobber (reg:CC FLAGS_REG))]
5571   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5572 {
5573   switch (get_attr_type (insn))
5574     {
5575     case TYPE_LEA:
5576       return "#";
5577
5578     case TYPE_INCDEC:
5579       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5580       if (operands[2] == const1_rtx)
5581         return "inc{<imodesuffix>}\t%0";
5582       else
5583         {
5584           gcc_assert (operands[2] == constm1_rtx);
5585           return "dec{<imodesuffix>}\t%0";
5586         }
5587
5588     default:
5589       /* For most processors, ADD is faster than LEA.  This alternative
5590          was added to use ADD as much as possible.  */
5591       if (which_alternative == 2)
5592         {
5593           rtx tmp;
5594           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5595         }
5596         
5597       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5598       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
5599         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
5600
5601       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
5602     }
5603 }
5604   [(set (attr "type")
5605      (cond [(eq_attr "alternative" "3")
5606               (const_string "lea")
5607             (match_operand:SWI48 2 "incdec_operand" "")
5608               (const_string "incdec")
5609            ]
5610            (const_string "alu")))
5611    (set (attr "length_immediate")
5612       (if_then_else
5613         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5614         (const_string "1")
5615         (const_string "*")))
5616    (set_attr "mode" "<MODE>")])
5617
5618 ;; It may seem that nonimmediate operand is proper one for operand 1.
5619 ;; The addsi_1 pattern allows nonimmediate operand at that place and
5620 ;; we take care in ix86_binary_operator_ok to not allow two memory
5621 ;; operands so proper swapping will be done in reload.  This allow
5622 ;; patterns constructed from addsi_1 to match.
5623
5624 (define_insn "addsi_1_zext"
5625   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
5626         (zero_extend:DI
5627           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r,r")
5628                    (match_operand:SI 2 "x86_64_general_operand" "rme,0,le"))))
5629    (clobber (reg:CC FLAGS_REG))]
5630   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5631 {
5632   switch (get_attr_type (insn))
5633     {
5634     case TYPE_LEA:
5635       return "#";
5636
5637     case TYPE_INCDEC:
5638       if (operands[2] == const1_rtx)
5639         return "inc{l}\t%k0";
5640       else
5641         {
5642           gcc_assert (operands[2] == constm1_rtx);
5643           return "dec{l}\t%k0";
5644         }
5645
5646     default:
5647       /* For most processors, ADD is faster than LEA.  This alternative
5648          was added to use ADD as much as possible.  */
5649       if (which_alternative == 1)
5650         {
5651           rtx tmp;
5652           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5653         }
5654
5655       if (x86_maybe_negate_const_int (&operands[2], SImode))
5656         return "sub{l}\t{%2, %k0|%k0, %2}";
5657
5658       return "add{l}\t{%2, %k0|%k0, %2}";
5659     }
5660 }
5661   [(set (attr "type")
5662      (cond [(eq_attr "alternative" "2")
5663               (const_string "lea")
5664             (match_operand:SI 2 "incdec_operand" "")
5665               (const_string "incdec")
5666            ]
5667            (const_string "alu")))
5668    (set (attr "length_immediate")
5669       (if_then_else
5670         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5671         (const_string "1")
5672         (const_string "*")))
5673    (set_attr "mode" "SI")])
5674
5675 (define_insn "*addhi_1"
5676   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r,Yp")
5677         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r,Yp")
5678                  (match_operand:HI 2 "general_operand" "rn,rm,0,ln")))
5679    (clobber (reg:CC FLAGS_REG))]
5680   "ix86_binary_operator_ok (PLUS, HImode, operands)"
5681 {
5682   switch (get_attr_type (insn))
5683     {
5684     case TYPE_LEA:
5685       return "#";
5686
5687     case TYPE_INCDEC:
5688       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5689       if (operands[2] == const1_rtx)
5690         return "inc{w}\t%0";
5691       else
5692         {
5693           gcc_assert (operands[2] == constm1_rtx);
5694           return "dec{w}\t%0";
5695         }
5696
5697     default:
5698       /* For most processors, ADD is faster than LEA.  This alternative
5699          was added to use ADD as much as possible.  */
5700       if (which_alternative == 2)
5701         {
5702           rtx tmp;
5703           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5704         }
5705
5706       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5707       if (x86_maybe_negate_const_int (&operands[2], HImode))
5708         return "sub{w}\t{%2, %0|%0, %2}";
5709
5710       return "add{w}\t{%2, %0|%0, %2}";
5711     }
5712 }
5713   [(set (attr "type")
5714      (cond [(eq_attr "alternative" "3")
5715               (const_string "lea")
5716             (match_operand:HI 2 "incdec_operand" "")
5717               (const_string "incdec")
5718            ]
5719            (const_string "alu")))
5720    (set (attr "length_immediate")
5721       (if_then_else
5722         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5723         (const_string "1")
5724         (const_string "*")))
5725    (set_attr "mode" "HI,HI,HI,SI")])
5726
5727 ;; %%% Potential partial reg stall on alternatives 3 and 4.  What to do?
5728 (define_insn "*addqi_1"
5729   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,q,r,r,Yp")
5730         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,q,0,r,Yp")
5731                  (match_operand:QI 2 "general_operand" "qn,qm,0,rn,0,ln")))
5732    (clobber (reg:CC FLAGS_REG))]
5733   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5734 {
5735   bool widen = (which_alternative == 3 || which_alternative == 4);
5736
5737   switch (get_attr_type (insn))
5738     {
5739     case TYPE_LEA:
5740       return "#";
5741
5742     case TYPE_INCDEC:
5743       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5744       if (operands[2] == const1_rtx)
5745         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
5746       else
5747         {
5748           gcc_assert (operands[2] == constm1_rtx);
5749           return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
5750         }
5751
5752     default:
5753       /* For most processors, ADD is faster than LEA.  These alternatives
5754          were added to use ADD as much as possible.  */
5755       if (which_alternative == 2 || which_alternative == 4)
5756         {
5757           rtx tmp;
5758           tmp = operands[1], operands[1] = operands[2], operands[2] = tmp;
5759         }
5760
5761       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5762       if (x86_maybe_negate_const_int (&operands[2], QImode))
5763         {
5764           if (widen)
5765             return "sub{l}\t{%2, %k0|%k0, %2}";
5766           else
5767             return "sub{b}\t{%2, %0|%0, %2}";
5768         }
5769       if (widen)
5770         return "add{l}\t{%k2, %k0|%k0, %k2}";
5771       else
5772         return "add{b}\t{%2, %0|%0, %2}";
5773     }
5774 }
5775   [(set (attr "type")
5776      (cond [(eq_attr "alternative" "5")
5777               (const_string "lea")
5778             (match_operand:QI 2 "incdec_operand" "")
5779               (const_string "incdec")
5780            ]
5781            (const_string "alu")))
5782    (set (attr "length_immediate")
5783       (if_then_else
5784         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5785         (const_string "1")
5786         (const_string "*")))
5787    (set_attr "mode" "QI,QI,QI,SI,SI,SI")])
5788
5789 (define_insn "*addqi_1_slp"
5790   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
5791         (plus:QI (match_dup 0)
5792                  (match_operand:QI 1 "general_operand" "qn,qm")))
5793    (clobber (reg:CC FLAGS_REG))]
5794   "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
5795    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
5796 {
5797   switch (get_attr_type (insn))
5798     {
5799     case TYPE_INCDEC:
5800       if (operands[1] == const1_rtx)
5801         return "inc{b}\t%0";
5802       else
5803         {
5804           gcc_assert (operands[1] == constm1_rtx);
5805           return "dec{b}\t%0";
5806         }
5807
5808     default:
5809       if (x86_maybe_negate_const_int (&operands[1], QImode))
5810         return "sub{b}\t{%1, %0|%0, %1}";
5811
5812       return "add{b}\t{%1, %0|%0, %1}";
5813     }
5814 }
5815   [(set (attr "type")
5816      (if_then_else (match_operand:QI 1 "incdec_operand" "")
5817         (const_string "incdec")
5818         (const_string "alu1")))
5819    (set (attr "memory")
5820      (if_then_else (match_operand 1 "memory_operand" "")
5821         (const_string "load")
5822         (const_string "none")))
5823    (set_attr "mode" "QI")])
5824
5825 ;; Split non destructive adds if we cannot use lea.
5826 (define_split
5827   [(set (match_operand:SWI48 0 "register_operand" "")
5828         (plus:SWI48 (match_operand:SWI48 1 "register_operand" "")
5829               (match_operand:SWI48 2 "nonmemory_operand" "")))
5830    (clobber (reg:CC FLAGS_REG))]
5831   "reload_completed && ix86_avoid_lea_for_add (insn, operands)"
5832   [(set (match_dup 0) (match_dup 1))
5833    (parallel [(set (match_dup 0) (plus:<MODE> (match_dup 0) (match_dup 2)))
5834               (clobber (reg:CC FLAGS_REG))])])
5835
5836 ;; Convert add to the lea pattern to avoid flags dependency.
5837 (define_split
5838   [(set (match_operand:SWI 0 "register_operand" "")
5839         (plus:SWI (match_operand:SWI 1 "register_operand" "")
5840                   (match_operand:SWI 2 "<nonmemory_operand>" "")))
5841    (clobber (reg:CC FLAGS_REG))]
5842   "reload_completed && ix86_lea_for_add_ok (insn, operands)" 
5843   [(const_int 0)]
5844 {
5845   enum machine_mode mode = <MODE>mode;
5846   rtx pat;
5847
5848   if (GET_MODE_SIZE (mode) < GET_MODE_SIZE (SImode))
5849     { 
5850       mode = SImode; 
5851       operands[0] = gen_lowpart (mode, operands[0]);
5852       operands[1] = gen_lowpart (mode, operands[1]);
5853       operands[2] = gen_lowpart (mode, operands[2]);
5854     }
5855
5856   pat = gen_rtx_PLUS (mode, operands[1], operands[2]);
5857
5858   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5859   DONE;
5860 })
5861
5862 ;; Convert add to the lea pattern to avoid flags dependency.
5863 (define_split
5864   [(set (match_operand:DI 0 "register_operand" "")
5865         (zero_extend:DI
5866           (plus:SI (match_operand:SI 1 "register_operand" "")
5867                    (match_operand:SI 2 "x86_64_nonmemory_operand" ""))))
5868    (clobber (reg:CC FLAGS_REG))]
5869   "TARGET_64BIT && reload_completed && ix86_lea_for_add_ok (insn, operands)"
5870   [(set (match_dup 0)
5871         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))])
5872
5873 (define_insn "*add<mode>_2"
5874   [(set (reg FLAGS_REG)
5875         (compare
5876           (plus:SWI
5877             (match_operand:SWI 1 "nonimmediate_operand" "%0,0")
5878             (match_operand:SWI 2 "<general_operand>" "<g>,<r><i>"))
5879           (const_int 0)))
5880    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>,<r>m")
5881         (plus:SWI (match_dup 1) (match_dup 2)))]
5882   "ix86_match_ccmode (insn, CCGOCmode)
5883    && ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5884 {
5885   switch (get_attr_type (insn))
5886     {
5887     case TYPE_INCDEC:
5888       if (operands[2] == const1_rtx)
5889         return "inc{<imodesuffix>}\t%0";
5890       else
5891         {
5892           gcc_assert (operands[2] == constm1_rtx);
5893           return "dec{<imodesuffix>}\t%0";
5894         }
5895
5896     default:
5897       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
5898         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
5899
5900       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
5901     }
5902 }
5903   [(set (attr "type")
5904      (if_then_else (match_operand:SWI 2 "incdec_operand" "")
5905         (const_string "incdec")
5906         (const_string "alu")))
5907    (set (attr "length_immediate")
5908       (if_then_else
5909         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5910         (const_string "1")
5911         (const_string "*")))
5912    (set_attr "mode" "<MODE>")])
5913
5914 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5915 (define_insn "*addsi_2_zext"
5916   [(set (reg FLAGS_REG)
5917         (compare
5918           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5919                    (match_operand:SI 2 "x86_64_general_operand" "rme"))
5920           (const_int 0)))
5921    (set (match_operand:DI 0 "register_operand" "=r")
5922         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5923   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5924    && ix86_binary_operator_ok (PLUS, SImode, operands)"
5925 {
5926   switch (get_attr_type (insn))
5927     {
5928     case TYPE_INCDEC:
5929       if (operands[2] == const1_rtx)
5930         return "inc{l}\t%k0";
5931       else
5932         {
5933           gcc_assert (operands[2] == constm1_rtx);
5934           return "dec{l}\t%k0";
5935         }
5936
5937     default:
5938       if (x86_maybe_negate_const_int (&operands[2], SImode))
5939         return "sub{l}\t{%2, %k0|%k0, %2}";
5940
5941       return "add{l}\t{%2, %k0|%k0, %2}";
5942     }
5943 }
5944   [(set (attr "type")
5945      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5946         (const_string "incdec")
5947         (const_string "alu")))
5948    (set (attr "length_immediate")
5949       (if_then_else
5950         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5951         (const_string "1")
5952         (const_string "*")))
5953    (set_attr "mode" "SI")])
5954
5955 (define_insn "*add<mode>_3"
5956   [(set (reg FLAGS_REG)
5957         (compare
5958           (neg:SWI (match_operand:SWI 2 "<general_operand>" "<g>"))
5959           (match_operand:SWI 1 "nonimmediate_operand" "%0")))
5960    (clobber (match_scratch:SWI 0 "=<r>"))]
5961   "ix86_match_ccmode (insn, CCZmode)
5962    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
5963 {
5964   switch (get_attr_type (insn))
5965     {
5966     case TYPE_INCDEC:
5967       if (operands[2] == const1_rtx)
5968         return "inc{<imodesuffix>}\t%0";
5969       else
5970         {
5971           gcc_assert (operands[2] == constm1_rtx);
5972           return "dec{<imodesuffix>}\t%0";
5973         }
5974
5975     default:
5976       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
5977         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
5978
5979       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
5980     }
5981 }
5982   [(set (attr "type")
5983      (if_then_else (match_operand:SWI 2 "incdec_operand" "")
5984         (const_string "incdec")
5985         (const_string "alu")))
5986    (set (attr "length_immediate")
5987       (if_then_else
5988         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
5989         (const_string "1")
5990         (const_string "*")))
5991    (set_attr "mode" "<MODE>")])
5992
5993 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5994 (define_insn "*addsi_3_zext"
5995   [(set (reg FLAGS_REG)
5996         (compare
5997           (neg:SI (match_operand:SI 2 "x86_64_general_operand" "rme"))
5998           (match_operand:SI 1 "nonimmediate_operand" "%0")))
5999    (set (match_operand:DI 0 "register_operand" "=r")
6000         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
6001   "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
6002    && ix86_binary_operator_ok (PLUS, SImode, operands)"
6003 {
6004   switch (get_attr_type (insn))
6005     {
6006     case TYPE_INCDEC:
6007       if (operands[2] == const1_rtx)
6008         return "inc{l}\t%k0";
6009       else
6010         {
6011           gcc_assert (operands[2] == constm1_rtx);
6012           return "dec{l}\t%k0";
6013         }
6014
6015     default:
6016       if (x86_maybe_negate_const_int (&operands[2], SImode))
6017         return "sub{l}\t{%2, %k0|%k0, %2}";
6018
6019       return "add{l}\t{%2, %k0|%k0, %2}";
6020     }
6021 }
6022   [(set (attr "type")
6023      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6024         (const_string "incdec")
6025         (const_string "alu")))
6026    (set (attr "length_immediate")
6027       (if_then_else
6028         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
6029         (const_string "1")
6030         (const_string "*")))
6031    (set_attr "mode" "SI")])
6032
6033 ; For comparisons against 1, -1 and 128, we may generate better code
6034 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
6035 ; is matched then.  We can't accept general immediate, because for
6036 ; case of overflows,  the result is messed up.
6037 ; Also carry flag is reversed compared to cmp, so this conversion is valid
6038 ; only for comparisons not depending on it.
6039
6040 (define_insn "*adddi_4"
6041   [(set (reg FLAGS_REG)
6042         (compare
6043           (match_operand:DI 1 "nonimmediate_operand" "0")
6044           (match_operand:DI 2 "x86_64_immediate_operand" "e")))
6045    (clobber (match_scratch:DI 0 "=rm"))]
6046   "TARGET_64BIT
6047    && ix86_match_ccmode (insn, CCGCmode)"
6048 {
6049   switch (get_attr_type (insn))
6050     {
6051     case TYPE_INCDEC:
6052       if (operands[2] == constm1_rtx)
6053         return "inc{q}\t%0";
6054       else
6055         {
6056           gcc_assert (operands[2] == const1_rtx);
6057           return "dec{q}\t%0";
6058         }
6059
6060     default:
6061       if (x86_maybe_negate_const_int (&operands[2], DImode))
6062         return "add{q}\t{%2, %0|%0, %2}";
6063
6064       return "sub{q}\t{%2, %0|%0, %2}";
6065     }
6066 }
6067   [(set (attr "type")
6068      (if_then_else (match_operand:DI 2 "incdec_operand" "")
6069         (const_string "incdec")
6070         (const_string "alu")))
6071    (set (attr "length_immediate")
6072       (if_then_else
6073         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
6074         (const_string "1")
6075         (const_string "*")))
6076    (set_attr "mode" "DI")])
6077
6078 ; For comparisons against 1, -1 and 128, we may generate better code
6079 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
6080 ; is matched then.  We can't accept general immediate, because for
6081 ; case of overflows,  the result is messed up.
6082 ; Also carry flag is reversed compared to cmp, so this conversion is valid
6083 ; only for comparisons not depending on it.
6084
6085 (define_insn "*add<mode>_4"
6086   [(set (reg FLAGS_REG)
6087         (compare
6088           (match_operand:SWI124 1 "nonimmediate_operand" "0")
6089           (match_operand:SWI124 2 "const_int_operand" "n")))
6090    (clobber (match_scratch:SWI124 0 "=<r>m"))]
6091   "ix86_match_ccmode (insn, CCGCmode)"
6092 {
6093   switch (get_attr_type (insn))
6094     {
6095     case TYPE_INCDEC:
6096       if (operands[2] == constm1_rtx)
6097         return "inc{<imodesuffix>}\t%0";
6098       else
6099         {
6100           gcc_assert (operands[2] == const1_rtx);
6101           return "dec{<imodesuffix>}\t%0";
6102         }
6103
6104     default:
6105       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
6106         return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
6107
6108       return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
6109     }
6110 }
6111   [(set (attr "type")
6112      (if_then_else (match_operand:<MODE> 2 "incdec_operand" "")
6113         (const_string "incdec")
6114         (const_string "alu")))
6115    (set (attr "length_immediate")
6116       (if_then_else
6117         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
6118         (const_string "1")
6119         (const_string "*")))
6120    (set_attr "mode" "<MODE>")])
6121
6122 (define_insn "*add<mode>_5"
6123   [(set (reg FLAGS_REG)
6124         (compare
6125           (plus:SWI
6126             (match_operand:SWI 1 "nonimmediate_operand" "%0")
6127             (match_operand:SWI 2 "<general_operand>" "<g>"))
6128           (const_int 0)))
6129    (clobber (match_scratch:SWI 0 "=<r>"))]
6130   "ix86_match_ccmode (insn, CCGOCmode)
6131    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6132 {
6133   switch (get_attr_type (insn))
6134     {
6135     case TYPE_INCDEC:
6136       if (operands[2] == const1_rtx)
6137         return "inc{<imodesuffix>}\t%0";
6138       else
6139         {
6140           gcc_assert (operands[2] == constm1_rtx);
6141           return "dec{<imodesuffix>}\t%0";
6142         }
6143
6144     default:
6145       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
6146         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
6147
6148       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
6149     }
6150 }
6151   [(set (attr "type")
6152      (if_then_else (match_operand:SWI 2 "incdec_operand" "")
6153         (const_string "incdec")
6154         (const_string "alu")))
6155    (set (attr "length_immediate")
6156       (if_then_else
6157         (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
6158         (const_string "1")
6159         (const_string "*")))
6160    (set_attr "mode" "<MODE>")])
6161
6162 (define_insn "*addqi_ext_1_rex64"
6163   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6164                          (const_int 8)
6165                          (const_int 8))
6166         (plus:SI
6167           (zero_extract:SI
6168             (match_operand 1 "ext_register_operand" "0")
6169             (const_int 8)
6170             (const_int 8))
6171           (match_operand:QI 2 "nonmemory_operand" "Qn")))
6172    (clobber (reg:CC FLAGS_REG))]
6173   "TARGET_64BIT"
6174 {
6175   switch (get_attr_type (insn))
6176     {
6177     case TYPE_INCDEC:
6178       if (operands[2] == const1_rtx)
6179         return "inc{b}\t%h0";
6180       else
6181         {
6182           gcc_assert (operands[2] == constm1_rtx);
6183           return "dec{b}\t%h0";
6184         }
6185
6186     default:
6187       return "add{b}\t{%2, %h0|%h0, %2}";
6188     }
6189 }
6190   [(set (attr "type")
6191      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6192         (const_string "incdec")
6193         (const_string "alu")))
6194    (set_attr "modrm" "1")
6195    (set_attr "mode" "QI")])
6196
6197 (define_insn "addqi_ext_1"
6198   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6199                          (const_int 8)
6200                          (const_int 8))
6201         (plus:SI
6202           (zero_extract:SI
6203             (match_operand 1 "ext_register_operand" "0")
6204             (const_int 8)
6205             (const_int 8))
6206           (match_operand:QI 2 "general_operand" "Qmn")))
6207    (clobber (reg:CC FLAGS_REG))]
6208   "!TARGET_64BIT"
6209 {
6210   switch (get_attr_type (insn))
6211     {
6212     case TYPE_INCDEC:
6213       if (operands[2] == const1_rtx)
6214         return "inc{b}\t%h0";
6215       else
6216         {
6217           gcc_assert (operands[2] == constm1_rtx);
6218           return "dec{b}\t%h0";
6219         }
6220
6221     default:
6222       return "add{b}\t{%2, %h0|%h0, %2}";
6223     }
6224 }
6225   [(set (attr "type")
6226      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6227         (const_string "incdec")
6228         (const_string "alu")))
6229    (set_attr "modrm" "1")
6230    (set_attr "mode" "QI")])
6231
6232 (define_insn "*addqi_ext_2"
6233   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6234                          (const_int 8)
6235                          (const_int 8))
6236         (plus:SI
6237           (zero_extract:SI
6238             (match_operand 1 "ext_register_operand" "%0")
6239             (const_int 8)
6240             (const_int 8))
6241           (zero_extract:SI
6242             (match_operand 2 "ext_register_operand" "Q")
6243             (const_int 8)
6244             (const_int 8))))
6245    (clobber (reg:CC FLAGS_REG))]
6246   ""
6247   "add{b}\t{%h2, %h0|%h0, %h2}"
6248   [(set_attr "type" "alu")
6249    (set_attr "mode" "QI")])
6250
6251 ;; The lea patterns for modes less than 32 bits need to be matched by
6252 ;; several insns converted to real lea by splitters.
6253
6254 (define_insn_and_split "*lea_general_1"
6255   [(set (match_operand 0 "register_operand" "=r")
6256         (plus (plus (match_operand 1 "index_register_operand" "l")
6257                     (match_operand 2 "register_operand" "r"))
6258               (match_operand 3 "immediate_operand" "i")))]
6259   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6260    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6261    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6262    && GET_MODE (operands[0]) == GET_MODE (operands[2])
6263    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
6264        || GET_MODE (operands[3]) == VOIDmode)"
6265   "#"
6266   "&& reload_completed"
6267   [(const_int 0)]
6268 {
6269   enum machine_mode mode = SImode;
6270   rtx pat;
6271
6272   operands[0] = gen_lowpart (mode, operands[0]);
6273   operands[1] = gen_lowpart (mode, operands[1]);
6274   operands[2] = gen_lowpart (mode, operands[2]);
6275   operands[3] = gen_lowpart (mode, operands[3]);
6276
6277   pat = gen_rtx_PLUS (mode, gen_rtx_PLUS (mode, operands[1], operands[2]),
6278                       operands[3]);
6279
6280   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6281   DONE;
6282 }
6283   [(set_attr "type" "lea")
6284    (set_attr "mode" "SI")])
6285
6286 (define_insn_and_split "*lea_general_2"
6287   [(set (match_operand 0 "register_operand" "=r")
6288         (plus (mult (match_operand 1 "index_register_operand" "l")
6289                     (match_operand 2 "const248_operand" "n"))
6290               (match_operand 3 "nonmemory_operand" "ri")))]
6291   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6292    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6293    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6294    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
6295        || GET_MODE (operands[3]) == VOIDmode)"
6296   "#"
6297   "&& reload_completed"
6298   [(const_int 0)]
6299 {
6300   enum machine_mode mode = SImode;
6301   rtx pat;
6302
6303   operands[0] = gen_lowpart (mode, operands[0]);
6304   operands[1] = gen_lowpart (mode, operands[1]);
6305   operands[3] = gen_lowpart (mode, operands[3]);
6306
6307   pat = gen_rtx_PLUS (mode, gen_rtx_MULT (mode, operands[1], operands[2]),
6308                       operands[3]);
6309
6310   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6311   DONE;
6312 }
6313   [(set_attr "type" "lea")
6314    (set_attr "mode" "SI")])
6315
6316 (define_insn_and_split "*lea_general_3"
6317   [(set (match_operand 0 "register_operand" "=r")
6318         (plus (plus (mult (match_operand 1 "index_register_operand" "l")
6319                           (match_operand 2 "const248_operand" "n"))
6320                     (match_operand 3 "register_operand" "r"))
6321               (match_operand 4 "immediate_operand" "i")))]
6322   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6323    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6324    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6325    && GET_MODE (operands[0]) == GET_MODE (operands[3])"
6326   "#"
6327   "&& reload_completed"
6328   [(const_int 0)]
6329 {
6330   enum machine_mode mode = SImode;
6331   rtx pat;
6332
6333   operands[0] = gen_lowpart (mode, operands[0]);
6334   operands[1] = gen_lowpart (mode, operands[1]);
6335   operands[3] = gen_lowpart (mode, operands[3]);
6336   operands[4] = gen_lowpart (mode, operands[4]);
6337
6338   pat = gen_rtx_PLUS (mode,
6339                       gen_rtx_PLUS (mode,
6340                                     gen_rtx_MULT (mode, operands[1],
6341                                                         operands[2]),
6342                                     operands[3]),
6343                       operands[4]);
6344
6345   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6346   DONE;
6347 }
6348   [(set_attr "type" "lea")
6349    (set_attr "mode" "SI")])
6350
6351 (define_insn_and_split "*lea_general_4"
6352   [(set (match_operand 0 "register_operand" "=r")
6353         (any_or (ashift
6354                   (match_operand 1 "index_register_operand" "l")
6355                   (match_operand 2 "const_int_operand" "n"))
6356                 (match_operand 3 "const_int_operand" "n")))]
6357   "(((GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
6358       && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)))
6359     || GET_MODE (operands[0]) == SImode
6360     || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
6361    && GET_MODE (operands[0]) == GET_MODE (operands[1])
6362    && ((unsigned HOST_WIDE_INT) INTVAL (operands[2])) - 1 < 3
6363    && ((unsigned HOST_WIDE_INT) INTVAL (operands[3])
6364        < ((unsigned HOST_WIDE_INT) 1 << INTVAL (operands[2])))"
6365   "#"
6366   "&& reload_completed"
6367   [(const_int 0)]
6368 {
6369   enum machine_mode mode = GET_MODE (operands[0]);
6370   rtx pat;
6371
6372   if (GET_MODE_SIZE (mode) < GET_MODE_SIZE (SImode))
6373     { 
6374       mode = SImode; 
6375       operands[0] = gen_lowpart (mode, operands[0]);
6376       operands[1] = gen_lowpart (mode, operands[1]);
6377     }
6378
6379   operands[2] = GEN_INT (1 << INTVAL (operands[2]));
6380
6381   pat = plus_constant (gen_rtx_MULT (mode, operands[1], operands[2]),
6382                        INTVAL (operands[3]));
6383
6384   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6385   DONE;
6386 }
6387   [(set_attr "type" "lea")
6388    (set (attr "mode")
6389       (if_then_else (match_operand:DI 0 "" "")
6390         (const_string "DI")
6391         (const_string "SI")))])
6392 \f
6393 ;; Subtract instructions
6394
6395 (define_expand "sub<mode>3"
6396   [(set (match_operand:SDWIM 0 "nonimmediate_operand" "")
6397         (minus:SDWIM (match_operand:SDWIM 1 "nonimmediate_operand" "")
6398                      (match_operand:SDWIM 2 "<general_operand>" "")))]
6399   ""
6400   "ix86_expand_binary_operator (MINUS, <MODE>mode, operands); DONE;")
6401
6402 (define_insn_and_split "*sub<dwi>3_doubleword"
6403   [(set (match_operand:<DWI> 0 "nonimmediate_operand" "=r,o")
6404         (minus:<DWI>
6405           (match_operand:<DWI> 1 "nonimmediate_operand" "0,0")
6406           (match_operand:<DWI> 2 "<general_operand>" "ro<di>,r<di>")))
6407    (clobber (reg:CC FLAGS_REG))]
6408   "ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6409   "#"
6410   "reload_completed"
6411   [(parallel [(set (reg:CC FLAGS_REG)
6412                    (compare:CC (match_dup 1) (match_dup 2)))
6413               (set (match_dup 0)
6414                    (minus:DWIH (match_dup 1) (match_dup 2)))])
6415    (parallel [(set (match_dup 3)
6416                    (minus:DWIH
6417                      (match_dup 4)
6418                      (plus:DWIH
6419                        (ltu:DWIH (reg:CC FLAGS_REG) (const_int 0))
6420                        (match_dup 5))))
6421               (clobber (reg:CC FLAGS_REG))])]
6422   "split_double_mode (<DWI>mode, &operands[0], 3, &operands[0], &operands[3]);")
6423
6424 (define_insn "*sub<mode>_1"
6425   [(set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6426         (minus:SWI
6427           (match_operand:SWI 1 "nonimmediate_operand" "0,0")
6428           (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m")))
6429    (clobber (reg:CC FLAGS_REG))]
6430   "ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6431   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
6432   [(set_attr "type" "alu")
6433    (set_attr "mode" "<MODE>")])
6434
6435 (define_insn "*subsi_1_zext"
6436   [(set (match_operand:DI 0 "register_operand" "=r")
6437         (zero_extend:DI
6438           (minus:SI (match_operand:SI 1 "register_operand" "0")
6439                     (match_operand:SI 2 "x86_64_general_operand" "rme"))))
6440    (clobber (reg:CC FLAGS_REG))]
6441   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6442   "sub{l}\t{%2, %k0|%k0, %2}"
6443   [(set_attr "type" "alu")
6444    (set_attr "mode" "SI")])
6445
6446 (define_insn "*subqi_1_slp"
6447   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6448         (minus:QI (match_dup 0)
6449                   (match_operand:QI 1 "general_operand" "qn,qm")))
6450    (clobber (reg:CC FLAGS_REG))]
6451   "(! TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
6452    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
6453   "sub{b}\t{%1, %0|%0, %1}"
6454   [(set_attr "type" "alu1")
6455    (set_attr "mode" "QI")])
6456
6457 (define_insn "*sub<mode>_2"
6458   [(set (reg FLAGS_REG)
6459         (compare
6460           (minus:SWI
6461             (match_operand:SWI 1 "nonimmediate_operand" "0,0")
6462             (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))
6463           (const_int 0)))
6464    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6465         (minus:SWI (match_dup 1) (match_dup 2)))]
6466   "ix86_match_ccmode (insn, CCGOCmode)
6467    && ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6468   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
6469   [(set_attr "type" "alu")
6470    (set_attr "mode" "<MODE>")])
6471
6472 (define_insn "*subsi_2_zext"
6473   [(set (reg FLAGS_REG)
6474         (compare
6475           (minus:SI (match_operand:SI 1 "register_operand" "0")
6476                     (match_operand:SI 2 "x86_64_general_operand" "rme"))
6477           (const_int 0)))
6478    (set (match_operand:DI 0 "register_operand" "=r")
6479         (zero_extend:DI
6480           (minus:SI (match_dup 1)
6481                     (match_dup 2))))]
6482   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6483    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6484   "sub{l}\t{%2, %k0|%k0, %2}"
6485   [(set_attr "type" "alu")
6486    (set_attr "mode" "SI")])
6487
6488 (define_insn "*sub<mode>_3"
6489   [(set (reg FLAGS_REG)
6490         (compare (match_operand:SWI 1 "nonimmediate_operand" "0,0")
6491                  (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m")))
6492    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6493         (minus:SWI (match_dup 1) (match_dup 2)))]
6494   "ix86_match_ccmode (insn, CCmode)
6495    && ix86_binary_operator_ok (MINUS, <MODE>mode, operands)"
6496   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
6497   [(set_attr "type" "alu")
6498    (set_attr "mode" "<MODE>")])
6499
6500 (define_insn "*subsi_3_zext"
6501   [(set (reg FLAGS_REG)
6502         (compare (match_operand:SI 1 "register_operand" "0")
6503                  (match_operand:SI 2 "x86_64_general_operand" "rme")))
6504    (set (match_operand:DI 0 "register_operand" "=r")
6505         (zero_extend:DI
6506           (minus:SI (match_dup 1)
6507                     (match_dup 2))))]
6508   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6509    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6510   "sub{l}\t{%2, %1|%1, %2}"
6511   [(set_attr "type" "alu")
6512    (set_attr "mode" "SI")])
6513 \f
6514 ;; Add with carry and subtract with borrow
6515
6516 (define_expand "<plusminus_insn><mode>3_carry"
6517   [(parallel
6518     [(set (match_operand:SWI 0 "nonimmediate_operand" "")
6519           (plusminus:SWI
6520             (match_operand:SWI 1 "nonimmediate_operand" "")
6521             (plus:SWI (match_operator:SWI 4 "ix86_carry_flag_operator"
6522                        [(match_operand 3 "flags_reg_operand" "")
6523                         (const_int 0)])
6524                       (match_operand:SWI 2 "<general_operand>" ""))))
6525      (clobber (reg:CC FLAGS_REG))])]
6526   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)")
6527
6528 (define_insn "*<plusminus_insn><mode>3_carry"
6529   [(set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6530         (plusminus:SWI
6531           (match_operand:SWI 1 "nonimmediate_operand" "<comm>0,0")
6532           (plus:SWI
6533             (match_operator 3 "ix86_carry_flag_operator"
6534              [(reg FLAGS_REG) (const_int 0)])
6535             (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))))
6536    (clobber (reg:CC FLAGS_REG))]
6537   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
6538   "<plusminus_carry_mnemonic>{<imodesuffix>}\t{%2, %0|%0, %2}"
6539   [(set_attr "type" "alu")
6540    (set_attr "use_carry" "1")
6541    (set_attr "pent_pair" "pu")
6542    (set_attr "mode" "<MODE>")])
6543
6544 (define_insn "*addsi3_carry_zext"
6545   [(set (match_operand:DI 0 "register_operand" "=r")
6546         (zero_extend:DI
6547           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
6548                    (plus:SI (match_operator 3 "ix86_carry_flag_operator"
6549                              [(reg FLAGS_REG) (const_int 0)])
6550                             (match_operand:SI 2 "x86_64_general_operand" "rme")))))
6551    (clobber (reg:CC FLAGS_REG))]
6552   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
6553   "adc{l}\t{%2, %k0|%k0, %2}"
6554   [(set_attr "type" "alu")
6555    (set_attr "use_carry" "1")
6556    (set_attr "pent_pair" "pu")
6557    (set_attr "mode" "SI")])
6558
6559 (define_insn "*subsi3_carry_zext"
6560   [(set (match_operand:DI 0 "register_operand" "=r")
6561         (zero_extend:DI
6562           (minus:SI (match_operand:SI 1 "register_operand" "0")
6563                     (plus:SI (match_operator 3 "ix86_carry_flag_operator"
6564                               [(reg FLAGS_REG) (const_int 0)])
6565                              (match_operand:SI 2 "x86_64_general_operand" "rme")))))
6566    (clobber (reg:CC FLAGS_REG))]
6567   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6568   "sbb{l}\t{%2, %k0|%k0, %2}"
6569   [(set_attr "type" "alu")
6570    (set_attr "pent_pair" "pu")
6571    (set_attr "mode" "SI")])
6572 \f
6573 ;; Overflow setting add and subtract instructions
6574
6575 (define_insn "*add<mode>3_cconly_overflow"
6576   [(set (reg:CCC FLAGS_REG)
6577         (compare:CCC
6578           (plus:SWI
6579             (match_operand:SWI 1 "nonimmediate_operand" "%0")
6580             (match_operand:SWI 2 "<general_operand>" "<g>"))
6581           (match_dup 1)))
6582    (clobber (match_scratch:SWI 0 "=<r>"))]
6583   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6584   "add{<imodesuffix>}\t{%2, %0|%0, %2}"
6585   [(set_attr "type" "alu")
6586    (set_attr "mode" "<MODE>")])
6587
6588 (define_insn "*sub<mode>3_cconly_overflow"
6589   [(set (reg:CCC FLAGS_REG)
6590         (compare:CCC
6591           (minus:SWI
6592             (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
6593             (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m"))
6594           (match_dup 0)))]
6595   ""
6596   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
6597   [(set_attr "type" "icmp")
6598    (set_attr "mode" "<MODE>")])
6599
6600 (define_insn "*<plusminus_insn><mode>3_cc_overflow"
6601   [(set (reg:CCC FLAGS_REG)
6602         (compare:CCC
6603             (plusminus:SWI
6604                 (match_operand:SWI 1 "nonimmediate_operand" "<comm>0,0")
6605                 (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))
6606             (match_dup 1)))
6607    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
6608         (plusminus:SWI (match_dup 1) (match_dup 2)))]
6609   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
6610   "<plusminus_mnemonic>{<imodesuffix>}\t{%2, %0|%0, %2}"
6611   [(set_attr "type" "alu")
6612    (set_attr "mode" "<MODE>")])
6613
6614 (define_insn "*<plusminus_insn>si3_zext_cc_overflow"
6615   [(set (reg:CCC FLAGS_REG)
6616         (compare:CCC
6617           (plusminus:SI
6618             (match_operand:SI 1 "nonimmediate_operand" "<comm>0")
6619             (match_operand:SI 2 "x86_64_general_operand" "rme"))
6620           (match_dup 1)))
6621    (set (match_operand:DI 0 "register_operand" "=r")
6622         (zero_extend:DI (plusminus:SI (match_dup 1) (match_dup 2))))]
6623   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
6624   "<plusminus_mnemonic>{l}\t{%2, %k0|%k0, %2}"
6625   [(set_attr "type" "alu")
6626    (set_attr "mode" "SI")])
6627
6628 ;; The patterns that match these are at the end of this file.
6629
6630 (define_expand "<plusminus_insn>xf3"
6631   [(set (match_operand:XF 0 "register_operand" "")
6632         (plusminus:XF
6633           (match_operand:XF 1 "register_operand" "")
6634           (match_operand:XF 2 "register_operand" "")))]
6635   "TARGET_80387")
6636
6637 (define_expand "<plusminus_insn><mode>3"
6638   [(set (match_operand:MODEF 0 "register_operand" "")
6639         (plusminus:MODEF
6640           (match_operand:MODEF 1 "register_operand" "")
6641           (match_operand:MODEF 2 "nonimmediate_operand" "")))]
6642   "(TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode))
6643     || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)")
6644 \f
6645 ;; Multiply instructions
6646
6647 (define_expand "mul<mode>3"
6648   [(parallel [(set (match_operand:SWIM248 0 "register_operand" "")
6649                    (mult:SWIM248
6650                      (match_operand:SWIM248 1 "register_operand" "")
6651                      (match_operand:SWIM248 2 "<general_operand>" "")))
6652               (clobber (reg:CC FLAGS_REG))])])
6653
6654 (define_expand "mulqi3"
6655   [(parallel [(set (match_operand:QI 0 "register_operand" "")
6656                    (mult:QI
6657                      (match_operand:QI 1 "register_operand" "")
6658                      (match_operand:QI 2 "nonimmediate_operand" "")))
6659               (clobber (reg:CC FLAGS_REG))])]
6660   "TARGET_QIMODE_MATH")
6661
6662 ;; On AMDFAM10
6663 ;; IMUL reg32/64, reg32/64, imm8        Direct
6664 ;; IMUL reg32/64, mem32/64, imm8        VectorPath
6665 ;; IMUL reg32/64, reg32/64, imm32       Direct
6666 ;; IMUL reg32/64, mem32/64, imm32       VectorPath
6667 ;; IMUL reg32/64, reg32/64              Direct
6668 ;; IMUL reg32/64, mem32/64              Direct
6669 ;;
6670 ;; On BDVER1, all above IMULs use DirectPath
6671
6672 (define_insn "*mul<mode>3_1"
6673   [(set (match_operand:SWI48 0 "register_operand" "=r,r,r")
6674         (mult:SWI48
6675           (match_operand:SWI48 1 "nonimmediate_operand" "%rm,rm,0")
6676           (match_operand:SWI48 2 "<general_operand>" "K,<i>,mr")))
6677    (clobber (reg:CC FLAGS_REG))]
6678   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6679   "@
6680    imul{<imodesuffix>}\t{%2, %1, %0|%0, %1, %2}
6681    imul{<imodesuffix>}\t{%2, %1, %0|%0, %1, %2}
6682    imul{<imodesuffix>}\t{%2, %0|%0, %2}"
6683   [(set_attr "type" "imul")
6684    (set_attr "prefix_0f" "0,0,1")
6685    (set (attr "athlon_decode")
6686         (cond [(eq_attr "cpu" "athlon")
6687                   (const_string "vector")
6688                (eq_attr "alternative" "1")
6689                   (const_string "vector")
6690                (and (eq_attr "alternative" "2")
6691                     (match_operand 1 "memory_operand" ""))
6692                   (const_string "vector")]
6693               (const_string "direct")))
6694    (set (attr "amdfam10_decode")
6695         (cond [(and (eq_attr "alternative" "0,1")
6696                     (match_operand 1 "memory_operand" ""))
6697                   (const_string "vector")]
6698               (const_string "direct")))
6699    (set_attr "bdver1_decode" "direct")
6700    (set_attr "mode" "<MODE>")])
6701
6702 (define_insn "*mulsi3_1_zext"
6703   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6704         (zero_extend:DI
6705           (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6706                    (match_operand:SI 2 "x86_64_general_operand" "K,e,mr"))))
6707    (clobber (reg:CC FLAGS_REG))]
6708   "TARGET_64BIT
6709    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6710   "@
6711    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6712    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6713    imul{l}\t{%2, %k0|%k0, %2}"
6714   [(set_attr "type" "imul")
6715    (set_attr "prefix_0f" "0,0,1")
6716    (set (attr "athlon_decode")
6717         (cond [(eq_attr "cpu" "athlon")
6718                   (const_string "vector")
6719                (eq_attr "alternative" "1")
6720                   (const_string "vector")
6721                (and (eq_attr "alternative" "2")
6722                     (match_operand 1 "memory_operand" ""))
6723                   (const_string "vector")]
6724               (const_string "direct")))
6725    (set (attr "amdfam10_decode")
6726         (cond [(and (eq_attr "alternative" "0,1")
6727                     (match_operand 1 "memory_operand" ""))
6728                   (const_string "vector")]
6729               (const_string "direct")))
6730    (set_attr "bdver1_decode" "direct")
6731    (set_attr "mode" "SI")])
6732
6733 ;; On AMDFAM10
6734 ;; IMUL reg16, reg16, imm8      VectorPath
6735 ;; IMUL reg16, mem16, imm8      VectorPath
6736 ;; IMUL reg16, reg16, imm16     VectorPath
6737 ;; IMUL reg16, mem16, imm16     VectorPath
6738 ;; IMUL reg16, reg16            Direct
6739 ;; IMUL reg16, mem16            Direct
6740 ;;
6741 ;; On BDVER1, all HI MULs use DoublePath
6742
6743 (define_insn "*mulhi3_1"
6744   [(set (match_operand:HI 0 "register_operand" "=r,r,r")
6745         (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
6746                  (match_operand:HI 2 "general_operand" "K,n,mr")))
6747    (clobber (reg:CC FLAGS_REG))]
6748   "TARGET_HIMODE_MATH
6749    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6750   "@
6751    imul{w}\t{%2, %1, %0|%0, %1, %2}
6752    imul{w}\t{%2, %1, %0|%0, %1, %2}
6753    imul{w}\t{%2, %0|%0, %2}"
6754   [(set_attr "type" "imul")
6755    (set_attr "prefix_0f" "0,0,1")
6756    (set (attr "athlon_decode")
6757         (cond [(eq_attr "cpu" "athlon")
6758                   (const_string "vector")
6759                (eq_attr "alternative" "1,2")
6760                   (const_string "vector")]
6761               (const_string "direct")))
6762    (set (attr "amdfam10_decode")
6763         (cond [(eq_attr "alternative" "0,1")
6764                   (const_string "vector")]
6765               (const_string "direct")))
6766    (set_attr "bdver1_decode" "double")
6767    (set_attr "mode" "HI")])
6768
6769 ;;On AMDFAM10 and BDVER1
6770 ;; MUL reg8     Direct
6771 ;; MUL mem8     Direct
6772
6773 (define_insn "*mulqi3_1"
6774   [(set (match_operand:QI 0 "register_operand" "=a")
6775         (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6776                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
6777    (clobber (reg:CC FLAGS_REG))]
6778   "TARGET_QIMODE_MATH
6779    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6780   "mul{b}\t%2"
6781   [(set_attr "type" "imul")
6782    (set_attr "length_immediate" "0")
6783    (set (attr "athlon_decode")
6784      (if_then_else (eq_attr "cpu" "athlon")
6785         (const_string "vector")
6786         (const_string "direct")))
6787    (set_attr "amdfam10_decode" "direct")
6788    (set_attr "bdver1_decode" "direct")
6789    (set_attr "mode" "QI")])
6790
6791 (define_expand "<u>mul<mode><dwi>3"
6792   [(parallel [(set (match_operand:<DWI> 0 "register_operand" "")
6793                    (mult:<DWI>
6794                      (any_extend:<DWI>
6795                        (match_operand:DWIH 1 "nonimmediate_operand" ""))
6796                      (any_extend:<DWI>
6797                        (match_operand:DWIH 2 "register_operand" ""))))
6798               (clobber (reg:CC FLAGS_REG))])])
6799
6800 (define_expand "<u>mulqihi3"
6801   [(parallel [(set (match_operand:HI 0 "register_operand" "")
6802                    (mult:HI
6803                      (any_extend:HI
6804                        (match_operand:QI 1 "nonimmediate_operand" ""))
6805                      (any_extend:HI
6806                        (match_operand:QI 2 "register_operand" ""))))
6807               (clobber (reg:CC FLAGS_REG))])]
6808   "TARGET_QIMODE_MATH")
6809
6810 (define_insn "*bmi2_umulditi3_1"
6811   [(set (match_operand:DI 0 "register_operand" "=r")
6812         (mult:DI
6813           (match_operand:DI 2 "nonimmediate_operand" "%d")
6814           (match_operand:DI 3 "nonimmediate_operand" "rm")))
6815    (set (match_operand:DI 1 "register_operand" "=r")
6816         (truncate:DI
6817           (lshiftrt:TI
6818             (mult:TI (zero_extend:TI (match_dup 2))
6819                      (zero_extend:TI (match_dup 3)))
6820             (const_int 64))))]
6821   "TARGET_64BIT && TARGET_BMI2
6822    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6823   "mulx\t{%3, %0, %1|%1, %0, %3}"
6824   [(set_attr "type" "imulx")
6825    (set_attr "prefix" "vex")
6826    (set_attr "mode" "DI")])
6827
6828 (define_insn "*bmi2_umulsidi3_1"
6829   [(set (match_operand:SI 0 "register_operand" "=r")
6830         (mult:SI
6831           (match_operand:SI 2 "nonimmediate_operand" "%d")
6832           (match_operand:SI 3 "nonimmediate_operand" "rm")))
6833    (set (match_operand:SI 1 "register_operand" "=r")
6834         (truncate:SI
6835           (lshiftrt:DI
6836             (mult:DI (zero_extend:DI (match_dup 2))
6837                      (zero_extend:DI (match_dup 3)))
6838             (const_int 32))))]
6839   "!TARGET_64BIT && TARGET_BMI2
6840    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6841   "mulx\t{%3, %0, %1|%1, %0, %3}"
6842   [(set_attr "type" "imulx")
6843    (set_attr "prefix" "vex")
6844    (set_attr "mode" "SI")])
6845
6846 (define_insn "*umul<mode><dwi>3_1"
6847   [(set (match_operand:<DWI> 0 "register_operand" "=A,r")
6848         (mult:<DWI>
6849           (zero_extend:<DWI>
6850             (match_operand:DWIH 1 "nonimmediate_operand" "%0,d"))
6851           (zero_extend:<DWI>
6852             (match_operand:DWIH 2 "nonimmediate_operand" "rm,rm"))))
6853    (clobber (reg:CC FLAGS_REG))]
6854   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6855   "@
6856    mul{<imodesuffix>}\t%2
6857    #"
6858   [(set_attr "isa" "*,bmi2")
6859    (set_attr "type" "imul,imulx")
6860    (set_attr "length_immediate" "0,*")
6861    (set (attr "athlon_decode")
6862         (cond [(eq_attr "alternative" "0")
6863                  (if_then_else (eq_attr "cpu" "athlon")
6864                    (const_string "vector")
6865                    (const_string "double"))]
6866               (const_string "*")))
6867    (set_attr "amdfam10_decode" "double,*")
6868    (set_attr "bdver1_decode" "direct,*")
6869    (set_attr "prefix" "orig,vex")
6870    (set_attr "mode" "<MODE>")])
6871
6872 ;; Convert mul to the mulx pattern to avoid flags dependency.
6873 (define_split
6874  [(set (match_operand:<DWI> 0 "register_operand" "")
6875        (mult:<DWI>
6876          (zero_extend:<DWI>
6877            (match_operand:DWIH 1 "register_operand" ""))
6878          (zero_extend:<DWI>
6879            (match_operand:DWIH 2 "nonimmediate_operand" ""))))
6880   (clobber (reg:CC FLAGS_REG))]
6881  "TARGET_BMI2 && reload_completed
6882   && true_regnum (operands[1]) == DX_REG"
6883   [(parallel [(set (match_dup 3)
6884                    (mult:DWIH (match_dup 1) (match_dup 2)))
6885               (set (match_dup 4)
6886                    (truncate:DWIH
6887                      (lshiftrt:<DWI>
6888                        (mult:<DWI> (zero_extend:<DWI> (match_dup 1))
6889                                    (zero_extend:<DWI> (match_dup 2)))
6890                        (match_dup 5))))])]
6891 {
6892   split_double_mode (<DWI>mode, &operands[0], 1, &operands[3], &operands[4]);
6893
6894   operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));
6895 })
6896
6897 (define_insn "*mul<mode><dwi>3_1"
6898   [(set (match_operand:<DWI> 0 "register_operand" "=A")
6899         (mult:<DWI>
6900           (sign_extend:<DWI>
6901             (match_operand:DWIH 1 "nonimmediate_operand" "%0"))
6902           (sign_extend:<DWI>
6903             (match_operand:DWIH 2 "nonimmediate_operand" "rm"))))
6904    (clobber (reg:CC FLAGS_REG))]
6905   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6906   "imul{<imodesuffix>}\t%2"
6907   [(set_attr "type" "imul")
6908    (set_attr "length_immediate" "0")
6909    (set (attr "athlon_decode")
6910      (if_then_else (eq_attr "cpu" "athlon")
6911         (const_string "vector")
6912         (const_string "double")))
6913    (set_attr "amdfam10_decode" "double")
6914    (set_attr "bdver1_decode" "direct")
6915    (set_attr "mode" "<MODE>")])
6916
6917 (define_insn "*<u>mulqihi3_1"
6918   [(set (match_operand:HI 0 "register_operand" "=a")
6919         (mult:HI
6920           (any_extend:HI
6921             (match_operand:QI 1 "nonimmediate_operand" "%0"))
6922           (any_extend:HI
6923             (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6924    (clobber (reg:CC FLAGS_REG))]
6925   "TARGET_QIMODE_MATH
6926    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6927   "<sgnprefix>mul{b}\t%2"
6928   [(set_attr "type" "imul")
6929    (set_attr "length_immediate" "0")
6930    (set (attr "athlon_decode")
6931      (if_then_else (eq_attr "cpu" "athlon")
6932         (const_string "vector")
6933         (const_string "direct")))
6934    (set_attr "amdfam10_decode" "direct")
6935    (set_attr "bdver1_decode" "direct")
6936    (set_attr "mode" "QI")])
6937
6938 (define_expand "<s>mul<mode>3_highpart"
6939   [(parallel [(set (match_operand:SWI48 0 "register_operand" "")
6940                    (truncate:SWI48
6941                      (lshiftrt:<DWI>
6942                        (mult:<DWI>
6943                          (any_extend:<DWI>
6944                            (match_operand:SWI48 1 "nonimmediate_operand" ""))
6945                          (any_extend:<DWI>
6946                            (match_operand:SWI48 2 "register_operand" "")))
6947                        (match_dup 4))))
6948               (clobber (match_scratch:SWI48 3 ""))
6949               (clobber (reg:CC FLAGS_REG))])]
6950   ""
6951   "operands[4] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));")
6952
6953 (define_insn "*<s>muldi3_highpart_1"
6954   [(set (match_operand:DI 0 "register_operand" "=d")
6955         (truncate:DI
6956           (lshiftrt:TI
6957             (mult:TI
6958               (any_extend:TI
6959                 (match_operand:DI 1 "nonimmediate_operand" "%a"))
6960               (any_extend:TI
6961                 (match_operand:DI 2 "nonimmediate_operand" "rm")))
6962             (const_int 64))))
6963    (clobber (match_scratch:DI 3 "=1"))
6964    (clobber (reg:CC FLAGS_REG))]
6965   "TARGET_64BIT
6966    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6967   "<sgnprefix>mul{q}\t%2"
6968   [(set_attr "type" "imul")
6969    (set_attr "length_immediate" "0")
6970    (set (attr "athlon_decode")
6971      (if_then_else (eq_attr "cpu" "athlon")
6972         (const_string "vector")
6973         (const_string "double")))
6974    (set_attr "amdfam10_decode" "double")
6975    (set_attr "bdver1_decode" "direct")
6976    (set_attr "mode" "DI")])
6977
6978 (define_insn "*<s>mulsi3_highpart_1"
6979   [(set (match_operand:SI 0 "register_operand" "=d")
6980         (truncate:SI
6981           (lshiftrt:DI
6982             (mult:DI
6983               (any_extend:DI
6984                 (match_operand:SI 1 "nonimmediate_operand" "%a"))
6985               (any_extend:DI
6986                 (match_operand:SI 2 "nonimmediate_operand" "rm")))
6987             (const_int 32))))
6988    (clobber (match_scratch:SI 3 "=1"))
6989    (clobber (reg:CC FLAGS_REG))]
6990   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
6991   "<sgnprefix>mul{l}\t%2"
6992   [(set_attr "type" "imul")
6993    (set_attr "length_immediate" "0")
6994    (set (attr "athlon_decode")
6995      (if_then_else (eq_attr "cpu" "athlon")
6996         (const_string "vector")
6997         (const_string "double")))
6998    (set_attr "amdfam10_decode" "double")
6999    (set_attr "bdver1_decode" "direct")
7000    (set_attr "mode" "SI")])
7001
7002 (define_insn "*<s>mulsi3_highpart_zext"
7003   [(set (match_operand:DI 0 "register_operand" "=d")
7004         (zero_extend:DI (truncate:SI
7005           (lshiftrt:DI
7006             (mult:DI (any_extend:DI
7007                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7008                      (any_extend:DI
7009                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7010             (const_int 32)))))
7011    (clobber (match_scratch:SI 3 "=1"))
7012    (clobber (reg:CC FLAGS_REG))]
7013   "TARGET_64BIT
7014    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7015   "<sgnprefix>mul{l}\t%2"
7016   [(set_attr "type" "imul")
7017    (set_attr "length_immediate" "0")
7018    (set (attr "athlon_decode")
7019      (if_then_else (eq_attr "cpu" "athlon")
7020         (const_string "vector")
7021         (const_string "double")))
7022    (set_attr "amdfam10_decode" "double")
7023    (set_attr "bdver1_decode" "direct")
7024    (set_attr "mode" "SI")])
7025
7026 ;; The patterns that match these are at the end of this file.
7027
7028 (define_expand "mulxf3"
7029   [(set (match_operand:XF 0 "register_operand" "")
7030         (mult:XF (match_operand:XF 1 "register_operand" "")
7031                  (match_operand:XF 2 "register_operand" "")))]
7032   "TARGET_80387")
7033
7034 (define_expand "mul<mode>3"
7035   [(set (match_operand:MODEF 0 "register_operand" "")
7036         (mult:MODEF (match_operand:MODEF 1 "register_operand" "")
7037                     (match_operand:MODEF 2 "nonimmediate_operand" "")))]
7038   "(TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode))
7039     || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)")
7040 \f
7041 ;; Divide instructions
7042
7043 ;; The patterns that match these are at the end of this file.
7044
7045 (define_expand "divxf3"
7046   [(set (match_operand:XF 0 "register_operand" "")
7047         (div:XF (match_operand:XF 1 "register_operand" "")
7048                 (match_operand:XF 2 "register_operand" "")))]
7049   "TARGET_80387")
7050
7051 (define_expand "divdf3"
7052   [(set (match_operand:DF 0 "register_operand" "")
7053         (div:DF (match_operand:DF 1 "register_operand" "")
7054                 (match_operand:DF 2 "nonimmediate_operand" "")))]
7055    "(TARGET_80387 && X87_ENABLE_ARITH (DFmode))
7056     || (TARGET_SSE2 && TARGET_SSE_MATH)")
7057
7058 (define_expand "divsf3"
7059   [(set (match_operand:SF 0 "register_operand" "")
7060         (div:SF (match_operand:SF 1 "register_operand" "")
7061                 (match_operand:SF 2 "nonimmediate_operand" "")))]
7062   "(TARGET_80387 && X87_ENABLE_ARITH (SFmode))
7063     || TARGET_SSE_MATH"
7064 {
7065   if (TARGET_SSE_MATH
7066       && TARGET_RECIP_DIV
7067       && optimize_insn_for_speed_p ()
7068       && flag_finite_math_only && !flag_trapping_math
7069       && flag_unsafe_math_optimizations)
7070     {
7071       ix86_emit_swdivsf (operands[0], operands[1],
7072                          operands[2], SFmode);
7073       DONE;
7074     }
7075 })
7076 \f
7077 ;; Divmod instructions.
7078
7079 (define_expand "divmod<mode>4"
7080   [(parallel [(set (match_operand:SWIM248 0 "register_operand" "")
7081                    (div:SWIM248
7082                      (match_operand:SWIM248 1 "register_operand" "")
7083                      (match_operand:SWIM248 2 "nonimmediate_operand" "")))
7084               (set (match_operand:SWIM248 3 "register_operand" "")
7085                    (mod:SWIM248 (match_dup 1) (match_dup 2)))
7086               (clobber (reg:CC FLAGS_REG))])])
7087
7088 ;; Split with 8bit unsigned divide:
7089 ;;      if (dividend an divisor are in [0-255])
7090 ;;         use 8bit unsigned integer divide
7091 ;;       else
7092 ;;         use original integer divide
7093 (define_split
7094   [(set (match_operand:SWI48 0 "register_operand" "")
7095         (div:SWI48 (match_operand:SWI48 2 "register_operand" "")
7096                     (match_operand:SWI48 3 "nonimmediate_operand" "")))
7097    (set (match_operand:SWI48 1 "register_operand" "")
7098         (mod:SWI48 (match_dup 2) (match_dup 3)))
7099    (clobber (reg:CC FLAGS_REG))]
7100   "TARGET_USE_8BIT_IDIV
7101    && TARGET_QIMODE_MATH
7102    && can_create_pseudo_p ()
7103    && !optimize_insn_for_size_p ()"
7104   [(const_int 0)]
7105   "ix86_split_idivmod (<MODE>mode, operands, true); DONE;")
7106
7107 (define_insn_and_split "divmod<mode>4_1"
7108   [(set (match_operand:SWI48 0 "register_operand" "=a")
7109         (div:SWI48 (match_operand:SWI48 2 "register_operand" "0")
7110                    (match_operand:SWI48 3 "nonimmediate_operand" "rm")))
7111    (set (match_operand:SWI48 1 "register_operand" "=&d")
7112         (mod:SWI48 (match_dup 2) (match_dup 3)))
7113    (unspec [(const_int 0)] UNSPEC_DIV_ALREADY_SPLIT)
7114    (clobber (reg:CC FLAGS_REG))]
7115   ""
7116   "#"
7117   "reload_completed"
7118   [(parallel [(set (match_dup 1)
7119                    (ashiftrt:SWI48 (match_dup 4) (match_dup 5)))
7120               (clobber (reg:CC FLAGS_REG))])
7121    (parallel [(set (match_dup 0)
7122                    (div:SWI48 (match_dup 2) (match_dup 3)))
7123               (set (match_dup 1)
7124                    (mod:SWI48 (match_dup 2) (match_dup 3)))
7125               (use (match_dup 1))
7126               (clobber (reg:CC FLAGS_REG))])]
7127 {
7128   operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1);
7129
7130   if (optimize_function_for_size_p (cfun) || TARGET_USE_CLTD)
7131     operands[4] = operands[2];
7132   else
7133     {
7134       /* Avoid use of cltd in favor of a mov+shift.  */
7135       emit_move_insn (operands[1], operands[2]);
7136       operands[4] = operands[1];
7137     }
7138 }
7139   [(set_attr "type" "multi")
7140    (set_attr "mode" "<MODE>")])
7141
7142 (define_insn_and_split "*divmod<mode>4"
7143   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7144         (div:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7145                     (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7146    (set (match_operand:SWIM248 1 "register_operand" "=&d")
7147         (mod:SWIM248 (match_dup 2) (match_dup 3)))
7148    (clobber (reg:CC FLAGS_REG))]
7149   ""
7150   "#"
7151   "reload_completed"
7152   [(parallel [(set (match_dup 1)
7153                    (ashiftrt:SWIM248 (match_dup 4) (match_dup 5)))
7154               (clobber (reg:CC FLAGS_REG))])
7155    (parallel [(set (match_dup 0)
7156                    (div:SWIM248 (match_dup 2) (match_dup 3)))
7157               (set (match_dup 1)
7158                    (mod:SWIM248 (match_dup 2) (match_dup 3)))
7159               (use (match_dup 1))
7160               (clobber (reg:CC FLAGS_REG))])]
7161 {
7162   operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1);
7163
7164   if (<MODE>mode != HImode
7165       && (optimize_function_for_size_p (cfun) || TARGET_USE_CLTD))
7166     operands[4] = operands[2];
7167   else
7168     {
7169       /* Avoid use of cltd in favor of a mov+shift.  */
7170       emit_move_insn (operands[1], operands[2]);
7171       operands[4] = operands[1];
7172     }
7173 }
7174   [(set_attr "type" "multi")
7175    (set_attr "mode" "<MODE>")])
7176
7177 (define_insn "*divmod<mode>4_noext"
7178   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7179         (div:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7180                     (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7181    (set (match_operand:SWIM248 1 "register_operand" "=d")
7182         (mod:SWIM248 (match_dup 2) (match_dup 3)))
7183    (use (match_operand:SWIM248 4 "register_operand" "1"))
7184    (clobber (reg:CC FLAGS_REG))]
7185   ""
7186   "idiv{<imodesuffix>}\t%3"
7187   [(set_attr "type" "idiv")
7188    (set_attr "mode" "<MODE>")])
7189
7190 (define_expand "divmodqi4"
7191   [(parallel [(set (match_operand:QI 0 "register_operand" "")
7192                    (div:QI
7193                      (match_operand:QI 1 "register_operand" "")
7194                      (match_operand:QI 2 "nonimmediate_operand" "")))
7195               (set (match_operand:QI 3 "register_operand" "")
7196                    (mod:QI (match_dup 1) (match_dup 2)))
7197               (clobber (reg:CC FLAGS_REG))])]
7198   "TARGET_QIMODE_MATH"
7199 {
7200   rtx div, mod, insn;
7201   rtx tmp0, tmp1;
7202   
7203   tmp0 = gen_reg_rtx (HImode);
7204   tmp1 = gen_reg_rtx (HImode);
7205
7206   /* Extend operands[1] to HImode.  Generate 8bit divide.  Result is
7207      in AX.  */
7208   emit_insn (gen_extendqihi2 (tmp1, operands[1]));
7209   emit_insn (gen_divmodhiqi3 (tmp0, tmp1, operands[2]));
7210
7211   /* Extract remainder from AH.  */
7212   tmp1 = gen_rtx_SIGN_EXTRACT (QImode, tmp0, GEN_INT (8), GEN_INT (8));
7213   insn = emit_move_insn (operands[3], tmp1);
7214
7215   mod = gen_rtx_MOD (QImode, operands[1], operands[2]);
7216   set_unique_reg_note (insn, REG_EQUAL, mod);
7217
7218   /* Extract quotient from AL.  */
7219   insn = emit_move_insn (operands[0], gen_lowpart (QImode, tmp0));
7220
7221   div = gen_rtx_DIV (QImode, operands[1], operands[2]);
7222   set_unique_reg_note (insn, REG_EQUAL, div);
7223
7224   DONE;
7225 })
7226
7227 ;; Divide AX by r/m8, with result stored in
7228 ;; AL <- Quotient
7229 ;; AH <- Remainder
7230 ;; Change div/mod to HImode and extend the second argument to HImode
7231 ;; so that mode of div/mod matches with mode of arguments.  Otherwise
7232 ;; combine may fail.
7233 (define_insn "divmodhiqi3"
7234   [(set (match_operand:HI 0 "register_operand" "=a")
7235         (ior:HI
7236           (ashift:HI
7237             (zero_extend:HI
7238               (truncate:QI
7239                 (mod:HI (match_operand:HI 1 "register_operand" "0")
7240                         (sign_extend:HI
7241                           (match_operand:QI 2 "nonimmediate_operand" "qm")))))
7242             (const_int 8))
7243           (zero_extend:HI
7244             (truncate:QI
7245               (div:HI (match_dup 1) (sign_extend:HI (match_dup 2)))))))
7246    (clobber (reg:CC FLAGS_REG))]
7247   "TARGET_QIMODE_MATH"
7248   "idiv{b}\t%2"
7249   [(set_attr "type" "idiv")
7250    (set_attr "mode" "QI")])
7251
7252 (define_expand "udivmod<mode>4"
7253   [(parallel [(set (match_operand:SWIM248 0 "register_operand" "")
7254                    (udiv:SWIM248
7255                      (match_operand:SWIM248 1 "register_operand" "")
7256                      (match_operand:SWIM248 2 "nonimmediate_operand" "")))
7257               (set (match_operand:SWIM248 3 "register_operand" "")
7258                    (umod:SWIM248 (match_dup 1) (match_dup 2)))
7259               (clobber (reg:CC FLAGS_REG))])])
7260
7261 ;; Split with 8bit unsigned divide:
7262 ;;      if (dividend an divisor are in [0-255])
7263 ;;         use 8bit unsigned integer divide
7264 ;;       else
7265 ;;         use original integer divide
7266 (define_split
7267   [(set (match_operand:SWI48 0 "register_operand" "")
7268         (udiv:SWI48 (match_operand:SWI48 2 "register_operand" "")
7269                     (match_operand:SWI48 3 "nonimmediate_operand" "")))
7270    (set (match_operand:SWI48 1 "register_operand" "")
7271         (umod:SWI48 (match_dup 2) (match_dup 3)))
7272    (clobber (reg:CC FLAGS_REG))]
7273   "TARGET_USE_8BIT_IDIV
7274    && TARGET_QIMODE_MATH
7275    && can_create_pseudo_p ()
7276    && !optimize_insn_for_size_p ()"
7277   [(const_int 0)]
7278   "ix86_split_idivmod (<MODE>mode, operands, false); DONE;")
7279
7280 (define_insn_and_split "udivmod<mode>4_1"
7281   [(set (match_operand:SWI48 0 "register_operand" "=a")
7282         (udiv:SWI48 (match_operand:SWI48 2 "register_operand" "0")
7283                     (match_operand:SWI48 3 "nonimmediate_operand" "rm")))
7284    (set (match_operand:SWI48 1 "register_operand" "=&d")
7285         (umod:SWI48 (match_dup 2) (match_dup 3)))
7286    (unspec [(const_int 0)] UNSPEC_DIV_ALREADY_SPLIT)
7287    (clobber (reg:CC FLAGS_REG))]
7288   ""
7289   "#"
7290   "reload_completed"
7291   [(set (match_dup 1) (const_int 0))
7292    (parallel [(set (match_dup 0)
7293                    (udiv:SWI48 (match_dup 2) (match_dup 3)))
7294               (set (match_dup 1)
7295                    (umod:SWI48 (match_dup 2) (match_dup 3)))
7296               (use (match_dup 1))
7297               (clobber (reg:CC FLAGS_REG))])]
7298   ""
7299   [(set_attr "type" "multi")
7300    (set_attr "mode" "<MODE>")])
7301
7302 (define_insn_and_split "*udivmod<mode>4"
7303   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7304         (udiv:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7305                       (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7306    (set (match_operand:SWIM248 1 "register_operand" "=&d")
7307         (umod:SWIM248 (match_dup 2) (match_dup 3)))
7308    (clobber (reg:CC FLAGS_REG))]
7309   ""
7310   "#"
7311   "reload_completed"
7312   [(set (match_dup 1) (const_int 0))
7313    (parallel [(set (match_dup 0)
7314                    (udiv:SWIM248 (match_dup 2) (match_dup 3)))
7315               (set (match_dup 1)
7316                    (umod:SWIM248 (match_dup 2) (match_dup 3)))
7317               (use (match_dup 1))
7318               (clobber (reg:CC FLAGS_REG))])]
7319   ""
7320   [(set_attr "type" "multi")
7321    (set_attr "mode" "<MODE>")])
7322
7323 (define_insn "*udivmod<mode>4_noext"
7324   [(set (match_operand:SWIM248 0 "register_operand" "=a")
7325         (udiv:SWIM248 (match_operand:SWIM248 2 "register_operand" "0")
7326                       (match_operand:SWIM248 3 "nonimmediate_operand" "rm")))
7327    (set (match_operand:SWIM248 1 "register_operand" "=d")
7328         (umod:SWIM248 (match_dup 2) (match_dup 3)))
7329    (use (match_operand:SWIM248 4 "register_operand" "1"))
7330    (clobber (reg:CC FLAGS_REG))]
7331   ""
7332   "div{<imodesuffix>}\t%3"
7333   [(set_attr "type" "idiv")
7334    (set_attr "mode" "<MODE>")])
7335
7336 (define_expand "udivmodqi4"
7337   [(parallel [(set (match_operand:QI 0 "register_operand" "")
7338                    (udiv:QI
7339                      (match_operand:QI 1 "register_operand" "")
7340                      (match_operand:QI 2 "nonimmediate_operand" "")))
7341               (set (match_operand:QI 3 "register_operand" "")
7342                    (umod:QI (match_dup 1) (match_dup 2)))
7343               (clobber (reg:CC FLAGS_REG))])]
7344   "TARGET_QIMODE_MATH"
7345 {
7346   rtx div, mod, insn;
7347   rtx tmp0, tmp1;
7348   
7349   tmp0 = gen_reg_rtx (HImode);
7350   tmp1 = gen_reg_rtx (HImode);
7351
7352   /* Extend operands[1] to HImode.  Generate 8bit divide.  Result is
7353      in AX.  */
7354   emit_insn (gen_zero_extendqihi2 (tmp1, operands[1]));
7355   emit_insn (gen_udivmodhiqi3 (tmp0, tmp1, operands[2]));
7356
7357   /* Extract remainder from AH.  */
7358   tmp1 = gen_rtx_ZERO_EXTRACT (SImode, tmp0, GEN_INT (8), GEN_INT (8));
7359   tmp1 = simplify_gen_subreg (QImode, tmp1, SImode, 0);
7360   insn = emit_move_insn (operands[3], tmp1);
7361
7362   mod = gen_rtx_UMOD (QImode, operands[1], operands[2]);
7363   set_unique_reg_note (insn, REG_EQUAL, mod);
7364
7365   /* Extract quotient from AL.  */
7366   insn = emit_move_insn (operands[0], gen_lowpart (QImode, tmp0));
7367
7368   div = gen_rtx_UDIV (QImode, operands[1], operands[2]);
7369   set_unique_reg_note (insn, REG_EQUAL, div);
7370
7371   DONE;
7372 })
7373
7374 (define_insn "udivmodhiqi3"
7375   [(set (match_operand:HI 0 "register_operand" "=a")
7376         (ior:HI
7377           (ashift:HI
7378             (zero_extend:HI
7379               (truncate:QI
7380                 (mod:HI (match_operand:HI 1 "register_operand" "0")
7381                         (zero_extend:HI
7382                           (match_operand:QI 2 "nonimmediate_operand" "qm")))))
7383             (const_int 8))
7384           (zero_extend:HI
7385             (truncate:QI
7386               (div:HI (match_dup 1) (zero_extend:HI (match_dup 2)))))))
7387    (clobber (reg:CC FLAGS_REG))]
7388   "TARGET_QIMODE_MATH"
7389   "div{b}\t%2"
7390   [(set_attr "type" "idiv")
7391    (set_attr "mode" "QI")])
7392
7393 ;; We cannot use div/idiv for double division, because it causes
7394 ;; "division by zero" on the overflow and that's not what we expect
7395 ;; from truncate.  Because true (non truncating) double division is
7396 ;; never generated, we can't create this insn anyway.
7397 ;
7398 ;(define_insn ""
7399 ;  [(set (match_operand:SI 0 "register_operand" "=a")
7400 ;       (truncate:SI
7401 ;         (udiv:DI (match_operand:DI 1 "register_operand" "A")
7402 ;                  (zero_extend:DI
7403 ;                    (match_operand:SI 2 "nonimmediate_operand" "rm")))))
7404 ;   (set (match_operand:SI 3 "register_operand" "=d")
7405 ;       (truncate:SI
7406 ;         (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
7407 ;   (clobber (reg:CC FLAGS_REG))]
7408 ;  ""
7409 ;  "div{l}\t{%2, %0|%0, %2}"
7410 ;  [(set_attr "type" "idiv")])
7411 \f
7412 ;;- Logical AND instructions
7413
7414 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
7415 ;; Note that this excludes ah.
7416
7417 (define_expand "testsi_ccno_1"
7418   [(set (reg:CCNO FLAGS_REG)
7419         (compare:CCNO
7420           (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
7421                   (match_operand:SI 1 "x86_64_nonmemory_operand" ""))
7422           (const_int 0)))])
7423
7424 (define_expand "testqi_ccz_1"
7425   [(set (reg:CCZ FLAGS_REG)
7426         (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
7427                              (match_operand:QI 1 "nonmemory_operand" ""))
7428                  (const_int 0)))])
7429
7430 (define_expand "testdi_ccno_1"
7431   [(set (reg:CCNO FLAGS_REG)
7432         (compare:CCNO
7433           (and:DI (match_operand:DI 0 "nonimmediate_operand" "")
7434                   (match_operand:DI 1 "x86_64_szext_general_operand" ""))
7435           (const_int 0)))]
7436   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))")
7437
7438 (define_insn "*testdi_1"
7439   [(set (reg FLAGS_REG)
7440         (compare
7441          (and:DI
7442           (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
7443           (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
7444          (const_int 0)))]
7445   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7446    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7447   "@
7448    test{l}\t{%k1, %k0|%k0, %k1}
7449    test{l}\t{%k1, %k0|%k0, %k1}
7450    test{q}\t{%1, %0|%0, %1}
7451    test{q}\t{%1, %0|%0, %1}
7452    test{q}\t{%1, %0|%0, %1}"
7453   [(set_attr "type" "test")
7454    (set_attr "modrm" "0,1,0,1,1")
7455    (set_attr "mode" "SI,SI,DI,DI,DI")])
7456
7457 (define_insn "*testqi_1_maybe_si"
7458   [(set (reg FLAGS_REG)
7459         (compare
7460           (and:QI
7461             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
7462             (match_operand:QI 1 "general_operand" "n,n,qn,n"))
7463           (const_int 0)))]
7464    "!(MEM_P (operands[0]) && MEM_P (operands[1]))
7465     && ix86_match_ccmode (insn,
7466                          CONST_INT_P (operands[1])
7467                          && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
7468 {
7469   if (which_alternative == 3)
7470     {
7471       if (CONST_INT_P (operands[1]) && INTVAL (operands[1]) < 0)
7472         operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
7473       return "test{l}\t{%1, %k0|%k0, %1}";
7474     }
7475   return "test{b}\t{%1, %0|%0, %1}";
7476 }
7477   [(set_attr "type" "test")
7478    (set_attr "modrm" "0,1,1,1")
7479    (set_attr "mode" "QI,QI,QI,SI")
7480    (set_attr "pent_pair" "uv,np,uv,np")])
7481
7482 (define_insn "*test<mode>_1"
7483   [(set (reg FLAGS_REG)
7484         (compare
7485          (and:SWI124
7486           (match_operand:SWI124 0 "nonimmediate_operand" "%!*a,<r>,<r>m")
7487           (match_operand:SWI124 1 "<general_operand>" "<i>,<i>,<r><i>"))
7488          (const_int 0)))]
7489   "ix86_match_ccmode (insn, CCNOmode)
7490    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7491   "test{<imodesuffix>}\t{%1, %0|%0, %1}"
7492   [(set_attr "type" "test")
7493    (set_attr "modrm" "0,1,1")
7494    (set_attr "mode" "<MODE>")
7495    (set_attr "pent_pair" "uv,np,uv")])
7496
7497 (define_expand "testqi_ext_ccno_0"
7498   [(set (reg:CCNO FLAGS_REG)
7499         (compare:CCNO
7500           (and:SI
7501             (zero_extract:SI
7502               (match_operand 0 "ext_register_operand" "")
7503               (const_int 8)
7504               (const_int 8))
7505             (match_operand 1 "const_int_operand" ""))
7506           (const_int 0)))])
7507
7508 (define_insn "*testqi_ext_0"
7509   [(set (reg FLAGS_REG)
7510         (compare
7511           (and:SI
7512             (zero_extract:SI
7513               (match_operand 0 "ext_register_operand" "Q")
7514               (const_int 8)
7515               (const_int 8))
7516             (match_operand 1 "const_int_operand" "n"))
7517           (const_int 0)))]
7518   "ix86_match_ccmode (insn, CCNOmode)"
7519   "test{b}\t{%1, %h0|%h0, %1}"
7520   [(set_attr "type" "test")
7521    (set_attr "mode" "QI")
7522    (set_attr "length_immediate" "1")
7523    (set_attr "modrm" "1")
7524    (set_attr "pent_pair" "np")])
7525
7526 (define_insn "*testqi_ext_1_rex64"
7527   [(set (reg FLAGS_REG)
7528         (compare
7529           (and:SI
7530             (zero_extract:SI
7531               (match_operand 0 "ext_register_operand" "Q")
7532               (const_int 8)
7533               (const_int 8))
7534             (zero_extend:SI
7535               (match_operand:QI 1 "register_operand" "Q")))
7536           (const_int 0)))]
7537   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7538   "test{b}\t{%1, %h0|%h0, %1}"
7539   [(set_attr "type" "test")
7540    (set_attr "mode" "QI")])
7541
7542 (define_insn "*testqi_ext_1"
7543   [(set (reg FLAGS_REG)
7544         (compare
7545           (and:SI
7546             (zero_extract:SI
7547               (match_operand 0 "ext_register_operand" "Q")
7548               (const_int 8)
7549               (const_int 8))
7550             (zero_extend:SI
7551               (match_operand:QI 1 "general_operand" "Qm")))
7552           (const_int 0)))]
7553   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7554   "test{b}\t{%1, %h0|%h0, %1}"
7555   [(set_attr "type" "test")
7556    (set_attr "mode" "QI")])
7557
7558 (define_insn "*testqi_ext_2"
7559   [(set (reg FLAGS_REG)
7560         (compare
7561           (and:SI
7562             (zero_extract:SI
7563               (match_operand 0 "ext_register_operand" "Q")
7564               (const_int 8)
7565               (const_int 8))
7566             (zero_extract:SI
7567               (match_operand 1 "ext_register_operand" "Q")
7568               (const_int 8)
7569               (const_int 8)))
7570           (const_int 0)))]
7571   "ix86_match_ccmode (insn, CCNOmode)"
7572   "test{b}\t{%h1, %h0|%h0, %h1}"
7573   [(set_attr "type" "test")
7574    (set_attr "mode" "QI")])
7575
7576 (define_insn "*testqi_ext_3_rex64"
7577   [(set (reg FLAGS_REG)
7578         (compare (zero_extract:DI
7579                    (match_operand 0 "nonimmediate_operand" "rm")
7580                    (match_operand:DI 1 "const_int_operand" "")
7581                    (match_operand:DI 2 "const_int_operand" ""))
7582                  (const_int 0)))]
7583   "TARGET_64BIT
7584    && ix86_match_ccmode (insn, CCNOmode)
7585    && INTVAL (operands[1]) > 0
7586    && INTVAL (operands[2]) >= 0
7587    /* Ensure that resulting mask is zero or sign extended operand.  */
7588    && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7589        || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
7590            && INTVAL (operands[1]) > 32))
7591    && (GET_MODE (operands[0]) == SImode
7592        || GET_MODE (operands[0]) == DImode
7593        || GET_MODE (operands[0]) == HImode
7594        || GET_MODE (operands[0]) == QImode)"
7595   "#")
7596
7597 ;; Combine likes to form bit extractions for some tests.  Humor it.
7598 (define_insn "*testqi_ext_3"
7599   [(set (reg FLAGS_REG)
7600         (compare (zero_extract:SI
7601                    (match_operand 0 "nonimmediate_operand" "rm")
7602                    (match_operand:SI 1 "const_int_operand" "")
7603                    (match_operand:SI 2 "const_int_operand" ""))
7604                  (const_int 0)))]
7605   "ix86_match_ccmode (insn, CCNOmode)
7606    && INTVAL (operands[1]) > 0
7607    && INTVAL (operands[2]) >= 0
7608    && INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7609    && (GET_MODE (operands[0]) == SImode
7610        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
7611        || GET_MODE (operands[0]) == HImode
7612        || GET_MODE (operands[0]) == QImode)"
7613   "#")
7614
7615 (define_split
7616   [(set (match_operand 0 "flags_reg_operand" "")
7617         (match_operator 1 "compare_operator"
7618           [(zero_extract
7619              (match_operand 2 "nonimmediate_operand" "")
7620              (match_operand 3 "const_int_operand" "")
7621              (match_operand 4 "const_int_operand" ""))
7622            (const_int 0)]))]
7623   "ix86_match_ccmode (insn, CCNOmode)"
7624   [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
7625 {
7626   rtx val = operands[2];
7627   HOST_WIDE_INT len = INTVAL (operands[3]);
7628   HOST_WIDE_INT pos = INTVAL (operands[4]);
7629   HOST_WIDE_INT mask;
7630   enum machine_mode mode, submode;
7631
7632   mode = GET_MODE (val);
7633   if (MEM_P (val))
7634     {
7635       /* ??? Combine likes to put non-volatile mem extractions in QImode
7636          no matter the size of the test.  So find a mode that works.  */
7637       if (! MEM_VOLATILE_P (val))
7638         {
7639           mode = smallest_mode_for_size (pos + len, MODE_INT);
7640           val = adjust_address (val, mode, 0);
7641         }
7642     }
7643   else if (GET_CODE (val) == SUBREG
7644            && (submode = GET_MODE (SUBREG_REG (val)),
7645                GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
7646            && pos + len <= GET_MODE_BITSIZE (submode)
7647            && GET_MODE_CLASS (submode) == MODE_INT)
7648     {
7649       /* Narrow a paradoxical subreg to prevent partial register stalls.  */
7650       mode = submode;
7651       val = SUBREG_REG (val);
7652     }
7653   else if (mode == HImode && pos + len <= 8)
7654     {
7655       /* Small HImode tests can be converted to QImode.  */
7656       mode = QImode;
7657       val = gen_lowpart (QImode, val);
7658     }
7659
7660   if (len == HOST_BITS_PER_WIDE_INT)
7661     mask = -1;
7662   else
7663     mask = ((HOST_WIDE_INT)1 << len) - 1;
7664   mask <<= pos;
7665
7666   operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
7667 })
7668
7669 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
7670 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
7671 ;; this is relatively important trick.
7672 ;; Do the conversion only post-reload to avoid limiting of the register class
7673 ;; to QI regs.
7674 (define_split
7675   [(set (match_operand 0 "flags_reg_operand" "")
7676         (match_operator 1 "compare_operator"
7677           [(and (match_operand 2 "register_operand" "")
7678                 (match_operand 3 "const_int_operand" ""))
7679            (const_int 0)]))]
7680    "reload_completed
7681     && QI_REG_P (operands[2])
7682     && GET_MODE (operands[2]) != QImode
7683     && ((ix86_match_ccmode (insn, CCZmode)
7684          && !(INTVAL (operands[3]) & ~(255 << 8)))
7685         || (ix86_match_ccmode (insn, CCNOmode)
7686             && !(INTVAL (operands[3]) & ~(127 << 8))))"
7687   [(set (match_dup 0)
7688         (match_op_dup 1
7689           [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
7690                    (match_dup 3))
7691            (const_int 0)]))]
7692   "operands[2] = gen_lowpart (SImode, operands[2]);
7693    operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);")
7694
7695 (define_split
7696   [(set (match_operand 0 "flags_reg_operand" "")
7697         (match_operator 1 "compare_operator"
7698           [(and (match_operand 2 "nonimmediate_operand" "")
7699                 (match_operand 3 "const_int_operand" ""))
7700            (const_int 0)]))]
7701    "reload_completed
7702     && GET_MODE (operands[2]) != QImode
7703     && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
7704     && ((ix86_match_ccmode (insn, CCZmode)
7705          && !(INTVAL (operands[3]) & ~255))
7706         || (ix86_match_ccmode (insn, CCNOmode)
7707             && !(INTVAL (operands[3]) & ~127)))"
7708   [(set (match_dup 0)
7709         (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
7710                          (const_int 0)]))]
7711   "operands[2] = gen_lowpart (QImode, operands[2]);
7712    operands[3] = gen_lowpart (QImode, operands[3]);")
7713
7714 ;; %%% This used to optimize known byte-wide and operations to memory,
7715 ;; and sometimes to QImode registers.  If this is considered useful,
7716 ;; it should be done with splitters.
7717
7718 (define_expand "and<mode>3"
7719   [(set (match_operand:SWIM 0 "nonimmediate_operand" "")
7720         (and:SWIM (match_operand:SWIM 1 "nonimmediate_operand" "")
7721                   (match_operand:SWIM 2 "<general_szext_operand>" "")))]
7722   ""
7723   "ix86_expand_binary_operator (AND, <MODE>mode, operands); DONE;")
7724
7725 (define_insn "*anddi_1"
7726   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
7727         (and:DI
7728          (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
7729          (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
7730    (clobber (reg:CC FLAGS_REG))]
7731   "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
7732 {
7733   switch (get_attr_type (insn))
7734     {
7735     case TYPE_IMOVX:
7736       {
7737         enum machine_mode mode;
7738
7739         gcc_assert (CONST_INT_P (operands[2]));
7740         if (INTVAL (operands[2]) == 0xff)
7741           mode = QImode;
7742         else
7743           {
7744             gcc_assert (INTVAL (operands[2]) == 0xffff);
7745             mode = HImode;
7746           }
7747
7748         operands[1] = gen_lowpart (mode, operands[1]);
7749         if (mode == QImode)
7750           return "movz{bl|x}\t{%1, %k0|%k0, %1}";
7751         else
7752           return "movz{wl|x}\t{%1, %k0|%k0, %1}";
7753       }
7754
7755     default:
7756       gcc_assert (rtx_equal_p (operands[0], operands[1]));
7757       if (get_attr_mode (insn) == MODE_SI)
7758         return "and{l}\t{%k2, %k0|%k0, %k2}";
7759       else
7760         return "and{q}\t{%2, %0|%0, %2}";
7761     }
7762 }
7763   [(set_attr "type" "alu,alu,alu,imovx")
7764    (set_attr "length_immediate" "*,*,*,0")
7765    (set (attr "prefix_rex")
7766      (if_then_else
7767        (and (eq_attr "type" "imovx")
7768             (and (match_test "INTVAL (operands[2]) == 0xff")
7769                  (match_operand 1 "ext_QIreg_operand" "")))
7770        (const_string "1")
7771        (const_string "*")))
7772    (set_attr "mode" "SI,DI,DI,SI")])
7773
7774 (define_insn "*andsi_1"
7775   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
7776         (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
7777                 (match_operand:SI 2 "x86_64_general_operand" "re,rm,L")))
7778    (clobber (reg:CC FLAGS_REG))]
7779   "ix86_binary_operator_ok (AND, SImode, operands)"
7780 {
7781   switch (get_attr_type (insn))
7782     {
7783     case TYPE_IMOVX:
7784       {
7785         enum machine_mode mode;
7786
7787         gcc_assert (CONST_INT_P (operands[2]));
7788         if (INTVAL (operands[2]) == 0xff)
7789           mode = QImode;
7790         else
7791           {
7792             gcc_assert (INTVAL (operands[2]) == 0xffff);
7793             mode = HImode;
7794           }
7795
7796         operands[1] = gen_lowpart (mode, operands[1]);
7797         if (mode == QImode)
7798           return "movz{bl|x}\t{%1, %0|%0, %1}";
7799         else
7800           return "movz{wl|x}\t{%1, %0|%0, %1}";
7801       }
7802
7803     default:
7804       gcc_assert (rtx_equal_p (operands[0], operands[1]));
7805       return "and{l}\t{%2, %0|%0, %2}";
7806     }
7807 }
7808   [(set_attr "type" "alu,alu,imovx")
7809    (set (attr "prefix_rex")
7810      (if_then_else
7811        (and (eq_attr "type" "imovx")
7812             (and (match_test "INTVAL (operands[2]) == 0xff")
7813                  (match_operand 1 "ext_QIreg_operand" "")))
7814        (const_string "1")
7815        (const_string "*")))
7816    (set_attr "length_immediate" "*,*,0")
7817    (set_attr "mode" "SI")])
7818
7819 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
7820 (define_insn "*andsi_1_zext"
7821   [(set (match_operand:DI 0 "register_operand" "=r")
7822         (zero_extend:DI
7823           (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
7824                   (match_operand:SI 2 "x86_64_general_operand" "rme"))))
7825    (clobber (reg:CC FLAGS_REG))]
7826   "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
7827   "and{l}\t{%2, %k0|%k0, %2}"
7828   [(set_attr "type" "alu")
7829    (set_attr "mode" "SI")])
7830
7831 (define_insn "*andhi_1"
7832   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
7833         (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
7834                 (match_operand:HI 2 "general_operand" "rn,rm,L")))
7835    (clobber (reg:CC FLAGS_REG))]
7836   "ix86_binary_operator_ok (AND, HImode, operands)"
7837 {
7838   switch (get_attr_type (insn))
7839     {
7840     case TYPE_IMOVX:
7841       gcc_assert (CONST_INT_P (operands[2]));
7842       gcc_assert (INTVAL (operands[2]) == 0xff);
7843       return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
7844
7845     default:
7846       gcc_assert (rtx_equal_p (operands[0], operands[1]));
7847
7848       return "and{w}\t{%2, %0|%0, %2}";
7849     }
7850 }
7851   [(set_attr "type" "alu,alu,imovx")
7852    (set_attr "length_immediate" "*,*,0")
7853    (set (attr "prefix_rex")
7854      (if_then_else
7855        (and (eq_attr "type" "imovx")
7856             (match_operand 1 "ext_QIreg_operand" ""))
7857        (const_string "1")
7858        (const_string "*")))
7859    (set_attr "mode" "HI,HI,SI")])
7860
7861 ;; %%% Potential partial reg stall on alternative 2.  What to do?
7862 (define_insn "*andqi_1"
7863   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
7864         (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7865                 (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
7866    (clobber (reg:CC FLAGS_REG))]
7867   "ix86_binary_operator_ok (AND, QImode, operands)"
7868   "@
7869    and{b}\t{%2, %0|%0, %2}
7870    and{b}\t{%2, %0|%0, %2}
7871    and{l}\t{%k2, %k0|%k0, %k2}"
7872   [(set_attr "type" "alu")
7873    (set_attr "mode" "QI,QI,SI")])
7874
7875 (define_insn "*andqi_1_slp"
7876   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
7877         (and:QI (match_dup 0)
7878                 (match_operand:QI 1 "general_operand" "qn,qmn")))
7879    (clobber (reg:CC FLAGS_REG))]
7880   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7881    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7882   "and{b}\t{%1, %0|%0, %1}"
7883   [(set_attr "type" "alu1")
7884    (set_attr "mode" "QI")])
7885
7886 (define_split
7887   [(set (match_operand 0 "register_operand" "")
7888         (and (match_dup 0)
7889              (const_int -65536)))
7890    (clobber (reg:CC FLAGS_REG))]
7891   "(TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)
7892     || optimize_function_for_size_p (cfun)"
7893   [(set (strict_low_part (match_dup 1)) (const_int 0))]
7894   "operands[1] = gen_lowpart (HImode, operands[0]);")
7895
7896 (define_split
7897   [(set (match_operand 0 "ext_register_operand" "")
7898         (and (match_dup 0)
7899              (const_int -256)))
7900    (clobber (reg:CC FLAGS_REG))]
7901   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7902    && reload_completed"
7903   [(set (strict_low_part (match_dup 1)) (const_int 0))]
7904   "operands[1] = gen_lowpart (QImode, operands[0]);")
7905
7906 (define_split
7907   [(set (match_operand 0 "ext_register_operand" "")
7908         (and (match_dup 0)
7909              (const_int -65281)))
7910    (clobber (reg:CC FLAGS_REG))]
7911   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
7912    && reload_completed"
7913   [(parallel [(set (zero_extract:SI (match_dup 0)
7914                                     (const_int 8)
7915                                     (const_int 8))
7916                    (xor:SI
7917                      (zero_extract:SI (match_dup 0)
7918                                       (const_int 8)
7919                                       (const_int 8))
7920                      (zero_extract:SI (match_dup 0)
7921                                       (const_int 8)
7922                                       (const_int 8))))
7923               (clobber (reg:CC FLAGS_REG))])]
7924   "operands[0] = gen_lowpart (SImode, operands[0]);")
7925
7926 (define_insn "*anddi_2"
7927   [(set (reg FLAGS_REG)
7928         (compare
7929          (and:DI
7930           (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
7931           (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
7932          (const_int 0)))
7933    (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
7934         (and:DI (match_dup 1) (match_dup 2)))]
7935   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7936    && ix86_binary_operator_ok (AND, DImode, operands)"
7937   "@
7938    and{l}\t{%k2, %k0|%k0, %k2}
7939    and{q}\t{%2, %0|%0, %2}
7940    and{q}\t{%2, %0|%0, %2}"
7941   [(set_attr "type" "alu")
7942    (set_attr "mode" "SI,DI,DI")])
7943
7944 (define_insn "*andqi_2_maybe_si"
7945   [(set (reg FLAGS_REG)
7946         (compare (and:QI
7947                   (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7948                   (match_operand:QI 2 "general_operand" "qmn,qn,n"))
7949                  (const_int 0)))
7950    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
7951         (and:QI (match_dup 1) (match_dup 2)))]
7952   "ix86_binary_operator_ok (AND, QImode, operands)
7953    && ix86_match_ccmode (insn,
7954                          CONST_INT_P (operands[2])
7955                          && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
7956 {
7957   if (which_alternative == 2)
7958     {
7959       if (CONST_INT_P (operands[2]) && INTVAL (operands[2]) < 0)
7960         operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
7961       return "and{l}\t{%2, %k0|%k0, %2}";
7962     }
7963   return "and{b}\t{%2, %0|%0, %2}";
7964 }
7965   [(set_attr "type" "alu")
7966    (set_attr "mode" "QI,QI,SI")])
7967
7968 (define_insn "*and<mode>_2"
7969   [(set (reg FLAGS_REG)
7970         (compare (and:SWI124
7971                   (match_operand:SWI124 1 "nonimmediate_operand" "%0,0")
7972                   (match_operand:SWI124 2 "<general_operand>" "<g>,<r><i>"))
7973                  (const_int 0)))
7974    (set (match_operand:SWI124 0 "nonimmediate_operand" "=<r>,<r>m")
7975         (and:SWI124 (match_dup 1) (match_dup 2)))]
7976   "ix86_match_ccmode (insn, CCNOmode)
7977    && ix86_binary_operator_ok (AND, <MODE>mode, operands)"
7978   "and{<imodesuffix>}\t{%2, %0|%0, %2}"
7979   [(set_attr "type" "alu")
7980    (set_attr "mode" "<MODE>")])
7981
7982 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
7983 (define_insn "*andsi_2_zext"
7984   [(set (reg FLAGS_REG)
7985         (compare (and:SI
7986                   (match_operand:SI 1 "nonimmediate_operand" "%0")
7987                   (match_operand:SI 2 "x86_64_general_operand" "rme"))
7988                  (const_int 0)))
7989    (set (match_operand:DI 0 "register_operand" "=r")
7990         (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
7991   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7992    && ix86_binary_operator_ok (AND, SImode, operands)"
7993   "and{l}\t{%2, %k0|%k0, %2}"
7994   [(set_attr "type" "alu")
7995    (set_attr "mode" "SI")])
7996
7997 (define_insn "*andqi_2_slp"
7998   [(set (reg FLAGS_REG)
7999         (compare (and:QI
8000                    (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8001                    (match_operand:QI 1 "nonimmediate_operand" "qmn,qn"))
8002                  (const_int 0)))
8003    (set (strict_low_part (match_dup 0))
8004         (and:QI (match_dup 0) (match_dup 1)))]
8005   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8006    && ix86_match_ccmode (insn, CCNOmode)
8007    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8008   "and{b}\t{%1, %0|%0, %1}"
8009   [(set_attr "type" "alu1")
8010    (set_attr "mode" "QI")])
8011
8012 ;; ??? A bug in recog prevents it from recognizing a const_int as an
8013 ;; operand to zero_extend in andqi_ext_1.  It was checking explicitly
8014 ;; for a QImode operand, which of course failed.
8015 (define_insn "andqi_ext_0"
8016   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8017                          (const_int 8)
8018                          (const_int 8))
8019         (and:SI
8020           (zero_extract:SI
8021             (match_operand 1 "ext_register_operand" "0")
8022             (const_int 8)
8023             (const_int 8))
8024           (match_operand 2 "const_int_operand" "n")))
8025    (clobber (reg:CC FLAGS_REG))]
8026   ""
8027   "and{b}\t{%2, %h0|%h0, %2}"
8028   [(set_attr "type" "alu")
8029    (set_attr "length_immediate" "1")
8030    (set_attr "modrm" "1")
8031    (set_attr "mode" "QI")])
8032
8033 ;; Generated by peephole translating test to and.  This shows up
8034 ;; often in fp comparisons.
8035 (define_insn "*andqi_ext_0_cc"
8036   [(set (reg FLAGS_REG)
8037         (compare
8038           (and:SI
8039             (zero_extract:SI
8040               (match_operand 1 "ext_register_operand" "0")
8041               (const_int 8)
8042               (const_int 8))
8043             (match_operand 2 "const_int_operand" "n"))
8044           (const_int 0)))
8045    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8046                          (const_int 8)
8047                          (const_int 8))
8048         (and:SI
8049           (zero_extract:SI
8050             (match_dup 1)
8051             (const_int 8)
8052             (const_int 8))
8053           (match_dup 2)))]
8054   "ix86_match_ccmode (insn, CCNOmode)"
8055   "and{b}\t{%2, %h0|%h0, %2}"
8056   [(set_attr "type" "alu")
8057    (set_attr "length_immediate" "1")
8058    (set_attr "modrm" "1")
8059    (set_attr "mode" "QI")])
8060
8061 (define_insn "*andqi_ext_1_rex64"
8062   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8063                          (const_int 8)
8064                          (const_int 8))
8065         (and:SI
8066           (zero_extract:SI
8067             (match_operand 1 "ext_register_operand" "0")
8068             (const_int 8)
8069             (const_int 8))
8070           (zero_extend:SI
8071             (match_operand 2 "ext_register_operand" "Q"))))
8072    (clobber (reg:CC FLAGS_REG))]
8073   "TARGET_64BIT"
8074   "and{b}\t{%2, %h0|%h0, %2}"
8075   [(set_attr "type" "alu")
8076    (set_attr "length_immediate" "0")
8077    (set_attr "mode" "QI")])
8078
8079 (define_insn "*andqi_ext_1"
8080   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8081                          (const_int 8)
8082                          (const_int 8))
8083         (and:SI
8084           (zero_extract:SI
8085             (match_operand 1 "ext_register_operand" "0")
8086             (const_int 8)
8087             (const_int 8))
8088           (zero_extend:SI
8089             (match_operand:QI 2 "general_operand" "Qm"))))
8090    (clobber (reg:CC FLAGS_REG))]
8091   "!TARGET_64BIT"
8092   "and{b}\t{%2, %h0|%h0, %2}"
8093   [(set_attr "type" "alu")
8094    (set_attr "length_immediate" "0")
8095    (set_attr "mode" "QI")])
8096
8097 (define_insn "*andqi_ext_2"
8098   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8099                          (const_int 8)
8100                          (const_int 8))
8101         (and:SI
8102           (zero_extract:SI
8103             (match_operand 1 "ext_register_operand" "%0")
8104             (const_int 8)
8105             (const_int 8))
8106           (zero_extract:SI
8107             (match_operand 2 "ext_register_operand" "Q")
8108             (const_int 8)
8109             (const_int 8))))
8110    (clobber (reg:CC FLAGS_REG))]
8111   ""
8112   "and{b}\t{%h2, %h0|%h0, %h2}"
8113   [(set_attr "type" "alu")
8114    (set_attr "length_immediate" "0")
8115    (set_attr "mode" "QI")])
8116
8117 ;; Convert wide AND instructions with immediate operand to shorter QImode
8118 ;; equivalents when possible.
8119 ;; Don't do the splitting with memory operands, since it introduces risk
8120 ;; of memory mismatch stalls.  We may want to do the splitting for optimizing
8121 ;; for size, but that can (should?) be handled by generic code instead.
8122 (define_split
8123   [(set (match_operand 0 "register_operand" "")
8124         (and (match_operand 1 "register_operand" "")
8125              (match_operand 2 "const_int_operand" "")))
8126    (clobber (reg:CC FLAGS_REG))]
8127    "reload_completed
8128     && QI_REG_P (operands[0])
8129     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8130     && !(~INTVAL (operands[2]) & ~(255 << 8))
8131     && GET_MODE (operands[0]) != QImode"
8132   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8133                    (and:SI (zero_extract:SI (match_dup 1)
8134                                             (const_int 8) (const_int 8))
8135                            (match_dup 2)))
8136               (clobber (reg:CC FLAGS_REG))])]
8137   "operands[0] = gen_lowpart (SImode, operands[0]);
8138    operands[1] = gen_lowpart (SImode, operands[1]);
8139    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8140
8141 ;; Since AND can be encoded with sign extended immediate, this is only
8142 ;; profitable when 7th bit is not set.
8143 (define_split
8144   [(set (match_operand 0 "register_operand" "")
8145         (and (match_operand 1 "general_operand" "")
8146              (match_operand 2 "const_int_operand" "")))
8147    (clobber (reg:CC FLAGS_REG))]
8148    "reload_completed
8149     && ANY_QI_REG_P (operands[0])
8150     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8151     && !(~INTVAL (operands[2]) & ~255)
8152     && !(INTVAL (operands[2]) & 128)
8153     && GET_MODE (operands[0]) != QImode"
8154   [(parallel [(set (strict_low_part (match_dup 0))
8155                    (and:QI (match_dup 1)
8156                            (match_dup 2)))
8157               (clobber (reg:CC FLAGS_REG))])]
8158   "operands[0] = gen_lowpart (QImode, operands[0]);
8159    operands[1] = gen_lowpart (QImode, operands[1]);
8160    operands[2] = gen_lowpart (QImode, operands[2]);")
8161 \f
8162 ;; Logical inclusive and exclusive OR instructions
8163
8164 ;; %%% This used to optimize known byte-wide and operations to memory.
8165 ;; If this is considered useful, it should be done with splitters.
8166
8167 (define_expand "<code><mode>3"
8168   [(set (match_operand:SWIM 0 "nonimmediate_operand" "")
8169         (any_or:SWIM (match_operand:SWIM 1 "nonimmediate_operand" "")
8170                      (match_operand:SWIM 2 "<general_operand>" "")))]
8171   ""
8172   "ix86_expand_binary_operator (<CODE>, <MODE>mode, operands); DONE;")
8173
8174 (define_insn "*<code><mode>_1"
8175   [(set (match_operand:SWI248 0 "nonimmediate_operand" "=r,rm")
8176         (any_or:SWI248
8177          (match_operand:SWI248 1 "nonimmediate_operand" "%0,0")
8178          (match_operand:SWI248 2 "<general_operand>" "<g>,r<i>")))
8179    (clobber (reg:CC FLAGS_REG))]
8180   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
8181   "<logic>{<imodesuffix>}\t{%2, %0|%0, %2}"
8182   [(set_attr "type" "alu")
8183    (set_attr "mode" "<MODE>")])
8184
8185 ;; %%% Potential partial reg stall on alternative 2.  What to do?
8186 (define_insn "*<code>qi_1"
8187   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
8188         (any_or:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8189                    (match_operand:QI 2 "general_operand" "qmn,qn,rn")))
8190    (clobber (reg:CC FLAGS_REG))]
8191   "ix86_binary_operator_ok (<CODE>, QImode, operands)"
8192   "@
8193    <logic>{b}\t{%2, %0|%0, %2}
8194    <logic>{b}\t{%2, %0|%0, %2}
8195    <logic>{l}\t{%k2, %k0|%k0, %k2}"
8196   [(set_attr "type" "alu")
8197    (set_attr "mode" "QI,QI,SI")])
8198
8199 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8200 (define_insn "*<code>si_1_zext"
8201   [(set (match_operand:DI 0 "register_operand" "=r")
8202         (zero_extend:DI
8203          (any_or:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8204                     (match_operand:SI 2 "x86_64_general_operand" "rme"))))
8205    (clobber (reg:CC FLAGS_REG))]
8206   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8207   "<logic>{l}\t{%2, %k0|%k0, %2}"
8208   [(set_attr "type" "alu")
8209    (set_attr "mode" "SI")])
8210
8211 (define_insn "*<code>si_1_zext_imm"
8212   [(set (match_operand:DI 0 "register_operand" "=r")
8213         (any_or:DI
8214          (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8215          (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8216    (clobber (reg:CC FLAGS_REG))]
8217   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8218   "<logic>{l}\t{%2, %k0|%k0, %2}"
8219   [(set_attr "type" "alu")
8220    (set_attr "mode" "SI")])
8221
8222 (define_insn "*<code>qi_1_slp"
8223   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
8224         (any_or:QI (match_dup 0)
8225                    (match_operand:QI 1 "general_operand" "qmn,qn")))
8226    (clobber (reg:CC FLAGS_REG))]
8227   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8228    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8229   "<logic>{b}\t{%1, %0|%0, %1}"
8230   [(set_attr "type" "alu1")
8231    (set_attr "mode" "QI")])
8232
8233 (define_insn "*<code><mode>_2"
8234   [(set (reg FLAGS_REG)
8235         (compare (any_or:SWI
8236                   (match_operand:SWI 1 "nonimmediate_operand" "%0,0")
8237                   (match_operand:SWI 2 "<general_operand>" "<g>,<r><i>"))
8238                  (const_int 0)))
8239    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>,<r>m")
8240         (any_or:SWI (match_dup 1) (match_dup 2)))]
8241   "ix86_match_ccmode (insn, CCNOmode)
8242    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
8243   "<logic>{<imodesuffix>}\t{%2, %0|%0, %2}"
8244   [(set_attr "type" "alu")
8245    (set_attr "mode" "<MODE>")])
8246
8247 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8248 ;; ??? Special case for immediate operand is missing - it is tricky.
8249 (define_insn "*<code>si_2_zext"
8250   [(set (reg FLAGS_REG)
8251         (compare (any_or:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8252                             (match_operand:SI 2 "x86_64_general_operand" "rme"))
8253                  (const_int 0)))
8254    (set (match_operand:DI 0 "register_operand" "=r")
8255         (zero_extend:DI (any_or:SI (match_dup 1) (match_dup 2))))]
8256   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8257    && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8258   "<logic>{l}\t{%2, %k0|%k0, %2}"
8259   [(set_attr "type" "alu")
8260    (set_attr "mode" "SI")])
8261
8262 (define_insn "*<code>si_2_zext_imm"
8263   [(set (reg FLAGS_REG)
8264         (compare (any_or:SI
8265                   (match_operand:SI 1 "nonimmediate_operand" "%0")
8266                   (match_operand:SI 2 "x86_64_zext_immediate_operand" "Z"))
8267                  (const_int 0)))
8268    (set (match_operand:DI 0 "register_operand" "=r")
8269         (any_or:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8270   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8271    && ix86_binary_operator_ok (<CODE>, SImode, operands)"
8272   "<logic>{l}\t{%2, %k0|%k0, %2}"
8273   [(set_attr "type" "alu")
8274    (set_attr "mode" "SI")])
8275
8276 (define_insn "*<code>qi_2_slp"
8277   [(set (reg FLAGS_REG)
8278         (compare (any_or:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8279                             (match_operand:QI 1 "general_operand" "qmn,qn"))
8280                  (const_int 0)))
8281    (set (strict_low_part (match_dup 0))
8282         (any_or:QI (match_dup 0) (match_dup 1)))]
8283   "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8284    && ix86_match_ccmode (insn, CCNOmode)
8285    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8286   "<logic>{b}\t{%1, %0|%0, %1}"
8287   [(set_attr "type" "alu1")
8288    (set_attr "mode" "QI")])
8289
8290 (define_insn "*<code><mode>_3"
8291   [(set (reg FLAGS_REG)
8292         (compare (any_or:SWI
8293                   (match_operand:SWI 1 "nonimmediate_operand" "%0")
8294                   (match_operand:SWI 2 "<general_operand>" "<g>"))
8295                  (const_int 0)))
8296    (clobber (match_scratch:SWI 0 "=<r>"))]
8297   "ix86_match_ccmode (insn, CCNOmode)
8298    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8299   "<logic>{<imodesuffix>}\t{%2, %0|%0, %2}"
8300   [(set_attr "type" "alu")
8301    (set_attr "mode" "<MODE>")])
8302
8303 (define_insn "*<code>qi_ext_0"
8304   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8305                          (const_int 8)
8306                          (const_int 8))
8307         (any_or:SI
8308           (zero_extract:SI
8309             (match_operand 1 "ext_register_operand" "0")
8310             (const_int 8)
8311             (const_int 8))
8312           (match_operand 2 "const_int_operand" "n")))
8313    (clobber (reg:CC FLAGS_REG))]
8314   "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
8315   "<logic>{b}\t{%2, %h0|%h0, %2}"
8316   [(set_attr "type" "alu")
8317    (set_attr "length_immediate" "1")
8318    (set_attr "modrm" "1")
8319    (set_attr "mode" "QI")])
8320
8321 (define_insn "*<code>qi_ext_1_rex64"
8322   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8323                          (const_int 8)
8324                          (const_int 8))
8325         (any_or:SI
8326           (zero_extract:SI
8327             (match_operand 1 "ext_register_operand" "0")
8328             (const_int 8)
8329             (const_int 8))
8330           (zero_extend:SI
8331             (match_operand 2 "ext_register_operand" "Q"))))
8332    (clobber (reg:CC FLAGS_REG))]
8333   "TARGET_64BIT
8334    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
8335   "<logic>{b}\t{%2, %h0|%h0, %2}"
8336   [(set_attr "type" "alu")
8337    (set_attr "length_immediate" "0")
8338    (set_attr "mode" "QI")])
8339
8340 (define_insn "*<code>qi_ext_1"
8341   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8342                          (const_int 8)
8343                          (const_int 8))
8344         (any_or:SI
8345           (zero_extract:SI
8346             (match_operand 1 "ext_register_operand" "0")
8347             (const_int 8)
8348             (const_int 8))
8349           (zero_extend:SI
8350             (match_operand:QI 2 "general_operand" "Qm"))))
8351    (clobber (reg:CC FLAGS_REG))]
8352   "!TARGET_64BIT
8353    && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))"
8354   "<logic>{b}\t{%2, %h0|%h0, %2}"
8355   [(set_attr "type" "alu")
8356    (set_attr "length_immediate" "0")
8357    (set_attr "mode" "QI")])
8358
8359 (define_insn "*<code>qi_ext_2"
8360   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8361                          (const_int 8)
8362                          (const_int 8))
8363         (any_or:SI
8364           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
8365                            (const_int 8)
8366                            (const_int 8))
8367           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
8368                            (const_int 8)
8369                            (const_int 8))))
8370    (clobber (reg:CC FLAGS_REG))]
8371   "!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)"
8372   "<logic>{b}\t{%h2, %h0|%h0, %h2}"
8373   [(set_attr "type" "alu")
8374    (set_attr "length_immediate" "0")
8375    (set_attr "mode" "QI")])
8376
8377 (define_split
8378   [(set (match_operand 0 "register_operand" "")
8379         (any_or (match_operand 1 "register_operand" "")
8380                 (match_operand 2 "const_int_operand" "")))
8381    (clobber (reg:CC FLAGS_REG))]
8382    "reload_completed
8383     && QI_REG_P (operands[0])
8384     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8385     && !(INTVAL (operands[2]) & ~(255 << 8))
8386     && GET_MODE (operands[0]) != QImode"
8387   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8388                    (any_or:SI (zero_extract:SI (match_dup 1)
8389                                                (const_int 8) (const_int 8))
8390                               (match_dup 2)))
8391               (clobber (reg:CC FLAGS_REG))])]
8392   "operands[0] = gen_lowpart (SImode, operands[0]);
8393    operands[1] = gen_lowpart (SImode, operands[1]);
8394    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8395
8396 ;; Since OR can be encoded with sign extended immediate, this is only
8397 ;; profitable when 7th bit is set.
8398 (define_split
8399   [(set (match_operand 0 "register_operand" "")
8400         (any_or (match_operand 1 "general_operand" "")
8401                 (match_operand 2 "const_int_operand" "")))
8402    (clobber (reg:CC FLAGS_REG))]
8403    "reload_completed
8404     && ANY_QI_REG_P (operands[0])
8405     && (!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun))
8406     && !(INTVAL (operands[2]) & ~255)
8407     && (INTVAL (operands[2]) & 128)
8408     && GET_MODE (operands[0]) != QImode"
8409   [(parallel [(set (strict_low_part (match_dup 0))
8410                    (any_or:QI (match_dup 1)
8411                               (match_dup 2)))
8412               (clobber (reg:CC FLAGS_REG))])]
8413   "operands[0] = gen_lowpart (QImode, operands[0]);
8414    operands[1] = gen_lowpart (QImode, operands[1]);
8415    operands[2] = gen_lowpart (QImode, operands[2]);")
8416
8417 (define_expand "xorqi_cc_ext_1"
8418   [(parallel [
8419      (set (reg:CCNO FLAGS_REG)
8420           (compare:CCNO
8421             (xor:SI
8422               (zero_extract:SI
8423                 (match_operand 1 "ext_register_operand" "")
8424                 (const_int 8)
8425                 (const_int 8))
8426               (match_operand:QI 2 "general_operand" ""))
8427             (const_int 0)))
8428      (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
8429                            (const_int 8)
8430                            (const_int 8))
8431           (xor:SI
8432             (zero_extract:SI
8433              (match_dup 1)
8434              (const_int 8)
8435              (const_int 8))
8436             (match_dup 2)))])])
8437
8438 (define_insn "*xorqi_cc_ext_1_rex64"
8439   [(set (reg FLAGS_REG)
8440         (compare
8441           (xor:SI
8442             (zero_extract:SI
8443               (match_operand 1 "ext_register_operand" "0")
8444               (const_int 8)
8445               (const_int 8))
8446             (match_operand:QI 2 "nonmemory_operand" "Qn"))
8447           (const_int 0)))
8448    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8449                          (const_int 8)
8450                          (const_int 8))
8451         (xor:SI
8452           (zero_extract:SI
8453            (match_dup 1)
8454            (const_int 8)
8455            (const_int 8))
8456           (match_dup 2)))]
8457   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
8458   "xor{b}\t{%2, %h0|%h0, %2}"
8459   [(set_attr "type" "alu")
8460    (set_attr "modrm" "1")
8461    (set_attr "mode" "QI")])
8462
8463 (define_insn "*xorqi_cc_ext_1"
8464   [(set (reg FLAGS_REG)
8465         (compare
8466           (xor:SI
8467             (zero_extract:SI
8468               (match_operand 1 "ext_register_operand" "0")
8469               (const_int 8)
8470               (const_int 8))
8471             (match_operand:QI 2 "general_operand" "qmn"))
8472           (const_int 0)))
8473    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
8474                          (const_int 8)
8475                          (const_int 8))
8476         (xor:SI
8477           (zero_extract:SI
8478            (match_dup 1)
8479            (const_int 8)
8480            (const_int 8))
8481           (match_dup 2)))]
8482   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
8483   "xor{b}\t{%2, %h0|%h0, %2}"
8484   [(set_attr "type" "alu")
8485    (set_attr "modrm" "1")
8486    (set_attr "mode" "QI")])
8487 \f
8488 ;; Negation instructions
8489
8490 (define_expand "neg<mode>2"
8491   [(set (match_operand:SDWIM 0 "nonimmediate_operand" "")
8492         (neg:SDWIM (match_operand:SDWIM 1 "nonimmediate_operand" "")))]
8493   ""
8494   "ix86_expand_unary_operator (NEG, <MODE>mode, operands); DONE;")
8495
8496 (define_insn_and_split "*neg<dwi>2_doubleword"
8497   [(set (match_operand:<DWI> 0 "nonimmediate_operand" "=ro")
8498         (neg:<DWI> (match_operand:<DWI> 1 "nonimmediate_operand" "0")))
8499    (clobber (reg:CC FLAGS_REG))]
8500   "ix86_unary_operator_ok (NEG, <DWI>mode, operands)"
8501   "#"
8502   "reload_completed"
8503   [(parallel
8504     [(set (reg:CCZ FLAGS_REG)
8505           (compare:CCZ (neg:DWIH (match_dup 1)) (const_int 0)))
8506      (set (match_dup 0) (neg:DWIH (match_dup 1)))])
8507    (parallel
8508     [(set (match_dup 2)
8509           (plus:DWIH (match_dup 3)
8510                      (plus:DWIH (ltu:DWIH (reg:CC FLAGS_REG) (const_int 0))
8511                                 (const_int 0))))
8512      (clobber (reg:CC FLAGS_REG))])
8513    (parallel
8514     [(set (match_dup 2)
8515           (neg:DWIH (match_dup 2)))
8516      (clobber (reg:CC FLAGS_REG))])]
8517   "split_double_mode (<DWI>mode, &operands[0], 2, &operands[0], &operands[2]);")
8518
8519 (define_insn "*neg<mode>2_1"
8520   [(set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
8521         (neg:SWI (match_operand:SWI 1 "nonimmediate_operand" "0")))
8522    (clobber (reg:CC FLAGS_REG))]
8523   "ix86_unary_operator_ok (NEG, <MODE>mode, operands)"
8524   "neg{<imodesuffix>}\t%0"
8525   [(set_attr "type" "negnot")
8526    (set_attr "mode" "<MODE>")])
8527
8528 ;; Combine is quite creative about this pattern.
8529 (define_insn "*negsi2_1_zext"
8530   [(set (match_operand:DI 0 "register_operand" "=r")
8531         (lshiftrt:DI
8532           (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
8533                              (const_int 32)))
8534         (const_int 32)))
8535    (clobber (reg:CC FLAGS_REG))]
8536   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
8537   "neg{l}\t%k0"
8538   [(set_attr "type" "negnot")
8539    (set_attr "mode" "SI")])
8540
8541 ;; The problem with neg is that it does not perform (compare x 0),
8542 ;; it really performs (compare 0 x), which leaves us with the zero
8543 ;; flag being the only useful item.
8544
8545 (define_insn "*neg<mode>2_cmpz"
8546   [(set (reg:CCZ FLAGS_REG)
8547         (compare:CCZ
8548           (neg:SWI (match_operand:SWI 1 "nonimmediate_operand" "0"))
8549                    (const_int 0)))
8550    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
8551         (neg:SWI (match_dup 1)))]
8552   "ix86_unary_operator_ok (NEG, <MODE>mode, operands)"
8553   "neg{<imodesuffix>}\t%0"
8554   [(set_attr "type" "negnot")
8555    (set_attr "mode" "<MODE>")])
8556
8557 (define_insn "*negsi2_cmpz_zext"
8558   [(set (reg:CCZ FLAGS_REG)
8559         (compare:CCZ
8560           (lshiftrt:DI
8561             (neg:DI (ashift:DI
8562                       (match_operand:DI 1 "register_operand" "0")
8563                       (const_int 32)))
8564             (const_int 32))
8565           (const_int 0)))
8566    (set (match_operand:DI 0 "register_operand" "=r")
8567         (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
8568                                         (const_int 32)))
8569                      (const_int 32)))]
8570   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
8571   "neg{l}\t%k0"
8572   [(set_attr "type" "negnot")
8573    (set_attr "mode" "SI")])
8574
8575 ;; Changing of sign for FP values is doable using integer unit too.
8576
8577 (define_expand "<code><mode>2"
8578   [(set (match_operand:X87MODEF 0 "register_operand" "")
8579         (absneg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "")))]
8580   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
8581   "ix86_expand_fp_absneg_operator (<CODE>, <MODE>mode, operands); DONE;")
8582
8583 (define_insn "*absneg<mode>2_mixed"
8584   [(set (match_operand:MODEF 0 "register_operand" "=x,x,f,!r")
8585         (match_operator:MODEF 3 "absneg_operator"
8586           [(match_operand:MODEF 1 "register_operand" "0,x,0,0")]))
8587    (use (match_operand:<ssevecmode> 2 "nonimmediate_operand" "xm,0,X,X"))
8588    (clobber (reg:CC FLAGS_REG))]
8589   "TARGET_MIX_SSE_I387 && SSE_FLOAT_MODE_P (<MODE>mode)"
8590   "#")
8591
8592 (define_insn "*absneg<mode>2_sse"
8593   [(set (match_operand:MODEF 0 "register_operand" "=x,x,!r")
8594         (match_operator:MODEF 3 "absneg_operator"
8595           [(match_operand:MODEF 1 "register_operand" "0 ,x,0")]))
8596    (use (match_operand:<ssevecmode> 2 "register_operand" "xm,0,X"))
8597    (clobber (reg:CC FLAGS_REG))]
8598   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
8599   "#")
8600
8601 (define_insn "*absneg<mode>2_i387"
8602   [(set (match_operand:X87MODEF 0 "register_operand" "=f,!r")
8603         (match_operator:X87MODEF 3 "absneg_operator"
8604           [(match_operand:X87MODEF 1 "register_operand" "0,0")]))
8605    (use (match_operand 2 "" ""))
8606    (clobber (reg:CC FLAGS_REG))]
8607   "TARGET_80387 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
8608   "#")
8609
8610 (define_expand "<code>tf2"
8611   [(set (match_operand:TF 0 "register_operand" "")
8612         (absneg:TF (match_operand:TF 1 "register_operand" "")))]
8613   "TARGET_SSE2"
8614   "ix86_expand_fp_absneg_operator (<CODE>, TFmode, operands); DONE;")
8615
8616 (define_insn "*absnegtf2_sse"
8617   [(set (match_operand:TF 0 "register_operand" "=x,x")
8618         (match_operator:TF 3 "absneg_operator"
8619           [(match_operand:TF 1 "register_operand" "0,x")]))
8620    (use (match_operand:TF 2 "nonimmediate_operand" "xm,0"))
8621    (clobber (reg:CC FLAGS_REG))]
8622   "TARGET_SSE2"
8623   "#")
8624
8625 ;; Splitters for fp abs and neg.
8626
8627 (define_split
8628   [(set (match_operand 0 "fp_register_operand" "")
8629         (match_operator 1 "absneg_operator" [(match_dup 0)]))
8630    (use (match_operand 2 "" ""))
8631    (clobber (reg:CC FLAGS_REG))]
8632   "reload_completed"
8633   [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))])
8634
8635 (define_split
8636   [(set (match_operand 0 "register_operand" "")
8637         (match_operator 3 "absneg_operator"
8638           [(match_operand 1 "register_operand" "")]))
8639    (use (match_operand 2 "nonimmediate_operand" ""))
8640    (clobber (reg:CC FLAGS_REG))]
8641   "reload_completed && SSE_REG_P (operands[0])"
8642   [(set (match_dup 0) (match_dup 3))]
8643 {
8644   enum machine_mode mode = GET_MODE (operands[0]);
8645   enum machine_mode vmode = GET_MODE (operands[2]);
8646   rtx tmp;
8647
8648   operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0);
8649   operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0);
8650   if (operands_match_p (operands[0], operands[2]))
8651     {
8652       tmp = operands[1];
8653       operands[1] = operands[2];
8654       operands[2] = tmp;
8655     }
8656   if (GET_CODE (operands[3]) == ABS)
8657     tmp = gen_rtx_AND (vmode, operands[1], operands[2]);
8658   else
8659     tmp = gen_rtx_XOR (vmode, operands[1], operands[2]);
8660   operands[3] = tmp;
8661 })
8662
8663 (define_split
8664   [(set (match_operand:SF 0 "register_operand" "")
8665         (match_operator:SF 1 "absneg_operator" [(match_dup 0)]))
8666    (use (match_operand:V4SF 2 "" ""))
8667    (clobber (reg:CC FLAGS_REG))]
8668   "reload_completed"
8669   [(parallel [(set (match_dup 0) (match_dup 1))
8670               (clobber (reg:CC FLAGS_REG))])]
8671 {
8672   rtx tmp;
8673   operands[0] = gen_lowpart (SImode, operands[0]);
8674   if (GET_CODE (operands[1]) == ABS)
8675     {
8676       tmp = gen_int_mode (0x7fffffff, SImode);
8677       tmp = gen_rtx_AND (SImode, operands[0], tmp);
8678     }
8679   else
8680     {
8681       tmp = gen_int_mode (0x80000000, SImode);
8682       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
8683     }
8684   operands[1] = tmp;
8685 })
8686
8687 (define_split
8688   [(set (match_operand:DF 0 "register_operand" "")
8689         (match_operator:DF 1 "absneg_operator" [(match_dup 0)]))
8690    (use (match_operand 2 "" ""))
8691    (clobber (reg:CC FLAGS_REG))]
8692   "reload_completed"
8693   [(parallel [(set (match_dup 0) (match_dup 1))
8694               (clobber (reg:CC FLAGS_REG))])]
8695 {
8696   rtx tmp;
8697   if (TARGET_64BIT)
8698     {
8699       tmp = gen_lowpart (DImode, operands[0]);
8700       tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63));
8701       operands[0] = tmp;
8702
8703       if (GET_CODE (operands[1]) == ABS)
8704         tmp = const0_rtx;
8705       else
8706         tmp = gen_rtx_NOT (DImode, tmp);
8707     }
8708   else
8709     {
8710       operands[0] = gen_highpart (SImode, operands[0]);
8711       if (GET_CODE (operands[1]) == ABS)
8712         {
8713           tmp = gen_int_mode (0x7fffffff, SImode);
8714           tmp = gen_rtx_AND (SImode, operands[0], tmp);
8715         }
8716       else
8717         {
8718           tmp = gen_int_mode (0x80000000, SImode);
8719           tmp = gen_rtx_XOR (SImode, operands[0], tmp);
8720         }
8721     }
8722   operands[1] = tmp;
8723 })
8724
8725 (define_split
8726   [(set (match_operand:XF 0 "register_operand" "")
8727         (match_operator:XF 1 "absneg_operator" [(match_dup 0)]))
8728    (use (match_operand 2 "" ""))
8729    (clobber (reg:CC FLAGS_REG))]
8730   "reload_completed"
8731   [(parallel [(set (match_dup 0) (match_dup 1))
8732               (clobber (reg:CC FLAGS_REG))])]
8733 {
8734   rtx tmp;
8735   operands[0] = gen_rtx_REG (SImode,
8736                              true_regnum (operands[0])
8737                              + (TARGET_64BIT ? 1 : 2));
8738   if (GET_CODE (operands[1]) == ABS)
8739     {
8740       tmp = GEN_INT (0x7fff);
8741       tmp = gen_rtx_AND (SImode, operands[0], tmp);
8742     }
8743   else
8744     {
8745       tmp = GEN_INT (0x8000);
8746       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
8747     }
8748   operands[1] = tmp;
8749 })
8750
8751 ;; Conditionalize these after reload. If they match before reload, we
8752 ;; lose the clobber and ability to use integer instructions.
8753
8754 (define_insn "*<code><mode>2_1"
8755   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
8756         (absneg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "0")))]
8757   "TARGET_80387
8758    && (reload_completed
8759        || !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
8760   "f<absneg_mnemonic>"
8761   [(set_attr "type" "fsgn")
8762    (set_attr "mode" "<MODE>")])
8763
8764 (define_insn "*<code>extendsfdf2"
8765   [(set (match_operand:DF 0 "register_operand" "=f")
8766         (absneg:DF (float_extend:DF
8767                      (match_operand:SF 1 "register_operand" "0"))))]
8768   "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
8769   "f<absneg_mnemonic>"
8770   [(set_attr "type" "fsgn")
8771    (set_attr "mode" "DF")])
8772
8773 (define_insn "*<code>extendsfxf2"
8774   [(set (match_operand:XF 0 "register_operand" "=f")
8775         (absneg:XF (float_extend:XF
8776                      (match_operand:SF 1 "register_operand" "0"))))]
8777   "TARGET_80387"
8778   "f<absneg_mnemonic>"
8779   [(set_attr "type" "fsgn")
8780    (set_attr "mode" "XF")])
8781
8782 (define_insn "*<code>extenddfxf2"
8783   [(set (match_operand:XF 0 "register_operand" "=f")
8784         (absneg:XF (float_extend:XF
8785                      (match_operand:DF 1 "register_operand" "0"))))]
8786   "TARGET_80387"
8787   "f<absneg_mnemonic>"
8788   [(set_attr "type" "fsgn")
8789    (set_attr "mode" "XF")])
8790
8791 ;; Copysign instructions
8792
8793 (define_mode_iterator CSGNMODE [SF DF TF])
8794 (define_mode_attr CSGNVMODE [(SF "V4SF") (DF "V2DF") (TF "TF")])
8795
8796 (define_expand "copysign<mode>3"
8797   [(match_operand:CSGNMODE 0 "register_operand" "")
8798    (match_operand:CSGNMODE 1 "nonmemory_operand" "")
8799    (match_operand:CSGNMODE 2 "register_operand" "")]
8800   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8801    || (TARGET_SSE2 && (<MODE>mode == TFmode))"
8802   "ix86_expand_copysign (operands); DONE;")
8803
8804 (define_insn_and_split "copysign<mode>3_const"
8805   [(set (match_operand:CSGNMODE 0 "register_operand" "=x")
8806         (unspec:CSGNMODE
8807           [(match_operand:<CSGNVMODE> 1 "vector_move_operand" "xmC")
8808            (match_operand:CSGNMODE 2 "register_operand" "0")
8809            (match_operand:<CSGNVMODE> 3 "nonimmediate_operand" "xm")]
8810           UNSPEC_COPYSIGN))]
8811   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8812    || (TARGET_SSE2 && (<MODE>mode == TFmode))"
8813   "#"
8814   "&& reload_completed"
8815   [(const_int 0)]
8816   "ix86_split_copysign_const (operands); DONE;")
8817
8818 (define_insn "copysign<mode>3_var"
8819   [(set (match_operand:CSGNMODE 0 "register_operand" "=x,x,x,x,x")
8820         (unspec:CSGNMODE
8821           [(match_operand:CSGNMODE 2 "register_operand" "x,0,0,x,x")
8822            (match_operand:CSGNMODE 3 "register_operand" "1,1,x,1,x")
8823            (match_operand:<CSGNVMODE> 4 "nonimmediate_operand" "X,xm,xm,0,0")
8824            (match_operand:<CSGNVMODE> 5 "nonimmediate_operand" "0,xm,1,xm,1")]
8825           UNSPEC_COPYSIGN))
8826    (clobber (match_scratch:<CSGNVMODE> 1 "=x,x,x,x,x"))]
8827   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8828    || (TARGET_SSE2 && (<MODE>mode == TFmode))"
8829   "#")
8830
8831 (define_split
8832   [(set (match_operand:CSGNMODE 0 "register_operand" "")
8833         (unspec:CSGNMODE
8834           [(match_operand:CSGNMODE 2 "register_operand" "")
8835            (match_operand:CSGNMODE 3 "register_operand" "")
8836            (match_operand:<CSGNVMODE> 4 "" "")
8837            (match_operand:<CSGNVMODE> 5 "" "")]
8838           UNSPEC_COPYSIGN))
8839    (clobber (match_scratch:<CSGNVMODE> 1 ""))]
8840   "((SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
8841     || (TARGET_SSE2 && (<MODE>mode == TFmode)))
8842    && reload_completed"
8843   [(const_int 0)]
8844   "ix86_split_copysign_var (operands); DONE;")
8845 \f
8846 ;; One complement instructions
8847
8848 (define_expand "one_cmpl<mode>2"
8849   [(set (match_operand:SWIM 0 "nonimmediate_operand" "")
8850         (not:SWIM (match_operand:SWIM 1 "nonimmediate_operand" "")))]
8851   ""
8852   "ix86_expand_unary_operator (NOT, <MODE>mode, operands); DONE;")
8853
8854 (define_insn "*one_cmpl<mode>2_1"
8855   [(set (match_operand:SWI248 0 "nonimmediate_operand" "=rm")
8856         (not:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" "0")))]
8857   "ix86_unary_operator_ok (NOT, <MODE>mode, operands)"
8858   "not{<imodesuffix>}\t%0"
8859   [(set_attr "type" "negnot")
8860    (set_attr "mode" "<MODE>")])
8861
8862 ;; %%% Potential partial reg stall on alternative 1.  What to do?
8863 (define_insn "*one_cmplqi2_1"
8864   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
8865         (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
8866   "ix86_unary_operator_ok (NOT, QImode, operands)"
8867   "@
8868    not{b}\t%0
8869    not{l}\t%k0"
8870   [(set_attr "type" "negnot")
8871    (set_attr "mode" "QI,SI")])
8872
8873 ;; ??? Currently never generated - xor is used instead.
8874 (define_insn "*one_cmplsi2_1_zext"
8875   [(set (match_operand:DI 0 "register_operand" "=r")
8876         (zero_extend:DI
8877           (not:SI (match_operand:SI 1 "register_operand" "0"))))]
8878   "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
8879   "not{l}\t%k0"
8880   [(set_attr "type" "negnot")
8881    (set_attr "mode" "SI")])
8882
8883 (define_insn "*one_cmpl<mode>2_2"
8884   [(set (reg FLAGS_REG)
8885         (compare (not:SWI (match_operand:SWI 1 "nonimmediate_operand" "0"))
8886                  (const_int 0)))
8887    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
8888         (not:SWI (match_dup 1)))]
8889   "ix86_match_ccmode (insn, CCNOmode)
8890    && ix86_unary_operator_ok (NOT, <MODE>mode, operands)"
8891   "#"
8892   [(set_attr "type" "alu1")
8893    (set_attr "mode" "<MODE>")])
8894
8895 (define_split
8896   [(set (match_operand 0 "flags_reg_operand" "")
8897         (match_operator 2 "compare_operator"
8898           [(not:SWI (match_operand:SWI 3 "nonimmediate_operand" ""))
8899            (const_int 0)]))
8900    (set (match_operand:SWI 1 "nonimmediate_operand" "")
8901         (not:SWI (match_dup 3)))]
8902   "ix86_match_ccmode (insn, CCNOmode)"
8903   [(parallel [(set (match_dup 0)
8904                    (match_op_dup 2 [(xor:SWI (match_dup 3) (const_int -1))
8905                                     (const_int 0)]))
8906               (set (match_dup 1)
8907                    (xor:SWI (match_dup 3) (const_int -1)))])])
8908
8909 ;; ??? Currently never generated - xor is used instead.
8910 (define_insn "*one_cmplsi2_2_zext"
8911   [(set (reg FLAGS_REG)
8912         (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
8913                  (const_int 0)))
8914    (set (match_operand:DI 0 "register_operand" "=r")
8915         (zero_extend:DI (not:SI (match_dup 1))))]
8916   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8917    && ix86_unary_operator_ok (NOT, SImode, operands)"
8918   "#"
8919   [(set_attr "type" "alu1")
8920    (set_attr "mode" "SI")])
8921
8922 (define_split
8923   [(set (match_operand 0 "flags_reg_operand" "")
8924         (match_operator 2 "compare_operator"
8925           [(not:SI (match_operand:SI 3 "register_operand" ""))
8926            (const_int 0)]))
8927    (set (match_operand:DI 1 "register_operand" "")
8928         (zero_extend:DI (not:SI (match_dup 3))))]
8929   "ix86_match_ccmode (insn, CCNOmode)"
8930   [(parallel [(set (match_dup 0)
8931                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
8932                                     (const_int 0)]))
8933               (set (match_dup 1)
8934                    (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])])
8935 \f
8936 ;; Shift instructions
8937
8938 ;; DImode shifts are implemented using the i386 "shift double" opcode,
8939 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem".  If the shift count
8940 ;; is variable, then the count is in %cl and the "imm" operand is dropped
8941 ;; from the assembler input.
8942 ;;
8943 ;; This instruction shifts the target reg/mem as usual, but instead of
8944 ;; shifting in zeros, bits are shifted in from reg operand.  If the insn
8945 ;; is a left shift double, bits are taken from the high order bits of
8946 ;; reg, else if the insn is a shift right double, bits are taken from the
8947 ;; low order bits of reg.  So if %eax is "1234" and %edx is "5678",
8948 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
8949 ;;
8950 ;; Since sh[lr]d does not change the `reg' operand, that is done
8951 ;; separately, making all shifts emit pairs of shift double and normal
8952 ;; shift.  Since sh[lr]d does not shift more than 31 bits, and we wish to
8953 ;; support a 63 bit shift, each shift where the count is in a reg expands
8954 ;; to a pair of shifts, a branch, a shift by 32 and a label.
8955 ;;
8956 ;; If the shift count is a constant, we need never emit more than one
8957 ;; shift pair, instead using moves and sign extension for counts greater
8958 ;; than 31.
8959
8960 (define_expand "ashl<mode>3"
8961   [(set (match_operand:SDWIM 0 "<shift_operand>" "")
8962         (ashift:SDWIM (match_operand:SDWIM 1 "<ashl_input_operand>" "")
8963                       (match_operand:QI 2 "nonmemory_operand" "")))]
8964   ""
8965   "ix86_expand_binary_operator (ASHIFT, <MODE>mode, operands); DONE;")
8966
8967 (define_insn "*ashl<mode>3_doubleword"
8968   [(set (match_operand:DWI 0 "register_operand" "=&r,r")
8969         (ashift:DWI (match_operand:DWI 1 "reg_or_pm1_operand" "n,0")
8970                     (match_operand:QI 2 "nonmemory_operand" "<S>c,<S>c")))
8971    (clobber (reg:CC FLAGS_REG))]
8972   ""
8973   "#"
8974   [(set_attr "type" "multi")])
8975
8976 (define_split
8977   [(set (match_operand:DWI 0 "register_operand" "")
8978         (ashift:DWI (match_operand:DWI 1 "nonmemory_operand" "")
8979                     (match_operand:QI 2 "nonmemory_operand" "")))
8980    (clobber (reg:CC FLAGS_REG))]
8981   "(optimize && flag_peephole2) ? epilogue_completed : reload_completed"
8982   [(const_int 0)]
8983   "ix86_split_ashl (operands, NULL_RTX, <MODE>mode); DONE;")
8984
8985 ;; By default we don't ask for a scratch register, because when DWImode
8986 ;; values are manipulated, registers are already at a premium.  But if
8987 ;; we have one handy, we won't turn it away.
8988
8989 (define_peephole2
8990   [(match_scratch:DWIH 3 "r")
8991    (parallel [(set (match_operand:<DWI> 0 "register_operand" "")
8992                    (ashift:<DWI>
8993                      (match_operand:<DWI> 1 "nonmemory_operand" "")
8994                      (match_operand:QI 2 "nonmemory_operand" "")))
8995               (clobber (reg:CC FLAGS_REG))])
8996    (match_dup 3)]
8997   "TARGET_CMOVE"
8998   [(const_int 0)]
8999   "ix86_split_ashl (operands, operands[3], <DWI>mode); DONE;")
9000
9001 (define_insn "x86_64_shld"
9002   [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m")
9003         (ior:DI (ashift:DI (match_dup 0)
9004                   (match_operand:QI 2 "nonmemory_operand" "Jc"))
9005                 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r")
9006                   (minus:QI (const_int 64) (match_dup 2)))))
9007    (clobber (reg:CC FLAGS_REG))]
9008   "TARGET_64BIT"
9009   "shld{q}\t{%s2%1, %0|%0, %1, %2}"
9010   [(set_attr "type" "ishift")
9011    (set_attr "prefix_0f" "1")
9012    (set_attr "mode" "DI")
9013    (set_attr "athlon_decode" "vector")
9014    (set_attr "amdfam10_decode" "vector")
9015    (set_attr "bdver1_decode" "vector")])
9016
9017 (define_insn "x86_shld"
9018   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m")
9019         (ior:SI (ashift:SI (match_dup 0)
9020                   (match_operand:QI 2 "nonmemory_operand" "Ic"))
9021                 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r")
9022                   (minus:QI (const_int 32) (match_dup 2)))))
9023    (clobber (reg:CC FLAGS_REG))]
9024   ""
9025   "shld{l}\t{%s2%1, %0|%0, %1, %2}"
9026   [(set_attr "type" "ishift")
9027    (set_attr "prefix_0f" "1")
9028    (set_attr "mode" "SI")
9029    (set_attr "pent_pair" "np")
9030    (set_attr "athlon_decode" "vector")
9031    (set_attr "amdfam10_decode" "vector")
9032    (set_attr "bdver1_decode" "vector")])
9033
9034 (define_expand "x86_shift<mode>_adj_1"
9035   [(set (reg:CCZ FLAGS_REG)
9036         (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
9037                              (match_dup 4))
9038                      (const_int 0)))
9039    (set (match_operand:SWI48 0 "register_operand" "")
9040         (if_then_else:SWI48 (ne (reg:CCZ FLAGS_REG) (const_int 0))
9041                             (match_operand:SWI48 1 "register_operand" "")
9042                             (match_dup 0)))
9043    (set (match_dup 1)
9044         (if_then_else:SWI48 (ne (reg:CCZ FLAGS_REG) (const_int 0))
9045                             (match_operand:SWI48 3 "register_operand" "r")
9046                             (match_dup 1)))]
9047   "TARGET_CMOVE"
9048   "operands[4] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));")
9049
9050 (define_expand "x86_shift<mode>_adj_2"
9051   [(use (match_operand:SWI48 0 "register_operand" ""))
9052    (use (match_operand:SWI48 1 "register_operand" ""))
9053    (use (match_operand:QI 2 "register_operand" ""))]
9054   ""
9055 {
9056   rtx label = gen_label_rtx ();
9057   rtx tmp;
9058
9059   emit_insn (gen_testqi_ccz_1 (operands[2],
9060                                GEN_INT (GET_MODE_BITSIZE (<MODE>mode))));
9061
9062   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
9063   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
9064   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
9065                               gen_rtx_LABEL_REF (VOIDmode, label),
9066                               pc_rtx);
9067   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
9068   JUMP_LABEL (tmp) = label;
9069
9070   emit_move_insn (operands[0], operands[1]);
9071   ix86_expand_clear (operands[1]);
9072
9073   emit_label (label);
9074   LABEL_NUSES (label) = 1;
9075
9076   DONE;
9077 })
9078
9079 ;; Avoid useless masking of count operand.
9080 (define_insn_and_split "*ashl<mode>3_mask"
9081   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm")
9082         (ashift:SWI48
9083           (match_operand:SWI48 1 "nonimmediate_operand" "0")
9084           (subreg:QI
9085             (and:SI
9086               (match_operand:SI 2 "nonimmediate_operand" "c")
9087               (match_operand:SI 3 "const_int_operand" "n")) 0)))
9088    (clobber (reg:CC FLAGS_REG))]
9089   "ix86_binary_operator_ok (ASHIFT, <MODE>mode, operands)
9090    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
9091       == GET_MODE_BITSIZE (<MODE>mode)-1"
9092   "#"
9093   "&& 1"
9094   [(parallel [(set (match_dup 0)
9095                    (ashift:SWI48 (match_dup 1) (match_dup 2)))
9096               (clobber (reg:CC FLAGS_REG))])]
9097 {
9098   if (can_create_pseudo_p ())
9099     operands [2] = force_reg (SImode, operands[2]);
9100
9101   operands[2] = simplify_gen_subreg (QImode, operands[2], SImode, 0);
9102 }
9103   [(set_attr "type" "ishift")
9104    (set_attr "mode" "<MODE>")])
9105
9106 (define_insn "*bmi2_ashl<mode>3_1"
9107   [(set (match_operand:SWI48 0 "register_operand" "=r")
9108         (ashift:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "rm")
9109                       (match_operand:SWI48 2 "register_operand" "r")))]
9110   "TARGET_BMI2"
9111   "shlx\t{%2, %1, %0|%0, %1, %2}"
9112   [(set_attr "type" "ishiftx")
9113    (set_attr "mode" "<MODE>")])
9114
9115 (define_insn "*ashl<mode>3_1"
9116   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r,r")
9117         (ashift:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "0,l,rm")
9118                       (match_operand:QI 2 "nonmemory_operand" "c<S>,M,r")))
9119    (clobber (reg:CC FLAGS_REG))]
9120   "ix86_binary_operator_ok (ASHIFT, <MODE>mode, operands)"
9121 {
9122   switch (get_attr_type (insn))
9123     {
9124     case TYPE_LEA:
9125     case TYPE_ISHIFTX:
9126       return "#";
9127
9128     case TYPE_ALU:
9129       gcc_assert (operands[2] == const1_rtx);
9130       gcc_assert (rtx_equal_p (operands[0], operands[1]));
9131       return "add{<imodesuffix>}\t%0, %0";
9132
9133     default:
9134       if (operands[2] == const1_rtx
9135           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9136         return "sal{<imodesuffix>}\t%0";
9137       else
9138         return "sal{<imodesuffix>}\t{%2, %0|%0, %2}";
9139     }
9140 }
9141   [(set_attr "isa" "*,*,bmi2")
9142    (set (attr "type")
9143      (cond [(eq_attr "alternative" "1")
9144               (const_string "lea")
9145             (eq_attr "alternative" "2")
9146               (const_string "ishiftx")
9147             (and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9148                       (match_operand 0 "register_operand" ""))
9149                  (match_operand 2 "const1_operand" ""))
9150               (const_string "alu")
9151            ]
9152            (const_string "ishift")))
9153    (set (attr "length_immediate")
9154      (if_then_else
9155        (ior (eq_attr "type" "alu")
9156             (and (eq_attr "type" "ishift")
9157                  (and (match_operand 2 "const1_operand" "")
9158                       (ior (match_test "TARGET_SHIFT1")
9159                            (match_test "optimize_function_for_size_p (cfun)")))))
9160        (const_string "0")
9161        (const_string "*")))
9162    (set_attr "mode" "<MODE>")])
9163
9164 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9165 (define_split
9166   [(set (match_operand:SWI48 0 "register_operand" "")
9167         (ashift:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
9168                       (match_operand:QI 2 "register_operand" "")))
9169    (clobber (reg:CC FLAGS_REG))]
9170   "TARGET_BMI2 && reload_completed"
9171   [(set (match_dup 0)
9172         (ashift:SWI48 (match_dup 1) (match_dup 2)))]
9173   "operands[2] = gen_lowpart (<MODE>mode, operands[2]);")
9174
9175 (define_insn "*bmi2_ashlsi3_1_zext"
9176   [(set (match_operand:DI 0 "register_operand" "=r")
9177         (zero_extend:DI
9178           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "rm")
9179                      (match_operand:SI 2 "register_operand" "r"))))]
9180   "TARGET_64BIT && TARGET_BMI2"
9181   "shlx\t{%2, %1, %k0|%k0, %1, %2}"
9182   [(set_attr "type" "ishiftx")
9183    (set_attr "mode" "SI")])
9184
9185 (define_insn "*ashlsi3_1_zext"
9186   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
9187         (zero_extend:DI
9188           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l,rm")
9189                      (match_operand:QI 2 "nonmemory_operand" "cI,M,r"))))
9190    (clobber (reg:CC FLAGS_REG))]
9191   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
9192 {
9193   switch (get_attr_type (insn))
9194     {
9195     case TYPE_LEA:
9196     case TYPE_ISHIFTX:
9197       return "#";
9198
9199     case TYPE_ALU:
9200       gcc_assert (operands[2] == const1_rtx);
9201       return "add{l}\t%k0, %k0";
9202
9203     default:
9204       if (operands[2] == const1_rtx
9205           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9206         return "sal{l}\t%k0";
9207       else
9208         return "sal{l}\t{%2, %k0|%k0, %2}";
9209     }
9210 }
9211   [(set_attr "isa" "*,*,bmi2")
9212    (set (attr "type")
9213      (cond [(eq_attr "alternative" "1")
9214               (const_string "lea")
9215             (eq_attr "alternative" "2")
9216               (const_string "ishiftx")
9217             (and (match_test "TARGET_DOUBLE_WITH_ADD")
9218                  (match_operand 2 "const1_operand" ""))
9219               (const_string "alu")
9220            ]
9221            (const_string "ishift")))
9222    (set (attr "length_immediate")
9223      (if_then_else
9224        (ior (eq_attr "type" "alu")
9225             (and (eq_attr "type" "ishift")
9226                  (and (match_operand 2 "const1_operand" "")
9227                       (ior (match_test "TARGET_SHIFT1")
9228                            (match_test "optimize_function_for_size_p (cfun)")))))
9229        (const_string "0")
9230        (const_string "*")))
9231    (set_attr "mode" "SI")])
9232
9233 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9234 (define_split
9235   [(set (match_operand:DI 0 "register_operand" "")
9236         (zero_extend:DI
9237           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
9238                      (match_operand:QI 2 "register_operand" ""))))
9239    (clobber (reg:CC FLAGS_REG))]
9240   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
9241   [(set (match_dup 0)
9242         (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
9243   "operands[2] = gen_lowpart (SImode, operands[2]);")
9244
9245 (define_insn "*ashlhi3_1"
9246   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,Yp")
9247         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
9248                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
9249    (clobber (reg:CC FLAGS_REG))]
9250   "ix86_binary_operator_ok (ASHIFT, HImode, operands)"
9251 {
9252   switch (get_attr_type (insn))
9253     {
9254     case TYPE_LEA:
9255       return "#";
9256
9257     case TYPE_ALU:
9258       gcc_assert (operands[2] == const1_rtx);
9259       return "add{w}\t%0, %0";
9260
9261     default:
9262       if (operands[2] == const1_rtx
9263           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9264         return "sal{w}\t%0";
9265       else
9266         return "sal{w}\t{%2, %0|%0, %2}";
9267     }
9268 }
9269   [(set (attr "type")
9270      (cond [(eq_attr "alternative" "1")
9271               (const_string "lea")
9272             (and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9273                       (match_operand 0 "register_operand" ""))
9274                  (match_operand 2 "const1_operand" ""))
9275               (const_string "alu")
9276            ]
9277            (const_string "ishift")))
9278    (set (attr "length_immediate")
9279      (if_then_else
9280        (ior (eq_attr "type" "alu")
9281             (and (eq_attr "type" "ishift")
9282                  (and (match_operand 2 "const1_operand" "")
9283                       (ior (match_test "TARGET_SHIFT1")
9284                            (match_test "optimize_function_for_size_p (cfun)")))))
9285        (const_string "0")
9286        (const_string "*")))
9287    (set_attr "mode" "HI,SI")])
9288
9289 ;; %%% Potential partial reg stall on alternative 1.  What to do?
9290 (define_insn "*ashlqi3_1"
9291   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,Yp")
9292         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
9293                    (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
9294    (clobber (reg:CC FLAGS_REG))]
9295   "ix86_binary_operator_ok (ASHIFT, QImode, operands)"
9296 {
9297   switch (get_attr_type (insn))
9298     {
9299     case TYPE_LEA:
9300       return "#";
9301
9302     case TYPE_ALU:
9303       gcc_assert (operands[2] == const1_rtx);
9304       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
9305         return "add{l}\t%k0, %k0";
9306       else
9307         return "add{b}\t%0, %0";
9308
9309     default:
9310       if (operands[2] == const1_rtx
9311           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9312         {
9313           if (get_attr_mode (insn) == MODE_SI)
9314             return "sal{l}\t%k0";
9315           else
9316             return "sal{b}\t%0";
9317         }
9318       else
9319         {
9320           if (get_attr_mode (insn) == MODE_SI)
9321             return "sal{l}\t{%2, %k0|%k0, %2}";
9322           else
9323             return "sal{b}\t{%2, %0|%0, %2}";
9324         }
9325     }
9326 }
9327   [(set (attr "type")
9328      (cond [(eq_attr "alternative" "2")
9329               (const_string "lea")
9330             (and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9331                       (match_operand 0 "register_operand" ""))
9332                  (match_operand 2 "const1_operand" ""))
9333               (const_string "alu")
9334            ]
9335            (const_string "ishift")))
9336    (set (attr "length_immediate")
9337      (if_then_else
9338        (ior (eq_attr "type" "alu")
9339             (and (eq_attr "type" "ishift")
9340                  (and (match_operand 2 "const1_operand" "")
9341                       (ior (match_test "TARGET_SHIFT1")
9342                            (match_test "optimize_function_for_size_p (cfun)")))))
9343        (const_string "0")
9344        (const_string "*")))
9345    (set_attr "mode" "QI,SI,SI")])
9346
9347 (define_insn "*ashlqi3_1_slp"
9348   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
9349         (ashift:QI (match_dup 0)
9350                    (match_operand:QI 1 "nonmemory_operand" "cI")))
9351    (clobber (reg:CC FLAGS_REG))]
9352   "(optimize_function_for_size_p (cfun)
9353     || !TARGET_PARTIAL_FLAG_REG_STALL
9354     || (operands[1] == const1_rtx
9355         && (TARGET_SHIFT1
9356             || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))"
9357 {
9358   switch (get_attr_type (insn))
9359     {
9360     case TYPE_ALU:
9361       gcc_assert (operands[1] == const1_rtx);
9362       return "add{b}\t%0, %0";
9363
9364     default:
9365       if (operands[1] == const1_rtx
9366           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9367         return "sal{b}\t%0";
9368       else
9369         return "sal{b}\t{%1, %0|%0, %1}";
9370     }
9371 }
9372   [(set (attr "type")
9373      (cond [(and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9374                       (match_operand 0 "register_operand" ""))
9375                  (match_operand 1 "const1_operand" ""))
9376               (const_string "alu")
9377            ]
9378            (const_string "ishift1")))
9379    (set (attr "length_immediate")
9380      (if_then_else
9381        (ior (eq_attr "type" "alu")
9382             (and (eq_attr "type" "ishift1")
9383                  (and (match_operand 1 "const1_operand" "")
9384                       (ior (match_test "TARGET_SHIFT1")
9385                            (match_test "optimize_function_for_size_p (cfun)")))))
9386        (const_string "0")
9387        (const_string "*")))
9388    (set_attr "mode" "QI")])
9389
9390 ;; Convert ashift to the lea pattern to avoid flags dependency.
9391 (define_split
9392   [(set (match_operand 0 "register_operand" "")
9393         (ashift (match_operand 1 "index_register_operand" "")
9394                 (match_operand:QI 2 "const_int_operand" "")))
9395    (clobber (reg:CC FLAGS_REG))]
9396   "GET_MODE (operands[0]) == GET_MODE (operands[1])
9397    && reload_completed
9398    && true_regnum (operands[0]) != true_regnum (operands[1])"
9399   [(const_int 0)]
9400 {
9401   enum machine_mode mode = GET_MODE (operands[0]);
9402   rtx pat;
9403
9404   if (GET_MODE_SIZE (mode) < GET_MODE_SIZE (SImode))
9405     { 
9406       mode = SImode; 
9407       operands[0] = gen_lowpart (mode, operands[0]);
9408       operands[1] = gen_lowpart (mode, operands[1]);
9409     }
9410
9411   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), mode);
9412
9413   pat = gen_rtx_MULT (mode, operands[1], operands[2]);
9414
9415   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
9416   DONE;
9417 })
9418
9419 ;; Convert ashift to the lea pattern to avoid flags dependency.
9420 (define_split
9421   [(set (match_operand:DI 0 "register_operand" "")
9422         (zero_extend:DI
9423           (ashift:SI (match_operand:SI 1 "index_register_operand" "")
9424                      (match_operand:QI 2 "const_int_operand" ""))))
9425    (clobber (reg:CC FLAGS_REG))]
9426   "TARGET_64BIT && reload_completed
9427    && true_regnum (operands[0]) != true_regnum (operands[1])"
9428   [(set (match_dup 0)
9429         (zero_extend:DI (subreg:SI (mult:DI (match_dup 1) (match_dup 2)) 0)))]
9430 {
9431   operands[1] = gen_lowpart (DImode, operands[1]);
9432   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);
9433 })
9434
9435 ;; This pattern can't accept a variable shift count, since shifts by
9436 ;; zero don't affect the flags.  We assume that shifts by constant
9437 ;; zero are optimized away.
9438 (define_insn "*ashl<mode>3_cmp"
9439   [(set (reg FLAGS_REG)
9440         (compare
9441           (ashift:SWI (match_operand:SWI 1 "nonimmediate_operand" "0")
9442                       (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9443           (const_int 0)))
9444    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
9445         (ashift:SWI (match_dup 1) (match_dup 2)))]
9446   "(optimize_function_for_size_p (cfun)
9447     || !TARGET_PARTIAL_FLAG_REG_STALL
9448     || (operands[2] == const1_rtx
9449         && (TARGET_SHIFT1
9450             || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
9451    && ix86_match_ccmode (insn, CCGOCmode)
9452    && ix86_binary_operator_ok (ASHIFT, <MODE>mode, operands)"
9453 {
9454   switch (get_attr_type (insn))
9455     {
9456     case TYPE_ALU:
9457       gcc_assert (operands[2] == const1_rtx);
9458       return "add{<imodesuffix>}\t%0, %0";
9459
9460     default:
9461       if (operands[2] == const1_rtx
9462           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9463         return "sal{<imodesuffix>}\t%0";
9464       else
9465         return "sal{<imodesuffix>}\t{%2, %0|%0, %2}";
9466     }
9467 }
9468   [(set (attr "type")
9469      (cond [(and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9470                       (match_operand 0 "register_operand" ""))
9471                  (match_operand 2 "const1_operand" ""))
9472               (const_string "alu")
9473            ]
9474            (const_string "ishift")))
9475    (set (attr "length_immediate")
9476      (if_then_else
9477        (ior (eq_attr "type" "alu")
9478             (and (eq_attr "type" "ishift")
9479                  (and (match_operand 2 "const1_operand" "")
9480                       (ior (match_test "TARGET_SHIFT1")
9481                            (match_test "optimize_function_for_size_p (cfun)")))))
9482        (const_string "0")
9483        (const_string "*")))
9484    (set_attr "mode" "<MODE>")])
9485
9486 (define_insn "*ashlsi3_cmp_zext"
9487   [(set (reg FLAGS_REG)
9488         (compare
9489           (ashift:SI (match_operand:SI 1 "register_operand" "0")
9490                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
9491           (const_int 0)))
9492    (set (match_operand:DI 0 "register_operand" "=r")
9493         (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
9494   "TARGET_64BIT
9495    && (optimize_function_for_size_p (cfun)
9496        || !TARGET_PARTIAL_FLAG_REG_STALL
9497        || (operands[2] == const1_rtx
9498            && (TARGET_SHIFT1
9499                || TARGET_DOUBLE_WITH_ADD)))
9500    && ix86_match_ccmode (insn, CCGOCmode)
9501    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
9502 {
9503   switch (get_attr_type (insn))
9504     {
9505     case TYPE_ALU:
9506       gcc_assert (operands[2] == const1_rtx);
9507       return "add{l}\t%k0, %k0";
9508
9509     default:
9510       if (operands[2] == const1_rtx
9511           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9512         return "sal{l}\t%k0";
9513       else
9514         return "sal{l}\t{%2, %k0|%k0, %2}";
9515     }
9516 }
9517   [(set (attr "type")
9518      (cond [(and (match_test "TARGET_DOUBLE_WITH_ADD")
9519                  (match_operand 2 "const1_operand" ""))
9520               (const_string "alu")
9521            ]
9522            (const_string "ishift")))
9523    (set (attr "length_immediate")
9524      (if_then_else
9525        (ior (eq_attr "type" "alu")
9526             (and (eq_attr "type" "ishift")
9527                  (and (match_operand 2 "const1_operand" "")
9528                       (ior (match_test "TARGET_SHIFT1")
9529                            (match_test "optimize_function_for_size_p (cfun)")))))
9530        (const_string "0")
9531        (const_string "*")))
9532    (set_attr "mode" "SI")])
9533
9534 (define_insn "*ashl<mode>3_cconly"
9535   [(set (reg FLAGS_REG)
9536         (compare
9537           (ashift:SWI (match_operand:SWI 1 "register_operand" "0")
9538                       (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9539           (const_int 0)))
9540    (clobber (match_scratch:SWI 0 "=<r>"))]
9541   "(optimize_function_for_size_p (cfun)
9542     || !TARGET_PARTIAL_FLAG_REG_STALL
9543     || (operands[2] == const1_rtx
9544         && (TARGET_SHIFT1
9545             || TARGET_DOUBLE_WITH_ADD)))
9546    && ix86_match_ccmode (insn, CCGOCmode)"
9547 {
9548   switch (get_attr_type (insn))
9549     {
9550     case TYPE_ALU:
9551       gcc_assert (operands[2] == const1_rtx);
9552       return "add{<imodesuffix>}\t%0, %0";
9553
9554     default:
9555       if (operands[2] == const1_rtx
9556           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9557         return "sal{<imodesuffix>}\t%0";
9558       else
9559         return "sal{<imodesuffix>}\t{%2, %0|%0, %2}";
9560     }
9561 }
9562   [(set (attr "type")
9563      (cond [(and (and (match_test "TARGET_DOUBLE_WITH_ADD")
9564                       (match_operand 0 "register_operand" ""))
9565                  (match_operand 2 "const1_operand" ""))
9566               (const_string "alu")
9567            ]
9568            (const_string "ishift")))
9569    (set (attr "length_immediate")
9570      (if_then_else
9571        (ior (eq_attr "type" "alu")
9572             (and (eq_attr "type" "ishift")
9573                  (and (match_operand 2 "const1_operand" "")
9574                       (ior (match_test "TARGET_SHIFT1")
9575                            (match_test "optimize_function_for_size_p (cfun)")))))
9576        (const_string "0")
9577        (const_string "*")))
9578    (set_attr "mode" "<MODE>")])
9579
9580 ;; See comment above `ashl<mode>3' about how this works.
9581
9582 (define_expand "<shiftrt_insn><mode>3"
9583   [(set (match_operand:SDWIM 0 "<shift_operand>" "")
9584         (any_shiftrt:SDWIM (match_operand:SDWIM 1 "<shift_operand>" "")
9585                            (match_operand:QI 2 "nonmemory_operand" "")))]
9586   ""
9587   "ix86_expand_binary_operator (<CODE>, <MODE>mode, operands); DONE;")
9588
9589 ;; Avoid useless masking of count operand.
9590 (define_insn_and_split "*<shiftrt_insn><mode>3_mask"
9591   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm")
9592         (any_shiftrt:SWI48
9593           (match_operand:SWI48 1 "nonimmediate_operand" "0")
9594           (subreg:QI
9595             (and:SI
9596               (match_operand:SI 2 "nonimmediate_operand" "c")
9597               (match_operand:SI 3 "const_int_operand" "n")) 0)))
9598    (clobber (reg:CC FLAGS_REG))]
9599   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)
9600    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
9601       == GET_MODE_BITSIZE (<MODE>mode)-1"
9602   "#"
9603   "&& 1"
9604   [(parallel [(set (match_dup 0)
9605                    (any_shiftrt:SWI48 (match_dup 1) (match_dup 2)))
9606               (clobber (reg:CC FLAGS_REG))])]
9607 {
9608   if (can_create_pseudo_p ())
9609     operands [2] = force_reg (SImode, operands[2]);
9610
9611   operands[2] = simplify_gen_subreg (QImode, operands[2], SImode, 0);
9612 }
9613   [(set_attr "type" "ishift")
9614    (set_attr "mode" "<MODE>")])
9615
9616 (define_insn_and_split "*<shiftrt_insn><mode>3_doubleword"
9617   [(set (match_operand:DWI 0 "register_operand" "=r")
9618         (any_shiftrt:DWI (match_operand:DWI 1 "register_operand" "0")
9619                          (match_operand:QI 2 "nonmemory_operand" "<S>c")))
9620    (clobber (reg:CC FLAGS_REG))]
9621   ""
9622   "#"
9623   "(optimize && flag_peephole2) ? epilogue_completed : reload_completed"
9624   [(const_int 0)]
9625   "ix86_split_<shiftrt_insn> (operands, NULL_RTX, <MODE>mode); DONE;"
9626   [(set_attr "type" "multi")])
9627
9628 ;; By default we don't ask for a scratch register, because when DWImode
9629 ;; values are manipulated, registers are already at a premium.  But if
9630 ;; we have one handy, we won't turn it away.
9631
9632 (define_peephole2
9633   [(match_scratch:DWIH 3 "r")
9634    (parallel [(set (match_operand:<DWI> 0 "register_operand" "")
9635                    (any_shiftrt:<DWI>
9636                      (match_operand:<DWI> 1 "register_operand" "")
9637                      (match_operand:QI 2 "nonmemory_operand" "")))
9638               (clobber (reg:CC FLAGS_REG))])
9639    (match_dup 3)]
9640   "TARGET_CMOVE"
9641   [(const_int 0)]
9642   "ix86_split_<shiftrt_insn> (operands, operands[3], <DWI>mode); DONE;")
9643
9644 (define_insn "x86_64_shrd"
9645   [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m")
9646         (ior:DI (ashiftrt:DI (match_dup 0)
9647                   (match_operand:QI 2 "nonmemory_operand" "Jc"))
9648                 (ashift:DI (match_operand:DI 1 "register_operand" "r")
9649                   (minus:QI (const_int 64) (match_dup 2)))))
9650    (clobber (reg:CC FLAGS_REG))]
9651   "TARGET_64BIT"
9652   "shrd{q}\t{%s2%1, %0|%0, %1, %2}"
9653   [(set_attr "type" "ishift")
9654    (set_attr "prefix_0f" "1")
9655    (set_attr "mode" "DI")
9656    (set_attr "athlon_decode" "vector")
9657    (set_attr "amdfam10_decode" "vector")
9658    (set_attr "bdver1_decode" "vector")])
9659
9660 (define_insn "x86_shrd"
9661   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m")
9662         (ior:SI (ashiftrt:SI (match_dup 0)
9663                   (match_operand:QI 2 "nonmemory_operand" "Ic"))
9664                 (ashift:SI (match_operand:SI 1 "register_operand" "r")
9665                   (minus:QI (const_int 32) (match_dup 2)))))
9666    (clobber (reg:CC FLAGS_REG))]
9667   ""
9668   "shrd{l}\t{%s2%1, %0|%0, %1, %2}"
9669   [(set_attr "type" "ishift")
9670    (set_attr "prefix_0f" "1")
9671    (set_attr "mode" "SI")
9672    (set_attr "pent_pair" "np")
9673    (set_attr "athlon_decode" "vector")
9674    (set_attr "amdfam10_decode" "vector")
9675    (set_attr "bdver1_decode" "vector")])
9676
9677 (define_insn "ashrdi3_cvt"
9678   [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
9679         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
9680                      (match_operand:QI 2 "const_int_operand" "")))
9681    (clobber (reg:CC FLAGS_REG))]
9682   "TARGET_64BIT && INTVAL (operands[2]) == 63
9683    && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
9684    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
9685   "@
9686    {cqto|cqo}
9687    sar{q}\t{%2, %0|%0, %2}"
9688   [(set_attr "type" "imovx,ishift")
9689    (set_attr "prefix_0f" "0,*")
9690    (set_attr "length_immediate" "0,*")
9691    (set_attr "modrm" "0,1")
9692    (set_attr "mode" "DI")])
9693
9694 (define_insn "ashrsi3_cvt"
9695   [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
9696         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
9697                      (match_operand:QI 2 "const_int_operand" "")))
9698    (clobber (reg:CC FLAGS_REG))]
9699   "INTVAL (operands[2]) == 31
9700    && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
9701    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
9702   "@
9703    {cltd|cdq}
9704    sar{l}\t{%2, %0|%0, %2}"
9705   [(set_attr "type" "imovx,ishift")
9706    (set_attr "prefix_0f" "0,*")
9707    (set_attr "length_immediate" "0,*")
9708    (set_attr "modrm" "0,1")
9709    (set_attr "mode" "SI")])
9710
9711 (define_insn "*ashrsi3_cvt_zext"
9712   [(set (match_operand:DI 0 "register_operand" "=*d,r")
9713         (zero_extend:DI
9714           (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
9715                        (match_operand:QI 2 "const_int_operand" ""))))
9716    (clobber (reg:CC FLAGS_REG))]
9717   "TARGET_64BIT && INTVAL (operands[2]) == 31
9718    && (TARGET_USE_CLTD || optimize_function_for_size_p (cfun))
9719    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
9720   "@
9721    {cltd|cdq}
9722    sar{l}\t{%2, %k0|%k0, %2}"
9723   [(set_attr "type" "imovx,ishift")
9724    (set_attr "prefix_0f" "0,*")
9725    (set_attr "length_immediate" "0,*")
9726    (set_attr "modrm" "0,1")
9727    (set_attr "mode" "SI")])
9728
9729 (define_expand "x86_shift<mode>_adj_3"
9730   [(use (match_operand:SWI48 0 "register_operand" ""))
9731    (use (match_operand:SWI48 1 "register_operand" ""))
9732    (use (match_operand:QI 2 "register_operand" ""))]
9733   ""
9734 {
9735   rtx label = gen_label_rtx ();
9736   rtx tmp;
9737
9738   emit_insn (gen_testqi_ccz_1 (operands[2],
9739                                GEN_INT (GET_MODE_BITSIZE (<MODE>mode))));
9740
9741   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
9742   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
9743   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
9744                               gen_rtx_LABEL_REF (VOIDmode, label),
9745                               pc_rtx);
9746   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
9747   JUMP_LABEL (tmp) = label;
9748
9749   emit_move_insn (operands[0], operands[1]);
9750   emit_insn (gen_ashr<mode>3_cvt (operands[1], operands[1],
9751                                   GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1)));
9752   emit_label (label);
9753   LABEL_NUSES (label) = 1;
9754
9755   DONE;
9756 })
9757
9758 (define_insn "*bmi2_<shiftrt_insn><mode>3_1"
9759   [(set (match_operand:SWI48 0 "register_operand" "=r")
9760         (any_shiftrt:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "rm")
9761                            (match_operand:SWI48 2 "register_operand" "r")))]
9762   "TARGET_BMI2"
9763   "<shiftrt>x\t{%2, %1, %0|%0, %1, %2}"
9764   [(set_attr "type" "ishiftx")
9765    (set_attr "mode" "<MODE>")])
9766
9767 (define_insn "*<shiftrt_insn><mode>3_1"
9768   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r")
9769         (any_shiftrt:SWI48
9770           (match_operand:SWI48 1 "nonimmediate_operand" "0,rm")
9771           (match_operand:QI 2 "nonmemory_operand" "c<S>,r")))
9772    (clobber (reg:CC FLAGS_REG))]
9773   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
9774 {
9775   switch (get_attr_type (insn))
9776     {
9777     case TYPE_ISHIFTX:
9778       return "#";
9779
9780     default:
9781       if (operands[2] == const1_rtx
9782           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9783         return "<shiftrt>{<imodesuffix>}\t%0";
9784       else
9785         return "<shiftrt>{<imodesuffix>}\t{%2, %0|%0, %2}";
9786     }
9787 }
9788   [(set_attr "isa" "*,bmi2")
9789    (set_attr "type" "ishift,ishiftx")
9790    (set (attr "length_immediate")
9791      (if_then_else
9792        (and (match_operand 2 "const1_operand" "")
9793             (ior (match_test "TARGET_SHIFT1")
9794                  (match_test "optimize_function_for_size_p (cfun)")))
9795        (const_string "0")
9796        (const_string "*")))
9797    (set_attr "mode" "<MODE>")])
9798
9799 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9800 (define_split
9801   [(set (match_operand:SWI48 0 "register_operand" "")
9802         (any_shiftrt:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
9803                            (match_operand:QI 2 "register_operand" "")))
9804    (clobber (reg:CC FLAGS_REG))]
9805   "TARGET_BMI2 && reload_completed"
9806   [(set (match_dup 0)
9807         (any_shiftrt:SWI48 (match_dup 1) (match_dup 2)))]
9808   "operands[2] = gen_lowpart (<MODE>mode, operands[2]);")
9809
9810 (define_insn "*bmi2_<shiftrt_insn>si3_1_zext"
9811   [(set (match_operand:DI 0 "register_operand" "=r")
9812         (zero_extend:DI
9813           (any_shiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "rm")
9814                           (match_operand:SI 2 "register_operand" "r"))))]
9815   "TARGET_64BIT && TARGET_BMI2"
9816   "<shiftrt>x\t{%2, %1, %k0|%k0, %1, %2}"
9817   [(set_attr "type" "ishiftx")
9818    (set_attr "mode" "SI")])
9819
9820 (define_insn "*<shiftrt_insn>si3_1_zext"
9821   [(set (match_operand:DI 0 "register_operand" "=r,r")
9822         (zero_extend:DI
9823           (any_shiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,rm")
9824                           (match_operand:QI 2 "nonmemory_operand" "cI,r"))))
9825    (clobber (reg:CC FLAGS_REG))]
9826   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
9827 {
9828   switch (get_attr_type (insn))
9829     {
9830     case TYPE_ISHIFTX:
9831       return "#";
9832
9833     default:
9834       if (operands[2] == const1_rtx
9835           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9836         return "<shiftrt>{l}\t%k0";
9837       else
9838         return "<shiftrt>{l}\t{%2, %k0|%k0, %2}";
9839     }
9840 }
9841   [(set_attr "isa" "*,bmi2")
9842    (set_attr "type" "ishift,ishiftx")
9843    (set (attr "length_immediate")
9844      (if_then_else
9845        (and (match_operand 2 "const1_operand" "")
9846             (ior (match_test "TARGET_SHIFT1")
9847                  (match_test "optimize_function_for_size_p (cfun)")))
9848        (const_string "0")
9849        (const_string "*")))
9850    (set_attr "mode" "SI")])
9851
9852 ;; Convert shift to the shiftx pattern to avoid flags dependency.
9853 (define_split
9854   [(set (match_operand:DI 0 "register_operand" "")
9855         (zero_extend:DI
9856           (any_shiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
9857                           (match_operand:QI 2 "register_operand" ""))))
9858    (clobber (reg:CC FLAGS_REG))]
9859   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
9860   [(set (match_dup 0)
9861         (zero_extend:DI (any_shiftrt:SI (match_dup 1) (match_dup 2))))]
9862   "operands[2] = gen_lowpart (SImode, operands[2]);")
9863
9864 (define_insn "*<shiftrt_insn><mode>3_1"
9865   [(set (match_operand:SWI12 0 "nonimmediate_operand" "=<r>m")
9866         (any_shiftrt:SWI12
9867           (match_operand:SWI12 1 "nonimmediate_operand" "0")
9868           (match_operand:QI 2 "nonmemory_operand" "c<S>")))
9869    (clobber (reg:CC FLAGS_REG))]
9870   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
9871 {
9872   if (operands[2] == const1_rtx
9873       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9874     return "<shiftrt>{<imodesuffix>}\t%0";
9875   else
9876     return "<shiftrt>{<imodesuffix>}\t{%2, %0|%0, %2}";
9877 }
9878   [(set_attr "type" "ishift")
9879    (set (attr "length_immediate")
9880      (if_then_else
9881        (and (match_operand 2 "const1_operand" "")
9882             (ior (match_test "TARGET_SHIFT1")
9883                  (match_test "optimize_function_for_size_p (cfun)")))
9884        (const_string "0")
9885        (const_string "*")))
9886    (set_attr "mode" "<MODE>")])
9887
9888 (define_insn "*<shiftrt_insn>qi3_1_slp"
9889   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
9890         (any_shiftrt:QI (match_dup 0)
9891                         (match_operand:QI 1 "nonmemory_operand" "cI")))
9892    (clobber (reg:CC FLAGS_REG))]
9893   "(optimize_function_for_size_p (cfun)
9894     || !TARGET_PARTIAL_REG_STALL
9895     || (operands[1] == const1_rtx
9896         && TARGET_SHIFT1))"
9897 {
9898   if (operands[1] == const1_rtx
9899       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9900     return "<shiftrt>{b}\t%0";
9901   else
9902     return "<shiftrt>{b}\t{%1, %0|%0, %1}";
9903 }
9904   [(set_attr "type" "ishift1")
9905    (set (attr "length_immediate")
9906      (if_then_else
9907        (and (match_operand 1 "const1_operand" "")
9908             (ior (match_test "TARGET_SHIFT1")
9909                  (match_test "optimize_function_for_size_p (cfun)")))
9910        (const_string "0")
9911        (const_string "*")))
9912    (set_attr "mode" "QI")])
9913
9914 ;; This pattern can't accept a variable shift count, since shifts by
9915 ;; zero don't affect the flags.  We assume that shifts by constant
9916 ;; zero are optimized away.
9917 (define_insn "*<shiftrt_insn><mode>3_cmp"
9918   [(set (reg FLAGS_REG)
9919         (compare
9920           (any_shiftrt:SWI
9921             (match_operand:SWI 1 "nonimmediate_operand" "0")
9922             (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9923           (const_int 0)))
9924    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m")
9925         (any_shiftrt:SWI (match_dup 1) (match_dup 2)))]
9926   "(optimize_function_for_size_p (cfun)
9927     || !TARGET_PARTIAL_FLAG_REG_STALL
9928     || (operands[2] == const1_rtx
9929         && TARGET_SHIFT1))
9930    && ix86_match_ccmode (insn, CCGOCmode)
9931    && ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
9932 {
9933   if (operands[2] == const1_rtx
9934       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9935     return "<shiftrt>{<imodesuffix>}\t%0";
9936   else
9937     return "<shiftrt>{<imodesuffix>}\t{%2, %0|%0, %2}";
9938 }
9939   [(set_attr "type" "ishift")
9940    (set (attr "length_immediate")
9941      (if_then_else
9942        (and (match_operand 2 "const1_operand" "")
9943             (ior (match_test "TARGET_SHIFT1")
9944                  (match_test "optimize_function_for_size_p (cfun)")))
9945        (const_string "0")
9946        (const_string "*")))
9947    (set_attr "mode" "<MODE>")])
9948
9949 (define_insn "*<shiftrt_insn>si3_cmp_zext"
9950   [(set (reg FLAGS_REG)
9951         (compare
9952           (any_shiftrt:SI (match_operand:SI 1 "register_operand" "0")
9953                           (match_operand:QI 2 "const_1_to_31_operand" "I"))
9954           (const_int 0)))
9955    (set (match_operand:DI 0 "register_operand" "=r")
9956         (zero_extend:DI (any_shiftrt:SI (match_dup 1) (match_dup 2))))]
9957   "TARGET_64BIT
9958    && (optimize_function_for_size_p (cfun)
9959        || !TARGET_PARTIAL_FLAG_REG_STALL
9960        || (operands[2] == const1_rtx
9961            && TARGET_SHIFT1))
9962    && ix86_match_ccmode (insn, CCGOCmode)
9963    && ix86_binary_operator_ok (<CODE>, SImode, operands)"
9964 {
9965   if (operands[2] == const1_rtx
9966       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9967     return "<shiftrt>{l}\t%k0";
9968   else
9969     return "<shiftrt>{l}\t{%2, %k0|%k0, %2}";
9970 }
9971   [(set_attr "type" "ishift")
9972    (set (attr "length_immediate")
9973      (if_then_else
9974        (and (match_operand 2 "const1_operand" "")
9975             (ior (match_test "TARGET_SHIFT1")
9976                  (match_test "optimize_function_for_size_p (cfun)")))
9977        (const_string "0")
9978        (const_string "*")))
9979    (set_attr "mode" "SI")])
9980
9981 (define_insn "*<shiftrt_insn><mode>3_cconly"
9982   [(set (reg FLAGS_REG)
9983         (compare
9984           (any_shiftrt:SWI
9985             (match_operand:SWI 1 "register_operand" "0")
9986             (match_operand:QI 2 "<shift_immediate_operand>" "<S>"))
9987           (const_int 0)))
9988    (clobber (match_scratch:SWI 0 "=<r>"))]
9989   "(optimize_function_for_size_p (cfun)
9990     || !TARGET_PARTIAL_FLAG_REG_STALL
9991     || (operands[2] == const1_rtx
9992         && TARGET_SHIFT1))
9993    && ix86_match_ccmode (insn, CCGOCmode)"
9994 {
9995   if (operands[2] == const1_rtx
9996       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
9997     return "<shiftrt>{<imodesuffix>}\t%0";
9998   else
9999     return "<shiftrt>{<imodesuffix>}\t{%2, %0|%0, %2}";
10000 }
10001   [(set_attr "type" "ishift")
10002    (set (attr "length_immediate")
10003      (if_then_else
10004        (and (match_operand 2 "const1_operand" "")
10005             (ior (match_test "TARGET_SHIFT1")
10006                  (match_test "optimize_function_for_size_p (cfun)")))
10007        (const_string "0")
10008        (const_string "*")))
10009    (set_attr "mode" "<MODE>")])
10010 \f
10011 ;; Rotate instructions
10012
10013 (define_expand "<rotate_insn>ti3"
10014   [(set (match_operand:TI 0 "register_operand" "")
10015         (any_rotate:TI (match_operand:TI 1 "register_operand" "")
10016                        (match_operand:QI 2 "nonmemory_operand" "")))]
10017   "TARGET_64BIT"
10018 {
10019   if (const_1_to_63_operand (operands[2], VOIDmode))
10020     emit_insn (gen_ix86_<rotate_insn>ti3_doubleword
10021                 (operands[0], operands[1], operands[2]));
10022   else
10023     FAIL;
10024
10025   DONE;
10026 })
10027
10028 (define_expand "<rotate_insn>di3"
10029   [(set (match_operand:DI 0 "shiftdi_operand" "")
10030         (any_rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
10031                        (match_operand:QI 2 "nonmemory_operand" "")))]
10032  ""
10033 {
10034   if (TARGET_64BIT)
10035     ix86_expand_binary_operator (<CODE>, DImode, operands);
10036   else if (const_1_to_31_operand (operands[2], VOIDmode))
10037     emit_insn (gen_ix86_<rotate_insn>di3_doubleword
10038                 (operands[0], operands[1], operands[2]));
10039   else
10040     FAIL;
10041
10042   DONE;
10043 })
10044
10045 (define_expand "<rotate_insn><mode>3"
10046   [(set (match_operand:SWIM124 0 "nonimmediate_operand" "")
10047         (any_rotate:SWIM124 (match_operand:SWIM124 1 "nonimmediate_operand" "")
10048                             (match_operand:QI 2 "nonmemory_operand" "")))]
10049   ""
10050   "ix86_expand_binary_operator (<CODE>, <MODE>mode, operands); DONE;")
10051
10052 ;; Avoid useless masking of count operand.
10053 (define_insn_and_split "*<rotate_insn><mode>3_mask"
10054   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm")
10055         (any_rotate:SWI48
10056           (match_operand:SWI48 1 "nonimmediate_operand" "0")
10057           (subreg:QI
10058             (and:SI
10059               (match_operand:SI 2 "nonimmediate_operand" "c")
10060               (match_operand:SI 3 "const_int_operand" "n")) 0)))
10061    (clobber (reg:CC FLAGS_REG))]
10062   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)
10063    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
10064       == GET_MODE_BITSIZE (<MODE>mode)-1"
10065   "#"
10066   "&& 1"
10067   [(parallel [(set (match_dup 0)
10068                    (any_rotate:SWI48 (match_dup 1) (match_dup 2)))
10069               (clobber (reg:CC FLAGS_REG))])]
10070 {
10071   if (can_create_pseudo_p ())
10072     operands [2] = force_reg (SImode, operands[2]);
10073
10074   operands[2] = simplify_gen_subreg (QImode, operands[2], SImode, 0);
10075 }
10076   [(set_attr "type" "rotate")
10077    (set_attr "mode" "<MODE>")])
10078
10079 ;; Implement rotation using two double-precision
10080 ;; shift instructions and a scratch register.
10081
10082 (define_insn_and_split "ix86_rotl<dwi>3_doubleword"
10083  [(set (match_operand:<DWI> 0 "register_operand" "=r")
10084        (rotate:<DWI> (match_operand:<DWI> 1 "register_operand" "0")
10085                      (match_operand:QI 2 "<shift_immediate_operand>" "<S>")))
10086   (clobber (reg:CC FLAGS_REG))
10087   (clobber (match_scratch:DWIH 3 "=&r"))]
10088  ""
10089  "#"
10090  "reload_completed"
10091  [(set (match_dup 3) (match_dup 4))
10092   (parallel
10093    [(set (match_dup 4)
10094          (ior:DWIH (ashift:DWIH (match_dup 4) (match_dup 2))
10095                    (lshiftrt:DWIH (match_dup 5)
10096                                   (minus:QI (match_dup 6) (match_dup 2)))))
10097     (clobber (reg:CC FLAGS_REG))])
10098   (parallel
10099    [(set (match_dup 5)
10100          (ior:DWIH (ashift:DWIH (match_dup 5) (match_dup 2))
10101                    (lshiftrt:DWIH (match_dup 3)
10102                                   (minus:QI (match_dup 6) (match_dup 2)))))
10103     (clobber (reg:CC FLAGS_REG))])]
10104 {
10105   operands[6] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));
10106
10107   split_double_mode (<DWI>mode, &operands[0], 1, &operands[4], &operands[5]);
10108 })
10109
10110 (define_insn_and_split "ix86_rotr<dwi>3_doubleword"
10111  [(set (match_operand:<DWI> 0 "register_operand" "=r")
10112        (rotatert:<DWI> (match_operand:<DWI> 1 "register_operand" "0")
10113                        (match_operand:QI 2 "<shift_immediate_operand>" "<S>")))
10114   (clobber (reg:CC FLAGS_REG))
10115   (clobber (match_scratch:DWIH 3 "=&r"))]
10116  ""
10117  "#"
10118  "reload_completed"
10119  [(set (match_dup 3) (match_dup 4))
10120   (parallel
10121    [(set (match_dup 4)
10122          (ior:DWIH (ashiftrt:DWIH (match_dup 4) (match_dup 2))
10123                    (ashift:DWIH (match_dup 5)
10124                                 (minus:QI (match_dup 6) (match_dup 2)))))
10125     (clobber (reg:CC FLAGS_REG))])
10126   (parallel
10127    [(set (match_dup 5)
10128          (ior:DWIH (ashiftrt:DWIH (match_dup 5) (match_dup 2))
10129                    (ashift:DWIH (match_dup 3)
10130                                 (minus:QI (match_dup 6) (match_dup 2)))))
10131     (clobber (reg:CC FLAGS_REG))])]
10132 {
10133   operands[6] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));
10134
10135   split_double_mode (<DWI>mode, &operands[0], 1, &operands[4], &operands[5]);
10136 })
10137
10138 (define_insn "*bmi2_rorx<mode>3_1"
10139   [(set (match_operand:SWI48 0 "register_operand" "=r")
10140         (rotatert:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "rm")
10141                         (match_operand:QI 2 "immediate_operand" "<S>")))]
10142   "TARGET_BMI2"
10143   "rorx\t{%2, %1, %0|%0, %1, %2}"
10144   [(set_attr "type" "rotatex")
10145    (set_attr "mode" "<MODE>")])
10146
10147 (define_insn "*<rotate_insn><mode>3_1"
10148   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=rm,r")
10149         (any_rotate:SWI48
10150           (match_operand:SWI48 1 "nonimmediate_operand" "0,rm")
10151           (match_operand:QI 2 "nonmemory_operand" "c<S>,<S>")))
10152    (clobber (reg:CC FLAGS_REG))]
10153   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
10154 {
10155   switch (get_attr_type (insn))
10156     {
10157     case TYPE_ROTATEX:
10158       return "#";
10159
10160     default:
10161       if (operands[2] == const1_rtx
10162           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10163         return "<rotate>{<imodesuffix>}\t%0";
10164       else
10165         return "<rotate>{<imodesuffix>}\t{%2, %0|%0, %2}";
10166     }
10167 }
10168   [(set_attr "isa" "*,bmi2")
10169    (set_attr "type" "rotate,rotatex")
10170    (set (attr "length_immediate")
10171      (if_then_else
10172        (and (eq_attr "type" "rotate")
10173             (and (match_operand 2 "const1_operand" "")
10174                  (ior (match_test "TARGET_SHIFT1")
10175                       (match_test "optimize_function_for_size_p (cfun)"))))
10176        (const_string "0")
10177        (const_string "*")))
10178    (set_attr "mode" "<MODE>")])
10179
10180 ;; Convert rotate to the rotatex pattern to avoid flags dependency.
10181 (define_split
10182   [(set (match_operand:SWI48 0 "register_operand" "")
10183         (rotate:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
10184                       (match_operand:QI 2 "immediate_operand" "")))
10185    (clobber (reg:CC FLAGS_REG))]
10186   "TARGET_BMI2 && reload_completed"
10187   [(set (match_dup 0)
10188         (rotatert:SWI48 (match_dup 1) (match_dup 2)))]
10189 {
10190   operands[2]
10191     = GEN_INT (GET_MODE_BITSIZE (<MODE>mode) - INTVAL (operands[2]));
10192 })
10193
10194 (define_split
10195   [(set (match_operand:SWI48 0 "register_operand" "")
10196         (rotatert:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
10197                         (match_operand:QI 2 "immediate_operand" "")))
10198    (clobber (reg:CC FLAGS_REG))]
10199   "TARGET_BMI2 && reload_completed"
10200   [(set (match_dup 0)
10201         (rotatert:SWI48 (match_dup 1) (match_dup 2)))])
10202
10203 (define_insn "*bmi2_rorxsi3_1_zext"
10204   [(set (match_operand:DI 0 "register_operand" "=r")
10205         (zero_extend:DI
10206           (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "rm")
10207                        (match_operand:QI 2 "immediate_operand" "I"))))]
10208   "TARGET_64BIT && TARGET_BMI2"
10209   "rorx\t{%2, %1, %k0|%k0, %1, %2}"
10210   [(set_attr "type" "rotatex")
10211    (set_attr "mode" "SI")])
10212
10213 (define_insn "*<rotate_insn>si3_1_zext"
10214   [(set (match_operand:DI 0 "register_operand" "=r,r")
10215         (zero_extend:DI
10216           (any_rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,rm")
10217                          (match_operand:QI 2 "nonmemory_operand" "cI,I"))))
10218    (clobber (reg:CC FLAGS_REG))]
10219   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
10220 {
10221   switch (get_attr_type (insn))
10222     {
10223     case TYPE_ROTATEX:
10224       return "#";
10225
10226     default:
10227       if (operands[2] == const1_rtx
10228           && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10229         return "<rotate>{l}\t%k0";
10230       else
10231         return "<rotate>{l}\t{%2, %k0|%k0, %2}";
10232     }
10233 }
10234   [(set_attr "isa" "*,bmi2")
10235    (set_attr "type" "rotate,rotatex")
10236    (set (attr "length_immediate")
10237      (if_then_else
10238        (and (eq_attr "type" "rotate")
10239             (and (match_operand 2 "const1_operand" "")
10240                  (ior (match_test "TARGET_SHIFT1")
10241                       (match_test "optimize_function_for_size_p (cfun)"))))
10242        (const_string "0")
10243        (const_string "*")))
10244    (set_attr "mode" "SI")])
10245
10246 ;; Convert rotate to the rotatex pattern to avoid flags dependency.
10247 (define_split
10248   [(set (match_operand:DI 0 "register_operand" "")
10249         (zero_extend:DI
10250           (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
10251                      (match_operand:QI 2 "immediate_operand" ""))))
10252    (clobber (reg:CC FLAGS_REG))]
10253   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
10254   [(set (match_dup 0)
10255         (zero_extend:DI (rotatert:SI (match_dup 1) (match_dup 2))))]
10256 {
10257   operands[2]
10258     = GEN_INT (GET_MODE_BITSIZE (SImode) - INTVAL (operands[2]));
10259 })
10260
10261 (define_split
10262   [(set (match_operand:DI 0 "register_operand" "")
10263         (zero_extend:DI
10264           (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
10265                        (match_operand:QI 2 "immediate_operand" ""))))
10266    (clobber (reg:CC FLAGS_REG))]
10267   "TARGET_64BIT && TARGET_BMI2 && reload_completed"
10268   [(set (match_dup 0)
10269         (zero_extend:DI (rotatert:SI (match_dup 1) (match_dup 2))))])
10270
10271 (define_insn "*<rotate_insn><mode>3_1"
10272   [(set (match_operand:SWI12 0 "nonimmediate_operand" "=<r>m")
10273         (any_rotate:SWI12 (match_operand:SWI12 1 "nonimmediate_operand" "0")
10274                           (match_operand:QI 2 "nonmemory_operand" "c<S>")))
10275    (clobber (reg:CC FLAGS_REG))]
10276   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
10277 {
10278   if (operands[2] == const1_rtx
10279       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10280     return "<rotate>{<imodesuffix>}\t%0";
10281   else
10282     return "<rotate>{<imodesuffix>}\t{%2, %0|%0, %2}";
10283 }
10284   [(set_attr "type" "rotate")
10285    (set (attr "length_immediate")
10286      (if_then_else
10287        (and (match_operand 2 "const1_operand" "")
10288             (ior (match_test "TARGET_SHIFT1")
10289                  (match_test "optimize_function_for_size_p (cfun)")))
10290        (const_string "0")
10291        (const_string "*")))
10292    (set_attr "mode" "<MODE>")])
10293
10294 (define_insn "*<rotate_insn>qi3_1_slp"
10295   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
10296         (any_rotate:QI (match_dup 0)
10297                        (match_operand:QI 1 "nonmemory_operand" "cI")))
10298    (clobber (reg:CC FLAGS_REG))]
10299   "(optimize_function_for_size_p (cfun)
10300     || !TARGET_PARTIAL_REG_STALL
10301     || (operands[1] == const1_rtx
10302         && TARGET_SHIFT1))"
10303 {
10304   if (operands[1] == const1_rtx
10305       && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
10306     return "<rotate>{b}\t%0";
10307   else
10308     return "<rotate>{b}\t{%1, %0|%0, %1}";
10309 }
10310   [(set_attr "type" "rotate1")
10311    (set (attr "length_immediate")
10312      (if_then_else
10313        (and (match_operand 1 "const1_operand" "")
10314             (ior (match_test "TARGET_SHIFT1")
10315                  (match_test "optimize_function_for_size_p (cfun)")))
10316        (const_string "0")
10317        (const_string "*")))
10318    (set_attr "mode" "QI")])
10319
10320 (define_split
10321  [(set (match_operand:HI 0 "register_operand" "")
10322        (any_rotate:HI (match_dup 0) (const_int 8)))
10323   (clobber (reg:CC FLAGS_REG))]
10324  "reload_completed
10325   && (TARGET_USE_XCHGB || optimize_function_for_size_p (cfun))"
10326  [(parallel [(set (strict_low_part (match_dup 0))
10327                   (bswap:HI (match_dup 0)))
10328              (clobber (reg:CC FLAGS_REG))])])
10329 \f
10330 ;; Bit set / bit test instructions
10331
10332 (define_expand "extv"
10333   [(set (match_operand:SI 0 "register_operand" "")
10334         (sign_extract:SI (match_operand:SI 1 "register_operand" "")
10335                          (match_operand:SI 2 "const8_operand" "")
10336                          (match_operand:SI 3 "const8_operand" "")))]
10337   ""
10338 {
10339   /* Handle extractions from %ah et al.  */
10340   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
10341     FAIL;
10342
10343   /* From mips.md: extract_bit_field doesn't verify that our source
10344      matches the predicate, so check it again here.  */
10345   if (! ext_register_operand (operands[1], VOIDmode))
10346     FAIL;
10347 })
10348
10349 (define_expand "extzv"
10350   [(set (match_operand:SI 0 "register_operand" "")
10351         (zero_extract:SI (match_operand 1 "ext_register_operand" "")
10352                          (match_operand:SI 2 "const8_operand" "")
10353                          (match_operand:SI 3 "const8_operand" "")))]
10354   ""
10355 {
10356   /* Handle extractions from %ah et al.  */
10357   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
10358     FAIL;
10359
10360   /* From mips.md: extract_bit_field doesn't verify that our source
10361      matches the predicate, so check it again here.  */
10362   if (! ext_register_operand (operands[1], VOIDmode))
10363     FAIL;
10364 })
10365
10366 (define_expand "insv"
10367   [(set (zero_extract (match_operand 0 "register_operand" "")
10368                       (match_operand 1 "const_int_operand" "")
10369                       (match_operand 2 "const_int_operand" ""))
10370         (match_operand 3 "register_operand" ""))]
10371   ""
10372 {
10373   rtx (*gen_mov_insv_1) (rtx, rtx);
10374
10375   if (ix86_expand_pinsr (operands))
10376     DONE;
10377
10378   /* Handle insertions to %ah et al.  */
10379   if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
10380     FAIL;
10381
10382   /* From mips.md: insert_bit_field doesn't verify that our source
10383      matches the predicate, so check it again here.  */
10384   if (! ext_register_operand (operands[0], VOIDmode))
10385     FAIL;
10386
10387   gen_mov_insv_1 = (TARGET_64BIT
10388                     ? gen_movdi_insv_1 : gen_movsi_insv_1);
10389
10390   emit_insn (gen_mov_insv_1 (operands[0], operands[3]));
10391   DONE;
10392 })
10393
10394 ;; %%% bts, btr, btc, bt.
10395 ;; In general these instructions are *slow* when applied to memory,
10396 ;; since they enforce atomic operation.  When applied to registers,
10397 ;; it depends on the cpu implementation.  They're never faster than
10398 ;; the corresponding and/ior/xor operations, so with 32-bit there's
10399 ;; no point.  But in 64-bit, we can't hold the relevant immediates
10400 ;; within the instruction itself, so operating on bits in the high
10401 ;; 32-bits of a register becomes easier.
10402 ;;
10403 ;; These are slow on Nocona, but fast on Athlon64.  We do require the use
10404 ;; of btrq and btcq for corner cases of post-reload expansion of absdf and
10405 ;; negdf respectively, so they can never be disabled entirely.
10406
10407 (define_insn "*btsq"
10408   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
10409                          (const_int 1)
10410                          (match_operand:DI 1 "const_0_to_63_operand" ""))
10411         (const_int 1))
10412    (clobber (reg:CC FLAGS_REG))]
10413   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
10414   "bts{q}\t{%1, %0|%0, %1}"
10415   [(set_attr "type" "alu1")
10416    (set_attr "prefix_0f" "1")
10417    (set_attr "mode" "DI")])
10418
10419 (define_insn "*btrq"
10420   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
10421                          (const_int 1)
10422                          (match_operand:DI 1 "const_0_to_63_operand" ""))
10423         (const_int 0))
10424    (clobber (reg:CC FLAGS_REG))]
10425   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
10426   "btr{q}\t{%1, %0|%0, %1}"
10427   [(set_attr "type" "alu1")
10428    (set_attr "prefix_0f" "1")
10429    (set_attr "mode" "DI")])
10430
10431 (define_insn "*btcq"
10432   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
10433                          (const_int 1)
10434                          (match_operand:DI 1 "const_0_to_63_operand" ""))
10435         (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
10436    (clobber (reg:CC FLAGS_REG))]
10437   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
10438   "btc{q}\t{%1, %0|%0, %1}"
10439   [(set_attr "type" "alu1")
10440    (set_attr "prefix_0f" "1")
10441    (set_attr "mode" "DI")])
10442
10443 ;; Allow Nocona to avoid these instructions if a register is available.
10444
10445 (define_peephole2
10446   [(match_scratch:DI 2 "r")
10447    (parallel [(set (zero_extract:DI
10448                      (match_operand:DI 0 "register_operand" "")
10449                      (const_int 1)
10450                      (match_operand:DI 1 "const_0_to_63_operand" ""))
10451                    (const_int 1))
10452               (clobber (reg:CC FLAGS_REG))])]
10453   "TARGET_64BIT && !TARGET_USE_BT"
10454   [(const_int 0)]
10455 {
10456   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
10457   rtx op1;
10458
10459   if (HOST_BITS_PER_WIDE_INT >= 64)
10460     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10461   else if (i < HOST_BITS_PER_WIDE_INT)
10462     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10463   else
10464     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
10465
10466   op1 = immed_double_const (lo, hi, DImode);
10467   if (i >= 31)
10468     {
10469       emit_move_insn (operands[2], op1);
10470       op1 = operands[2];
10471     }
10472
10473   emit_insn (gen_iordi3 (operands[0], operands[0], op1));
10474   DONE;
10475 })
10476
10477 (define_peephole2
10478   [(match_scratch:DI 2 "r")
10479    (parallel [(set (zero_extract:DI
10480                      (match_operand:DI 0 "register_operand" "")
10481                      (const_int 1)
10482                      (match_operand:DI 1 "const_0_to_63_operand" ""))
10483                    (const_int 0))
10484               (clobber (reg:CC FLAGS_REG))])]
10485   "TARGET_64BIT && !TARGET_USE_BT"
10486   [(const_int 0)]
10487 {
10488   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
10489   rtx op1;
10490
10491   if (HOST_BITS_PER_WIDE_INT >= 64)
10492     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10493   else if (i < HOST_BITS_PER_WIDE_INT)
10494     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10495   else
10496     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
10497
10498   op1 = immed_double_const (~lo, ~hi, DImode);
10499   if (i >= 32)
10500     {
10501       emit_move_insn (operands[2], op1);
10502       op1 = operands[2];
10503     }
10504
10505   emit_insn (gen_anddi3 (operands[0], operands[0], op1));
10506   DONE;
10507 })
10508
10509 (define_peephole2
10510   [(match_scratch:DI 2 "r")
10511    (parallel [(set (zero_extract:DI
10512                      (match_operand:DI 0 "register_operand" "")
10513                      (const_int 1)
10514                      (match_operand:DI 1 "const_0_to_63_operand" ""))
10515               (not:DI (zero_extract:DI
10516                         (match_dup 0) (const_int 1) (match_dup 1))))
10517               (clobber (reg:CC FLAGS_REG))])]
10518   "TARGET_64BIT && !TARGET_USE_BT"
10519   [(const_int 0)]
10520 {
10521   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
10522   rtx op1;
10523
10524   if (HOST_BITS_PER_WIDE_INT >= 64)
10525     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10526   else if (i < HOST_BITS_PER_WIDE_INT)
10527     lo = (HOST_WIDE_INT)1 << i, hi = 0;
10528   else
10529     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
10530
10531   op1 = immed_double_const (lo, hi, DImode);
10532   if (i >= 31)
10533     {
10534       emit_move_insn (operands[2], op1);
10535       op1 = operands[2];
10536     }
10537
10538   emit_insn (gen_xordi3 (operands[0], operands[0], op1));
10539   DONE;
10540 })
10541
10542 (define_insn "*bt<mode>"
10543   [(set (reg:CCC FLAGS_REG)
10544         (compare:CCC
10545           (zero_extract:SWI48
10546             (match_operand:SWI48 0 "register_operand" "r")
10547             (const_int 1)
10548             (match_operand:SWI48 1 "x86_64_nonmemory_operand" "rN"))
10549           (const_int 0)))]
10550   "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
10551   "bt{<imodesuffix>}\t{%1, %0|%0, %1}"
10552   [(set_attr "type" "alu1")
10553    (set_attr "prefix_0f" "1")
10554    (set_attr "mode" "<MODE>")])
10555 \f
10556 ;; Store-flag instructions.
10557
10558 ;; For all sCOND expanders, also expand the compare or test insn that
10559 ;; generates cc0.  Generate an equality comparison if `seq' or `sne'.
10560
10561 (define_insn_and_split "*setcc_di_1"
10562   [(set (match_operand:DI 0 "register_operand" "=q")
10563         (match_operator:DI 1 "ix86_comparison_operator"
10564           [(reg FLAGS_REG) (const_int 0)]))]
10565   "TARGET_64BIT && !TARGET_PARTIAL_REG_STALL"
10566   "#"
10567   "&& reload_completed"
10568   [(set (match_dup 2) (match_dup 1))
10569    (set (match_dup 0) (zero_extend:DI (match_dup 2)))]
10570 {
10571   PUT_MODE (operands[1], QImode);
10572   operands[2] = gen_lowpart (QImode, operands[0]);
10573 })
10574
10575 (define_insn_and_split "*setcc_si_1_and"
10576   [(set (match_operand:SI 0 "register_operand" "=q")
10577         (match_operator:SI 1 "ix86_comparison_operator"
10578           [(reg FLAGS_REG) (const_int 0)]))
10579    (clobber (reg:CC FLAGS_REG))]
10580   "!TARGET_PARTIAL_REG_STALL
10581    && TARGET_ZERO_EXTEND_WITH_AND && optimize_function_for_speed_p (cfun)"
10582   "#"
10583   "&& reload_completed"
10584   [(set (match_dup 2) (match_dup 1))
10585    (parallel [(set (match_dup 0) (zero_extend:SI (match_dup 2)))
10586               (clobber (reg:CC FLAGS_REG))])]
10587 {
10588   PUT_MODE (operands[1], QImode);
10589   operands[2] = gen_lowpart (QImode, operands[0]);
10590 })
10591
10592 (define_insn_and_split "*setcc_si_1_movzbl"
10593   [(set (match_operand:SI 0 "register_operand" "=q")
10594         (match_operator:SI 1 "ix86_comparison_operator"
10595           [(reg FLAGS_REG) (const_int 0)]))]
10596   "!TARGET_PARTIAL_REG_STALL
10597    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_function_for_size_p (cfun))"
10598   "#"
10599   "&& reload_completed"
10600   [(set (match_dup 2) (match_dup 1))
10601    (set (match_dup 0) (zero_extend:SI (match_dup 2)))]
10602 {
10603   PUT_MODE (operands[1], QImode);
10604   operands[2] = gen_lowpart (QImode, operands[0]);
10605 })
10606
10607 (define_insn "*setcc_qi"
10608   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10609         (match_operator:QI 1 "ix86_comparison_operator"
10610           [(reg FLAGS_REG) (const_int 0)]))]
10611   ""
10612   "set%C1\t%0"
10613   [(set_attr "type" "setcc")
10614    (set_attr "mode" "QI")])
10615
10616 (define_insn "*setcc_qi_slp"
10617   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
10618         (match_operator:QI 1 "ix86_comparison_operator"
10619           [(reg FLAGS_REG) (const_int 0)]))]
10620   ""
10621   "set%C1\t%0"
10622   [(set_attr "type" "setcc")
10623    (set_attr "mode" "QI")])
10624
10625 ;; In general it is not safe to assume too much about CCmode registers,
10626 ;; so simplify-rtx stops when it sees a second one.  Under certain
10627 ;; conditions this is safe on x86, so help combine not create
10628 ;;
10629 ;;      seta    %al
10630 ;;      testb   %al, %al
10631 ;;      sete    %al
10632
10633 (define_split
10634   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10635         (ne:QI (match_operator 1 "ix86_comparison_operator"
10636                  [(reg FLAGS_REG) (const_int 0)])
10637             (const_int 0)))]
10638   ""
10639   [(set (match_dup 0) (match_dup 1))]
10640   "PUT_MODE (operands[1], QImode);")
10641
10642 (define_split
10643   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
10644         (ne:QI (match_operator 1 "ix86_comparison_operator"
10645                  [(reg FLAGS_REG) (const_int 0)])
10646             (const_int 0)))]
10647   ""
10648   [(set (match_dup 0) (match_dup 1))]
10649   "PUT_MODE (operands[1], QImode);")
10650
10651 (define_split
10652   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10653         (eq:QI (match_operator 1 "ix86_comparison_operator"
10654                  [(reg FLAGS_REG) (const_int 0)])
10655             (const_int 0)))]
10656   ""
10657   [(set (match_dup 0) (match_dup 1))]
10658 {
10659   rtx new_op1 = copy_rtx (operands[1]);
10660   operands[1] = new_op1;
10661   PUT_MODE (new_op1, QImode);
10662   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
10663                                              GET_MODE (XEXP (new_op1, 0))));
10664
10665   /* Make sure that (a) the CCmode we have for the flags is strong
10666      enough for the reversed compare or (b) we have a valid FP compare.  */
10667   if (! ix86_comparison_operator (new_op1, VOIDmode))
10668     FAIL;
10669 })
10670
10671 (define_split
10672   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
10673         (eq:QI (match_operator 1 "ix86_comparison_operator"
10674                  [(reg FLAGS_REG) (const_int 0)])
10675             (const_int 0)))]
10676   ""
10677   [(set (match_dup 0) (match_dup 1))]
10678 {
10679   rtx new_op1 = copy_rtx (operands[1]);
10680   operands[1] = new_op1;
10681   PUT_MODE (new_op1, QImode);
10682   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
10683                                              GET_MODE (XEXP (new_op1, 0))));
10684
10685   /* Make sure that (a) the CCmode we have for the flags is strong
10686      enough for the reversed compare or (b) we have a valid FP compare.  */
10687   if (! ix86_comparison_operator (new_op1, VOIDmode))
10688     FAIL;
10689 })
10690
10691 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
10692 ;; subsequent logical operations are used to imitate conditional moves.
10693 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
10694 ;; it directly.
10695
10696 (define_insn "setcc_<mode>_sse"
10697   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
10698         (match_operator:MODEF 3 "sse_comparison_operator"
10699           [(match_operand:MODEF 1 "register_operand" "0,x")
10700            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]))]
10701   "SSE_FLOAT_MODE_P (<MODE>mode)"
10702   "@
10703    cmp%D3<ssemodesuffix>\t{%2, %0|%0, %2}
10704    vcmp%D3<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
10705   [(set_attr "isa" "noavx,avx")
10706    (set_attr "type" "ssecmp")
10707    (set_attr "length_immediate" "1")
10708    (set_attr "prefix" "orig,vex")
10709    (set_attr "mode" "<MODE>")])
10710 \f
10711 ;; Basic conditional jump instructions.
10712 ;; We ignore the overflow flag for signed branch instructions.
10713
10714 (define_insn "*jcc_1"
10715   [(set (pc)
10716         (if_then_else (match_operator 1 "ix86_comparison_operator"
10717                                       [(reg FLAGS_REG) (const_int 0)])
10718                       (label_ref (match_operand 0 "" ""))
10719                       (pc)))]
10720   ""
10721   "%+j%C1\t%l0"
10722   [(set_attr "type" "ibr")
10723    (set_attr "modrm" "0")
10724    (set (attr "length")
10725            (if_then_else (and (ge (minus (match_dup 0) (pc))
10726                                   (const_int -126))
10727                               (lt (minus (match_dup 0) (pc))
10728                                   (const_int 128)))
10729              (const_int 2)
10730              (const_int 6)))])
10731
10732 (define_insn "*jcc_2"
10733   [(set (pc)
10734         (if_then_else (match_operator 1 "ix86_comparison_operator"
10735                                       [(reg FLAGS_REG) (const_int 0)])
10736                       (pc)
10737                       (label_ref (match_operand 0 "" ""))))]
10738   ""
10739   "%+j%c1\t%l0"
10740   [(set_attr "type" "ibr")
10741    (set_attr "modrm" "0")
10742    (set (attr "length")
10743            (if_then_else (and (ge (minus (match_dup 0) (pc))
10744                                   (const_int -126))
10745                               (lt (minus (match_dup 0) (pc))
10746                                   (const_int 128)))
10747              (const_int 2)
10748              (const_int 6)))])
10749
10750 ;; In general it is not safe to assume too much about CCmode registers,
10751 ;; so simplify-rtx stops when it sees a second one.  Under certain
10752 ;; conditions this is safe on x86, so help combine not create
10753 ;;
10754 ;;      seta    %al
10755 ;;      testb   %al, %al
10756 ;;      je      Lfoo
10757
10758 (define_split
10759   [(set (pc)
10760         (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
10761                                       [(reg FLAGS_REG) (const_int 0)])
10762                           (const_int 0))
10763                       (label_ref (match_operand 1 "" ""))
10764                       (pc)))]
10765   ""
10766   [(set (pc)
10767         (if_then_else (match_dup 0)
10768                       (label_ref (match_dup 1))
10769                       (pc)))]
10770   "PUT_MODE (operands[0], VOIDmode);")
10771
10772 (define_split
10773   [(set (pc)
10774         (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
10775                                       [(reg FLAGS_REG) (const_int 0)])
10776                           (const_int 0))
10777                       (label_ref (match_operand 1 "" ""))
10778                       (pc)))]
10779   ""
10780   [(set (pc)
10781         (if_then_else (match_dup 0)
10782                       (label_ref (match_dup 1))
10783                       (pc)))]
10784 {
10785   rtx new_op0 = copy_rtx (operands[0]);
10786   operands[0] = new_op0;
10787   PUT_MODE (new_op0, VOIDmode);
10788   PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0),
10789                                              GET_MODE (XEXP (new_op0, 0))));
10790
10791   /* Make sure that (a) the CCmode we have for the flags is strong
10792      enough for the reversed compare or (b) we have a valid FP compare.  */
10793   if (! ix86_comparison_operator (new_op0, VOIDmode))
10794     FAIL;
10795 })
10796
10797 ;; zero_extend in SImode is correct also for DImode, since this is what combine
10798 ;; pass generates from shift insn with QImode operand.  Actually, the mode
10799 ;; of operand 2 (bit offset operand) doesn't matter since bt insn takes
10800 ;; appropriate modulo of the bit offset value.
10801
10802 (define_insn_and_split "*jcc_bt<mode>"
10803   [(set (pc)
10804         (if_then_else (match_operator 0 "bt_comparison_operator"
10805                         [(zero_extract:SWI48
10806                            (match_operand:SWI48 1 "register_operand" "r")
10807                            (const_int 1)
10808                            (zero_extend:SI
10809                              (match_operand:QI 2 "register_operand" "r")))
10810                          (const_int 0)])
10811                       (label_ref (match_operand 3 "" ""))
10812                       (pc)))
10813    (clobber (reg:CC FLAGS_REG))]
10814   "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
10815   "#"
10816   "&& 1"
10817   [(set (reg:CCC FLAGS_REG)
10818         (compare:CCC
10819           (zero_extract:SWI48
10820             (match_dup 1)
10821             (const_int 1)
10822             (match_dup 2))
10823           (const_int 0)))
10824    (set (pc)
10825         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10826                       (label_ref (match_dup 3))
10827                       (pc)))]
10828 {
10829   operands[2] = simplify_gen_subreg (<MODE>mode, operands[2], QImode, 0);
10830
10831   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
10832 })
10833
10834 ;; Avoid useless masking of bit offset operand.  "and" in SImode is correct
10835 ;; also for DImode, this is what combine produces.
10836 (define_insn_and_split "*jcc_bt<mode>_mask"
10837   [(set (pc)
10838         (if_then_else (match_operator 0 "bt_comparison_operator"
10839                         [(zero_extract:SWI48
10840                            (match_operand:SWI48 1 "register_operand" "r")
10841                            (const_int 1)
10842                            (and:SI
10843                              (match_operand:SI 2 "register_operand" "r")
10844                              (match_operand:SI 3 "const_int_operand" "n")))])
10845                       (label_ref (match_operand 4 "" ""))
10846                       (pc)))
10847    (clobber (reg:CC FLAGS_REG))]
10848   "(TARGET_USE_BT || optimize_function_for_size_p (cfun))
10849    && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
10850       == GET_MODE_BITSIZE (<MODE>mode)-1"
10851   "#"
10852   "&& 1"
10853   [(set (reg:CCC FLAGS_REG)
10854         (compare:CCC
10855           (zero_extract:SWI48
10856             (match_dup 1)
10857             (const_int 1)
10858             (match_dup 2))
10859           (const_int 0)))
10860    (set (pc)
10861         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10862                       (label_ref (match_dup 4))
10863                       (pc)))]
10864 {
10865   operands[2] = simplify_gen_subreg (<MODE>mode, operands[2], SImode, 0);
10866
10867   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
10868 })
10869
10870 (define_insn_and_split "*jcc_btsi_1"
10871   [(set (pc)
10872         (if_then_else (match_operator 0 "bt_comparison_operator"
10873                         [(and:SI
10874                            (lshiftrt:SI
10875                              (match_operand:SI 1 "register_operand" "r")
10876                              (match_operand:QI 2 "register_operand" "r"))
10877                            (const_int 1))
10878                          (const_int 0)])
10879                       (label_ref (match_operand 3 "" ""))
10880                       (pc)))
10881    (clobber (reg:CC FLAGS_REG))]
10882   "TARGET_USE_BT || optimize_function_for_size_p (cfun)"
10883   "#"
10884   "&& 1"
10885   [(set (reg:CCC FLAGS_REG)
10886         (compare:CCC
10887           (zero_extract:SI
10888             (match_dup 1)
10889             (const_int 1)
10890             (match_dup 2))
10891           (const_int 0)))
10892    (set (pc)
10893         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10894                       (label_ref (match_dup 3))
10895                       (pc)))]
10896 {
10897   operands[2] = simplify_gen_subreg (SImode, operands[2], QImode, 0);
10898
10899   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
10900 })
10901
10902 ;; avoid useless masking of bit offset operand
10903 (define_insn_and_split "*jcc_btsi_mask_1"
10904   [(set (pc)
10905         (if_then_else
10906           (match_operator 0 "bt_comparison_operator"
10907             [(and:SI
10908                (lshiftrt:SI
10909                  (match_operand:SI 1 "register_operand" "r")
10910                  (subreg:QI
10911                    (and:SI
10912                      (match_operand:SI 2 "register_operand" "r")
10913                      (match_operand:SI 3 "const_int_operand" "n")) 0))
10914                (const_int 1))
10915              (const_int 0)])
10916           (label_ref (match_operand 4 "" ""))
10917           (pc)))
10918    (clobber (reg:CC FLAGS_REG))]
10919   "(TARGET_USE_BT || optimize_function_for_size_p (cfun))
10920    && (INTVAL (operands[3]) & 0x1f) == 0x1f"
10921   "#"
10922   "&& 1"
10923   [(set (reg:CCC FLAGS_REG)
10924         (compare:CCC
10925           (zero_extract:SI
10926             (match_dup 1)
10927             (const_int 1)
10928             (match_dup 2))
10929           (const_int 0)))
10930    (set (pc)
10931         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
10932                       (label_ref (match_dup 4))
10933                       (pc)))]
10934   "PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));")
10935
10936 ;; Define combination compare-and-branch fp compare instructions to help
10937 ;; combine.
10938
10939 (define_insn "*fp_jcc_1_387"
10940   [(set (pc)
10941         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10942                         [(match_operand 1 "register_operand" "f")
10943                          (match_operand 2 "nonimmediate_operand" "fm")])
10944           (label_ref (match_operand 3 "" ""))
10945           (pc)))
10946    (clobber (reg:CCFP FPSR_REG))
10947    (clobber (reg:CCFP FLAGS_REG))
10948    (clobber (match_scratch:HI 4 "=a"))]
10949   "TARGET_80387
10950    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
10951    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10952    && SELECT_CC_MODE (GET_CODE (operands[0]),
10953                       operands[1], operands[2]) == CCFPmode
10954    && !TARGET_CMOVE"
10955   "#")
10956
10957 (define_insn "*fp_jcc_1r_387"
10958   [(set (pc)
10959         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10960                         [(match_operand 1 "register_operand" "f")
10961                          (match_operand 2 "nonimmediate_operand" "fm")])
10962           (pc)
10963           (label_ref (match_operand 3 "" ""))))
10964    (clobber (reg:CCFP FPSR_REG))
10965    (clobber (reg:CCFP FLAGS_REG))
10966    (clobber (match_scratch:HI 4 "=a"))]
10967   "TARGET_80387
10968    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
10969    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10970    && SELECT_CC_MODE (GET_CODE (operands[0]),
10971                       operands[1], operands[2]) == CCFPmode
10972    && !TARGET_CMOVE"
10973   "#")
10974
10975 (define_insn "*fp_jcc_2_387"
10976   [(set (pc)
10977         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10978                         [(match_operand 1 "register_operand" "f")
10979                          (match_operand 2 "register_operand" "f")])
10980           (label_ref (match_operand 3 "" ""))
10981           (pc)))
10982    (clobber (reg:CCFP FPSR_REG))
10983    (clobber (reg:CCFP FLAGS_REG))
10984    (clobber (match_scratch:HI 4 "=a"))]
10985   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
10986    && GET_MODE (operands[1]) == GET_MODE (operands[2])
10987    && !TARGET_CMOVE"
10988   "#")
10989
10990 (define_insn "*fp_jcc_2r_387"
10991   [(set (pc)
10992         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
10993                         [(match_operand 1 "register_operand" "f")
10994                          (match_operand 2 "register_operand" "f")])
10995           (pc)
10996           (label_ref (match_operand 3 "" ""))))
10997    (clobber (reg:CCFP FPSR_REG))
10998    (clobber (reg:CCFP FLAGS_REG))
10999    (clobber (match_scratch:HI 4 "=a"))]
11000   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
11001    && GET_MODE (operands[1]) == GET_MODE (operands[2])
11002    && !TARGET_CMOVE"
11003   "#")
11004
11005 (define_insn "*fp_jcc_3_387"
11006   [(set (pc)
11007         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
11008                         [(match_operand 1 "register_operand" "f")
11009                          (match_operand 2 "const0_operand" "")])
11010           (label_ref (match_operand 3 "" ""))
11011           (pc)))
11012    (clobber (reg:CCFP FPSR_REG))
11013    (clobber (reg:CCFP FLAGS_REG))
11014    (clobber (match_scratch:HI 4 "=a"))]
11015   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
11016    && GET_MODE (operands[1]) == GET_MODE (operands[2])
11017    && SELECT_CC_MODE (GET_CODE (operands[0]),
11018                       operands[1], operands[2]) == CCFPmode
11019    && !TARGET_CMOVE"
11020   "#")
11021
11022 (define_split
11023   [(set (pc)
11024         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
11025                         [(match_operand 1 "register_operand" "")
11026                          (match_operand 2 "nonimmediate_operand" "")])
11027           (match_operand 3 "" "")
11028           (match_operand 4 "" "")))
11029    (clobber (reg:CCFP FPSR_REG))
11030    (clobber (reg:CCFP FLAGS_REG))]
11031   "reload_completed"
11032   [(const_int 0)]
11033 {
11034   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
11035                         operands[3], operands[4], NULL_RTX, NULL_RTX);
11036   DONE;
11037 })
11038
11039 (define_split
11040   [(set (pc)
11041         (if_then_else (match_operator 0 "ix86_fp_comparison_operator"
11042                         [(match_operand 1 "register_operand" "")
11043                          (match_operand 2 "general_operand" "")])
11044           (match_operand 3 "" "")
11045           (match_operand 4 "" "")))
11046    (clobber (reg:CCFP FPSR_REG))
11047    (clobber (reg:CCFP FLAGS_REG))
11048    (clobber (match_scratch:HI 5 "=a"))]
11049   "reload_completed"
11050   [(const_int 0)]
11051 {
11052   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
11053                         operands[3], operands[4], operands[5], NULL_RTX);
11054   DONE;
11055 })
11056
11057 ;; The order of operands in *fp_jcc_4_387 is forced by combine in
11058 ;; simplify_comparison () function. Float operator is treated as RTX_OBJ
11059 ;; with a precedence over other operators and is always put in the first
11060 ;; place. Swap condition and operands to match ficom instruction.
11061
11062 (define_insn "*fp_jcc_4_<mode>_387"
11063   [(set (pc)
11064         (if_then_else
11065           (match_operator 0 "ix86_swapped_fp_comparison_operator"
11066             [(match_operator 1 "float_operator"
11067               [(match_operand:SWI24 2 "nonimmediate_operand" "m,?r")])
11068              (match_operand 3 "register_operand" "f,f")])
11069           (label_ref (match_operand 4 "" ""))
11070           (pc)))
11071    (clobber (reg:CCFP FPSR_REG))
11072    (clobber (reg:CCFP FLAGS_REG))
11073    (clobber (match_scratch:HI 5 "=a,a"))]
11074   "X87_FLOAT_MODE_P (GET_MODE (operands[3]))
11075    && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))
11076    && GET_MODE (operands[1]) == GET_MODE (operands[3])
11077    && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode
11078    && !TARGET_CMOVE"
11079   "#")
11080
11081 (define_split
11082   [(set (pc)
11083         (if_then_else
11084           (match_operator 0 "ix86_swapped_fp_comparison_operator"
11085             [(match_operator 1 "float_operator"
11086               [(match_operand:SWI24 2 "memory_operand" "")])
11087              (match_operand 3 "register_operand" "")])
11088           (match_operand 4 "" "")
11089           (match_operand 5 "" "")))
11090    (clobber (reg:CCFP FPSR_REG))
11091    (clobber (reg:CCFP FLAGS_REG))
11092    (clobber (match_scratch:HI 6 "=a"))]
11093   "reload_completed"
11094   [(const_int 0)]
11095 {
11096   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]);
11097
11098   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
11099                         operands[3], operands[7],
11100                         operands[4], operands[5], operands[6], NULL_RTX);
11101   DONE;
11102 })
11103
11104 ;; %%% Kill this when reload knows how to do it.
11105 (define_split
11106   [(set (pc)
11107         (if_then_else
11108           (match_operator 0 "ix86_swapped_fp_comparison_operator"
11109             [(match_operator 1 "float_operator"
11110               [(match_operand:SWI24 2 "register_operand" "")])
11111              (match_operand 3 "register_operand" "")])
11112           (match_operand 4 "" "")
11113           (match_operand 5 "" "")))
11114    (clobber (reg:CCFP FPSR_REG))
11115    (clobber (reg:CCFP FLAGS_REG))
11116    (clobber (match_scratch:HI 6 "=a"))]
11117   "reload_completed"
11118   [(const_int 0)]
11119 {
11120   operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
11121   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]);
11122
11123   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
11124                         operands[3], operands[7],
11125                         operands[4], operands[5], operands[6], operands[2]);
11126   DONE;
11127 })
11128 \f
11129 ;; Unconditional and other jump instructions
11130
11131 (define_insn "jump"
11132   [(set (pc)
11133         (label_ref (match_operand 0 "" "")))]
11134   ""
11135   "jmp\t%l0"
11136   [(set_attr "type" "ibr")
11137    (set (attr "length")
11138            (if_then_else (and (ge (minus (match_dup 0) (pc))
11139                                   (const_int -126))
11140                               (lt (minus (match_dup 0) (pc))
11141                                   (const_int 128)))
11142              (const_int 2)
11143              (const_int 5)))
11144    (set_attr "modrm" "0")])
11145
11146 (define_expand "indirect_jump"
11147   [(set (pc) (match_operand 0 "indirect_branch_operand" ""))])
11148
11149 (define_insn "*indirect_jump"
11150   [(set (pc) (match_operand:P 0 "indirect_branch_operand" "rw"))]
11151   ""
11152   "jmp\t%A0"
11153   [(set_attr "type" "ibr")
11154    (set_attr "length_immediate" "0")])
11155
11156 (define_expand "tablejump"
11157   [(parallel [(set (pc) (match_operand 0 "indirect_branch_operand" ""))
11158               (use (label_ref (match_operand 1 "" "")))])]
11159   ""
11160 {
11161   /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
11162      relative.  Convert the relative address to an absolute address.  */
11163   if (flag_pic)
11164     {
11165       rtx op0, op1;
11166       enum rtx_code code;
11167
11168       /* We can't use @GOTOFF for text labels on VxWorks;
11169          see gotoff_operand.  */
11170       if (TARGET_64BIT || TARGET_VXWORKS_RTP)
11171         {
11172           code = PLUS;
11173           op0 = operands[0];
11174           op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
11175         }
11176       else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
11177         {
11178           code = PLUS;
11179           op0 = operands[0];
11180           op1 = pic_offset_table_rtx;
11181         }
11182       else
11183         {
11184           code = MINUS;
11185           op0 = pic_offset_table_rtx;
11186           op1 = operands[0];
11187         }
11188
11189       operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
11190                                          OPTAB_DIRECT);
11191     }
11192   else if (TARGET_X32)
11193     operands[0] = convert_memory_address (Pmode, operands[0]);
11194 })
11195
11196 (define_insn "*tablejump_1"
11197   [(set (pc) (match_operand:P 0 "indirect_branch_operand" "rw"))
11198    (use (label_ref (match_operand 1 "" "")))]
11199   ""
11200   "jmp\t%A0"
11201   [(set_attr "type" "ibr")
11202    (set_attr "length_immediate" "0")])
11203 \f
11204 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
11205
11206 (define_peephole2
11207   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
11208    (set (match_operand:QI 1 "register_operand" "")
11209         (match_operator:QI 2 "ix86_comparison_operator"
11210           [(reg FLAGS_REG) (const_int 0)]))
11211    (set (match_operand 3 "q_regs_operand" "")
11212         (zero_extend (match_dup 1)))]
11213   "(peep2_reg_dead_p (3, operands[1])
11214     || operands_match_p (operands[1], operands[3]))
11215    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
11216   [(set (match_dup 4) (match_dup 0))
11217    (set (strict_low_part (match_dup 5))
11218         (match_dup 2))]
11219 {
11220   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
11221   operands[5] = gen_lowpart (QImode, operands[3]);
11222   ix86_expand_clear (operands[3]);
11223 })
11224
11225 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
11226
11227 (define_peephole2
11228   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
11229    (set (match_operand:QI 1 "register_operand" "")
11230         (match_operator:QI 2 "ix86_comparison_operator"
11231           [(reg FLAGS_REG) (const_int 0)]))
11232    (parallel [(set (match_operand 3 "q_regs_operand" "")
11233                    (zero_extend (match_dup 1)))
11234               (clobber (reg:CC FLAGS_REG))])]
11235   "(peep2_reg_dead_p (3, operands[1])
11236     || operands_match_p (operands[1], operands[3]))
11237    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
11238   [(set (match_dup 4) (match_dup 0))
11239    (set (strict_low_part (match_dup 5))
11240         (match_dup 2))]
11241 {
11242   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
11243   operands[5] = gen_lowpart (QImode, operands[3]);
11244   ix86_expand_clear (operands[3]);
11245 })
11246 \f
11247 ;; Call instructions.
11248
11249 ;; The predicates normally associated with named expanders are not properly
11250 ;; checked for calls.  This is a bug in the generic code, but it isn't that
11251 ;; easy to fix.  Ignore it for now and be prepared to fix things up.
11252
11253 ;; P6 processors will jump to the address after the decrement when %esp
11254 ;; is used as a call operand, so they will execute return address as a code.
11255 ;; See Pentium Pro errata 70, Pentium 2 errata A33 and Pentium 3 errata E17.
11256
11257 ;; Register constraint for call instruction.
11258 (define_mode_attr c [(SI "l") (DI "r")])
11259
11260 ;; Call subroutine returning no value.
11261
11262 (define_expand "call"
11263   [(call (match_operand:QI 0 "" "")
11264          (match_operand 1 "" ""))
11265    (use (match_operand 2 "" ""))]
11266   ""
11267 {
11268   ix86_expand_call (NULL, operands[0], operands[1],
11269                     operands[2], NULL, false);
11270   DONE;
11271 })
11272
11273 (define_expand "sibcall"
11274   [(call (match_operand:QI 0 "" "")
11275          (match_operand 1 "" ""))
11276    (use (match_operand 2 "" ""))]
11277   ""
11278 {
11279   ix86_expand_call (NULL, operands[0], operands[1],
11280                     operands[2], NULL, true);
11281   DONE;
11282 })
11283
11284 (define_insn_and_split "*call_vzeroupper"
11285   [(call (mem:QI (match_operand:P 0 "call_insn_operand" "<c>zw"))
11286          (match_operand 1 "" ""))
11287    (unspec [(match_operand 2 "const_int_operand" "")]
11288            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11289   "TARGET_VZEROUPPER && !SIBLING_CALL_P (insn)"
11290   "#"
11291   "&& reload_completed"
11292   [(const_int 0)]
11293   "ix86_split_call_vzeroupper (curr_insn, operands[2]); DONE;"
11294   [(set_attr "type" "call")])
11295
11296 (define_insn "*call"
11297   [(call (mem:QI (match_operand:P 0 "call_insn_operand" "<c>zw"))
11298          (match_operand 1 "" ""))]
11299   "!SIBLING_CALL_P (insn)"
11300   "* return ix86_output_call_insn (insn, operands[0]);"
11301   [(set_attr "type" "call")])
11302
11303 (define_insn_and_split "*call_rex64_ms_sysv_vzeroupper"
11304   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rzw"))
11305          (match_operand 1 "" ""))
11306    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11307    (clobber (reg:TI XMM6_REG))
11308    (clobber (reg:TI XMM7_REG))
11309    (clobber (reg:TI XMM8_REG))
11310    (clobber (reg:TI XMM9_REG))
11311    (clobber (reg:TI XMM10_REG))
11312    (clobber (reg:TI XMM11_REG))
11313    (clobber (reg:TI XMM12_REG))
11314    (clobber (reg:TI XMM13_REG))
11315    (clobber (reg:TI XMM14_REG))
11316    (clobber (reg:TI XMM15_REG))
11317    (clobber (reg:DI SI_REG))
11318    (clobber (reg:DI DI_REG))
11319    (unspec [(match_operand 2 "const_int_operand" "")]
11320            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11321   "TARGET_VZEROUPPER && TARGET_64BIT && !SIBLING_CALL_P (insn)"
11322   "#"
11323   "&& reload_completed"
11324   [(const_int 0)]
11325   "ix86_split_call_vzeroupper (curr_insn, operands[2]); DONE;"
11326   [(set_attr "type" "call")])
11327
11328 (define_insn "*call_rex64_ms_sysv"
11329   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rzw"))
11330          (match_operand 1 "" ""))
11331    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11332    (clobber (reg:TI XMM6_REG))
11333    (clobber (reg:TI XMM7_REG))
11334    (clobber (reg:TI XMM8_REG))
11335    (clobber (reg:TI XMM9_REG))
11336    (clobber (reg:TI XMM10_REG))
11337    (clobber (reg:TI XMM11_REG))
11338    (clobber (reg:TI XMM12_REG))
11339    (clobber (reg:TI XMM13_REG))
11340    (clobber (reg:TI XMM14_REG))
11341    (clobber (reg:TI XMM15_REG))
11342    (clobber (reg:DI SI_REG))
11343    (clobber (reg:DI DI_REG))]
11344   "TARGET_64BIT && !SIBLING_CALL_P (insn)"
11345   "* return ix86_output_call_insn (insn, operands[0]);"
11346   [(set_attr "type" "call")])
11347
11348 (define_insn_and_split "*sibcall_vzeroupper"
11349   [(call (mem:QI (match_operand:P 0 "sibcall_insn_operand" "Uz"))
11350          (match_operand 1 "" ""))
11351    (unspec [(match_operand 2 "const_int_operand" "")]
11352            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11353   "TARGET_VZEROUPPER && SIBLING_CALL_P (insn)"
11354   "#"
11355   "&& reload_completed"
11356   [(const_int 0)]
11357   "ix86_split_call_vzeroupper (curr_insn, operands[2]); DONE;"
11358   [(set_attr "type" "call")])
11359
11360 (define_insn "*sibcall"
11361   [(call (mem:QI (match_operand:P 0 "sibcall_insn_operand" "Uz"))
11362          (match_operand 1 "" ""))]
11363   "SIBLING_CALL_P (insn)"
11364   "* return ix86_output_call_insn (insn, operands[0]);"
11365   [(set_attr "type" "call")])
11366
11367 (define_expand "call_pop"
11368   [(parallel [(call (match_operand:QI 0 "" "")
11369                     (match_operand:SI 1 "" ""))
11370               (set (reg:SI SP_REG)
11371                    (plus:SI (reg:SI SP_REG)
11372                             (match_operand:SI 3 "" "")))])]
11373   "!TARGET_64BIT"
11374 {
11375   ix86_expand_call (NULL, operands[0], operands[1],
11376                     operands[2], operands[3], false);
11377   DONE;
11378 })
11379
11380 (define_insn_and_split "*call_pop_vzeroupper"
11381   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "lzm"))
11382          (match_operand:SI 1 "" ""))
11383    (set (reg:SI SP_REG)
11384         (plus:SI (reg:SI SP_REG)
11385                  (match_operand:SI 2 "immediate_operand" "i")))
11386    (unspec [(match_operand 3 "const_int_operand" "")]
11387            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11388   "TARGET_VZEROUPPER && !TARGET_64BIT && !SIBLING_CALL_P (insn)"
11389   "#"
11390   "&& reload_completed"
11391   [(const_int 0)]
11392   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11393   [(set_attr "type" "call")])
11394
11395 (define_insn "*call_pop"
11396   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "lzm"))
11397          (match_operand 1 "" ""))
11398    (set (reg:SI SP_REG)
11399         (plus:SI (reg:SI SP_REG)
11400                  (match_operand:SI 2 "immediate_operand" "i")))]
11401   "!TARGET_64BIT && !SIBLING_CALL_P (insn)"
11402   "* return ix86_output_call_insn (insn, operands[0]);"
11403   [(set_attr "type" "call")])
11404
11405 (define_insn_and_split "*sibcall_pop_vzeroupper"
11406   [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "Uz"))
11407          (match_operand 1 "" ""))
11408    (set (reg:SI SP_REG)
11409         (plus:SI (reg:SI SP_REG)
11410                  (match_operand:SI 2 "immediate_operand" "i")))
11411    (unspec [(match_operand 3 "const_int_operand" "")]
11412            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11413   "TARGET_VZEROUPPER && !TARGET_64BIT && SIBLING_CALL_P (insn)"
11414   "#"
11415   "&& reload_completed"
11416   [(const_int 0)]
11417   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11418   [(set_attr "type" "call")])
11419
11420 (define_insn "*sibcall_pop"
11421   [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "Uz"))
11422          (match_operand 1 "" ""))
11423    (set (reg:SI SP_REG)
11424         (plus:SI (reg:SI SP_REG)
11425                  (match_operand:SI 2 "immediate_operand" "i")))]
11426   "!TARGET_64BIT && SIBLING_CALL_P (insn)"
11427   "* return ix86_output_call_insn (insn, operands[0]);"
11428   [(set_attr "type" "call")])
11429
11430 ;; Call subroutine, returning value in operand 0
11431
11432 (define_expand "call_value"
11433   [(set (match_operand 0 "" "")
11434         (call (match_operand:QI 1 "" "")
11435               (match_operand 2 "" "")))
11436    (use (match_operand 3 "" ""))]
11437   ""
11438 {
11439   ix86_expand_call (operands[0], operands[1], operands[2],
11440                     operands[3], NULL, false);
11441   DONE;
11442 })
11443
11444 (define_expand "sibcall_value"
11445   [(set (match_operand 0 "" "")
11446         (call (match_operand:QI 1 "" "")
11447               (match_operand 2 "" "")))
11448    (use (match_operand 3 "" ""))]
11449   ""
11450 {
11451   ix86_expand_call (operands[0], operands[1], operands[2],
11452                     operands[3], NULL, true);
11453   DONE;
11454 })
11455
11456 (define_insn_and_split "*call_value_vzeroupper"
11457   [(set (match_operand 0 "" "")
11458         (call (mem:QI (match_operand:P 1 "call_insn_operand" "<c>zw"))
11459               (match_operand 2 "" "")))
11460    (unspec [(match_operand 3 "const_int_operand" "")]
11461            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11462   "TARGET_VZEROUPPER && !SIBLING_CALL_P (insn)"
11463   "#"
11464   "&& reload_completed"
11465   [(const_int 0)]
11466   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11467   [(set_attr "type" "callv")])
11468
11469 (define_insn "*call_value"
11470   [(set (match_operand 0 "" "")
11471         (call (mem:QI (match_operand:P 1 "call_insn_operand" "<c>zw"))
11472               (match_operand 2 "" "")))]
11473   "!SIBLING_CALL_P (insn)"
11474   "* return ix86_output_call_insn (insn, operands[1]);"
11475   [(set_attr "type" "callv")])
11476
11477 (define_insn_and_split "*sibcall_value_vzeroupper"
11478   [(set (match_operand 0 "" "")
11479         (call (mem:QI (match_operand:P 1 "sibcall_insn_operand" "Uz"))
11480               (match_operand 2 "" "")))
11481    (unspec [(match_operand 3 "const_int_operand" "")]
11482            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11483   "TARGET_VZEROUPPER && SIBLING_CALL_P (insn)"
11484   "#"
11485   "&& reload_completed"
11486   [(const_int 0)]
11487   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11488   [(set_attr "type" "callv")])
11489
11490 (define_insn "*sibcall_value"
11491   [(set (match_operand 0 "" "")
11492         (call (mem:QI (match_operand:P 1 "sibcall_insn_operand" "Uz"))
11493               (match_operand 2 "" "")))]
11494   "SIBLING_CALL_P (insn)"
11495   "* return ix86_output_call_insn (insn, operands[1]);"
11496   [(set_attr "type" "callv")])
11497
11498 (define_insn_and_split "*call_value_rex64_ms_sysv_vzeroupper"
11499   [(set (match_operand 0 "" "")
11500         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rzw"))
11501               (match_operand 2 "" "")))
11502    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11503    (clobber (reg:TI XMM6_REG))
11504    (clobber (reg:TI XMM7_REG))
11505    (clobber (reg:TI XMM8_REG))
11506    (clobber (reg:TI XMM9_REG))
11507    (clobber (reg:TI XMM10_REG))
11508    (clobber (reg:TI XMM11_REG))
11509    (clobber (reg:TI XMM12_REG))
11510    (clobber (reg:TI XMM13_REG))
11511    (clobber (reg:TI XMM14_REG))
11512    (clobber (reg:TI XMM15_REG))
11513    (clobber (reg:DI SI_REG))
11514    (clobber (reg:DI DI_REG))
11515    (unspec [(match_operand 3 "const_int_operand" "")]
11516            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11517   "TARGET_VZEROUPPER && TARGET_64BIT && !SIBLING_CALL_P (insn)"
11518   "#"
11519   "&& reload_completed"
11520   [(const_int 0)]
11521   "ix86_split_call_vzeroupper (curr_insn, operands[3]); DONE;"
11522   [(set_attr "type" "callv")])
11523
11524 (define_insn "*call_value_rex64_ms_sysv"
11525   [(set (match_operand 0 "" "")
11526         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rzw"))
11527               (match_operand 2 "" "")))
11528    (unspec [(const_int 0)] UNSPEC_MS_TO_SYSV_CALL)
11529    (clobber (reg:TI XMM6_REG))
11530    (clobber (reg:TI XMM7_REG))
11531    (clobber (reg:TI XMM8_REG))
11532    (clobber (reg:TI XMM9_REG))
11533    (clobber (reg:TI XMM10_REG))
11534    (clobber (reg:TI XMM11_REG))
11535    (clobber (reg:TI XMM12_REG))
11536    (clobber (reg:TI XMM13_REG))
11537    (clobber (reg:TI XMM14_REG))
11538    (clobber (reg:TI XMM15_REG))
11539    (clobber (reg:DI SI_REG))
11540    (clobber (reg:DI DI_REG))]
11541   "TARGET_64BIT && !SIBLING_CALL_P (insn)"
11542   "* return ix86_output_call_insn (insn, operands[1]);"
11543   [(set_attr "type" "callv")])
11544
11545 (define_expand "call_value_pop"
11546   [(parallel [(set (match_operand 0 "" "")
11547                    (call (match_operand:QI 1 "" "")
11548                          (match_operand:SI 2 "" "")))
11549               (set (reg:SI SP_REG)
11550                    (plus:SI (reg:SI SP_REG)
11551                             (match_operand:SI 4 "" "")))])]
11552   "!TARGET_64BIT"
11553 {
11554   ix86_expand_call (operands[0], operands[1], operands[2],
11555                     operands[3], operands[4], false);
11556   DONE;
11557 })
11558
11559 (define_insn_and_split "*call_value_pop_vzeroupper"
11560   [(set (match_operand 0 "" "")
11561         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "lzm"))
11562               (match_operand 2 "" "")))
11563    (set (reg:SI SP_REG)
11564         (plus:SI (reg:SI SP_REG)
11565                  (match_operand:SI 3 "immediate_operand" "i")))
11566    (unspec [(match_operand 4 "const_int_operand" "")]
11567            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11568   "TARGET_VZEROUPPER && !TARGET_64BIT && !SIBLING_CALL_P (insn)"
11569   "#"
11570   "&& reload_completed"
11571   [(const_int 0)]
11572   "ix86_split_call_vzeroupper (curr_insn, operands[4]); DONE;"
11573   [(set_attr "type" "callv")])
11574
11575 (define_insn "*call_value_pop"
11576   [(set (match_operand 0 "" "")
11577         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "lzm"))
11578               (match_operand 2 "" "")))
11579    (set (reg:SI SP_REG)
11580         (plus:SI (reg:SI SP_REG)
11581                  (match_operand:SI 3 "immediate_operand" "i")))]
11582   "!TARGET_64BIT && !SIBLING_CALL_P (insn)"
11583   "* return ix86_output_call_insn (insn, operands[1]);"
11584   [(set_attr "type" "callv")])
11585
11586 (define_insn_and_split "*sibcall_value_pop_vzeroupper"
11587   [(set (match_operand 0 "" "")
11588         (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "Uz"))
11589               (match_operand 2 "" "")))
11590    (set (reg:SI SP_REG)
11591         (plus:SI (reg:SI SP_REG)
11592                  (match_operand:SI 3 "immediate_operand" "i")))
11593    (unspec [(match_operand 4 "const_int_operand" "")]
11594            UNSPEC_CALL_NEEDS_VZEROUPPER)]
11595   "TARGET_VZEROUPPER && !TARGET_64BIT && SIBLING_CALL_P (insn)"
11596   "#"
11597   "&& reload_completed"
11598   [(const_int 0)]
11599   "ix86_split_call_vzeroupper (curr_insn, operands[4]); DONE;"
11600   [(set_attr "type" "callv")])
11601
11602 (define_insn "*sibcall_value_pop"
11603   [(set (match_operand 0 "" "")
11604         (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "Uz"))
11605               (match_operand 2 "" "")))
11606    (set (reg:SI SP_REG)
11607         (plus:SI (reg:SI SP_REG)
11608                  (match_operand:SI 3 "immediate_operand" "i")))]
11609   "!TARGET_64BIT && SIBLING_CALL_P (insn)"
11610   "* return ix86_output_call_insn (insn, operands[1]);"
11611   [(set_attr "type" "callv")])
11612
11613 ;; Call subroutine returning any type.
11614
11615 (define_expand "untyped_call"
11616   [(parallel [(call (match_operand 0 "" "")
11617                     (const_int 0))
11618               (match_operand 1 "" "")
11619               (match_operand 2 "" "")])]
11620   ""
11621 {
11622   int i;
11623
11624   /* In order to give reg-stack an easier job in validating two
11625      coprocessor registers as containing a possible return value,
11626      simply pretend the untyped call returns a complex long double
11627      value. 
11628
11629      We can't use SSE_REGPARM_MAX here since callee is unprototyped
11630      and should have the default ABI.  */
11631
11632   ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
11633                      ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
11634                     operands[0], const0_rtx,
11635                     GEN_INT ((TARGET_64BIT
11636                               ? (ix86_abi == SYSV_ABI
11637                                  ? X86_64_SSE_REGPARM_MAX
11638                                  : X86_64_MS_SSE_REGPARM_MAX)
11639                               : X86_32_SSE_REGPARM_MAX)
11640                              - 1),
11641                     NULL, false);
11642
11643   for (i = 0; i < XVECLEN (operands[2], 0); i++)
11644     {
11645       rtx set = XVECEXP (operands[2], 0, i);
11646       emit_move_insn (SET_DEST (set), SET_SRC (set));
11647     }
11648
11649   /* The optimizer does not know that the call sets the function value
11650      registers we stored in the result block.  We avoid problems by
11651      claiming that all hard registers are used and clobbered at this
11652      point.  */
11653   emit_insn (gen_blockage ());
11654
11655   DONE;
11656 })
11657 \f
11658 ;; Prologue and epilogue instructions
11659
11660 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
11661 ;; all of memory.  This blocks insns from being moved across this point.
11662
11663 (define_insn "blockage"
11664   [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
11665   ""
11666   ""
11667   [(set_attr "length" "0")])
11668
11669 ;; Do not schedule instructions accessing memory across this point.
11670
11671 (define_expand "memory_blockage"
11672   [(set (match_dup 0)
11673         (unspec:BLK [(match_dup 0)] UNSPEC_MEMORY_BLOCKAGE))]
11674   ""
11675 {
11676   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
11677   MEM_VOLATILE_P (operands[0]) = 1;
11678 })
11679
11680 (define_insn "*memory_blockage"
11681   [(set (match_operand:BLK 0 "" "")
11682         (unspec:BLK [(match_dup 0)] UNSPEC_MEMORY_BLOCKAGE))]
11683   ""
11684   ""
11685   [(set_attr "length" "0")])
11686
11687 ;; As USE insns aren't meaningful after reload, this is used instead
11688 ;; to prevent deleting instructions setting registers for PIC code
11689 (define_insn "prologue_use"
11690   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_PROLOGUE_USE)]
11691   ""
11692   ""
11693   [(set_attr "length" "0")])
11694
11695 ;; Insn emitted into the body of a function to return from a function.
11696 ;; This is only done if the function's epilogue is known to be simple.
11697 ;; See comments for ix86_can_use_return_insn_p in i386.c.
11698
11699 (define_expand "return"
11700   [(simple_return)]
11701   "ix86_can_use_return_insn_p ()"
11702 {
11703   if (crtl->args.pops_args)
11704     {
11705       rtx popc = GEN_INT (crtl->args.pops_args);
11706       emit_jump_insn (gen_simple_return_pop_internal (popc));
11707       DONE;
11708     }
11709 })
11710
11711 (define_expand "simple_return"
11712   [(simple_return)]
11713   ""
11714 {
11715   if (crtl->args.pops_args)
11716     {
11717       rtx popc = GEN_INT (crtl->args.pops_args);
11718       emit_jump_insn (gen_simple_return_pop_internal (popc));
11719       DONE;
11720     }
11721 })
11722
11723 (define_insn "simple_return_internal"
11724   [(simple_return)]
11725   "reload_completed"
11726   "ret"
11727   [(set_attr "length" "1")
11728    (set_attr "atom_unit" "jeu")
11729    (set_attr "length_immediate" "0")
11730    (set_attr "modrm" "0")])
11731
11732 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
11733 ;; instruction Athlon and K8 have.
11734
11735 (define_insn "simple_return_internal_long"
11736   [(simple_return)
11737    (unspec [(const_int 0)] UNSPEC_REP)]
11738   "reload_completed"
11739   "rep\;ret"
11740   [(set_attr "length" "2")
11741    (set_attr "atom_unit" "jeu")
11742    (set_attr "length_immediate" "0")
11743    (set_attr "prefix_rep" "1")
11744    (set_attr "modrm" "0")])
11745
11746 (define_insn "simple_return_pop_internal"
11747   [(simple_return)
11748    (use (match_operand:SI 0 "const_int_operand" ""))]
11749   "reload_completed"
11750   "ret\t%0"
11751   [(set_attr "length" "3")
11752    (set_attr "atom_unit" "jeu")
11753    (set_attr "length_immediate" "2")
11754    (set_attr "modrm" "0")])
11755
11756 (define_insn "simple_return_indirect_internal"
11757   [(simple_return)
11758    (use (match_operand:SI 0 "register_operand" "r"))]
11759   "reload_completed"
11760   "jmp\t%A0"
11761   [(set_attr "type" "ibr")
11762    (set_attr "length_immediate" "0")])
11763
11764 (define_insn "nop"
11765   [(const_int 0)]
11766   ""
11767   "nop"
11768   [(set_attr "length" "1")
11769    (set_attr "length_immediate" "0")
11770    (set_attr "modrm" "0")])
11771
11772 ;; Generate nops.  Operand 0 is the number of nops, up to 8.
11773 (define_insn "nops"
11774   [(unspec_volatile [(match_operand 0 "const_int_operand" "")]
11775                     UNSPECV_NOPS)]
11776   "reload_completed"
11777 {
11778   int num = INTVAL (operands[0]);
11779
11780   gcc_assert (num >= 1 && num <= 8);
11781
11782   while (num--)
11783     fputs ("\tnop\n", asm_out_file);
11784
11785   return "";
11786 }
11787   [(set (attr "length") (symbol_ref "INTVAL (operands[0])"))
11788    (set_attr "length_immediate" "0")
11789    (set_attr "modrm" "0")])
11790
11791 ;; Pad to 16-byte boundary, max skip in op0.  Used to avoid
11792 ;; branch prediction penalty for the third jump in a 16-byte
11793 ;; block on K8.
11794
11795 (define_insn "pad"
11796   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
11797   ""
11798 {
11799 #ifdef ASM_OUTPUT_MAX_SKIP_PAD
11800   ASM_OUTPUT_MAX_SKIP_PAD (asm_out_file, 4, (int)INTVAL (operands[0]));
11801 #else
11802   /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
11803      The align insn is used to avoid 3 jump instructions in the row to improve
11804      branch prediction and the benefits hardly outweigh the cost of extra 8
11805      nops on the average inserted by full alignment pseudo operation.  */
11806 #endif
11807   return "";
11808 }
11809   [(set_attr "length" "16")])
11810
11811 (define_expand "prologue"
11812   [(const_int 0)]
11813   ""
11814   "ix86_expand_prologue (); DONE;")
11815
11816 (define_insn "set_got"
11817   [(set (match_operand:SI 0 "register_operand" "=r")
11818         (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
11819    (clobber (reg:CC FLAGS_REG))]
11820   "!TARGET_64BIT"
11821   "* return output_set_got (operands[0], NULL_RTX);"
11822   [(set_attr "type" "multi")
11823    (set_attr "length" "12")])
11824
11825 (define_insn "set_got_labelled"
11826   [(set (match_operand:SI 0 "register_operand" "=r")
11827         (unspec:SI [(label_ref (match_operand 1 "" ""))]
11828          UNSPEC_SET_GOT))
11829    (clobber (reg:CC FLAGS_REG))]
11830   "!TARGET_64BIT"
11831   "* return output_set_got (operands[0], operands[1]);"
11832   [(set_attr "type" "multi")
11833    (set_attr "length" "12")])
11834
11835 (define_insn "set_got_rex64"
11836   [(set (match_operand:DI 0 "register_operand" "=r")
11837         (unspec:DI [(const_int 0)] UNSPEC_SET_GOT))]
11838   "TARGET_64BIT"
11839   "lea{q}\t{_GLOBAL_OFFSET_TABLE_(%%rip), %0|%0, _GLOBAL_OFFSET_TABLE_[rip]}"
11840   [(set_attr "type" "lea")
11841    (set_attr "length_address" "4")
11842    (set_attr "mode" "DI")])
11843
11844 (define_insn "set_rip_rex64"
11845   [(set (match_operand:DI 0 "register_operand" "=r")
11846         (unspec:DI [(label_ref (match_operand 1 "" ""))] UNSPEC_SET_RIP))]
11847   "TARGET_64BIT"
11848   "lea{q}\t{%l1(%%rip), %0|%0, %l1[rip]}"
11849   [(set_attr "type" "lea")
11850    (set_attr "length_address" "4")
11851    (set_attr "mode" "DI")])
11852
11853 (define_insn "set_got_offset_rex64"
11854   [(set (match_operand:DI 0 "register_operand" "=r")
11855         (unspec:DI
11856           [(label_ref (match_operand 1 "" ""))]
11857           UNSPEC_SET_GOT_OFFSET))]
11858   "TARGET_LP64"
11859   "movabs{q}\t{$_GLOBAL_OFFSET_TABLE_-%l1, %0|%0, OFFSET FLAT:_GLOBAL_OFFSET_TABLE_-%l1}"
11860   [(set_attr "type" "imov")
11861    (set_attr "length_immediate" "0")
11862    (set_attr "length_address" "8")
11863    (set_attr "mode" "DI")])
11864
11865 (define_expand "epilogue"
11866   [(const_int 0)]
11867   ""
11868   "ix86_expand_epilogue (1); DONE;")
11869
11870 (define_expand "sibcall_epilogue"
11871   [(const_int 0)]
11872   ""
11873   "ix86_expand_epilogue (0); DONE;")
11874
11875 (define_expand "eh_return"
11876   [(use (match_operand 0 "register_operand" ""))]
11877   ""
11878 {
11879   rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
11880
11881   /* Tricky bit: we write the address of the handler to which we will
11882      be returning into someone else's stack frame, one word below the
11883      stack address we wish to restore.  */
11884   tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
11885   tmp = plus_constant (tmp, -UNITS_PER_WORD);
11886   tmp = gen_rtx_MEM (Pmode, tmp);
11887   emit_move_insn (tmp, ra);
11888
11889   emit_jump_insn (gen_eh_return_internal ());
11890   emit_barrier ();
11891   DONE;
11892 })
11893
11894 (define_insn_and_split "eh_return_internal"
11895   [(eh_return)]
11896   ""
11897   "#"
11898   "epilogue_completed"
11899   [(const_int 0)]
11900   "ix86_expand_epilogue (2); DONE;")
11901
11902 (define_insn "leave"
11903   [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4)))
11904    (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG)))
11905    (clobber (mem:BLK (scratch)))]
11906   "!TARGET_64BIT"
11907   "leave"
11908   [(set_attr "type" "leave")])
11909
11910 (define_insn "leave_rex64"
11911   [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8)))
11912    (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG)))
11913    (clobber (mem:BLK (scratch)))]
11914   "TARGET_64BIT"
11915   "leave"
11916   [(set_attr "type" "leave")])
11917 \f
11918 ;; Handle -fsplit-stack.
11919
11920 (define_expand "split_stack_prologue"
11921   [(const_int 0)]
11922   ""
11923 {
11924   ix86_expand_split_stack_prologue ();
11925   DONE;
11926 })
11927
11928 ;; In order to support the call/return predictor, we use a return
11929 ;; instruction which the middle-end doesn't see.
11930 (define_insn "split_stack_return"
11931   [(unspec_volatile [(match_operand:SI 0 "const_int_operand" "")]
11932                      UNSPECV_SPLIT_STACK_RETURN)]
11933   ""
11934 {
11935   if (operands[0] == const0_rtx)
11936     return "ret";
11937   else
11938     return "ret\t%0";
11939 }
11940   [(set_attr "atom_unit" "jeu")
11941    (set_attr "modrm" "0")
11942    (set (attr "length")
11943         (if_then_else (match_operand:SI 0 "const0_operand" "")
11944                       (const_int 1)
11945                       (const_int 3)))
11946    (set (attr "length_immediate")
11947         (if_then_else (match_operand:SI 0 "const0_operand" "")
11948                       (const_int 0)
11949                       (const_int 2)))])
11950
11951 ;; If there are operand 0 bytes available on the stack, jump to
11952 ;; operand 1.
11953
11954 (define_expand "split_stack_space_check"
11955   [(set (pc) (if_then_else
11956               (ltu (minus (reg SP_REG)
11957                           (match_operand 0 "register_operand" ""))
11958                    (unspec [(const_int 0)] UNSPEC_STACK_CHECK))
11959               (label_ref (match_operand 1 "" ""))
11960               (pc)))]
11961   ""
11962 {
11963   rtx reg, size, limit;
11964
11965   reg = gen_reg_rtx (Pmode);
11966   size = force_reg (Pmode, operands[0]);
11967   emit_insn (gen_sub3_insn (reg, stack_pointer_rtx, size));
11968   limit = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, const0_rtx),
11969                           UNSPEC_STACK_CHECK);
11970   limit = gen_rtx_MEM (Pmode, gen_rtx_CONST (Pmode, limit));
11971   ix86_expand_branch (GEU, reg, limit, operands[1]);
11972
11973   DONE;
11974 })
11975 \f
11976 ;; Bit manipulation instructions.
11977
11978 (define_expand "ffs<mode>2"
11979   [(set (match_dup 2) (const_int -1))
11980    (parallel [(set (reg:CCZ FLAGS_REG)
11981                    (compare:CCZ
11982                      (match_operand:SWI48 1 "nonimmediate_operand" "")
11983                      (const_int 0)))
11984               (set (match_operand:SWI48 0 "register_operand" "")
11985                    (ctz:SWI48 (match_dup 1)))])
11986    (set (match_dup 0) (if_then_else:SWI48
11987                         (eq (reg:CCZ FLAGS_REG) (const_int 0))
11988                         (match_dup 2)
11989                         (match_dup 0)))
11990    (parallel [(set (match_dup 0) (plus:SWI48 (match_dup 0) (const_int 1)))
11991               (clobber (reg:CC FLAGS_REG))])]
11992   ""
11993 {
11994   if (<MODE>mode == SImode && !TARGET_CMOVE)
11995     {
11996       emit_insn (gen_ffssi2_no_cmove (operands[0], operands [1]));
11997       DONE;
11998     }
11999   operands[2] = gen_reg_rtx (<MODE>mode);
12000 })
12001
12002 (define_insn_and_split "ffssi2_no_cmove"
12003   [(set (match_operand:SI 0 "register_operand" "=r")
12004         (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
12005    (clobber (match_scratch:SI 2 "=&q"))
12006    (clobber (reg:CC FLAGS_REG))]
12007   "!TARGET_CMOVE"
12008   "#"
12009   "&& reload_completed"
12010   [(parallel [(set (reg:CCZ FLAGS_REG)
12011                    (compare:CCZ (match_dup 1) (const_int 0)))
12012               (set (match_dup 0) (ctz:SI (match_dup 1)))])
12013    (set (strict_low_part (match_dup 3))
12014         (eq:QI (reg:CCZ FLAGS_REG) (const_int 0)))
12015    (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
12016               (clobber (reg:CC FLAGS_REG))])
12017    (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
12018               (clobber (reg:CC FLAGS_REG))])
12019    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
12020               (clobber (reg:CC FLAGS_REG))])]
12021 {
12022   operands[3] = gen_lowpart (QImode, operands[2]);
12023   ix86_expand_clear (operands[2]);
12024 })
12025
12026 (define_insn "*ffs<mode>_1"
12027   [(set (reg:CCZ FLAGS_REG)
12028         (compare:CCZ (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12029                      (const_int 0)))
12030    (set (match_operand:SWI48 0 "register_operand" "=r")
12031         (ctz:SWI48 (match_dup 1)))]
12032   ""
12033   "bsf{<imodesuffix>}\t{%1, %0|%0, %1}"
12034   [(set_attr "type" "alu1")
12035    (set_attr "prefix_0f" "1")
12036    (set_attr "mode" "<MODE>")])
12037
12038 (define_insn "ctz<mode>2"
12039   [(set (match_operand:SWI248 0 "register_operand" "=r")
12040         (ctz:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" "rm")))
12041    (clobber (reg:CC FLAGS_REG))]
12042   ""
12043 {
12044   if (TARGET_BMI)
12045     return "tzcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
12046   else
12047     return "bsf{<imodesuffix>}\t{%1, %0|%0, %1}";
12048 }
12049   [(set_attr "type" "alu1")
12050    (set_attr "prefix_0f" "1")
12051    (set (attr "prefix_rep") (symbol_ref "TARGET_BMI"))
12052    (set_attr "mode" "<MODE>")])
12053
12054 (define_expand "clz<mode>2"
12055   [(parallel
12056      [(set (match_operand:SWI248 0 "register_operand" "")
12057            (minus:SWI248
12058              (match_dup 2)
12059              (clz:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" ""))))
12060       (clobber (reg:CC FLAGS_REG))])
12061    (parallel
12062      [(set (match_dup 0) (xor:SWI248 (match_dup 0) (match_dup 2)))
12063       (clobber (reg:CC FLAGS_REG))])]
12064   ""
12065 {
12066   if (TARGET_LZCNT)
12067     {
12068       emit_insn (gen_clz<mode>2_lzcnt (operands[0], operands[1]));
12069       DONE;
12070     }
12071   operands[2] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode)-1);
12072 })
12073
12074 (define_insn "clz<mode>2_lzcnt"
12075   [(set (match_operand:SWI248 0 "register_operand" "=r")
12076         (clz:SWI248 (match_operand:SWI248 1 "nonimmediate_operand" "rm")))
12077    (clobber (reg:CC FLAGS_REG))]
12078   "TARGET_LZCNT"
12079   "lzcnt{<imodesuffix>}\t{%1, %0|%0, %1}"
12080   [(set_attr "prefix_rep" "1")
12081    (set_attr "type" "bitmanip")
12082    (set_attr "mode" "<MODE>")])
12083
12084 ;; BMI instructions.
12085 (define_insn "*bmi_andn_<mode>"
12086   [(set (match_operand:SWI48 0 "register_operand" "=r")
12087         (and:SWI48
12088           (not:SWI48
12089             (match_operand:SWI48 1 "register_operand" "r"))
12090             (match_operand:SWI48 2 "nonimmediate_operand" "rm")))
12091    (clobber (reg:CC FLAGS_REG))]
12092   "TARGET_BMI"
12093   "andn\t{%2, %1, %0|%0, %1, %2}"
12094   [(set_attr "type" "bitmanip")
12095    (set_attr "mode" "<MODE>")])
12096
12097 (define_insn "bmi_bextr_<mode>"
12098   [(set (match_operand:SWI48 0 "register_operand" "=r")
12099         (unspec:SWI48 [(match_operand:SWI48 1 "nonimmediate_operand" "rm")
12100                        (match_operand:SWI48 2 "register_operand" "r")]
12101                        UNSPEC_BEXTR))
12102    (clobber (reg:CC FLAGS_REG))]
12103   "TARGET_BMI"
12104   "bextr\t{%2, %1, %0|%0, %1, %2}"
12105   [(set_attr "type" "bitmanip")
12106    (set_attr "mode" "<MODE>")])
12107
12108 (define_insn "*bmi_blsi_<mode>"
12109   [(set (match_operand:SWI48 0 "register_operand" "=r")
12110         (and:SWI48
12111           (neg:SWI48
12112             (match_operand:SWI48 1 "nonimmediate_operand" "rm"))
12113           (match_dup 1)))
12114    (clobber (reg:CC FLAGS_REG))]
12115   "TARGET_BMI"
12116   "blsi\t{%1, %0|%0, %1}"
12117   [(set_attr "type" "bitmanip")
12118    (set_attr "mode" "<MODE>")])
12119
12120 (define_insn "*bmi_blsmsk_<mode>"
12121   [(set (match_operand:SWI48 0 "register_operand" "=r")
12122         (xor:SWI48
12123           (plus:SWI48
12124             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12125             (const_int -1))
12126           (match_dup 1)))
12127    (clobber (reg:CC FLAGS_REG))]
12128   "TARGET_BMI"
12129   "blsmsk\t{%1, %0|%0, %1}"
12130   [(set_attr "type" "bitmanip")
12131    (set_attr "mode" "<MODE>")])
12132
12133 (define_insn "*bmi_blsr_<mode>"
12134   [(set (match_operand:SWI48 0 "register_operand" "=r")
12135         (and:SWI48
12136           (plus:SWI48
12137             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12138             (const_int -1))
12139           (match_dup 1)))
12140    (clobber (reg:CC FLAGS_REG))]
12141    "TARGET_BMI"
12142    "blsr\t{%1, %0|%0, %1}"
12143   [(set_attr "type" "bitmanip")
12144    (set_attr "mode" "<MODE>")])
12145
12146 ;; BMI2 instructions.
12147 (define_insn "bmi2_bzhi_<mode>3"
12148   [(set (match_operand:SWI48 0 "register_operand" "=r")
12149         (and:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12150                    (lshiftrt:SWI48 (const_int -1)
12151                                    (match_operand:SWI48 2 "register_operand" "r"))))
12152    (clobber (reg:CC FLAGS_REG))]
12153   "TARGET_BMI2"
12154   "bzhi\t{%2, %1, %0|%0, %1, %2}"
12155   [(set_attr "type" "bitmanip")
12156    (set_attr "prefix" "vex")
12157    (set_attr "mode" "<MODE>")])
12158
12159 (define_insn "bmi2_pdep_<mode>3"
12160   [(set (match_operand:SWI48 0 "register_operand" "=r")
12161         (unspec:SWI48 [(match_operand:SWI48 1 "nonimmediate_operand" "rm")
12162                        (match_operand:SWI48 2 "register_operand" "r")]
12163                        UNSPEC_PDEP))]
12164   "TARGET_BMI2"
12165   "pdep\t{%2, %1, %0|%0, %1, %2}"
12166   [(set_attr "type" "bitmanip")
12167    (set_attr "prefix" "vex")
12168    (set_attr "mode" "<MODE>")])
12169
12170 (define_insn "bmi2_pext_<mode>3"
12171   [(set (match_operand:SWI48 0 "register_operand" "=r")
12172         (unspec:SWI48 [(match_operand:SWI48 1 "nonimmediate_operand" "rm")
12173                        (match_operand:SWI48 2 "register_operand" "r")]
12174                        UNSPEC_PEXT))]
12175   "TARGET_BMI2"
12176   "pext\t{%2, %1, %0|%0, %1, %2}"
12177   [(set_attr "type" "bitmanip")
12178    (set_attr "prefix" "vex")
12179    (set_attr "mode" "<MODE>")])
12180
12181 ;; TBM instructions.
12182 (define_insn "tbm_bextri_<mode>"
12183   [(set (match_operand:SWI48 0 "register_operand" "=r")
12184         (zero_extract:SWI48
12185           (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12186           (match_operand:SWI48 2 "const_0_to_255_operand" "n")
12187           (match_operand:SWI48 3 "const_0_to_255_operand" "n")))
12188    (clobber (reg:CC FLAGS_REG))]
12189    "TARGET_TBM"
12190 {
12191   operands[2] = GEN_INT (INTVAL (operands[2]) << 8 | INTVAL (operands[3]));
12192   return "bextr\t{%2, %1, %0|%0, %1, %2}";
12193 }
12194   [(set_attr "type" "bitmanip")
12195    (set_attr "mode" "<MODE>")])
12196
12197 (define_insn "*tbm_blcfill_<mode>"
12198   [(set (match_operand:SWI48 0 "register_operand" "=r")
12199         (and:SWI48
12200           (plus:SWI48
12201             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12202             (const_int 1))
12203           (match_dup 1)))
12204    (clobber (reg:CC FLAGS_REG))]
12205    "TARGET_TBM"
12206    "blcfill\t{%1, %0|%0, %1}"
12207   [(set_attr "type" "bitmanip")
12208    (set_attr "mode" "<MODE>")])
12209
12210 (define_insn "*tbm_blci_<mode>"
12211   [(set (match_operand:SWI48 0 "register_operand" "=r")
12212         (ior:SWI48
12213           (not:SWI48
12214             (plus:SWI48
12215               (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12216               (const_int 1)))
12217           (match_dup 1)))
12218    (clobber (reg:CC FLAGS_REG))]
12219    "TARGET_TBM"
12220    "blci\t{%1, %0|%0, %1}"
12221   [(set_attr "type" "bitmanip")
12222    (set_attr "mode" "<MODE>")])
12223
12224 (define_insn "*tbm_blcic_<mode>"
12225   [(set (match_operand:SWI48 0 "register_operand" "=r")
12226         (and:SWI48
12227           (plus:SWI48
12228             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12229             (const_int 1))
12230           (not:SWI48
12231             (match_dup 1))))
12232    (clobber (reg:CC FLAGS_REG))]
12233    "TARGET_TBM"
12234    "blcic\t{%1, %0|%0, %1}"
12235   [(set_attr "type" "bitmanip")
12236    (set_attr "mode" "<MODE>")])
12237
12238 (define_insn "*tbm_blcmsk_<mode>"
12239   [(set (match_operand:SWI48 0 "register_operand" "=r")
12240         (xor:SWI48
12241           (plus:SWI48
12242             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12243             (const_int 1))
12244           (match_dup 1)))
12245    (clobber (reg:CC FLAGS_REG))]
12246    "TARGET_TBM"
12247    "blcmsk\t{%1, %0|%0, %1}"
12248   [(set_attr "type" "bitmanip")
12249    (set_attr "mode" "<MODE>")])
12250
12251 (define_insn "*tbm_blcs_<mode>"
12252   [(set (match_operand:SWI48 0 "register_operand" "=r")
12253         (ior:SWI48
12254           (plus:SWI48
12255             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12256             (const_int 1))
12257           (match_dup 1)))
12258    (clobber (reg:CC FLAGS_REG))]
12259    "TARGET_TBM"
12260    "blcs\t{%1, %0|%0, %1}"
12261   [(set_attr "type" "bitmanip")
12262    (set_attr "mode" "<MODE>")])
12263
12264 (define_insn "*tbm_blsfill_<mode>"
12265   [(set (match_operand:SWI48 0 "register_operand" "=r")
12266         (ior:SWI48
12267           (plus:SWI48
12268             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12269             (const_int -1))
12270           (match_dup 1)))
12271    (clobber (reg:CC FLAGS_REG))]
12272    "TARGET_TBM"
12273    "blsfill\t{%1, %0|%0, %1}"
12274   [(set_attr "type" "bitmanip")
12275    (set_attr "mode" "<MODE>")])
12276
12277 (define_insn "*tbm_blsic_<mode>"
12278   [(set (match_operand:SWI48 0 "register_operand" "=r")
12279         (ior:SWI48
12280           (plus:SWI48
12281             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12282             (const_int -1))
12283           (not:SWI48
12284             (match_dup 1))))
12285    (clobber (reg:CC FLAGS_REG))]
12286    "TARGET_TBM"
12287    "blsic\t{%1, %0|%0, %1}"
12288   [(set_attr "type" "bitmanip")
12289    (set_attr "mode" "<MODE>")])
12290
12291 (define_insn "*tbm_t1mskc_<mode>"
12292   [(set (match_operand:SWI48 0 "register_operand" "=r")
12293         (ior:SWI48
12294           (plus:SWI48
12295             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12296             (const_int 1))
12297           (not:SWI48
12298             (match_dup 1))))
12299    (clobber (reg:CC FLAGS_REG))]
12300    "TARGET_TBM"
12301    "t1mskc\t{%1, %0|%0, %1}"
12302   [(set_attr "type" "bitmanip")
12303    (set_attr "mode" "<MODE>")])
12304
12305 (define_insn "*tbm_tzmsk_<mode>"
12306   [(set (match_operand:SWI48 0 "register_operand" "=r")
12307         (and:SWI48
12308           (plus:SWI48
12309             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
12310             (const_int -1))
12311           (not:SWI48
12312             (match_dup 1))))
12313    (clobber (reg:CC FLAGS_REG))]
12314    "TARGET_TBM"
12315    "tzmsk\t{%1, %0|%0, %1}"
12316   [(set_attr "type" "bitmanip")
12317    (set_attr "mode" "<MODE>")])
12318
12319 (define_insn "bsr_rex64"
12320   [(set (match_operand:DI 0 "register_operand" "=r")
12321         (minus:DI (const_int 63)
12322                   (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))))
12323    (clobber (reg:CC FLAGS_REG))]
12324   "TARGET_64BIT"
12325   "bsr{q}\t{%1, %0|%0, %1}"
12326   [(set_attr "type" "alu1")
12327    (set_attr "prefix_0f" "1")
12328    (set_attr "mode" "DI")])
12329
12330 (define_insn "bsr"
12331   [(set (match_operand:SI 0 "register_operand" "=r")
12332         (minus:SI (const_int 31)
12333                   (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
12334    (clobber (reg:CC FLAGS_REG))]
12335   ""
12336   "bsr{l}\t{%1, %0|%0, %1}"
12337   [(set_attr "type" "alu1")
12338    (set_attr "prefix_0f" "1")
12339    (set_attr "mode" "SI")])
12340
12341 (define_insn "*bsrhi"
12342   [(set (match_operand:HI 0 "register_operand" "=r")
12343         (minus:HI (const_int 15)
12344                   (clz:HI (match_operand:HI 1 "nonimmediate_operand" "rm"))))
12345    (clobber (reg:CC FLAGS_REG))]
12346   ""
12347   "bsr{w}\t{%1, %0|%0, %1}"
12348   [(set_attr "type" "alu1")
12349    (set_attr "prefix_0f" "1")
12350    (set_attr "mode" "HI")])
12351
12352 (define_insn "popcount<mode>2"
12353   [(set (match_operand:SWI248 0 "register_operand" "=r")
12354         (popcount:SWI248
12355           (match_operand:SWI248 1 "nonimmediate_operand" "rm")))
12356    (clobber (reg:CC FLAGS_REG))]
12357   "TARGET_POPCNT"
12358 {
12359 #if TARGET_MACHO
12360   return "popcnt\t{%1, %0|%0, %1}";
12361 #else
12362   return "popcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
12363 #endif
12364 }
12365   [(set_attr "prefix_rep" "1")
12366    (set_attr "type" "bitmanip")
12367    (set_attr "mode" "<MODE>")])
12368
12369 (define_insn "*popcount<mode>2_cmp"
12370   [(set (reg FLAGS_REG)
12371         (compare
12372           (popcount:SWI248
12373             (match_operand:SWI248 1 "nonimmediate_operand" "rm"))
12374           (const_int 0)))
12375    (set (match_operand:SWI248 0 "register_operand" "=r")
12376         (popcount:SWI248 (match_dup 1)))]
12377   "TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
12378 {
12379 #if TARGET_MACHO
12380   return "popcnt\t{%1, %0|%0, %1}";
12381 #else
12382   return "popcnt{<imodesuffix>}\t{%1, %0|%0, %1}";
12383 #endif
12384 }
12385   [(set_attr "prefix_rep" "1")
12386    (set_attr "type" "bitmanip")
12387    (set_attr "mode" "<MODE>")])
12388
12389 (define_insn "*popcountsi2_cmp_zext"
12390   [(set (reg FLAGS_REG)
12391         (compare
12392           (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))
12393           (const_int 0)))
12394    (set (match_operand:DI 0 "register_operand" "=r")
12395         (zero_extend:DI(popcount:SI (match_dup 1))))]
12396   "TARGET_64BIT && TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
12397 {
12398 #if TARGET_MACHO
12399   return "popcnt\t{%1, %0|%0, %1}";
12400 #else
12401   return "popcnt{l}\t{%1, %0|%0, %1}";
12402 #endif
12403 }
12404   [(set_attr "prefix_rep" "1")
12405    (set_attr "type" "bitmanip")
12406    (set_attr "mode" "SI")])
12407
12408 (define_expand "bswap<mode>2"
12409   [(set (match_operand:SWI48 0 "register_operand" "")
12410         (bswap:SWI48 (match_operand:SWI48 1 "register_operand" "")))]
12411   ""
12412 {
12413   if (<MODE>mode == SImode && !(TARGET_BSWAP || TARGET_MOVBE))
12414     {
12415       rtx x = operands[0];
12416
12417       emit_move_insn (x, operands[1]);
12418       emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
12419       emit_insn (gen_rotlsi3 (x, x, GEN_INT (16)));
12420       emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
12421       DONE;
12422     }
12423 })
12424
12425 (define_insn "*bswap<mode>2_movbe"
12426   [(set (match_operand:SWI48 0 "nonimmediate_operand" "=r,r,m")
12427         (bswap:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "0,m,r")))]
12428   "TARGET_MOVBE
12429    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
12430   "@
12431     bswap\t%0
12432     movbe\t{%1, %0|%0, %1}
12433     movbe\t{%1, %0|%0, %1}"
12434   [(set_attr "type" "bitmanip,imov,imov")
12435    (set_attr "modrm" "0,1,1")
12436    (set_attr "prefix_0f" "*,1,1")
12437    (set_attr "prefix_extra" "*,1,1")
12438    (set_attr "mode" "<MODE>")])
12439
12440 (define_insn "*bswap<mode>2_1"
12441   [(set (match_operand:SWI48 0 "register_operand" "=r")
12442         (bswap:SWI48 (match_operand:SWI48 1 "register_operand" "0")))]
12443   "TARGET_BSWAP"
12444   "bswap\t%0"
12445   [(set_attr "type" "bitmanip")
12446    (set_attr "modrm" "0")
12447    (set_attr "mode" "<MODE>")])
12448
12449 (define_insn "*bswaphi_lowpart_1"
12450   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+Q,r"))
12451         (bswap:HI (match_dup 0)))
12452    (clobber (reg:CC FLAGS_REG))]
12453   "TARGET_USE_XCHGB || optimize_function_for_size_p (cfun)"
12454   "@
12455     xchg{b}\t{%h0, %b0|%b0, %h0}
12456     rol{w}\t{$8, %0|%0, 8}"
12457   [(set_attr "length" "2,4")
12458    (set_attr "mode" "QI,HI")])
12459
12460 (define_insn "bswaphi_lowpart"
12461   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
12462         (bswap:HI (match_dup 0)))
12463    (clobber (reg:CC FLAGS_REG))]
12464   ""
12465   "rol{w}\t{$8, %0|%0, 8}"
12466   [(set_attr "length" "4")
12467    (set_attr "mode" "HI")])
12468
12469 (define_expand "paritydi2"
12470   [(set (match_operand:DI 0 "register_operand" "")
12471         (parity:DI (match_operand:DI 1 "register_operand" "")))]
12472   "! TARGET_POPCNT"
12473 {
12474   rtx scratch = gen_reg_rtx (QImode);
12475   rtx cond;
12476
12477   emit_insn (gen_paritydi2_cmp (NULL_RTX, NULL_RTX,
12478                                 NULL_RTX, operands[1]));
12479
12480   cond = gen_rtx_fmt_ee (ORDERED, QImode,
12481                          gen_rtx_REG (CCmode, FLAGS_REG),
12482                          const0_rtx);
12483   emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
12484
12485   if (TARGET_64BIT)
12486     emit_insn (gen_zero_extendqidi2 (operands[0], scratch));
12487   else
12488     {
12489       rtx tmp = gen_reg_rtx (SImode);
12490
12491       emit_insn (gen_zero_extendqisi2 (tmp, scratch));
12492       emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
12493     }
12494   DONE;
12495 })
12496
12497 (define_expand "paritysi2"
12498   [(set (match_operand:SI 0 "register_operand" "")
12499         (parity:SI (match_operand:SI 1 "register_operand" "")))]
12500   "! TARGET_POPCNT"
12501 {
12502   rtx scratch = gen_reg_rtx (QImode);
12503   rtx cond;
12504
12505   emit_insn (gen_paritysi2_cmp (NULL_RTX, NULL_RTX, operands[1]));
12506
12507   cond = gen_rtx_fmt_ee (ORDERED, QImode,
12508                          gen_rtx_REG (CCmode, FLAGS_REG),
12509                          const0_rtx);
12510   emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
12511
12512   emit_insn (gen_zero_extendqisi2 (operands[0], scratch));
12513   DONE;
12514 })
12515
12516 (define_insn_and_split "paritydi2_cmp"
12517   [(set (reg:CC FLAGS_REG)
12518         (unspec:CC [(match_operand:DI 3 "register_operand" "0")]
12519                    UNSPEC_PARITY))
12520    (clobber (match_scratch:DI 0 "=r"))
12521    (clobber (match_scratch:SI 1 "=&r"))
12522    (clobber (match_scratch:HI 2 "=Q"))]
12523   "! TARGET_POPCNT"
12524   "#"
12525   "&& reload_completed"
12526   [(parallel
12527      [(set (match_dup 1)
12528            (xor:SI (match_dup 1) (match_dup 4)))
12529       (clobber (reg:CC FLAGS_REG))])
12530    (parallel
12531      [(set (reg:CC FLAGS_REG)
12532            (unspec:CC [(match_dup 1)] UNSPEC_PARITY))
12533       (clobber (match_dup 1))
12534       (clobber (match_dup 2))])]
12535 {
12536   operands[4] = gen_lowpart (SImode, operands[3]);
12537
12538   if (TARGET_64BIT)
12539     {
12540       emit_move_insn (operands[1], gen_lowpart (SImode, operands[3]));
12541       emit_insn (gen_lshrdi3 (operands[3], operands[3], GEN_INT (32)));
12542     }
12543   else
12544     operands[1] = gen_highpart (SImode, operands[3]);
12545 })
12546
12547 (define_insn_and_split "paritysi2_cmp"
12548   [(set (reg:CC FLAGS_REG)
12549         (unspec:CC [(match_operand:SI 2 "register_operand" "0")]
12550                    UNSPEC_PARITY))
12551    (clobber (match_scratch:SI 0 "=r"))
12552    (clobber (match_scratch:HI 1 "=&Q"))]
12553   "! TARGET_POPCNT"
12554   "#"
12555   "&& reload_completed"
12556   [(parallel
12557      [(set (match_dup 1)
12558            (xor:HI (match_dup 1) (match_dup 3)))
12559       (clobber (reg:CC FLAGS_REG))])
12560    (parallel
12561      [(set (reg:CC FLAGS_REG)
12562            (unspec:CC [(match_dup 1)] UNSPEC_PARITY))
12563       (clobber (match_dup 1))])]
12564 {
12565   operands[3] = gen_lowpart (HImode, operands[2]);
12566
12567   emit_move_insn (operands[1], gen_lowpart (HImode, operands[2]));
12568   emit_insn (gen_lshrsi3 (operands[2], operands[2], GEN_INT (16)));
12569 })
12570
12571 (define_insn "*parityhi2_cmp"
12572   [(set (reg:CC FLAGS_REG)
12573         (unspec:CC [(match_operand:HI 1 "register_operand" "0")]
12574                    UNSPEC_PARITY))
12575    (clobber (match_scratch:HI 0 "=Q"))]
12576   "! TARGET_POPCNT"
12577   "xor{b}\t{%h0, %b0|%b0, %h0}"
12578   [(set_attr "length" "2")
12579    (set_attr "mode" "HI")])
12580
12581 \f
12582 ;; Thread-local storage patterns for ELF.
12583 ;;
12584 ;; Note that these code sequences must appear exactly as shown
12585 ;; in order to allow linker relaxation.
12586
12587 (define_insn "*tls_global_dynamic_32_gnu"
12588   [(set (match_operand:SI 0 "register_operand" "=a")
12589         (unspec:SI
12590          [(match_operand:SI 1 "register_operand" "b")
12591           (match_operand:SI 2 "tls_symbolic_operand" "")
12592           (match_operand:SI 3 "constant_call_address_operand" "z")]
12593          UNSPEC_TLS_GD))
12594    (clobber (match_scratch:SI 4 "=d"))
12595    (clobber (match_scratch:SI 5 "=c"))
12596    (clobber (reg:CC FLAGS_REG))]
12597   "!TARGET_64BIT && TARGET_GNU_TLS"
12598 {
12599   output_asm_insn
12600     ("lea{l}\t{%a2@tlsgd(,%1,1), %0|%0, %a2@tlsgd[%1*1]}", operands);
12601   if (TARGET_SUN_TLS)
12602 #ifdef HAVE_AS_IX86_TLSGDPLT
12603     return "call\t%a2@tlsgdplt";
12604 #else
12605     return "call\t%p3@plt";
12606 #endif
12607   return "call\t%P3";
12608 }
12609   [(set_attr "type" "multi")
12610    (set_attr "length" "12")])
12611
12612 (define_expand "tls_global_dynamic_32"
12613   [(parallel
12614     [(set (match_operand:SI 0 "register_operand" "")
12615           (unspec:SI [(match_operand:SI 2 "register_operand" "")
12616                       (match_operand:SI 1 "tls_symbolic_operand" "")
12617                       (match_operand:SI 3 "constant_call_address_operand" "")]
12618                      UNSPEC_TLS_GD))
12619      (clobber (match_scratch:SI 4 ""))
12620      (clobber (match_scratch:SI 5 ""))
12621      (clobber (reg:CC FLAGS_REG))])])
12622
12623 (define_insn "*tls_global_dynamic_64"
12624   [(set (match_operand:DI 0 "register_operand" "=a")
12625         (call:DI
12626          (mem:QI (match_operand:DI 2 "constant_call_address_operand" "z"))
12627          (match_operand:DI 3 "" "")))
12628    (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12629               UNSPEC_TLS_GD)]
12630   "TARGET_64BIT"
12631 {
12632   if (!TARGET_X32)
12633     fputs (ASM_BYTE "0x66\n", asm_out_file);
12634   output_asm_insn
12635     ("lea{q}\t{%a1@tlsgd(%%rip), %%rdi|rdi, %a1@tlsgd[rip]}", operands);
12636   fputs (ASM_SHORT "0x6666\n", asm_out_file);
12637   fputs ("\trex64\n", asm_out_file);
12638   if (TARGET_SUN_TLS)
12639     return "call\t%p2@plt";
12640   return "call\t%P2";
12641 }
12642   [(set_attr "type" "multi")
12643    (set (attr "length")
12644         (symbol_ref "TARGET_X32 ? 15 : 16"))])
12645
12646 (define_expand "tls_global_dynamic_64"
12647   [(parallel
12648     [(set (match_operand:DI 0 "register_operand" "")
12649           (call:DI
12650            (mem:QI (match_operand:DI 2 "constant_call_address_operand" ""))
12651            (const_int 0)))
12652      (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12653                 UNSPEC_TLS_GD)])])
12654
12655 (define_insn "*tls_local_dynamic_base_32_gnu"
12656   [(set (match_operand:SI 0 "register_operand" "=a")
12657         (unspec:SI
12658          [(match_operand:SI 1 "register_operand" "b")
12659           (match_operand:SI 2 "constant_call_address_operand" "z")]
12660          UNSPEC_TLS_LD_BASE))
12661    (clobber (match_scratch:SI 3 "=d"))
12662    (clobber (match_scratch:SI 4 "=c"))
12663    (clobber (reg:CC FLAGS_REG))]
12664   "!TARGET_64BIT && TARGET_GNU_TLS"
12665 {
12666   output_asm_insn
12667     ("lea{l}\t{%&@tlsldm(%1), %0|%0, %&@tlsldm[%1]}", operands);
12668   if (TARGET_SUN_TLS)
12669 #ifdef HAVE_AS_IX86_TLSLDMPLT
12670     return "call\t%&@tlsldmplt";
12671 #else
12672     return "call\t%p2@plt";
12673 #endif
12674   return "call\t%P2";
12675 }
12676   [(set_attr "type" "multi")
12677    (set_attr "length" "11")])
12678
12679 (define_expand "tls_local_dynamic_base_32"
12680   [(parallel
12681      [(set (match_operand:SI 0 "register_operand" "")
12682            (unspec:SI
12683             [(match_operand:SI 1 "register_operand" "")
12684              (match_operand:SI 2 "constant_call_address_operand" "")]
12685             UNSPEC_TLS_LD_BASE))
12686       (clobber (match_scratch:SI 3 ""))
12687       (clobber (match_scratch:SI 4 ""))
12688       (clobber (reg:CC FLAGS_REG))])])
12689
12690 (define_insn "*tls_local_dynamic_base_64"
12691   [(set (match_operand:DI 0 "register_operand" "=a")
12692         (call:DI
12693          (mem:QI (match_operand:DI 1 "constant_call_address_operand" "z"))
12694          (match_operand:DI 2 "" "")))
12695    (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
12696   "TARGET_64BIT"
12697 {
12698   output_asm_insn
12699     ("lea{q}\t{%&@tlsld(%%rip), %%rdi|rdi, %&@tlsld[rip]}", operands);
12700   if (TARGET_SUN_TLS)
12701     return "call\t%p1@plt";
12702   return "call\t%P1";
12703 }
12704   [(set_attr "type" "multi")
12705    (set_attr "length" "12")])
12706
12707 (define_expand "tls_local_dynamic_base_64"
12708   [(parallel
12709      [(set (match_operand:DI 0 "register_operand" "")
12710            (call:DI
12711             (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
12712             (const_int 0)))
12713       (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])])
12714
12715 ;; Local dynamic of a single variable is a lose.  Show combine how
12716 ;; to convert that back to global dynamic.
12717
12718 (define_insn_and_split "*tls_local_dynamic_32_once"
12719   [(set (match_operand:SI 0 "register_operand" "=a")
12720         (plus:SI
12721          (unspec:SI [(match_operand:SI 1 "register_operand" "b")
12722                      (match_operand:SI 2 "constant_call_address_operand" "z")]
12723                     UNSPEC_TLS_LD_BASE)
12724          (const:SI (unspec:SI
12725                     [(match_operand:SI 3 "tls_symbolic_operand" "")]
12726                     UNSPEC_DTPOFF))))
12727    (clobber (match_scratch:SI 4 "=d"))
12728    (clobber (match_scratch:SI 5 "=c"))
12729    (clobber (reg:CC FLAGS_REG))]
12730   ""
12731   "#"
12732   ""
12733   [(parallel
12734      [(set (match_dup 0)
12735            (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
12736                       UNSPEC_TLS_GD))
12737       (clobber (match_dup 4))
12738       (clobber (match_dup 5))
12739       (clobber (reg:CC FLAGS_REG))])])
12740
12741 ;; Segment register for the thread base ptr load
12742 (define_mode_attr tp_seg [(SI "gs") (DI "fs")])
12743
12744 ;; Load and add the thread base pointer from %<tp_seg>:0.
12745 (define_insn "*load_tp_x32"
12746   [(set (match_operand:SI 0 "register_operand" "=r")
12747         (unspec:SI [(const_int 0)] UNSPEC_TP))]
12748   "TARGET_X32"
12749   "mov{l}\t{%%fs:0, %0|%0, DWORD PTR fs:0}"
12750   [(set_attr "type" "imov")
12751    (set_attr "modrm" "0")
12752    (set_attr "length" "7")
12753    (set_attr "memory" "load")
12754    (set_attr "imm_disp" "false")])
12755
12756 (define_insn "*load_tp_x32_zext"
12757   [(set (match_operand:DI 0 "register_operand" "=r")
12758         (zero_extend:DI (unspec:SI [(const_int 0)] UNSPEC_TP)))]
12759   "TARGET_X32"
12760   "mov{l}\t{%%fs:0, %k0|%k0, DWORD PTR fs:0}"
12761   [(set_attr "type" "imov")
12762    (set_attr "modrm" "0")
12763    (set_attr "length" "7")
12764    (set_attr "memory" "load")
12765    (set_attr "imm_disp" "false")])
12766
12767 (define_insn "*load_tp_<mode>"
12768   [(set (match_operand:P 0 "register_operand" "=r")
12769         (unspec:P [(const_int 0)] UNSPEC_TP))]
12770   "!TARGET_X32"
12771   "mov{<imodesuffix>}\t{%%<tp_seg>:0, %0|%0, <iptrsize> PTR <tp_seg>:0}"
12772   [(set_attr "type" "imov")
12773    (set_attr "modrm" "0")
12774    (set_attr "length" "7")
12775    (set_attr "memory" "load")
12776    (set_attr "imm_disp" "false")])
12777
12778 (define_insn "*add_tp_x32"
12779   [(set (match_operand:SI 0 "register_operand" "=r")
12780         (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
12781                  (match_operand:SI 1 "register_operand" "0")))
12782    (clobber (reg:CC FLAGS_REG))]
12783   "TARGET_X32"
12784   "add{l}\t{%%fs:0, %0|%0, DWORD PTR fs:0}"
12785   [(set_attr "type" "alu")
12786    (set_attr "modrm" "0")
12787    (set_attr "length" "7")
12788    (set_attr "memory" "load")
12789    (set_attr "imm_disp" "false")])
12790
12791 (define_insn "*add_tp_x32_zext"
12792   [(set (match_operand:DI 0 "register_operand" "=r")
12793         (zero_extend:DI
12794           (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
12795                    (match_operand:SI 1 "register_operand" "0"))))
12796    (clobber (reg:CC FLAGS_REG))]
12797   "TARGET_X32"
12798   "add{l}\t{%%fs:0, %k0|%k0, DWORD PTR fs:0}"
12799   [(set_attr "type" "alu")
12800    (set_attr "modrm" "0")
12801    (set_attr "length" "7")
12802    (set_attr "memory" "load")
12803    (set_attr "imm_disp" "false")])
12804
12805 (define_insn "*add_tp_<mode>"
12806   [(set (match_operand:P 0 "register_operand" "=r")
12807         (plus:P (unspec:P [(const_int 0)] UNSPEC_TP)
12808                 (match_operand:P 1 "register_operand" "0")))
12809    (clobber (reg:CC FLAGS_REG))]
12810   "!TARGET_X32"
12811   "add{<imodesuffix>}\t{%%<tp_seg>:0, %0|%0, <iptrsize> PTR <tp_seg>:0}"
12812   [(set_attr "type" "alu")
12813    (set_attr "modrm" "0")
12814    (set_attr "length" "7")
12815    (set_attr "memory" "load")
12816    (set_attr "imm_disp" "false")])
12817
12818 ;; The Sun linker took the AMD64 TLS spec literally and can only handle
12819 ;; %rax as destination of the initial executable code sequence.
12820 (define_insn "tls_initial_exec_64_sun"
12821   [(set (match_operand:DI 0 "register_operand" "=a")
12822         (unspec:DI
12823          [(match_operand:DI 1 "tls_symbolic_operand" "")]
12824          UNSPEC_TLS_IE_SUN))
12825    (clobber (reg:CC FLAGS_REG))]
12826   "TARGET_64BIT && TARGET_SUN_TLS"
12827 {
12828   output_asm_insn
12829     ("mov{q}\t{%%fs:0, %0|%0, QWORD PTR fs:0}", operands);
12830   return "add{q}\t{%a1@gottpoff(%%rip), %0|%0, %a1@gottpoff[rip]}";
12831 }
12832   [(set_attr "type" "multi")])
12833
12834 ;; GNU2 TLS patterns can be split.
12835
12836 (define_expand "tls_dynamic_gnu2_32"
12837   [(set (match_dup 3)
12838         (plus:SI (match_operand:SI 2 "register_operand" "")
12839                  (const:SI
12840                   (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")]
12841                              UNSPEC_TLSDESC))))
12842    (parallel
12843     [(set (match_operand:SI 0 "register_operand" "")
12844           (unspec:SI [(match_dup 1) (match_dup 3)
12845                       (match_dup 2) (reg:SI SP_REG)]
12846                       UNSPEC_TLSDESC))
12847      (clobber (reg:CC FLAGS_REG))])]
12848   "!TARGET_64BIT && TARGET_GNU2_TLS"
12849 {
12850   operands[3] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12851   ix86_tls_descriptor_calls_expanded_in_cfun = true;
12852 })
12853
12854 (define_insn "*tls_dynamic_gnu2_lea_32"
12855   [(set (match_operand:SI 0 "register_operand" "=r")
12856         (plus:SI (match_operand:SI 1 "register_operand" "b")
12857                  (const:SI
12858                   (unspec:SI [(match_operand:SI 2 "tls_symbolic_operand" "")]
12859                               UNSPEC_TLSDESC))))]
12860   "!TARGET_64BIT && TARGET_GNU2_TLS"
12861   "lea{l}\t{%a2@TLSDESC(%1), %0|%0, %a2@TLSDESC[%1]}"
12862   [(set_attr "type" "lea")
12863    (set_attr "mode" "SI")
12864    (set_attr "length" "6")
12865    (set_attr "length_address" "4")])
12866
12867 (define_insn "*tls_dynamic_gnu2_call_32"
12868   [(set (match_operand:SI 0 "register_operand" "=a")
12869         (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")
12870                     (match_operand:SI 2 "register_operand" "0")
12871                     ;; we have to make sure %ebx still points to the GOT
12872                     (match_operand:SI 3 "register_operand" "b")
12873                     (reg:SI SP_REG)]
12874                    UNSPEC_TLSDESC))
12875    (clobber (reg:CC FLAGS_REG))]
12876   "!TARGET_64BIT && TARGET_GNU2_TLS"
12877   "call\t{*%a1@TLSCALL(%2)|[DWORD PTR [%2+%a1@TLSCALL]]}"
12878   [(set_attr "type" "call")
12879    (set_attr "length" "2")
12880    (set_attr "length_address" "0")])
12881
12882 (define_insn_and_split "*tls_dynamic_gnu2_combine_32"
12883   [(set (match_operand:SI 0 "register_operand" "=&a")
12884         (plus:SI
12885          (unspec:SI [(match_operand:SI 3 "tls_modbase_operand" "")
12886                      (match_operand:SI 4 "" "")
12887                      (match_operand:SI 2 "register_operand" "b")
12888                      (reg:SI SP_REG)]
12889                     UNSPEC_TLSDESC)
12890          (const:SI (unspec:SI
12891                     [(match_operand:SI 1 "tls_symbolic_operand" "")]
12892                     UNSPEC_DTPOFF))))
12893    (clobber (reg:CC FLAGS_REG))]
12894   "!TARGET_64BIT && TARGET_GNU2_TLS"
12895   "#"
12896   ""
12897   [(set (match_dup 0) (match_dup 5))]
12898 {
12899   operands[5] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12900   emit_insn (gen_tls_dynamic_gnu2_32 (operands[5], operands[1], operands[2]));
12901 })
12902
12903 (define_expand "tls_dynamic_gnu2_64"
12904   [(set (match_dup 2)
12905         (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12906                    UNSPEC_TLSDESC))
12907    (parallel
12908     [(set (match_operand:DI 0 "register_operand" "")
12909           (unspec:DI [(match_dup 1) (match_dup 2) (reg:DI SP_REG)]
12910                      UNSPEC_TLSDESC))
12911      (clobber (reg:CC FLAGS_REG))])]
12912   "TARGET_64BIT && TARGET_GNU2_TLS"
12913 {
12914   operands[2] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12915   ix86_tls_descriptor_calls_expanded_in_cfun = true;
12916 })
12917
12918 (define_insn "*tls_dynamic_gnu2_lea_64"
12919   [(set (match_operand:DI 0 "register_operand" "=r")
12920         (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")]
12921                    UNSPEC_TLSDESC))]
12922   "TARGET_64BIT && TARGET_GNU2_TLS"
12923   "lea{q}\t{%a1@TLSDESC(%%rip), %0|%0, %a1@TLSDESC[rip]}"
12924   [(set_attr "type" "lea")
12925    (set_attr "mode" "DI")
12926    (set_attr "length" "7")
12927    (set_attr "length_address" "4")])
12928
12929 (define_insn "*tls_dynamic_gnu2_call_64"
12930   [(set (match_operand:DI 0 "register_operand" "=a")
12931         (unspec:DI [(match_operand 1 "tls_symbolic_operand" "")
12932                     (match_operand:DI 2 "register_operand" "0")
12933                     (reg:DI SP_REG)]
12934                    UNSPEC_TLSDESC))
12935    (clobber (reg:CC FLAGS_REG))]
12936   "TARGET_64BIT && TARGET_GNU2_TLS"
12937   "call\t{*%a1@TLSCALL(%2)|[QWORD PTR [%2+%a1@TLSCALL]]}"
12938   [(set_attr "type" "call")
12939    (set_attr "length" "2")
12940    (set_attr "length_address" "0")])
12941
12942 (define_insn_and_split "*tls_dynamic_gnu2_combine_64"
12943   [(set (match_operand:DI 0 "register_operand" "=&a")
12944         (plus:DI
12945          (unspec:DI [(match_operand:DI 2 "tls_modbase_operand" "")
12946                      (match_operand:DI 3 "" "")
12947                      (reg:DI SP_REG)]
12948                     UNSPEC_TLSDESC)
12949          (const:DI (unspec:DI
12950                     [(match_operand 1 "tls_symbolic_operand" "")]
12951                     UNSPEC_DTPOFF))))
12952    (clobber (reg:CC FLAGS_REG))]
12953   "TARGET_64BIT && TARGET_GNU2_TLS"
12954   "#"
12955   ""
12956   [(set (match_dup 0) (match_dup 4))]
12957 {
12958   operands[4] = can_create_pseudo_p () ? gen_reg_rtx (Pmode) : operands[0];
12959   emit_insn (gen_tls_dynamic_gnu2_64 (operands[4], operands[1]));
12960 })
12961 \f
12962 ;; These patterns match the binary 387 instructions for addM3, subM3,
12963 ;; mulM3 and divM3.  There are three patterns for each of DFmode and
12964 ;; SFmode.  The first is the normal insn, the second the same insn but
12965 ;; with one operand a conversion, and the third the same insn but with
12966 ;; the other operand a conversion.  The conversion may be SFmode or
12967 ;; SImode if the target mode DFmode, but only SImode if the target mode
12968 ;; is SFmode.
12969
12970 ;; Gcc is slightly more smart about handling normal two address instructions
12971 ;; so use special patterns for add and mull.
12972
12973 (define_insn "*fop_<mode>_comm_mixed"
12974   [(set (match_operand:MODEF 0 "register_operand" "=f,x,x")
12975         (match_operator:MODEF 3 "binary_fp_operator"
12976           [(match_operand:MODEF 1 "nonimmediate_operand" "%0,0,x")
12977            (match_operand:MODEF 2 "nonimmediate_operand" "fm,xm,xm")]))]
12978   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
12979    && COMMUTATIVE_ARITH_P (operands[3])
12980    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
12981   "* return output_387_binary_op (insn, operands);"
12982   [(set (attr "type")
12983         (if_then_else (eq_attr "alternative" "1,2")
12984            (if_then_else (match_operand:MODEF 3 "mult_operator" "")
12985               (const_string "ssemul")
12986               (const_string "sseadd"))
12987            (if_then_else (match_operand:MODEF 3 "mult_operator" "")
12988               (const_string "fmul")
12989               (const_string "fop"))))
12990    (set_attr "isa" "*,noavx,avx")
12991    (set_attr "prefix" "orig,orig,vex")
12992    (set_attr "mode" "<MODE>")])
12993
12994 (define_insn "*fop_<mode>_comm_sse"
12995   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
12996         (match_operator:MODEF 3 "binary_fp_operator"
12997           [(match_operand:MODEF 1 "nonimmediate_operand" "%0,x")
12998            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]))]
12999   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
13000    && COMMUTATIVE_ARITH_P (operands[3])
13001    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
13002   "* return output_387_binary_op (insn, operands);"
13003   [(set (attr "type")
13004         (if_then_else (match_operand:MODEF 3 "mult_operator" "")
13005            (const_string "ssemul")
13006            (const_string "sseadd")))
13007    (set_attr "isa" "noavx,avx")
13008    (set_attr "prefix" "orig,vex")
13009    (set_attr "mode" "<MODE>")])
13010
13011 (define_insn "*fop_<mode>_comm_i387"
13012   [(set (match_operand:MODEF 0 "register_operand" "=f")
13013         (match_operator:MODEF 3 "binary_fp_operator"
13014           [(match_operand:MODEF 1 "nonimmediate_operand" "%0")
13015            (match_operand:MODEF 2 "nonimmediate_operand" "fm")]))]
13016   "TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode)
13017    && COMMUTATIVE_ARITH_P (operands[3])
13018    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
13019   "* return output_387_binary_op (insn, operands);"
13020   [(set (attr "type")
13021         (if_then_else (match_operand:MODEF 3 "mult_operator" "")
13022            (const_string "fmul")
13023            (const_string "fop")))
13024    (set_attr "mode" "<MODE>")])
13025
13026 (define_insn "*fop_<mode>_1_mixed"
13027   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x")
13028         (match_operator:MODEF 3 "binary_fp_operator"
13029           [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm,0,x")
13030            (match_operand:MODEF 2 "nonimmediate_operand" "fm,0,xm,xm")]))]
13031   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
13032    && !COMMUTATIVE_ARITH_P (operands[3])
13033    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
13034   "* return output_387_binary_op (insn, operands);"
13035   [(set (attr "type")
13036         (cond [(and (eq_attr "alternative" "2,3")
13037                     (match_operand:MODEF 3 "mult_operator" ""))
13038                  (const_string "ssemul")
13039                (and (eq_attr "alternative" "2,3")
13040                     (match_operand:MODEF 3 "div_operator" ""))
13041                  (const_string "ssediv")
13042                (eq_attr "alternative" "2,3")
13043                  (const_string "sseadd")
13044                (match_operand:MODEF 3 "mult_operator" "")
13045                  (const_string "fmul")
13046                (match_operand:MODEF 3 "div_operator" "")
13047                  (const_string "fdiv")
13048               ]
13049               (const_string "fop")))
13050    (set_attr "isa" "*,*,noavx,avx")
13051    (set_attr "prefix" "orig,orig,orig,vex")
13052    (set_attr "mode" "<MODE>")])
13053
13054 (define_insn "*rcpsf2_sse"
13055   [(set (match_operand:SF 0 "register_operand" "=x")
13056         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
13057                    UNSPEC_RCP))]
13058   "TARGET_SSE_MATH"
13059   "%vrcpss\t{%1, %d0|%d0, %1}"
13060   [(set_attr "type" "sse")
13061    (set_attr "atom_sse_attr" "rcp")
13062    (set_attr "prefix" "maybe_vex")
13063    (set_attr "mode" "SF")])
13064
13065 (define_insn "*fop_<mode>_1_sse"
13066   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
13067         (match_operator:MODEF 3 "binary_fp_operator"
13068           [(match_operand:MODEF 1 "register_operand" "0,x")
13069            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]))]
13070   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
13071    && !COMMUTATIVE_ARITH_P (operands[3])"
13072   "* return output_387_binary_op (insn, operands);"
13073   [(set (attr "type")
13074         (cond [(match_operand:MODEF 3 "mult_operator" "")
13075                  (const_string "ssemul")
13076                (match_operand:MODEF 3 "div_operator" "")
13077                  (const_string "ssediv")
13078               ]
13079               (const_string "sseadd")))
13080    (set_attr "isa" "noavx,avx")
13081    (set_attr "prefix" "orig,vex")
13082    (set_attr "mode" "<MODE>")])
13083
13084 ;; This pattern is not fully shadowed by the pattern above.
13085 (define_insn "*fop_<mode>_1_i387"
13086   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
13087         (match_operator:MODEF 3 "binary_fp_operator"
13088           [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm")
13089            (match_operand:MODEF 2 "nonimmediate_operand" "fm,0")]))]
13090   "TARGET_80387 && X87_ENABLE_ARITH (<MODE>mode)
13091    && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13092    && !COMMUTATIVE_ARITH_P (operands[3])
13093    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
13094   "* return output_387_binary_op (insn, operands);"
13095   [(set (attr "type")
13096         (cond [(match_operand:MODEF 3 "mult_operator" "")
13097                  (const_string "fmul")
13098                (match_operand:MODEF 3 "div_operator" "")
13099                  (const_string "fdiv")
13100               ]
13101               (const_string "fop")))
13102    (set_attr "mode" "<MODE>")])
13103
13104 ;; ??? Add SSE splitters for these!
13105 (define_insn "*fop_<MODEF:mode>_2_i387"
13106   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
13107         (match_operator:MODEF 3 "binary_fp_operator"
13108           [(float:MODEF
13109              (match_operand:SWI24 1 "nonimmediate_operand" "m,?r"))
13110            (match_operand:MODEF 2 "register_operand" "0,0")]))]
13111   "TARGET_80387 && X87_ENABLE_FLOAT (<MODEF:MODE>mode, <SWI24:MODE>mode)
13112    && !(SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH)
13113    && (TARGET_USE_<SWI24:MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13114   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13115   [(set (attr "type")
13116         (cond [(match_operand:MODEF 3 "mult_operator" "")
13117                  (const_string "fmul")
13118                (match_operand:MODEF 3 "div_operator" "")
13119                  (const_string "fdiv")
13120               ]
13121               (const_string "fop")))
13122    (set_attr "fp_int_src" "true")
13123    (set_attr "mode" "<SWI24:MODE>")])
13124
13125 (define_insn "*fop_<MODEF:mode>_3_i387"
13126   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
13127         (match_operator:MODEF 3 "binary_fp_operator"
13128           [(match_operand:MODEF 1 "register_operand" "0,0")
13129            (float:MODEF
13130              (match_operand:SWI24 2 "nonimmediate_operand" "m,?r"))]))]
13131   "TARGET_80387 && X87_ENABLE_FLOAT (<MODEF:MODE>mode, <SWI24:MODE>mode)
13132    && !(SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH)
13133    && (TARGET_USE_<SWI24:MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13134   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13135   [(set (attr "type")
13136         (cond [(match_operand:MODEF 3 "mult_operator" "")
13137                  (const_string "fmul")
13138                (match_operand:MODEF 3 "div_operator" "")
13139                  (const_string "fdiv")
13140               ]
13141               (const_string "fop")))
13142    (set_attr "fp_int_src" "true")
13143    (set_attr "mode" "<MODE>")])
13144
13145 (define_insn "*fop_df_4_i387"
13146   [(set (match_operand:DF 0 "register_operand" "=f,f")
13147         (match_operator:DF 3 "binary_fp_operator"
13148            [(float_extend:DF
13149              (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
13150             (match_operand:DF 2 "register_operand" "0,f")]))]
13151   "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
13152    && !(TARGET_SSE2 && TARGET_SSE_MATH)
13153    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
13154   "* return output_387_binary_op (insn, operands);"
13155   [(set (attr "type")
13156         (cond [(match_operand:DF 3 "mult_operator" "")
13157                  (const_string "fmul")
13158                (match_operand:DF 3 "div_operator" "")
13159                  (const_string "fdiv")
13160               ]
13161               (const_string "fop")))
13162    (set_attr "mode" "SF")])
13163
13164 (define_insn "*fop_df_5_i387"
13165   [(set (match_operand:DF 0 "register_operand" "=f,f")
13166         (match_operator:DF 3 "binary_fp_operator"
13167           [(match_operand:DF 1 "register_operand" "0,f")
13168            (float_extend:DF
13169             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
13170   "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
13171    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
13172   "* return output_387_binary_op (insn, operands);"
13173   [(set (attr "type")
13174         (cond [(match_operand:DF 3 "mult_operator" "")
13175                  (const_string "fmul")
13176                (match_operand:DF 3 "div_operator" "")
13177                  (const_string "fdiv")
13178               ]
13179               (const_string "fop")))
13180    (set_attr "mode" "SF")])
13181
13182 (define_insn "*fop_df_6_i387"
13183   [(set (match_operand:DF 0 "register_operand" "=f,f")
13184         (match_operator:DF 3 "binary_fp_operator"
13185           [(float_extend:DF
13186             (match_operand:SF 1 "register_operand" "0,f"))
13187            (float_extend:DF
13188             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
13189   "TARGET_80387 && X87_ENABLE_ARITH (DFmode)
13190    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
13191   "* return output_387_binary_op (insn, operands);"
13192   [(set (attr "type")
13193         (cond [(match_operand:DF 3 "mult_operator" "")
13194                  (const_string "fmul")
13195                (match_operand:DF 3 "div_operator" "")
13196                  (const_string "fdiv")
13197               ]
13198               (const_string "fop")))
13199    (set_attr "mode" "SF")])
13200
13201 (define_insn "*fop_xf_comm_i387"
13202   [(set (match_operand:XF 0 "register_operand" "=f")
13203         (match_operator:XF 3 "binary_fp_operator"
13204                         [(match_operand:XF 1 "register_operand" "%0")
13205                          (match_operand:XF 2 "register_operand" "f")]))]
13206   "TARGET_80387
13207    && COMMUTATIVE_ARITH_P (operands[3])"
13208   "* return output_387_binary_op (insn, operands);"
13209   [(set (attr "type")
13210         (if_then_else (match_operand:XF 3 "mult_operator" "")
13211            (const_string "fmul")
13212            (const_string "fop")))
13213    (set_attr "mode" "XF")])
13214
13215 (define_insn "*fop_xf_1_i387"
13216   [(set (match_operand:XF 0 "register_operand" "=f,f")
13217         (match_operator:XF 3 "binary_fp_operator"
13218                         [(match_operand:XF 1 "register_operand" "0,f")
13219                          (match_operand:XF 2 "register_operand" "f,0")]))]
13220   "TARGET_80387
13221    && !COMMUTATIVE_ARITH_P (operands[3])"
13222   "* return output_387_binary_op (insn, operands);"
13223   [(set (attr "type")
13224         (cond [(match_operand:XF 3 "mult_operator" "")
13225                  (const_string "fmul")
13226                (match_operand:XF 3 "div_operator" "")
13227                  (const_string "fdiv")
13228               ]
13229               (const_string "fop")))
13230    (set_attr "mode" "XF")])
13231
13232 (define_insn "*fop_xf_2_i387"
13233   [(set (match_operand:XF 0 "register_operand" "=f,f")
13234         (match_operator:XF 3 "binary_fp_operator"
13235           [(float:XF
13236              (match_operand:SWI24 1 "nonimmediate_operand" "m,?r"))
13237            (match_operand:XF 2 "register_operand" "0,0")]))]
13238   "TARGET_80387 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13239   "* return which_alternative ? \"#\" : 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 "fp_int_src" "true")
13248    (set_attr "mode" "<MODE>")])
13249
13250 (define_insn "*fop_xf_3_i387"
13251   [(set (match_operand:XF 0 "register_operand" "=f,f")
13252         (match_operator:XF 3 "binary_fp_operator"
13253           [(match_operand:XF 1 "register_operand" "0,0")
13254            (float:XF
13255              (match_operand:SWI24 2 "nonimmediate_operand" "m,?r"))]))]
13256   "TARGET_80387 && (TARGET_USE_<MODE>MODE_FIOP || optimize_function_for_size_p (cfun))"
13257   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
13258   [(set (attr "type")
13259         (cond [(match_operand:XF 3 "mult_operator" "")
13260                  (const_string "fmul")
13261                (match_operand:XF 3 "div_operator" "")
13262                  (const_string "fdiv")
13263               ]
13264               (const_string "fop")))
13265    (set_attr "fp_int_src" "true")
13266    (set_attr "mode" "<MODE>")])
13267
13268 (define_insn "*fop_xf_4_i387"
13269   [(set (match_operand:XF 0 "register_operand" "=f,f")
13270         (match_operator:XF 3 "binary_fp_operator"
13271            [(float_extend:XF
13272               (match_operand:MODEF 1 "nonimmediate_operand" "fm,0"))
13273             (match_operand:XF 2 "register_operand" "0,f")]))]
13274   "TARGET_80387"
13275   "* return output_387_binary_op (insn, operands);"
13276   [(set (attr "type")
13277         (cond [(match_operand:XF 3 "mult_operator" "")
13278                  (const_string "fmul")
13279                (match_operand:XF 3 "div_operator" "")
13280                  (const_string "fdiv")
13281               ]
13282               (const_string "fop")))
13283    (set_attr "mode" "<MODE>")])
13284
13285 (define_insn "*fop_xf_5_i387"
13286   [(set (match_operand:XF 0 "register_operand" "=f,f")
13287         (match_operator:XF 3 "binary_fp_operator"
13288           [(match_operand:XF 1 "register_operand" "0,f")
13289            (float_extend:XF
13290              (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
13291   "TARGET_80387"
13292   "* return output_387_binary_op (insn, operands);"
13293   [(set (attr "type")
13294         (cond [(match_operand:XF 3 "mult_operator" "")
13295                  (const_string "fmul")
13296                (match_operand:XF 3 "div_operator" "")
13297                  (const_string "fdiv")
13298               ]
13299               (const_string "fop")))
13300    (set_attr "mode" "<MODE>")])
13301
13302 (define_insn "*fop_xf_6_i387"
13303   [(set (match_operand:XF 0 "register_operand" "=f,f")
13304         (match_operator:XF 3 "binary_fp_operator"
13305           [(float_extend:XF
13306              (match_operand:MODEF 1 "register_operand" "0,f"))
13307            (float_extend:XF
13308              (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
13309   "TARGET_80387"
13310   "* return output_387_binary_op (insn, operands);"
13311   [(set (attr "type")
13312         (cond [(match_operand:XF 3 "mult_operator" "")
13313                  (const_string "fmul")
13314                (match_operand:XF 3 "div_operator" "")
13315                  (const_string "fdiv")
13316               ]
13317               (const_string "fop")))
13318    (set_attr "mode" "<MODE>")])
13319
13320 (define_split
13321   [(set (match_operand 0 "register_operand" "")
13322         (match_operator 3 "binary_fp_operator"
13323            [(float (match_operand:SWI24 1 "register_operand" ""))
13324             (match_operand 2 "register_operand" "")]))]
13325   "reload_completed
13326    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))
13327    && X87_ENABLE_FLOAT (GET_MODE (operands[0]), GET_MODE (operands[1]))"
13328   [(const_int 0)]
13329 {
13330   operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
13331   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
13332   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
13333                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
13334                                           GET_MODE (operands[3]),
13335                                           operands[4],
13336                                           operands[2])));
13337   ix86_free_from_memory (GET_MODE (operands[1]));
13338   DONE;
13339 })
13340
13341 (define_split
13342   [(set (match_operand 0 "register_operand" "")
13343         (match_operator 3 "binary_fp_operator"
13344            [(match_operand 1 "register_operand" "")
13345             (float (match_operand:SWI24 2 "register_operand" ""))]))]
13346   "reload_completed
13347    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))
13348    && X87_ENABLE_FLOAT (GET_MODE (operands[0]), GET_MODE (operands[2]))"
13349   [(const_int 0)]
13350 {
13351   operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
13352   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
13353   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
13354                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
13355                                           GET_MODE (operands[3]),
13356                                           operands[1],
13357                                           operands[4])));
13358   ix86_free_from_memory (GET_MODE (operands[2]));
13359   DONE;
13360 })
13361 \f
13362 ;; FPU special functions.
13363
13364 ;; This pattern implements a no-op XFmode truncation for
13365 ;; all fancy i386 XFmode math functions.
13366
13367 (define_insn "truncxf<mode>2_i387_noop_unspec"
13368   [(set (match_operand:MODEF 0 "register_operand" "=f")
13369         (unspec:MODEF [(match_operand:XF 1 "register_operand" "f")]
13370         UNSPEC_TRUNC_NOOP))]
13371   "TARGET_USE_FANCY_MATH_387"
13372   "* return output_387_reg_move (insn, operands);"
13373   [(set_attr "type" "fmov")
13374    (set_attr "mode" "<MODE>")])
13375
13376 (define_insn "sqrtxf2"
13377   [(set (match_operand:XF 0 "register_operand" "=f")
13378         (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
13379   "TARGET_USE_FANCY_MATH_387"
13380   "fsqrt"
13381   [(set_attr "type" "fpspc")
13382    (set_attr "mode" "XF")
13383    (set_attr "athlon_decode" "direct")
13384    (set_attr "amdfam10_decode" "direct")
13385    (set_attr "bdver1_decode" "direct")])
13386
13387 (define_insn "sqrt_extend<mode>xf2_i387"
13388   [(set (match_operand:XF 0 "register_operand" "=f")
13389         (sqrt:XF
13390           (float_extend:XF
13391             (match_operand:MODEF 1 "register_operand" "0"))))]
13392   "TARGET_USE_FANCY_MATH_387"
13393   "fsqrt"
13394   [(set_attr "type" "fpspc")
13395    (set_attr "mode" "XF")
13396    (set_attr "athlon_decode" "direct")
13397    (set_attr "amdfam10_decode" "direct")
13398    (set_attr "bdver1_decode" "direct")])
13399
13400 (define_insn "*rsqrtsf2_sse"
13401   [(set (match_operand:SF 0 "register_operand" "=x")
13402         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
13403                    UNSPEC_RSQRT))]
13404   "TARGET_SSE_MATH"
13405   "%vrsqrtss\t{%1, %d0|%d0, %1}"
13406   [(set_attr "type" "sse")
13407    (set_attr "atom_sse_attr" "rcp")
13408    (set_attr "prefix" "maybe_vex")
13409    (set_attr "mode" "SF")])
13410
13411 (define_expand "rsqrtsf2"
13412   [(set (match_operand:SF 0 "register_operand" "")
13413         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "")]
13414                    UNSPEC_RSQRT))]
13415   "TARGET_SSE_MATH"
13416 {
13417   ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 1);
13418   DONE;
13419 })
13420
13421 (define_insn "*sqrt<mode>2_sse"
13422   [(set (match_operand:MODEF 0 "register_operand" "=x")
13423         (sqrt:MODEF
13424           (match_operand:MODEF 1 "nonimmediate_operand" "xm")))]
13425   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
13426   "%vsqrt<ssemodesuffix>\t{%1, %d0|%d0, %1}"
13427   [(set_attr "type" "sse")
13428    (set_attr "atom_sse_attr" "sqrt")
13429    (set_attr "prefix" "maybe_vex")
13430    (set_attr "mode" "<MODE>")
13431    (set_attr "athlon_decode" "*")
13432    (set_attr "amdfam10_decode" "*")
13433    (set_attr "bdver1_decode" "*")])
13434
13435 (define_expand "sqrt<mode>2"
13436   [(set (match_operand:MODEF 0 "register_operand" "")
13437         (sqrt:MODEF
13438           (match_operand:MODEF 1 "nonimmediate_operand" "")))]
13439   "(TARGET_USE_FANCY_MATH_387 && X87_ENABLE_ARITH (<MODE>mode))
13440    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
13441 {
13442   if (<MODE>mode == SFmode
13443       && TARGET_SSE_MATH
13444       && TARGET_RECIP_SQRT
13445       && !optimize_function_for_size_p (cfun)
13446       && flag_finite_math_only && !flag_trapping_math
13447       && flag_unsafe_math_optimizations)
13448     {
13449       ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 0);
13450       DONE;
13451     }
13452
13453   if (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
13454     {
13455       rtx op0 = gen_reg_rtx (XFmode);
13456       rtx op1 = force_reg (<MODE>mode, operands[1]);
13457
13458       emit_insn (gen_sqrt_extend<mode>xf2_i387 (op0, op1));
13459       emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op0));
13460       DONE;
13461    }
13462 })
13463
13464 (define_insn "fpremxf4_i387"
13465   [(set (match_operand:XF 0 "register_operand" "=f")
13466         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
13467                     (match_operand:XF 3 "register_operand" "1")]
13468                    UNSPEC_FPREM_F))
13469    (set (match_operand:XF 1 "register_operand" "=u")
13470         (unspec:XF [(match_dup 2) (match_dup 3)]
13471                    UNSPEC_FPREM_U))
13472    (set (reg:CCFP FPSR_REG)
13473         (unspec:CCFP [(match_dup 2) (match_dup 3)]
13474                      UNSPEC_C2_FLAG))]
13475   "TARGET_USE_FANCY_MATH_387"
13476   "fprem"
13477   [(set_attr "type" "fpspc")
13478    (set_attr "mode" "XF")])
13479
13480 (define_expand "fmodxf3"
13481   [(use (match_operand:XF 0 "register_operand" ""))
13482    (use (match_operand:XF 1 "general_operand" ""))
13483    (use (match_operand:XF 2 "general_operand" ""))]
13484   "TARGET_USE_FANCY_MATH_387"
13485 {
13486   rtx label = gen_label_rtx ();
13487
13488   rtx op1 = gen_reg_rtx (XFmode);
13489   rtx op2 = gen_reg_rtx (XFmode);
13490
13491   emit_move_insn (op2, operands[2]);
13492   emit_move_insn (op1, operands[1]);
13493
13494   emit_label (label);
13495   emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
13496   ix86_emit_fp_unordered_jump (label);
13497   LABEL_NUSES (label) = 1;
13498
13499   emit_move_insn (operands[0], op1);
13500   DONE;
13501 })
13502
13503 (define_expand "fmod<mode>3"
13504   [(use (match_operand:MODEF 0 "register_operand" ""))
13505    (use (match_operand:MODEF 1 "general_operand" ""))
13506    (use (match_operand:MODEF 2 "general_operand" ""))]
13507   "TARGET_USE_FANCY_MATH_387"
13508 {
13509   rtx (*gen_truncxf) (rtx, rtx);
13510
13511   rtx label = gen_label_rtx ();
13512
13513   rtx op1 = gen_reg_rtx (XFmode);
13514   rtx op2 = gen_reg_rtx (XFmode);
13515
13516   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
13517   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13518
13519   emit_label (label);
13520   emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
13521   ix86_emit_fp_unordered_jump (label);
13522   LABEL_NUSES (label) = 1;
13523
13524   /* Truncate the result properly for strict SSE math.  */
13525   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
13526       && !TARGET_MIX_SSE_I387)
13527     gen_truncxf = gen_truncxf<mode>2;
13528   else
13529     gen_truncxf = gen_truncxf<mode>2_i387_noop_unspec;
13530
13531   emit_insn (gen_truncxf (operands[0], op1));
13532   DONE;
13533 })
13534
13535 (define_insn "fprem1xf4_i387"
13536   [(set (match_operand:XF 0 "register_operand" "=f")
13537         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
13538                     (match_operand:XF 3 "register_operand" "1")]
13539                    UNSPEC_FPREM1_F))
13540    (set (match_operand:XF 1 "register_operand" "=u")
13541         (unspec:XF [(match_dup 2) (match_dup 3)]
13542                    UNSPEC_FPREM1_U))
13543    (set (reg:CCFP FPSR_REG)
13544         (unspec:CCFP [(match_dup 2) (match_dup 3)]
13545                      UNSPEC_C2_FLAG))]
13546   "TARGET_USE_FANCY_MATH_387"
13547   "fprem1"
13548   [(set_attr "type" "fpspc")
13549    (set_attr "mode" "XF")])
13550
13551 (define_expand "remainderxf3"
13552   [(use (match_operand:XF 0 "register_operand" ""))
13553    (use (match_operand:XF 1 "general_operand" ""))
13554    (use (match_operand:XF 2 "general_operand" ""))]
13555   "TARGET_USE_FANCY_MATH_387"
13556 {
13557   rtx label = gen_label_rtx ();
13558
13559   rtx op1 = gen_reg_rtx (XFmode);
13560   rtx op2 = gen_reg_rtx (XFmode);
13561
13562   emit_move_insn (op2, operands[2]);
13563   emit_move_insn (op1, operands[1]);
13564
13565   emit_label (label);
13566   emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
13567   ix86_emit_fp_unordered_jump (label);
13568   LABEL_NUSES (label) = 1;
13569
13570   emit_move_insn (operands[0], op1);
13571   DONE;
13572 })
13573
13574 (define_expand "remainder<mode>3"
13575   [(use (match_operand:MODEF 0 "register_operand" ""))
13576    (use (match_operand:MODEF 1 "general_operand" ""))
13577    (use (match_operand:MODEF 2 "general_operand" ""))]
13578   "TARGET_USE_FANCY_MATH_387"
13579 {
13580   rtx (*gen_truncxf) (rtx, rtx);
13581
13582   rtx label = gen_label_rtx ();
13583
13584   rtx op1 = gen_reg_rtx (XFmode);
13585   rtx op2 = gen_reg_rtx (XFmode);
13586
13587   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
13588   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13589
13590   emit_label (label);
13591
13592   emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
13593   ix86_emit_fp_unordered_jump (label);
13594   LABEL_NUSES (label) = 1;
13595
13596   /* Truncate the result properly for strict SSE math.  */
13597   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
13598       && !TARGET_MIX_SSE_I387)
13599     gen_truncxf = gen_truncxf<mode>2;
13600   else
13601     gen_truncxf = gen_truncxf<mode>2_i387_noop_unspec;
13602
13603   emit_insn (gen_truncxf (operands[0], op1));
13604   DONE;
13605 })
13606
13607 (define_insn "*sinxf2_i387"
13608   [(set (match_operand:XF 0 "register_operand" "=f")
13609         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
13610   "TARGET_USE_FANCY_MATH_387
13611    && flag_unsafe_math_optimizations"
13612   "fsin"
13613   [(set_attr "type" "fpspc")
13614    (set_attr "mode" "XF")])
13615
13616 (define_insn "*sin_extend<mode>xf2_i387"
13617   [(set (match_operand:XF 0 "register_operand" "=f")
13618         (unspec:XF [(float_extend:XF
13619                       (match_operand:MODEF 1 "register_operand" "0"))]
13620                    UNSPEC_SIN))]
13621   "TARGET_USE_FANCY_MATH_387
13622    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13623        || TARGET_MIX_SSE_I387)
13624    && flag_unsafe_math_optimizations"
13625   "fsin"
13626   [(set_attr "type" "fpspc")
13627    (set_attr "mode" "XF")])
13628
13629 (define_insn "*cosxf2_i387"
13630   [(set (match_operand:XF 0 "register_operand" "=f")
13631         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
13632   "TARGET_USE_FANCY_MATH_387
13633    && flag_unsafe_math_optimizations"
13634   "fcos"
13635   [(set_attr "type" "fpspc")
13636    (set_attr "mode" "XF")])
13637
13638 (define_insn "*cos_extend<mode>xf2_i387"
13639   [(set (match_operand:XF 0 "register_operand" "=f")
13640         (unspec:XF [(float_extend:XF
13641                       (match_operand:MODEF 1 "register_operand" "0"))]
13642                    UNSPEC_COS))]
13643   "TARGET_USE_FANCY_MATH_387
13644    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13645        || TARGET_MIX_SSE_I387)
13646    && flag_unsafe_math_optimizations"
13647   "fcos"
13648   [(set_attr "type" "fpspc")
13649    (set_attr "mode" "XF")])
13650
13651 ;; When sincos pattern is defined, sin and cos builtin functions will be
13652 ;; expanded to sincos pattern with one of its outputs left unused.
13653 ;; CSE pass will figure out if two sincos patterns can be combined,
13654 ;; otherwise sincos pattern will be split back to sin or cos pattern,
13655 ;; depending on the unused output.
13656
13657 (define_insn "sincosxf3"
13658   [(set (match_operand:XF 0 "register_operand" "=f")
13659         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
13660                    UNSPEC_SINCOS_COS))
13661    (set (match_operand:XF 1 "register_operand" "=u")
13662         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
13663   "TARGET_USE_FANCY_MATH_387
13664    && flag_unsafe_math_optimizations"
13665   "fsincos"
13666   [(set_attr "type" "fpspc")
13667    (set_attr "mode" "XF")])
13668
13669 (define_split
13670   [(set (match_operand:XF 0 "register_operand" "")
13671         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
13672                    UNSPEC_SINCOS_COS))
13673    (set (match_operand:XF 1 "register_operand" "")
13674         (unspec: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) (unspec:XF [(match_dup 2)] UNSPEC_SIN))])
13678
13679 (define_split
13680   [(set (match_operand:XF 0 "register_operand" "")
13681         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
13682                    UNSPEC_SINCOS_COS))
13683    (set (match_operand:XF 1 "register_operand" "")
13684         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
13685   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
13686    && can_create_pseudo_p ()"
13687   [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))])
13688
13689 (define_insn "sincos_extend<mode>xf3_i387"
13690   [(set (match_operand:XF 0 "register_operand" "=f")
13691         (unspec:XF [(float_extend:XF
13692                       (match_operand:MODEF 2 "register_operand" "0"))]
13693                    UNSPEC_SINCOS_COS))
13694    (set (match_operand:XF 1 "register_operand" "=u")
13695         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
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   "fsincos"
13701   [(set_attr "type" "fpspc")
13702    (set_attr "mode" "XF")])
13703
13704 (define_split
13705   [(set (match_operand:XF 0 "register_operand" "")
13706         (unspec:XF [(float_extend:XF
13707                       (match_operand:MODEF 2 "register_operand" ""))]
13708                    UNSPEC_SINCOS_COS))
13709    (set (match_operand:XF 1 "register_operand" "")
13710         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
13711   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
13712    && can_create_pseudo_p ()"
13713   [(set (match_dup 1)
13714         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SIN))])
13715
13716 (define_split
13717   [(set (match_operand:XF 0 "register_operand" "")
13718         (unspec:XF [(float_extend:XF
13719                       (match_operand:MODEF 2 "register_operand" ""))]
13720                    UNSPEC_SINCOS_COS))
13721    (set (match_operand:XF 1 "register_operand" "")
13722         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
13723   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
13724    && can_create_pseudo_p ()"
13725   [(set (match_dup 0)
13726         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_COS))])
13727
13728 (define_expand "sincos<mode>3"
13729   [(use (match_operand:MODEF 0 "register_operand" ""))
13730    (use (match_operand:MODEF 1 "register_operand" ""))
13731    (use (match_operand:MODEF 2 "register_operand" ""))]
13732   "TARGET_USE_FANCY_MATH_387
13733    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13734        || TARGET_MIX_SSE_I387)
13735    && flag_unsafe_math_optimizations"
13736 {
13737   rtx op0 = gen_reg_rtx (XFmode);
13738   rtx op1 = gen_reg_rtx (XFmode);
13739
13740   emit_insn (gen_sincos_extend<mode>xf3_i387 (op0, op1, operands[2]));
13741   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13742   emit_insn (gen_truncxf<mode>2_i387_noop (operands[1], op1));
13743   DONE;
13744 })
13745
13746 (define_insn "fptanxf4_i387"
13747   [(set (match_operand:XF 0 "register_operand" "=f")
13748         (match_operand:XF 3 "const_double_operand" "F"))
13749    (set (match_operand:XF 1 "register_operand" "=u")
13750         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
13751                    UNSPEC_TAN))]
13752   "TARGET_USE_FANCY_MATH_387
13753    && flag_unsafe_math_optimizations
13754    && standard_80387_constant_p (operands[3]) == 2"
13755   "fptan"
13756   [(set_attr "type" "fpspc")
13757    (set_attr "mode" "XF")])
13758
13759 (define_insn "fptan_extend<mode>xf4_i387"
13760   [(set (match_operand:MODEF 0 "register_operand" "=f")
13761         (match_operand:MODEF 3 "const_double_operand" "F"))
13762    (set (match_operand:XF 1 "register_operand" "=u")
13763         (unspec:XF [(float_extend:XF
13764                       (match_operand:MODEF 2 "register_operand" "0"))]
13765                    UNSPEC_TAN))]
13766   "TARGET_USE_FANCY_MATH_387
13767    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13768        || TARGET_MIX_SSE_I387)
13769    && flag_unsafe_math_optimizations
13770    && standard_80387_constant_p (operands[3]) == 2"
13771   "fptan"
13772   [(set_attr "type" "fpspc")
13773    (set_attr "mode" "XF")])
13774
13775 (define_expand "tanxf2"
13776   [(use (match_operand:XF 0 "register_operand" ""))
13777    (use (match_operand:XF 1 "register_operand" ""))]
13778   "TARGET_USE_FANCY_MATH_387
13779    && flag_unsafe_math_optimizations"
13780 {
13781   rtx one = gen_reg_rtx (XFmode);
13782   rtx op2 = CONST1_RTX (XFmode); /* fld1 */
13783
13784   emit_insn (gen_fptanxf4_i387 (one, operands[0], operands[1], op2));
13785   DONE;
13786 })
13787
13788 (define_expand "tan<mode>2"
13789   [(use (match_operand:MODEF 0 "register_operand" ""))
13790    (use (match_operand:MODEF 1 "register_operand" ""))]
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 {
13796   rtx op0 = gen_reg_rtx (XFmode);
13797
13798   rtx one = gen_reg_rtx (<MODE>mode);
13799   rtx op2 = CONST1_RTX (<MODE>mode); /* fld1 */
13800
13801   emit_insn (gen_fptan_extend<mode>xf4_i387 (one, op0,
13802                                              operands[1], op2));
13803   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13804   DONE;
13805 })
13806
13807 (define_insn "*fpatanxf3_i387"
13808   [(set (match_operand:XF 0 "register_operand" "=f")
13809         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
13810                     (match_operand:XF 2 "register_operand" "u")]
13811                    UNSPEC_FPATAN))
13812    (clobber (match_scratch:XF 3 "=2"))]
13813   "TARGET_USE_FANCY_MATH_387
13814    && flag_unsafe_math_optimizations"
13815   "fpatan"
13816   [(set_attr "type" "fpspc")
13817    (set_attr "mode" "XF")])
13818
13819 (define_insn "fpatan_extend<mode>xf3_i387"
13820   [(set (match_operand:XF 0 "register_operand" "=f")
13821         (unspec:XF [(float_extend:XF
13822                       (match_operand:MODEF 1 "register_operand" "0"))
13823                     (float_extend:XF
13824                       (match_operand:MODEF 2 "register_operand" "u"))]
13825                    UNSPEC_FPATAN))
13826    (clobber (match_scratch:XF 3 "=2"))]
13827   "TARGET_USE_FANCY_MATH_387
13828    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13829        || TARGET_MIX_SSE_I387)
13830    && flag_unsafe_math_optimizations"
13831   "fpatan"
13832   [(set_attr "type" "fpspc")
13833    (set_attr "mode" "XF")])
13834
13835 (define_expand "atan2xf3"
13836   [(parallel [(set (match_operand:XF 0 "register_operand" "")
13837                    (unspec:XF [(match_operand:XF 2 "register_operand" "")
13838                                (match_operand:XF 1 "register_operand" "")]
13839                               UNSPEC_FPATAN))
13840               (clobber (match_scratch:XF 3 ""))])]
13841   "TARGET_USE_FANCY_MATH_387
13842    && flag_unsafe_math_optimizations")
13843
13844 (define_expand "atan2<mode>3"
13845   [(use (match_operand:MODEF 0 "register_operand" ""))
13846    (use (match_operand:MODEF 1 "register_operand" ""))
13847    (use (match_operand:MODEF 2 "register_operand" ""))]
13848   "TARGET_USE_FANCY_MATH_387
13849    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13850        || TARGET_MIX_SSE_I387)
13851    && flag_unsafe_math_optimizations"
13852 {
13853   rtx op0 = gen_reg_rtx (XFmode);
13854
13855   emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, operands[2], operands[1]));
13856   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13857   DONE;
13858 })
13859
13860 (define_expand "atanxf2"
13861   [(parallel [(set (match_operand:XF 0 "register_operand" "")
13862                    (unspec:XF [(match_dup 2)
13863                                (match_operand:XF 1 "register_operand" "")]
13864                               UNSPEC_FPATAN))
13865               (clobber (match_scratch:XF 3 ""))])]
13866   "TARGET_USE_FANCY_MATH_387
13867    && flag_unsafe_math_optimizations"
13868 {
13869   operands[2] = gen_reg_rtx (XFmode);
13870   emit_move_insn (operands[2], CONST1_RTX (XFmode));  /* fld1 */
13871 })
13872
13873 (define_expand "atan<mode>2"
13874   [(use (match_operand:MODEF 0 "register_operand" ""))
13875    (use (match_operand:MODEF 1 "register_operand" ""))]
13876   "TARGET_USE_FANCY_MATH_387
13877    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13878        || TARGET_MIX_SSE_I387)
13879    && flag_unsafe_math_optimizations"
13880 {
13881   rtx op0 = gen_reg_rtx (XFmode);
13882
13883   rtx op2 = gen_reg_rtx (<MODE>mode);
13884   emit_move_insn (op2, CONST1_RTX (<MODE>mode));  /* fld1 */
13885
13886   emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, op2, operands[1]));
13887   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13888   DONE;
13889 })
13890
13891 (define_expand "asinxf2"
13892   [(set (match_dup 2)
13893         (mult:XF (match_operand:XF 1 "register_operand" "")
13894                  (match_dup 1)))
13895    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
13896    (set (match_dup 5) (sqrt:XF (match_dup 4)))
13897    (parallel [(set (match_operand:XF 0 "register_operand" "")
13898                    (unspec:XF [(match_dup 5) (match_dup 1)]
13899                               UNSPEC_FPATAN))
13900               (clobber (match_scratch:XF 6 ""))])]
13901   "TARGET_USE_FANCY_MATH_387
13902    && flag_unsafe_math_optimizations"
13903 {
13904   int i;
13905
13906   if (optimize_insn_for_size_p ())
13907     FAIL;
13908
13909   for (i = 2; i < 6; i++)
13910     operands[i] = gen_reg_rtx (XFmode);
13911
13912   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
13913 })
13914
13915 (define_expand "asin<mode>2"
13916   [(use (match_operand:MODEF 0 "register_operand" ""))
13917    (use (match_operand:MODEF 1 "general_operand" ""))]
13918  "TARGET_USE_FANCY_MATH_387
13919    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
13920        || TARGET_MIX_SSE_I387)
13921    && flag_unsafe_math_optimizations"
13922 {
13923   rtx op0 = gen_reg_rtx (XFmode);
13924   rtx op1 = gen_reg_rtx (XFmode);
13925
13926   if (optimize_insn_for_size_p ())
13927     FAIL;
13928
13929   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13930   emit_insn (gen_asinxf2 (op0, op1));
13931   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13932   DONE;
13933 })
13934
13935 (define_expand "acosxf2"
13936   [(set (match_dup 2)
13937         (mult:XF (match_operand:XF 1 "register_operand" "")
13938                  (match_dup 1)))
13939    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
13940    (set (match_dup 5) (sqrt:XF (match_dup 4)))
13941    (parallel [(set (match_operand:XF 0 "register_operand" "")
13942                    (unspec:XF [(match_dup 1) (match_dup 5)]
13943                               UNSPEC_FPATAN))
13944               (clobber (match_scratch:XF 6 ""))])]
13945   "TARGET_USE_FANCY_MATH_387
13946    && flag_unsafe_math_optimizations"
13947 {
13948   int i;
13949
13950   if (optimize_insn_for_size_p ())
13951     FAIL;
13952
13953   for (i = 2; i < 6; i++)
13954     operands[i] = gen_reg_rtx (XFmode);
13955
13956   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
13957 })
13958
13959 (define_expand "acos<mode>2"
13960   [(use (match_operand:MODEF 0 "register_operand" ""))
13961    (use (match_operand:MODEF 1 "general_operand" ""))]
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 {
13967   rtx op0 = gen_reg_rtx (XFmode);
13968   rtx op1 = gen_reg_rtx (XFmode);
13969
13970   if (optimize_insn_for_size_p ())
13971     FAIL;
13972
13973   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
13974   emit_insn (gen_acosxf2 (op0, op1));
13975   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
13976   DONE;
13977 })
13978
13979 (define_insn "fyl2xxf3_i387"
13980   [(set (match_operand:XF 0 "register_operand" "=f")
13981         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
13982                     (match_operand:XF 2 "register_operand" "u")]
13983                    UNSPEC_FYL2X))
13984    (clobber (match_scratch:XF 3 "=2"))]
13985   "TARGET_USE_FANCY_MATH_387
13986    && flag_unsafe_math_optimizations"
13987   "fyl2x"
13988   [(set_attr "type" "fpspc")
13989    (set_attr "mode" "XF")])
13990
13991 (define_insn "fyl2x_extend<mode>xf3_i387"
13992   [(set (match_operand:XF 0 "register_operand" "=f")
13993         (unspec:XF [(float_extend:XF
13994                       (match_operand:MODEF 1 "register_operand" "0"))
13995                     (match_operand:XF 2 "register_operand" "u")]
13996                    UNSPEC_FYL2X))
13997    (clobber (match_scratch:XF 3 "=2"))]
13998   "TARGET_USE_FANCY_MATH_387
13999    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14000        || TARGET_MIX_SSE_I387)
14001    && flag_unsafe_math_optimizations"
14002   "fyl2x"
14003   [(set_attr "type" "fpspc")
14004    (set_attr "mode" "XF")])
14005
14006 (define_expand "logxf2"
14007   [(parallel [(set (match_operand:XF 0 "register_operand" "")
14008                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14009                                (match_dup 2)] UNSPEC_FYL2X))
14010               (clobber (match_scratch:XF 3 ""))])]
14011   "TARGET_USE_FANCY_MATH_387
14012    && flag_unsafe_math_optimizations"
14013 {
14014   operands[2] = gen_reg_rtx (XFmode);
14015   emit_move_insn (operands[2], standard_80387_constant_rtx (4)); /* fldln2 */
14016 })
14017
14018 (define_expand "log<mode>2"
14019   [(use (match_operand:MODEF 0 "register_operand" ""))
14020    (use (match_operand:MODEF 1 "register_operand" ""))]
14021   "TARGET_USE_FANCY_MATH_387
14022    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14023        || TARGET_MIX_SSE_I387)
14024    && flag_unsafe_math_optimizations"
14025 {
14026   rtx op0 = gen_reg_rtx (XFmode);
14027
14028   rtx op2 = gen_reg_rtx (XFmode);
14029   emit_move_insn (op2, standard_80387_constant_rtx (4)); /* fldln2 */
14030
14031   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
14032   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14033   DONE;
14034 })
14035
14036 (define_expand "log10xf2"
14037   [(parallel [(set (match_operand:XF 0 "register_operand" "")
14038                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14039                                (match_dup 2)] UNSPEC_FYL2X))
14040               (clobber (match_scratch:XF 3 ""))])]
14041   "TARGET_USE_FANCY_MATH_387
14042    && flag_unsafe_math_optimizations"
14043 {
14044   operands[2] = gen_reg_rtx (XFmode);
14045   emit_move_insn (operands[2], standard_80387_constant_rtx (3)); /* fldlg2 */
14046 })
14047
14048 (define_expand "log10<mode>2"
14049   [(use (match_operand:MODEF 0 "register_operand" ""))
14050    (use (match_operand:MODEF 1 "register_operand" ""))]
14051   "TARGET_USE_FANCY_MATH_387
14052    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14053        || TARGET_MIX_SSE_I387)
14054    && flag_unsafe_math_optimizations"
14055 {
14056   rtx op0 = gen_reg_rtx (XFmode);
14057
14058   rtx op2 = gen_reg_rtx (XFmode);
14059   emit_move_insn (op2, standard_80387_constant_rtx (3)); /* fldlg2 */
14060
14061   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
14062   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14063   DONE;
14064 })
14065
14066 (define_expand "log2xf2"
14067   [(parallel [(set (match_operand:XF 0 "register_operand" "")
14068                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14069                                (match_dup 2)] UNSPEC_FYL2X))
14070               (clobber (match_scratch:XF 3 ""))])]
14071   "TARGET_USE_FANCY_MATH_387
14072    && flag_unsafe_math_optimizations"
14073 {
14074   operands[2] = gen_reg_rtx (XFmode);
14075   emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
14076 })
14077
14078 (define_expand "log2<mode>2"
14079   [(use (match_operand:MODEF 0 "register_operand" ""))
14080    (use (match_operand:MODEF 1 "register_operand" ""))]
14081   "TARGET_USE_FANCY_MATH_387
14082    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14083        || TARGET_MIX_SSE_I387)
14084    && flag_unsafe_math_optimizations"
14085 {
14086   rtx op0 = gen_reg_rtx (XFmode);
14087
14088   rtx op2 = gen_reg_rtx (XFmode);
14089   emit_move_insn (op2, CONST1_RTX (XFmode)); /* fld1 */
14090
14091   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
14092   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14093   DONE;
14094 })
14095
14096 (define_insn "fyl2xp1xf3_i387"
14097   [(set (match_operand:XF 0 "register_operand" "=f")
14098         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
14099                     (match_operand:XF 2 "register_operand" "u")]
14100                    UNSPEC_FYL2XP1))
14101    (clobber (match_scratch:XF 3 "=2"))]
14102   "TARGET_USE_FANCY_MATH_387
14103    && flag_unsafe_math_optimizations"
14104   "fyl2xp1"
14105   [(set_attr "type" "fpspc")
14106    (set_attr "mode" "XF")])
14107
14108 (define_insn "fyl2xp1_extend<mode>xf3_i387"
14109   [(set (match_operand:XF 0 "register_operand" "=f")
14110         (unspec:XF [(float_extend:XF
14111                       (match_operand:MODEF 1 "register_operand" "0"))
14112                     (match_operand:XF 2 "register_operand" "u")]
14113                    UNSPEC_FYL2XP1))
14114    (clobber (match_scratch:XF 3 "=2"))]
14115   "TARGET_USE_FANCY_MATH_387
14116    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14117        || TARGET_MIX_SSE_I387)
14118    && flag_unsafe_math_optimizations"
14119   "fyl2xp1"
14120   [(set_attr "type" "fpspc")
14121    (set_attr "mode" "XF")])
14122
14123 (define_expand "log1pxf2"
14124   [(use (match_operand:XF 0 "register_operand" ""))
14125    (use (match_operand:XF 1 "register_operand" ""))]
14126   "TARGET_USE_FANCY_MATH_387
14127    && flag_unsafe_math_optimizations"
14128 {
14129   if (optimize_insn_for_size_p ())
14130     FAIL;
14131
14132   ix86_emit_i387_log1p (operands[0], operands[1]);
14133   DONE;
14134 })
14135
14136 (define_expand "log1p<mode>2"
14137   [(use (match_operand:MODEF 0 "register_operand" ""))
14138    (use (match_operand:MODEF 1 "register_operand" ""))]
14139   "TARGET_USE_FANCY_MATH_387
14140    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14141        || TARGET_MIX_SSE_I387)
14142    && flag_unsafe_math_optimizations"
14143 {
14144   rtx op0;
14145
14146   if (optimize_insn_for_size_p ())
14147     FAIL;
14148
14149   op0 = gen_reg_rtx (XFmode);
14150
14151   operands[1] = gen_rtx_FLOAT_EXTEND (XFmode, operands[1]);
14152
14153   ix86_emit_i387_log1p (op0, operands[1]);
14154   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14155   DONE;
14156 })
14157
14158 (define_insn "fxtractxf3_i387"
14159   [(set (match_operand:XF 0 "register_operand" "=f")
14160         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
14161                    UNSPEC_XTRACT_FRACT))
14162    (set (match_operand:XF 1 "register_operand" "=u")
14163         (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]
14164   "TARGET_USE_FANCY_MATH_387
14165    && flag_unsafe_math_optimizations"
14166   "fxtract"
14167   [(set_attr "type" "fpspc")
14168    (set_attr "mode" "XF")])
14169
14170 (define_insn "fxtract_extend<mode>xf3_i387"
14171   [(set (match_operand:XF 0 "register_operand" "=f")
14172         (unspec:XF [(float_extend:XF
14173                       (match_operand:MODEF 2 "register_operand" "0"))]
14174                    UNSPEC_XTRACT_FRACT))
14175    (set (match_operand:XF 1 "register_operand" "=u")
14176         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_XTRACT_EXP))]
14177   "TARGET_USE_FANCY_MATH_387
14178    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14179        || TARGET_MIX_SSE_I387)
14180    && flag_unsafe_math_optimizations"
14181   "fxtract"
14182   [(set_attr "type" "fpspc")
14183    (set_attr "mode" "XF")])
14184
14185 (define_expand "logbxf2"
14186   [(parallel [(set (match_dup 2)
14187                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
14188                               UNSPEC_XTRACT_FRACT))
14189               (set (match_operand:XF 0 "register_operand" "")
14190                    (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
14191   "TARGET_USE_FANCY_MATH_387
14192    && flag_unsafe_math_optimizations"
14193   "operands[2] = gen_reg_rtx (XFmode);")
14194
14195 (define_expand "logb<mode>2"
14196   [(use (match_operand:MODEF 0 "register_operand" ""))
14197    (use (match_operand:MODEF 1 "register_operand" ""))]
14198   "TARGET_USE_FANCY_MATH_387
14199    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14200        || TARGET_MIX_SSE_I387)
14201    && flag_unsafe_math_optimizations"
14202 {
14203   rtx op0 = gen_reg_rtx (XFmode);
14204   rtx op1 = gen_reg_rtx (XFmode);
14205
14206   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
14207   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op1));
14208   DONE;
14209 })
14210
14211 (define_expand "ilogbxf2"
14212   [(use (match_operand:SI 0 "register_operand" ""))
14213    (use (match_operand:XF 1 "register_operand" ""))]
14214   "TARGET_USE_FANCY_MATH_387
14215    && flag_unsafe_math_optimizations"
14216 {
14217   rtx op0, op1;
14218
14219   if (optimize_insn_for_size_p ())
14220     FAIL;
14221
14222   op0 = gen_reg_rtx (XFmode);
14223   op1 = gen_reg_rtx (XFmode);
14224
14225   emit_insn (gen_fxtractxf3_i387 (op0, op1, operands[1]));
14226   emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
14227   DONE;
14228 })
14229
14230 (define_expand "ilogb<mode>2"
14231   [(use (match_operand:SI 0 "register_operand" ""))
14232    (use (match_operand:MODEF 1 "register_operand" ""))]
14233   "TARGET_USE_FANCY_MATH_387
14234    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14235        || TARGET_MIX_SSE_I387)
14236    && flag_unsafe_math_optimizations"
14237 {
14238   rtx op0, op1;
14239
14240   if (optimize_insn_for_size_p ())
14241     FAIL;
14242
14243   op0 = gen_reg_rtx (XFmode);
14244   op1 = gen_reg_rtx (XFmode);
14245
14246   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
14247   emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
14248   DONE;
14249 })
14250
14251 (define_insn "*f2xm1xf2_i387"
14252   [(set (match_operand:XF 0 "register_operand" "=f")
14253         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
14254                    UNSPEC_F2XM1))]
14255   "TARGET_USE_FANCY_MATH_387
14256    && flag_unsafe_math_optimizations"
14257   "f2xm1"
14258   [(set_attr "type" "fpspc")
14259    (set_attr "mode" "XF")])
14260
14261 (define_insn "*fscalexf4_i387"
14262   [(set (match_operand:XF 0 "register_operand" "=f")
14263         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
14264                     (match_operand:XF 3 "register_operand" "1")]
14265                    UNSPEC_FSCALE_FRACT))
14266    (set (match_operand:XF 1 "register_operand" "=u")
14267         (unspec:XF [(match_dup 2) (match_dup 3)]
14268                    UNSPEC_FSCALE_EXP))]
14269   "TARGET_USE_FANCY_MATH_387
14270    && flag_unsafe_math_optimizations"
14271   "fscale"
14272   [(set_attr "type" "fpspc")
14273    (set_attr "mode" "XF")])
14274
14275 (define_expand "expNcorexf3"
14276   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
14277                                (match_operand:XF 2 "register_operand" "")))
14278    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
14279    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
14280    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
14281    (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
14282    (parallel [(set (match_operand:XF 0 "register_operand" "")
14283                    (unspec:XF [(match_dup 8) (match_dup 4)]
14284                               UNSPEC_FSCALE_FRACT))
14285               (set (match_dup 9)
14286                    (unspec:XF [(match_dup 8) (match_dup 4)]
14287                               UNSPEC_FSCALE_EXP))])]
14288   "TARGET_USE_FANCY_MATH_387
14289    && flag_unsafe_math_optimizations"
14290 {
14291   int i;
14292
14293   if (optimize_insn_for_size_p ())
14294     FAIL;
14295
14296   for (i = 3; i < 10; i++)
14297     operands[i] = gen_reg_rtx (XFmode);
14298
14299   emit_move_insn (operands[7], CONST1_RTX (XFmode));  /* fld1 */
14300 })
14301
14302 (define_expand "expxf2"
14303   [(use (match_operand:XF 0 "register_operand" ""))
14304    (use (match_operand:XF 1 "register_operand" ""))]
14305   "TARGET_USE_FANCY_MATH_387
14306    && flag_unsafe_math_optimizations"
14307 {
14308   rtx op2;
14309
14310   if (optimize_insn_for_size_p ())
14311     FAIL;
14312
14313   op2 = gen_reg_rtx (XFmode);
14314   emit_move_insn (op2, standard_80387_constant_rtx (5)); /* fldl2e */
14315
14316   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
14317   DONE;
14318 })
14319
14320 (define_expand "exp<mode>2"
14321   [(use (match_operand:MODEF 0 "register_operand" ""))
14322    (use (match_operand:MODEF 1 "general_operand" ""))]
14323  "TARGET_USE_FANCY_MATH_387
14324    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14325        || TARGET_MIX_SSE_I387)
14326    && flag_unsafe_math_optimizations"
14327 {
14328   rtx op0, op1;
14329
14330   if (optimize_insn_for_size_p ())
14331     FAIL;
14332
14333   op0 = gen_reg_rtx (XFmode);
14334   op1 = gen_reg_rtx (XFmode);
14335
14336   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14337   emit_insn (gen_expxf2 (op0, op1));
14338   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14339   DONE;
14340 })
14341
14342 (define_expand "exp10xf2"
14343   [(use (match_operand:XF 0 "register_operand" ""))
14344    (use (match_operand:XF 1 "register_operand" ""))]
14345   "TARGET_USE_FANCY_MATH_387
14346    && flag_unsafe_math_optimizations"
14347 {
14348   rtx op2;
14349
14350   if (optimize_insn_for_size_p ())
14351     FAIL;
14352
14353   op2 = gen_reg_rtx (XFmode);
14354   emit_move_insn (op2, standard_80387_constant_rtx (6)); /* fldl2t */
14355
14356   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
14357   DONE;
14358 })
14359
14360 (define_expand "exp10<mode>2"
14361   [(use (match_operand:MODEF 0 "register_operand" ""))
14362    (use (match_operand:MODEF 1 "general_operand" ""))]
14363  "TARGET_USE_FANCY_MATH_387
14364    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14365        || TARGET_MIX_SSE_I387)
14366    && flag_unsafe_math_optimizations"
14367 {
14368   rtx op0, op1;
14369
14370   if (optimize_insn_for_size_p ())
14371     FAIL;
14372
14373   op0 = gen_reg_rtx (XFmode);
14374   op1 = gen_reg_rtx (XFmode);
14375
14376   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14377   emit_insn (gen_exp10xf2 (op0, op1));
14378   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14379   DONE;
14380 })
14381
14382 (define_expand "exp2xf2"
14383   [(use (match_operand:XF 0 "register_operand" ""))
14384    (use (match_operand:XF 1 "register_operand" ""))]
14385   "TARGET_USE_FANCY_MATH_387
14386    && flag_unsafe_math_optimizations"
14387 {
14388   rtx op2;
14389
14390   if (optimize_insn_for_size_p ())
14391     FAIL;
14392
14393   op2 = gen_reg_rtx (XFmode);
14394   emit_move_insn (op2, CONST1_RTX (XFmode));  /* fld1 */
14395
14396   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
14397   DONE;
14398 })
14399
14400 (define_expand "exp2<mode>2"
14401   [(use (match_operand:MODEF 0 "register_operand" ""))
14402    (use (match_operand:MODEF 1 "general_operand" ""))]
14403  "TARGET_USE_FANCY_MATH_387
14404    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14405        || TARGET_MIX_SSE_I387)
14406    && flag_unsafe_math_optimizations"
14407 {
14408   rtx op0, op1;
14409
14410   if (optimize_insn_for_size_p ())
14411     FAIL;
14412
14413   op0 = gen_reg_rtx (XFmode);
14414   op1 = gen_reg_rtx (XFmode);
14415
14416   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14417   emit_insn (gen_exp2xf2 (op0, op1));
14418   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14419   DONE;
14420 })
14421
14422 (define_expand "expm1xf2"
14423   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
14424                                (match_dup 2)))
14425    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
14426    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
14427    (set (match_dup 9) (float_extend:XF (match_dup 13)))
14428    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
14429    (parallel [(set (match_dup 7)
14430                    (unspec:XF [(match_dup 6) (match_dup 4)]
14431                               UNSPEC_FSCALE_FRACT))
14432               (set (match_dup 8)
14433                    (unspec:XF [(match_dup 6) (match_dup 4)]
14434                               UNSPEC_FSCALE_EXP))])
14435    (parallel [(set (match_dup 10)
14436                    (unspec:XF [(match_dup 9) (match_dup 8)]
14437                               UNSPEC_FSCALE_FRACT))
14438               (set (match_dup 11)
14439                    (unspec:XF [(match_dup 9) (match_dup 8)]
14440                               UNSPEC_FSCALE_EXP))])
14441    (set (match_dup 12) (minus:XF (match_dup 10)
14442                                  (float_extend:XF (match_dup 13))))
14443    (set (match_operand:XF 0 "register_operand" "")
14444         (plus:XF (match_dup 12) (match_dup 7)))]
14445   "TARGET_USE_FANCY_MATH_387
14446    && flag_unsafe_math_optimizations"
14447 {
14448   int i;
14449
14450   if (optimize_insn_for_size_p ())
14451     FAIL;
14452
14453   for (i = 2; i < 13; i++)
14454     operands[i] = gen_reg_rtx (XFmode);
14455
14456   operands[13]
14457     = validize_mem (force_const_mem (SFmode, CONST1_RTX (SFmode))); /* fld1 */
14458
14459   emit_move_insn (operands[2], standard_80387_constant_rtx (5)); /* fldl2e */
14460 })
14461
14462 (define_expand "expm1<mode>2"
14463   [(use (match_operand:MODEF 0 "register_operand" ""))
14464    (use (match_operand:MODEF 1 "general_operand" ""))]
14465  "TARGET_USE_FANCY_MATH_387
14466    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14467        || TARGET_MIX_SSE_I387)
14468    && flag_unsafe_math_optimizations"
14469 {
14470   rtx op0, op1;
14471
14472   if (optimize_insn_for_size_p ())
14473     FAIL;
14474
14475   op0 = gen_reg_rtx (XFmode);
14476   op1 = gen_reg_rtx (XFmode);
14477
14478   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14479   emit_insn (gen_expm1xf2 (op0, op1));
14480   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14481   DONE;
14482 })
14483
14484 (define_expand "ldexpxf3"
14485   [(set (match_dup 3)
14486         (float:XF (match_operand:SI 2 "register_operand" "")))
14487    (parallel [(set (match_operand:XF 0 " register_operand" "")
14488                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14489                                (match_dup 3)]
14490                               UNSPEC_FSCALE_FRACT))
14491               (set (match_dup 4)
14492                    (unspec:XF [(match_dup 1) (match_dup 3)]
14493                               UNSPEC_FSCALE_EXP))])]
14494   "TARGET_USE_FANCY_MATH_387
14495    && flag_unsafe_math_optimizations"
14496 {
14497   if (optimize_insn_for_size_p ())
14498     FAIL;
14499
14500   operands[3] = gen_reg_rtx (XFmode);
14501   operands[4] = gen_reg_rtx (XFmode);
14502 })
14503
14504 (define_expand "ldexp<mode>3"
14505   [(use (match_operand:MODEF 0 "register_operand" ""))
14506    (use (match_operand:MODEF 1 "general_operand" ""))
14507    (use (match_operand:SI 2 "register_operand" ""))]
14508  "TARGET_USE_FANCY_MATH_387
14509    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14510        || TARGET_MIX_SSE_I387)
14511    && flag_unsafe_math_optimizations"
14512 {
14513   rtx op0, op1;
14514
14515   if (optimize_insn_for_size_p ())
14516     FAIL;
14517
14518   op0 = gen_reg_rtx (XFmode);
14519   op1 = gen_reg_rtx (XFmode);
14520
14521   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14522   emit_insn (gen_ldexpxf3 (op0, op1, operands[2]));
14523   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14524   DONE;
14525 })
14526
14527 (define_expand "scalbxf3"
14528   [(parallel [(set (match_operand:XF 0 " register_operand" "")
14529                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
14530                                (match_operand:XF 2 "register_operand" "")]
14531                               UNSPEC_FSCALE_FRACT))
14532               (set (match_dup 3)
14533                    (unspec:XF [(match_dup 1) (match_dup 2)]
14534                               UNSPEC_FSCALE_EXP))])]
14535   "TARGET_USE_FANCY_MATH_387
14536    && flag_unsafe_math_optimizations"
14537 {
14538   if (optimize_insn_for_size_p ())
14539     FAIL;
14540
14541   operands[3] = gen_reg_rtx (XFmode);
14542 })
14543
14544 (define_expand "scalb<mode>3"
14545   [(use (match_operand:MODEF 0 "register_operand" ""))
14546    (use (match_operand:MODEF 1 "general_operand" ""))
14547    (use (match_operand:MODEF 2 "general_operand" ""))]
14548  "TARGET_USE_FANCY_MATH_387
14549    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14550        || TARGET_MIX_SSE_I387)
14551    && flag_unsafe_math_optimizations"
14552 {
14553   rtx op0, op1, op2;
14554
14555   if (optimize_insn_for_size_p ())
14556     FAIL;
14557
14558   op0 = gen_reg_rtx (XFmode);
14559   op1 = gen_reg_rtx (XFmode);
14560   op2 = gen_reg_rtx (XFmode);
14561
14562   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14563   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
14564   emit_insn (gen_scalbxf3 (op0, op1, op2));
14565   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14566   DONE;
14567 })
14568
14569 (define_expand "significandxf2"
14570   [(parallel [(set (match_operand:XF 0 "register_operand" "")
14571                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
14572                               UNSPEC_XTRACT_FRACT))
14573               (set (match_dup 2)
14574                    (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
14575   "TARGET_USE_FANCY_MATH_387
14576    && flag_unsafe_math_optimizations"
14577   "operands[2] = gen_reg_rtx (XFmode);")
14578
14579 (define_expand "significand<mode>2"
14580   [(use (match_operand:MODEF 0 "register_operand" ""))
14581    (use (match_operand:MODEF 1 "register_operand" ""))]
14582   "TARGET_USE_FANCY_MATH_387
14583    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14584        || TARGET_MIX_SSE_I387)
14585    && flag_unsafe_math_optimizations"
14586 {
14587   rtx op0 = gen_reg_rtx (XFmode);
14588   rtx op1 = gen_reg_rtx (XFmode);
14589
14590   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
14591   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14592   DONE;
14593 })
14594 \f
14595
14596 (define_insn "sse4_1_round<mode>2"
14597   [(set (match_operand:MODEF 0 "register_operand" "=x")
14598         (unspec:MODEF [(match_operand:MODEF 1 "register_operand" "x")
14599                        (match_operand:SI 2 "const_0_to_15_operand" "n")]
14600                       UNSPEC_ROUND))]
14601   "TARGET_ROUND"
14602   "%vround<ssemodesuffix>\t{%2, %1, %d0|%d0, %1, %2}"
14603   [(set_attr "type" "ssecvt")
14604    (set_attr "prefix_extra" "1")
14605    (set_attr "prefix" "maybe_vex")
14606    (set_attr "mode" "<MODE>")])
14607
14608 (define_insn "rintxf2"
14609   [(set (match_operand:XF 0 "register_operand" "=f")
14610         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
14611                    UNSPEC_FRNDINT))]
14612   "TARGET_USE_FANCY_MATH_387
14613    && flag_unsafe_math_optimizations"
14614   "frndint"
14615   [(set_attr "type" "fpspc")
14616    (set_attr "mode" "XF")])
14617
14618 (define_expand "rint<mode>2"
14619   [(use (match_operand:MODEF 0 "register_operand" ""))
14620    (use (match_operand:MODEF 1 "register_operand" ""))]
14621   "(TARGET_USE_FANCY_MATH_387
14622     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14623         || TARGET_MIX_SSE_I387)
14624     && flag_unsafe_math_optimizations)
14625    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14626        && !flag_trapping_math)"
14627 {
14628   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14629       && !flag_trapping_math)
14630     {
14631       if (TARGET_ROUND)
14632         emit_insn (gen_sse4_1_round<mode>2
14633                    (operands[0], operands[1], GEN_INT (ROUND_MXCSR)));
14634       else if (optimize_insn_for_size_p ())
14635         FAIL;
14636       else
14637         ix86_expand_rint (operand0, operand1);
14638     }
14639   else
14640     {
14641       rtx op0 = gen_reg_rtx (XFmode);
14642       rtx op1 = gen_reg_rtx (XFmode);
14643
14644       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14645       emit_insn (gen_rintxf2 (op0, op1));
14646
14647       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14648     }
14649   DONE;
14650 })
14651
14652 (define_expand "round<mode>2"
14653   [(match_operand:X87MODEF 0 "register_operand" "")
14654    (match_operand:X87MODEF 1 "nonimmediate_operand" "")]
14655   "(TARGET_USE_FANCY_MATH_387
14656     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14657         || TARGET_MIX_SSE_I387)
14658     && flag_unsafe_math_optimizations)
14659    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14660        && !flag_trapping_math && !flag_rounding_math)"
14661 {
14662   if (optimize_insn_for_size_p ())
14663     FAIL;
14664
14665   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14666       && !flag_trapping_math && !flag_rounding_math)
14667     {
14668       if (TARGET_ROUND)
14669         {
14670           operands[1] = force_reg (<MODE>mode, operands[1]);
14671           ix86_expand_round_sse4 (operands[0], operands[1]);
14672         }
14673       else if (TARGET_64BIT || (<MODE>mode != DFmode))
14674         ix86_expand_round (operands[0], operands[1]);
14675       else
14676         ix86_expand_rounddf_32 (operands[0], operands[1]);
14677     }
14678   else
14679     {
14680       operands[1] = force_reg (<MODE>mode, operands[1]);
14681       ix86_emit_i387_round (operands[0], operands[1]);
14682     }
14683   DONE;
14684 })
14685
14686 (define_insn_and_split "*fistdi2_1"
14687   [(set (match_operand:DI 0 "nonimmediate_operand" "")
14688         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14689                    UNSPEC_FIST))]
14690   "TARGET_USE_FANCY_MATH_387
14691    && can_create_pseudo_p ()"
14692   "#"
14693   "&& 1"
14694   [(const_int 0)]
14695 {
14696   if (memory_operand (operands[0], VOIDmode))
14697     emit_insn (gen_fistdi2 (operands[0], operands[1]));
14698   else
14699     {
14700       operands[2] = assign_386_stack_local (DImode, SLOT_TEMP);
14701       emit_insn (gen_fistdi2_with_temp (operands[0], operands[1],
14702                                          operands[2]));
14703     }
14704   DONE;
14705 }
14706   [(set_attr "type" "fpspc")
14707    (set_attr "mode" "DI")])
14708
14709 (define_insn "fistdi2"
14710   [(set (match_operand:DI 0 "memory_operand" "=m")
14711         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
14712                    UNSPEC_FIST))
14713    (clobber (match_scratch:XF 2 "=&1f"))]
14714   "TARGET_USE_FANCY_MATH_387"
14715   "* return output_fix_trunc (insn, operands, false);"
14716   [(set_attr "type" "fpspc")
14717    (set_attr "mode" "DI")])
14718
14719 (define_insn "fistdi2_with_temp"
14720   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
14721         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
14722                    UNSPEC_FIST))
14723    (clobber (match_operand:DI 2 "memory_operand" "=X,m"))
14724    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
14725   "TARGET_USE_FANCY_MATH_387"
14726   "#"
14727   [(set_attr "type" "fpspc")
14728    (set_attr "mode" "DI")])
14729
14730 (define_split
14731   [(set (match_operand:DI 0 "register_operand" "")
14732         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14733                    UNSPEC_FIST))
14734    (clobber (match_operand:DI 2 "memory_operand" ""))
14735    (clobber (match_scratch 3 ""))]
14736   "reload_completed"
14737   [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
14738               (clobber (match_dup 3))])
14739    (set (match_dup 0) (match_dup 2))])
14740
14741 (define_split
14742   [(set (match_operand:DI 0 "memory_operand" "")
14743         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14744                    UNSPEC_FIST))
14745    (clobber (match_operand:DI 2 "memory_operand" ""))
14746    (clobber (match_scratch 3 ""))]
14747   "reload_completed"
14748   [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
14749               (clobber (match_dup 3))])])
14750
14751 (define_insn_and_split "*fist<mode>2_1"
14752   [(set (match_operand:SWI24 0 "register_operand" "")
14753         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
14754                       UNSPEC_FIST))]
14755   "TARGET_USE_FANCY_MATH_387
14756    && can_create_pseudo_p ()"
14757   "#"
14758   "&& 1"
14759   [(const_int 0)]
14760 {
14761   operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
14762   emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1],
14763                                         operands[2]));
14764   DONE;
14765 }
14766   [(set_attr "type" "fpspc")
14767    (set_attr "mode" "<MODE>")])
14768
14769 (define_insn "fist<mode>2"
14770   [(set (match_operand:SWI24 0 "memory_operand" "=m")
14771         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
14772                       UNSPEC_FIST))]
14773   "TARGET_USE_FANCY_MATH_387"
14774   "* return output_fix_trunc (insn, operands, false);"
14775   [(set_attr "type" "fpspc")
14776    (set_attr "mode" "<MODE>")])
14777
14778 (define_insn "fist<mode>2_with_temp"
14779   [(set (match_operand:SWI24 0 "register_operand" "=r")
14780         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
14781                       UNSPEC_FIST))
14782    (clobber (match_operand:SWI24 2 "memory_operand" "=m"))]
14783   "TARGET_USE_FANCY_MATH_387"
14784   "#"
14785   [(set_attr "type" "fpspc")
14786    (set_attr "mode" "<MODE>")])
14787
14788 (define_split
14789   [(set (match_operand:SWI24 0 "register_operand" "")
14790         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
14791                       UNSPEC_FIST))
14792    (clobber (match_operand:SWI24 2 "memory_operand" ""))]
14793   "reload_completed"
14794   [(set (match_dup 2) (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST))
14795    (set (match_dup 0) (match_dup 2))])
14796
14797 (define_split
14798   [(set (match_operand:SWI24 0 "memory_operand" "")
14799         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
14800                       UNSPEC_FIST))
14801    (clobber (match_operand:SWI24 2 "memory_operand" ""))]
14802   "reload_completed"
14803   [(set (match_dup 0) (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST))])
14804
14805 (define_expand "lrintxf<mode>2"
14806   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
14807      (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
14808                      UNSPEC_FIST))]
14809   "TARGET_USE_FANCY_MATH_387")
14810
14811 (define_expand "lrint<MODEF:mode><SWI48x:mode>2"
14812   [(set (match_operand:SWI48x 0 "nonimmediate_operand" "")
14813      (unspec:SWI48x [(match_operand:MODEF 1 "register_operand" "")]
14814                         UNSPEC_FIX_NOTRUNC))]
14815   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
14816    && ((<SWI48x:MODE>mode != DImode) || TARGET_64BIT)")
14817
14818 (define_expand "lround<X87MODEF:mode><SWI248x:mode>2"
14819   [(match_operand:SWI248x 0 "nonimmediate_operand" "")
14820    (match_operand:X87MODEF 1 "register_operand" "")]
14821   "(TARGET_USE_FANCY_MATH_387
14822     && (!(SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
14823         || TARGET_MIX_SSE_I387)
14824     && flag_unsafe_math_optimizations)
14825    || (SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
14826        && <SWI248x:MODE>mode != HImode 
14827        && ((<SWI248x:MODE>mode != DImode) || TARGET_64BIT)
14828        && !flag_trapping_math && !flag_rounding_math)"
14829 {
14830   if (optimize_insn_for_size_p ())
14831     FAIL;
14832
14833   if (SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
14834       && <SWI248x:MODE>mode != HImode
14835       && ((<SWI248x:MODE>mode != DImode) || TARGET_64BIT)
14836       && !flag_trapping_math && !flag_rounding_math)
14837     ix86_expand_lround (operand0, operand1);
14838   else
14839     ix86_emit_i387_round (operands[0], operands[1]);
14840   DONE;
14841 })
14842
14843 ;; Rounding mode control word calculation could clobber FLAGS_REG.
14844 (define_insn_and_split "frndintxf2_floor"
14845   [(set (match_operand:XF 0 "register_operand" "")
14846         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
14847          UNSPEC_FRNDINT_FLOOR))
14848    (clobber (reg:CC FLAGS_REG))]
14849   "TARGET_USE_FANCY_MATH_387
14850    && flag_unsafe_math_optimizations
14851    && can_create_pseudo_p ()"
14852   "#"
14853   "&& 1"
14854   [(const_int 0)]
14855 {
14856   ix86_optimize_mode_switching[I387_FLOOR] = 1;
14857
14858   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
14859   operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
14860
14861   emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1],
14862                                         operands[2], operands[3]));
14863   DONE;
14864 }
14865   [(set_attr "type" "frndint")
14866    (set_attr "i387_cw" "floor")
14867    (set_attr "mode" "XF")])
14868
14869 (define_insn "frndintxf2_floor_i387"
14870   [(set (match_operand:XF 0 "register_operand" "=f")
14871         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
14872          UNSPEC_FRNDINT_FLOOR))
14873    (use (match_operand:HI 2 "memory_operand" "m"))
14874    (use (match_operand:HI 3 "memory_operand" "m"))]
14875   "TARGET_USE_FANCY_MATH_387
14876    && flag_unsafe_math_optimizations"
14877   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
14878   [(set_attr "type" "frndint")
14879    (set_attr "i387_cw" "floor")
14880    (set_attr "mode" "XF")])
14881
14882 (define_expand "floorxf2"
14883   [(use (match_operand:XF 0 "register_operand" ""))
14884    (use (match_operand:XF 1 "register_operand" ""))]
14885   "TARGET_USE_FANCY_MATH_387
14886    && flag_unsafe_math_optimizations"
14887 {
14888   if (optimize_insn_for_size_p ())
14889     FAIL;
14890   emit_insn (gen_frndintxf2_floor (operands[0], operands[1]));
14891   DONE;
14892 })
14893
14894 (define_expand "floor<mode>2"
14895   [(use (match_operand:MODEF 0 "register_operand" ""))
14896    (use (match_operand:MODEF 1 "register_operand" ""))]
14897   "(TARGET_USE_FANCY_MATH_387
14898     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
14899         || TARGET_MIX_SSE_I387)
14900     && flag_unsafe_math_optimizations)
14901    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14902        && !flag_trapping_math)"
14903 {
14904   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
14905       && !flag_trapping_math)
14906     {
14907       if (TARGET_ROUND)
14908         emit_insn (gen_sse4_1_round<mode>2
14909                    (operands[0], operands[1], GEN_INT (ROUND_FLOOR)));
14910       else if (optimize_insn_for_size_p ())
14911         FAIL;
14912       else if (TARGET_64BIT || (<MODE>mode != DFmode))
14913         ix86_expand_floorceil (operand0, operand1, true);
14914       else
14915         ix86_expand_floorceildf_32 (operand0, operand1, true);
14916     }
14917   else
14918     {
14919       rtx op0, op1;
14920
14921       if (optimize_insn_for_size_p ())
14922         FAIL;
14923
14924       op0 = gen_reg_rtx (XFmode);
14925       op1 = gen_reg_rtx (XFmode);
14926       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
14927       emit_insn (gen_frndintxf2_floor (op0, op1));
14928
14929       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
14930     }
14931   DONE;
14932 })
14933
14934 (define_insn_and_split "*fist<mode>2_floor_1"
14935   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
14936         (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
14937                         UNSPEC_FIST_FLOOR))
14938    (clobber (reg:CC FLAGS_REG))]
14939   "TARGET_USE_FANCY_MATH_387
14940    && flag_unsafe_math_optimizations
14941    && can_create_pseudo_p ()"
14942   "#"
14943   "&& 1"
14944   [(const_int 0)]
14945 {
14946   ix86_optimize_mode_switching[I387_FLOOR] = 1;
14947
14948   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
14949   operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
14950   if (memory_operand (operands[0], VOIDmode))
14951     emit_insn (gen_fist<mode>2_floor (operands[0], operands[1],
14952                                       operands[2], operands[3]));
14953   else
14954     {
14955       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
14956       emit_insn (gen_fist<mode>2_floor_with_temp (operands[0], operands[1],
14957                                                   operands[2], operands[3],
14958                                                   operands[4]));
14959     }
14960   DONE;
14961 }
14962   [(set_attr "type" "fistp")
14963    (set_attr "i387_cw" "floor")
14964    (set_attr "mode" "<MODE>")])
14965
14966 (define_insn "fistdi2_floor"
14967   [(set (match_operand:DI 0 "memory_operand" "=m")
14968         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
14969                    UNSPEC_FIST_FLOOR))
14970    (use (match_operand:HI 2 "memory_operand" "m"))
14971    (use (match_operand:HI 3 "memory_operand" "m"))
14972    (clobber (match_scratch:XF 4 "=&1f"))]
14973   "TARGET_USE_FANCY_MATH_387
14974    && flag_unsafe_math_optimizations"
14975   "* return output_fix_trunc (insn, operands, false);"
14976   [(set_attr "type" "fistp")
14977    (set_attr "i387_cw" "floor")
14978    (set_attr "mode" "DI")])
14979
14980 (define_insn "fistdi2_floor_with_temp"
14981   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
14982         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
14983                    UNSPEC_FIST_FLOOR))
14984    (use (match_operand:HI 2 "memory_operand" "m,m"))
14985    (use (match_operand:HI 3 "memory_operand" "m,m"))
14986    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
14987    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
14988   "TARGET_USE_FANCY_MATH_387
14989    && flag_unsafe_math_optimizations"
14990   "#"
14991   [(set_attr "type" "fistp")
14992    (set_attr "i387_cw" "floor")
14993    (set_attr "mode" "DI")])
14994
14995 (define_split
14996   [(set (match_operand:DI 0 "register_operand" "")
14997         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
14998                    UNSPEC_FIST_FLOOR))
14999    (use (match_operand:HI 2 "memory_operand" ""))
15000    (use (match_operand:HI 3 "memory_operand" ""))
15001    (clobber (match_operand:DI 4 "memory_operand" ""))
15002    (clobber (match_scratch 5 ""))]
15003   "reload_completed"
15004   [(parallel [(set (match_dup 4)
15005                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
15006               (use (match_dup 2))
15007               (use (match_dup 3))
15008               (clobber (match_dup 5))])
15009    (set (match_dup 0) (match_dup 4))])
15010
15011 (define_split
15012   [(set (match_operand:DI 0 "memory_operand" "")
15013         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
15014                    UNSPEC_FIST_FLOOR))
15015    (use (match_operand:HI 2 "memory_operand" ""))
15016    (use (match_operand:HI 3 "memory_operand" ""))
15017    (clobber (match_operand:DI 4 "memory_operand" ""))
15018    (clobber (match_scratch 5 ""))]
15019   "reload_completed"
15020   [(parallel [(set (match_dup 0)
15021                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
15022               (use (match_dup 2))
15023               (use (match_dup 3))
15024               (clobber (match_dup 5))])])
15025
15026 (define_insn "fist<mode>2_floor"
15027   [(set (match_operand:SWI24 0 "memory_operand" "=m")
15028         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
15029                       UNSPEC_FIST_FLOOR))
15030    (use (match_operand:HI 2 "memory_operand" "m"))
15031    (use (match_operand:HI 3 "memory_operand" "m"))]
15032   "TARGET_USE_FANCY_MATH_387
15033    && flag_unsafe_math_optimizations"
15034   "* return output_fix_trunc (insn, operands, false);"
15035   [(set_attr "type" "fistp")
15036    (set_attr "i387_cw" "floor")
15037    (set_attr "mode" "<MODE>")])
15038
15039 (define_insn "fist<mode>2_floor_with_temp"
15040   [(set (match_operand:SWI24 0 "nonimmediate_operand" "=m,?r")
15041         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f,f")]
15042                       UNSPEC_FIST_FLOOR))
15043    (use (match_operand:HI 2 "memory_operand" "m,m"))
15044    (use (match_operand:HI 3 "memory_operand" "m,m"))
15045    (clobber (match_operand:SWI24 4 "memory_operand" "=X,m"))]
15046   "TARGET_USE_FANCY_MATH_387
15047    && flag_unsafe_math_optimizations"
15048   "#"
15049   [(set_attr "type" "fistp")
15050    (set_attr "i387_cw" "floor")
15051    (set_attr "mode" "<MODE>")])
15052
15053 (define_split
15054   [(set (match_operand:SWI24 0 "register_operand" "")
15055         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15056                       UNSPEC_FIST_FLOOR))
15057    (use (match_operand:HI 2 "memory_operand" ""))
15058    (use (match_operand:HI 3 "memory_operand" ""))
15059    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15060   "reload_completed"
15061   [(parallel [(set (match_dup 4)
15062                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_FLOOR))
15063               (use (match_dup 2))
15064               (use (match_dup 3))])
15065    (set (match_dup 0) (match_dup 4))])
15066
15067 (define_split
15068   [(set (match_operand:SWI24 0 "memory_operand" "")
15069         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15070                       UNSPEC_FIST_FLOOR))
15071    (use (match_operand:HI 2 "memory_operand" ""))
15072    (use (match_operand:HI 3 "memory_operand" ""))
15073    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15074   "reload_completed"
15075   [(parallel [(set (match_dup 0)
15076                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_FLOOR))
15077               (use (match_dup 2))
15078               (use (match_dup 3))])])
15079
15080 (define_expand "lfloorxf<mode>2"
15081   [(parallel [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
15082                    (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
15083                                    UNSPEC_FIST_FLOOR))
15084               (clobber (reg:CC FLAGS_REG))])]
15085   "TARGET_USE_FANCY_MATH_387
15086    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15087    && flag_unsafe_math_optimizations")
15088
15089 (define_expand "lfloor<MODEF:mode><SWI48:mode>2"
15090   [(match_operand:SWI48 0 "nonimmediate_operand" "")
15091    (match_operand:MODEF 1 "register_operand" "")]
15092   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
15093    && !flag_trapping_math"
15094 {
15095   if (TARGET_64BIT && optimize_insn_for_size_p ())
15096     FAIL;
15097   ix86_expand_lfloorceil (operand0, operand1, true);
15098   DONE;
15099 })
15100
15101 ;; Rounding mode control word calculation could clobber FLAGS_REG.
15102 (define_insn_and_split "frndintxf2_ceil"
15103   [(set (match_operand:XF 0 "register_operand" "")
15104         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15105          UNSPEC_FRNDINT_CEIL))
15106    (clobber (reg:CC FLAGS_REG))]
15107   "TARGET_USE_FANCY_MATH_387
15108    && flag_unsafe_math_optimizations
15109    && can_create_pseudo_p ()"
15110   "#"
15111   "&& 1"
15112   [(const_int 0)]
15113 {
15114   ix86_optimize_mode_switching[I387_CEIL] = 1;
15115
15116   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15117   operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
15118
15119   emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1],
15120                                        operands[2], operands[3]));
15121   DONE;
15122 }
15123   [(set_attr "type" "frndint")
15124    (set_attr "i387_cw" "ceil")
15125    (set_attr "mode" "XF")])
15126
15127 (define_insn "frndintxf2_ceil_i387"
15128   [(set (match_operand:XF 0 "register_operand" "=f")
15129         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15130          UNSPEC_FRNDINT_CEIL))
15131    (use (match_operand:HI 2 "memory_operand" "m"))
15132    (use (match_operand:HI 3 "memory_operand" "m"))]
15133   "TARGET_USE_FANCY_MATH_387
15134    && flag_unsafe_math_optimizations"
15135   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
15136   [(set_attr "type" "frndint")
15137    (set_attr "i387_cw" "ceil")
15138    (set_attr "mode" "XF")])
15139
15140 (define_expand "ceilxf2"
15141   [(use (match_operand:XF 0 "register_operand" ""))
15142    (use (match_operand:XF 1 "register_operand" ""))]
15143   "TARGET_USE_FANCY_MATH_387
15144    && flag_unsafe_math_optimizations"
15145 {
15146   if (optimize_insn_for_size_p ())
15147     FAIL;
15148   emit_insn (gen_frndintxf2_ceil (operands[0], operands[1]));
15149   DONE;
15150 })
15151
15152 (define_expand "ceil<mode>2"
15153   [(use (match_operand:MODEF 0 "register_operand" ""))
15154    (use (match_operand:MODEF 1 "register_operand" ""))]
15155   "(TARGET_USE_FANCY_MATH_387
15156     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
15157         || TARGET_MIX_SSE_I387)
15158     && flag_unsafe_math_optimizations)
15159    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15160        && !flag_trapping_math)"
15161 {
15162   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15163       && !flag_trapping_math)
15164     {
15165       if (TARGET_ROUND)
15166         emit_insn (gen_sse4_1_round<mode>2
15167                    (operands[0], operands[1], GEN_INT (ROUND_CEIL)));
15168       else if (optimize_insn_for_size_p ())
15169         FAIL;
15170       else if (TARGET_64BIT || (<MODE>mode != DFmode))
15171         ix86_expand_floorceil (operand0, operand1, false);
15172       else
15173         ix86_expand_floorceildf_32 (operand0, operand1, false);
15174     }
15175   else
15176     {
15177       rtx op0, op1;
15178
15179       if (optimize_insn_for_size_p ())
15180         FAIL;
15181
15182       op0 = gen_reg_rtx (XFmode);
15183       op1 = gen_reg_rtx (XFmode);
15184       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
15185       emit_insn (gen_frndintxf2_ceil (op0, op1));
15186
15187       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
15188     }
15189   DONE;
15190 })
15191
15192 (define_insn_and_split "*fist<mode>2_ceil_1"
15193   [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
15194         (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
15195                         UNSPEC_FIST_CEIL))
15196    (clobber (reg:CC FLAGS_REG))]
15197   "TARGET_USE_FANCY_MATH_387
15198    && flag_unsafe_math_optimizations
15199    && can_create_pseudo_p ()"
15200   "#"
15201   "&& 1"
15202   [(const_int 0)]
15203 {
15204   ix86_optimize_mode_switching[I387_CEIL] = 1;
15205
15206   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15207   operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
15208   if (memory_operand (operands[0], VOIDmode))
15209     emit_insn (gen_fist<mode>2_ceil (operands[0], operands[1],
15210                                      operands[2], operands[3]));
15211   else
15212     {
15213       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
15214       emit_insn (gen_fist<mode>2_ceil_with_temp (operands[0], operands[1],
15215                                                  operands[2], operands[3],
15216                                                  operands[4]));
15217     }
15218   DONE;
15219 }
15220   [(set_attr "type" "fistp")
15221    (set_attr "i387_cw" "ceil")
15222    (set_attr "mode" "<MODE>")])
15223
15224 (define_insn "fistdi2_ceil"
15225   [(set (match_operand:DI 0 "memory_operand" "=m")
15226         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
15227                    UNSPEC_FIST_CEIL))
15228    (use (match_operand:HI 2 "memory_operand" "m"))
15229    (use (match_operand:HI 3 "memory_operand" "m"))
15230    (clobber (match_scratch:XF 4 "=&1f"))]
15231   "TARGET_USE_FANCY_MATH_387
15232    && flag_unsafe_math_optimizations"
15233   "* return output_fix_trunc (insn, operands, false);"
15234   [(set_attr "type" "fistp")
15235    (set_attr "i387_cw" "ceil")
15236    (set_attr "mode" "DI")])
15237
15238 (define_insn "fistdi2_ceil_with_temp"
15239   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
15240         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
15241                    UNSPEC_FIST_CEIL))
15242    (use (match_operand:HI 2 "memory_operand" "m,m"))
15243    (use (match_operand:HI 3 "memory_operand" "m,m"))
15244    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
15245    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
15246   "TARGET_USE_FANCY_MATH_387
15247    && flag_unsafe_math_optimizations"
15248   "#"
15249   [(set_attr "type" "fistp")
15250    (set_attr "i387_cw" "ceil")
15251    (set_attr "mode" "DI")])
15252
15253 (define_split
15254   [(set (match_operand:DI 0 "register_operand" "")
15255         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
15256                    UNSPEC_FIST_CEIL))
15257    (use (match_operand:HI 2 "memory_operand" ""))
15258    (use (match_operand:HI 3 "memory_operand" ""))
15259    (clobber (match_operand:DI 4 "memory_operand" ""))
15260    (clobber (match_scratch 5 ""))]
15261   "reload_completed"
15262   [(parallel [(set (match_dup 4)
15263                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
15264               (use (match_dup 2))
15265               (use (match_dup 3))
15266               (clobber (match_dup 5))])
15267    (set (match_dup 0) (match_dup 4))])
15268
15269 (define_split
15270   [(set (match_operand:DI 0 "memory_operand" "")
15271         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
15272                    UNSPEC_FIST_CEIL))
15273    (use (match_operand:HI 2 "memory_operand" ""))
15274    (use (match_operand:HI 3 "memory_operand" ""))
15275    (clobber (match_operand:DI 4 "memory_operand" ""))
15276    (clobber (match_scratch 5 ""))]
15277   "reload_completed"
15278   [(parallel [(set (match_dup 0)
15279                    (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
15280               (use (match_dup 2))
15281               (use (match_dup 3))
15282               (clobber (match_dup 5))])])
15283
15284 (define_insn "fist<mode>2_ceil"
15285   [(set (match_operand:SWI24 0 "memory_operand" "=m")
15286         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f")]
15287                       UNSPEC_FIST_CEIL))
15288    (use (match_operand:HI 2 "memory_operand" "m"))
15289    (use (match_operand:HI 3 "memory_operand" "m"))]
15290   "TARGET_USE_FANCY_MATH_387
15291    && flag_unsafe_math_optimizations"
15292   "* return output_fix_trunc (insn, operands, false);"
15293   [(set_attr "type" "fistp")
15294    (set_attr "i387_cw" "ceil")
15295    (set_attr "mode" "<MODE>")])
15296
15297 (define_insn "fist<mode>2_ceil_with_temp"
15298   [(set (match_operand:SWI24 0 "nonimmediate_operand" "=m,?r")
15299         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "f,f")]
15300                       UNSPEC_FIST_CEIL))
15301    (use (match_operand:HI 2 "memory_operand" "m,m"))
15302    (use (match_operand:HI 3 "memory_operand" "m,m"))
15303    (clobber (match_operand:SWI24 4 "memory_operand" "=X,m"))]
15304   "TARGET_USE_FANCY_MATH_387
15305    && flag_unsafe_math_optimizations"
15306   "#"
15307   [(set_attr "type" "fistp")
15308    (set_attr "i387_cw" "ceil")
15309    (set_attr "mode" "<MODE>")])
15310
15311 (define_split
15312   [(set (match_operand:SWI24 0 "register_operand" "")
15313         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15314                       UNSPEC_FIST_CEIL))
15315    (use (match_operand:HI 2 "memory_operand" ""))
15316    (use (match_operand:HI 3 "memory_operand" ""))
15317    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15318   "reload_completed"
15319   [(parallel [(set (match_dup 4)
15320                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_CEIL))
15321               (use (match_dup 2))
15322               (use (match_dup 3))])
15323    (set (match_dup 0) (match_dup 4))])
15324
15325 (define_split
15326   [(set (match_operand:SWI24 0 "memory_operand" "")
15327         (unspec:SWI24 [(match_operand:XF 1 "register_operand" "")]
15328                       UNSPEC_FIST_CEIL))
15329    (use (match_operand:HI 2 "memory_operand" ""))
15330    (use (match_operand:HI 3 "memory_operand" ""))
15331    (clobber (match_operand:SWI24 4 "memory_operand" ""))]
15332   "reload_completed"
15333   [(parallel [(set (match_dup 0)
15334                    (unspec:SWI24 [(match_dup 1)] UNSPEC_FIST_CEIL))
15335               (use (match_dup 2))
15336               (use (match_dup 3))])])
15337
15338 (define_expand "lceilxf<mode>2"
15339   [(parallel [(set (match_operand:SWI248x 0 "nonimmediate_operand" "")
15340                    (unspec:SWI248x [(match_operand:XF 1 "register_operand" "")]
15341                                    UNSPEC_FIST_CEIL))
15342               (clobber (reg:CC FLAGS_REG))])]
15343   "TARGET_USE_FANCY_MATH_387
15344    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15345    && flag_unsafe_math_optimizations")
15346
15347 (define_expand "lceil<MODEF:mode><SWI48:mode>2"
15348   [(match_operand:SWI48 0 "nonimmediate_operand" "")
15349    (match_operand:MODEF 1 "register_operand" "")]
15350   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
15351    && !flag_trapping_math"
15352 {
15353   ix86_expand_lfloorceil (operand0, operand1, false);
15354   DONE;
15355 })
15356
15357 ;; Rounding mode control word calculation could clobber FLAGS_REG.
15358 (define_insn_and_split "frndintxf2_trunc"
15359   [(set (match_operand:XF 0 "register_operand" "")
15360         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15361          UNSPEC_FRNDINT_TRUNC))
15362    (clobber (reg:CC FLAGS_REG))]
15363   "TARGET_USE_FANCY_MATH_387
15364    && flag_unsafe_math_optimizations
15365    && can_create_pseudo_p ()"
15366   "#"
15367   "&& 1"
15368   [(const_int 0)]
15369 {
15370   ix86_optimize_mode_switching[I387_TRUNC] = 1;
15371
15372   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15373   operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
15374
15375   emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1],
15376                                         operands[2], operands[3]));
15377   DONE;
15378 }
15379   [(set_attr "type" "frndint")
15380    (set_attr "i387_cw" "trunc")
15381    (set_attr "mode" "XF")])
15382
15383 (define_insn "frndintxf2_trunc_i387"
15384   [(set (match_operand:XF 0 "register_operand" "=f")
15385         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15386          UNSPEC_FRNDINT_TRUNC))
15387    (use (match_operand:HI 2 "memory_operand" "m"))
15388    (use (match_operand:HI 3 "memory_operand" "m"))]
15389   "TARGET_USE_FANCY_MATH_387
15390    && flag_unsafe_math_optimizations"
15391   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
15392   [(set_attr "type" "frndint")
15393    (set_attr "i387_cw" "trunc")
15394    (set_attr "mode" "XF")])
15395
15396 (define_expand "btruncxf2"
15397   [(use (match_operand:XF 0 "register_operand" ""))
15398    (use (match_operand:XF 1 "register_operand" ""))]
15399   "TARGET_USE_FANCY_MATH_387
15400    && flag_unsafe_math_optimizations"
15401 {
15402   if (optimize_insn_for_size_p ())
15403     FAIL;
15404   emit_insn (gen_frndintxf2_trunc (operands[0], operands[1]));
15405   DONE;
15406 })
15407
15408 (define_expand "btrunc<mode>2"
15409   [(use (match_operand:MODEF 0 "register_operand" ""))
15410    (use (match_operand:MODEF 1 "register_operand" ""))]
15411   "(TARGET_USE_FANCY_MATH_387
15412     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
15413         || TARGET_MIX_SSE_I387)
15414     && flag_unsafe_math_optimizations)
15415    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15416        && !flag_trapping_math)"
15417 {
15418   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15419       && !flag_trapping_math)
15420     {
15421       if (TARGET_ROUND)
15422         emit_insn (gen_sse4_1_round<mode>2
15423                    (operands[0], operands[1], GEN_INT (ROUND_TRUNC)));
15424       else if (optimize_insn_for_size_p ())
15425         FAIL;
15426       else if (TARGET_64BIT || (<MODE>mode != DFmode))
15427         ix86_expand_trunc (operand0, operand1);
15428       else
15429         ix86_expand_truncdf_32 (operand0, operand1);
15430     }
15431   else
15432     {
15433       rtx op0, op1;
15434
15435       if (optimize_insn_for_size_p ())
15436         FAIL;
15437
15438       op0 = gen_reg_rtx (XFmode);
15439       op1 = gen_reg_rtx (XFmode);
15440       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
15441       emit_insn (gen_frndintxf2_trunc (op0, op1));
15442
15443       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
15444     }
15445   DONE;
15446 })
15447
15448 ;; Rounding mode control word calculation could clobber FLAGS_REG.
15449 (define_insn_and_split "frndintxf2_mask_pm"
15450   [(set (match_operand:XF 0 "register_operand" "")
15451         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15452          UNSPEC_FRNDINT_MASK_PM))
15453    (clobber (reg:CC FLAGS_REG))]
15454   "TARGET_USE_FANCY_MATH_387
15455    && flag_unsafe_math_optimizations
15456    && can_create_pseudo_p ()"
15457   "#"
15458   "&& 1"
15459   [(const_int 0)]
15460 {
15461   ix86_optimize_mode_switching[I387_MASK_PM] = 1;
15462
15463   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
15464   operands[3] = assign_386_stack_local (HImode, SLOT_CW_MASK_PM);
15465
15466   emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1],
15467                                           operands[2], operands[3]));
15468   DONE;
15469 }
15470   [(set_attr "type" "frndint")
15471    (set_attr "i387_cw" "mask_pm")
15472    (set_attr "mode" "XF")])
15473
15474 (define_insn "frndintxf2_mask_pm_i387"
15475   [(set (match_operand:XF 0 "register_operand" "=f")
15476         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15477          UNSPEC_FRNDINT_MASK_PM))
15478    (use (match_operand:HI 2 "memory_operand" "m"))
15479    (use (match_operand:HI 3 "memory_operand" "m"))]
15480   "TARGET_USE_FANCY_MATH_387
15481    && flag_unsafe_math_optimizations"
15482   "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2"
15483   [(set_attr "type" "frndint")
15484    (set_attr "i387_cw" "mask_pm")
15485    (set_attr "mode" "XF")])
15486
15487 (define_expand "nearbyintxf2"
15488   [(use (match_operand:XF 0 "register_operand" ""))
15489    (use (match_operand:XF 1 "register_operand" ""))]
15490   "TARGET_USE_FANCY_MATH_387
15491    && flag_unsafe_math_optimizations"
15492 {
15493   emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1]));
15494   DONE;
15495 })
15496
15497 (define_expand "nearbyint<mode>2"
15498   [(use (match_operand:MODEF 0 "register_operand" ""))
15499    (use (match_operand:MODEF 1 "register_operand" ""))]
15500   "TARGET_USE_FANCY_MATH_387
15501    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
15502        || TARGET_MIX_SSE_I387)
15503    && flag_unsafe_math_optimizations"
15504 {
15505   rtx op0 = gen_reg_rtx (XFmode);
15506   rtx op1 = gen_reg_rtx (XFmode);
15507
15508   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
15509   emit_insn (gen_frndintxf2_mask_pm (op0, op1));
15510
15511   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
15512   DONE;
15513 })
15514
15515 (define_insn "fxam<mode>2_i387"
15516   [(set (match_operand:HI 0 "register_operand" "=a")
15517         (unspec:HI
15518           [(match_operand:X87MODEF 1 "register_operand" "f")]
15519           UNSPEC_FXAM))]
15520   "TARGET_USE_FANCY_MATH_387"
15521   "fxam\n\tfnstsw\t%0"
15522   [(set_attr "type" "multi")
15523    (set_attr "length" "4")
15524    (set_attr "unit" "i387")
15525    (set_attr "mode" "<MODE>")])
15526
15527 (define_insn_and_split "fxam<mode>2_i387_with_temp"
15528   [(set (match_operand:HI 0 "register_operand" "")
15529         (unspec:HI
15530           [(match_operand:MODEF 1 "memory_operand" "")]
15531           UNSPEC_FXAM_MEM))]
15532   "TARGET_USE_FANCY_MATH_387
15533    && can_create_pseudo_p ()"
15534   "#"
15535   "&& 1"
15536   [(set (match_dup 2)(match_dup 1))
15537    (set (match_dup 0)
15538         (unspec:HI [(match_dup 2)] UNSPEC_FXAM))]
15539 {
15540   operands[2] = gen_reg_rtx (<MODE>mode);
15541
15542   MEM_VOLATILE_P (operands[1]) = 1;
15543 }
15544   [(set_attr "type" "multi")
15545    (set_attr "unit" "i387")
15546    (set_attr "mode" "<MODE>")])
15547
15548 (define_expand "isinfxf2"
15549   [(use (match_operand:SI 0 "register_operand" ""))
15550    (use (match_operand:XF 1 "register_operand" ""))]
15551   "TARGET_USE_FANCY_MATH_387
15552    && TARGET_C99_FUNCTIONS"
15553 {
15554   rtx mask = GEN_INT (0x45);
15555   rtx val = GEN_INT (0x05);
15556
15557   rtx cond;
15558
15559   rtx scratch = gen_reg_rtx (HImode);
15560   rtx res = gen_reg_rtx (QImode);
15561
15562   emit_insn (gen_fxamxf2_i387 (scratch, operands[1]));
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 "isinf<mode>2"
15575   [(use (match_operand:SI 0 "register_operand" ""))
15576    (use (match_operand:MODEF 1 "nonimmediate_operand" ""))]
15577   "TARGET_USE_FANCY_MATH_387
15578    && TARGET_C99_FUNCTIONS
15579    && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
15580 {
15581   rtx mask = GEN_INT (0x45);
15582   rtx val = GEN_INT (0x05);
15583
15584   rtx cond;
15585
15586   rtx scratch = gen_reg_rtx (HImode);
15587   rtx res = gen_reg_rtx (QImode);
15588
15589   /* Remove excess precision by forcing value through memory. */
15590   if (memory_operand (operands[1], VOIDmode))
15591     emit_insn (gen_fxam<mode>2_i387_with_temp (scratch, operands[1]));
15592   else
15593     {
15594       enum ix86_stack_slot slot = (virtuals_instantiated
15595                                    ? SLOT_TEMP
15596                                    : SLOT_VIRTUAL);
15597       rtx temp = assign_386_stack_local (<MODE>mode, slot);
15598
15599       emit_move_insn (temp, operands[1]);
15600       emit_insn (gen_fxam<mode>2_i387_with_temp (scratch, temp));
15601     }
15602
15603   emit_insn (gen_andqi_ext_0 (scratch, scratch, mask));
15604   emit_insn (gen_cmpqi_ext_3 (scratch, val));
15605   cond = gen_rtx_fmt_ee (EQ, QImode,
15606                          gen_rtx_REG (CCmode, FLAGS_REG),
15607                          const0_rtx);
15608   emit_insn (gen_rtx_SET (VOIDmode, res, cond));
15609   emit_insn (gen_zero_extendqisi2 (operands[0], res));
15610   DONE;
15611 })
15612
15613 (define_expand "signbitxf2"
15614   [(use (match_operand:SI 0 "register_operand" ""))
15615    (use (match_operand:XF 1 "register_operand" ""))]
15616   "TARGET_USE_FANCY_MATH_387"
15617 {
15618   rtx scratch = gen_reg_rtx (HImode);
15619
15620   emit_insn (gen_fxamxf2_i387 (scratch, operands[1]));
15621   emit_insn (gen_andsi3 (operands[0],
15622              gen_lowpart (SImode, scratch), GEN_INT (0x200)));
15623   DONE;
15624 })
15625
15626 (define_insn "movmsk_df"
15627   [(set (match_operand:SI 0 "register_operand" "=r")
15628         (unspec:SI
15629           [(match_operand:DF 1 "register_operand" "x")]
15630           UNSPEC_MOVMSK))]
15631   "SSE_FLOAT_MODE_P (DFmode) && TARGET_SSE_MATH"
15632   "%vmovmskpd\t{%1, %0|%0, %1}"
15633   [(set_attr "type" "ssemov")
15634    (set_attr "prefix" "maybe_vex")
15635    (set_attr "mode" "DF")])
15636
15637 ;; Use movmskpd in SSE mode to avoid store forwarding stall
15638 ;; for 32bit targets and movq+shrq sequence for 64bit targets.
15639 (define_expand "signbitdf2"
15640   [(use (match_operand:SI 0 "register_operand" ""))
15641    (use (match_operand:DF 1 "register_operand" ""))]
15642   "TARGET_USE_FANCY_MATH_387
15643    || (SSE_FLOAT_MODE_P (DFmode) && TARGET_SSE_MATH)"
15644 {
15645   if (SSE_FLOAT_MODE_P (DFmode) && TARGET_SSE_MATH)
15646     {
15647       emit_insn (gen_movmsk_df (operands[0], operands[1]));
15648       emit_insn (gen_andsi3 (operands[0], operands[0], const1_rtx));
15649     }
15650   else
15651     {
15652       rtx scratch = gen_reg_rtx (HImode);
15653
15654       emit_insn (gen_fxamdf2_i387 (scratch, operands[1]));
15655       emit_insn (gen_andsi3 (operands[0],
15656                  gen_lowpart (SImode, scratch), GEN_INT (0x200)));
15657     }
15658   DONE;
15659 })
15660
15661 (define_expand "signbitsf2"
15662   [(use (match_operand:SI 0 "register_operand" ""))
15663    (use (match_operand:SF 1 "register_operand" ""))]
15664   "TARGET_USE_FANCY_MATH_387
15665    && !(SSE_FLOAT_MODE_P (SFmode) && TARGET_SSE_MATH)"
15666 {
15667   rtx scratch = gen_reg_rtx (HImode);
15668
15669   emit_insn (gen_fxamsf2_i387 (scratch, operands[1]));
15670   emit_insn (gen_andsi3 (operands[0],
15671              gen_lowpart (SImode, scratch), GEN_INT (0x200)));
15672   DONE;
15673 })
15674 \f
15675 ;; Block operation instructions
15676
15677 (define_insn "cld"
15678   [(unspec_volatile [(const_int 0)] UNSPECV_CLD)]
15679   ""
15680   "cld"
15681   [(set_attr "length" "1")
15682    (set_attr "length_immediate" "0")
15683    (set_attr "modrm" "0")])
15684
15685 (define_expand "movmem<mode>"
15686   [(use (match_operand:BLK 0 "memory_operand" ""))
15687    (use (match_operand:BLK 1 "memory_operand" ""))
15688    (use (match_operand:SWI48 2 "nonmemory_operand" ""))
15689    (use (match_operand:SWI48 3 "const_int_operand" ""))
15690    (use (match_operand:SI 4 "const_int_operand" ""))
15691    (use (match_operand:SI 5 "const_int_operand" ""))]
15692   ""
15693 {
15694  if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3],
15695                          operands[4], operands[5]))
15696    DONE;
15697  else
15698    FAIL;
15699 })
15700
15701 ;; Most CPUs don't like single string operations
15702 ;; Handle this case here to simplify previous expander.
15703
15704 (define_expand "strmov"
15705   [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
15706    (set (match_operand 1 "memory_operand" "") (match_dup 4))
15707    (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
15708               (clobber (reg:CC FLAGS_REG))])
15709    (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
15710               (clobber (reg:CC FLAGS_REG))])]
15711   ""
15712 {
15713   rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
15714
15715   /* If .md ever supports :P for Pmode, these can be directly
15716      in the pattern above.  */
15717   operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
15718   operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
15719
15720   /* Can't use this if the user has appropriated esi or edi.  */
15721   if ((TARGET_SINGLE_STRINGOP || optimize_insn_for_size_p ())
15722       && !(fixed_regs[SI_REG] || fixed_regs[DI_REG]))
15723     {
15724       emit_insn (gen_strmov_singleop (operands[0], operands[1],
15725                                       operands[2], operands[3],
15726                                       operands[5], operands[6]));
15727       DONE;
15728     }
15729
15730   operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
15731 })
15732
15733 (define_expand "strmov_singleop"
15734   [(parallel [(set (match_operand 1 "memory_operand" "")
15735                    (match_operand 3 "memory_operand" ""))
15736               (set (match_operand 0 "register_operand" "")
15737                    (match_operand 4 "" ""))
15738               (set (match_operand 2 "register_operand" "")
15739                    (match_operand 5 "" ""))])]
15740   ""
15741   "ix86_current_function_needs_cld = 1;")
15742
15743 (define_insn "*strmovdi_rex_1"
15744   [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
15745         (mem:DI (match_operand:DI 3 "register_operand" "1")))
15746    (set (match_operand:DI 0 "register_operand" "=D")
15747         (plus:DI (match_dup 2)
15748                  (const_int 8)))
15749    (set (match_operand:DI 1 "register_operand" "=S")
15750         (plus:DI (match_dup 3)
15751                  (const_int 8)))]
15752   "TARGET_64BIT
15753    && !(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15754   "movsq"
15755   [(set_attr "type" "str")
15756    (set_attr "memory" "both")
15757    (set_attr "mode" "DI")])
15758
15759 (define_insn "*strmovsi_1"
15760   [(set (mem:SI (match_operand:P 2 "register_operand" "0"))
15761         (mem:SI (match_operand:P 3 "register_operand" "1")))
15762    (set (match_operand:P 0 "register_operand" "=D")
15763         (plus:P (match_dup 2)
15764                 (const_int 4)))
15765    (set (match_operand:P 1 "register_operand" "=S")
15766         (plus:P (match_dup 3)
15767                 (const_int 4)))]
15768   "!(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15769   "movs{l|d}"
15770   [(set_attr "type" "str")
15771    (set_attr "memory" "both")
15772    (set_attr "mode" "SI")])
15773
15774 (define_insn "*strmovhi_1"
15775   [(set (mem:HI (match_operand:P 2 "register_operand" "0"))
15776         (mem:HI (match_operand:P 3 "register_operand" "1")))
15777    (set (match_operand:P 0 "register_operand" "=D")
15778         (plus:P (match_dup 2)
15779                 (const_int 2)))
15780    (set (match_operand:P 1 "register_operand" "=S")
15781         (plus:P (match_dup 3)
15782                 (const_int 2)))]
15783   "!(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15784   "movsw"
15785   [(set_attr "type" "str")
15786    (set_attr "memory" "both")
15787    (set_attr "mode" "HI")])
15788
15789 (define_insn "*strmovqi_1"
15790   [(set (mem:QI (match_operand:P 2 "register_operand" "0"))
15791         (mem:QI (match_operand:P 3 "register_operand" "1")))
15792    (set (match_operand:P 0 "register_operand" "=D")
15793         (plus:P (match_dup 2)
15794                 (const_int 1)))
15795    (set (match_operand:P 1 "register_operand" "=S")
15796         (plus:P (match_dup 3)
15797                 (const_int 1)))]
15798   "!(fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15799   "movsb"
15800   [(set_attr "type" "str")
15801    (set_attr "memory" "both")
15802    (set (attr "prefix_rex")
15803         (if_then_else
15804           (match_test "<P:MODE>mode == DImode")
15805           (const_string "0")
15806           (const_string "*")))
15807    (set_attr "mode" "QI")])
15808
15809 (define_expand "rep_mov"
15810   [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
15811               (set (match_operand 0 "register_operand" "")
15812                    (match_operand 5 "" ""))
15813               (set (match_operand 2 "register_operand" "")
15814                    (match_operand 6 "" ""))
15815               (set (match_operand 1 "memory_operand" "")
15816                    (match_operand 3 "memory_operand" ""))
15817               (use (match_dup 4))])]
15818   ""
15819   "ix86_current_function_needs_cld = 1;")
15820
15821 (define_insn "*rep_movdi_rex64"
15822   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
15823    (set (match_operand:DI 0 "register_operand" "=D")
15824         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
15825                             (const_int 3))
15826                  (match_operand:DI 3 "register_operand" "0")))
15827    (set (match_operand:DI 1 "register_operand" "=S")
15828         (plus:DI (ashift:DI (match_dup 5) (const_int 3))
15829                  (match_operand:DI 4 "register_operand" "1")))
15830    (set (mem:BLK (match_dup 3))
15831         (mem:BLK (match_dup 4)))
15832    (use (match_dup 5))]
15833   "TARGET_64BIT
15834    && !(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15835   "rep{%;} movsq"
15836   [(set_attr "type" "str")
15837    (set_attr "prefix_rep" "1")
15838    (set_attr "memory" "both")
15839    (set_attr "mode" "DI")])
15840
15841 (define_insn "*rep_movsi"
15842   [(set (match_operand:P 2 "register_operand" "=c") (const_int 0))
15843    (set (match_operand:P 0 "register_operand" "=D")
15844         (plus:P (ashift:P (match_operand:P 5 "register_operand" "2")
15845                           (const_int 2))
15846                  (match_operand:P 3 "register_operand" "0")))
15847    (set (match_operand:P 1 "register_operand" "=S")
15848         (plus:P (ashift:P (match_dup 5) (const_int 2))
15849                 (match_operand:P 4 "register_operand" "1")))
15850    (set (mem:BLK (match_dup 3))
15851         (mem:BLK (match_dup 4)))
15852    (use (match_dup 5))]
15853   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15854   "rep{%;} movs{l|d}"
15855   [(set_attr "type" "str")
15856    (set_attr "prefix_rep" "1")
15857    (set_attr "memory" "both")
15858    (set_attr "mode" "SI")])
15859
15860 (define_insn "*rep_movqi"
15861   [(set (match_operand:P 2 "register_operand" "=c") (const_int 0))
15862    (set (match_operand:P 0 "register_operand" "=D")
15863         (plus:P (match_operand:P 3 "register_operand" "0")
15864                 (match_operand:P 5 "register_operand" "2")))
15865    (set (match_operand:P 1 "register_operand" "=S")
15866         (plus:P (match_operand:P 4 "register_operand" "1") (match_dup 5)))
15867    (set (mem:BLK (match_dup 3))
15868         (mem:BLK (match_dup 4)))
15869    (use (match_dup 5))]
15870   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
15871   "rep{%;} movsb"
15872   [(set_attr "type" "str")
15873    (set_attr "prefix_rep" "1")
15874    (set_attr "memory" "both")
15875    (set_attr "mode" "QI")])
15876
15877 (define_expand "setmem<mode>"
15878    [(use (match_operand:BLK 0 "memory_operand" ""))
15879     (use (match_operand:SWI48 1 "nonmemory_operand" ""))
15880     (use (match_operand:QI 2 "nonmemory_operand" ""))
15881     (use (match_operand 3 "const_int_operand" ""))
15882     (use (match_operand:SI 4 "const_int_operand" ""))
15883     (use (match_operand:SI 5 "const_int_operand" ""))]
15884   ""
15885 {
15886  if (ix86_expand_setmem (operands[0], operands[1],
15887                          operands[2], operands[3],
15888                          operands[4], operands[5]))
15889    DONE;
15890  else
15891    FAIL;
15892 })
15893
15894 ;; Most CPUs don't like single string operations
15895 ;; Handle this case here to simplify previous expander.
15896
15897 (define_expand "strset"
15898   [(set (match_operand 1 "memory_operand" "")
15899         (match_operand 2 "register_operand" ""))
15900    (parallel [(set (match_operand 0 "register_operand" "")
15901                    (match_dup 3))
15902               (clobber (reg:CC FLAGS_REG))])]
15903   ""
15904 {
15905   if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
15906     operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
15907
15908   /* If .md ever supports :P for Pmode, this can be directly
15909      in the pattern above.  */
15910   operands[3] = gen_rtx_PLUS (Pmode, operands[0],
15911                               GEN_INT (GET_MODE_SIZE (GET_MODE
15912                                                       (operands[2]))));
15913   /* Can't use this if the user has appropriated eax or edi.  */
15914   if ((TARGET_SINGLE_STRINGOP || optimize_insn_for_size_p ())
15915       && !(fixed_regs[AX_REG] || fixed_regs[DI_REG]))
15916     {
15917       emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
15918                                       operands[3]));
15919       DONE;
15920     }
15921 })
15922
15923 (define_expand "strset_singleop"
15924   [(parallel [(set (match_operand 1 "memory_operand" "")
15925                    (match_operand 2 "register_operand" ""))
15926               (set (match_operand 0 "register_operand" "")
15927                    (match_operand 3 "" ""))])]
15928   ""
15929   "ix86_current_function_needs_cld = 1;")
15930
15931 (define_insn "*strsetdi_rex_1"
15932   [(set (mem:DI (match_operand:DI 1 "register_operand" "0"))
15933         (match_operand:DI 2 "register_operand" "a"))
15934    (set (match_operand:DI 0 "register_operand" "=D")
15935         (plus:DI (match_dup 1)
15936                  (const_int 8)))]
15937   "TARGET_64BIT
15938    && !(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15939   "stosq"
15940   [(set_attr "type" "str")
15941    (set_attr "memory" "store")
15942    (set_attr "mode" "DI")])
15943
15944 (define_insn "*strsetsi_1"
15945   [(set (mem:SI (match_operand:P 1 "register_operand" "0"))
15946         (match_operand:SI 2 "register_operand" "a"))
15947    (set (match_operand:P 0 "register_operand" "=D")
15948         (plus:P (match_dup 1)
15949                 (const_int 4)))]
15950   "!(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15951   "stos{l|d}"
15952   [(set_attr "type" "str")
15953    (set_attr "memory" "store")
15954    (set_attr "mode" "SI")])
15955
15956 (define_insn "*strsethi_1"
15957   [(set (mem:HI (match_operand:P 1 "register_operand" "0"))
15958         (match_operand:HI 2 "register_operand" "a"))
15959    (set (match_operand:P 0 "register_operand" "=D")
15960         (plus:P (match_dup 1)
15961                 (const_int 2)))]
15962   "!(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15963   "stosw"
15964   [(set_attr "type" "str")
15965    (set_attr "memory" "store")
15966    (set_attr "mode" "HI")])
15967
15968 (define_insn "*strsetqi_1"
15969   [(set (mem:QI (match_operand:P 1 "register_operand" "0"))
15970         (match_operand:QI 2 "register_operand" "a"))
15971    (set (match_operand:P 0 "register_operand" "=D")
15972         (plus:P (match_dup 1)
15973                 (const_int 1)))]
15974   "!(fixed_regs[AX_REG] || fixed_regs[DI_REG])"
15975   "stosb"
15976   [(set_attr "type" "str")
15977    (set_attr "memory" "store")
15978    (set (attr "prefix_rex")
15979         (if_then_else
15980           (match_test "<P:MODE>mode == DImode")
15981           (const_string "0")
15982           (const_string "*")))
15983    (set_attr "mode" "QI")])
15984
15985 (define_expand "rep_stos"
15986   [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
15987               (set (match_operand 0 "register_operand" "")
15988                    (match_operand 4 "" ""))
15989               (set (match_operand 2 "memory_operand" "") (const_int 0))
15990               (use (match_operand 3 "register_operand" ""))
15991               (use (match_dup 1))])]
15992   ""
15993   "ix86_current_function_needs_cld = 1;")
15994
15995 (define_insn "*rep_stosdi_rex64"
15996   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
15997    (set (match_operand:DI 0 "register_operand" "=D")
15998         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
15999                             (const_int 3))
16000                  (match_operand:DI 3 "register_operand" "0")))
16001    (set (mem:BLK (match_dup 3))
16002         (const_int 0))
16003    (use (match_operand:DI 2 "register_operand" "a"))
16004    (use (match_dup 4))]
16005   "TARGET_64BIT
16006    && !(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
16007   "rep{%;} stosq"
16008   [(set_attr "type" "str")
16009    (set_attr "prefix_rep" "1")
16010    (set_attr "memory" "store")
16011    (set_attr "mode" "DI")])
16012
16013 (define_insn "*rep_stossi"
16014   [(set (match_operand:P 1 "register_operand" "=c") (const_int 0))
16015    (set (match_operand:P 0 "register_operand" "=D")
16016         (plus:P (ashift:P (match_operand:P 4 "register_operand" "1")
16017                           (const_int 2))
16018                  (match_operand:P 3 "register_operand" "0")))
16019    (set (mem:BLK (match_dup 3))
16020         (const_int 0))
16021    (use (match_operand:SI 2 "register_operand" "a"))
16022    (use (match_dup 4))]
16023   "!(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
16024   "rep{%;} stos{l|d}"
16025   [(set_attr "type" "str")
16026    (set_attr "prefix_rep" "1")
16027    (set_attr "memory" "store")
16028    (set_attr "mode" "SI")])
16029
16030 (define_insn "*rep_stosqi"
16031   [(set (match_operand:P 1 "register_operand" "=c") (const_int 0))
16032    (set (match_operand:P 0 "register_operand" "=D")
16033         (plus:P (match_operand:P 3 "register_operand" "0")
16034                 (match_operand:P 4 "register_operand" "1")))
16035    (set (mem:BLK (match_dup 3))
16036         (const_int 0))
16037    (use (match_operand:QI 2 "register_operand" "a"))
16038    (use (match_dup 4))]
16039   "!(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
16040   "rep{%;} stosb"
16041   [(set_attr "type" "str")
16042    (set_attr "prefix_rep" "1")
16043    (set_attr "memory" "store")
16044    (set (attr "prefix_rex")
16045         (if_then_else
16046           (match_test "<P:MODE>mode == DImode")
16047           (const_string "0")
16048           (const_string "*")))
16049    (set_attr "mode" "QI")])
16050
16051 (define_expand "cmpstrnsi"
16052   [(set (match_operand:SI 0 "register_operand" "")
16053         (compare:SI (match_operand:BLK 1 "general_operand" "")
16054                     (match_operand:BLK 2 "general_operand" "")))
16055    (use (match_operand 3 "general_operand" ""))
16056    (use (match_operand 4 "immediate_operand" ""))]
16057   ""
16058 {
16059   rtx addr1, addr2, out, outlow, count, countreg, align;
16060
16061   if (optimize_insn_for_size_p () && !TARGET_INLINE_ALL_STRINGOPS)
16062     FAIL;
16063
16064   /* Can't use this if the user has appropriated ecx, esi or edi.  */
16065   if (fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])
16066     FAIL;
16067
16068   out = operands[0];
16069   if (!REG_P (out))
16070     out = gen_reg_rtx (SImode);
16071
16072   addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
16073   addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
16074   if (addr1 != XEXP (operands[1], 0))
16075     operands[1] = replace_equiv_address_nv (operands[1], addr1);
16076   if (addr2 != XEXP (operands[2], 0))
16077     operands[2] = replace_equiv_address_nv (operands[2], addr2);
16078
16079   count = operands[3];
16080   countreg = ix86_zero_extend_to_Pmode (count);
16081
16082   /* %%% Iff we are testing strict equality, we can use known alignment
16083      to good advantage.  This may be possible with combine, particularly
16084      once cc0 is dead.  */
16085   align = operands[4];
16086
16087   if (CONST_INT_P (count))
16088     {
16089       if (INTVAL (count) == 0)
16090         {
16091           emit_move_insn (operands[0], const0_rtx);
16092           DONE;
16093         }
16094       emit_insn (gen_cmpstrnqi_nz_1 (addr1, addr2, countreg, align,
16095                                      operands[1], operands[2]));
16096     }
16097   else
16098     {
16099       rtx (*gen_cmp) (rtx, rtx);
16100
16101       gen_cmp = (TARGET_64BIT
16102                  ? gen_cmpdi_1 : gen_cmpsi_1);
16103
16104       emit_insn (gen_cmp (countreg, countreg));
16105       emit_insn (gen_cmpstrnqi_1 (addr1, addr2, countreg, align,
16106                                   operands[1], operands[2]));
16107     }
16108
16109   outlow = gen_lowpart (QImode, out);
16110   emit_insn (gen_cmpintqi (outlow));
16111   emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
16112
16113   if (operands[0] != out)
16114     emit_move_insn (operands[0], out);
16115
16116   DONE;
16117 })
16118
16119 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
16120
16121 (define_expand "cmpintqi"
16122   [(set (match_dup 1)
16123         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
16124    (set (match_dup 2)
16125         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
16126    (parallel [(set (match_operand:QI 0 "register_operand" "")
16127                    (minus:QI (match_dup 1)
16128                              (match_dup 2)))
16129               (clobber (reg:CC FLAGS_REG))])]
16130   ""
16131 {
16132   operands[1] = gen_reg_rtx (QImode);
16133   operands[2] = gen_reg_rtx (QImode);
16134 })
16135
16136 ;; memcmp recognizers.  The `cmpsb' opcode does nothing if the count is
16137 ;; zero.  Emit extra code to make sure that a zero-length compare is EQ.
16138
16139 (define_expand "cmpstrnqi_nz_1"
16140   [(parallel [(set (reg:CC FLAGS_REG)
16141                    (compare:CC (match_operand 4 "memory_operand" "")
16142                                (match_operand 5 "memory_operand" "")))
16143               (use (match_operand 2 "register_operand" ""))
16144               (use (match_operand:SI 3 "immediate_operand" ""))
16145               (clobber (match_operand 0 "register_operand" ""))
16146               (clobber (match_operand 1 "register_operand" ""))
16147               (clobber (match_dup 2))])]
16148   ""
16149   "ix86_current_function_needs_cld = 1;")
16150
16151 (define_insn "*cmpstrnqi_nz_1"
16152   [(set (reg:CC FLAGS_REG)
16153         (compare:CC (mem:BLK (match_operand:P 4 "register_operand" "0"))
16154                     (mem:BLK (match_operand:P 5 "register_operand" "1"))))
16155    (use (match_operand:P 6 "register_operand" "2"))
16156    (use (match_operand:SI 3 "immediate_operand" "i"))
16157    (clobber (match_operand:P 0 "register_operand" "=S"))
16158    (clobber (match_operand:P 1 "register_operand" "=D"))
16159    (clobber (match_operand:P 2 "register_operand" "=c"))]
16160   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
16161   "repz{%;} cmpsb"
16162   [(set_attr "type" "str")
16163    (set_attr "mode" "QI")
16164    (set (attr "prefix_rex")
16165         (if_then_else
16166           (match_test "<P:MODE>mode == DImode")
16167           (const_string "0")
16168           (const_string "*")))
16169    (set_attr "prefix_rep" "1")])
16170
16171 ;; The same, but the count is not known to not be zero.
16172
16173 (define_expand "cmpstrnqi_1"
16174   [(parallel [(set (reg:CC FLAGS_REG)
16175                 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
16176                                      (const_int 0))
16177                   (compare:CC (match_operand 4 "memory_operand" "")
16178                               (match_operand 5 "memory_operand" ""))
16179                   (const_int 0)))
16180               (use (match_operand:SI 3 "immediate_operand" ""))
16181               (use (reg:CC FLAGS_REG))
16182               (clobber (match_operand 0 "register_operand" ""))
16183               (clobber (match_operand 1 "register_operand" ""))
16184               (clobber (match_dup 2))])]
16185   ""
16186   "ix86_current_function_needs_cld = 1;")
16187
16188 (define_insn "*cmpstrnqi_1"
16189   [(set (reg:CC FLAGS_REG)
16190         (if_then_else:CC (ne (match_operand:P 6 "register_operand" "2")
16191                              (const_int 0))
16192           (compare:CC (mem:BLK (match_operand:P 4 "register_operand" "0"))
16193                       (mem:BLK (match_operand:P 5 "register_operand" "1")))
16194           (const_int 0)))
16195    (use (match_operand:SI 3 "immediate_operand" "i"))
16196    (use (reg:CC FLAGS_REG))
16197    (clobber (match_operand:P 0 "register_operand" "=S"))
16198    (clobber (match_operand:P 1 "register_operand" "=D"))
16199    (clobber (match_operand:P 2 "register_operand" "=c"))]
16200   "!(fixed_regs[CX_REG] || fixed_regs[SI_REG] || fixed_regs[DI_REG])"
16201   "repz{%;} cmpsb"
16202   [(set_attr "type" "str")
16203    (set_attr "mode" "QI")
16204    (set (attr "prefix_rex")
16205         (if_then_else
16206           (match_test "<P:MODE>mode == DImode")
16207           (const_string "0")
16208           (const_string "*")))
16209    (set_attr "prefix_rep" "1")])
16210
16211 (define_expand "strlen<mode>"
16212   [(set (match_operand:P 0 "register_operand" "")
16213         (unspec:P [(match_operand:BLK 1 "general_operand" "")
16214                    (match_operand:QI 2 "immediate_operand" "")
16215                    (match_operand 3 "immediate_operand" "")]
16216                   UNSPEC_SCAS))]
16217   ""
16218 {
16219  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
16220    DONE;
16221  else
16222    FAIL;
16223 })
16224
16225 (define_expand "strlenqi_1"
16226   [(parallel [(set (match_operand 0 "register_operand" "")
16227                    (match_operand 2 "" ""))
16228               (clobber (match_operand 1 "register_operand" ""))
16229               (clobber (reg:CC FLAGS_REG))])]
16230   ""
16231   "ix86_current_function_needs_cld = 1;")
16232
16233 (define_insn "*strlenqi_1"
16234   [(set (match_operand:P 0 "register_operand" "=&c")
16235         (unspec:P [(mem:BLK (match_operand:P 5 "register_operand" "1"))
16236                    (match_operand:QI 2 "register_operand" "a")
16237                    (match_operand:P 3 "immediate_operand" "i")
16238                    (match_operand:P 4 "register_operand" "0")] UNSPEC_SCAS))
16239    (clobber (match_operand:P 1 "register_operand" "=D"))
16240    (clobber (reg:CC FLAGS_REG))]
16241   "!(fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])"
16242   "repnz{%;} scasb"
16243   [(set_attr "type" "str")
16244    (set_attr "mode" "QI")
16245    (set (attr "prefix_rex")
16246         (if_then_else
16247           (match_test "<P:MODE>mode == DImode")
16248           (const_string "0")
16249           (const_string "*")))
16250    (set_attr "prefix_rep" "1")])
16251
16252 ;; Peephole optimizations to clean up after cmpstrn*.  This should be
16253 ;; handled in combine, but it is not currently up to the task.
16254 ;; When used for their truth value, the cmpstrn* expanders generate
16255 ;; code like this:
16256 ;;
16257 ;;   repz cmpsb
16258 ;;   seta       %al
16259 ;;   setb       %dl
16260 ;;   cmpb       %al, %dl
16261 ;;   jcc        label
16262 ;;
16263 ;; The intermediate three instructions are unnecessary.
16264
16265 ;; This one handles cmpstrn*_nz_1...
16266 (define_peephole2
16267   [(parallel[
16268      (set (reg:CC FLAGS_REG)
16269           (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
16270                       (mem:BLK (match_operand 5 "register_operand" ""))))
16271      (use (match_operand 6 "register_operand" ""))
16272      (use (match_operand:SI 3 "immediate_operand" ""))
16273      (clobber (match_operand 0 "register_operand" ""))
16274      (clobber (match_operand 1 "register_operand" ""))
16275      (clobber (match_operand 2 "register_operand" ""))])
16276    (set (match_operand:QI 7 "register_operand" "")
16277         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
16278    (set (match_operand:QI 8 "register_operand" "")
16279         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
16280    (set (reg FLAGS_REG)
16281         (compare (match_dup 7) (match_dup 8)))
16282   ]
16283   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
16284   [(parallel[
16285      (set (reg:CC FLAGS_REG)
16286           (compare:CC (mem:BLK (match_dup 4))
16287                       (mem:BLK (match_dup 5))))
16288      (use (match_dup 6))
16289      (use (match_dup 3))
16290      (clobber (match_dup 0))
16291      (clobber (match_dup 1))
16292      (clobber (match_dup 2))])])
16293
16294 ;; ...and this one handles cmpstrn*_1.
16295 (define_peephole2
16296   [(parallel[
16297      (set (reg:CC FLAGS_REG)
16298           (if_then_else:CC (ne (match_operand 6 "register_operand" "")
16299                                (const_int 0))
16300             (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
16301                         (mem:BLK (match_operand 5 "register_operand" "")))
16302             (const_int 0)))
16303      (use (match_operand:SI 3 "immediate_operand" ""))
16304      (use (reg:CC FLAGS_REG))
16305      (clobber (match_operand 0 "register_operand" ""))
16306      (clobber (match_operand 1 "register_operand" ""))
16307      (clobber (match_operand 2 "register_operand" ""))])
16308    (set (match_operand:QI 7 "register_operand" "")
16309         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
16310    (set (match_operand:QI 8 "register_operand" "")
16311         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
16312    (set (reg FLAGS_REG)
16313         (compare (match_dup 7) (match_dup 8)))
16314   ]
16315   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
16316   [(parallel[
16317      (set (reg:CC FLAGS_REG)
16318           (if_then_else:CC (ne (match_dup 6)
16319                                (const_int 0))
16320             (compare:CC (mem:BLK (match_dup 4))
16321                         (mem:BLK (match_dup 5)))
16322             (const_int 0)))
16323      (use (match_dup 3))
16324      (use (reg:CC FLAGS_REG))
16325      (clobber (match_dup 0))
16326      (clobber (match_dup 1))
16327      (clobber (match_dup 2))])])
16328 \f
16329 ;; Conditional move instructions.
16330
16331 (define_expand "mov<mode>cc"
16332   [(set (match_operand:SWIM 0 "register_operand" "")
16333         (if_then_else:SWIM (match_operand 1 "ordered_comparison_operator" "")
16334                            (match_operand:SWIM 2 "<general_operand>" "")
16335                            (match_operand:SWIM 3 "<general_operand>" "")))]
16336   ""
16337   "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
16338
16339 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
16340 ;; the register first winds up with `sbbl $0,reg', which is also weird.
16341 ;; So just document what we're doing explicitly.
16342
16343 (define_expand "x86_mov<mode>cc_0_m1"
16344   [(parallel
16345     [(set (match_operand:SWI48 0 "register_operand" "")
16346           (if_then_else:SWI48
16347             (match_operator:SWI48 2 "ix86_carry_flag_operator"
16348              [(match_operand 1 "flags_reg_operand" "")
16349               (const_int 0)])
16350             (const_int -1)
16351             (const_int 0)))
16352      (clobber (reg:CC FLAGS_REG))])])
16353
16354 (define_insn "*x86_mov<mode>cc_0_m1"
16355   [(set (match_operand:SWI48 0 "register_operand" "=r")
16356         (if_then_else:SWI48 (match_operator 1 "ix86_carry_flag_operator"
16357                              [(reg FLAGS_REG) (const_int 0)])
16358           (const_int -1)
16359           (const_int 0)))
16360    (clobber (reg:CC FLAGS_REG))]
16361   ""
16362   "sbb{<imodesuffix>}\t%0, %0"
16363   ; Since we don't have the proper number of operands for an alu insn,
16364   ; fill in all the blanks.
16365   [(set_attr "type" "alu")
16366    (set_attr "use_carry" "1")
16367    (set_attr "pent_pair" "pu")
16368    (set_attr "memory" "none")
16369    (set_attr "imm_disp" "false")
16370    (set_attr "mode" "<MODE>")
16371    (set_attr "length_immediate" "0")])
16372
16373 (define_insn "*x86_mov<mode>cc_0_m1_se"
16374   [(set (match_operand:SWI48 0 "register_operand" "=r")
16375         (sign_extract:SWI48 (match_operator 1 "ix86_carry_flag_operator"
16376                              [(reg FLAGS_REG) (const_int 0)])
16377                             (const_int 1)
16378                             (const_int 0)))
16379    (clobber (reg:CC FLAGS_REG))]
16380   ""
16381   "sbb{<imodesuffix>}\t%0, %0"
16382   [(set_attr "type" "alu")
16383    (set_attr "use_carry" "1")
16384    (set_attr "pent_pair" "pu")
16385    (set_attr "memory" "none")
16386    (set_attr "imm_disp" "false")
16387    (set_attr "mode" "<MODE>")
16388    (set_attr "length_immediate" "0")])
16389
16390 (define_insn "*x86_mov<mode>cc_0_m1_neg"
16391   [(set (match_operand:SWI48 0 "register_operand" "=r")
16392         (neg:SWI48 (match_operator 1 "ix86_carry_flag_operator"
16393                     [(reg FLAGS_REG) (const_int 0)])))]
16394   ""
16395   "sbb{<imodesuffix>}\t%0, %0"
16396   [(set_attr "type" "alu")
16397    (set_attr "use_carry" "1")
16398    (set_attr "pent_pair" "pu")
16399    (set_attr "memory" "none")
16400    (set_attr "imm_disp" "false")
16401    (set_attr "mode" "<MODE>")
16402    (set_attr "length_immediate" "0")])
16403
16404 (define_insn "*mov<mode>cc_noc"
16405   [(set (match_operand:SWI248 0 "register_operand" "=r,r")
16406         (if_then_else:SWI248 (match_operator 1 "ix86_comparison_operator"
16407                                [(reg FLAGS_REG) (const_int 0)])
16408           (match_operand:SWI248 2 "nonimmediate_operand" "rm,0")
16409           (match_operand:SWI248 3 "nonimmediate_operand" "0,rm")))]
16410   "TARGET_CMOVE && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16411   "@
16412    cmov%O2%C1\t{%2, %0|%0, %2}
16413    cmov%O2%c1\t{%3, %0|%0, %3}"
16414   [(set_attr "type" "icmov")
16415    (set_attr "mode" "<MODE>")])
16416
16417 (define_insn_and_split "*movqicc_noc"
16418   [(set (match_operand:QI 0 "register_operand" "=r,r")
16419         (if_then_else:QI (match_operator 1 "ix86_comparison_operator"
16420                            [(match_operand 4 "flags_reg_operand" "")
16421                             (const_int 0)])
16422                       (match_operand:QI 2 "register_operand" "r,0")
16423                       (match_operand:QI 3 "register_operand" "0,r")))]
16424   "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
16425   "#"
16426   "&& reload_completed"
16427   [(set (match_dup 0)
16428         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
16429                       (match_dup 2)
16430                       (match_dup 3)))]
16431   "operands[0] = gen_lowpart (SImode, operands[0]);
16432    operands[2] = gen_lowpart (SImode, operands[2]);
16433    operands[3] = gen_lowpart (SImode, operands[3]);"
16434   [(set_attr "type" "icmov")
16435    (set_attr "mode" "SI")])
16436
16437 (define_expand "mov<mode>cc"
16438   [(set (match_operand:X87MODEF 0 "register_operand" "")
16439         (if_then_else:X87MODEF
16440           (match_operand 1 "ix86_fp_comparison_operator" "")
16441           (match_operand:X87MODEF 2 "register_operand" "")
16442           (match_operand:X87MODEF 3 "register_operand" "")))]
16443   "(TARGET_80387 && TARGET_CMOVE)
16444    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
16445   "if (ix86_expand_fp_movcc (operands)) DONE; else FAIL;")
16446
16447 (define_insn "*movxfcc_1"
16448   [(set (match_operand:XF 0 "register_operand" "=f,f")
16449         (if_then_else:XF (match_operator 1 "fcmov_comparison_operator"
16450                                 [(reg FLAGS_REG) (const_int 0)])
16451                       (match_operand:XF 2 "register_operand" "f,0")
16452                       (match_operand:XF 3 "register_operand" "0,f")))]
16453   "TARGET_80387 && TARGET_CMOVE"
16454   "@
16455    fcmov%F1\t{%2, %0|%0, %2}
16456    fcmov%f1\t{%3, %0|%0, %3}"
16457   [(set_attr "type" "fcmov")
16458    (set_attr "mode" "XF")])
16459
16460 (define_insn "*movdfcc_1_rex64"
16461   [(set (match_operand:DF 0 "register_operand" "=f,f,r,r")
16462         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
16463                                 [(reg FLAGS_REG) (const_int 0)])
16464                       (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
16465                       (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
16466   "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
16467    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16468   "@
16469    fcmov%F1\t{%2, %0|%0, %2}
16470    fcmov%f1\t{%3, %0|%0, %3}
16471    cmov%O2%C1\t{%2, %0|%0, %2}
16472    cmov%O2%c1\t{%3, %0|%0, %3}"
16473   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
16474    (set_attr "mode" "DF,DF,DI,DI")])
16475
16476 (define_insn "*movdfcc_1"
16477   [(set (match_operand:DF 0 "register_operand" "=f,f,&r,&r")
16478         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
16479                                 [(reg FLAGS_REG) (const_int 0)])
16480                       (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
16481                       (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
16482   "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
16483    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16484   "@
16485    fcmov%F1\t{%2, %0|%0, %2}
16486    fcmov%f1\t{%3, %0|%0, %3}
16487    #
16488    #"
16489   [(set_attr "type" "fcmov,fcmov,multi,multi")
16490    (set_attr "mode" "DF,DF,DI,DI")])
16491
16492 (define_split
16493   [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand" "")
16494         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
16495                                 [(match_operand 4 "flags_reg_operand" "")
16496                                  (const_int 0)])
16497                       (match_operand:DF 2 "nonimmediate_operand" "")
16498                       (match_operand:DF 3 "nonimmediate_operand" "")))]
16499   "!TARGET_64BIT && reload_completed"
16500   [(set (match_dup 2)
16501         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
16502                       (match_dup 5)
16503                       (match_dup 6)))
16504    (set (match_dup 3)
16505         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
16506                       (match_dup 7)
16507                       (match_dup 8)))]
16508 {
16509   split_double_mode (DImode, &operands[2], 2, &operands[5], &operands[7]);
16510   split_double_mode (DImode, &operands[0], 1, &operands[2], &operands[3]);
16511 })
16512
16513 (define_insn "*movsfcc_1_387"
16514   [(set (match_operand:SF 0 "register_operand" "=f,f,r,r")
16515         (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
16516                                 [(reg FLAGS_REG) (const_int 0)])
16517                       (match_operand:SF 2 "nonimmediate_operand" "f,0,rm,0")
16518                       (match_operand:SF 3 "nonimmediate_operand" "0,f,0,rm")))]
16519   "TARGET_80387 && TARGET_CMOVE
16520    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
16521   "@
16522    fcmov%F1\t{%2, %0|%0, %2}
16523    fcmov%f1\t{%3, %0|%0, %3}
16524    cmov%O2%C1\t{%2, %0|%0, %2}
16525    cmov%O2%c1\t{%3, %0|%0, %3}"
16526   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
16527    (set_attr "mode" "SF,SF,SI,SI")])
16528
16529 ;; All moves in XOP pcmov instructions are 128 bits and hence we restrict
16530 ;; the scalar versions to have only XMM registers as operands.
16531
16532 ;; XOP conditional move
16533 (define_insn "*xop_pcmov_<mode>"
16534   [(set (match_operand:MODEF 0 "register_operand" "=x")
16535         (if_then_else:MODEF
16536           (match_operand:MODEF 1 "register_operand" "x")
16537           (match_operand:MODEF 2 "register_operand" "x")
16538           (match_operand:MODEF 3 "register_operand" "x")))]
16539   "TARGET_XOP"
16540   "vpcmov\t{%1, %3, %2, %0|%0, %2, %3, %1}"
16541   [(set_attr "type" "sse4arg")])
16542
16543 ;; These versions of the min/max patterns are intentionally ignorant of
16544 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
16545 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
16546 ;; are undefined in this condition, we're certain this is correct.
16547
16548 (define_insn "<code><mode>3"
16549   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
16550         (smaxmin:MODEF
16551           (match_operand:MODEF 1 "nonimmediate_operand" "%0,x")
16552           (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")))]
16553   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16554   "@
16555    <maxmin_float><ssemodesuffix>\t{%2, %0|%0, %2}
16556    v<maxmin_float><ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
16557   [(set_attr "isa" "noavx,avx")
16558    (set_attr "prefix" "orig,vex")
16559    (set_attr "type" "sseadd")
16560    (set_attr "mode" "<MODE>")])
16561
16562 ;; These versions of the min/max patterns implement exactly the operations
16563 ;;   min = (op1 < op2 ? op1 : op2)
16564 ;;   max = (!(op1 < op2) ? op1 : op2)
16565 ;; Their operands are not commutative, and thus they may be used in the
16566 ;; presence of -0.0 and NaN.
16567
16568 (define_insn "*ieee_smin<mode>3"
16569   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
16570         (unspec:MODEF
16571           [(match_operand:MODEF 1 "register_operand" "0,x")
16572            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]
16573          UNSPEC_IEEE_MIN))]
16574   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16575   "@
16576    min<ssemodesuffix>\t{%2, %0|%0, %2}
16577    vmin<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
16578   [(set_attr "isa" "noavx,avx")
16579    (set_attr "prefix" "orig,vex")
16580    (set_attr "type" "sseadd")
16581    (set_attr "mode" "<MODE>")])
16582
16583 (define_insn "*ieee_smax<mode>3"
16584   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
16585         (unspec:MODEF
16586           [(match_operand:MODEF 1 "register_operand" "0,x")
16587            (match_operand:MODEF 2 "nonimmediate_operand" "xm,xm")]
16588          UNSPEC_IEEE_MAX))]
16589   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16590   "@
16591    max<ssemodesuffix>\t{%2, %0|%0, %2}
16592    vmax<ssemodesuffix>\t{%2, %1, %0|%0, %1, %2}"
16593   [(set_attr "isa" "noavx,avx")
16594    (set_attr "prefix" "orig,vex")
16595    (set_attr "type" "sseadd")
16596    (set_attr "mode" "<MODE>")])
16597
16598 ;; Make two stack loads independent:
16599 ;;   fld aa              fld aa
16600 ;;   fld %st(0)     ->   fld bb
16601 ;;   fmul bb             fmul %st(1), %st
16602 ;;
16603 ;; Actually we only match the last two instructions for simplicity.
16604 (define_peephole2
16605   [(set (match_operand 0 "fp_register_operand" "")
16606         (match_operand 1 "fp_register_operand" ""))
16607    (set (match_dup 0)
16608         (match_operator 2 "binary_fp_operator"
16609            [(match_dup 0)
16610             (match_operand 3 "memory_operand" "")]))]
16611   "REGNO (operands[0]) != REGNO (operands[1])"
16612   [(set (match_dup 0) (match_dup 3))
16613    (set (match_dup 0) (match_dup 4))]
16614
16615   ;; The % modifier is not operational anymore in peephole2's, so we have to
16616   ;; swap the operands manually in the case of addition and multiplication.
16617   "if (COMMUTATIVE_ARITH_P (operands[2]))
16618      operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]),
16619                                    GET_MODE (operands[2]),
16620                                    operands[0], operands[1]);
16621    else
16622      operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]),
16623                                    GET_MODE (operands[2]),
16624                                    operands[1], operands[0]);")
16625
16626 ;; Conditional addition patterns
16627 (define_expand "add<mode>cc"
16628   [(match_operand:SWI 0 "register_operand" "")
16629    (match_operand 1 "ordered_comparison_operator" "")
16630    (match_operand:SWI 2 "register_operand" "")
16631    (match_operand:SWI 3 "const_int_operand" "")]
16632   ""
16633   "if (ix86_expand_int_addcc (operands)) DONE; else FAIL;")
16634 \f
16635 ;; Misc patterns (?)
16636
16637 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
16638 ;; Otherwise there will be nothing to keep
16639 ;;
16640 ;; [(set (reg ebp) (reg esp))]
16641 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
16642 ;;  (clobber (eflags)]
16643 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
16644 ;;
16645 ;; in proper program order.
16646
16647 (define_insn "pro_epilogue_adjust_stack_<mode>_add"
16648   [(set (match_operand:P 0 "register_operand" "=r,r")
16649         (plus:P (match_operand:P 1 "register_operand" "0,r")
16650                 (match_operand:P 2 "<nonmemory_operand>" "r<i>,l<i>")))
16651    (clobber (reg:CC FLAGS_REG))
16652    (clobber (mem:BLK (scratch)))]
16653   ""
16654 {
16655   switch (get_attr_type (insn))
16656     {
16657     case TYPE_IMOV:
16658       return "mov{<imodesuffix>}\t{%1, %0|%0, %1}";
16659
16660     case TYPE_ALU:
16661       gcc_assert (rtx_equal_p (operands[0], operands[1]));
16662       if (x86_maybe_negate_const_int (&operands[2], <MODE>mode))
16663         return "sub{<imodesuffix>}\t{%2, %0|%0, %2}";
16664
16665       return "add{<imodesuffix>}\t{%2, %0|%0, %2}";
16666
16667     default:
16668       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
16669       return "lea{<imodesuffix>}\t{%a2, %0|%0, %a2}";
16670     }
16671 }
16672   [(set (attr "type")
16673         (cond [(and (eq_attr "alternative" "0")
16674                     (not (match_test "TARGET_OPT_AGU")))
16675                  (const_string "alu")
16676                (match_operand:<MODE> 2 "const0_operand" "")
16677                  (const_string "imov")
16678               ]
16679               (const_string "lea")))
16680    (set (attr "length_immediate")
16681         (cond [(eq_attr "type" "imov")
16682                  (const_string "0")
16683                (and (eq_attr "type" "alu")
16684                     (match_operand 2 "const128_operand" ""))
16685                  (const_string "1")
16686               ]
16687               (const_string "*")))
16688    (set_attr "mode" "<MODE>")])
16689
16690 (define_insn "pro_epilogue_adjust_stack_<mode>_sub"
16691   [(set (match_operand:P 0 "register_operand" "=r")
16692         (minus:P (match_operand:P 1 "register_operand" "0")
16693                  (match_operand:P 2 "register_operand" "r")))
16694    (clobber (reg:CC FLAGS_REG))
16695    (clobber (mem:BLK (scratch)))]
16696   ""
16697   "sub{<imodesuffix>}\t{%2, %0|%0, %2}"
16698   [(set_attr "type" "alu")
16699    (set_attr "mode" "<MODE>")])
16700
16701 (define_insn "allocate_stack_worker_probe_<mode>"
16702   [(set (match_operand:P 0 "register_operand" "=a")
16703         (unspec_volatile:P [(match_operand:P 1 "register_operand" "0")]
16704                             UNSPECV_STACK_PROBE))
16705    (clobber (reg:CC FLAGS_REG))]
16706   "ix86_target_stack_probe ()"
16707   "call\t___chkstk_ms"
16708   [(set_attr "type" "multi")
16709    (set_attr "length" "5")])
16710
16711 (define_expand "allocate_stack"
16712   [(match_operand 0 "register_operand" "")
16713    (match_operand 1 "general_operand" "")]
16714   "ix86_target_stack_probe ()"
16715 {
16716   rtx x;
16717
16718 #ifndef CHECK_STACK_LIMIT
16719 #define CHECK_STACK_LIMIT 0
16720 #endif
16721
16722   if (CHECK_STACK_LIMIT && CONST_INT_P (operands[1])
16723       && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
16724     {
16725       x = expand_simple_binop (Pmode, MINUS, stack_pointer_rtx, operands[1],
16726                                stack_pointer_rtx, 0, OPTAB_DIRECT);
16727       if (x != stack_pointer_rtx)
16728         emit_move_insn (stack_pointer_rtx, x);
16729     }
16730   else
16731     {
16732       x = copy_to_mode_reg (Pmode, operands[1]);
16733       if (TARGET_64BIT)
16734         emit_insn (gen_allocate_stack_worker_probe_di (x, x));
16735       else
16736         emit_insn (gen_allocate_stack_worker_probe_si (x, x));
16737       x = expand_simple_binop (Pmode, MINUS, stack_pointer_rtx, x,
16738                                stack_pointer_rtx, 0, OPTAB_DIRECT);
16739       if (x != stack_pointer_rtx)
16740         emit_move_insn (stack_pointer_rtx, x);
16741     }
16742
16743   emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
16744   DONE;
16745 })
16746
16747 ;; Use IOR for stack probes, this is shorter.
16748 (define_expand "probe_stack"
16749   [(match_operand 0 "memory_operand" "")]
16750   ""
16751 {
16752   rtx (*gen_ior3) (rtx, rtx, rtx);
16753
16754   gen_ior3 = (GET_MODE (operands[0]) == DImode
16755               ? gen_iordi3 : gen_iorsi3);
16756
16757   emit_insn (gen_ior3 (operands[0], operands[0], const0_rtx));
16758   DONE;
16759 })
16760
16761 (define_insn "adjust_stack_and_probe<mode>"
16762   [(set (match_operand:P 0 "register_operand" "=r")
16763         (unspec_volatile:P [(match_operand:P 1 "register_operand" "0")]
16764                             UNSPECV_PROBE_STACK_RANGE))
16765    (set (reg:P SP_REG)
16766         (minus:P (reg:P SP_REG) (match_operand:P 2 "const_int_operand" "n")))
16767    (clobber (reg:CC FLAGS_REG))
16768    (clobber (mem:BLK (scratch)))]
16769   ""
16770   "* return output_adjust_stack_and_probe (operands[0]);"
16771   [(set_attr "type" "multi")])
16772
16773 (define_insn "probe_stack_range<mode>"
16774   [(set (match_operand:P 0 "register_operand" "=r")
16775         (unspec_volatile:P [(match_operand:P 1 "register_operand" "0")
16776                             (match_operand:P 2 "const_int_operand" "n")]
16777                             UNSPECV_PROBE_STACK_RANGE))
16778    (clobber (reg:CC FLAGS_REG))]
16779   ""
16780   "* return output_probe_stack_range (operands[0], operands[2]);"
16781   [(set_attr "type" "multi")])
16782
16783 (define_expand "builtin_setjmp_receiver"
16784   [(label_ref (match_operand 0 "" ""))]
16785   "!TARGET_64BIT && flag_pic"
16786 {
16787 #if TARGET_MACHO
16788   if (TARGET_MACHO)
16789     {
16790       rtx xops[3];
16791       rtx picreg = gen_rtx_REG (Pmode, PIC_OFFSET_TABLE_REGNUM);
16792       rtx label_rtx = gen_label_rtx ();
16793       emit_insn (gen_set_got_labelled (pic_offset_table_rtx, label_rtx));
16794       xops[0] = xops[1] = picreg;
16795       xops[2] = machopic_gen_offset (gen_rtx_LABEL_REF (SImode, label_rtx));
16796       ix86_expand_binary_operator (MINUS, SImode, xops);
16797     }
16798   else
16799 #endif
16800     emit_insn (gen_set_got (pic_offset_table_rtx));
16801   DONE;
16802 })
16803 \f
16804 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
16805
16806 (define_split
16807   [(set (match_operand 0 "register_operand" "")
16808         (match_operator 3 "promotable_binary_operator"
16809            [(match_operand 1 "register_operand" "")
16810             (match_operand 2 "aligned_operand" "")]))
16811    (clobber (reg:CC FLAGS_REG))]
16812   "! TARGET_PARTIAL_REG_STALL && reload_completed
16813    && ((GET_MODE (operands[0]) == HImode
16814         && ((optimize_function_for_speed_p (cfun) && !TARGET_FAST_PREFIX)
16815             /* ??? next two lines just !satisfies_constraint_K (...) */
16816             || !CONST_INT_P (operands[2])
16817             || satisfies_constraint_K (operands[2])))
16818        || (GET_MODE (operands[0]) == QImode
16819            && (TARGET_PROMOTE_QImode || optimize_function_for_size_p (cfun))))"
16820   [(parallel [(set (match_dup 0)
16821                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
16822               (clobber (reg:CC FLAGS_REG))])]
16823   "operands[0] = gen_lowpart (SImode, operands[0]);
16824    operands[1] = gen_lowpart (SImode, operands[1]);
16825    if (GET_CODE (operands[3]) != ASHIFT)
16826      operands[2] = gen_lowpart (SImode, operands[2]);
16827    PUT_MODE (operands[3], SImode);")
16828
16829 ; Promote the QImode tests, as i386 has encoding of the AND
16830 ; instruction with 32-bit sign-extended immediate and thus the
16831 ; instruction size is unchanged, except in the %eax case for
16832 ; which it is increased by one byte, hence the ! optimize_size.
16833 (define_split
16834   [(set (match_operand 0 "flags_reg_operand" "")
16835         (match_operator 2 "compare_operator"
16836           [(and (match_operand 3 "aligned_operand" "")
16837                 (match_operand 4 "const_int_operand" ""))
16838            (const_int 0)]))
16839    (set (match_operand 1 "register_operand" "")
16840         (and (match_dup 3) (match_dup 4)))]
16841   "! TARGET_PARTIAL_REG_STALL && reload_completed
16842    && optimize_insn_for_speed_p ()
16843    && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
16844        || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))
16845    /* Ensure that the operand will remain sign-extended immediate.  */
16846    && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)"
16847   [(parallel [(set (match_dup 0)
16848                    (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
16849                                     (const_int 0)]))
16850               (set (match_dup 1)
16851                    (and:SI (match_dup 3) (match_dup 4)))])]
16852 {
16853   operands[4]
16854     = gen_int_mode (INTVAL (operands[4])
16855                     & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
16856   operands[1] = gen_lowpart (SImode, operands[1]);
16857   operands[3] = gen_lowpart (SImode, operands[3]);
16858 })
16859
16860 ; Don't promote the QImode tests, as i386 doesn't have encoding of
16861 ; the TEST instruction with 32-bit sign-extended immediate and thus
16862 ; the instruction size would at least double, which is not what we
16863 ; want even with ! optimize_size.
16864 (define_split
16865   [(set (match_operand 0 "flags_reg_operand" "")
16866         (match_operator 1 "compare_operator"
16867           [(and (match_operand:HI 2 "aligned_operand" "")
16868                 (match_operand:HI 3 "const_int_operand" ""))
16869            (const_int 0)]))]
16870   "! TARGET_PARTIAL_REG_STALL && reload_completed
16871    && ! TARGET_FAST_PREFIX
16872    && optimize_insn_for_speed_p ()
16873    /* Ensure that the operand will remain sign-extended immediate.  */
16874    && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)"
16875   [(set (match_dup 0)
16876         (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
16877                          (const_int 0)]))]
16878 {
16879   operands[3]
16880     = gen_int_mode (INTVAL (operands[3])
16881                     & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
16882   operands[2] = gen_lowpart (SImode, operands[2]);
16883 })
16884
16885 (define_split
16886   [(set (match_operand 0 "register_operand" "")
16887         (neg (match_operand 1 "register_operand" "")))
16888    (clobber (reg:CC FLAGS_REG))]
16889   "! TARGET_PARTIAL_REG_STALL && reload_completed
16890    && (GET_MODE (operands[0]) == HImode
16891        || (GET_MODE (operands[0]) == QImode
16892            && (TARGET_PROMOTE_QImode
16893                || optimize_insn_for_size_p ())))"
16894   [(parallel [(set (match_dup 0)
16895                    (neg:SI (match_dup 1)))
16896               (clobber (reg:CC FLAGS_REG))])]
16897   "operands[0] = gen_lowpart (SImode, operands[0]);
16898    operands[1] = gen_lowpart (SImode, operands[1]);")
16899
16900 (define_split
16901   [(set (match_operand 0 "register_operand" "")
16902         (not (match_operand 1 "register_operand" "")))]
16903   "! TARGET_PARTIAL_REG_STALL && reload_completed
16904    && (GET_MODE (operands[0]) == HImode
16905        || (GET_MODE (operands[0]) == QImode
16906            && (TARGET_PROMOTE_QImode
16907                || optimize_insn_for_size_p ())))"
16908   [(set (match_dup 0)
16909         (not:SI (match_dup 1)))]
16910   "operands[0] = gen_lowpart (SImode, operands[0]);
16911    operands[1] = gen_lowpart (SImode, operands[1]);")
16912
16913 (define_split
16914   [(set (match_operand 0 "register_operand" "")
16915         (if_then_else (match_operator 1 "ordered_comparison_operator"
16916                                 [(reg FLAGS_REG) (const_int 0)])
16917                       (match_operand 2 "register_operand" "")
16918                       (match_operand 3 "register_operand" "")))]
16919   "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE
16920    && (GET_MODE (operands[0]) == HImode
16921        || (GET_MODE (operands[0]) == QImode
16922            && (TARGET_PROMOTE_QImode
16923                || optimize_insn_for_size_p ())))"
16924   [(set (match_dup 0)
16925         (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
16926   "operands[0] = gen_lowpart (SImode, operands[0]);
16927    operands[2] = gen_lowpart (SImode, operands[2]);
16928    operands[3] = gen_lowpart (SImode, operands[3]);")
16929 \f
16930 ;; RTL Peephole optimizations, run before sched2.  These primarily look to
16931 ;; transform a complex memory operation into two memory to register operations.
16932
16933 ;; Don't push memory operands
16934 (define_peephole2
16935   [(set (match_operand:SWI 0 "push_operand" "")
16936         (match_operand:SWI 1 "memory_operand" ""))
16937    (match_scratch:SWI 2 "<r>")]
16938   "!(TARGET_PUSH_MEMORY || optimize_insn_for_size_p ())
16939    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
16940   [(set (match_dup 2) (match_dup 1))
16941    (set (match_dup 0) (match_dup 2))])
16942
16943 ;; We need to handle SFmode only, because DFmode and XFmode are split to
16944 ;; SImode pushes.
16945 (define_peephole2
16946   [(set (match_operand:SF 0 "push_operand" "")
16947         (match_operand:SF 1 "memory_operand" ""))
16948    (match_scratch:SF 2 "r")]
16949   "!(TARGET_PUSH_MEMORY || optimize_insn_for_size_p ())
16950    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
16951   [(set (match_dup 2) (match_dup 1))
16952    (set (match_dup 0) (match_dup 2))])
16953
16954 ;; Don't move an immediate directly to memory when the instruction
16955 ;; gets too big.
16956 (define_peephole2
16957   [(match_scratch:SWI124 1 "<r>")
16958    (set (match_operand:SWI124 0 "memory_operand" "")
16959         (const_int 0))]
16960   "optimize_insn_for_speed_p ()
16961    && !TARGET_USE_MOV0
16962    && TARGET_SPLIT_LONG_MOVES
16963    && get_attr_length (insn) >= ix86_cur_cost ()->large_insn
16964    && peep2_regno_dead_p (0, FLAGS_REG)"
16965   [(parallel [(set (match_dup 2) (const_int 0))
16966               (clobber (reg:CC FLAGS_REG))])
16967    (set (match_dup 0) (match_dup 1))]
16968   "operands[2] = gen_lowpart (SImode, operands[1]);")
16969
16970 (define_peephole2
16971   [(match_scratch:SWI124 2 "<r>")
16972    (set (match_operand:SWI124 0 "memory_operand" "")
16973         (match_operand:SWI124 1 "immediate_operand" ""))]
16974   "optimize_insn_for_speed_p ()
16975    && TARGET_SPLIT_LONG_MOVES
16976    && get_attr_length (insn) >= ix86_cur_cost ()->large_insn"
16977   [(set (match_dup 2) (match_dup 1))
16978    (set (match_dup 0) (match_dup 2))])
16979
16980 ;; Don't compare memory with zero, load and use a test instead.
16981 (define_peephole2
16982   [(set (match_operand 0 "flags_reg_operand" "")
16983         (match_operator 1 "compare_operator"
16984           [(match_operand:SI 2 "memory_operand" "")
16985            (const_int 0)]))
16986    (match_scratch:SI 3 "r")]
16987   "optimize_insn_for_speed_p () && ix86_match_ccmode (insn, CCNOmode)"
16988   [(set (match_dup 3) (match_dup 2))
16989    (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))])
16990
16991 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer.
16992 ;; Don't split NOTs with a displacement operand, because resulting XOR
16993 ;; will not be pairable anyway.
16994 ;;
16995 ;; On AMD K6, NOT is vector decoded with memory operand that cannot be
16996 ;; represented using a modRM byte.  The XOR replacement is long decoded,
16997 ;; so this split helps here as well.
16998 ;;
16999 ;; Note: Can't do this as a regular split because we can't get proper
17000 ;; lifetime information then.
17001
17002 (define_peephole2
17003   [(set (match_operand:SWI124 0 "nonimmediate_operand" "")
17004         (not:SWI124 (match_operand:SWI124 1 "nonimmediate_operand" "")))]
17005   "optimize_insn_for_speed_p ()
17006    && ((TARGET_NOT_UNPAIRABLE
17007         && (!MEM_P (operands[0])
17008             || !memory_displacement_operand (operands[0], <MODE>mode)))
17009        || (TARGET_NOT_VECTORMODE
17010            && long_memory_operand (operands[0], <MODE>mode)))
17011    && peep2_regno_dead_p (0, FLAGS_REG)"
17012   [(parallel [(set (match_dup 0)
17013                    (xor:SWI124 (match_dup 1) (const_int -1)))
17014               (clobber (reg:CC FLAGS_REG))])])
17015
17016 ;; Non pairable "test imm, reg" instructions can be translated to
17017 ;; "and imm, reg" if reg dies.  The "and" form is also shorter (one
17018 ;; byte opcode instead of two, have a short form for byte operands),
17019 ;; so do it for other CPUs as well.  Given that the value was dead,
17020 ;; this should not create any new dependencies.  Pass on the sub-word
17021 ;; versions if we're concerned about partial register stalls.
17022
17023 (define_peephole2
17024   [(set (match_operand 0 "flags_reg_operand" "")
17025         (match_operator 1 "compare_operator"
17026           [(and:SI (match_operand:SI 2 "register_operand" "")
17027                    (match_operand:SI 3 "immediate_operand" ""))
17028            (const_int 0)]))]
17029   "ix86_match_ccmode (insn, CCNOmode)
17030    && (true_regnum (operands[2]) != AX_REG
17031        || satisfies_constraint_K (operands[3]))
17032    && peep2_reg_dead_p (1, operands[2])"
17033   [(parallel
17034      [(set (match_dup 0)
17035            (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
17036                             (const_int 0)]))
17037       (set (match_dup 2)
17038            (and:SI (match_dup 2) (match_dup 3)))])])
17039
17040 ;; We don't need to handle HImode case, because it will be promoted to SImode
17041 ;; on ! TARGET_PARTIAL_REG_STALL
17042
17043 (define_peephole2
17044   [(set (match_operand 0 "flags_reg_operand" "")
17045         (match_operator 1 "compare_operator"
17046           [(and:QI (match_operand:QI 2 "register_operand" "")
17047                    (match_operand:QI 3 "immediate_operand" ""))
17048            (const_int 0)]))]
17049   "! TARGET_PARTIAL_REG_STALL
17050    && ix86_match_ccmode (insn, CCNOmode)
17051    && true_regnum (operands[2]) != AX_REG
17052    && peep2_reg_dead_p (1, operands[2])"
17053   [(parallel
17054      [(set (match_dup 0)
17055            (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
17056                             (const_int 0)]))
17057       (set (match_dup 2)
17058            (and:QI (match_dup 2) (match_dup 3)))])])
17059
17060 (define_peephole2
17061   [(set (match_operand 0 "flags_reg_operand" "")
17062         (match_operator 1 "compare_operator"
17063           [(and:SI
17064              (zero_extract:SI
17065                (match_operand 2 "ext_register_operand" "")
17066                (const_int 8)
17067                (const_int 8))
17068              (match_operand 3 "const_int_operand" ""))
17069            (const_int 0)]))]
17070   "! TARGET_PARTIAL_REG_STALL
17071    && ix86_match_ccmode (insn, CCNOmode)
17072    && true_regnum (operands[2]) != AX_REG
17073    && peep2_reg_dead_p (1, operands[2])"
17074   [(parallel [(set (match_dup 0)
17075                    (match_op_dup 1
17076                      [(and:SI
17077                         (zero_extract:SI
17078                           (match_dup 2)
17079                           (const_int 8)
17080                           (const_int 8))
17081                         (match_dup 3))
17082                       (const_int 0)]))
17083               (set (zero_extract:SI (match_dup 2)
17084                                     (const_int 8)
17085                                     (const_int 8))
17086                    (and:SI
17087                      (zero_extract:SI
17088                        (match_dup 2)
17089                        (const_int 8)
17090                        (const_int 8))
17091                      (match_dup 3)))])])
17092
17093 ;; Don't do logical operations with memory inputs.
17094 (define_peephole2
17095   [(match_scratch:SI 2 "r")
17096    (parallel [(set (match_operand:SI 0 "register_operand" "")
17097                    (match_operator:SI 3 "arith_or_logical_operator"
17098                      [(match_dup 0)
17099                       (match_operand:SI 1 "memory_operand" "")]))
17100               (clobber (reg:CC FLAGS_REG))])]
17101   "!(TARGET_READ_MODIFY || optimize_insn_for_size_p ())"
17102   [(set (match_dup 2) (match_dup 1))
17103    (parallel [(set (match_dup 0)
17104                    (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
17105               (clobber (reg:CC FLAGS_REG))])])
17106
17107 (define_peephole2
17108   [(match_scratch:SI 2 "r")
17109    (parallel [(set (match_operand:SI 0 "register_operand" "")
17110                    (match_operator:SI 3 "arith_or_logical_operator"
17111                      [(match_operand:SI 1 "memory_operand" "")
17112                       (match_dup 0)]))
17113               (clobber (reg:CC FLAGS_REG))])]
17114   "!(TARGET_READ_MODIFY || optimize_insn_for_size_p ())"
17115   [(set (match_dup 2) (match_dup 1))
17116    (parallel [(set (match_dup 0)
17117                    (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
17118               (clobber (reg:CC FLAGS_REG))])])
17119
17120 ;; Prefer Load+RegOp to Mov+MemOp.  Watch out for cases when the memory address
17121 ;; refers to the destination of the load!
17122
17123 (define_peephole2
17124   [(set (match_operand:SI 0 "register_operand" "")
17125         (match_operand:SI 1 "register_operand" ""))
17126    (parallel [(set (match_dup 0)
17127                    (match_operator:SI 3 "commutative_operator"
17128                      [(match_dup 0)
17129                       (match_operand:SI 2 "memory_operand" "")]))
17130               (clobber (reg:CC FLAGS_REG))])]
17131   "REGNO (operands[0]) != REGNO (operands[1])
17132    && GENERAL_REGNO_P (REGNO (operands[0]))
17133    && GENERAL_REGNO_P (REGNO (operands[1]))"
17134   [(set (match_dup 0) (match_dup 4))
17135    (parallel [(set (match_dup 0)
17136                    (match_op_dup 3 [(match_dup 0) (match_dup 1)]))
17137               (clobber (reg:CC FLAGS_REG))])]
17138   "operands[4] = replace_rtx (operands[2], operands[0], operands[1]);")
17139
17140 (define_peephole2
17141   [(set (match_operand 0 "register_operand" "")
17142         (match_operand 1 "register_operand" ""))
17143    (set (match_dup 0)
17144                    (match_operator 3 "commutative_operator"
17145                      [(match_dup 0)
17146                       (match_operand 2 "memory_operand" "")]))]
17147   "REGNO (operands[0]) != REGNO (operands[1])
17148    && ((MMX_REG_P (operands[0]) && MMX_REG_P (operands[1])) 
17149        || (SSE_REG_P (operands[0]) && SSE_REG_P (operands[1])))"
17150   [(set (match_dup 0) (match_dup 2))
17151    (set (match_dup 0)
17152         (match_op_dup 3 [(match_dup 0) (match_dup 1)]))])
17153
17154 ; Don't do logical operations with memory outputs
17155 ;
17156 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
17157 ; instruction into two 1-uop insns plus a 2-uop insn.  That last has
17158 ; the same decoder scheduling characteristics as the original.
17159
17160 (define_peephole2
17161   [(match_scratch:SI 2 "r")
17162    (parallel [(set (match_operand:SI 0 "memory_operand" "")
17163                    (match_operator:SI 3 "arith_or_logical_operator"
17164                      [(match_dup 0)
17165                       (match_operand:SI 1 "nonmemory_operand" "")]))
17166               (clobber (reg:CC FLAGS_REG))])]
17167   "!(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17168    /* Do not split stack checking probes.  */
17169    && GET_CODE (operands[3]) != IOR && operands[1] != const0_rtx"
17170   [(set (match_dup 2) (match_dup 0))
17171    (parallel [(set (match_dup 2)
17172                    (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
17173               (clobber (reg:CC FLAGS_REG))])
17174    (set (match_dup 0) (match_dup 2))])
17175
17176 (define_peephole2
17177   [(match_scratch:SI 2 "r")
17178    (parallel [(set (match_operand:SI 0 "memory_operand" "")
17179                    (match_operator:SI 3 "arith_or_logical_operator"
17180                      [(match_operand:SI 1 "nonmemory_operand" "")
17181                       (match_dup 0)]))
17182               (clobber (reg:CC FLAGS_REG))])]
17183   "!(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17184    /* Do not split stack checking probes.  */
17185    && GET_CODE (operands[3]) != IOR && operands[1] != const0_rtx"
17186   [(set (match_dup 2) (match_dup 0))
17187    (parallel [(set (match_dup 2)
17188                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
17189               (clobber (reg:CC FLAGS_REG))])
17190    (set (match_dup 0) (match_dup 2))])
17191
17192 ;; Attempt to use arith or logical operations with memory outputs with
17193 ;; setting of flags.
17194 (define_peephole2
17195   [(set (match_operand:SWI 0 "register_operand" "")
17196         (match_operand:SWI 1 "memory_operand" ""))
17197    (parallel [(set (match_dup 0)
17198                    (match_operator:SWI 3 "plusminuslogic_operator"
17199                      [(match_dup 0)
17200                       (match_operand:SWI 2 "<nonmemory_operand>" "")]))
17201               (clobber (reg:CC FLAGS_REG))])
17202    (set (match_dup 1) (match_dup 0))
17203    (set (reg FLAGS_REG) (compare (match_dup 0) (const_int 0)))]
17204   "(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17205    && peep2_reg_dead_p (4, operands[0])
17206    && !reg_overlap_mentioned_p (operands[0], operands[1])
17207    && ix86_match_ccmode (peep2_next_insn (3),
17208                          (GET_CODE (operands[3]) == PLUS
17209                           || GET_CODE (operands[3]) == MINUS)
17210                          ? CCGOCmode : CCNOmode)"
17211   [(parallel [(set (match_dup 4) (match_dup 5))
17212               (set (match_dup 1) (match_op_dup 3 [(match_dup 1)
17213                                                   (match_dup 2)]))])]
17214   "operands[4] = SET_DEST (PATTERN (peep2_next_insn (3)));
17215    operands[5] = gen_rtx_fmt_ee (GET_CODE (operands[3]), <MODE>mode,
17216                                  copy_rtx (operands[1]),
17217                                  copy_rtx (operands[2]));
17218    operands[5] = gen_rtx_COMPARE (GET_MODE (operands[4]),
17219                                   operands[5], const0_rtx);")
17220
17221 (define_peephole2
17222   [(parallel [(set (match_operand:SWI 0 "register_operand" "")
17223                    (match_operator:SWI 2 "plusminuslogic_operator"
17224                      [(match_dup 0)
17225                       (match_operand:SWI 1 "memory_operand" "")]))
17226               (clobber (reg:CC FLAGS_REG))])
17227    (set (match_dup 1) (match_dup 0))
17228    (set (reg FLAGS_REG) (compare (match_dup 0) (const_int 0)))]
17229   "(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17230    && GET_CODE (operands[2]) != MINUS
17231    && peep2_reg_dead_p (3, operands[0])
17232    && !reg_overlap_mentioned_p (operands[0], operands[1])
17233    && ix86_match_ccmode (peep2_next_insn (2),
17234                          GET_CODE (operands[2]) == PLUS
17235                          ? CCGOCmode : CCNOmode)"
17236   [(parallel [(set (match_dup 3) (match_dup 4))
17237               (set (match_dup 1) (match_op_dup 2 [(match_dup 1)
17238                                                   (match_dup 0)]))])]
17239   "operands[3] = SET_DEST (PATTERN (peep2_next_insn (2)));
17240    operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), <MODE>mode,
17241                                  copy_rtx (operands[1]),
17242                                  copy_rtx (operands[0]));
17243    operands[4] = gen_rtx_COMPARE (GET_MODE (operands[3]),
17244                                   operands[4], const0_rtx);")
17245
17246 (define_peephole2
17247   [(set (match_operand:SWI12 0 "register_operand" "")
17248         (match_operand:SWI12 1 "memory_operand" ""))
17249    (parallel [(set (match_operand:SI 4 "register_operand" "")
17250                    (match_operator:SI 3 "plusminuslogic_operator"
17251                      [(match_dup 4)
17252                       (match_operand:SI 2 "nonmemory_operand" "")]))
17253               (clobber (reg:CC FLAGS_REG))])
17254    (set (match_dup 1) (match_dup 0))
17255    (set (reg FLAGS_REG) (compare (match_dup 0) (const_int 0)))]
17256   "(TARGET_READ_MODIFY_WRITE || optimize_insn_for_size_p ())
17257    && REG_P (operands[0]) && REG_P (operands[4])
17258    && REGNO (operands[0]) == REGNO (operands[4])
17259    && peep2_reg_dead_p (4, operands[0])
17260    && !reg_overlap_mentioned_p (operands[0], operands[1])
17261    && ix86_match_ccmode (peep2_next_insn (3),
17262                          (GET_CODE (operands[3]) == PLUS
17263                           || GET_CODE (operands[3]) == MINUS)
17264                          ? CCGOCmode : CCNOmode)"
17265   [(parallel [(set (match_dup 4) (match_dup 5))
17266               (set (match_dup 1) (match_dup 6))])]
17267   "operands[2] = gen_lowpart (<MODE>mode, operands[2]);
17268    operands[4] = SET_DEST (PATTERN (peep2_next_insn (3)));
17269    operands[5] = gen_rtx_fmt_ee (GET_CODE (operands[3]), <MODE>mode,
17270                                  copy_rtx (operands[1]), operands[2]);
17271    operands[5] = gen_rtx_COMPARE (GET_MODE (operands[4]),
17272                                   operands[5], const0_rtx);
17273    operands[6] = gen_rtx_fmt_ee (GET_CODE (operands[3]), <MODE>mode,
17274                                  copy_rtx (operands[1]),
17275                                  copy_rtx (operands[2]));")
17276
17277 ;; Attempt to always use XOR for zeroing registers.
17278 (define_peephole2
17279   [(set (match_operand 0 "register_operand" "")
17280         (match_operand 1 "const0_operand" ""))]
17281   "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD
17282    && (! TARGET_USE_MOV0 || optimize_insn_for_size_p ())
17283    && GENERAL_REG_P (operands[0])
17284    && peep2_regno_dead_p (0, FLAGS_REG)"
17285   [(parallel [(set (match_dup 0) (const_int 0))
17286               (clobber (reg:CC FLAGS_REG))])]
17287   "operands[0] = gen_lowpart (word_mode, operands[0]);")
17288
17289 (define_peephole2
17290   [(set (strict_low_part (match_operand 0 "register_operand" ""))
17291         (const_int 0))]
17292   "(GET_MODE (operands[0]) == QImode
17293     || GET_MODE (operands[0]) == HImode)
17294    && (! TARGET_USE_MOV0 || optimize_insn_for_size_p ())
17295    && peep2_regno_dead_p (0, FLAGS_REG)"
17296   [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
17297               (clobber (reg:CC FLAGS_REG))])])
17298
17299 ;; For HI, SI and DI modes, or $-1,reg is smaller than mov $-1,reg.
17300 (define_peephole2
17301   [(set (match_operand:SWI248 0 "register_operand" "")
17302         (const_int -1))]
17303   "(optimize_insn_for_size_p () || TARGET_MOVE_M1_VIA_OR)
17304    && peep2_regno_dead_p (0, FLAGS_REG)"
17305   [(parallel [(set (match_dup 0) (const_int -1))
17306               (clobber (reg:CC FLAGS_REG))])]
17307 {
17308   if (GET_MODE_SIZE (<MODE>mode) < GET_MODE_SIZE (SImode))
17309     operands[0] = gen_lowpart (SImode, operands[0]);
17310 })
17311
17312 ;; Attempt to convert simple lea to add/shift.
17313 ;; These can be created by move expanders.
17314
17315 (define_peephole2
17316   [(set (match_operand:SWI48 0 "register_operand" "")
17317         (plus:SWI48 (match_dup 0)
17318                     (match_operand:SWI48 1 "<nonmemory_operand>" "")))]
17319   "peep2_regno_dead_p (0, FLAGS_REG)"
17320   [(parallel [(set (match_dup 0) (plus:SWI48 (match_dup 0) (match_dup 1)))
17321               (clobber (reg:CC FLAGS_REG))])])
17322
17323 (define_peephole2
17324   [(set (match_operand:SI 0 "register_operand" "")
17325         (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
17326                             (match_operand:DI 2 "nonmemory_operand" "")) 0))]
17327   "TARGET_64BIT
17328    && peep2_regno_dead_p (0, FLAGS_REG)
17329    && REGNO (operands[0]) == REGNO (operands[1])"
17330   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
17331               (clobber (reg:CC FLAGS_REG))])]
17332   "operands[2] = gen_lowpart (SImode, operands[2]);")
17333
17334 (define_peephole2
17335   [(set (match_operand:SWI48 0 "register_operand" "")
17336         (mult:SWI48 (match_dup 0)
17337                     (match_operand:SWI48 1 "const_int_operand" "")))]
17338   "exact_log2 (INTVAL (operands[1])) >= 0
17339    && peep2_regno_dead_p (0, FLAGS_REG)"
17340   [(parallel [(set (match_dup 0) (ashift:SWI48 (match_dup 0) (match_dup 2)))
17341               (clobber (reg:CC FLAGS_REG))])]
17342   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
17343
17344 (define_peephole2
17345   [(set (match_operand:SI 0 "register_operand" "")
17346         (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
17347                    (match_operand:DI 2 "const_int_operand" "")) 0))]
17348   "TARGET_64BIT
17349    && exact_log2 (INTVAL (operands[2])) >= 0
17350    && REGNO (operands[0]) == REGNO (operands[1])
17351    && peep2_regno_dead_p (0, FLAGS_REG)"
17352   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
17353               (clobber (reg:CC FLAGS_REG))])]
17354   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
17355
17356 ;; The ESP adjustments can be done by the push and pop instructions.  Resulting
17357 ;; code is shorter, since push is only 1 byte, while add imm, %esp is 3 bytes.
17358 ;; On many CPUs it is also faster, since special hardware to avoid esp
17359 ;; dependencies is present.
17360
17361 ;; While some of these conversions may be done using splitters, we use
17362 ;; peepholes in order to allow combine_stack_adjustments pass to see
17363 ;; nonobfuscated RTL.
17364
17365 ;; Convert prologue esp subtractions to push.
17366 ;; We need register to push.  In order to keep verify_flow_info happy we have
17367 ;; two choices
17368 ;; - use scratch and clobber it in order to avoid dependencies
17369 ;; - use already live register
17370 ;; We can't use the second way right now, since there is no reliable way how to
17371 ;; verify that given register is live.  First choice will also most likely in
17372 ;; fewer dependencies.  On the place of esp adjustments it is very likely that
17373 ;; call clobbered registers are dead.  We may want to use base pointer as an
17374 ;; alternative when no register is available later.
17375
17376 (define_peephole2
17377   [(match_scratch:P 1 "r")
17378    (parallel [(set (reg:P SP_REG)
17379                    (plus:P (reg:P SP_REG)
17380                            (match_operand:P 0 "const_int_operand" "")))
17381               (clobber (reg:CC FLAGS_REG))
17382               (clobber (mem:BLK (scratch)))])]
17383   "(TARGET_SINGLE_PUSH || optimize_insn_for_size_p ())
17384    && INTVAL (operands[0]) == -GET_MODE_SIZE (Pmode)"
17385   [(clobber (match_dup 1))
17386    (parallel [(set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17387               (clobber (mem:BLK (scratch)))])])
17388
17389 (define_peephole2
17390   [(match_scratch:P 1 "r")
17391    (parallel [(set (reg:P SP_REG)
17392                    (plus:P (reg:P SP_REG)
17393                            (match_operand:P 0 "const_int_operand" "")))
17394               (clobber (reg:CC FLAGS_REG))
17395               (clobber (mem:BLK (scratch)))])]
17396   "(TARGET_DOUBLE_PUSH || optimize_insn_for_size_p ())
17397    && INTVAL (operands[0]) == -2*GET_MODE_SIZE (Pmode)"
17398   [(clobber (match_dup 1))
17399    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17400    (parallel [(set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17401               (clobber (mem:BLK (scratch)))])])
17402
17403 ;; Convert esp subtractions to push.
17404 (define_peephole2
17405   [(match_scratch:P 1 "r")
17406    (parallel [(set (reg:P SP_REG)
17407                    (plus:P (reg:P SP_REG)
17408                            (match_operand:P 0 "const_int_operand" "")))
17409               (clobber (reg:CC FLAGS_REG))])]
17410   "(TARGET_SINGLE_PUSH || optimize_insn_for_size_p ())
17411    && INTVAL (operands[0]) == -GET_MODE_SIZE (Pmode)"
17412   [(clobber (match_dup 1))
17413    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))])
17414
17415 (define_peephole2
17416   [(match_scratch:P 1 "r")
17417    (parallel [(set (reg:P SP_REG)
17418                    (plus:P (reg:P SP_REG)
17419                            (match_operand:P 0 "const_int_operand" "")))
17420               (clobber (reg:CC FLAGS_REG))])]
17421   "(TARGET_DOUBLE_PUSH || optimize_insn_for_size_p ())
17422    && INTVAL (operands[0]) == -2*GET_MODE_SIZE (Pmode)"
17423   [(clobber (match_dup 1))
17424    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))
17425    (set (mem:P (pre_dec:P (reg:P SP_REG))) (match_dup 1))])
17426
17427 ;; Convert epilogue deallocator to pop.
17428 (define_peephole2
17429   [(match_scratch:P 1 "r")
17430    (parallel [(set (reg:P SP_REG)
17431                    (plus:P (reg:P SP_REG)
17432                            (match_operand:P 0 "const_int_operand" "")))
17433               (clobber (reg:CC FLAGS_REG))
17434               (clobber (mem:BLK (scratch)))])]
17435   "(TARGET_SINGLE_POP || optimize_insn_for_size_p ())
17436    && INTVAL (operands[0]) == GET_MODE_SIZE (Pmode)"
17437   [(parallel [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17438               (clobber (mem:BLK (scratch)))])])
17439
17440 ;; Two pops case is tricky, since pop causes dependency
17441 ;; on destination register.  We use two registers if available.
17442 (define_peephole2
17443   [(match_scratch:P 1 "r")
17444    (match_scratch:P 2 "r")
17445    (parallel [(set (reg:P SP_REG)
17446                    (plus:P (reg:P SP_REG)
17447                            (match_operand:P 0 "const_int_operand" "")))
17448               (clobber (reg:CC FLAGS_REG))
17449               (clobber (mem:BLK (scratch)))])]
17450   "(TARGET_DOUBLE_POP || optimize_insn_for_size_p ())
17451    && INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17452   [(parallel [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17453               (clobber (mem:BLK (scratch)))])
17454    (set (match_dup 2) (mem:P (post_inc:P (reg:P SP_REG))))])
17455
17456 (define_peephole2
17457   [(match_scratch:P 1 "r")
17458    (parallel [(set (reg:P SP_REG)
17459                    (plus:P (reg:P SP_REG)
17460                            (match_operand:P 0 "const_int_operand" "")))
17461               (clobber (reg:CC FLAGS_REG))
17462               (clobber (mem:BLK (scratch)))])]
17463   "optimize_insn_for_size_p ()
17464    && INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17465   [(parallel [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17466               (clobber (mem:BLK (scratch)))])
17467    (set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))])
17468
17469 ;; Convert esp additions to pop.
17470 (define_peephole2
17471   [(match_scratch:P 1 "r")
17472    (parallel [(set (reg:P SP_REG)
17473                    (plus:P (reg:P SP_REG)
17474                            (match_operand:P 0 "const_int_operand" "")))
17475               (clobber (reg:CC FLAGS_REG))])]
17476   "INTVAL (operands[0]) == GET_MODE_SIZE (Pmode)"
17477   [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))])
17478
17479 ;; Two pops case is tricky, since pop causes dependency
17480 ;; on destination register.  We use two registers if available.
17481 (define_peephole2
17482   [(match_scratch:P 1 "r")
17483    (match_scratch:P 2 "r")
17484    (parallel [(set (reg:P SP_REG)
17485                    (plus:P (reg:P SP_REG)
17486                            (match_operand:P 0 "const_int_operand" "")))
17487               (clobber (reg:CC FLAGS_REG))])]
17488   "INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17489   [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17490    (set (match_dup 2) (mem:P (post_inc:P (reg:P SP_REG))))])
17491
17492 (define_peephole2
17493   [(match_scratch:P 1 "r")
17494    (parallel [(set (reg:P SP_REG)
17495                    (plus:P (reg:P SP_REG)
17496                            (match_operand:P 0 "const_int_operand" "")))
17497               (clobber (reg:CC FLAGS_REG))])]
17498   "optimize_insn_for_size_p ()
17499    && INTVAL (operands[0]) == 2*GET_MODE_SIZE (Pmode)"
17500   [(set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))
17501    (set (match_dup 1) (mem:P (post_inc:P (reg:P SP_REG))))])
17502 \f
17503 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
17504 ;; required and register dies.  Similarly for 128 to -128.
17505 (define_peephole2
17506   [(set (match_operand 0 "flags_reg_operand" "")
17507         (match_operator 1 "compare_operator"
17508           [(match_operand 2 "register_operand" "")
17509            (match_operand 3 "const_int_operand" "")]))]
17510   "(((!TARGET_FUSE_CMP_AND_BRANCH || optimize_insn_for_size_p ())
17511      && incdec_operand (operands[3], GET_MODE (operands[3])))
17512     || (!TARGET_FUSE_CMP_AND_BRANCH
17513         && INTVAL (operands[3]) == 128))
17514    && ix86_match_ccmode (insn, CCGCmode)
17515    && peep2_reg_dead_p (1, operands[2])"
17516   [(parallel [(set (match_dup 0)
17517                    (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
17518               (clobber (match_dup 2))])])
17519 \f
17520 ;; Convert imul by three, five and nine into lea
17521 (define_peephole2
17522   [(parallel
17523     [(set (match_operand:SWI48 0 "register_operand" "")
17524           (mult:SWI48 (match_operand:SWI48 1 "register_operand" "")
17525                       (match_operand:SWI48 2 "const359_operand" "")))
17526      (clobber (reg:CC FLAGS_REG))])]
17527   "!TARGET_PARTIAL_REG_STALL
17528    || <MODE>mode == SImode
17529    || optimize_function_for_size_p (cfun)"
17530   [(set (match_dup 0)
17531         (plus:SWI48 (mult:SWI48 (match_dup 1) (match_dup 2))
17532                     (match_dup 1)))]
17533   "operands[2] = GEN_INT (INTVAL (operands[2]) - 1);")
17534
17535 (define_peephole2
17536   [(parallel
17537     [(set (match_operand:SWI48 0 "register_operand" "")
17538           (mult:SWI48 (match_operand:SWI48 1 "nonimmediate_operand" "")
17539                       (match_operand:SWI48 2 "const359_operand" "")))
17540      (clobber (reg:CC FLAGS_REG))])]
17541   "optimize_insn_for_speed_p ()
17542    && (!TARGET_PARTIAL_REG_STALL || <MODE>mode == SImode)"
17543   [(set (match_dup 0) (match_dup 1))
17544    (set (match_dup 0)
17545         (plus:SWI48 (mult:SWI48 (match_dup 0) (match_dup 2))
17546                     (match_dup 0)))]
17547   "operands[2] = GEN_INT (INTVAL (operands[2]) - 1);")
17548
17549 ;; imul $32bit_imm, mem, reg is vector decoded, while
17550 ;; imul $32bit_imm, reg, reg is direct decoded.
17551 (define_peephole2
17552   [(match_scratch:SWI48 3 "r")
17553    (parallel [(set (match_operand:SWI48 0 "register_operand" "")
17554                    (mult:SWI48 (match_operand:SWI48 1 "memory_operand" "")
17555                                (match_operand:SWI48 2 "immediate_operand" "")))
17556               (clobber (reg:CC FLAGS_REG))])]
17557   "TARGET_SLOW_IMUL_IMM32_MEM && optimize_insn_for_speed_p ()
17558    && !satisfies_constraint_K (operands[2])"
17559   [(set (match_dup 3) (match_dup 1))
17560    (parallel [(set (match_dup 0) (mult:SWI48 (match_dup 3) (match_dup 2)))
17561               (clobber (reg:CC FLAGS_REG))])])
17562
17563 (define_peephole2
17564   [(match_scratch:SI 3 "r")
17565    (parallel [(set (match_operand:DI 0 "register_operand" "")
17566                    (zero_extend:DI
17567                      (mult:SI (match_operand:SI 1 "memory_operand" "")
17568                               (match_operand:SI 2 "immediate_operand" ""))))
17569               (clobber (reg:CC FLAGS_REG))])]
17570   "TARGET_64BIT
17571    && TARGET_SLOW_IMUL_IMM32_MEM && optimize_insn_for_speed_p ()
17572    && !satisfies_constraint_K (operands[2])"
17573   [(set (match_dup 3) (match_dup 1))
17574    (parallel [(set (match_dup 0)
17575                    (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
17576               (clobber (reg:CC FLAGS_REG))])])
17577
17578 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
17579 ;; Convert it into imul reg, reg
17580 ;; It would be better to force assembler to encode instruction using long
17581 ;; immediate, but there is apparently no way to do so.
17582 (define_peephole2
17583   [(parallel [(set (match_operand:SWI248 0 "register_operand" "")
17584                    (mult:SWI248
17585                     (match_operand:SWI248 1 "nonimmediate_operand" "")
17586                     (match_operand:SWI248 2 "const_int_operand" "")))
17587               (clobber (reg:CC FLAGS_REG))])
17588    (match_scratch:SWI248 3 "r")]
17589   "TARGET_SLOW_IMUL_IMM8 && optimize_insn_for_speed_p ()
17590    && satisfies_constraint_K (operands[2])"
17591   [(set (match_dup 3) (match_dup 2))
17592    (parallel [(set (match_dup 0) (mult:SWI248 (match_dup 0) (match_dup 3)))
17593               (clobber (reg:CC FLAGS_REG))])]
17594 {
17595   if (!rtx_equal_p (operands[0], operands[1]))
17596     emit_move_insn (operands[0], operands[1]);
17597 })
17598
17599 ;; After splitting up read-modify operations, array accesses with memory
17600 ;; operands might end up in form:
17601 ;;  sall    $2, %eax
17602 ;;  movl    4(%esp), %edx
17603 ;;  addl    %edx, %eax
17604 ;; instead of pre-splitting:
17605 ;;  sall    $2, %eax
17606 ;;  addl    4(%esp), %eax
17607 ;; Turn it into:
17608 ;;  movl    4(%esp), %edx
17609 ;;  leal    (%edx,%eax,4), %eax
17610
17611 (define_peephole2
17612   [(match_scratch:P 5 "r")
17613    (parallel [(set (match_operand 0 "register_operand" "")
17614                    (ashift (match_operand 1 "register_operand" "")
17615                            (match_operand 2 "const_int_operand" "")))
17616                (clobber (reg:CC FLAGS_REG))])
17617    (parallel [(set (match_operand 3 "register_operand" "")
17618                    (plus (match_dup 0)
17619                          (match_operand 4 "x86_64_general_operand" "")))
17620                    (clobber (reg:CC FLAGS_REG))])]
17621   "IN_RANGE (INTVAL (operands[2]), 1, 3)
17622    /* Validate MODE for lea.  */
17623    && ((!TARGET_PARTIAL_REG_STALL
17624         && (GET_MODE (operands[0]) == QImode
17625             || GET_MODE (operands[0]) == HImode))
17626        || GET_MODE (operands[0]) == SImode
17627        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
17628    && (rtx_equal_p (operands[0], operands[3])
17629        || peep2_reg_dead_p (2, operands[0]))
17630    /* We reorder load and the shift.  */
17631    && !reg_overlap_mentioned_p (operands[0], operands[4])"
17632   [(set (match_dup 5) (match_dup 4))
17633    (set (match_dup 0) (match_dup 1))]
17634 {
17635   enum machine_mode op1mode = GET_MODE (operands[1]);
17636   enum machine_mode mode = op1mode == DImode ? DImode : SImode;
17637   int scale = 1 << INTVAL (operands[2]);
17638   rtx index = gen_lowpart (Pmode, operands[1]);
17639   rtx base = gen_lowpart (Pmode, operands[5]);
17640   rtx dest = gen_lowpart (mode, operands[3]);
17641
17642   operands[1] = gen_rtx_PLUS (Pmode, base,
17643                               gen_rtx_MULT (Pmode, index, GEN_INT (scale)));
17644   operands[5] = base;
17645   if (mode != Pmode)
17646     operands[1] = gen_rtx_SUBREG (mode, operands[1], 0);
17647   if (op1mode != Pmode)
17648     operands[5] = gen_rtx_SUBREG (op1mode, operands[5], 0);
17649   operands[0] = dest;
17650 })
17651 \f
17652 ;; We used to use "int $5", in honor of #BR which maps to interrupt vector 5.
17653 ;; That, however, is usually mapped by the OS to SIGSEGV, which is often
17654 ;; caught for use by garbage collectors and the like.  Using an insn that
17655 ;; maps to SIGILL makes it more likely the program will rightfully die.
17656 ;; Keeping with tradition, "6" is in honor of #UD.
17657 (define_insn "trap"
17658   [(trap_if (const_int 1) (const_int 6))]
17659   ""
17660   { return ASM_SHORT "0x0b0f"; }
17661   [(set_attr "length" "2")])
17662
17663 (define_expand "prefetch"
17664   [(prefetch (match_operand 0 "address_operand" "")
17665              (match_operand:SI 1 "const_int_operand" "")
17666              (match_operand:SI 2 "const_int_operand" ""))]
17667   "TARGET_PREFETCH_SSE || TARGET_3DNOW"
17668 {
17669   int rw = INTVAL (operands[1]);
17670   int locality = INTVAL (operands[2]);
17671
17672   gcc_assert (rw == 0 || rw == 1);
17673   gcc_assert (locality >= 0 && locality <= 3);
17674   gcc_assert (GET_MODE (operands[0]) == Pmode
17675               || GET_MODE (operands[0]) == VOIDmode);
17676
17677   /* Use 3dNOW prefetch in case we are asking for write prefetch not
17678      supported by SSE counterpart or the SSE prefetch is not available
17679      (K6 machines).  Otherwise use SSE prefetch as it allows specifying
17680      of locality.  */
17681   if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
17682     operands[2] = GEN_INT (3);
17683   else
17684     operands[1] = const0_rtx;
17685 })
17686
17687 (define_insn "*prefetch_sse_<mode>"
17688   [(prefetch (match_operand:P 0 "address_operand" "p")
17689              (const_int 0)
17690              (match_operand:SI 1 "const_int_operand" ""))]
17691   "TARGET_PREFETCH_SSE"
17692 {
17693   static const char * const patterns[4] = {
17694    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
17695   };
17696
17697   int locality = INTVAL (operands[1]);
17698   gcc_assert (locality >= 0 && locality <= 3);
17699
17700   return patterns[locality];
17701 }
17702   [(set_attr "type" "sse")
17703    (set_attr "atom_sse_attr" "prefetch")
17704    (set (attr "length_address")
17705         (symbol_ref "memory_address_length (operands[0])"))
17706    (set_attr "memory" "none")])
17707
17708 (define_insn "*prefetch_3dnow_<mode>"
17709   [(prefetch (match_operand:P 0 "address_operand" "p")
17710              (match_operand:SI 1 "const_int_operand" "n")
17711              (const_int 3))]
17712   "TARGET_3DNOW"
17713 {
17714   if (INTVAL (operands[1]) == 0)
17715     return "prefetch\t%a0";
17716   else
17717     return "prefetchw\t%a0";
17718 }
17719   [(set_attr "type" "mmx")
17720    (set (attr "length_address")
17721         (symbol_ref "memory_address_length (operands[0])"))
17722    (set_attr "memory" "none")])
17723
17724 (define_expand "stack_protect_set"
17725   [(match_operand 0 "memory_operand" "")
17726    (match_operand 1 "memory_operand" "")]
17727   ""
17728 {
17729   rtx (*insn)(rtx, rtx);
17730
17731 #ifdef TARGET_THREAD_SSP_OFFSET
17732   operands[1] = GEN_INT (TARGET_THREAD_SSP_OFFSET);
17733   insn = (TARGET_LP64
17734           ? gen_stack_tls_protect_set_di
17735           : gen_stack_tls_protect_set_si);
17736 #else
17737   insn = (TARGET_LP64
17738           ? gen_stack_protect_set_di
17739           : gen_stack_protect_set_si);
17740 #endif
17741
17742   emit_insn (insn (operands[0], operands[1]));
17743   DONE;
17744 })
17745
17746 (define_insn "stack_protect_set_<mode>"
17747   [(set (match_operand:PTR 0 "memory_operand" "=m")
17748         (unspec:PTR [(match_operand:PTR 1 "memory_operand" "m")]
17749                     UNSPEC_SP_SET))
17750    (set (match_scratch:PTR 2 "=&r") (const_int 0))
17751    (clobber (reg:CC FLAGS_REG))]
17752   ""
17753   "mov{<imodesuffix>}\t{%1, %2|%2, %1}\;mov{<imodesuffix>}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
17754   [(set_attr "type" "multi")])
17755
17756 (define_insn "stack_tls_protect_set_<mode>"
17757   [(set (match_operand:PTR 0 "memory_operand" "=m")
17758         (unspec:PTR [(match_operand:PTR 1 "const_int_operand" "i")]
17759                     UNSPEC_SP_TLS_SET))
17760    (set (match_scratch:PTR 2 "=&r") (const_int 0))
17761    (clobber (reg:CC FLAGS_REG))]
17762   ""
17763   "mov{<imodesuffix>}\t{%@:%P1, %2|%2, <iptrsize> PTR %@:%P1}\;mov{<imodesuffix>}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
17764   [(set_attr "type" "multi")])
17765
17766 (define_expand "stack_protect_test"
17767   [(match_operand 0 "memory_operand" "")
17768    (match_operand 1 "memory_operand" "")
17769    (match_operand 2 "" "")]
17770   ""
17771 {
17772   rtx flags = gen_rtx_REG (CCZmode, FLAGS_REG);
17773
17774   rtx (*insn)(rtx, rtx, rtx);
17775
17776 #ifdef TARGET_THREAD_SSP_OFFSET
17777   operands[1] = GEN_INT (TARGET_THREAD_SSP_OFFSET);
17778   insn = (TARGET_LP64
17779           ? gen_stack_tls_protect_test_di
17780           : gen_stack_tls_protect_test_si);
17781 #else
17782   insn = (TARGET_LP64
17783           ? gen_stack_protect_test_di
17784           : gen_stack_protect_test_si);
17785 #endif
17786
17787   emit_insn (insn (flags, operands[0], operands[1]));
17788
17789   emit_jump_insn (gen_cbranchcc4 (gen_rtx_EQ (VOIDmode, flags, const0_rtx),
17790                                   flags, const0_rtx, operands[2]));
17791   DONE;
17792 })
17793
17794 (define_insn "stack_protect_test_<mode>"
17795   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
17796         (unspec:CCZ [(match_operand:PTR 1 "memory_operand" "m")
17797                      (match_operand:PTR 2 "memory_operand" "m")]
17798                     UNSPEC_SP_TEST))
17799    (clobber (match_scratch:PTR 3 "=&r"))]
17800   ""
17801   "mov{<imodesuffix>}\t{%1, %3|%3, %1}\;xor{<imodesuffix>}\t{%2, %3|%3, %2}"
17802   [(set_attr "type" "multi")])
17803
17804 (define_insn "stack_tls_protect_test_<mode>"
17805   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
17806         (unspec:CCZ [(match_operand:PTR 1 "memory_operand" "m")
17807                      (match_operand:PTR 2 "const_int_operand" "i")]
17808                     UNSPEC_SP_TLS_TEST))
17809    (clobber (match_scratch:PTR 3 "=r"))]
17810   ""
17811   "mov{<imodesuffix>}\t{%1, %3|%3, %1}\;xor{<imodesuffix>}\t{%@:%P2, %3|%3, <iptrsize> PTR %@:%P2}"
17812   [(set_attr "type" "multi")])
17813
17814 (define_insn "sse4_2_crc32<mode>"
17815   [(set (match_operand:SI 0 "register_operand" "=r")
17816         (unspec:SI
17817           [(match_operand:SI 1 "register_operand" "0")
17818            (match_operand:SWI124 2 "nonimmediate_operand" "<r>m")]
17819           UNSPEC_CRC32))]
17820   "TARGET_SSE4_2 || TARGET_CRC32"
17821   "crc32{<imodesuffix>}\t{%2, %0|%0, %2}"
17822   [(set_attr "type" "sselog1")
17823    (set_attr "prefix_rep" "1")
17824    (set_attr "prefix_extra" "1")
17825    (set (attr "prefix_data16")
17826      (if_then_else (match_operand:HI 2 "" "")
17827        (const_string "1")
17828        (const_string "*")))
17829    (set (attr "prefix_rex")
17830      (if_then_else (match_operand:QI 2 "ext_QIreg_operand" "")
17831        (const_string "1")
17832        (const_string "*")))
17833    (set_attr "mode" "SI")])
17834
17835 (define_insn "sse4_2_crc32di"
17836   [(set (match_operand:DI 0 "register_operand" "=r")
17837         (unspec:DI
17838           [(match_operand:DI 1 "register_operand" "0")
17839            (match_operand:DI 2 "nonimmediate_operand" "rm")]
17840           UNSPEC_CRC32))]
17841   "TARGET_64BIT && (TARGET_SSE4_2 || TARGET_CRC32)"
17842   "crc32{q}\t{%2, %0|%0, %2}"
17843   [(set_attr "type" "sselog1")
17844    (set_attr "prefix_rep" "1")
17845    (set_attr "prefix_extra" "1")
17846    (set_attr "mode" "DI")])
17847
17848 (define_expand "rdpmc"
17849   [(match_operand:DI 0 "register_operand" "")
17850    (match_operand:SI 1 "register_operand" "")]
17851   ""
17852 {
17853   rtx reg = gen_reg_rtx (DImode);
17854   rtx si;
17855
17856   /* Force operand 1 into ECX.  */
17857   rtx ecx = gen_rtx_REG (SImode, CX_REG);
17858   emit_insn (gen_rtx_SET (VOIDmode, ecx, operands[1]));
17859   si = gen_rtx_UNSPEC_VOLATILE (DImode, gen_rtvec (1, ecx),
17860                                 UNSPECV_RDPMC);
17861
17862   if (TARGET_64BIT)
17863     {
17864       rtvec vec = rtvec_alloc (2);
17865       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17866       rtx upper = gen_reg_rtx (DImode);
17867       rtx di = gen_rtx_UNSPEC_VOLATILE (DImode,
17868                                         gen_rtvec (1, const0_rtx),
17869                                         UNSPECV_RDPMC);
17870       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, reg, si);
17871       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, upper, di);
17872       emit_insn (load);
17873       upper = expand_simple_binop (DImode, ASHIFT, upper, GEN_INT (32),
17874                                    NULL, 1, OPTAB_DIRECT);
17875       reg = expand_simple_binop (DImode, IOR, reg, upper, reg, 1,
17876                                  OPTAB_DIRECT);
17877     }
17878   else
17879     emit_insn (gen_rtx_SET (VOIDmode, reg, si));
17880   emit_insn (gen_rtx_SET (VOIDmode, operands[0], reg));
17881   DONE;
17882 })
17883
17884 (define_insn "*rdpmc"
17885   [(set (match_operand:DI 0 "register_operand" "=A")
17886         (unspec_volatile:DI [(match_operand:SI 1 "register_operand" "c")]
17887                             UNSPECV_RDPMC))]
17888   "!TARGET_64BIT"
17889   "rdpmc"
17890   [(set_attr "type" "other")
17891    (set_attr "length" "2")])
17892
17893 (define_insn "*rdpmc_rex64"
17894   [(set (match_operand:DI 0 "register_operand" "=a")
17895         (unspec_volatile:DI [(match_operand:SI 2 "register_operand" "c")]
17896                             UNSPECV_RDPMC))
17897   (set (match_operand:DI 1 "register_operand" "=d")
17898        (unspec_volatile:DI [(const_int 0)] UNSPECV_RDPMC))]
17899   "TARGET_64BIT"
17900   "rdpmc"
17901   [(set_attr "type" "other")
17902    (set_attr "length" "2")])
17903
17904 (define_expand "rdtsc"
17905   [(set (match_operand:DI 0 "register_operand" "")
17906         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))]
17907   ""
17908 {
17909   if (TARGET_64BIT)
17910     {
17911       rtvec vec = rtvec_alloc (2);
17912       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17913       rtx upper = gen_reg_rtx (DImode);
17914       rtx lower = gen_reg_rtx (DImode);
17915       rtx src = gen_rtx_UNSPEC_VOLATILE (DImode,
17916                                          gen_rtvec (1, const0_rtx),
17917                                          UNSPECV_RDTSC);
17918       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, lower, src);
17919       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, upper, src);
17920       emit_insn (load);
17921       upper = expand_simple_binop (DImode, ASHIFT, upper, GEN_INT (32),
17922                                    NULL, 1, OPTAB_DIRECT);
17923       lower = expand_simple_binop (DImode, IOR, lower, upper, lower, 1,
17924                                    OPTAB_DIRECT);
17925       emit_insn (gen_rtx_SET (VOIDmode, operands[0], lower));
17926       DONE;
17927     }
17928 })
17929
17930 (define_insn "*rdtsc"
17931   [(set (match_operand:DI 0 "register_operand" "=A")
17932         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))]
17933   "!TARGET_64BIT"
17934   "rdtsc"
17935   [(set_attr "type" "other")
17936    (set_attr "length" "2")])
17937
17938 (define_insn "*rdtsc_rex64"
17939   [(set (match_operand:DI 0 "register_operand" "=a")
17940         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))
17941    (set (match_operand:DI 1 "register_operand" "=d")
17942         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSC))]
17943   "TARGET_64BIT"
17944   "rdtsc"
17945   [(set_attr "type" "other")
17946    (set_attr "length" "2")])
17947
17948 (define_expand "rdtscp"
17949   [(match_operand:DI 0 "register_operand" "")
17950    (match_operand:SI 1 "memory_operand" "")]
17951   ""
17952 {
17953   rtx di = gen_rtx_UNSPEC_VOLATILE (DImode,
17954                                     gen_rtvec (1, const0_rtx),
17955                                     UNSPECV_RDTSCP);
17956   rtx si = gen_rtx_UNSPEC_VOLATILE (SImode,
17957                                     gen_rtvec (1, const0_rtx),
17958                                     UNSPECV_RDTSCP);
17959   rtx reg = gen_reg_rtx (DImode);
17960   rtx tmp = gen_reg_rtx (SImode);
17961
17962   if (TARGET_64BIT)
17963     {
17964       rtvec vec = rtvec_alloc (3);
17965       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17966       rtx upper = gen_reg_rtx (DImode);
17967       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, reg, di);
17968       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, upper, di);
17969       RTVEC_ELT (vec, 2) = gen_rtx_SET (VOIDmode, tmp, si);
17970       emit_insn (load);
17971       upper = expand_simple_binop (DImode, ASHIFT, upper, GEN_INT (32),
17972                                    NULL, 1, OPTAB_DIRECT);
17973       reg = expand_simple_binop (DImode, IOR, reg, upper, reg, 1,
17974                                  OPTAB_DIRECT);
17975     }
17976   else
17977     {
17978       rtvec vec = rtvec_alloc (2);
17979       rtx load = gen_rtx_PARALLEL (VOIDmode, vec);
17980       RTVEC_ELT (vec, 0) = gen_rtx_SET (VOIDmode, reg, di);
17981       RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, tmp, si);
17982       emit_insn (load);
17983     }
17984   emit_insn (gen_rtx_SET (VOIDmode, operands[0], reg));
17985   emit_insn (gen_rtx_SET (VOIDmode, operands[1], tmp));
17986   DONE;
17987 })
17988
17989 (define_insn "*rdtscp"
17990   [(set (match_operand:DI 0 "register_operand" "=A")
17991         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSCP))
17992    (set (match_operand:SI 1 "register_operand" "=c")
17993         (unspec_volatile:SI [(const_int 0)] UNSPECV_RDTSCP))]
17994   "!TARGET_64BIT"
17995   "rdtscp"
17996   [(set_attr "type" "other")
17997    (set_attr "length" "3")])
17998
17999 (define_insn "*rdtscp_rex64"
18000   [(set (match_operand:DI 0 "register_operand" "=a")
18001         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSCP))
18002    (set (match_operand:DI 1 "register_operand" "=d")
18003         (unspec_volatile:DI [(const_int 0)] UNSPECV_RDTSCP))
18004    (set (match_operand:SI 2 "register_operand" "=c")
18005         (unspec_volatile:SI [(const_int 0)] UNSPECV_RDTSCP))]
18006   "TARGET_64BIT"
18007   "rdtscp"
18008   [(set_attr "type" "other")
18009    (set_attr "length" "3")])
18010
18011 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
18012 ;;
18013 ;; LWP instructions
18014 ;;
18015 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
18016
18017 (define_expand "lwp_llwpcb"
18018   [(unspec_volatile [(match_operand 0 "register_operand" "r")]
18019                     UNSPECV_LLWP_INTRINSIC)]
18020   "TARGET_LWP")
18021
18022 (define_insn "*lwp_llwpcb<mode>1"
18023   [(unspec_volatile [(match_operand:P 0 "register_operand" "r")]
18024                     UNSPECV_LLWP_INTRINSIC)]
18025   "TARGET_LWP"
18026   "llwpcb\t%0"
18027   [(set_attr "type" "lwp")
18028    (set_attr "mode" "<MODE>")
18029    (set_attr "length" "5")])
18030
18031 (define_expand "lwp_slwpcb"
18032   [(set (match_operand 0 "register_operand" "=r")
18033         (unspec_volatile [(const_int 0)] UNSPECV_SLWP_INTRINSIC))]
18034   "TARGET_LWP"
18035 {
18036   rtx (*insn)(rtx);
18037
18038   insn = (TARGET_64BIT
18039           ? gen_lwp_slwpcbdi
18040           : gen_lwp_slwpcbsi);
18041
18042   emit_insn (insn (operands[0]));
18043   DONE;
18044 })
18045
18046 (define_insn "lwp_slwpcb<mode>"
18047   [(set (match_operand:P 0 "register_operand" "=r")
18048         (unspec_volatile:P [(const_int 0)] UNSPECV_SLWP_INTRINSIC))]
18049   "TARGET_LWP"
18050   "slwpcb\t%0"
18051   [(set_attr "type" "lwp")
18052    (set_attr "mode" "<MODE>")
18053    (set_attr "length" "5")])
18054
18055 (define_expand "lwp_lwpval<mode>3"
18056   [(unspec_volatile [(match_operand:SWI48 1 "register_operand" "r")
18057                      (match_operand:SI 2 "nonimmediate_operand" "rm")
18058                      (match_operand:SI 3 "const_int_operand" "i")]
18059                     UNSPECV_LWPVAL_INTRINSIC)]
18060   "TARGET_LWP"
18061   "/* Avoid unused variable warning.  */
18062    (void) operand0;")
18063
18064 (define_insn "*lwp_lwpval<mode>3_1"
18065   [(unspec_volatile [(match_operand:SWI48 0 "register_operand" "r")
18066                      (match_operand:SI 1 "nonimmediate_operand" "rm")
18067                      (match_operand:SI 2 "const_int_operand" "i")]
18068                     UNSPECV_LWPVAL_INTRINSIC)]
18069   "TARGET_LWP"
18070   "lwpval\t{%2, %1, %0|%0, %1, %2}"
18071   [(set_attr "type" "lwp")
18072    (set_attr "mode" "<MODE>")
18073    (set (attr "length")
18074         (symbol_ref "ix86_attr_length_address_default (insn) + 9"))])
18075
18076 (define_expand "lwp_lwpins<mode>3"
18077   [(set (reg:CCC FLAGS_REG)
18078         (unspec_volatile:CCC [(match_operand:SWI48 1 "register_operand" "r")
18079                               (match_operand:SI 2 "nonimmediate_operand" "rm")
18080                               (match_operand:SI 3 "const_int_operand" "i")]
18081                              UNSPECV_LWPINS_INTRINSIC))
18082    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
18083         (eq:QI (reg:CCC FLAGS_REG) (const_int 0)))]
18084   "TARGET_LWP")
18085
18086 (define_insn "*lwp_lwpins<mode>3_1"
18087   [(set (reg:CCC FLAGS_REG)
18088         (unspec_volatile:CCC [(match_operand:SWI48 0 "register_operand" "r")
18089                               (match_operand:SI 1 "nonimmediate_operand" "rm")
18090                               (match_operand:SI 2 "const_int_operand" "i")]
18091                              UNSPECV_LWPINS_INTRINSIC))]
18092   "TARGET_LWP"
18093   "lwpins\t{%2, %1, %0|%0, %1, %2}"
18094   [(set_attr "type" "lwp")
18095    (set_attr "mode" "<MODE>")
18096    (set (attr "length")
18097         (symbol_ref "ix86_attr_length_address_default (insn) + 9"))])
18098
18099 (define_insn "rdfsbase<mode>"
18100   [(set (match_operand:SWI48 0 "register_operand" "=r")
18101         (unspec_volatile:SWI48 [(const_int 0)] UNSPECV_RDFSBASE))]
18102   "TARGET_64BIT && TARGET_FSGSBASE"
18103   "rdfsbase %0"
18104   [(set_attr "type" "other")
18105    (set_attr "prefix_extra" "2")])
18106
18107 (define_insn "rdgsbase<mode>"
18108   [(set (match_operand:SWI48 0 "register_operand" "=r")
18109         (unspec_volatile:SWI48 [(const_int 0)] UNSPECV_RDGSBASE))]
18110   "TARGET_64BIT && TARGET_FSGSBASE"
18111   "rdgsbase %0"
18112   [(set_attr "type" "other")
18113    (set_attr "prefix_extra" "2")])
18114
18115 (define_insn "wrfsbase<mode>"
18116   [(unspec_volatile [(match_operand:SWI48 0 "register_operand" "r")]
18117                     UNSPECV_WRFSBASE)]
18118   "TARGET_64BIT && TARGET_FSGSBASE"
18119   "wrfsbase %0"
18120   [(set_attr "type" "other")
18121    (set_attr "prefix_extra" "2")])
18122
18123 (define_insn "wrgsbase<mode>"
18124   [(unspec_volatile [(match_operand:SWI48 0 "register_operand" "r")]
18125                     UNSPECV_WRGSBASE)]
18126   "TARGET_64BIT && TARGET_FSGSBASE"
18127   "wrgsbase %0"
18128   [(set_attr "type" "other")
18129    (set_attr "prefix_extra" "2")])
18130
18131 (define_insn "rdrand<mode>_1"
18132   [(set (match_operand:SWI248 0 "register_operand" "=r")
18133         (unspec:SWI248 [(const_int 0)] UNSPEC_RDRAND))
18134    (set (reg:CCC FLAGS_REG)
18135         (unspec:CCC [(const_int 0)] UNSPEC_RDRAND))]
18136   "TARGET_RDRND"
18137   "rdrand\t%0"
18138   [(set_attr "type" "other")
18139    (set_attr "prefix_extra" "1")])
18140
18141 (define_expand "pause"
18142   [(set (match_dup 0)
18143         (unspec:BLK [(match_dup 0)] UNSPEC_PAUSE))]
18144   ""
18145 {
18146   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
18147   MEM_VOLATILE_P (operands[0]) = 1;
18148 })
18149
18150 ;; Use "rep; nop", instead of "pause", to support older assemblers.
18151 ;; They have the same encoding.
18152 (define_insn "*pause"
18153   [(set (match_operand:BLK 0 "" "")
18154         (unspec:BLK [(match_dup 0)] UNSPEC_PAUSE))]
18155   ""
18156   "rep; nop"
18157   [(set_attr "length" "2")
18158    (set_attr "memory" "unknown")])
18159
18160 (include "mmx.md")
18161 (include "sse.md")
18162 (include "sync.md")