OSDN Git Service

PR target/36473
[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
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 ;; 'z' mov%z1 would be movl, movw, or movb depending on the mode of
31 ;;     operands[1].
32 ;; 'L' Print the opcode suffix for a 32-bit integer opcode.
33 ;; 'W' Print the opcode suffix for a 16-bit integer opcode.
34 ;; 'B' Print the opcode suffix for an 8-bit integer opcode.
35 ;; 'Q' Print the opcode suffix for a 64-bit float opcode.
36 ;; 'S' Print the opcode suffix for a 32-bit float opcode.
37 ;; 'T' Print the opcode suffix for an 80-bit extended real XFmode float opcode.
38 ;; 'J' Print the appropriate jump operand.
39 ;;
40 ;; 'b' Print the QImode name of the register for the indicated operand.
41 ;;     %b0 would print %al if operands[0] is reg 0.
42 ;; 'w' Likewise, print the HImode name of the register.
43 ;; 'k' Likewise, print the SImode name of the register.
44 ;; 'h' Print the QImode name for a "high" register, either ah, bh, ch or dh.
45 ;; 'y' Print "st(0)" instead of "st" as a register.
46
47 ;; UNSPEC usage:
48
49 (define_constants
50   [; Relocation specifiers
51    (UNSPEC_GOT                  0)
52    (UNSPEC_GOTOFF               1)
53    (UNSPEC_GOTPCREL             2)
54    (UNSPEC_GOTTPOFF             3)
55    (UNSPEC_TPOFF                4)
56    (UNSPEC_NTPOFF               5)
57    (UNSPEC_DTPOFF               6)
58    (UNSPEC_GOTNTPOFF            7)
59    (UNSPEC_INDNTPOFF            8)
60    (UNSPEC_PLTOFF               9)
61
62    ; Prologue support
63    (UNSPEC_STACK_ALLOC          11)
64    (UNSPEC_SET_GOT              12)
65    (UNSPEC_SSE_PROLOGUE_SAVE    13)
66    (UNSPEC_REG_SAVE             14)
67    (UNSPEC_DEF_CFA              15)
68    (UNSPEC_SET_RIP              16)
69    (UNSPEC_SET_GOT_OFFSET       17)
70
71    ; TLS support
72    (UNSPEC_TP                   18)
73    (UNSPEC_TLS_GD               19)
74    (UNSPEC_TLS_LD_BASE          20)
75    (UNSPEC_TLSDESC              21)
76
77    ; Other random patterns
78    (UNSPEC_SCAS                 30)
79    (UNSPEC_FNSTSW               31)
80    (UNSPEC_SAHF                 32)
81    (UNSPEC_FSTCW                33)
82    (UNSPEC_ADD_CARRY            34)
83    (UNSPEC_FLDCW                35)
84    (UNSPEC_REP                  36)
85    (UNSPEC_EH_RETURN            37)
86    (UNSPEC_LD_MPIC              38)     ; load_macho_picbase
87    (UNSPEC_TRUNC_NOOP           39)
88
89    ; For SSE/MMX support:
90    (UNSPEC_FIX_NOTRUNC          40)
91    (UNSPEC_MASKMOV              41)
92    (UNSPEC_MOVMSK               42)
93    (UNSPEC_MOVNT                43)
94    (UNSPEC_MOVU                 44)
95    (UNSPEC_RCP                  45)
96    (UNSPEC_RSQRT                46)
97    (UNSPEC_SFENCE               47)
98    (UNSPEC_PFRCP                49)
99    (UNSPEC_PFRCPIT1             40)
100    (UNSPEC_PFRCPIT2             41)
101    (UNSPEC_PFRSQRT              42)
102    (UNSPEC_PFRSQIT1             43)
103    (UNSPEC_MFENCE               44)
104    (UNSPEC_LFENCE               45)
105    (UNSPEC_PSADBW               46)
106    (UNSPEC_LDDQU                47)
107
108    ; Generic math support
109    (UNSPEC_COPYSIGN             50)
110    (UNSPEC_IEEE_MIN             51)     ; not commutative
111    (UNSPEC_IEEE_MAX             52)     ; not commutative
112
113    ; x87 Floating point
114    (UNSPEC_SIN                  60)
115    (UNSPEC_COS                  61)
116    (UNSPEC_FPATAN               62)
117    (UNSPEC_FYL2X                63)
118    (UNSPEC_FYL2XP1              64)
119    (UNSPEC_FRNDINT              65)
120    (UNSPEC_FIST                 66)
121    (UNSPEC_F2XM1                67)
122    (UNSPEC_TAN                  68)
123    (UNSPEC_FXAM                 69)
124
125    ; x87 Rounding
126    (UNSPEC_FRNDINT_FLOOR        70)
127    (UNSPEC_FRNDINT_CEIL         71)
128    (UNSPEC_FRNDINT_TRUNC        72)
129    (UNSPEC_FRNDINT_MASK_PM      73)
130    (UNSPEC_FIST_FLOOR           74)
131    (UNSPEC_FIST_CEIL            75)
132
133    ; x87 Double output FP
134    (UNSPEC_SINCOS_COS           80)
135    (UNSPEC_SINCOS_SIN           81)
136    (UNSPEC_XTRACT_FRACT         84)
137    (UNSPEC_XTRACT_EXP           85)
138    (UNSPEC_FSCALE_FRACT         86)
139    (UNSPEC_FSCALE_EXP           87)
140    (UNSPEC_FPREM_F              88)
141    (UNSPEC_FPREM_U              89)
142    (UNSPEC_FPREM1_F             90)
143    (UNSPEC_FPREM1_U             91)
144
145    (UNSPEC_C2_FLAG              95)
146
147    ; SSP patterns
148    (UNSPEC_SP_SET               100)
149    (UNSPEC_SP_TEST              101)
150    (UNSPEC_SP_TLS_SET           102)
151    (UNSPEC_SP_TLS_TEST          103)
152
153    ; SSSE3
154    (UNSPEC_PSHUFB               120)
155    (UNSPEC_PSIGN                121)
156    (UNSPEC_PALIGNR              122)
157
158    ; For SSE4A support
159    (UNSPEC_EXTRQI               130)
160    (UNSPEC_EXTRQ                131)
161    (UNSPEC_INSERTQI             132)
162    (UNSPEC_INSERTQ              133)
163
164    ; For SSE4.1 support
165    (UNSPEC_BLENDV               134)
166    (UNSPEC_INSERTPS             135)
167    (UNSPEC_DP                   136)
168    (UNSPEC_MOVNTDQA             137)
169    (UNSPEC_MPSADBW              138)
170    (UNSPEC_PHMINPOSUW           139)
171    (UNSPEC_PTEST                140)
172    (UNSPEC_ROUND                141)
173
174    ; For SSE4.2 support
175    (UNSPEC_CRC32                143)
176    (UNSPEC_PCMPESTR             144)
177    (UNSPEC_PCMPISTR             145)
178
179    ;; For SSE5
180    (UNSPEC_SSE5_INTRINSIC       150)
181    (UNSPEC_SSE5_UNSIGNED_CMP    151)
182    (UNSPEC_SSE5_TRUEFALSE       152)
183    (UNSPEC_SSE5_PERMUTE         153)
184    (UNSPEC_FRCZ                 154)
185    (UNSPEC_CVTPH2PS             155)
186    (UNSPEC_CVTPS2PH             156)
187
188    ; For AES support
189    (UNSPEC_AESENC               159)
190    (UNSPEC_AESENCLAST           160)
191    (UNSPEC_AESDEC               161)
192    (UNSPEC_AESDECLAST           162)
193    (UNSPEC_AESIMC               163)
194    (UNSPEC_AESKEYGENASSIST      164)
195
196    ; For PCLMUL support
197    (UNSPEC_PCLMUL               165)
198   ])
199
200 (define_constants
201   [(UNSPECV_BLOCKAGE            0)
202    (UNSPECV_STACK_PROBE         1)
203    (UNSPECV_EMMS                2)
204    (UNSPECV_LDMXCSR             3)
205    (UNSPECV_STMXCSR             4)
206    (UNSPECV_FEMMS               5)
207    (UNSPECV_CLFLUSH             6)
208    (UNSPECV_ALIGN               7)
209    (UNSPECV_MONITOR             8)
210    (UNSPECV_MWAIT               9)
211    (UNSPECV_CMPXCHG_1           10)
212    (UNSPECV_CMPXCHG_2           11)
213    (UNSPECV_XCHG                12)
214    (UNSPECV_LOCK                13)
215    (UNSPECV_PROLOGUE_USE        14)
216    (UNSPECV_CLD                 15)
217   ])
218
219 ;; Constants to represent pcomtrue/pcomfalse variants
220 (define_constants
221   [(PCOM_FALSE                  0)
222    (PCOM_TRUE                   1)
223    (COM_FALSE_S                 2)
224    (COM_FALSE_P                 3)
225    (COM_TRUE_S                  4)
226    (COM_TRUE_P                  5)
227   ])
228
229 ;; Constants used in the SSE5 pperm instruction
230 (define_constants
231   [(PPERM_SRC                   0x00)   /* copy source */
232    (PPERM_INVERT                0x20)   /* invert source */
233    (PPERM_REVERSE               0x40)   /* bit reverse source */
234    (PPERM_REV_INV               0x60)   /* bit reverse & invert src */
235    (PPERM_ZERO                  0x80)   /* all 0's */
236    (PPERM_ONES                  0xa0)   /* all 1's */
237    (PPERM_SIGN                  0xc0)   /* propagate sign bit */
238    (PPERM_INV_SIGN              0xe0)   /* invert & propagate sign */
239    (PPERM_SRC1                  0x00)   /* use first source byte */
240    (PPERM_SRC2                  0x10)   /* use second source byte */
241    ])
242
243 ;; Registers by name.
244 (define_constants
245   [(AX_REG                       0)
246    (DX_REG                       1)
247    (CX_REG                       2)
248    (SI_REG                       4)
249    (DI_REG                       5)
250    (BP_REG                       6)
251    (SP_REG                       7)
252    (FLAGS_REG                   17)
253    (FPSR_REG                    18)
254    (FPCR_REG                    19)
255    (R10_REG                     39)
256    (R11_REG                     40)
257   ])
258
259 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
260 ;; from i386.c.
261
262 ;; In C guard expressions, put expressions which may be compile-time
263 ;; constants first.  This allows for better optimization.  For
264 ;; example, write "TARGET_64BIT && reload_completed", not
265 ;; "reload_completed && TARGET_64BIT".
266
267 \f
268 ;; Processor type.  This attribute must exactly match the processor_type
269 ;; enumeration in i386.h.
270 (define_attr "cpu" "i386,i486,pentium,pentiumpro,geode,k6,athlon,pentium4,k8,
271                     nocona,core2,generic32,generic64,amdfam10"
272   (const (symbol_ref "ix86_tune")))
273
274 ;; A basic instruction type.  Refinements due to arguments to be
275 ;; provided in other attributes.
276 (define_attr "type"
277   "other,multi,
278    alu,alu1,negnot,imov,imovx,lea,
279    incdec,ishift,ishift1,rotate,rotate1,imul,idiv,
280    icmp,test,ibr,setcc,icmov,
281    push,pop,call,callv,leave,
282    str,bitmanip,
283    fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint,
284    sselog,sselog1,sseiadd,sseiadd1,sseishft,sseimul,
285    sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,ssecvt1,sseicvt,ssediv,sseins,
286    ssemuladd,sse4arg,
287    mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft"
288   (const_string "other"))
289
290 ;; Main data type used by the insn
291 (define_attr "mode"
292   "unknown,none,QI,HI,SI,DI,SF,DF,XF,TI,V4SF,V2DF,V2SF,V1DF"
293   (const_string "unknown"))
294
295 ;; The CPU unit operations uses.
296 (define_attr "unit" "integer,i387,sse,mmx,unknown"
297   (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint")
298            (const_string "i387")
299          (eq_attr "type" "sselog,sselog1,sseiadd,sseiadd1,sseishft,sseimul,
300                           sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,
301                           ssecvt1,sseicvt,ssediv,sseins,ssemuladd,sse4arg")
302            (const_string "sse")
303          (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft")
304            (const_string "mmx")
305          (eq_attr "type" "other")
306            (const_string "unknown")]
307          (const_string "integer")))
308
309 ;; The (bounding maximum) length of an instruction immediate.
310 (define_attr "length_immediate" ""
311   (cond [(eq_attr "type" "incdec,setcc,icmov,str,lea,other,multi,idiv,leave,
312                           bitmanip")
313            (const_int 0)
314          (eq_attr "unit" "i387,sse,mmx")
315            (const_int 0)
316          (eq_attr "type" "alu,alu1,negnot,imovx,ishift,rotate,ishift1,rotate1,
317                           imul,icmp,push,pop")
318            (symbol_ref "ix86_attr_length_immediate_default(insn,1)")
319          (eq_attr "type" "imov,test")
320            (symbol_ref "ix86_attr_length_immediate_default(insn,0)")
321          (eq_attr "type" "call")
322            (if_then_else (match_operand 0 "constant_call_address_operand" "")
323              (const_int 4)
324              (const_int 0))
325          (eq_attr "type" "callv")
326            (if_then_else (match_operand 1 "constant_call_address_operand" "")
327              (const_int 4)
328              (const_int 0))
329          ;; We don't know the size before shorten_branches.  Expect
330          ;; the instruction to fit for better scheduling.
331          (eq_attr "type" "ibr")
332            (const_int 1)
333          ]
334          (symbol_ref "/* Update immediate_length and other attributes! */
335                       gcc_unreachable (),1")))
336
337 ;; The (bounding maximum) length of an instruction address.
338 (define_attr "length_address" ""
339   (cond [(eq_attr "type" "str,other,multi,fxch")
340            (const_int 0)
341          (and (eq_attr "type" "call")
342               (match_operand 0 "constant_call_address_operand" ""))
343              (const_int 0)
344          (and (eq_attr "type" "callv")
345               (match_operand 1 "constant_call_address_operand" ""))
346              (const_int 0)
347          ]
348          (symbol_ref "ix86_attr_length_address_default (insn)")))
349
350 ;; Set when length prefix is used.
351 (define_attr "prefix_data16" ""
352   (if_then_else (ior (eq_attr "mode" "HI")
353                      (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF")))
354     (const_int 1)
355     (const_int 0)))
356
357 ;; Set when string REP prefix is used.
358 (define_attr "prefix_rep" ""
359   (if_then_else (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF"))
360     (const_int 1)
361     (const_int 0)))
362
363 ;; Set when 0f opcode prefix is used.
364 (define_attr "prefix_0f" ""
365   (if_then_else
366     (ior (eq_attr "type" "imovx,setcc,icmov,bitmanip")
367          (eq_attr "unit" "sse,mmx"))
368     (const_int 1)
369     (const_int 0)))
370
371 ;; Set when REX opcode prefix is used.
372 (define_attr "prefix_rex" ""
373   (cond [(and (eq_attr "mode" "DI")
374               (eq_attr "type" "!push,pop,call,callv,leave,ibr"))
375            (const_int 1)
376          (and (eq_attr "mode" "QI")
377               (ne (symbol_ref "x86_extended_QIreg_mentioned_p (insn)")
378                   (const_int 0)))
379            (const_int 1)
380          (ne (symbol_ref "x86_extended_reg_mentioned_p (insn)")
381              (const_int 0))
382            (const_int 1)
383         ]
384         (const_int 0)))
385
386 ;; There are also additional prefixes in SSSE3.
387 (define_attr "prefix_extra" "" (const_int 0))
388
389 ;; Set when modrm byte is used.
390 (define_attr "modrm" ""
391   (cond [(eq_attr "type" "str,leave")
392            (const_int 0)
393          (eq_attr "unit" "i387")
394            (const_int 0)
395          (and (eq_attr "type" "incdec")
396               (ior (match_operand:SI 1 "register_operand" "")
397                    (match_operand:HI 1 "register_operand" "")))
398            (const_int 0)
399          (and (eq_attr "type" "push")
400               (not (match_operand 1 "memory_operand" "")))
401            (const_int 0)
402          (and (eq_attr "type" "pop")
403               (not (match_operand 0 "memory_operand" "")))
404            (const_int 0)
405          (and (eq_attr "type" "imov")
406               (ior (and (match_operand 0 "register_operand" "")
407                         (match_operand 1 "immediate_operand" ""))
408                    (ior (and (match_operand 0 "ax_reg_operand" "")
409                              (match_operand 1 "memory_displacement_only_operand" ""))
410                         (and (match_operand 0 "memory_displacement_only_operand" "")
411                              (match_operand 1 "ax_reg_operand" "")))))
412            (const_int 0)
413          (and (eq_attr "type" "call")
414               (match_operand 0 "constant_call_address_operand" ""))
415              (const_int 0)
416          (and (eq_attr "type" "callv")
417               (match_operand 1 "constant_call_address_operand" ""))
418              (const_int 0)
419          ]
420          (const_int 1)))
421
422 ;; The (bounding maximum) length of an instruction in bytes.
423 ;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences.
424 ;; Later we may want to split them and compute proper length as for
425 ;; other insns.
426 (define_attr "length" ""
427   (cond [(eq_attr "type" "other,multi,fistp,frndint")
428            (const_int 16)
429          (eq_attr "type" "fcmp")
430            (const_int 4)
431          (eq_attr "unit" "i387")
432            (plus (const_int 2)
433                  (plus (attr "prefix_data16")
434                        (attr "length_address")))]
435          (plus (plus (attr "modrm")
436                      (plus (attr "prefix_0f")
437                            (plus (attr "prefix_rex")
438                                  (plus (attr "prefix_extra")
439                                        (const_int 1)))))
440                (plus (attr "prefix_rep")
441                      (plus (attr "prefix_data16")
442                            (plus (attr "length_immediate")
443                                  (attr "length_address")))))))
444
445 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
446 ;; `store' if there is a simple memory reference therein, or `unknown'
447 ;; if the instruction is complex.
448
449 (define_attr "memory" "none,load,store,both,unknown"
450   (cond [(eq_attr "type" "other,multi,str")
451            (const_string "unknown")
452          (eq_attr "type" "lea,fcmov,fpspc")
453            (const_string "none")
454          (eq_attr "type" "fistp,leave")
455            (const_string "both")
456          (eq_attr "type" "frndint")
457            (const_string "load")
458          (eq_attr "type" "push")
459            (if_then_else (match_operand 1 "memory_operand" "")
460              (const_string "both")
461              (const_string "store"))
462          (eq_attr "type" "pop")
463            (if_then_else (match_operand 0 "memory_operand" "")
464              (const_string "both")
465              (const_string "load"))
466          (eq_attr "type" "setcc")
467            (if_then_else (match_operand 0 "memory_operand" "")
468              (const_string "store")
469              (const_string "none"))
470          (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp")
471            (if_then_else (ior (match_operand 0 "memory_operand" "")
472                               (match_operand 1 "memory_operand" ""))
473              (const_string "load")
474              (const_string "none"))
475          (eq_attr "type" "ibr")
476            (if_then_else (match_operand 0 "memory_operand" "")
477              (const_string "load")
478              (const_string "none"))
479          (eq_attr "type" "call")
480            (if_then_else (match_operand 0 "constant_call_address_operand" "")
481              (const_string "none")
482              (const_string "load"))
483          (eq_attr "type" "callv")
484            (if_then_else (match_operand 1 "constant_call_address_operand" "")
485              (const_string "none")
486              (const_string "load"))
487          (and (eq_attr "type" "alu1,negnot,ishift1,sselog1")
488               (match_operand 1 "memory_operand" ""))
489            (const_string "both")
490          (and (match_operand 0 "memory_operand" "")
491               (match_operand 1 "memory_operand" ""))
492            (const_string "both")
493          (match_operand 0 "memory_operand" "")
494            (const_string "store")
495          (match_operand 1 "memory_operand" "")
496            (const_string "load")
497          (and (eq_attr "type"
498                  "!alu1,negnot,ishift1,
499                    imov,imovx,icmp,test,bitmanip,
500                    fmov,fcmp,fsgn,
501                    sse,ssemov,ssecmp,ssecomi,ssecvt,ssecvt1,sseicvt,sselog1,
502                    sseiadd1,mmx,mmxmov,mmxcmp,mmxcvt")
503               (match_operand 2 "memory_operand" ""))
504            (const_string "load")
505          (and (eq_attr "type" "icmov,ssemuladd,sse4arg")
506               (match_operand 3 "memory_operand" ""))
507            (const_string "load")
508         ]
509         (const_string "none")))
510
511 ;; Indicates if an instruction has both an immediate and a displacement.
512
513 (define_attr "imm_disp" "false,true,unknown"
514   (cond [(eq_attr "type" "other,multi")
515            (const_string "unknown")
516          (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1")
517               (and (match_operand 0 "memory_displacement_operand" "")
518                    (match_operand 1 "immediate_operand" "")))
519            (const_string "true")
520          (and (eq_attr "type" "alu,ishift,rotate,imul,idiv")
521               (and (match_operand 0 "memory_displacement_operand" "")
522                    (match_operand 2 "immediate_operand" "")))
523            (const_string "true")
524         ]
525         (const_string "false")))
526
527 ;; Indicates if an FP operation has an integer source.
528
529 (define_attr "fp_int_src" "false,true"
530   (const_string "false"))
531
532 ;; Defines rounding mode of an FP operation.
533
534 (define_attr "i387_cw" "trunc,floor,ceil,mask_pm,uninitialized,any"
535   (const_string "any"))
536
537 ;; Describe a user's asm statement.
538 (define_asm_attributes
539   [(set_attr "length" "128")
540    (set_attr "type" "multi")])
541
542 ;; All integer comparison codes.
543 (define_code_iterator int_cond [ne eq ge gt le lt geu gtu leu ltu ])
544
545 ;; All floating-point comparison codes.
546 (define_code_iterator fp_cond [unordered ordered
547                                uneq unge ungt unle unlt ltgt ])
548
549 (define_code_iterator plusminus [plus minus])
550
551 (define_code_iterator sat_plusminus [ss_plus us_plus ss_minus us_minus])
552
553 ;; Base name for define_insn
554 (define_code_attr plusminus_insn
555   [(plus "add") (ss_plus "ssadd") (us_plus "usadd")
556    (minus "sub") (ss_minus "sssub") (us_minus "ussub")])
557
558 ;; Base name for insn mnemonic.
559 (define_code_attr plusminus_mnemonic
560   [(plus "add") (ss_plus "adds") (us_plus "addus")
561    (minus "sub") (ss_minus "subs") (us_minus "subus")])
562
563 ;; Mark commutative operators as such in constraints.
564 (define_code_attr comm [(plus "%") (ss_plus "%") (us_plus "%")
565                         (minus "") (ss_minus "") (us_minus "")])
566
567 ;; Mapping of signed max and min
568 (define_code_iterator smaxmin [smax smin])
569
570 ;; Mapping of unsigned max and min
571 (define_code_iterator umaxmin [umax umin])
572
573 ;; Base name for integer and FP insn mnemonic
574 (define_code_attr maxminiprefix [(smax "maxs") (smin "mins")
575                                  (umax "maxu") (umin "minu")])
576 (define_code_attr maxminfprefix [(smax "max") (smin "min")])
577
578 ;; Mapping of parallel logic operators
579 (define_code_iterator plogic [and ior xor])
580
581 ;; Base name for insn mnemonic.
582 (define_code_attr plogicprefix [(and "and") (ior "or") (xor "xor")])
583
584 ;; Mapping of abs neg operators
585 (define_code_iterator absneg [abs neg])
586
587 ;; Base name for x87 insn mnemonic.
588 (define_code_attr absnegprefix [(abs "abs") (neg "chs")])
589
590 ;; All single word integer modes.
591 (define_mode_iterator SWI [QI HI SI (DI "TARGET_64BIT")])
592
593 ;; Instruction suffix for integer modes.
594 (define_mode_attr imodesuffix [(QI "b") (HI "w") (SI "l") (DI "q")])
595
596 ;; Register class for integer modes.
597 (define_mode_attr r [(QI "q") (HI "r") (SI "r") (DI "r")])
598
599 ;; Immediate operand constraint for integer modes.
600 (define_mode_attr i [(QI "i") (HI "i") (SI "i") (DI "e")])
601
602 ;; General operand predicate for integer modes.
603 (define_mode_attr general_operand
604         [(QI "general_operand")
605          (HI "general_operand")
606          (SI "general_operand")
607          (DI "x86_64_general_operand")])
608
609 ;; SSE and x87 SFmode and DFmode floating point modes
610 (define_mode_iterator MODEF [SF DF])
611
612 ;; All x87 floating point modes
613 (define_mode_iterator X87MODEF [SF DF XF])
614
615 ;; All integer modes handled by x87 fisttp operator.
616 (define_mode_iterator X87MODEI [HI SI DI])
617
618 ;; All integer modes handled by integer x87 operators.
619 (define_mode_iterator X87MODEI12 [HI SI])
620
621 ;; All integer modes handled by SSE cvtts?2si* operators.
622 (define_mode_iterator SSEMODEI24 [SI DI])
623
624 ;; SSE asm suffix for floating point modes
625 (define_mode_attr ssemodefsuffix [(SF "s") (DF "d")])
626
627 ;; SSE vector mode corresponding to a scalar mode
628 (define_mode_attr ssevecmode
629   [(QI "V16QI") (HI "V8HI") (SI "V4SI") (DI "V2DI") (SF "V4SF") (DF "V2DF")])
630
631 ;; Instruction suffix for REX 64bit operators.
632 (define_mode_attr rex64suffix [(SI "") (DI "{q}")])
633
634 ;; This mode iterator allows :P to be used for patterns that operate on
635 ;; pointer-sized quantities.  Exactly one of the two alternatives will match.
636 (define_mode_iterator P [(SI "Pmode == SImode") (DI "Pmode == DImode")])
637
638 \f
639 ;; Scheduling descriptions
640
641 (include "pentium.md")
642 (include "ppro.md")
643 (include "k6.md")
644 (include "athlon.md")
645 (include "geode.md")
646
647 \f
648 ;; Operand and operator predicates and constraints
649
650 (include "predicates.md")
651 (include "constraints.md")
652
653 \f
654 ;; Compare instructions.
655
656 ;; All compare insns have expanders that save the operands away without
657 ;; actually generating RTL.  The bCOND or sCOND (emitted immediately
658 ;; after the cmp) will actually emit the cmpM.
659
660 (define_expand "cmpti"
661   [(set (reg:CC FLAGS_REG)
662         (compare:CC (match_operand:TI 0 "nonimmediate_operand" "")
663                     (match_operand:TI 1 "x86_64_general_operand" "")))]
664   "TARGET_64BIT"
665 {
666   if (MEM_P (operands[0]) && MEM_P (operands[1]))
667     operands[0] = force_reg (TImode, operands[0]);
668   ix86_compare_op0 = operands[0];
669   ix86_compare_op1 = operands[1];
670   DONE;
671 })
672
673 (define_expand "cmpdi"
674   [(set (reg:CC FLAGS_REG)
675         (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
676                     (match_operand:DI 1 "x86_64_general_operand" "")))]
677   ""
678 {
679   if (MEM_P (operands[0]) && MEM_P (operands[1]))
680     operands[0] = force_reg (DImode, operands[0]);
681   ix86_compare_op0 = operands[0];
682   ix86_compare_op1 = operands[1];
683   DONE;
684 })
685
686 (define_expand "cmpsi"
687   [(set (reg:CC FLAGS_REG)
688         (compare:CC (match_operand:SI 0 "cmpsi_operand" "")
689                     (match_operand:SI 1 "general_operand" "")))]
690   ""
691 {
692   if (MEM_P (operands[0]) && MEM_P (operands[1]))
693     operands[0] = force_reg (SImode, operands[0]);
694   ix86_compare_op0 = operands[0];
695   ix86_compare_op1 = operands[1];
696   DONE;
697 })
698
699 (define_expand "cmphi"
700   [(set (reg:CC FLAGS_REG)
701         (compare:CC (match_operand:HI 0 "nonimmediate_operand" "")
702                     (match_operand:HI 1 "general_operand" "")))]
703   ""
704 {
705   if (MEM_P (operands[0]) && MEM_P (operands[1]))
706     operands[0] = force_reg (HImode, operands[0]);
707   ix86_compare_op0 = operands[0];
708   ix86_compare_op1 = operands[1];
709   DONE;
710 })
711
712 (define_expand "cmpqi"
713   [(set (reg:CC FLAGS_REG)
714         (compare:CC (match_operand:QI 0 "nonimmediate_operand" "")
715                     (match_operand:QI 1 "general_operand" "")))]
716   "TARGET_QIMODE_MATH"
717 {
718   if (MEM_P (operands[0]) && MEM_P (operands[1]))
719     operands[0] = force_reg (QImode, operands[0]);
720   ix86_compare_op0 = operands[0];
721   ix86_compare_op1 = operands[1];
722   DONE;
723 })
724
725 (define_insn "cmpdi_ccno_1_rex64"
726   [(set (reg FLAGS_REG)
727         (compare (match_operand:DI 0 "nonimmediate_operand" "r,?mr")
728                  (match_operand:DI 1 "const0_operand" "n,n")))]
729   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
730   "@
731    test{q}\t%0, %0
732    cmp{q}\t{%1, %0|%0, %1}"
733   [(set_attr "type" "test,icmp")
734    (set_attr "length_immediate" "0,1")
735    (set_attr "mode" "DI")])
736
737 (define_insn "*cmpdi_minus_1_rex64"
738   [(set (reg FLAGS_REG)
739         (compare (minus:DI (match_operand:DI 0 "nonimmediate_operand" "rm,r")
740                            (match_operand:DI 1 "x86_64_general_operand" "re,mr"))
741                  (const_int 0)))]
742   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)"
743   "cmp{q}\t{%1, %0|%0, %1}"
744   [(set_attr "type" "icmp")
745    (set_attr "mode" "DI")])
746
747 (define_expand "cmpdi_1_rex64"
748   [(set (reg:CC FLAGS_REG)
749         (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
750                     (match_operand:DI 1 "general_operand" "")))]
751   "TARGET_64BIT"
752   "")
753
754 (define_insn "cmpdi_1_insn_rex64"
755   [(set (reg FLAGS_REG)
756         (compare (match_operand:DI 0 "nonimmediate_operand" "mr,r")
757                  (match_operand:DI 1 "x86_64_general_operand" "re,mr")))]
758   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
759   "cmp{q}\t{%1, %0|%0, %1}"
760   [(set_attr "type" "icmp")
761    (set_attr "mode" "DI")])
762
763
764 (define_insn "*cmpsi_ccno_1"
765   [(set (reg FLAGS_REG)
766         (compare (match_operand:SI 0 "nonimmediate_operand" "r,?mr")
767                  (match_operand:SI 1 "const0_operand" "n,n")))]
768   "ix86_match_ccmode (insn, CCNOmode)"
769   "@
770    test{l}\t%0, %0
771    cmp{l}\t{%1, %0|%0, %1}"
772   [(set_attr "type" "test,icmp")
773    (set_attr "length_immediate" "0,1")
774    (set_attr "mode" "SI")])
775
776 (define_insn "*cmpsi_minus_1"
777   [(set (reg FLAGS_REG)
778         (compare (minus:SI (match_operand:SI 0 "nonimmediate_operand" "rm,r")
779                            (match_operand:SI 1 "general_operand" "ri,mr"))
780                  (const_int 0)))]
781   "ix86_match_ccmode (insn, CCGOCmode)"
782   "cmp{l}\t{%1, %0|%0, %1}"
783   [(set_attr "type" "icmp")
784    (set_attr "mode" "SI")])
785
786 (define_expand "cmpsi_1"
787   [(set (reg:CC FLAGS_REG)
788         (compare:CC (match_operand:SI 0 "nonimmediate_operand" "")
789                     (match_operand:SI 1 "general_operand" "")))]
790   ""
791   "")
792
793 (define_insn "*cmpsi_1_insn"
794   [(set (reg FLAGS_REG)
795         (compare (match_operand:SI 0 "nonimmediate_operand" "rm,r")
796                  (match_operand:SI 1 "general_operand" "ri,mr")))]
797   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
798     && ix86_match_ccmode (insn, CCmode)"
799   "cmp{l}\t{%1, %0|%0, %1}"
800   [(set_attr "type" "icmp")
801    (set_attr "mode" "SI")])
802
803 (define_insn "*cmphi_ccno_1"
804   [(set (reg FLAGS_REG)
805         (compare (match_operand:HI 0 "nonimmediate_operand" "r,?mr")
806                  (match_operand:HI 1 "const0_operand" "n,n")))]
807   "ix86_match_ccmode (insn, CCNOmode)"
808   "@
809    test{w}\t%0, %0
810    cmp{w}\t{%1, %0|%0, %1}"
811   [(set_attr "type" "test,icmp")
812    (set_attr "length_immediate" "0,1")
813    (set_attr "mode" "HI")])
814
815 (define_insn "*cmphi_minus_1"
816   [(set (reg FLAGS_REG)
817         (compare (minus:HI (match_operand:HI 0 "nonimmediate_operand" "rm,r")
818                            (match_operand:HI 1 "general_operand" "ri,mr"))
819                  (const_int 0)))]
820   "ix86_match_ccmode (insn, CCGOCmode)"
821   "cmp{w}\t{%1, %0|%0, %1}"
822   [(set_attr "type" "icmp")
823    (set_attr "mode" "HI")])
824
825 (define_insn "*cmphi_1"
826   [(set (reg FLAGS_REG)
827         (compare (match_operand:HI 0 "nonimmediate_operand" "rm,r")
828                  (match_operand:HI 1 "general_operand" "ri,mr")))]
829   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
830    && ix86_match_ccmode (insn, CCmode)"
831   "cmp{w}\t{%1, %0|%0, %1}"
832   [(set_attr "type" "icmp")
833    (set_attr "mode" "HI")])
834
835 (define_insn "*cmpqi_ccno_1"
836   [(set (reg FLAGS_REG)
837         (compare (match_operand:QI 0 "nonimmediate_operand" "q,?mq")
838                  (match_operand:QI 1 "const0_operand" "n,n")))]
839   "ix86_match_ccmode (insn, CCNOmode)"
840   "@
841    test{b}\t%0, %0
842    cmp{b}\t{$0, %0|%0, 0}"
843   [(set_attr "type" "test,icmp")
844    (set_attr "length_immediate" "0,1")
845    (set_attr "mode" "QI")])
846
847 (define_insn "*cmpqi_1"
848   [(set (reg FLAGS_REG)
849         (compare (match_operand:QI 0 "nonimmediate_operand" "qm,q")
850                  (match_operand:QI 1 "general_operand" "qi,mq")))]
851   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
852     && ix86_match_ccmode (insn, CCmode)"
853   "cmp{b}\t{%1, %0|%0, %1}"
854   [(set_attr "type" "icmp")
855    (set_attr "mode" "QI")])
856
857 (define_insn "*cmpqi_minus_1"
858   [(set (reg FLAGS_REG)
859         (compare (minus:QI (match_operand:QI 0 "nonimmediate_operand" "qm,q")
860                            (match_operand:QI 1 "general_operand" "qi,mq"))
861                  (const_int 0)))]
862   "ix86_match_ccmode (insn, CCGOCmode)"
863   "cmp{b}\t{%1, %0|%0, %1}"
864   [(set_attr "type" "icmp")
865    (set_attr "mode" "QI")])
866
867 (define_insn "*cmpqi_ext_1"
868   [(set (reg FLAGS_REG)
869         (compare
870           (match_operand:QI 0 "general_operand" "Qm")
871           (subreg:QI
872             (zero_extract:SI
873               (match_operand 1 "ext_register_operand" "Q")
874               (const_int 8)
875               (const_int 8)) 0)))]
876   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
877   "cmp{b}\t{%h1, %0|%0, %h1}"
878   [(set_attr "type" "icmp")
879    (set_attr "mode" "QI")])
880
881 (define_insn "*cmpqi_ext_1_rex64"
882   [(set (reg FLAGS_REG)
883         (compare
884           (match_operand:QI 0 "register_operand" "Q")
885           (subreg:QI
886             (zero_extract:SI
887               (match_operand 1 "ext_register_operand" "Q")
888               (const_int 8)
889               (const_int 8)) 0)))]
890   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
891   "cmp{b}\t{%h1, %0|%0, %h1}"
892   [(set_attr "type" "icmp")
893    (set_attr "mode" "QI")])
894
895 (define_insn "*cmpqi_ext_2"
896   [(set (reg FLAGS_REG)
897         (compare
898           (subreg:QI
899             (zero_extract:SI
900               (match_operand 0 "ext_register_operand" "Q")
901               (const_int 8)
902               (const_int 8)) 0)
903           (match_operand:QI 1 "const0_operand" "n")))]
904   "ix86_match_ccmode (insn, CCNOmode)"
905   "test{b}\t%h0, %h0"
906   [(set_attr "type" "test")
907    (set_attr "length_immediate" "0")
908    (set_attr "mode" "QI")])
909
910 (define_expand "cmpqi_ext_3"
911   [(set (reg:CC FLAGS_REG)
912         (compare:CC
913           (subreg:QI
914             (zero_extract:SI
915               (match_operand 0 "ext_register_operand" "")
916               (const_int 8)
917               (const_int 8)) 0)
918           (match_operand:QI 1 "general_operand" "")))]
919   ""
920   "")
921
922 (define_insn "cmpqi_ext_3_insn"
923   [(set (reg FLAGS_REG)
924         (compare
925           (subreg:QI
926             (zero_extract:SI
927               (match_operand 0 "ext_register_operand" "Q")
928               (const_int 8)
929               (const_int 8)) 0)
930           (match_operand:QI 1 "general_operand" "Qmn")))]
931   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
932   "cmp{b}\t{%1, %h0|%h0, %1}"
933   [(set_attr "type" "icmp")
934    (set_attr "mode" "QI")])
935
936 (define_insn "cmpqi_ext_3_insn_rex64"
937   [(set (reg FLAGS_REG)
938         (compare
939           (subreg:QI
940             (zero_extract:SI
941               (match_operand 0 "ext_register_operand" "Q")
942               (const_int 8)
943               (const_int 8)) 0)
944           (match_operand:QI 1 "nonmemory_operand" "Qn")))]
945   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
946   "cmp{b}\t{%1, %h0|%h0, %1}"
947   [(set_attr "type" "icmp")
948    (set_attr "mode" "QI")])
949
950 (define_insn "*cmpqi_ext_4"
951   [(set (reg FLAGS_REG)
952         (compare
953           (subreg:QI
954             (zero_extract:SI
955               (match_operand 0 "ext_register_operand" "Q")
956               (const_int 8)
957               (const_int 8)) 0)
958           (subreg:QI
959             (zero_extract:SI
960               (match_operand 1 "ext_register_operand" "Q")
961               (const_int 8)
962               (const_int 8)) 0)))]
963   "ix86_match_ccmode (insn, CCmode)"
964   "cmp{b}\t{%h1, %h0|%h0, %h1}"
965   [(set_attr "type" "icmp")
966    (set_attr "mode" "QI")])
967
968 ;; These implement float point compares.
969 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
970 ;; which would allow mix and match FP modes on the compares.  Which is what
971 ;; the old patterns did, but with many more of them.
972
973 (define_expand "cmpxf"
974   [(set (reg:CC FLAGS_REG)
975         (compare:CC (match_operand:XF 0 "nonmemory_operand" "")
976                     (match_operand:XF 1 "nonmemory_operand" "")))]
977   "TARGET_80387"
978 {
979   ix86_compare_op0 = operands[0];
980   ix86_compare_op1 = operands[1];
981   DONE;
982 })
983
984 (define_expand "cmp<mode>"
985   [(set (reg:CC FLAGS_REG)
986         (compare:CC (match_operand:MODEF 0 "cmp_fp_expander_operand" "")
987                     (match_operand:MODEF 1 "cmp_fp_expander_operand" "")))]
988   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
989 {
990   ix86_compare_op0 = operands[0];
991   ix86_compare_op1 = operands[1];
992   DONE;
993 })
994
995 ;; FP compares, step 1:
996 ;; Set the FP condition codes.
997 ;;
998 ;; CCFPmode     compare with exceptions
999 ;; CCFPUmode    compare with no exceptions
1000
1001 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
1002 ;; used to manage the reg stack popping would not be preserved.
1003
1004 (define_insn "*cmpfp_0"
1005   [(set (match_operand:HI 0 "register_operand" "=a")
1006         (unspec:HI
1007           [(compare:CCFP
1008              (match_operand 1 "register_operand" "f")
1009              (match_operand 2 "const0_operand" "X"))]
1010         UNSPEC_FNSTSW))]
1011   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1012    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1013   "* return output_fp_compare (insn, operands, 0, 0);"
1014   [(set_attr "type" "multi")
1015    (set_attr "unit" "i387")
1016    (set (attr "mode")
1017      (cond [(match_operand:SF 1 "" "")
1018               (const_string "SF")
1019             (match_operand:DF 1 "" "")
1020               (const_string "DF")
1021            ]
1022            (const_string "XF")))])
1023
1024 (define_insn_and_split "*cmpfp_0_cc"
1025   [(set (reg:CCFP FLAGS_REG)
1026         (compare:CCFP
1027           (match_operand 1 "register_operand" "f")
1028           (match_operand 2 "const0_operand" "X")))
1029    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1030   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1031    && TARGET_SAHF && !TARGET_CMOVE
1032    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1033   "#"
1034   "&& reload_completed"
1035   [(set (match_dup 0)
1036         (unspec:HI
1037           [(compare:CCFP (match_dup 1)(match_dup 2))]
1038         UNSPEC_FNSTSW))
1039    (set (reg:CC FLAGS_REG)
1040         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1041   ""
1042   [(set_attr "type" "multi")
1043    (set_attr "unit" "i387")
1044    (set (attr "mode")
1045      (cond [(match_operand:SF 1 "" "")
1046               (const_string "SF")
1047             (match_operand:DF 1 "" "")
1048               (const_string "DF")
1049            ]
1050            (const_string "XF")))])
1051
1052 (define_insn "*cmpfp_xf"
1053   [(set (match_operand:HI 0 "register_operand" "=a")
1054         (unspec:HI
1055           [(compare:CCFP
1056              (match_operand:XF 1 "register_operand" "f")
1057              (match_operand:XF 2 "register_operand" "f"))]
1058           UNSPEC_FNSTSW))]
1059   "TARGET_80387"
1060   "* return output_fp_compare (insn, operands, 0, 0);"
1061   [(set_attr "type" "multi")
1062    (set_attr "unit" "i387")
1063    (set_attr "mode" "XF")])
1064
1065 (define_insn_and_split "*cmpfp_xf_cc"
1066   [(set (reg:CCFP FLAGS_REG)
1067         (compare:CCFP
1068           (match_operand:XF 1 "register_operand" "f")
1069           (match_operand:XF 2 "register_operand" "f")))
1070    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1071   "TARGET_80387
1072    && TARGET_SAHF && !TARGET_CMOVE"
1073   "#"
1074   "&& reload_completed"
1075   [(set (match_dup 0)
1076         (unspec:HI
1077           [(compare:CCFP (match_dup 1)(match_dup 2))]
1078         UNSPEC_FNSTSW))
1079    (set (reg:CC FLAGS_REG)
1080         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1081   ""
1082   [(set_attr "type" "multi")
1083    (set_attr "unit" "i387")
1084    (set_attr "mode" "XF")])
1085
1086 (define_insn "*cmpfp_<mode>"
1087   [(set (match_operand:HI 0 "register_operand" "=a")
1088         (unspec:HI
1089           [(compare:CCFP
1090              (match_operand:MODEF 1 "register_operand" "f")
1091              (match_operand:MODEF 2 "nonimmediate_operand" "fm"))]
1092           UNSPEC_FNSTSW))]
1093   "TARGET_80387"
1094   "* return output_fp_compare (insn, operands, 0, 0);"
1095   [(set_attr "type" "multi")
1096    (set_attr "unit" "i387")
1097    (set_attr "mode" "<MODE>")])
1098
1099 (define_insn_and_split "*cmpfp_<mode>_cc"
1100   [(set (reg:CCFP FLAGS_REG)
1101         (compare:CCFP
1102           (match_operand:MODEF 1 "register_operand" "f")
1103           (match_operand:MODEF 2 "nonimmediate_operand" "fm")))
1104    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1105   "TARGET_80387
1106    && TARGET_SAHF && !TARGET_CMOVE"
1107   "#"
1108   "&& reload_completed"
1109   [(set (match_dup 0)
1110         (unspec:HI
1111           [(compare:CCFP (match_dup 1)(match_dup 2))]
1112         UNSPEC_FNSTSW))
1113    (set (reg:CC FLAGS_REG)
1114         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1115   ""
1116   [(set_attr "type" "multi")
1117    (set_attr "unit" "i387")
1118    (set_attr "mode" "<MODE>")])
1119
1120 (define_insn "*cmpfp_u"
1121   [(set (match_operand:HI 0 "register_operand" "=a")
1122         (unspec:HI
1123           [(compare:CCFPU
1124              (match_operand 1 "register_operand" "f")
1125              (match_operand 2 "register_operand" "f"))]
1126           UNSPEC_FNSTSW))]
1127   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1128    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1129   "* return output_fp_compare (insn, operands, 0, 1);"
1130   [(set_attr "type" "multi")
1131    (set_attr "unit" "i387")
1132    (set (attr "mode")
1133      (cond [(match_operand:SF 1 "" "")
1134               (const_string "SF")
1135             (match_operand:DF 1 "" "")
1136               (const_string "DF")
1137            ]
1138            (const_string "XF")))])
1139
1140 (define_insn_and_split "*cmpfp_u_cc"
1141   [(set (reg:CCFPU FLAGS_REG)
1142         (compare:CCFPU
1143           (match_operand 1 "register_operand" "f")
1144           (match_operand 2 "register_operand" "f")))
1145    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1146   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1147    && TARGET_SAHF && !TARGET_CMOVE
1148    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1149   "#"
1150   "&& reload_completed"
1151   [(set (match_dup 0)
1152         (unspec:HI
1153           [(compare:CCFPU (match_dup 1)(match_dup 2))]
1154         UNSPEC_FNSTSW))
1155    (set (reg:CC FLAGS_REG)
1156         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1157   ""
1158   [(set_attr "type" "multi")
1159    (set_attr "unit" "i387")
1160    (set (attr "mode")
1161      (cond [(match_operand:SF 1 "" "")
1162               (const_string "SF")
1163             (match_operand:DF 1 "" "")
1164               (const_string "DF")
1165            ]
1166            (const_string "XF")))])
1167
1168 (define_insn "*cmpfp_<mode>"
1169   [(set (match_operand:HI 0 "register_operand" "=a")
1170         (unspec:HI
1171           [(compare:CCFP
1172              (match_operand 1 "register_operand" "f")
1173              (match_operator 3 "float_operator"
1174                [(match_operand:X87MODEI12 2 "memory_operand" "m")]))]
1175           UNSPEC_FNSTSW))]
1176   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1177    && (TARGET_USE_<MODE>MODE_FIOP || optimize_size)
1178    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1179   "* return output_fp_compare (insn, operands, 0, 0);"
1180   [(set_attr "type" "multi")
1181    (set_attr "unit" "i387")
1182    (set_attr "fp_int_src" "true")
1183    (set_attr "mode" "<MODE>")])
1184
1185 (define_insn_and_split "*cmpfp_<mode>_cc"
1186   [(set (reg:CCFP FLAGS_REG)
1187         (compare:CCFP
1188           (match_operand 1 "register_operand" "f")
1189           (match_operator 3 "float_operator"
1190             [(match_operand:X87MODEI12 2 "memory_operand" "m")])))
1191    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1192   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1193    && TARGET_SAHF && !TARGET_CMOVE
1194    && (TARGET_USE_<MODE>MODE_FIOP || optimize_size)
1195    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1196   "#"
1197   "&& reload_completed"
1198   [(set (match_dup 0)
1199         (unspec:HI
1200           [(compare:CCFP
1201              (match_dup 1)
1202              (match_op_dup 3 [(match_dup 2)]))]
1203         UNSPEC_FNSTSW))
1204    (set (reg:CC FLAGS_REG)
1205         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1206   ""
1207   [(set_attr "type" "multi")
1208    (set_attr "unit" "i387")
1209    (set_attr "fp_int_src" "true")
1210    (set_attr "mode" "<MODE>")])
1211
1212 ;; FP compares, step 2
1213 ;; Move the fpsw to ax.
1214
1215 (define_insn "x86_fnstsw_1"
1216   [(set (match_operand:HI 0 "register_operand" "=a")
1217         (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))]
1218   "TARGET_80387"
1219   "fnstsw\t%0"
1220   [(set_attr "length" "2")
1221    (set_attr "mode" "SI")
1222    (set_attr "unit" "i387")])
1223
1224 ;; FP compares, step 3
1225 ;; Get ax into flags, general case.
1226
1227 (define_insn "x86_sahf_1"
1228   [(set (reg:CC FLAGS_REG)
1229         (unspec:CC [(match_operand:HI 0 "register_operand" "a")]
1230                    UNSPEC_SAHF))]
1231   "TARGET_SAHF"
1232 {
1233 #ifdef HAVE_AS_IX86_SAHF
1234   return "sahf";
1235 #else
1236   return ".byte\t0x9e";
1237 #endif
1238 }
1239   [(set_attr "length" "1")
1240    (set_attr "athlon_decode" "vector")
1241    (set_attr "amdfam10_decode" "direct")
1242    (set_attr "mode" "SI")])
1243
1244 ;; Pentium Pro can do steps 1 through 3 in one go.
1245 ;; comi*, ucomi*, fcomi*, ficomi*,fucomi* (i387 instructions set condition codes)
1246 (define_insn "*cmpfp_i_mixed"
1247   [(set (reg:CCFP FLAGS_REG)
1248         (compare:CCFP (match_operand 0 "register_operand" "f,x")
1249                       (match_operand 1 "nonimmediate_operand" "f,xm")))]
1250   "TARGET_MIX_SSE_I387
1251    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1252    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1253   "* return output_fp_compare (insn, operands, 1, 0);"
1254   [(set_attr "type" "fcmp,ssecomi")
1255    (set (attr "mode")
1256      (if_then_else (match_operand:SF 1 "" "")
1257         (const_string "SF")
1258         (const_string "DF")))
1259    (set_attr "athlon_decode" "vector")
1260    (set_attr "amdfam10_decode" "direct")])
1261
1262 (define_insn "*cmpfp_i_sse"
1263   [(set (reg:CCFP FLAGS_REG)
1264         (compare:CCFP (match_operand 0 "register_operand" "x")
1265                       (match_operand 1 "nonimmediate_operand" "xm")))]
1266   "TARGET_SSE_MATH
1267    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1268    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1269   "* return output_fp_compare (insn, operands, 1, 0);"
1270   [(set_attr "type" "ssecomi")
1271    (set (attr "mode")
1272      (if_then_else (match_operand:SF 1 "" "")
1273         (const_string "SF")
1274         (const_string "DF")))
1275    (set_attr "athlon_decode" "vector")
1276    (set_attr "amdfam10_decode" "direct")])
1277
1278 (define_insn "*cmpfp_i_i387"
1279   [(set (reg:CCFP FLAGS_REG)
1280         (compare:CCFP (match_operand 0 "register_operand" "f")
1281                       (match_operand 1 "register_operand" "f")))]
1282   "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1283    && TARGET_CMOVE
1284    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1285    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1286   "* return output_fp_compare (insn, operands, 1, 0);"
1287   [(set_attr "type" "fcmp")
1288    (set (attr "mode")
1289      (cond [(match_operand:SF 1 "" "")
1290               (const_string "SF")
1291             (match_operand:DF 1 "" "")
1292               (const_string "DF")
1293            ]
1294            (const_string "XF")))
1295    (set_attr "athlon_decode" "vector")
1296    (set_attr "amdfam10_decode" "direct")])
1297
1298 (define_insn "*cmpfp_iu_mixed"
1299   [(set (reg:CCFPU FLAGS_REG)
1300         (compare:CCFPU (match_operand 0 "register_operand" "f,x")
1301                        (match_operand 1 "nonimmediate_operand" "f,xm")))]
1302   "TARGET_MIX_SSE_I387
1303    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1304    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1305   "* return output_fp_compare (insn, operands, 1, 1);"
1306   [(set_attr "type" "fcmp,ssecomi")
1307    (set (attr "mode")
1308      (if_then_else (match_operand:SF 1 "" "")
1309         (const_string "SF")
1310         (const_string "DF")))
1311    (set_attr "athlon_decode" "vector")
1312    (set_attr "amdfam10_decode" "direct")])
1313
1314 (define_insn "*cmpfp_iu_sse"
1315   [(set (reg:CCFPU FLAGS_REG)
1316         (compare:CCFPU (match_operand 0 "register_operand" "x")
1317                        (match_operand 1 "nonimmediate_operand" "xm")))]
1318   "TARGET_SSE_MATH
1319    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1320    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1321   "* return output_fp_compare (insn, operands, 1, 1);"
1322   [(set_attr "type" "ssecomi")
1323    (set (attr "mode")
1324      (if_then_else (match_operand:SF 1 "" "")
1325         (const_string "SF")
1326         (const_string "DF")))
1327    (set_attr "athlon_decode" "vector")
1328    (set_attr "amdfam10_decode" "direct")])
1329
1330 (define_insn "*cmpfp_iu_387"
1331   [(set (reg:CCFPU FLAGS_REG)
1332         (compare:CCFPU (match_operand 0 "register_operand" "f")
1333                        (match_operand 1 "register_operand" "f")))]
1334   "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1335    && TARGET_CMOVE
1336    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1337    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1338   "* return output_fp_compare (insn, operands, 1, 1);"
1339   [(set_attr "type" "fcmp")
1340    (set (attr "mode")
1341      (cond [(match_operand:SF 1 "" "")
1342               (const_string "SF")
1343             (match_operand:DF 1 "" "")
1344               (const_string "DF")
1345            ]
1346            (const_string "XF")))
1347    (set_attr "athlon_decode" "vector")
1348    (set_attr "amdfam10_decode" "direct")])
1349 \f
1350 ;; Move instructions.
1351
1352 ;; General case of fullword move.
1353
1354 (define_expand "movsi"
1355   [(set (match_operand:SI 0 "nonimmediate_operand" "")
1356         (match_operand:SI 1 "general_operand" ""))]
1357   ""
1358   "ix86_expand_move (SImode, operands); DONE;")
1359
1360 ;; Push/pop instructions.  They are separate since autoinc/dec is not a
1361 ;; general_operand.
1362 ;;
1363 ;; %%% We don't use a post-inc memory reference because x86 is not a
1364 ;; general AUTO_INC_DEC host, which impacts how it is treated in flow.
1365 ;; Changing this impacts compiler performance on other non-AUTO_INC_DEC
1366 ;; targets without our curiosities, and it is just as easy to represent
1367 ;; this differently.
1368
1369 (define_insn "*pushsi2"
1370   [(set (match_operand:SI 0 "push_operand" "=<")
1371         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1372   "!TARGET_64BIT"
1373   "push{l}\t%1"
1374   [(set_attr "type" "push")
1375    (set_attr "mode" "SI")])
1376
1377 ;; For 64BIT abi we always round up to 8 bytes.
1378 (define_insn "*pushsi2_rex64"
1379   [(set (match_operand:SI 0 "push_operand" "=X")
1380         (match_operand:SI 1 "nonmemory_no_elim_operand" "ri"))]
1381   "TARGET_64BIT"
1382   "push{q}\t%q1"
1383   [(set_attr "type" "push")
1384    (set_attr "mode" "SI")])
1385
1386 (define_insn "*pushsi2_prologue"
1387   [(set (match_operand:SI 0 "push_operand" "=<")
1388         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))
1389    (clobber (mem:BLK (scratch)))]
1390   "!TARGET_64BIT"
1391   "push{l}\t%1"
1392   [(set_attr "type" "push")
1393    (set_attr "mode" "SI")])
1394
1395 (define_insn "*popsi1_epilogue"
1396   [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1397         (mem:SI (reg:SI SP_REG)))
1398    (set (reg:SI SP_REG)
1399         (plus:SI (reg:SI SP_REG) (const_int 4)))
1400    (clobber (mem:BLK (scratch)))]
1401   "!TARGET_64BIT"
1402   "pop{l}\t%0"
1403   [(set_attr "type" "pop")
1404    (set_attr "mode" "SI")])
1405
1406 (define_insn "popsi1"
1407   [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1408         (mem:SI (reg:SI SP_REG)))
1409    (set (reg:SI SP_REG)
1410         (plus:SI (reg:SI SP_REG) (const_int 4)))]
1411   "!TARGET_64BIT"
1412   "pop{l}\t%0"
1413   [(set_attr "type" "pop")
1414    (set_attr "mode" "SI")])
1415
1416 (define_insn "*movsi_xor"
1417   [(set (match_operand:SI 0 "register_operand" "=r")
1418         (match_operand:SI 1 "const0_operand" "i"))
1419    (clobber (reg:CC FLAGS_REG))]
1420   "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1421   "xor{l}\t%0, %0"
1422   [(set_attr "type" "alu1")
1423    (set_attr "mode" "SI")
1424    (set_attr "length_immediate" "0")])
1425
1426 (define_insn "*movsi_or"
1427   [(set (match_operand:SI 0 "register_operand" "=r")
1428         (match_operand:SI 1 "immediate_operand" "i"))
1429    (clobber (reg:CC FLAGS_REG))]
1430   "reload_completed
1431    && operands[1] == constm1_rtx
1432    && (TARGET_MOVE_M1_VIA_OR || optimize_size)"
1433 {
1434   operands[1] = constm1_rtx;
1435   return "or{l}\t{%1, %0|%0, %1}";
1436 }
1437   [(set_attr "type" "alu1")
1438    (set_attr "mode" "SI")
1439    (set_attr "length_immediate" "1")])
1440
1441 (define_insn "*movsi_1"
1442   [(set (match_operand:SI 0 "nonimmediate_operand"
1443                         "=r  ,m  ,*y,*y,?rm,?*y,*x,*x,?r ,m ,?*Yi,*x")
1444         (match_operand:SI 1 "general_operand"
1445                         "rinm,rin,C ,*y,*y ,rm ,C ,*x,*Yi,*x,r   ,m "))]
1446   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1447 {
1448   switch (get_attr_type (insn))
1449     {
1450     case TYPE_SSELOG1:
1451       if (get_attr_mode (insn) == MODE_TI)
1452         return "pxor\t%0, %0";
1453       return "xorps\t%0, %0";
1454
1455     case TYPE_SSEMOV:
1456       switch (get_attr_mode (insn))
1457         {
1458         case MODE_TI:
1459           return "movdqa\t{%1, %0|%0, %1}";
1460         case MODE_V4SF:
1461           return "movaps\t{%1, %0|%0, %1}";
1462         case MODE_SI:
1463           return "movd\t{%1, %0|%0, %1}";
1464         case MODE_SF:
1465           return "movss\t{%1, %0|%0, %1}";
1466         default:
1467           gcc_unreachable ();
1468         }
1469
1470     case TYPE_MMXADD:
1471       return "pxor\t%0, %0";
1472
1473     case TYPE_MMXMOV:
1474       if (get_attr_mode (insn) == MODE_DI)
1475         return "movq\t{%1, %0|%0, %1}";
1476       return "movd\t{%1, %0|%0, %1}";
1477
1478     case TYPE_LEA:
1479       return "lea{l}\t{%1, %0|%0, %1}";
1480
1481     default:
1482       gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
1483       return "mov{l}\t{%1, %0|%0, %1}";
1484     }
1485 }
1486   [(set (attr "type")
1487      (cond [(eq_attr "alternative" "2")
1488               (const_string "mmxadd")
1489             (eq_attr "alternative" "3,4,5")
1490               (const_string "mmxmov")
1491             (eq_attr "alternative" "6")
1492               (const_string "sselog1")
1493             (eq_attr "alternative" "7,8,9,10,11")
1494               (const_string "ssemov")
1495             (match_operand:DI 1 "pic_32bit_operand" "")
1496               (const_string "lea")
1497            ]
1498            (const_string "imov")))
1499    (set (attr "mode")
1500      (cond [(eq_attr "alternative" "2,3")
1501               (const_string "DI")
1502             (eq_attr "alternative" "6,7")
1503               (if_then_else
1504                 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
1505                 (const_string "V4SF")
1506                 (const_string "TI"))
1507             (and (eq_attr "alternative" "8,9,10,11")
1508                  (eq (symbol_ref "TARGET_SSE2") (const_int 0)))
1509               (const_string "SF")
1510            ]
1511            (const_string "SI")))])
1512
1513 ;; Stores and loads of ax to arbitrary constant address.
1514 ;; We fake an second form of instruction to force reload to load address
1515 ;; into register when rax is not available
1516 (define_insn "*movabssi_1_rex64"
1517   [(set (mem:SI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1518         (match_operand:SI 1 "nonmemory_operand" "a,er"))]
1519   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1520   "@
1521    movabs{l}\t{%1, %P0|%P0, %1}
1522    mov{l}\t{%1, %a0|%a0, %1}"
1523   [(set_attr "type" "imov")
1524    (set_attr "modrm" "0,*")
1525    (set_attr "length_address" "8,0")
1526    (set_attr "length_immediate" "0,*")
1527    (set_attr "memory" "store")
1528    (set_attr "mode" "SI")])
1529
1530 (define_insn "*movabssi_2_rex64"
1531   [(set (match_operand:SI 0 "register_operand" "=a,r")
1532         (mem:SI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1533   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1534   "@
1535    movabs{l}\t{%P1, %0|%0, %P1}
1536    mov{l}\t{%a1, %0|%0, %a1}"
1537   [(set_attr "type" "imov")
1538    (set_attr "modrm" "0,*")
1539    (set_attr "length_address" "8,0")
1540    (set_attr "length_immediate" "0")
1541    (set_attr "memory" "load")
1542    (set_attr "mode" "SI")])
1543
1544 (define_insn "*swapsi"
1545   [(set (match_operand:SI 0 "register_operand" "+r")
1546         (match_operand:SI 1 "register_operand" "+r"))
1547    (set (match_dup 1)
1548         (match_dup 0))]
1549   ""
1550   "xchg{l}\t%1, %0"
1551   [(set_attr "type" "imov")
1552    (set_attr "mode" "SI")
1553    (set_attr "pent_pair" "np")
1554    (set_attr "athlon_decode" "vector")
1555    (set_attr "amdfam10_decode" "double")])
1556
1557 (define_expand "movhi"
1558   [(set (match_operand:HI 0 "nonimmediate_operand" "")
1559         (match_operand:HI 1 "general_operand" ""))]
1560   ""
1561   "ix86_expand_move (HImode, operands); DONE;")
1562
1563 (define_insn "*pushhi2"
1564   [(set (match_operand:HI 0 "push_operand" "=X")
1565         (match_operand:HI 1 "nonmemory_no_elim_operand" "rn"))]
1566   "!TARGET_64BIT"
1567   "push{l}\t%k1"
1568   [(set_attr "type" "push")
1569    (set_attr "mode" "SI")])
1570
1571 ;; For 64BIT abi we always round up to 8 bytes.
1572 (define_insn "*pushhi2_rex64"
1573   [(set (match_operand:HI 0 "push_operand" "=X")
1574         (match_operand:HI 1 "nonmemory_no_elim_operand" "ri"))]
1575   "TARGET_64BIT"
1576   "push{q}\t%q1"
1577   [(set_attr "type" "push")
1578    (set_attr "mode" "DI")])
1579
1580 (define_insn "*movhi_1"
1581   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
1582         (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
1583   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1584 {
1585   switch (get_attr_type (insn))
1586     {
1587     case TYPE_IMOVX:
1588       /* movzwl is faster than movw on p2 due to partial word stalls,
1589          though not as fast as an aligned movl.  */
1590       return "movz{wl|x}\t{%1, %k0|%k0, %1}";
1591     default:
1592       if (get_attr_mode (insn) == MODE_SI)
1593         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1594       else
1595         return "mov{w}\t{%1, %0|%0, %1}";
1596     }
1597 }
1598   [(set (attr "type")
1599      (cond [(ne (symbol_ref "optimize_size") (const_int 0))
1600               (const_string "imov")
1601             (and (eq_attr "alternative" "0")
1602                  (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1603                           (const_int 0))
1604                       (eq (symbol_ref "TARGET_HIMODE_MATH")
1605                           (const_int 0))))
1606               (const_string "imov")
1607             (and (eq_attr "alternative" "1,2")
1608                  (match_operand:HI 1 "aligned_operand" ""))
1609               (const_string "imov")
1610             (and (ne (symbol_ref "TARGET_MOVX")
1611                      (const_int 0))
1612                  (eq_attr "alternative" "0,2"))
1613               (const_string "imovx")
1614            ]
1615            (const_string "imov")))
1616     (set (attr "mode")
1617       (cond [(eq_attr "type" "imovx")
1618                (const_string "SI")
1619              (and (eq_attr "alternative" "1,2")
1620                   (match_operand:HI 1 "aligned_operand" ""))
1621                (const_string "SI")
1622              (and (eq_attr "alternative" "0")
1623                   (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1624                            (const_int 0))
1625                        (eq (symbol_ref "TARGET_HIMODE_MATH")
1626                            (const_int 0))))
1627                (const_string "SI")
1628             ]
1629             (const_string "HI")))])
1630
1631 ;; Stores and loads of ax to arbitrary constant address.
1632 ;; We fake an second form of instruction to force reload to load address
1633 ;; into register when rax is not available
1634 (define_insn "*movabshi_1_rex64"
1635   [(set (mem:HI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1636         (match_operand:HI 1 "nonmemory_operand" "a,er"))]
1637   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1638   "@
1639    movabs{w}\t{%1, %P0|%P0, %1}
1640    mov{w}\t{%1, %a0|%a0, %1}"
1641   [(set_attr "type" "imov")
1642    (set_attr "modrm" "0,*")
1643    (set_attr "length_address" "8,0")
1644    (set_attr "length_immediate" "0,*")
1645    (set_attr "memory" "store")
1646    (set_attr "mode" "HI")])
1647
1648 (define_insn "*movabshi_2_rex64"
1649   [(set (match_operand:HI 0 "register_operand" "=a,r")
1650         (mem:HI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1651   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1652   "@
1653    movabs{w}\t{%P1, %0|%0, %P1}
1654    mov{w}\t{%a1, %0|%0, %a1}"
1655   [(set_attr "type" "imov")
1656    (set_attr "modrm" "0,*")
1657    (set_attr "length_address" "8,0")
1658    (set_attr "length_immediate" "0")
1659    (set_attr "memory" "load")
1660    (set_attr "mode" "HI")])
1661
1662 (define_insn "*swaphi_1"
1663   [(set (match_operand:HI 0 "register_operand" "+r")
1664         (match_operand:HI 1 "register_operand" "+r"))
1665    (set (match_dup 1)
1666         (match_dup 0))]
1667   "!TARGET_PARTIAL_REG_STALL || optimize_size"
1668   "xchg{l}\t%k1, %k0"
1669   [(set_attr "type" "imov")
1670    (set_attr "mode" "SI")
1671    (set_attr "pent_pair" "np")
1672    (set_attr "athlon_decode" "vector")
1673    (set_attr "amdfam10_decode" "double")])
1674
1675 ;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL is disabled for AMDFAM10
1676 (define_insn "*swaphi_2"
1677   [(set (match_operand:HI 0 "register_operand" "+r")
1678         (match_operand:HI 1 "register_operand" "+r"))
1679    (set (match_dup 1)
1680         (match_dup 0))]
1681   "TARGET_PARTIAL_REG_STALL"
1682   "xchg{w}\t%1, %0"
1683   [(set_attr "type" "imov")
1684    (set_attr "mode" "HI")
1685    (set_attr "pent_pair" "np")
1686    (set_attr "athlon_decode" "vector")])
1687
1688 (define_expand "movstricthi"
1689   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" ""))
1690         (match_operand:HI 1 "general_operand" ""))]
1691   "! TARGET_PARTIAL_REG_STALL || optimize_size"
1692 {
1693   /* Don't generate memory->memory moves, go through a register */
1694   if (MEM_P (operands[0]) && MEM_P (operands[1]))
1695     operands[1] = force_reg (HImode, operands[1]);
1696 })
1697
1698 (define_insn "*movstricthi_1"
1699   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+rm,r"))
1700         (match_operand:HI 1 "general_operand" "rn,m"))]
1701   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1702    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1703   "mov{w}\t{%1, %0|%0, %1}"
1704   [(set_attr "type" "imov")
1705    (set_attr "mode" "HI")])
1706
1707 (define_insn "*movstricthi_xor"
1708   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
1709         (match_operand:HI 1 "const0_operand" "i"))
1710    (clobber (reg:CC FLAGS_REG))]
1711   "reload_completed
1712    && ((!TARGET_USE_MOV0 && !TARGET_PARTIAL_REG_STALL) || optimize_size)"
1713   "xor{w}\t%0, %0"
1714   [(set_attr "type" "alu1")
1715    (set_attr "mode" "HI")
1716    (set_attr "length_immediate" "0")])
1717
1718 (define_expand "movqi"
1719   [(set (match_operand:QI 0 "nonimmediate_operand" "")
1720         (match_operand:QI 1 "general_operand" ""))]
1721   ""
1722   "ix86_expand_move (QImode, operands); DONE;")
1723
1724 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1725 ;; "push a byte".  But actually we use pushl, which has the effect
1726 ;; of rounding the amount pushed up to a word.
1727
1728 (define_insn "*pushqi2"
1729   [(set (match_operand:QI 0 "push_operand" "=X")
1730         (match_operand:QI 1 "nonmemory_no_elim_operand" "rn"))]
1731   "!TARGET_64BIT"
1732   "push{l}\t%k1"
1733   [(set_attr "type" "push")
1734    (set_attr "mode" "SI")])
1735
1736 ;; For 64BIT abi we always round up to 8 bytes.
1737 (define_insn "*pushqi2_rex64"
1738   [(set (match_operand:QI 0 "push_operand" "=X")
1739         (match_operand:QI 1 "nonmemory_no_elim_operand" "qi"))]
1740   "TARGET_64BIT"
1741   "push{q}\t%q1"
1742   [(set_attr "type" "push")
1743    (set_attr "mode" "DI")])
1744
1745 ;; Situation is quite tricky about when to choose full sized (SImode) move
1746 ;; over QImode moves.  For Q_REG -> Q_REG move we use full size only for
1747 ;; partial register dependency machines (such as AMD Athlon), where QImode
1748 ;; moves issue extra dependency and for partial register stalls machines
1749 ;; that don't use QImode patterns (and QImode move cause stall on the next
1750 ;; instruction).
1751 ;;
1752 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
1753 ;; register stall machines with, where we use QImode instructions, since
1754 ;; partial register stall can be caused there.  Then we use movzx.
1755 (define_insn "*movqi_1"
1756   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
1757         (match_operand:QI 1 "general_operand"      " q,qn,qm,q,rn,qm,qn"))]
1758   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1759 {
1760   switch (get_attr_type (insn))
1761     {
1762     case TYPE_IMOVX:
1763       gcc_assert (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]));
1764       return "movz{bl|x}\t{%1, %k0|%k0, %1}";
1765     default:
1766       if (get_attr_mode (insn) == MODE_SI)
1767         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1768       else
1769         return "mov{b}\t{%1, %0|%0, %1}";
1770     }
1771 }
1772   [(set (attr "type")
1773      (cond [(and (eq_attr "alternative" "5")
1774                  (not (match_operand:QI 1 "aligned_operand" "")))
1775               (const_string "imovx")
1776             (ne (symbol_ref "optimize_size") (const_int 0))
1777               (const_string "imov")
1778             (and (eq_attr "alternative" "3")
1779                  (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1780                           (const_int 0))
1781                       (eq (symbol_ref "TARGET_QIMODE_MATH")
1782                           (const_int 0))))
1783               (const_string "imov")
1784             (eq_attr "alternative" "3,5")
1785               (const_string "imovx")
1786             (and (ne (symbol_ref "TARGET_MOVX")
1787                      (const_int 0))
1788                  (eq_attr "alternative" "2"))
1789               (const_string "imovx")
1790            ]
1791            (const_string "imov")))
1792    (set (attr "mode")
1793       (cond [(eq_attr "alternative" "3,4,5")
1794                (const_string "SI")
1795              (eq_attr "alternative" "6")
1796                (const_string "QI")
1797              (eq_attr "type" "imovx")
1798                (const_string "SI")
1799              (and (eq_attr "type" "imov")
1800                   (and (eq_attr "alternative" "0,1")
1801                        (and (ne (symbol_ref "TARGET_PARTIAL_REG_DEPENDENCY")
1802                                 (const_int 0))
1803                             (and (eq (symbol_ref "optimize_size")
1804                                      (const_int 0))
1805                                  (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1806                                      (const_int 0))))))
1807                (const_string "SI")
1808              ;; Avoid partial register stalls when not using QImode arithmetic
1809              (and (eq_attr "type" "imov")
1810                   (and (eq_attr "alternative" "0,1")
1811                        (and (ne (symbol_ref "TARGET_PARTIAL_REG_STALL")
1812                                 (const_int 0))
1813                             (eq (symbol_ref "TARGET_QIMODE_MATH")
1814                                 (const_int 0)))))
1815                (const_string "SI")
1816            ]
1817            (const_string "QI")))])
1818
1819 (define_insn "*swapqi_1"
1820   [(set (match_operand:QI 0 "register_operand" "+r")
1821         (match_operand:QI 1 "register_operand" "+r"))
1822    (set (match_dup 1)
1823         (match_dup 0))]
1824   "!TARGET_PARTIAL_REG_STALL || optimize_size"
1825   "xchg{l}\t%k1, %k0"
1826   [(set_attr "type" "imov")
1827    (set_attr "mode" "SI")
1828    (set_attr "pent_pair" "np")
1829    (set_attr "athlon_decode" "vector")
1830    (set_attr "amdfam10_decode" "vector")])
1831
1832 ;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL is disabled for AMDFAM10
1833 (define_insn "*swapqi_2"
1834   [(set (match_operand:QI 0 "register_operand" "+q")
1835         (match_operand:QI 1 "register_operand" "+q"))
1836    (set (match_dup 1)
1837         (match_dup 0))]
1838   "TARGET_PARTIAL_REG_STALL"
1839   "xchg{b}\t%1, %0"
1840   [(set_attr "type" "imov")
1841    (set_attr "mode" "QI")
1842    (set_attr "pent_pair" "np")
1843    (set_attr "athlon_decode" "vector")])
1844
1845 (define_expand "movstrictqi"
1846   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
1847         (match_operand:QI 1 "general_operand" ""))]
1848   "! TARGET_PARTIAL_REG_STALL || optimize_size"
1849 {
1850   /* Don't generate memory->memory moves, go through a register.  */
1851   if (MEM_P (operands[0]) && MEM_P (operands[1]))
1852     operands[1] = force_reg (QImode, operands[1]);
1853 })
1854
1855 (define_insn "*movstrictqi_1"
1856   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
1857         (match_operand:QI 1 "general_operand" "*qn,m"))]
1858   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1859    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1860   "mov{b}\t{%1, %0|%0, %1}"
1861   [(set_attr "type" "imov")
1862    (set_attr "mode" "QI")])
1863
1864 (define_insn "*movstrictqi_xor"
1865   [(set (strict_low_part (match_operand:QI 0 "q_regs_operand" "+q"))
1866         (match_operand:QI 1 "const0_operand" "i"))
1867    (clobber (reg:CC FLAGS_REG))]
1868   "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1869   "xor{b}\t%0, %0"
1870   [(set_attr "type" "alu1")
1871    (set_attr "mode" "QI")
1872    (set_attr "length_immediate" "0")])
1873
1874 (define_insn "*movsi_extv_1"
1875   [(set (match_operand:SI 0 "register_operand" "=R")
1876         (sign_extract:SI (match_operand 1 "ext_register_operand" "Q")
1877                          (const_int 8)
1878                          (const_int 8)))]
1879   ""
1880   "movs{bl|x}\t{%h1, %0|%0, %h1}"
1881   [(set_attr "type" "imovx")
1882    (set_attr "mode" "SI")])
1883
1884 (define_insn "*movhi_extv_1"
1885   [(set (match_operand:HI 0 "register_operand" "=R")
1886         (sign_extract:HI (match_operand 1 "ext_register_operand" "Q")
1887                          (const_int 8)
1888                          (const_int 8)))]
1889   ""
1890   "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
1891   [(set_attr "type" "imovx")
1892    (set_attr "mode" "SI")])
1893
1894 (define_insn "*movqi_extv_1"
1895   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
1896         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1897                          (const_int 8)
1898                          (const_int 8)))]
1899   "!TARGET_64BIT"
1900 {
1901   switch (get_attr_type (insn))
1902     {
1903     case TYPE_IMOVX:
1904       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1905     default:
1906       return "mov{b}\t{%h1, %0|%0, %h1}";
1907     }
1908 }
1909   [(set (attr "type")
1910      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1911                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1912                              (ne (symbol_ref "TARGET_MOVX")
1913                                  (const_int 0))))
1914         (const_string "imovx")
1915         (const_string "imov")))
1916    (set (attr "mode")
1917      (if_then_else (eq_attr "type" "imovx")
1918         (const_string "SI")
1919         (const_string "QI")))])
1920
1921 (define_insn "*movqi_extv_1_rex64"
1922   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1923         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1924                          (const_int 8)
1925                          (const_int 8)))]
1926   "TARGET_64BIT"
1927 {
1928   switch (get_attr_type (insn))
1929     {
1930     case TYPE_IMOVX:
1931       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1932     default:
1933       return "mov{b}\t{%h1, %0|%0, %h1}";
1934     }
1935 }
1936   [(set (attr "type")
1937      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1938                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1939                              (ne (symbol_ref "TARGET_MOVX")
1940                                  (const_int 0))))
1941         (const_string "imovx")
1942         (const_string "imov")))
1943    (set (attr "mode")
1944      (if_then_else (eq_attr "type" "imovx")
1945         (const_string "SI")
1946         (const_string "QI")))])
1947
1948 ;; Stores and loads of ax to arbitrary constant address.
1949 ;; We fake an second form of instruction to force reload to load address
1950 ;; into register when rax is not available
1951 (define_insn "*movabsqi_1_rex64"
1952   [(set (mem:QI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1953         (match_operand:QI 1 "nonmemory_operand" "a,er"))]
1954   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1955   "@
1956    movabs{b}\t{%1, %P0|%P0, %1}
1957    mov{b}\t{%1, %a0|%a0, %1}"
1958   [(set_attr "type" "imov")
1959    (set_attr "modrm" "0,*")
1960    (set_attr "length_address" "8,0")
1961    (set_attr "length_immediate" "0,*")
1962    (set_attr "memory" "store")
1963    (set_attr "mode" "QI")])
1964
1965 (define_insn "*movabsqi_2_rex64"
1966   [(set (match_operand:QI 0 "register_operand" "=a,r")
1967         (mem:QI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1968   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1969   "@
1970    movabs{b}\t{%P1, %0|%0, %P1}
1971    mov{b}\t{%a1, %0|%0, %a1}"
1972   [(set_attr "type" "imov")
1973    (set_attr "modrm" "0,*")
1974    (set_attr "length_address" "8,0")
1975    (set_attr "length_immediate" "0")
1976    (set_attr "memory" "load")
1977    (set_attr "mode" "QI")])
1978
1979 (define_insn "*movdi_extzv_1"
1980   [(set (match_operand:DI 0 "register_operand" "=R")
1981         (zero_extract:DI (match_operand 1 "ext_register_operand" "Q")
1982                          (const_int 8)
1983                          (const_int 8)))]
1984   "TARGET_64BIT"
1985   "movz{bl|x}\t{%h1, %k0|%k0, %h1}"
1986   [(set_attr "type" "imovx")
1987    (set_attr "mode" "DI")])
1988
1989 (define_insn "*movsi_extzv_1"
1990   [(set (match_operand:SI 0 "register_operand" "=R")
1991         (zero_extract:SI (match_operand 1 "ext_register_operand" "Q")
1992                          (const_int 8)
1993                          (const_int 8)))]
1994   ""
1995   "movz{bl|x}\t{%h1, %0|%0, %h1}"
1996   [(set_attr "type" "imovx")
1997    (set_attr "mode" "SI")])
1998
1999 (define_insn "*movqi_extzv_2"
2000   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
2001         (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2002                                     (const_int 8)
2003                                     (const_int 8)) 0))]
2004   "!TARGET_64BIT"
2005 {
2006   switch (get_attr_type (insn))
2007     {
2008     case TYPE_IMOVX:
2009       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
2010     default:
2011       return "mov{b}\t{%h1, %0|%0, %h1}";
2012     }
2013 }
2014   [(set (attr "type")
2015      (if_then_else (and (match_operand:QI 0 "register_operand" "")
2016                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
2017                              (ne (symbol_ref "TARGET_MOVX")
2018                                  (const_int 0))))
2019         (const_string "imovx")
2020         (const_string "imov")))
2021    (set (attr "mode")
2022      (if_then_else (eq_attr "type" "imovx")
2023         (const_string "SI")
2024         (const_string "QI")))])
2025
2026 (define_insn "*movqi_extzv_2_rex64"
2027   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2028         (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2029                                     (const_int 8)
2030                                     (const_int 8)) 0))]
2031   "TARGET_64BIT"
2032 {
2033   switch (get_attr_type (insn))
2034     {
2035     case TYPE_IMOVX:
2036       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
2037     default:
2038       return "mov{b}\t{%h1, %0|%0, %h1}";
2039     }
2040 }
2041   [(set (attr "type")
2042      (if_then_else (ior (not (match_operand:QI 0 "q_regs_operand" ""))
2043                         (ne (symbol_ref "TARGET_MOVX")
2044                             (const_int 0)))
2045         (const_string "imovx")
2046         (const_string "imov")))
2047    (set (attr "mode")
2048      (if_then_else (eq_attr "type" "imovx")
2049         (const_string "SI")
2050         (const_string "QI")))])
2051
2052 (define_insn "movsi_insv_1"
2053   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2054                          (const_int 8)
2055                          (const_int 8))
2056         (match_operand:SI 1 "general_operand" "Qmn"))]
2057   "!TARGET_64BIT"
2058   "mov{b}\t{%b1, %h0|%h0, %b1}"
2059   [(set_attr "type" "imov")
2060    (set_attr "mode" "QI")])
2061
2062 (define_insn "*movsi_insv_1_rex64"
2063   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2064                          (const_int 8)
2065                          (const_int 8))
2066         (match_operand:SI 1 "nonmemory_operand" "Qn"))]
2067   "TARGET_64BIT"
2068   "mov{b}\t{%b1, %h0|%h0, %b1}"
2069   [(set_attr "type" "imov")
2070    (set_attr "mode" "QI")])
2071
2072 (define_insn "movdi_insv_1_rex64"
2073   [(set (zero_extract:DI (match_operand 0 "ext_register_operand" "+Q")
2074                          (const_int 8)
2075                          (const_int 8))
2076         (match_operand:DI 1 "nonmemory_operand" "Qn"))]
2077   "TARGET_64BIT"
2078   "mov{b}\t{%b1, %h0|%h0, %b1}"
2079   [(set_attr "type" "imov")
2080    (set_attr "mode" "QI")])
2081
2082 (define_insn "*movqi_insv_2"
2083   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2084                          (const_int 8)
2085                          (const_int 8))
2086         (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
2087                      (const_int 8)))]
2088   ""
2089   "mov{b}\t{%h1, %h0|%h0, %h1}"
2090   [(set_attr "type" "imov")
2091    (set_attr "mode" "QI")])
2092
2093 (define_expand "movdi"
2094   [(set (match_operand:DI 0 "nonimmediate_operand" "")
2095         (match_operand:DI 1 "general_operand" ""))]
2096   ""
2097   "ix86_expand_move (DImode, operands); DONE;")
2098
2099 (define_insn "*pushdi"
2100   [(set (match_operand:DI 0 "push_operand" "=<")
2101         (match_operand:DI 1 "general_no_elim_operand" "riF*m"))]
2102   "!TARGET_64BIT"
2103   "#")
2104
2105 (define_insn "*pushdi2_rex64"
2106   [(set (match_operand:DI 0 "push_operand" "=<,!<")
2107         (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
2108   "TARGET_64BIT"
2109   "@
2110    push{q}\t%1
2111    #"
2112   [(set_attr "type" "push,multi")
2113    (set_attr "mode" "DI")])
2114
2115 ;; Convert impossible pushes of immediate to existing instructions.
2116 ;; First try to get scratch register and go through it.  In case this
2117 ;; fails, push sign extended lower part first and then overwrite
2118 ;; upper part by 32bit move.
2119 (define_peephole2
2120   [(match_scratch:DI 2 "r")
2121    (set (match_operand:DI 0 "push_operand" "")
2122         (match_operand:DI 1 "immediate_operand" ""))]
2123   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2124    && !x86_64_immediate_operand (operands[1], DImode)"
2125   [(set (match_dup 2) (match_dup 1))
2126    (set (match_dup 0) (match_dup 2))]
2127   "")
2128
2129 ;; We need to define this as both peepholer and splitter for case
2130 ;; peephole2 pass is not run.
2131 ;; "&& 1" is needed to keep it from matching the previous pattern.
2132 (define_peephole2
2133   [(set (match_operand:DI 0 "push_operand" "")
2134         (match_operand:DI 1 "immediate_operand" ""))]
2135   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2136    && !x86_64_immediate_operand (operands[1], DImode) && 1"
2137   [(set (match_dup 0) (match_dup 1))
2138    (set (match_dup 2) (match_dup 3))]
2139   "split_di (&operands[1], 1, &operands[2], &operands[3]);
2140    operands[1] = gen_lowpart (DImode, operands[2]);
2141    operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
2142                                                     GEN_INT (4)));
2143   ")
2144
2145 (define_split
2146   [(set (match_operand:DI 0 "push_operand" "")
2147         (match_operand:DI 1 "immediate_operand" ""))]
2148   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2149                     ? epilogue_completed : reload_completed)
2150    && !symbolic_operand (operands[1], DImode)
2151    && !x86_64_immediate_operand (operands[1], DImode)"
2152   [(set (match_dup 0) (match_dup 1))
2153    (set (match_dup 2) (match_dup 3))]
2154   "split_di (&operands[1], 1, &operands[2], &operands[3]);
2155    operands[1] = gen_lowpart (DImode, operands[2]);
2156    operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
2157                                                     GEN_INT (4)));
2158   ")
2159
2160 (define_insn "*pushdi2_prologue_rex64"
2161   [(set (match_operand:DI 0 "push_operand" "=<")
2162         (match_operand:DI 1 "general_no_elim_operand" "re*m"))
2163    (clobber (mem:BLK (scratch)))]
2164   "TARGET_64BIT"
2165   "push{q}\t%1"
2166   [(set_attr "type" "push")
2167    (set_attr "mode" "DI")])
2168
2169 (define_insn "*popdi1_epilogue_rex64"
2170   [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
2171         (mem:DI (reg:DI SP_REG)))
2172    (set (reg:DI SP_REG)
2173         (plus:DI (reg:DI SP_REG) (const_int 8)))
2174    (clobber (mem:BLK (scratch)))]
2175   "TARGET_64BIT"
2176   "pop{q}\t%0"
2177   [(set_attr "type" "pop")
2178    (set_attr "mode" "DI")])
2179
2180 (define_insn "popdi1"
2181   [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
2182         (mem:DI (reg:DI SP_REG)))
2183    (set (reg:DI SP_REG)
2184         (plus:DI (reg:DI SP_REG) (const_int 8)))]
2185   "TARGET_64BIT"
2186   "pop{q}\t%0"
2187   [(set_attr "type" "pop")
2188    (set_attr "mode" "DI")])
2189
2190 (define_insn "*movdi_xor_rex64"
2191   [(set (match_operand:DI 0 "register_operand" "=r")
2192         (match_operand:DI 1 "const0_operand" "i"))
2193    (clobber (reg:CC FLAGS_REG))]
2194   "TARGET_64BIT && (!TARGET_USE_MOV0 || optimize_size)
2195    && reload_completed"
2196   "xor{l}\t%k0, %k0";
2197   [(set_attr "type" "alu1")
2198    (set_attr "mode" "SI")
2199    (set_attr "length_immediate" "0")])
2200
2201 (define_insn "*movdi_or_rex64"
2202   [(set (match_operand:DI 0 "register_operand" "=r")
2203         (match_operand:DI 1 "const_int_operand" "i"))
2204    (clobber (reg:CC FLAGS_REG))]
2205   "TARGET_64BIT && (TARGET_MOVE_M1_VIA_OR || optimize_size)
2206    && reload_completed
2207    && operands[1] == constm1_rtx"
2208 {
2209   operands[1] = constm1_rtx;
2210   return "or{q}\t{%1, %0|%0, %1}";
2211 }
2212   [(set_attr "type" "alu1")
2213    (set_attr "mode" "DI")
2214    (set_attr "length_immediate" "1")])
2215
2216 (define_insn "*movdi_2"
2217   [(set (match_operand:DI 0 "nonimmediate_operand"
2218                         "=r  ,o  ,*y,m*y,*y,*Y2,m  ,*Y2,*Y2,*x,m ,*x,*x")
2219         (match_operand:DI 1 "general_operand"
2220                         "riFo,riF,C ,*y ,m ,C  ,*Y2,*Y2,m  ,C ,*x,*x,m "))]
2221   "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2222   "@
2223    #
2224    #
2225    pxor\t%0, %0
2226    movq\t{%1, %0|%0, %1}
2227    movq\t{%1, %0|%0, %1}
2228    pxor\t%0, %0
2229    movq\t{%1, %0|%0, %1}
2230    movdqa\t{%1, %0|%0, %1}
2231    movq\t{%1, %0|%0, %1}
2232    xorps\t%0, %0
2233    movlps\t{%1, %0|%0, %1}
2234    movaps\t{%1, %0|%0, %1}
2235    movlps\t{%1, %0|%0, %1}"
2236   [(set_attr "type" "*,*,mmx,mmxmov,mmxmov,sselog1,ssemov,ssemov,ssemov,sselog1,ssemov,ssemov,ssemov")
2237    (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF")])
2238
2239 (define_split
2240   [(set (match_operand:DI 0 "push_operand" "")
2241         (match_operand:DI 1 "general_operand" ""))]
2242   "!TARGET_64BIT && reload_completed
2243    && (! MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
2244   [(const_int 0)]
2245   "ix86_split_long_move (operands); DONE;")
2246
2247 ;; %%% This multiword shite has got to go.
2248 (define_split
2249   [(set (match_operand:DI 0 "nonimmediate_operand" "")
2250         (match_operand:DI 1 "general_operand" ""))]
2251   "!TARGET_64BIT && reload_completed
2252    && (!MMX_REG_P (operands[0]) && !SSE_REG_P (operands[0]))
2253    && (!MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
2254   [(const_int 0)]
2255   "ix86_split_long_move (operands); DONE;")
2256
2257 (define_insn "*movdi_1_rex64"
2258   [(set (match_operand:DI 0 "nonimmediate_operand"
2259           "=r,r  ,r,m ,!m,*y,*y,?r ,m ,?*Ym,?*y,*x,*x,?r ,m,?*Yi,*x,?*x,?*Ym")
2260         (match_operand:DI 1 "general_operand"
2261           "Z ,rem,i,re,n ,C ,*y,*Ym,*y,r   ,m  ,C ,*x,*Yi,*x,r  ,m ,*Ym,*x"))]
2262   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2263 {
2264   switch (get_attr_type (insn))
2265     {
2266     case TYPE_SSECVT:
2267       if (SSE_REG_P (operands[0]))
2268         return "movq2dq\t{%1, %0|%0, %1}";
2269       else
2270         return "movdq2q\t{%1, %0|%0, %1}";
2271
2272     case TYPE_SSEMOV:
2273       if (get_attr_mode (insn) == MODE_TI)
2274         return "movdqa\t{%1, %0|%0, %1}";
2275       /* FALLTHRU */
2276
2277     case TYPE_MMXMOV:
2278       /* Moves from and into integer register is done using movd
2279          opcode with REX prefix.  */
2280       if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
2281         return "movd\t{%1, %0|%0, %1}";
2282       return "movq\t{%1, %0|%0, %1}";
2283
2284     case TYPE_SSELOG1:
2285     case TYPE_MMXADD:
2286       return "pxor\t%0, %0";
2287
2288     case TYPE_MULTI:
2289       return "#";
2290
2291     case TYPE_LEA:
2292       return "lea{q}\t{%a1, %0|%0, %a1}";
2293
2294     default:
2295       gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
2296       if (get_attr_mode (insn) == MODE_SI)
2297         return "mov{l}\t{%k1, %k0|%k0, %k1}";
2298       else if (which_alternative == 2)
2299         return "movabs{q}\t{%1, %0|%0, %1}";
2300       else
2301         return "mov{q}\t{%1, %0|%0, %1}";
2302     }
2303 }
2304   [(set (attr "type")
2305      (cond [(eq_attr "alternative" "5")
2306               (const_string "mmxadd")
2307             (eq_attr "alternative" "6,7,8,9,10")
2308               (const_string "mmxmov")
2309             (eq_attr "alternative" "11")
2310               (const_string "sselog1")
2311             (eq_attr "alternative" "12,13,14,15,16")
2312               (const_string "ssemov")
2313             (eq_attr "alternative" "17,18")
2314               (const_string "ssecvt")
2315             (eq_attr "alternative" "4")
2316               (const_string "multi")
2317             (match_operand:DI 1 "pic_32bit_operand" "")
2318               (const_string "lea")
2319            ]
2320            (const_string "imov")))
2321    (set_attr "modrm" "*,0,0,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*")
2322    (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*")
2323    (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,DI,DI,TI,TI,DI,DI,DI,DI,DI,DI")])
2324
2325 ;; Stores and loads of ax to arbitrary constant address.
2326 ;; We fake an second form of instruction to force reload to load address
2327 ;; into register when rax is not available
2328 (define_insn "*movabsdi_1_rex64"
2329   [(set (mem:DI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2330         (match_operand:DI 1 "nonmemory_operand" "a,er"))]
2331   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
2332   "@
2333    movabs{q}\t{%1, %P0|%P0, %1}
2334    mov{q}\t{%1, %a0|%a0, %1}"
2335   [(set_attr "type" "imov")
2336    (set_attr "modrm" "0,*")
2337    (set_attr "length_address" "8,0")
2338    (set_attr "length_immediate" "0,*")
2339    (set_attr "memory" "store")
2340    (set_attr "mode" "DI")])
2341
2342 (define_insn "*movabsdi_2_rex64"
2343   [(set (match_operand:DI 0 "register_operand" "=a,r")
2344         (mem:DI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2345   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
2346   "@
2347    movabs{q}\t{%P1, %0|%0, %P1}
2348    mov{q}\t{%a1, %0|%0, %a1}"
2349   [(set_attr "type" "imov")
2350    (set_attr "modrm" "0,*")
2351    (set_attr "length_address" "8,0")
2352    (set_attr "length_immediate" "0")
2353    (set_attr "memory" "load")
2354    (set_attr "mode" "DI")])
2355
2356 ;; Convert impossible stores of immediate to existing instructions.
2357 ;; First try to get scratch register and go through it.  In case this
2358 ;; fails, move by 32bit parts.
2359 (define_peephole2
2360   [(match_scratch:DI 2 "r")
2361    (set (match_operand:DI 0 "memory_operand" "")
2362         (match_operand:DI 1 "immediate_operand" ""))]
2363   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2364    && !x86_64_immediate_operand (operands[1], DImode)"
2365   [(set (match_dup 2) (match_dup 1))
2366    (set (match_dup 0) (match_dup 2))]
2367   "")
2368
2369 ;; We need to define this as both peepholer and splitter for case
2370 ;; peephole2 pass is not run.
2371 ;; "&& 1" is needed to keep it from matching the previous pattern.
2372 (define_peephole2
2373   [(set (match_operand:DI 0 "memory_operand" "")
2374         (match_operand:DI 1 "immediate_operand" ""))]
2375   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2376    && !x86_64_immediate_operand (operands[1], DImode) && 1"
2377   [(set (match_dup 2) (match_dup 3))
2378    (set (match_dup 4) (match_dup 5))]
2379   "split_di (&operands[0], 2, &operands[2], &operands[4]);")
2380
2381 (define_split
2382   [(set (match_operand:DI 0 "memory_operand" "")
2383         (match_operand:DI 1 "immediate_operand" ""))]
2384   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2385                     ? epilogue_completed : reload_completed)
2386    && !symbolic_operand (operands[1], DImode)
2387    && !x86_64_immediate_operand (operands[1], DImode)"
2388   [(set (match_dup 2) (match_dup 3))
2389    (set (match_dup 4) (match_dup 5))]
2390   "split_di (&operands[0], 2, &operands[2], &operands[4]);")
2391
2392 (define_insn "*swapdi_rex64"
2393   [(set (match_operand:DI 0 "register_operand" "+r")
2394         (match_operand:DI 1 "register_operand" "+r"))
2395    (set (match_dup 1)
2396         (match_dup 0))]
2397   "TARGET_64BIT"
2398   "xchg{q}\t%1, %0"
2399   [(set_attr "type" "imov")
2400    (set_attr "mode" "DI")
2401    (set_attr "pent_pair" "np")
2402    (set_attr "athlon_decode" "vector")
2403    (set_attr "amdfam10_decode" "double")])
2404
2405 (define_expand "movti"
2406   [(set (match_operand:TI 0 "nonimmediate_operand" "")
2407         (match_operand:TI 1 "nonimmediate_operand" ""))]
2408   "TARGET_SSE || TARGET_64BIT"
2409 {
2410   if (TARGET_64BIT)
2411     ix86_expand_move (TImode, operands);
2412   else if (push_operand (operands[0], TImode))
2413     ix86_expand_push (TImode, operands[1]);
2414   else
2415     ix86_expand_vector_move (TImode, operands);
2416   DONE;
2417 })
2418
2419 (define_insn "*movti_internal"
2420   [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
2421         (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
2422   "TARGET_SSE && !TARGET_64BIT
2423    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2424 {
2425   switch (which_alternative)
2426     {
2427     case 0:
2428       if (get_attr_mode (insn) == MODE_V4SF)
2429         return "xorps\t%0, %0";
2430       else
2431         return "pxor\t%0, %0";
2432     case 1:
2433     case 2:
2434       /* TDmode values are passed as TImode on the stack.  Moving them
2435          to stack may result in unaligned memory access.  */
2436       if (misaligned_operand (operands[0], TImode)
2437           || misaligned_operand (operands[1], TImode))
2438         { 
2439           if (get_attr_mode (insn) == MODE_V4SF)
2440             return "movups\t{%1, %0|%0, %1}";
2441          else
2442            return "movdqu\t{%1, %0|%0, %1}";
2443         }
2444       else
2445         { 
2446           if (get_attr_mode (insn) == MODE_V4SF)
2447             return "movaps\t{%1, %0|%0, %1}";
2448          else
2449            return "movdqa\t{%1, %0|%0, %1}";
2450         }
2451     default:
2452       gcc_unreachable ();
2453     }
2454 }
2455   [(set_attr "type" "sselog1,ssemov,ssemov")
2456    (set (attr "mode")
2457         (cond [(ior (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2458                     (ne (symbol_ref "optimize_size") (const_int 0)))
2459                  (const_string "V4SF")
2460                (and (eq_attr "alternative" "2")
2461                     (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2462                         (const_int 0)))
2463                  (const_string "V4SF")]
2464               (const_string "TI")))])
2465
2466 (define_insn "*movti_rex64"
2467   [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o,x,x,xm")
2468         (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
2469   "TARGET_64BIT
2470    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2471 {
2472   switch (which_alternative)
2473     {
2474     case 0:
2475     case 1:
2476       return "#";
2477     case 2:
2478       if (get_attr_mode (insn) == MODE_V4SF)
2479         return "xorps\t%0, %0";
2480       else
2481         return "pxor\t%0, %0";
2482     case 3:
2483     case 4:
2484       /* TDmode values are passed as TImode on the stack.  Moving them
2485          to stack may result in unaligned memory access.  */
2486       if (misaligned_operand (operands[0], TImode)
2487           || misaligned_operand (operands[1], TImode))
2488         { 
2489           if (get_attr_mode (insn) == MODE_V4SF)
2490             return "movups\t{%1, %0|%0, %1}";
2491          else
2492            return "movdqu\t{%1, %0|%0, %1}";
2493         }
2494       else
2495         { 
2496           if (get_attr_mode (insn) == MODE_V4SF)
2497             return "movaps\t{%1, %0|%0, %1}";
2498          else
2499            return "movdqa\t{%1, %0|%0, %1}";
2500         }
2501     default:
2502       gcc_unreachable ();
2503     }
2504 }
2505   [(set_attr "type" "*,*,sselog1,ssemov,ssemov")
2506    (set (attr "mode")
2507         (cond [(eq_attr "alternative" "2,3")
2508                  (if_then_else
2509                    (ne (symbol_ref "optimize_size")
2510                        (const_int 0))
2511                    (const_string "V4SF")
2512                    (const_string "TI"))
2513                (eq_attr "alternative" "4")
2514                  (if_then_else
2515                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2516                             (const_int 0))
2517                         (ne (symbol_ref "optimize_size")
2518                             (const_int 0)))
2519                    (const_string "V4SF")
2520                    (const_string "TI"))]
2521                (const_string "DI")))])
2522
2523 (define_split
2524   [(set (match_operand:TI 0 "nonimmediate_operand" "")
2525         (match_operand:TI 1 "general_operand" ""))]
2526   "reload_completed && !SSE_REG_P (operands[0])
2527    && !SSE_REG_P (operands[1])"
2528   [(const_int 0)]
2529   "ix86_split_long_move (operands); DONE;")
2530
2531 ;; This expands to what emit_move_complex would generate if we didn't
2532 ;; have a movti pattern.  Having this avoids problems with reload on
2533 ;; 32-bit targets when SSE is present, but doesn't seem to be harmful
2534 ;; to have around all the time.
2535 (define_expand "movcdi"
2536   [(set (match_operand:CDI 0 "nonimmediate_operand" "")
2537         (match_operand:CDI 1 "general_operand" ""))]
2538   ""
2539 {
2540   if (push_operand (operands[0], CDImode))
2541     emit_move_complex_push (CDImode, operands[0], operands[1]);
2542   else
2543     emit_move_complex_parts (operands[0], operands[1]);
2544   DONE;
2545 })
2546
2547 (define_expand "movsf"
2548   [(set (match_operand:SF 0 "nonimmediate_operand" "")
2549         (match_operand:SF 1 "general_operand" ""))]
2550   ""
2551   "ix86_expand_move (SFmode, operands); DONE;")
2552
2553 (define_insn "*pushsf"
2554   [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2555         (match_operand:SF 1 "general_no_elim_operand" "f,rFm,x"))]
2556   "!TARGET_64BIT"
2557 {
2558   /* Anything else should be already split before reg-stack.  */
2559   gcc_assert (which_alternative == 1);
2560   return "push{l}\t%1";
2561 }
2562   [(set_attr "type" "multi,push,multi")
2563    (set_attr "unit" "i387,*,*")
2564    (set_attr "mode" "SF,SI,SF")])
2565
2566 (define_insn "*pushsf_rex64"
2567   [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2568         (match_operand:SF 1 "nonmemory_no_elim_operand" "f,rF,x"))]
2569   "TARGET_64BIT"
2570 {
2571   /* Anything else should be already split before reg-stack.  */
2572   gcc_assert (which_alternative == 1);
2573   return "push{q}\t%q1";
2574 }
2575   [(set_attr "type" "multi,push,multi")
2576    (set_attr "unit" "i387,*,*")
2577    (set_attr "mode" "SF,DI,SF")])
2578
2579 (define_split
2580   [(set (match_operand:SF 0 "push_operand" "")
2581         (match_operand:SF 1 "memory_operand" ""))]
2582   "reload_completed
2583    && MEM_P (operands[1])
2584    && (operands[2] = find_constant_src (insn))"
2585   [(set (match_dup 0)
2586         (match_dup 2))])
2587
2588
2589 ;; %%% Kill this when call knows how to work this out.
2590 (define_split
2591   [(set (match_operand:SF 0 "push_operand" "")
2592         (match_operand:SF 1 "any_fp_register_operand" ""))]
2593   "!TARGET_64BIT"
2594   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
2595    (set (mem:SF (reg:SI SP_REG)) (match_dup 1))])
2596
2597 (define_split
2598   [(set (match_operand:SF 0 "push_operand" "")
2599         (match_operand:SF 1 "any_fp_register_operand" ""))]
2600   "TARGET_64BIT"
2601   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2602    (set (mem:SF (reg:DI SP_REG)) (match_dup 1))])
2603
2604 (define_insn "*movsf_1"
2605   [(set (match_operand:SF 0 "nonimmediate_operand"
2606           "=f,m,f,r  ,m ,x,x,x ,m,!*y,!m,!*y,?Yi,?r,!*Ym,!r")
2607         (match_operand:SF 1 "general_operand"
2608           "fm,f,G,rmF,Fr,C,x,xm,x,m  ,*y,*y ,r  ,Yi,r   ,*Ym"))]
2609   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2610    && (reload_in_progress || reload_completed
2611        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2612        || (!TARGET_SSE_MATH && optimize_size
2613            && standard_80387_constant_p (operands[1]))
2614        || GET_CODE (operands[1]) != CONST_DOUBLE
2615        || memory_operand (operands[0], SFmode))"
2616 {
2617   switch (which_alternative)
2618     {
2619     case 0:
2620     case 1:
2621       return output_387_reg_move (insn, operands);
2622
2623     case 2:
2624       return standard_80387_constant_opcode (operands[1]);
2625
2626     case 3:
2627     case 4:
2628       return "mov{l}\t{%1, %0|%0, %1}";
2629     case 5:
2630       if (get_attr_mode (insn) == MODE_TI)
2631         return "pxor\t%0, %0";
2632       else
2633         return "xorps\t%0, %0";
2634     case 6:
2635       if (get_attr_mode (insn) == MODE_V4SF)
2636         return "movaps\t{%1, %0|%0, %1}";
2637       else
2638         return "movss\t{%1, %0|%0, %1}";
2639     case 7: case 8:
2640       return "movss\t{%1, %0|%0, %1}";
2641
2642     case 9: case 10:
2643     case 12: case 13: case 14: case 15:
2644       return "movd\t{%1, %0|%0, %1}";
2645
2646     case 11:
2647       return "movq\t{%1, %0|%0, %1}";
2648
2649     default:
2650       gcc_unreachable ();
2651     }
2652 }
2653   [(set_attr "type" "fmov,fmov,fmov,imov,imov,sselog1,ssemov,ssemov,ssemov,mmxmov,mmxmov,mmxmov,ssemov,ssemov,mmxmov,mmxmov")
2654    (set (attr "mode")
2655         (cond [(eq_attr "alternative" "3,4,9,10")
2656                  (const_string "SI")
2657                (eq_attr "alternative" "5")
2658                  (if_then_else
2659                    (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2660                                  (const_int 0))
2661                              (ne (symbol_ref "TARGET_SSE2")
2662                                  (const_int 0)))
2663                         (eq (symbol_ref "optimize_size")
2664                             (const_int 0)))
2665                    (const_string "TI")
2666                    (const_string "V4SF"))
2667                /* For architectures resolving dependencies on
2668                   whole SSE registers use APS move to break dependency
2669                   chains, otherwise use short move to avoid extra work.
2670
2671                   Do the same for architectures resolving dependencies on
2672                   the parts.  While in DF mode it is better to always handle
2673                   just register parts, the SF mode is different due to lack
2674                   of instructions to load just part of the register.  It is
2675                   better to maintain the whole registers in single format
2676                   to avoid problems on using packed logical operations.  */
2677                (eq_attr "alternative" "6")
2678                  (if_then_else
2679                    (ior (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2680                             (const_int 0))
2681                         (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2682                             (const_int 0)))
2683                    (const_string "V4SF")
2684                    (const_string "SF"))
2685                (eq_attr "alternative" "11")
2686                  (const_string "DI")]
2687                (const_string "SF")))])
2688
2689 (define_insn "*swapsf"
2690   [(set (match_operand:SF 0 "fp_register_operand" "+f")
2691         (match_operand:SF 1 "fp_register_operand" "+f"))
2692    (set (match_dup 1)
2693         (match_dup 0))]
2694   "reload_completed || TARGET_80387"
2695 {
2696   if (STACK_TOP_P (operands[0]))
2697     return "fxch\t%1";
2698   else
2699     return "fxch\t%0";
2700 }
2701   [(set_attr "type" "fxch")
2702    (set_attr "mode" "SF")])
2703
2704 (define_expand "movdf"
2705   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2706         (match_operand:DF 1 "general_operand" ""))]
2707   ""
2708   "ix86_expand_move (DFmode, operands); DONE;")
2709
2710 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2711 ;; Size of pushdf using integer instructions is 2+2*memory operand size
2712 ;; On the average, pushdf using integers can be still shorter.  Allow this
2713 ;; pattern for optimize_size too.
2714
2715 (define_insn "*pushdf_nointeger"
2716   [(set (match_operand:DF 0 "push_operand" "=<,<,<,<")
2717         (match_operand:DF 1 "general_no_elim_operand" "f,Fo,*r,Y2"))]
2718   "!TARGET_64BIT && !TARGET_INTEGER_DFMODE_MOVES"
2719 {
2720   /* This insn should be already split before reg-stack.  */
2721   gcc_unreachable ();
2722 }
2723   [(set_attr "type" "multi")
2724    (set_attr "unit" "i387,*,*,*")
2725    (set_attr "mode" "DF,SI,SI,DF")])
2726
2727 (define_insn "*pushdf_integer"
2728   [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2729         (match_operand:DF 1 "general_no_elim_operand" "f,rFo,Y2"))]
2730   "TARGET_64BIT || TARGET_INTEGER_DFMODE_MOVES"
2731 {
2732   /* This insn should be already split before reg-stack.  */
2733   gcc_unreachable ();
2734 }
2735   [(set_attr "type" "multi")
2736    (set_attr "unit" "i387,*,*")
2737    (set_attr "mode" "DF,SI,DF")])
2738
2739 ;; %%% Kill this when call knows how to work this out.
2740 (define_split
2741   [(set (match_operand:DF 0 "push_operand" "")
2742         (match_operand:DF 1 "any_fp_register_operand" ""))]
2743   "reload_completed"
2744   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -8)))
2745    (set (mem:DF (reg:P SP_REG)) (match_dup 1))]
2746   "")
2747
2748 (define_split
2749   [(set (match_operand:DF 0 "push_operand" "")
2750         (match_operand:DF 1 "general_operand" ""))]
2751   "reload_completed"
2752   [(const_int 0)]
2753   "ix86_split_long_move (operands); DONE;")
2754
2755 ;; Moving is usually shorter when only FP registers are used. This separate
2756 ;; movdf pattern avoids the use of integer registers for FP operations
2757 ;; when optimizing for size.
2758
2759 (define_insn "*movdf_nointeger"
2760   [(set (match_operand:DF 0 "nonimmediate_operand"
2761                         "=f,m,f,*r  ,o  ,Y2*x,Y2*x,Y2*x ,m  ")
2762         (match_operand:DF 1 "general_operand"
2763                         "fm,f,G,*roF,*Fr,C   ,Y2*x,mY2*x,Y2*x"))]
2764   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2765    && ((optimize_size || !TARGET_INTEGER_DFMODE_MOVES) && !TARGET_64BIT)
2766    && (reload_in_progress || reload_completed
2767        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2768        || (!(TARGET_SSE2 && TARGET_SSE_MATH) && optimize_size
2769            && !memory_operand (operands[0], DFmode)
2770            && standard_80387_constant_p (operands[1]))
2771        || GET_CODE (operands[1]) != CONST_DOUBLE
2772        || ((optimize_size
2773             || !TARGET_MEMORY_MISMATCH_STALL
2774             || reload_in_progress || reload_completed)
2775            && memory_operand (operands[0], DFmode)))"
2776 {
2777   switch (which_alternative)
2778     {
2779     case 0:
2780     case 1:
2781       return output_387_reg_move (insn, operands);
2782
2783     case 2:
2784       return standard_80387_constant_opcode (operands[1]);
2785
2786     case 3:
2787     case 4:
2788       return "#";
2789     case 5:
2790       switch (get_attr_mode (insn))
2791         {
2792         case MODE_V4SF:
2793           return "xorps\t%0, %0";
2794         case MODE_V2DF:
2795           return "xorpd\t%0, %0";
2796         case MODE_TI:
2797           return "pxor\t%0, %0";
2798         default:
2799           gcc_unreachable ();
2800         }
2801     case 6:
2802     case 7:
2803     case 8:
2804       switch (get_attr_mode (insn))
2805         {
2806         case MODE_V4SF:
2807           return "movaps\t{%1, %0|%0, %1}";
2808         case MODE_V2DF:
2809           return "movapd\t{%1, %0|%0, %1}";
2810         case MODE_TI:
2811           return "movdqa\t{%1, %0|%0, %1}";
2812         case MODE_DI:
2813           return "movq\t{%1, %0|%0, %1}";
2814         case MODE_DF:
2815           return "movsd\t{%1, %0|%0, %1}";
2816         case MODE_V1DF:
2817           return "movlpd\t{%1, %0|%0, %1}";
2818         case MODE_V2SF:
2819           return "movlps\t{%1, %0|%0, %1}";
2820         default:
2821           gcc_unreachable ();
2822         }
2823
2824     default:
2825       gcc_unreachable ();
2826     }
2827 }
2828   [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov")
2829    (set (attr "mode")
2830         (cond [(eq_attr "alternative" "0,1,2")
2831                  (const_string "DF")
2832                (eq_attr "alternative" "3,4")
2833                  (const_string "SI")
2834
2835                /* For SSE1, we have many fewer alternatives.  */
2836                (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2837                  (cond [(eq_attr "alternative" "5,6")
2838                           (const_string "V4SF")
2839                        ]
2840                    (const_string "V2SF"))
2841
2842                /* xorps is one byte shorter.  */
2843                (eq_attr "alternative" "5")
2844                  (cond [(ne (symbol_ref "optimize_size")
2845                             (const_int 0))
2846                           (const_string "V4SF")
2847                         (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2848                             (const_int 0))
2849                           (const_string "TI")
2850                        ]
2851                        (const_string "V2DF"))
2852
2853                /* For architectures resolving dependencies on
2854                   whole SSE registers use APD move to break dependency
2855                   chains, otherwise use short move to avoid extra work.
2856
2857                   movaps encodes one byte shorter.  */
2858                (eq_attr "alternative" "6")
2859                  (cond
2860                    [(ne (symbol_ref "optimize_size")
2861                         (const_int 0))
2862                       (const_string "V4SF")
2863                     (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2864                         (const_int 0))
2865                       (const_string "V2DF")
2866                    ]
2867                    (const_string "DF"))
2868                /* For architectures resolving dependencies on register
2869                   parts we may avoid extra work to zero out upper part
2870                   of register.  */
2871                (eq_attr "alternative" "7")
2872                  (if_then_else
2873                    (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2874                        (const_int 0))
2875                    (const_string "V1DF")
2876                    (const_string "DF"))
2877               ]
2878               (const_string "DF")))])
2879
2880 (define_insn "*movdf_integer_rex64"
2881   [(set (match_operand:DF 0 "nonimmediate_operand"
2882                 "=f,m,f,r  ,m ,Y2*x,Y2*x,Y2*x,m   ,Yi,r ")
2883         (match_operand:DF 1 "general_operand"
2884                 "fm,f,G,rmF,Fr,C   ,Y2*x,m   ,Y2*x,r ,Yi"))]
2885   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))
2886    && (reload_in_progress || reload_completed
2887        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2888        || (!(TARGET_SSE2 && TARGET_SSE_MATH) && optimize_size
2889            && standard_80387_constant_p (operands[1]))
2890        || GET_CODE (operands[1]) != CONST_DOUBLE
2891        || memory_operand (operands[0], DFmode))"
2892 {
2893   switch (which_alternative)
2894     {
2895     case 0:
2896     case 1:
2897       return output_387_reg_move (insn, operands);
2898
2899     case 2:
2900       return standard_80387_constant_opcode (operands[1]);
2901
2902     case 3:
2903     case 4:
2904       return "#";
2905
2906     case 5:
2907       switch (get_attr_mode (insn))
2908         {
2909         case MODE_V4SF:
2910           return "xorps\t%0, %0";
2911         case MODE_V2DF:
2912           return "xorpd\t%0, %0";
2913         case MODE_TI:
2914           return "pxor\t%0, %0";
2915         default:
2916           gcc_unreachable ();
2917         }
2918     case 6:
2919     case 7:
2920     case 8:
2921       switch (get_attr_mode (insn))
2922         {
2923         case MODE_V4SF:
2924           return "movaps\t{%1, %0|%0, %1}";
2925         case MODE_V2DF:
2926           return "movapd\t{%1, %0|%0, %1}";
2927         case MODE_TI:
2928           return "movdqa\t{%1, %0|%0, %1}";
2929         case MODE_DI:
2930           return "movq\t{%1, %0|%0, %1}";
2931         case MODE_DF:
2932           return "movsd\t{%1, %0|%0, %1}";
2933         case MODE_V1DF:
2934           return "movlpd\t{%1, %0|%0, %1}";
2935         case MODE_V2SF:
2936           return "movlps\t{%1, %0|%0, %1}";
2937         default:
2938           gcc_unreachable ();
2939         }
2940
2941     case 9:
2942     case 10:
2943       return "movd\t{%1, %0|%0, %1}";
2944
2945     default:
2946       gcc_unreachable();
2947     }
2948 }
2949   [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov,ssemov,ssemov")
2950    (set (attr "mode")
2951         (cond [(eq_attr "alternative" "0,1,2")
2952                  (const_string "DF")
2953                (eq_attr "alternative" "3,4,9,10")
2954                  (const_string "DI")
2955
2956                /* For SSE1, we have many fewer alternatives.  */
2957                (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2958                  (cond [(eq_attr "alternative" "5,6")
2959                           (const_string "V4SF")
2960                        ]
2961                    (const_string "V2SF"))
2962
2963                /* xorps is one byte shorter.  */
2964                (eq_attr "alternative" "5")
2965                  (cond [(ne (symbol_ref "optimize_size")
2966                             (const_int 0))
2967                           (const_string "V4SF")
2968                         (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2969                             (const_int 0))
2970                           (const_string "TI")
2971                        ]
2972                        (const_string "V2DF"))
2973
2974                /* For architectures resolving dependencies on
2975                   whole SSE registers use APD move to break dependency
2976                   chains, otherwise use short move to avoid extra work.
2977
2978                   movaps encodes one byte shorter.  */
2979                (eq_attr "alternative" "6")
2980                  (cond
2981                    [(ne (symbol_ref "optimize_size")
2982                         (const_int 0))
2983                       (const_string "V4SF")
2984                     (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2985                         (const_int 0))
2986                       (const_string "V2DF")
2987                    ]
2988                    (const_string "DF"))
2989                /* For architectures resolving dependencies on register
2990                   parts we may avoid extra work to zero out upper part
2991                   of register.  */
2992                (eq_attr "alternative" "7")
2993                  (if_then_else
2994                    (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2995                        (const_int 0))
2996                    (const_string "V1DF")
2997                    (const_string "DF"))
2998               ]
2999               (const_string "DF")))])
3000
3001 (define_insn "*movdf_integer"
3002   [(set (match_operand:DF 0 "nonimmediate_operand"
3003                 "=f,m,f,r  ,o ,Y2*x,Y2*x,Y2*x,m   ")
3004         (match_operand:DF 1 "general_operand"
3005                 "fm,f,G,roF,Fr,C   ,Y2*x,m   ,Y2*x"))]
3006   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
3007    && !optimize_size && TARGET_INTEGER_DFMODE_MOVES
3008    && (reload_in_progress || reload_completed
3009        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
3010        || (!(TARGET_SSE2 && TARGET_SSE_MATH) && optimize_size
3011            && standard_80387_constant_p (operands[1]))
3012        || GET_CODE (operands[1]) != CONST_DOUBLE
3013        || memory_operand (operands[0], DFmode))"
3014 {
3015   switch (which_alternative)
3016     {
3017     case 0:
3018     case 1:
3019       return output_387_reg_move (insn, operands);
3020
3021     case 2:
3022       return standard_80387_constant_opcode (operands[1]);
3023
3024     case 3:
3025     case 4:
3026       return "#";
3027
3028     case 5:
3029       switch (get_attr_mode (insn))
3030         {
3031         case MODE_V4SF:
3032           return "xorps\t%0, %0";
3033         case MODE_V2DF:
3034           return "xorpd\t%0, %0";
3035         case MODE_TI:
3036           return "pxor\t%0, %0";
3037         default:
3038           gcc_unreachable ();
3039         }
3040     case 6:
3041     case 7:
3042     case 8:
3043       switch (get_attr_mode (insn))
3044         {
3045         case MODE_V4SF:
3046           return "movaps\t{%1, %0|%0, %1}";
3047         case MODE_V2DF:
3048           return "movapd\t{%1, %0|%0, %1}";
3049         case MODE_TI:
3050           return "movdqa\t{%1, %0|%0, %1}";
3051         case MODE_DI:
3052           return "movq\t{%1, %0|%0, %1}";
3053         case MODE_DF:
3054           return "movsd\t{%1, %0|%0, %1}";
3055         case MODE_V1DF:
3056           return "movlpd\t{%1, %0|%0, %1}";
3057         case MODE_V2SF:
3058           return "movlps\t{%1, %0|%0, %1}";
3059         default:
3060           gcc_unreachable ();
3061         }
3062
3063     default:
3064       gcc_unreachable();
3065     }
3066 }
3067   [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov")
3068    (set (attr "mode")
3069         (cond [(eq_attr "alternative" "0,1,2")
3070                  (const_string "DF")
3071                (eq_attr "alternative" "3,4")
3072                  (const_string "SI")
3073
3074                /* For SSE1, we have many fewer alternatives.  */
3075                (eq (symbol_ref "TARGET_SSE2") (const_int 0))
3076                  (cond [(eq_attr "alternative" "5,6")
3077                           (const_string "V4SF")
3078                        ]
3079                    (const_string "V2SF"))
3080
3081                /* xorps is one byte shorter.  */
3082                (eq_attr "alternative" "5")
3083                  (cond [(ne (symbol_ref "optimize_size")
3084                             (const_int 0))
3085                           (const_string "V4SF")
3086                         (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
3087                             (const_int 0))
3088                           (const_string "TI")
3089                        ]
3090                        (const_string "V2DF"))
3091
3092                /* For architectures resolving dependencies on
3093                   whole SSE registers use APD move to break dependency
3094                   chains, otherwise use short move to avoid extra work.
3095
3096                   movaps encodes one byte shorter.  */
3097                (eq_attr "alternative" "6")
3098                  (cond
3099                    [(ne (symbol_ref "optimize_size")
3100                         (const_int 0))
3101                       (const_string "V4SF")
3102                     (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3103                         (const_int 0))
3104                       (const_string "V2DF")
3105                    ]
3106                    (const_string "DF"))
3107                /* For architectures resolving dependencies on register
3108                   parts we may avoid extra work to zero out upper part
3109                   of register.  */
3110                (eq_attr "alternative" "7")
3111                  (if_then_else
3112                    (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
3113                        (const_int 0))
3114                    (const_string "V1DF")
3115                    (const_string "DF"))
3116               ]
3117               (const_string "DF")))])
3118
3119 (define_split
3120   [(set (match_operand:DF 0 "nonimmediate_operand" "")
3121         (match_operand:DF 1 "general_operand" ""))]
3122   "reload_completed
3123    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3124    && ! (ANY_FP_REG_P (operands[0]) ||
3125          (GET_CODE (operands[0]) == SUBREG
3126           && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
3127    && ! (ANY_FP_REG_P (operands[1]) ||
3128          (GET_CODE (operands[1]) == SUBREG
3129           && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
3130   [(const_int 0)]
3131   "ix86_split_long_move (operands); DONE;")
3132
3133 (define_insn "*swapdf"
3134   [(set (match_operand:DF 0 "fp_register_operand" "+f")
3135         (match_operand:DF 1 "fp_register_operand" "+f"))
3136    (set (match_dup 1)
3137         (match_dup 0))]
3138   "reload_completed || TARGET_80387"
3139 {
3140   if (STACK_TOP_P (operands[0]))
3141     return "fxch\t%1";
3142   else
3143     return "fxch\t%0";
3144 }
3145   [(set_attr "type" "fxch")
3146    (set_attr "mode" "DF")])
3147
3148 (define_expand "movxf"
3149   [(set (match_operand:XF 0 "nonimmediate_operand" "")
3150         (match_operand:XF 1 "general_operand" ""))]
3151   ""
3152   "ix86_expand_move (XFmode, operands); DONE;")
3153
3154 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
3155 ;; Size of pushdf using integer instructions is 3+3*memory operand size
3156 ;; Pushing using integer instructions is longer except for constants
3157 ;; and direct memory references.
3158 ;; (assuming that any given constant is pushed only once, but this ought to be
3159 ;;  handled elsewhere).
3160
3161 (define_insn "*pushxf_nointeger"
3162   [(set (match_operand:XF 0 "push_operand" "=X,X,X")
3163         (match_operand:XF 1 "general_no_elim_operand" "f,Fo,*r"))]
3164   "optimize_size"
3165 {
3166   /* This insn should be already split before reg-stack.  */
3167   gcc_unreachable ();
3168 }
3169   [(set_attr "type" "multi")
3170    (set_attr "unit" "i387,*,*")
3171    (set_attr "mode" "XF,SI,SI")])
3172
3173 (define_insn "*pushxf_integer"
3174   [(set (match_operand:XF 0 "push_operand" "=<,<")
3175         (match_operand:XF 1 "general_no_elim_operand" "f,ro"))]
3176   "!optimize_size"
3177 {
3178   /* This insn should be already split before reg-stack.  */
3179   gcc_unreachable ();
3180 }
3181   [(set_attr "type" "multi")
3182    (set_attr "unit" "i387,*")
3183    (set_attr "mode" "XF,SI")])
3184
3185 (define_split
3186   [(set (match_operand 0 "push_operand" "")
3187         (match_operand 1 "general_operand" ""))]
3188   "reload_completed
3189    && (GET_MODE (operands[0]) == XFmode
3190        || GET_MODE (operands[0]) == DFmode)
3191    && !ANY_FP_REG_P (operands[1])"
3192   [(const_int 0)]
3193   "ix86_split_long_move (operands); DONE;")
3194
3195 (define_split
3196   [(set (match_operand:XF 0 "push_operand" "")
3197         (match_operand:XF 1 "any_fp_register_operand" ""))]
3198   ""
3199   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
3200    (set (mem:XF (reg:P SP_REG)) (match_dup 1))]
3201   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3202
3203 ;; Do not use integer registers when optimizing for size
3204 (define_insn "*movxf_nointeger"
3205   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,*r,o")
3206         (match_operand:XF 1 "general_operand" "fm,f,G,*roF,F*r"))]
3207   "optimize_size
3208    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3209    && (reload_in_progress || reload_completed
3210        || (optimize_size && standard_80387_constant_p (operands[1]))
3211        || GET_CODE (operands[1]) != CONST_DOUBLE
3212        || memory_operand (operands[0], XFmode))"
3213 {
3214   switch (which_alternative)
3215     {
3216     case 0:
3217     case 1:
3218       return output_387_reg_move (insn, operands);
3219
3220     case 2:
3221       return standard_80387_constant_opcode (operands[1]);
3222
3223     case 3: case 4:
3224       return "#";
3225     default:
3226       gcc_unreachable ();
3227     }
3228 }
3229   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
3230    (set_attr "mode" "XF,XF,XF,SI,SI")])
3231
3232 (define_insn "*movxf_integer"
3233   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,r,o")
3234         (match_operand:XF 1 "general_operand" "fm,f,G,roF,Fr"))]
3235   "!optimize_size
3236    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3237    && (reload_in_progress || reload_completed
3238        || (optimize_size && standard_80387_constant_p (operands[1]))
3239        || GET_CODE (operands[1]) != CONST_DOUBLE
3240        || memory_operand (operands[0], XFmode))"
3241 {
3242   switch (which_alternative)
3243     {
3244     case 0:
3245     case 1:
3246       return output_387_reg_move (insn, operands);
3247
3248     case 2:
3249       return standard_80387_constant_opcode (operands[1]);
3250
3251     case 3: case 4:
3252       return "#";
3253
3254     default:
3255       gcc_unreachable ();
3256     }
3257 }
3258   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
3259    (set_attr "mode" "XF,XF,XF,SI,SI")])
3260
3261 (define_expand "movtf"
3262   [(set (match_operand:TF 0 "nonimmediate_operand" "")
3263         (match_operand:TF 1 "nonimmediate_operand" ""))]
3264   "TARGET_64BIT"
3265 {
3266   ix86_expand_move (TFmode, operands);
3267   DONE;
3268 })
3269
3270 (define_insn "*movtf_internal"
3271   [(set (match_operand:TF 0 "nonimmediate_operand" "=x,m,x,?r,?o")
3272         (match_operand:TF 1 "general_operand" "xm,x,C,roF,Fr"))]
3273   "TARGET_64BIT
3274    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
3275 {
3276   switch (which_alternative)
3277     {
3278     case 0:
3279     case 1:
3280       if (get_attr_mode (insn) == MODE_V4SF)
3281         return "movaps\t{%1, %0|%0, %1}";
3282       else
3283         return "movdqa\t{%1, %0|%0, %1}";
3284     case 2:
3285       if (get_attr_mode (insn) == MODE_V4SF)
3286         return "xorps\t%0, %0";
3287       else
3288         return "pxor\t%0, %0";
3289     case 3:
3290     case 4:
3291         return "#";
3292     default:
3293       gcc_unreachable ();
3294     }
3295 }
3296   [(set_attr "type" "ssemov,ssemov,sselog1,*,*")
3297    (set (attr "mode")
3298         (cond [(eq_attr "alternative" "0,2")
3299                  (if_then_else
3300                    (ne (symbol_ref "optimize_size")
3301                        (const_int 0))
3302                    (const_string "V4SF")
3303                    (const_string "TI"))
3304                (eq_attr "alternative" "1")
3305                  (if_then_else
3306                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
3307                             (const_int 0))
3308                         (ne (symbol_ref "optimize_size")
3309                             (const_int 0)))
3310                    (const_string "V4SF")
3311                    (const_string "TI"))]
3312                (const_string "DI")))])
3313
3314 (define_split
3315   [(set (match_operand 0 "nonimmediate_operand" "")
3316         (match_operand 1 "general_operand" ""))]
3317   "reload_completed
3318    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3319    && GET_MODE (operands[0]) == XFmode
3320    && ! (ANY_FP_REG_P (operands[0]) ||
3321          (GET_CODE (operands[0]) == SUBREG
3322           && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
3323    && ! (ANY_FP_REG_P (operands[1]) ||
3324          (GET_CODE (operands[1]) == SUBREG
3325           && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
3326   [(const_int 0)]
3327   "ix86_split_long_move (operands); DONE;")
3328
3329 (define_split
3330   [(set (match_operand 0 "register_operand" "")
3331         (match_operand 1 "memory_operand" ""))]
3332   "reload_completed
3333    && MEM_P (operands[1])
3334    && (GET_MODE (operands[0]) == TFmode
3335        || GET_MODE (operands[0]) == XFmode
3336        || GET_MODE (operands[0]) == SFmode
3337        || GET_MODE (operands[0]) == DFmode)
3338    && (operands[2] = find_constant_src (insn))"
3339   [(set (match_dup 0) (match_dup 2))]
3340 {
3341   rtx c = operands[2];
3342   rtx r = operands[0];
3343
3344   if (GET_CODE (r) == SUBREG)
3345     r = SUBREG_REG (r);
3346
3347   if (SSE_REG_P (r))
3348     {
3349       if (!standard_sse_constant_p (c))
3350         FAIL;
3351     }
3352   else if (FP_REG_P (r))
3353     {
3354       if (!standard_80387_constant_p (c))
3355         FAIL;
3356     }
3357   else if (MMX_REG_P (r))
3358     FAIL;
3359 })
3360
3361 (define_split
3362   [(set (match_operand 0 "register_operand" "")
3363         (float_extend (match_operand 1 "memory_operand" "")))]
3364   "reload_completed
3365    && MEM_P (operands[1])
3366    && (GET_MODE (operands[0]) == TFmode
3367        || GET_MODE (operands[0]) == XFmode
3368        || GET_MODE (operands[0]) == SFmode
3369        || GET_MODE (operands[0]) == DFmode)
3370    && (operands[2] = find_constant_src (insn))"
3371   [(set (match_dup 0) (match_dup 2))]
3372 {
3373   rtx c = operands[2];
3374   rtx r = operands[0];
3375
3376   if (GET_CODE (r) == SUBREG)
3377     r = SUBREG_REG (r);
3378
3379   if (SSE_REG_P (r))
3380     {
3381       if (!standard_sse_constant_p (c))
3382         FAIL;
3383     }
3384   else if (FP_REG_P (r))
3385     {
3386       if (!standard_80387_constant_p (c))
3387         FAIL;
3388     }
3389   else if (MMX_REG_P (r))
3390     FAIL;
3391 })
3392
3393 (define_insn "swapxf"
3394   [(set (match_operand:XF 0 "register_operand" "+f")
3395         (match_operand:XF 1 "register_operand" "+f"))
3396    (set (match_dup 1)
3397         (match_dup 0))]
3398   "TARGET_80387"
3399 {
3400   if (STACK_TOP_P (operands[0]))
3401     return "fxch\t%1";
3402   else
3403     return "fxch\t%0";
3404 }
3405   [(set_attr "type" "fxch")
3406    (set_attr "mode" "XF")])
3407
3408 ;; Split the load of -0.0 or -1.0 into fldz;fchs or fld1;fchs sequence
3409 (define_split
3410   [(set (match_operand:X87MODEF 0 "register_operand" "")
3411         (match_operand:X87MODEF 1 "immediate_operand" ""))]
3412   "reload_completed && FP_REGNO_P (REGNO (operands[0]))
3413    && (standard_80387_constant_p (operands[1]) == 8
3414        || standard_80387_constant_p (operands[1]) == 9)"
3415   [(set (match_dup 0)(match_dup 1))
3416    (set (match_dup 0)
3417         (neg:X87MODEF (match_dup 0)))]
3418 {
3419   REAL_VALUE_TYPE r;
3420
3421   REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
3422   if (real_isnegzero (&r))
3423     operands[1] = CONST0_RTX (<MODE>mode);
3424   else
3425     operands[1] = CONST1_RTX (<MODE>mode);
3426 })
3427
3428 (define_split
3429   [(set (match_operand:TF 0 "nonimmediate_operand" "")
3430         (match_operand:TF 1 "general_operand" ""))]
3431   "reload_completed
3432    && !(SSE_REG_P (operands[0]) || SSE_REG_P (operands[1]))"
3433   [(const_int 0)]
3434   "ix86_split_long_move (operands); DONE;")
3435 \f
3436 ;; Zero extension instructions
3437
3438 (define_expand "zero_extendhisi2"
3439   [(set (match_operand:SI 0 "register_operand" "")
3440      (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
3441   ""
3442 {
3443   if (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3444     {
3445       operands[1] = force_reg (HImode, operands[1]);
3446       emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
3447       DONE;
3448     }
3449 })
3450
3451 (define_insn "zero_extendhisi2_and"
3452   [(set (match_operand:SI 0 "register_operand" "=r")
3453      (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
3454    (clobber (reg:CC FLAGS_REG))]
3455   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3456   "#"
3457   [(set_attr "type" "alu1")
3458    (set_attr "mode" "SI")])
3459
3460 (define_split
3461   [(set (match_operand:SI 0 "register_operand" "")
3462         (zero_extend:SI (match_operand:HI 1 "register_operand" "")))
3463    (clobber (reg:CC FLAGS_REG))]
3464   "reload_completed && TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3465   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
3466               (clobber (reg:CC FLAGS_REG))])]
3467   "")
3468
3469 (define_insn "*zero_extendhisi2_movzwl"
3470   [(set (match_operand:SI 0 "register_operand" "=r")
3471      (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3472   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3473   "movz{wl|x}\t{%1, %0|%0, %1}"
3474   [(set_attr "type" "imovx")
3475    (set_attr "mode" "SI")])
3476
3477 (define_expand "zero_extendqihi2"
3478   [(parallel
3479     [(set (match_operand:HI 0 "register_operand" "")
3480        (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3481      (clobber (reg:CC FLAGS_REG))])]
3482   ""
3483   "")
3484
3485 (define_insn "*zero_extendqihi2_and"
3486   [(set (match_operand:HI 0 "register_operand" "=r,?&q")
3487      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3488    (clobber (reg:CC FLAGS_REG))]
3489   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3490   "#"
3491   [(set_attr "type" "alu1")
3492    (set_attr "mode" "HI")])
3493
3494 (define_insn "*zero_extendqihi2_movzbw_and"
3495   [(set (match_operand:HI 0 "register_operand" "=r,r")
3496      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3497    (clobber (reg:CC FLAGS_REG))]
3498   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3499   "#"
3500   [(set_attr "type" "imovx,alu1")
3501    (set_attr "mode" "HI")])
3502
3503 ; zero extend to SImode here to avoid partial register stalls
3504 (define_insn "*zero_extendqihi2_movzbl"
3505   [(set (match_operand:HI 0 "register_operand" "=r")
3506      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3507   "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3508   "movz{bl|x}\t{%1, %k0|%k0, %1}"
3509   [(set_attr "type" "imovx")
3510    (set_attr "mode" "SI")])
3511
3512 ;; For the movzbw case strip only the clobber
3513 (define_split
3514   [(set (match_operand:HI 0 "register_operand" "")
3515         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3516    (clobber (reg:CC FLAGS_REG))]
3517   "reload_completed
3518    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3519    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3520   [(set (match_operand:HI 0 "register_operand" "")
3521         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))])
3522
3523 ;; When source and destination does not overlap, clear destination
3524 ;; first and then do the movb
3525 (define_split
3526   [(set (match_operand:HI 0 "register_operand" "")
3527         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3528    (clobber (reg:CC FLAGS_REG))]
3529   "reload_completed
3530    && ANY_QI_REG_P (operands[0])
3531    && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3532    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3533   [(set (match_dup 0) (const_int 0))
3534    (set (strict_low_part (match_dup 2)) (match_dup 1))]
3535   "operands[2] = gen_lowpart (QImode, operands[0]);")
3536
3537 ;; Rest is handled by single and.
3538 (define_split
3539   [(set (match_operand:HI 0 "register_operand" "")
3540         (zero_extend:HI (match_operand:QI 1 "register_operand" "")))
3541    (clobber (reg:CC FLAGS_REG))]
3542   "reload_completed
3543    && true_regnum (operands[0]) == true_regnum (operands[1])"
3544   [(parallel [(set (match_dup 0) (and:HI (match_dup 0) (const_int 255)))
3545               (clobber (reg:CC FLAGS_REG))])]
3546   "")
3547
3548 (define_expand "zero_extendqisi2"
3549   [(parallel
3550     [(set (match_operand:SI 0 "register_operand" "")
3551        (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3552      (clobber (reg:CC FLAGS_REG))])]
3553   ""
3554   "")
3555
3556 (define_insn "*zero_extendqisi2_and"
3557   [(set (match_operand:SI 0 "register_operand" "=r,?&q")
3558      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3559    (clobber (reg:CC FLAGS_REG))]
3560   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3561   "#"
3562   [(set_attr "type" "alu1")
3563    (set_attr "mode" "SI")])
3564
3565 (define_insn "*zero_extendqisi2_movzbw_and"
3566   [(set (match_operand:SI 0 "register_operand" "=r,r")
3567      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3568    (clobber (reg:CC FLAGS_REG))]
3569   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3570   "#"
3571   [(set_attr "type" "imovx,alu1")
3572    (set_attr "mode" "SI")])
3573
3574 (define_insn "*zero_extendqisi2_movzbw"
3575   [(set (match_operand:SI 0 "register_operand" "=r")
3576      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3577   "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3578   "movz{bl|x}\t{%1, %0|%0, %1}"
3579   [(set_attr "type" "imovx")
3580    (set_attr "mode" "SI")])
3581
3582 ;; For the movzbl case strip only the clobber
3583 (define_split
3584   [(set (match_operand:SI 0 "register_operand" "")
3585         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3586    (clobber (reg:CC FLAGS_REG))]
3587   "reload_completed
3588    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3589    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3590   [(set (match_dup 0)
3591         (zero_extend:SI (match_dup 1)))])
3592
3593 ;; When source and destination does not overlap, clear destination
3594 ;; first and then do the movb
3595 (define_split
3596   [(set (match_operand:SI 0 "register_operand" "")
3597         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3598    (clobber (reg:CC FLAGS_REG))]
3599   "reload_completed
3600    && ANY_QI_REG_P (operands[0])
3601    && (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]))
3602    && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3603    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3604   [(set (match_dup 0) (const_int 0))
3605    (set (strict_low_part (match_dup 2)) (match_dup 1))]
3606   "operands[2] = gen_lowpart (QImode, operands[0]);")
3607
3608 ;; Rest is handled by single and.
3609 (define_split
3610   [(set (match_operand:SI 0 "register_operand" "")
3611         (zero_extend:SI (match_operand:QI 1 "register_operand" "")))
3612    (clobber (reg:CC FLAGS_REG))]
3613   "reload_completed
3614    && true_regnum (operands[0]) == true_regnum (operands[1])"
3615   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 255)))
3616               (clobber (reg:CC FLAGS_REG))])]
3617   "")
3618
3619 ;; %%% Kill me once multi-word ops are sane.
3620 (define_expand "zero_extendsidi2"
3621   [(set (match_operand:DI 0 "register_operand" "")
3622      (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
3623   ""
3624 {
3625   if (!TARGET_64BIT)
3626     {
3627       emit_insn (gen_zero_extendsidi2_32 (operands[0], operands[1]));
3628       DONE;
3629     }
3630 })
3631
3632 (define_insn "zero_extendsidi2_32"
3633   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?o,?*Ym,?*y,?*Yi,*Y2")
3634         (zero_extend:DI
3635          (match_operand:SI 1 "nonimmediate_operand" "0,rm,r ,r   ,m  ,r   ,m")))
3636    (clobber (reg:CC FLAGS_REG))]
3637   "!TARGET_64BIT"
3638   "@
3639    #
3640    #
3641    #
3642    movd\t{%1, %0|%0, %1}
3643    movd\t{%1, %0|%0, %1}
3644    movd\t{%1, %0|%0, %1}
3645    movd\t{%1, %0|%0, %1}"
3646   [(set_attr "mode" "SI,SI,SI,DI,DI,TI,TI")
3647    (set_attr "type" "multi,multi,multi,mmxmov,mmxmov,ssemov,ssemov")])
3648
3649 (define_insn "zero_extendsidi2_rex64"
3650   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,?*Ym,?*y,?*Yi,*Y2")
3651      (zero_extend:DI
3652        (match_operand:SI 1 "nonimmediate_operand"  "rm,0,r   ,m  ,r   ,m")))]
3653   "TARGET_64BIT"
3654   "@
3655    mov\t{%k1, %k0|%k0, %k1}
3656    #
3657    movd\t{%1, %0|%0, %1}
3658    movd\t{%1, %0|%0, %1}
3659    movd\t{%1, %0|%0, %1}
3660    movd\t{%1, %0|%0, %1}"
3661   [(set_attr "type" "imovx,imov,mmxmov,mmxmov,ssemov,ssemov")
3662    (set_attr "mode" "SI,DI,DI,DI,TI,TI")])
3663
3664 (define_split
3665   [(set (match_operand:DI 0 "memory_operand" "")
3666      (zero_extend:DI (match_dup 0)))]
3667   "TARGET_64BIT"
3668   [(set (match_dup 4) (const_int 0))]
3669   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3670
3671 (define_split
3672   [(set (match_operand:DI 0 "register_operand" "")
3673         (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3674    (clobber (reg:CC FLAGS_REG))]
3675   "!TARGET_64BIT && reload_completed
3676    && true_regnum (operands[0]) == true_regnum (operands[1])"
3677   [(set (match_dup 4) (const_int 0))]
3678   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3679
3680 (define_split
3681   [(set (match_operand:DI 0 "nonimmediate_operand" "")
3682         (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3683    (clobber (reg:CC FLAGS_REG))]
3684   "!TARGET_64BIT && reload_completed
3685    && !SSE_REG_P (operands[0]) && !MMX_REG_P (operands[0])"
3686   [(set (match_dup 3) (match_dup 1))
3687    (set (match_dup 4) (const_int 0))]
3688   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3689
3690 (define_insn "zero_extendhidi2"
3691   [(set (match_operand:DI 0 "register_operand" "=r")
3692      (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3693   "TARGET_64BIT"
3694   "movz{wl|x}\t{%1, %k0|%k0, %1}"
3695   [(set_attr "type" "imovx")
3696    (set_attr "mode" "DI")])
3697
3698 (define_insn "zero_extendqidi2"
3699   [(set (match_operand:DI 0 "register_operand" "=r")
3700      (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "rm")))]
3701   "TARGET_64BIT"
3702   "movz{bl|x}\t{%1, %k0|%k0, %1}"
3703   [(set_attr "type" "imovx")
3704    (set_attr "mode" "DI")])
3705 \f
3706 ;; Sign extension instructions
3707
3708 (define_expand "extendsidi2"
3709   [(parallel [(set (match_operand:DI 0 "register_operand" "")
3710                    (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3711               (clobber (reg:CC FLAGS_REG))
3712               (clobber (match_scratch:SI 2 ""))])]
3713   ""
3714 {
3715   if (TARGET_64BIT)
3716     {
3717       emit_insn (gen_extendsidi2_rex64 (operands[0], operands[1]));
3718       DONE;
3719     }
3720 })
3721
3722 (define_insn "*extendsidi2_1"
3723   [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3724         (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3725    (clobber (reg:CC FLAGS_REG))
3726    (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3727   "!TARGET_64BIT"
3728   "#")
3729
3730 (define_insn "extendsidi2_rex64"
3731   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3732         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3733   "TARGET_64BIT"
3734   "@
3735    {cltq|cdqe}
3736    movs{lq|x}\t{%1,%0|%0, %1}"
3737   [(set_attr "type" "imovx")
3738    (set_attr "mode" "DI")
3739    (set_attr "prefix_0f" "0")
3740    (set_attr "modrm" "0,1")])
3741
3742 (define_insn "extendhidi2"
3743   [(set (match_operand:DI 0 "register_operand" "=r")
3744         (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3745   "TARGET_64BIT"
3746   "movs{wq|x}\t{%1,%0|%0, %1}"
3747   [(set_attr "type" "imovx")
3748    (set_attr "mode" "DI")])
3749
3750 (define_insn "extendqidi2"
3751   [(set (match_operand:DI 0 "register_operand" "=r")
3752         (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3753   "TARGET_64BIT"
3754   "movs{bq|x}\t{%1,%0|%0, %1}"
3755    [(set_attr "type" "imovx")
3756     (set_attr "mode" "DI")])
3757
3758 ;; Extend to memory case when source register does die.
3759 (define_split
3760   [(set (match_operand:DI 0 "memory_operand" "")
3761         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3762    (clobber (reg:CC FLAGS_REG))
3763    (clobber (match_operand:SI 2 "register_operand" ""))]
3764   "(reload_completed
3765     && dead_or_set_p (insn, operands[1])
3766     && !reg_mentioned_p (operands[1], operands[0]))"
3767   [(set (match_dup 3) (match_dup 1))
3768    (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3769               (clobber (reg:CC FLAGS_REG))])
3770    (set (match_dup 4) (match_dup 1))]
3771   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3772
3773 ;; Extend to memory case when source register does not die.
3774 (define_split
3775   [(set (match_operand:DI 0 "memory_operand" "")
3776         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3777    (clobber (reg:CC FLAGS_REG))
3778    (clobber (match_operand:SI 2 "register_operand" ""))]
3779   "reload_completed"
3780   [(const_int 0)]
3781 {
3782   split_di (&operands[0], 1, &operands[3], &operands[4]);
3783
3784   emit_move_insn (operands[3], operands[1]);
3785
3786   /* Generate a cltd if possible and doing so it profitable.  */
3787   if ((optimize_size || TARGET_USE_CLTD)
3788       && true_regnum (operands[1]) == AX_REG
3789       && true_regnum (operands[2]) == DX_REG)
3790     {
3791       emit_insn (gen_ashrsi3_31 (operands[2], operands[1], GEN_INT (31)));
3792     }
3793   else
3794     {
3795       emit_move_insn (operands[2], operands[1]);
3796       emit_insn (gen_ashrsi3_31 (operands[2], operands[2], GEN_INT (31)));
3797     }
3798   emit_move_insn (operands[4], operands[2]);
3799   DONE;
3800 })
3801
3802 ;; Extend to register case.  Optimize case where source and destination
3803 ;; registers match and cases where we can use cltd.
3804 (define_split
3805   [(set (match_operand:DI 0 "register_operand" "")
3806         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3807    (clobber (reg:CC FLAGS_REG))
3808    (clobber (match_scratch:SI 2 ""))]
3809   "reload_completed"
3810   [(const_int 0)]
3811 {
3812   split_di (&operands[0], 1, &operands[3], &operands[4]);
3813
3814   if (true_regnum (operands[3]) != true_regnum (operands[1]))
3815     emit_move_insn (operands[3], operands[1]);
3816
3817   /* Generate a cltd if possible and doing so it profitable.  */
3818   if ((optimize_size || TARGET_USE_CLTD)
3819       && true_regnum (operands[3]) == AX_REG)
3820     {
3821       emit_insn (gen_ashrsi3_31 (operands[4], operands[3], GEN_INT (31)));
3822       DONE;
3823     }
3824
3825   if (true_regnum (operands[4]) != true_regnum (operands[1]))
3826     emit_move_insn (operands[4], operands[1]);
3827
3828   emit_insn (gen_ashrsi3_31 (operands[4], operands[4], GEN_INT (31)));
3829   DONE;
3830 })
3831
3832 (define_insn "extendhisi2"
3833   [(set (match_operand:SI 0 "register_operand" "=*a,r")
3834         (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3835   ""
3836 {
3837   switch (get_attr_prefix_0f (insn))
3838     {
3839     case 0:
3840       return "{cwtl|cwde}";
3841     default:
3842       return "movs{wl|x}\t{%1,%0|%0, %1}";
3843     }
3844 }
3845   [(set_attr "type" "imovx")
3846    (set_attr "mode" "SI")
3847    (set (attr "prefix_0f")
3848      ;; movsx is short decodable while cwtl is vector decoded.
3849      (if_then_else (and (eq_attr "cpu" "!k6")
3850                         (eq_attr "alternative" "0"))
3851         (const_string "0")
3852         (const_string "1")))
3853    (set (attr "modrm")
3854      (if_then_else (eq_attr "prefix_0f" "0")
3855         (const_string "0")
3856         (const_string "1")))])
3857
3858 (define_insn "*extendhisi2_zext"
3859   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3860         (zero_extend:DI
3861           (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3862   "TARGET_64BIT"
3863 {
3864   switch (get_attr_prefix_0f (insn))
3865     {
3866     case 0:
3867       return "{cwtl|cwde}";
3868     default:
3869       return "movs{wl|x}\t{%1,%k0|%k0, %1}";
3870     }
3871 }
3872   [(set_attr "type" "imovx")
3873    (set_attr "mode" "SI")
3874    (set (attr "prefix_0f")
3875      ;; movsx is short decodable while cwtl is vector decoded.
3876      (if_then_else (and (eq_attr "cpu" "!k6")
3877                         (eq_attr "alternative" "0"))
3878         (const_string "0")
3879         (const_string "1")))
3880    (set (attr "modrm")
3881      (if_then_else (eq_attr "prefix_0f" "0")
3882         (const_string "0")
3883         (const_string "1")))])
3884
3885 (define_insn "extendqihi2"
3886   [(set (match_operand:HI 0 "register_operand" "=*a,r")
3887         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3888   ""
3889 {
3890   switch (get_attr_prefix_0f (insn))
3891     {
3892     case 0:
3893       return "{cbtw|cbw}";
3894     default:
3895       return "movs{bw|x}\t{%1,%0|%0, %1}";
3896     }
3897 }
3898   [(set_attr "type" "imovx")
3899    (set_attr "mode" "HI")
3900    (set (attr "prefix_0f")
3901      ;; movsx is short decodable while cwtl is vector decoded.
3902      (if_then_else (and (eq_attr "cpu" "!k6")
3903                         (eq_attr "alternative" "0"))
3904         (const_string "0")
3905         (const_string "1")))
3906    (set (attr "modrm")
3907      (if_then_else (eq_attr "prefix_0f" "0")
3908         (const_string "0")
3909         (const_string "1")))])
3910
3911 (define_insn "extendqisi2"
3912   [(set (match_operand:SI 0 "register_operand" "=r")
3913         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3914   ""
3915   "movs{bl|x}\t{%1,%0|%0, %1}"
3916    [(set_attr "type" "imovx")
3917     (set_attr "mode" "SI")])
3918
3919 (define_insn "*extendqisi2_zext"
3920   [(set (match_operand:DI 0 "register_operand" "=r")
3921         (zero_extend:DI
3922           (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3923   "TARGET_64BIT"
3924   "movs{bl|x}\t{%1,%k0|%k0, %1}"
3925    [(set_attr "type" "imovx")
3926     (set_attr "mode" "SI")])
3927 \f
3928 ;; Conversions between float and double.
3929
3930 ;; These are all no-ops in the model used for the 80387.  So just
3931 ;; emit moves.
3932
3933 ;; %%% Kill these when call knows how to work out a DFmode push earlier.
3934 (define_insn "*dummy_extendsfdf2"
3935   [(set (match_operand:DF 0 "push_operand" "=<")
3936         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fY2")))]
3937   "0"
3938   "#")
3939
3940 (define_split
3941   [(set (match_operand:DF 0 "push_operand" "")
3942         (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3943   ""
3944   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (const_int -8)))
3945    (set (mem:DF (reg:P SP_REG)) (float_extend:DF (match_dup 1)))])
3946
3947 (define_insn "*dummy_extendsfxf2"
3948   [(set (match_operand:XF 0 "push_operand" "=<")
3949         (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "f")))]
3950   "0"
3951   "#")
3952
3953 (define_split
3954   [(set (match_operand:XF 0 "push_operand" "")
3955         (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3956   ""
3957   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
3958    (set (mem:XF (reg:P SP_REG)) (float_extend:XF (match_dup 1)))]
3959   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3960
3961 (define_split
3962   [(set (match_operand:XF 0 "push_operand" "")
3963         (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3964   ""
3965   [(set (reg:P SP_REG) (plus:P (reg:P SP_REG) (match_dup 2)))
3966    (set (mem:DF (reg:P SP_REG)) (float_extend:XF (match_dup 1)))]
3967   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3968
3969 (define_expand "extendsfdf2"
3970   [(set (match_operand:DF 0 "nonimmediate_operand" "")
3971         (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
3972   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3973 {
3974   /* ??? Needed for compress_float_constant since all fp constants
3975      are LEGITIMATE_CONSTANT_P.  */
3976   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3977     {
3978       if ((!TARGET_SSE2 || TARGET_MIX_SSE_I387)
3979           && standard_80387_constant_p (operands[1]) > 0)
3980         {
3981           operands[1] = simplify_const_unary_operation
3982             (FLOAT_EXTEND, DFmode, operands[1], SFmode);
3983           emit_move_insn_1 (operands[0], operands[1]);
3984           DONE;
3985         }
3986       operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3987     }
3988 })
3989
3990 /* For converting SF(xmm2) to DF(xmm1), use the following code instead of
3991    cvtss2sd:
3992       unpcklps xmm2,xmm2   ; packed conversion might crash on signaling NaNs
3993       cvtps2pd xmm2,xmm1
3994    We do the conversion post reload to avoid producing of 128bit spills
3995    that might lead to ICE on 32bit target.  The sequence unlikely combine
3996    anyway.  */
3997 (define_split
3998   [(set (match_operand:DF 0 "register_operand" "")
3999         (float_extend:DF
4000           (match_operand:SF 1 "nonimmediate_operand" "")))]
4001   "(TARGET_USE_VECTOR_CONVERTS || TARGET_GENERIC) && !optimize_size
4002    && reload_completed && SSE_REG_P (operands[0])"
4003    [(set (match_dup 2)
4004          (float_extend:V2DF
4005            (vec_select:V2SF
4006              (match_dup 3)
4007              (parallel [(const_int 0) (const_int 1)]))))]
4008 {
4009   operands[2] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
4010   operands[3] = simplify_gen_subreg (V4SFmode, operands[0], DFmode, 0);
4011   /* Use movss for loading from memory, unpcklps reg, reg for registers.
4012      Try to avoid move when unpacking can be done in source.  */
4013   if (REG_P (operands[1]))
4014     {
4015       /* If it is unsafe to overwrite upper half of source, we need
4016          to move to destination and unpack there.  */
4017       if ((ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
4018            || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 4)
4019           && true_regnum (operands[0]) != true_regnum (operands[1]))
4020         {
4021           rtx tmp = gen_rtx_REG (SFmode, true_regnum (operands[0]));
4022           emit_move_insn (tmp, operands[1]);
4023         }
4024       else
4025         operands[3] = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
4026       emit_insn (gen_sse_unpcklps (operands[3], operands[3], operands[3]));
4027     }
4028   else
4029     emit_insn (gen_vec_setv4sf_0 (operands[3],
4030                                   CONST0_RTX (V4SFmode), operands[1]));
4031 })
4032
4033 (define_insn "*extendsfdf2_mixed"
4034   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m,x")
4035         (float_extend:DF
4036           (match_operand:SF 1 "nonimmediate_operand" "fm,f,xm")))]
4037   "TARGET_SSE2 && TARGET_MIX_SSE_I387"
4038 {
4039   switch (which_alternative)
4040     {
4041     case 0:
4042     case 1:
4043       return output_387_reg_move (insn, operands);
4044
4045     case 2:
4046       return "cvtss2sd\t{%1, %0|%0, %1}";
4047
4048     default:
4049       gcc_unreachable ();
4050     }
4051 }
4052   [(set_attr "type" "fmov,fmov,ssecvt")
4053    (set_attr "mode" "SF,XF,DF")])
4054
4055 (define_insn "*extendsfdf2_sse"
4056   [(set (match_operand:DF 0 "nonimmediate_operand" "=x")
4057         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
4058   "TARGET_SSE2 && TARGET_SSE_MATH"
4059   "cvtss2sd\t{%1, %0|%0, %1}"
4060   [(set_attr "type" "ssecvt")
4061    (set_attr "mode" "DF")])
4062
4063 (define_insn "*extendsfdf2_i387"
4064   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
4065         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
4066   "TARGET_80387"
4067   "* return output_387_reg_move (insn, operands);"
4068   [(set_attr "type" "fmov")
4069    (set_attr "mode" "SF,XF")])
4070
4071 (define_expand "extend<mode>xf2"
4072   [(set (match_operand:XF 0 "nonimmediate_operand" "")
4073         (float_extend:XF (match_operand:MODEF 1 "general_operand" "")))]
4074   "TARGET_80387"
4075 {
4076   /* ??? Needed for compress_float_constant since all fp constants
4077      are LEGITIMATE_CONSTANT_P.  */
4078   if (GET_CODE (operands[1]) == CONST_DOUBLE)
4079     {
4080       if (standard_80387_constant_p (operands[1]) > 0)
4081         {
4082           operands[1] = simplify_const_unary_operation
4083             (FLOAT_EXTEND, XFmode, operands[1], <MODE>mode);
4084           emit_move_insn_1 (operands[0], operands[1]);
4085           DONE;
4086         }
4087       operands[1] = validize_mem (force_const_mem (<MODE>mode, operands[1]));
4088     }
4089 })
4090
4091 (define_insn "*extend<mode>xf2_i387"
4092   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
4093         (float_extend:XF
4094           (match_operand:MODEF 1 "nonimmediate_operand" "fm,f")))]
4095   "TARGET_80387"
4096   "* return output_387_reg_move (insn, operands);"
4097   [(set_attr "type" "fmov")
4098    (set_attr "mode" "<MODE>,XF")])
4099
4100 ;; %%% This seems bad bad news.
4101 ;; This cannot output into an f-reg because there is no way to be sure
4102 ;; of truncating in that case.  Otherwise this is just like a simple move
4103 ;; insn.  So we pretend we can output to a reg in order to get better
4104 ;; register preferencing, but we really use a stack slot.
4105
4106 ;; Conversion from DFmode to SFmode.
4107
4108 (define_expand "truncdfsf2"
4109   [(set (match_operand:SF 0 "nonimmediate_operand" "")
4110         (float_truncate:SF
4111           (match_operand:DF 1 "nonimmediate_operand" "")))]
4112   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4113 {
4114   if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387)
4115     ;
4116   else if (flag_unsafe_math_optimizations)
4117     ;
4118   else
4119     {
4120       int slot = virtuals_instantiated ? SLOT_TEMP : SLOT_VIRTUAL;
4121       rtx temp = assign_386_stack_local (SFmode, slot);
4122       emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp));
4123       DONE;
4124     }
4125 })
4126
4127 /* For converting DF(xmm2) to SF(xmm1), use the following code instead of
4128    cvtsd2ss:
4129       unpcklpd xmm2,xmm2   ; packed conversion might crash on signaling NaNs
4130       cvtpd2ps xmm2,xmm1
4131    We do the conversion post reload to avoid producing of 128bit spills
4132    that might lead to ICE on 32bit target.  The sequence unlikely combine
4133    anyway.  */
4134 (define_split
4135   [(set (match_operand:SF 0 "register_operand" "")
4136         (float_truncate:SF
4137           (match_operand:DF 1 "nonimmediate_operand" "")))]
4138   "(TARGET_USE_VECTOR_CONVERTS || TARGET_GENERIC) && !optimize_size
4139    && reload_completed && SSE_REG_P (operands[0])"
4140    [(set (match_dup 2)
4141          (vec_concat:V4SF
4142            (float_truncate:V2SF
4143              (match_dup 4))
4144            (match_dup 3)))]
4145 {
4146   operands[2] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
4147   operands[3] = CONST0_RTX (V2SFmode);
4148   operands[4] = simplify_gen_subreg (V2DFmode, operands[0], SFmode, 0);
4149   /* Use movsd for loading from memory, unpcklpd for registers.
4150      Try to avoid move when unpacking can be done in source, or SSE3
4151      movddup is available.  */
4152   if (REG_P (operands[1]))
4153     {
4154       if (!TARGET_SSE3
4155           && true_regnum (operands[0]) != true_regnum (operands[1])
4156           && (ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
4157               || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 8))
4158         {
4159           rtx tmp = simplify_gen_subreg (DFmode, operands[0], SFmode, 0);
4160           emit_move_insn (tmp, operands[1]);
4161           operands[1] = tmp;
4162         }
4163       else if (!TARGET_SSE3)
4164         operands[4] = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
4165       emit_insn (gen_vec_dupv2df (operands[4], operands[1]));
4166     }
4167   else
4168     emit_insn (gen_sse2_loadlpd (operands[4],
4169                                  CONST0_RTX (V2DFmode), operands[1]));
4170 })
4171
4172 (define_expand "truncdfsf2_with_temp"
4173   [(parallel [(set (match_operand:SF 0 "" "")
4174                    (float_truncate:SF (match_operand:DF 1 "" "")))
4175               (clobber (match_operand:SF 2 "" ""))])]
4176   "")
4177
4178 (define_insn "*truncdfsf_fast_mixed"
4179   [(set (match_operand:SF 0 "nonimmediate_operand"   "=fm,x")
4180         (float_truncate:SF
4181           (match_operand:DF 1 "nonimmediate_operand" "f  ,xm")))]
4182   "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations"
4183 {
4184   switch (which_alternative)
4185     {
4186     case 0:
4187       return output_387_reg_move (insn, operands);
4188     case 1:
4189       return "cvtsd2ss\t{%1, %0|%0, %1}";
4190     default:
4191       gcc_unreachable ();
4192     }
4193 }
4194   [(set_attr "type" "fmov,ssecvt")
4195    (set_attr "mode" "SF")])
4196
4197 ;; Yes, this one doesn't depend on flag_unsafe_math_optimizations,
4198 ;; because nothing we do here is unsafe.
4199 (define_insn "*truncdfsf_fast_sse"
4200   [(set (match_operand:SF 0 "nonimmediate_operand"   "=x")
4201         (float_truncate:SF
4202           (match_operand:DF 1 "nonimmediate_operand" "xm")))]
4203   "TARGET_SSE2 && TARGET_SSE_MATH"
4204   "cvtsd2ss\t{%1, %0|%0, %1}"
4205   [(set_attr "type" "ssecvt")
4206    (set_attr "mode" "SF")])
4207
4208 (define_insn "*truncdfsf_fast_i387"
4209   [(set (match_operand:SF 0 "nonimmediate_operand"   "=fm")
4210         (float_truncate:SF
4211           (match_operand:DF 1 "nonimmediate_operand" "f")))]
4212   "TARGET_80387 && flag_unsafe_math_optimizations"
4213   "* return output_387_reg_move (insn, operands);"
4214   [(set_attr "type" "fmov")
4215    (set_attr "mode" "SF")])
4216
4217 (define_insn "*truncdfsf_mixed"
4218   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,?fx*r,Y2")
4219         (float_truncate:SF
4220           (match_operand:DF 1 "nonimmediate_operand" "f ,f    ,Y2m")))
4221    (clobber (match_operand:SF 2 "memory_operand"     "=X,m    ,X"))]
4222   "TARGET_MIX_SSE_I387"
4223 {
4224   switch (which_alternative)
4225     {
4226     case 0:
4227       return output_387_reg_move (insn, operands);
4228
4229     case 1:
4230       return "#";
4231     case 2:
4232       return "cvtsd2ss\t{%1, %0|%0, %1}";
4233     default:
4234       gcc_unreachable ();
4235     }
4236 }
4237   [(set_attr "type" "fmov,multi,ssecvt")
4238    (set_attr "unit" "*,i387,*")
4239    (set_attr "mode" "SF")])
4240
4241 (define_insn "*truncdfsf_i387"
4242   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r")
4243         (float_truncate:SF
4244           (match_operand:DF 1 "nonimmediate_operand" "f,f")))
4245    (clobber (match_operand:SF 2 "memory_operand" "=X,m"))]
4246   "TARGET_80387"
4247 {
4248   switch (which_alternative)
4249     {
4250     case 0:
4251       return output_387_reg_move (insn, operands);
4252
4253     case 1:
4254       return "#";
4255     default:
4256       gcc_unreachable ();
4257     }
4258 }
4259   [(set_attr "type" "fmov,multi")
4260    (set_attr "unit" "*,i387")
4261    (set_attr "mode" "SF")])
4262
4263 (define_insn "*truncdfsf2_i387_1"
4264   [(set (match_operand:SF 0 "memory_operand" "=m")
4265         (float_truncate:SF
4266           (match_operand:DF 1 "register_operand" "f")))]
4267   "TARGET_80387
4268    && !(TARGET_SSE2 && TARGET_SSE_MATH)
4269    && !TARGET_MIX_SSE_I387"
4270   "* return output_387_reg_move (insn, operands);"
4271   [(set_attr "type" "fmov")
4272    (set_attr "mode" "SF")])
4273
4274 (define_split
4275   [(set (match_operand:SF 0 "register_operand" "")
4276         (float_truncate:SF
4277          (match_operand:DF 1 "fp_register_operand" "")))
4278    (clobber (match_operand 2 "" ""))]
4279   "reload_completed"
4280   [(set (match_dup 2) (match_dup 1))
4281    (set (match_dup 0) (match_dup 2))]
4282 {
4283   operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1]));
4284 })
4285
4286 ;; Conversion from XFmode to {SF,DF}mode
4287
4288 (define_expand "truncxf<mode>2"
4289   [(parallel [(set (match_operand:MODEF 0 "nonimmediate_operand" "")
4290                    (float_truncate:MODEF
4291                      (match_operand:XF 1 "register_operand" "")))
4292               (clobber (match_dup 2))])]
4293   "TARGET_80387"
4294 {
4295   if (flag_unsafe_math_optimizations)
4296     {
4297       rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (<MODE>mode);
4298       emit_insn (gen_truncxf<mode>2_i387_noop (reg, operands[1]));
4299       if (reg != operands[0])
4300         emit_move_insn (operands[0], reg);
4301       DONE;
4302     }
4303   else
4304     {
4305       int slot = virtuals_instantiated ? SLOT_TEMP : SLOT_VIRTUAL;
4306       operands[2] = assign_386_stack_local (<MODE>mode, slot);
4307     }
4308 })
4309
4310 (define_insn "*truncxfsf2_mixed"
4311   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r")
4312         (float_truncate:SF
4313           (match_operand:XF 1 "register_operand" "f,f")))
4314    (clobber (match_operand:SF 2 "memory_operand" "=X,m"))]
4315   "TARGET_80387"
4316 {
4317   gcc_assert (!which_alternative);
4318   return output_387_reg_move (insn, operands);
4319 }
4320   [(set_attr "type" "fmov,multi")
4321    (set_attr "unit" "*,i387")
4322    (set_attr "mode" "SF")])
4323
4324 (define_insn "*truncxfdf2_mixed"
4325   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?fY2*r")
4326         (float_truncate:DF
4327           (match_operand:XF 1 "register_operand" "f,f")))
4328    (clobber (match_operand:DF 2 "memory_operand" "=X,m"))]
4329   "TARGET_80387"
4330 {
4331   gcc_assert (!which_alternative);
4332   return output_387_reg_move (insn, operands);
4333 }
4334   [(set_attr "type" "fmov,multi")
4335    (set_attr "unit" "*,i387")
4336    (set_attr "mode" "DF")])
4337
4338 (define_insn "truncxf<mode>2_i387_noop"
4339   [(set (match_operand:MODEF 0 "register_operand" "=f")
4340         (float_truncate:MODEF
4341           (match_operand:XF 1 "register_operand" "f")))]
4342   "TARGET_80387 && flag_unsafe_math_optimizations"
4343   "* return output_387_reg_move (insn, operands);"
4344   [(set_attr "type" "fmov")
4345    (set_attr "mode" "<MODE>")])
4346
4347 (define_insn "*truncxf<mode>2_i387"
4348   [(set (match_operand:MODEF 0 "memory_operand" "=m")
4349         (float_truncate:MODEF
4350           (match_operand:XF 1 "register_operand" "f")))]
4351   "TARGET_80387"
4352   "* return output_387_reg_move (insn, operands);"
4353   [(set_attr "type" "fmov")
4354    (set_attr "mode" "<MODE>")])
4355
4356 (define_split
4357   [(set (match_operand:MODEF 0 "register_operand" "")
4358         (float_truncate:MODEF
4359           (match_operand:XF 1 "register_operand" "")))
4360    (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4361   "TARGET_80387 && reload_completed"
4362   [(set (match_dup 2) (float_truncate:MODEF (match_dup 1)))
4363    (set (match_dup 0) (match_dup 2))]
4364   "")
4365
4366 (define_split
4367   [(set (match_operand:MODEF 0 "memory_operand" "")
4368         (float_truncate:MODEF
4369           (match_operand:XF 1 "register_operand" "")))
4370    (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4371   "TARGET_80387"
4372   [(set (match_dup 0) (float_truncate:MODEF (match_dup 1)))]
4373   "")
4374 \f
4375 ;; Signed conversion to DImode.
4376
4377 (define_expand "fix_truncxfdi2"
4378   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4379                    (fix:DI (match_operand:XF 1 "register_operand" "")))
4380               (clobber (reg:CC FLAGS_REG))])]
4381   "TARGET_80387"
4382 {
4383   if (TARGET_FISTTP)
4384    {
4385      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4386      DONE;
4387    }
4388 })
4389
4390 (define_expand "fix_trunc<mode>di2"
4391   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4392                    (fix:DI (match_operand:MODEF 1 "register_operand" "")))
4393               (clobber (reg:CC FLAGS_REG))])]
4394   "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))"
4395 {
4396   if (TARGET_FISTTP
4397       && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4398    {
4399      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4400      DONE;
4401    }
4402   if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))
4403    {
4404      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4405      emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1]));
4406      if (out != operands[0])
4407         emit_move_insn (operands[0], out);
4408      DONE;
4409    }
4410 })
4411
4412 ;; Signed conversion to SImode.
4413
4414 (define_expand "fix_truncxfsi2"
4415   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4416                    (fix:SI (match_operand:XF 1 "register_operand" "")))
4417               (clobber (reg:CC FLAGS_REG))])]
4418   "TARGET_80387"
4419 {
4420   if (TARGET_FISTTP)
4421    {
4422      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4423      DONE;
4424    }
4425 })
4426
4427 (define_expand "fix_trunc<mode>si2"
4428   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4429                    (fix:SI (match_operand:MODEF 1 "register_operand" "")))
4430               (clobber (reg:CC FLAGS_REG))])]
4431   "TARGET_80387 || SSE_FLOAT_MODE_P (<MODE>mode)"
4432 {
4433   if (TARGET_FISTTP
4434       && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4435    {
4436      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4437      DONE;
4438    }
4439   if (SSE_FLOAT_MODE_P (<MODE>mode))
4440    {
4441      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4442      emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1]));
4443      if (out != operands[0])
4444         emit_move_insn (operands[0], out);
4445      DONE;
4446    }
4447 })
4448
4449 ;; Signed conversion to HImode.
4450
4451 (define_expand "fix_trunc<mode>hi2"
4452   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4453                    (fix:HI (match_operand:X87MODEF 1 "register_operand" "")))
4454               (clobber (reg:CC FLAGS_REG))])]
4455   "TARGET_80387
4456    && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))"
4457 {
4458   if (TARGET_FISTTP)
4459    {
4460      emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1]));
4461      DONE;
4462    }
4463 })
4464
4465 ;; Unsigned conversion to SImode.
4466
4467 (define_expand "fixuns_trunc<mode>si2"
4468   [(parallel
4469     [(set (match_operand:SI 0 "register_operand" "")
4470           (unsigned_fix:SI
4471             (match_operand:MODEF 1 "nonimmediate_operand" "")))
4472      (use (match_dup 2))
4473      (clobber (match_scratch:<ssevecmode> 3 ""))
4474      (clobber (match_scratch:<ssevecmode> 4 ""))])]
4475   "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH && !optimize_size"
4476 {
4477   enum machine_mode mode = <MODE>mode;
4478   enum machine_mode vecmode = <ssevecmode>mode;
4479   REAL_VALUE_TYPE TWO31r;
4480   rtx two31;
4481
4482   real_ldexp (&TWO31r, &dconst1, 31);
4483   two31 = const_double_from_real_value (TWO31r, mode);
4484   two31 = ix86_build_const_vector (mode, true, two31);
4485   operands[2] = force_reg (vecmode, two31);
4486 })
4487
4488 (define_insn_and_split "*fixuns_trunc<mode>_1"
4489   [(set (match_operand:SI 0 "register_operand" "=&x,&x")
4490         (unsigned_fix:SI
4491           (match_operand:MODEF 3 "nonimmediate_operand" "xm,xm")))
4492    (use (match_operand:<ssevecmode> 4  "nonimmediate_operand" "m,x"))
4493    (clobber (match_scratch:<ssevecmode> 1 "=x,&x"))
4494    (clobber (match_scratch:<ssevecmode> 2 "=x,x"))]
4495   "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH && !optimize_size"
4496   "#"
4497   "&& reload_completed"
4498   [(const_int 0)]
4499 {
4500   ix86_split_convert_uns_si_sse (operands);
4501   DONE;
4502 })
4503
4504 ;; Unsigned conversion to HImode.
4505 ;; Without these patterns, we'll try the unsigned SI conversion which
4506 ;; is complex for SSE, rather than the signed SI conversion, which isn't.
4507
4508 (define_expand "fixuns_trunc<mode>hi2"
4509   [(set (match_dup 2)
4510         (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "")))
4511    (set (match_operand:HI 0 "nonimmediate_operand" "")
4512         (subreg:HI (match_dup 2) 0))]
4513   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
4514   "operands[2] = gen_reg_rtx (SImode);")
4515
4516 ;; When SSE is available, it is always faster to use it!
4517 (define_insn "fix_trunc<mode>di_sse"
4518   [(set (match_operand:DI 0 "register_operand" "=r,r")
4519         (fix:DI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4520   "TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode)
4521    && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4522   "cvtts<ssemodefsuffix>2si{q}\t{%1, %0|%0, %1}"
4523   [(set_attr "type" "sseicvt")
4524    (set_attr "mode" "<MODE>")
4525    (set_attr "athlon_decode" "double,vector")
4526    (set_attr "amdfam10_decode" "double,double")])
4527
4528 (define_insn "fix_trunc<mode>si_sse"
4529   [(set (match_operand:SI 0 "register_operand" "=r,r")
4530         (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4531   "SSE_FLOAT_MODE_P (<MODE>mode)
4532    && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4533   "cvtts<ssemodefsuffix>2si\t{%1, %0|%0, %1}"
4534   [(set_attr "type" "sseicvt")
4535    (set_attr "mode" "<MODE>")
4536    (set_attr "athlon_decode" "double,vector")
4537    (set_attr "amdfam10_decode" "double,double")])
4538
4539 ;; Shorten x87->SSE reload sequences of fix_trunc?f?i_sse patterns.
4540 (define_peephole2
4541   [(set (match_operand:MODEF 0 "register_operand" "")
4542         (match_operand:MODEF 1 "memory_operand" ""))
4543    (set (match_operand:SSEMODEI24 2 "register_operand" "")
4544         (fix:SSEMODEI24 (match_dup 0)))]
4545   "TARGET_SHORTEN_X87_SSE
4546    && peep2_reg_dead_p (2, operands[0])"
4547   [(set (match_dup 2) (fix:SSEMODEI24 (match_dup 1)))]
4548   "")
4549
4550 ;; Avoid vector decoded forms of the instruction.
4551 (define_peephole2
4552   [(match_scratch:DF 2 "Y2")
4553    (set (match_operand:SSEMODEI24 0 "register_operand" "")
4554         (fix:SSEMODEI24 (match_operand:DF 1 "memory_operand" "")))]
4555   "TARGET_AVOID_VECTOR_DECODE && !optimize_size"
4556   [(set (match_dup 2) (match_dup 1))
4557    (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4558   "")
4559
4560 (define_peephole2
4561   [(match_scratch:SF 2 "x")
4562    (set (match_operand:SSEMODEI24 0 "register_operand" "")
4563         (fix:SSEMODEI24 (match_operand:SF 1 "memory_operand" "")))]
4564   "TARGET_AVOID_VECTOR_DECODE && !optimize_size"
4565   [(set (match_dup 2) (match_dup 1))
4566    (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4567   "")
4568
4569 (define_insn_and_split "fix_trunc<mode>_fisttp_i387_1"
4570   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
4571         (fix:X87MODEI (match_operand 1 "register_operand" "")))]
4572   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4573    && TARGET_FISTTP
4574    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4575          && (TARGET_64BIT || <MODE>mode != DImode))
4576         && TARGET_SSE_MATH)
4577    && !(reload_completed || reload_in_progress)"
4578   "#"
4579   "&& 1"
4580   [(const_int 0)]
4581 {
4582   if (memory_operand (operands[0], VOIDmode))
4583     emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1]));
4584   else
4585     {
4586       operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4587       emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0],
4588                                                             operands[1],
4589                                                             operands[2]));
4590     }
4591   DONE;
4592 }
4593   [(set_attr "type" "fisttp")
4594    (set_attr "mode" "<MODE>")])
4595
4596 (define_insn "fix_trunc<mode>_i387_fisttp"
4597   [(set (match_operand:X87MODEI 0 "memory_operand" "=m")
4598         (fix:X87MODEI (match_operand 1 "register_operand" "f")))
4599    (clobber (match_scratch:XF 2 "=&1f"))]
4600   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4601    && TARGET_FISTTP
4602    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4603          && (TARGET_64BIT || <MODE>mode != DImode))
4604         && TARGET_SSE_MATH)"
4605   "* return output_fix_trunc (insn, operands, 1);"
4606   [(set_attr "type" "fisttp")
4607    (set_attr "mode" "<MODE>")])
4608
4609 (define_insn "fix_trunc<mode>_i387_fisttp_with_temp"
4610   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4611         (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
4612    (clobber (match_operand:X87MODEI 2 "memory_operand" "=X,m"))
4613    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
4614   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4615    && TARGET_FISTTP
4616    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4617         && (TARGET_64BIT || <MODE>mode != DImode))
4618         && TARGET_SSE_MATH)"
4619   "#"
4620   [(set_attr "type" "fisttp")
4621    (set_attr "mode" "<MODE>")])
4622
4623 (define_split
4624   [(set (match_operand:X87MODEI 0 "register_operand" "")
4625         (fix:X87MODEI (match_operand 1 "register_operand" "")))
4626    (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4627    (clobber (match_scratch 3 ""))]
4628   "reload_completed"
4629   [(parallel [(set (match_dup 2) (fix:X87MODEI (match_dup 1)))
4630               (clobber (match_dup 3))])
4631    (set (match_dup 0) (match_dup 2))]
4632   "")
4633
4634 (define_split
4635   [(set (match_operand:X87MODEI 0 "memory_operand" "")
4636         (fix:X87MODEI (match_operand 1 "register_operand" "")))
4637    (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4638    (clobber (match_scratch 3 ""))]
4639   "reload_completed"
4640   [(parallel [(set (match_dup 0) (fix:X87MODEI (match_dup 1)))
4641               (clobber (match_dup 3))])]
4642   "")
4643
4644 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4645 ;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control
4646 ;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG
4647 ;; clobbering insns can be used. Look at emit_i387_cw_initialization ()
4648 ;; function in i386.c.
4649 (define_insn_and_split "*fix_trunc<mode>_i387_1"
4650   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
4651         (fix:X87MODEI (match_operand 1 "register_operand" "")))
4652    (clobber (reg:CC FLAGS_REG))]
4653   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4654    && !TARGET_FISTTP
4655    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4656          && (TARGET_64BIT || <MODE>mode != DImode))
4657    && !(reload_completed || reload_in_progress)"
4658   "#"
4659   "&& 1"
4660   [(const_int 0)]
4661 {
4662   ix86_optimize_mode_switching[I387_TRUNC] = 1;
4663
4664   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
4665   operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
4666   if (memory_operand (operands[0], VOIDmode))
4667     emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1],
4668                                          operands[2], operands[3]));
4669   else
4670     {
4671       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4672       emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1],
4673                                                      operands[2], operands[3],
4674                                                      operands[4]));
4675     }
4676   DONE;
4677 }
4678   [(set_attr "type" "fistp")
4679    (set_attr "i387_cw" "trunc")
4680    (set_attr "mode" "<MODE>")])
4681
4682 (define_insn "fix_truncdi_i387"
4683   [(set (match_operand:DI 0 "memory_operand" "=m")
4684         (fix:DI (match_operand 1 "register_operand" "f")))
4685    (use (match_operand:HI 2 "memory_operand" "m"))
4686    (use (match_operand:HI 3 "memory_operand" "m"))
4687    (clobber (match_scratch:XF 4 "=&1f"))]
4688   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4689    && !TARGET_FISTTP
4690    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4691   "* return output_fix_trunc (insn, operands, 0);"
4692   [(set_attr "type" "fistp")
4693    (set_attr "i387_cw" "trunc")
4694    (set_attr "mode" "DI")])
4695
4696 (define_insn "fix_truncdi_i387_with_temp"
4697   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4698         (fix:DI (match_operand 1 "register_operand" "f,f")))
4699    (use (match_operand:HI 2 "memory_operand" "m,m"))
4700    (use (match_operand:HI 3 "memory_operand" "m,m"))
4701    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
4702    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
4703   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4704    && !TARGET_FISTTP
4705    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4706   "#"
4707   [(set_attr "type" "fistp")
4708    (set_attr "i387_cw" "trunc")
4709    (set_attr "mode" "DI")])
4710
4711 (define_split
4712   [(set (match_operand:DI 0 "register_operand" "")
4713         (fix:DI (match_operand 1 "register_operand" "")))
4714    (use (match_operand:HI 2 "memory_operand" ""))
4715    (use (match_operand:HI 3 "memory_operand" ""))
4716    (clobber (match_operand:DI 4 "memory_operand" ""))
4717    (clobber (match_scratch 5 ""))]
4718   "reload_completed"
4719   [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
4720               (use (match_dup 2))
4721               (use (match_dup 3))
4722               (clobber (match_dup 5))])
4723    (set (match_dup 0) (match_dup 4))]
4724   "")
4725
4726 (define_split
4727   [(set (match_operand:DI 0 "memory_operand" "")
4728         (fix:DI (match_operand 1 "register_operand" "")))
4729    (use (match_operand:HI 2 "memory_operand" ""))
4730    (use (match_operand:HI 3 "memory_operand" ""))
4731    (clobber (match_operand:DI 4 "memory_operand" ""))
4732    (clobber (match_scratch 5 ""))]
4733   "reload_completed"
4734   [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
4735               (use (match_dup 2))
4736               (use (match_dup 3))
4737               (clobber (match_dup 5))])]
4738   "")
4739
4740 (define_insn "fix_trunc<mode>_i387"
4741   [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
4742         (fix:X87MODEI12 (match_operand 1 "register_operand" "f")))
4743    (use (match_operand:HI 2 "memory_operand" "m"))
4744    (use (match_operand:HI 3 "memory_operand" "m"))]
4745   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4746    && !TARGET_FISTTP
4747    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4748   "* return output_fix_trunc (insn, operands, 0);"
4749   [(set_attr "type" "fistp")
4750    (set_attr "i387_cw" "trunc")
4751    (set_attr "mode" "<MODE>")])
4752
4753 (define_insn "fix_trunc<mode>_i387_with_temp"
4754   [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
4755         (fix:X87MODEI12 (match_operand 1 "register_operand" "f,f")))
4756    (use (match_operand:HI 2 "memory_operand" "m,m"))
4757    (use (match_operand:HI 3 "memory_operand" "m,m"))
4758    (clobber (match_operand:X87MODEI12 4 "memory_operand" "=X,m"))]
4759   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4760    && !TARGET_FISTTP
4761    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4762   "#"
4763   [(set_attr "type" "fistp")
4764    (set_attr "i387_cw" "trunc")
4765    (set_attr "mode" "<MODE>")])
4766
4767 (define_split
4768   [(set (match_operand:X87MODEI12 0 "register_operand" "")
4769         (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4770    (use (match_operand:HI 2 "memory_operand" ""))
4771    (use (match_operand:HI 3 "memory_operand" ""))
4772    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4773   "reload_completed"
4774   [(parallel [(set (match_dup 4) (fix:X87MODEI12 (match_dup 1)))
4775               (use (match_dup 2))
4776               (use (match_dup 3))])
4777    (set (match_dup 0) (match_dup 4))]
4778   "")
4779
4780 (define_split
4781   [(set (match_operand:X87MODEI12 0 "memory_operand" "")
4782         (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4783    (use (match_operand:HI 2 "memory_operand" ""))
4784    (use (match_operand:HI 3 "memory_operand" ""))
4785    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4786   "reload_completed"
4787   [(parallel [(set (match_dup 0) (fix:X87MODEI12 (match_dup 1)))
4788               (use (match_dup 2))
4789               (use (match_dup 3))])]
4790   "")
4791
4792 (define_insn "x86_fnstcw_1"
4793   [(set (match_operand:HI 0 "memory_operand" "=m")
4794         (unspec:HI [(reg:HI FPCR_REG)] UNSPEC_FSTCW))]
4795   "TARGET_80387"
4796   "fnstcw\t%0"
4797   [(set_attr "length" "2")
4798    (set_attr "mode" "HI")
4799    (set_attr "unit" "i387")])
4800
4801 (define_insn "x86_fldcw_1"
4802   [(set (reg:HI FPCR_REG)
4803         (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
4804   "TARGET_80387"
4805   "fldcw\t%0"
4806   [(set_attr "length" "2")
4807    (set_attr "mode" "HI")
4808    (set_attr "unit" "i387")
4809    (set_attr "athlon_decode" "vector")
4810    (set_attr "amdfam10_decode" "vector")])
4811 \f
4812 ;; Conversion between fixed point and floating point.
4813
4814 ;; Even though we only accept memory inputs, the backend _really_
4815 ;; wants to be able to do this between registers.
4816
4817 (define_expand "floathi<mode>2"
4818   [(set (match_operand:X87MODEF 0 "register_operand" "")
4819         (float:X87MODEF (match_operand:HI 1 "nonimmediate_operand" "")))]
4820   "TARGET_80387
4821    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4822        || TARGET_MIX_SSE_I387)"
4823   "")
4824
4825 ;; Pre-reload splitter to add memory clobber to the pattern.
4826 (define_insn_and_split "*floathi<mode>2_1"
4827   [(set (match_operand:X87MODEF 0 "register_operand" "")
4828         (float:X87MODEF (match_operand:HI 1 "register_operand" "")))]
4829   "TARGET_80387
4830    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4831        || TARGET_MIX_SSE_I387)
4832    && !(reload_completed || reload_in_progress)"
4833   "#"
4834   "&& 1"
4835   [(parallel [(set (match_dup 0)
4836               (float:X87MODEF (match_dup 1)))
4837    (clobber (match_dup 2))])]
4838   "operands[2] = assign_386_stack_local (HImode, SLOT_TEMP);")
4839
4840 (define_insn "*floathi<mode>2_i387_with_temp"
4841   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
4842         (float:X87MODEF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))
4843   (clobber (match_operand:HI 2 "memory_operand" "=m,m"))]
4844   "TARGET_80387
4845    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4846        || TARGET_MIX_SSE_I387)"
4847   "#"
4848   [(set_attr "type" "fmov,multi")
4849    (set_attr "mode" "<MODE>")
4850    (set_attr "unit" "*,i387")
4851    (set_attr "fp_int_src" "true")])
4852
4853 (define_insn "*floathi<mode>2_i387"
4854   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
4855         (float:X87MODEF (match_operand:HI 1 "memory_operand" "m")))]
4856   "TARGET_80387
4857    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4858        || TARGET_MIX_SSE_I387)"
4859   "fild%z1\t%1"
4860   [(set_attr "type" "fmov")
4861    (set_attr "mode" "<MODE>")
4862    (set_attr "fp_int_src" "true")])
4863
4864 (define_split
4865   [(set (match_operand:X87MODEF 0 "register_operand" "")
4866         (float:X87MODEF (match_operand:HI 1 "register_operand" "")))
4867    (clobber (match_operand:HI 2 "memory_operand" ""))]
4868   "TARGET_80387
4869    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4870        || TARGET_MIX_SSE_I387)
4871    && reload_completed"
4872   [(set (match_dup 2) (match_dup 1))
4873    (set (match_dup 0) (float:X87MODEF (match_dup 2)))]
4874   "")
4875
4876 (define_split
4877   [(set (match_operand:X87MODEF 0 "register_operand" "")
4878         (float:X87MODEF (match_operand:HI 1 "memory_operand" "")))
4879    (clobber (match_operand:HI 2 "memory_operand" ""))]
4880    "TARGET_80387
4881     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4882         || TARGET_MIX_SSE_I387)
4883     && reload_completed"
4884   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))]
4885   "")
4886
4887 (define_expand "float<SSEMODEI24:mode><X87MODEF:mode>2"
4888   [(set (match_operand:X87MODEF 0 "register_operand" "")
4889         (float:X87MODEF
4890           (match_operand:SSEMODEI24 1 "nonimmediate_operand" "")))]
4891   "TARGET_80387
4892    || ((<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
4893        && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)"
4894   "")
4895
4896 ;; Pre-reload splitter to add memory clobber to the pattern.
4897 (define_insn_and_split "*float<SSEMODEI24:mode><X87MODEF:mode>2_1"
4898   [(set (match_operand:X87MODEF 0 "register_operand" "")
4899         (float:X87MODEF (match_operand:SSEMODEI24 1 "register_operand" "")))]
4900   "((TARGET_80387
4901      && (!((<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
4902            && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH)
4903          || TARGET_MIX_SSE_I387))
4904     || ((<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
4905         && SSE_FLOAT_MODE_P (<X87MODEF:MODE>mode) && TARGET_SSE_MATH
4906         && ((<SSEMODEI24:MODE>mode == SImode
4907              && TARGET_SSE2 && TARGET_USE_VECTOR_CONVERTS && !optimize_size
4908              && flag_trapping_math)
4909             || !(TARGET_INTER_UNIT_CONVERSIONS || optimize_size))))
4910    && !(reload_completed || reload_in_progress)"
4911   "#"
4912   "&& 1"
4913   [(parallel [(set (match_dup 0) (float:X87MODEF (match_dup 1)))
4914               (clobber (match_dup 2))])]
4915 {
4916   operands[2] = assign_386_stack_local (<SSEMODEI24:MODE>mode, SLOT_TEMP);
4917
4918   /* Avoid store forwarding (partial memory) stall penalty
4919      by passing DImode value through XMM registers.  */
4920   if (<SSEMODEI24:MODE>mode == DImode && !TARGET_64BIT 
4921       && TARGET_80387 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES 
4922       && !optimize_size)
4923     {
4924       emit_insn (gen_floatdi<X87MODEF:mode>2_i387_with_xmm (operands[0],
4925                                                             operands[1],
4926                                                             operands[2]));
4927       DONE;
4928     }
4929 })
4930
4931 (define_insn "*floatsi<mode>2_vector_mixed_with_temp"
4932   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x,x")
4933         (float:MODEF
4934           (match_operand:SI 1 "nonimmediate_operand" "m,?r,r,m,!x")))
4935    (clobber (match_operand:SI 2 "memory_operand" "=X,m,m,X,m"))]
4936   "TARGET_SSE2 && TARGET_MIX_SSE_I387
4937    && TARGET_USE_VECTOR_CONVERTS && !optimize_size"
4938   "#"
4939   [(set_attr "type" "fmov,multi,sseicvt,sseicvt,sseicvt")
4940    (set_attr "mode" "<MODE>,<MODE>,<MODE>,<MODE>,<ssevecmode>")
4941    (set_attr "unit" "*,i387,*,*,*")
4942    (set_attr "athlon_decode" "*,*,double,direct,double")
4943    (set_attr "amdfam10_decode" "*,*,vector,double,double")
4944    (set_attr "fp_int_src" "true")])
4945
4946 (define_insn "*floatsi<mode>2_vector_mixed"
4947   [(set (match_operand:MODEF 0 "register_operand" "=f,x")
4948         (float:MODEF (match_operand:SI 1 "memory_operand" "m,m")))]
4949   "TARGET_SSE2 && TARGET_MIX_SSE_I387
4950    && TARGET_USE_VECTOR_CONVERTS && !optimize_size"
4951   "@
4952    fild%z1\t%1
4953    #"
4954   [(set_attr "type" "fmov,sseicvt")
4955    (set_attr "mode" "<MODE>,<ssevecmode>")
4956    (set_attr "unit" "i387,*")
4957    (set_attr "athlon_decode" "*,direct")
4958    (set_attr "amdfam10_decode" "*,double")
4959    (set_attr "fp_int_src" "true")])
4960
4961 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_mixed_with_temp"
4962   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x,x")
4963         (float:MODEF
4964           (match_operand:SSEMODEI24 1 "nonimmediate_operand" "m,?r,r,m")))
4965   (clobber (match_operand:SSEMODEI24 2 "memory_operand" "=X,m,m,X"))]
4966   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
4967    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387"
4968   "#"
4969   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4970    (set_attr "mode" "<MODEF:MODE>")
4971    (set_attr "unit" "*,i387,*,*")
4972    (set_attr "athlon_decode" "*,*,double,direct")
4973    (set_attr "amdfam10_decode" "*,*,vector,double")
4974    (set_attr "fp_int_src" "true")])
4975
4976 (define_split
4977   [(set (match_operand:MODEF 0 "register_operand" "")
4978         (float:MODEF (match_operand:SSEMODEI24 1 "register_operand" "")))
4979    (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
4980   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
4981    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4982    && TARGET_INTER_UNIT_CONVERSIONS
4983    && reload_completed
4984    && (SSE_REG_P (operands[0])
4985        || (GET_CODE (operands[0]) == SUBREG
4986            && SSE_REG_P (operands[0])))"
4987   [(set (match_dup 0) (float:MODEF (match_dup 1)))]
4988   "")
4989
4990 (define_split
4991   [(set (match_operand:MODEF 0 "register_operand" "")
4992         (float:MODEF (match_operand:SSEMODEI24 1 "register_operand" "")))
4993    (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
4994   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
4995    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
4996    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_size)
4997    && reload_completed
4998    && (SSE_REG_P (operands[0])
4999        || (GET_CODE (operands[0]) == SUBREG
5000            && SSE_REG_P (operands[0])))"
5001   [(set (match_dup 2) (match_dup 1))
5002    (set (match_dup 0) (float:MODEF (match_dup 2)))]
5003   "")
5004
5005 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_mixed_interunit"
5006   [(set (match_operand:MODEF 0 "register_operand" "=f,x,x")
5007         (float:MODEF
5008           (match_operand:SSEMODEI24 1 "nonimmediate_operand" "m,r,m")))]
5009   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5010    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
5011    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_size)"
5012   "@
5013    fild%z1\t%1
5014    cvtsi2s<MODEF:ssemodefsuffix><SSEMODEI24:rex64suffix>\t{%1, %0|%0, %1}
5015    cvtsi2s<MODEF:ssemodefsuffix><SSEMODEI24:rex64suffix>\t{%1, %0|%0, %1}"
5016   [(set_attr "type" "fmov,sseicvt,sseicvt")
5017    (set_attr "mode" "<MODEF:MODE>")
5018    (set_attr "unit" "i387,*,*")
5019    (set_attr "athlon_decode" "*,double,direct")
5020    (set_attr "amdfam10_decode" "*,vector,double")
5021    (set_attr "fp_int_src" "true")])
5022
5023 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_mixed_nointerunit"
5024   [(set (match_operand:MODEF 0 "register_operand" "=f,x")
5025         (float:MODEF
5026           (match_operand:SSEMODEI24 1 "memory_operand" "m,m")))]
5027   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5028    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_MIX_SSE_I387
5029    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_size)"
5030   "@
5031    fild%z1\t%1
5032    cvtsi2s<MODEF:ssemodefsuffix><SSEMODEI24:rex64suffix>\t{%1, %0|%0, %1}"
5033   [(set_attr "type" "fmov,sseicvt")
5034    (set_attr "mode" "<MODEF:MODE>")
5035    (set_attr "athlon_decode" "*,direct")
5036    (set_attr "amdfam10_decode" "*,double")
5037    (set_attr "fp_int_src" "true")])
5038
5039 (define_insn "*floatsi<mode>2_vector_sse_with_temp"
5040   [(set (match_operand:MODEF 0 "register_operand" "=x,x,x")
5041         (float:MODEF
5042           (match_operand:SI 1 "nonimmediate_operand" "r,m,!x")))
5043    (clobber (match_operand:SI 2 "memory_operand" "=m,X,m"))]
5044   "TARGET_SSE2 && TARGET_SSE_MATH
5045    && TARGET_USE_VECTOR_CONVERTS && !optimize_size"
5046   "#"
5047   [(set_attr "type" "sseicvt")
5048    (set_attr "mode" "<MODE>,<MODE>,<ssevecmode>")
5049    (set_attr "athlon_decode" "double,direct,double")
5050    (set_attr "amdfam10_decode" "vector,double,double")
5051    (set_attr "fp_int_src" "true")])
5052
5053 (define_insn "*floatsi<mode>2_vector_sse"
5054   [(set (match_operand:MODEF 0 "register_operand" "=x")
5055         (float:MODEF (match_operand:SI 1 "memory_operand" "m")))]
5056   "TARGET_SSE2 && TARGET_SSE_MATH
5057    && TARGET_USE_VECTOR_CONVERTS && !optimize_size"
5058   "#"
5059   [(set_attr "type" "sseicvt")
5060    (set_attr "mode" "<MODE>")
5061    (set_attr "athlon_decode" "direct")
5062    (set_attr "amdfam10_decode" "double")
5063    (set_attr "fp_int_src" "true")])
5064
5065 (define_split
5066   [(set (match_operand:MODEF 0 "register_operand" "")
5067         (float:MODEF (match_operand:SI 1 "register_operand" "")))
5068    (clobber (match_operand:SI 2 "memory_operand" ""))]
5069   "TARGET_SSE2 && TARGET_SSE_MATH
5070    && TARGET_USE_VECTOR_CONVERTS && !optimize_size
5071    && reload_completed
5072    && (SSE_REG_P (operands[0])
5073        || (GET_CODE (operands[0]) == SUBREG
5074            && SSE_REG_P (operands[0])))"
5075   [(const_int 0)]
5076 {
5077   rtx op1 = operands[1];
5078
5079   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5080                                      <MODE>mode, 0);
5081   if (GET_CODE (op1) == SUBREG)
5082     op1 = SUBREG_REG (op1);
5083
5084   if (GENERAL_REG_P (op1) && TARGET_INTER_UNIT_MOVES)
5085     {
5086       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5087       emit_insn (gen_sse2_loadld (operands[4],
5088                                   CONST0_RTX (V4SImode), operands[1]));
5089     }
5090   /* We can ignore possible trapping value in the
5091      high part of SSE register for non-trapping math. */
5092   else if (SSE_REG_P (op1) && !flag_trapping_math)
5093     operands[4] = simplify_gen_subreg (V4SImode, operands[1], SImode, 0);
5094   else
5095     {
5096       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5097       emit_move_insn (operands[2], operands[1]);
5098       emit_insn (gen_sse2_loadld (operands[4],
5099                                   CONST0_RTX (V4SImode), operands[2]));
5100     }
5101   emit_insn
5102     (gen_sse2_cvtdq2p<ssemodefsuffix> (operands[3], operands[4]));
5103   DONE;
5104 })
5105
5106 (define_split
5107   [(set (match_operand:MODEF 0 "register_operand" "")
5108         (float:MODEF (match_operand:SI 1 "memory_operand" "")))
5109    (clobber (match_operand:SI 2 "memory_operand" ""))]
5110   "TARGET_SSE2 && TARGET_SSE_MATH
5111    && TARGET_USE_VECTOR_CONVERTS && !optimize_size
5112    && reload_completed
5113    && (SSE_REG_P (operands[0])
5114        || (GET_CODE (operands[0]) == SUBREG
5115            && SSE_REG_P (operands[0])))"
5116   [(const_int 0)]
5117 {
5118   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5119                                      <MODE>mode, 0);
5120   operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5121
5122   emit_insn (gen_sse2_loadld (operands[4],
5123                               CONST0_RTX (V4SImode), operands[1]));
5124   emit_insn
5125     (gen_sse2_cvtdq2p<ssemodefsuffix> (operands[3], operands[4]));
5126   DONE;
5127 })
5128
5129 (define_split
5130   [(set (match_operand:MODEF 0 "register_operand" "")
5131         (float:MODEF (match_operand:SI 1 "register_operand" "")))]
5132   "TARGET_SSE2 && TARGET_SSE_MATH
5133    && TARGET_USE_VECTOR_CONVERTS && !optimize_size
5134    && reload_completed
5135    && (SSE_REG_P (operands[0])
5136        || (GET_CODE (operands[0]) == SUBREG
5137            && SSE_REG_P (operands[0])))"
5138   [(const_int 0)]
5139 {
5140   rtx op1 = operands[1];
5141
5142   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5143                                      <MODE>mode, 0);
5144   if (GET_CODE (op1) == SUBREG)
5145     op1 = SUBREG_REG (op1);
5146
5147   if (GENERAL_REG_P (op1) && TARGET_INTER_UNIT_MOVES)
5148     {
5149       operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5150       emit_insn (gen_sse2_loadld (operands[4],
5151                                   CONST0_RTX (V4SImode), operands[1]));
5152     }
5153   /* We can ignore possible trapping value in the
5154      high part of SSE register for non-trapping math. */
5155   else if (SSE_REG_P (op1) && !flag_trapping_math)
5156     operands[4] = simplify_gen_subreg (V4SImode, operands[1], SImode, 0);
5157   else
5158     gcc_unreachable ();
5159 })
5160
5161 (define_split
5162   [(set (match_operand:MODEF 0 "register_operand" "")
5163         (float:MODEF (match_operand:SI 1 "memory_operand" "")))]
5164   "TARGET_SSE2 && TARGET_SSE_MATH
5165    && TARGET_USE_VECTOR_CONVERTS && !optimize_size
5166    && reload_completed
5167    && (SSE_REG_P (operands[0])
5168        || (GET_CODE (operands[0]) == SUBREG
5169            && SSE_REG_P (operands[0])))"
5170   [(const_int 0)]
5171 {
5172   operands[3] = simplify_gen_subreg (<ssevecmode>mode, operands[0],
5173                                      <MODE>mode, 0);
5174   operands[4] = simplify_gen_subreg (V4SImode, operands[0], <MODE>mode, 0);
5175
5176   emit_insn (gen_sse2_loadld (operands[4],
5177                               CONST0_RTX (V4SImode), operands[1]));
5178   emit_insn
5179     (gen_sse2_cvtdq2p<ssemodefsuffix> (operands[3], operands[4]));
5180   DONE;
5181 })
5182
5183 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_sse_with_temp"
5184   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
5185         (float:MODEF
5186           (match_operand:SSEMODEI24 1 "nonimmediate_operand" "r,m")))
5187   (clobber (match_operand:SSEMODEI24 2 "memory_operand" "=m,X"))]
5188   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5189    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH"
5190   "#"
5191   [(set_attr "type" "sseicvt")
5192    (set_attr "mode" "<MODEF:MODE>")
5193    (set_attr "athlon_decode" "double,direct")
5194    (set_attr "amdfam10_decode" "vector,double")
5195    (set_attr "fp_int_src" "true")])
5196
5197 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_sse_interunit"
5198   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
5199         (float:MODEF
5200           (match_operand:SSEMODEI24 1 "nonimmediate_operand" "r,m")))]
5201   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5202    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5203    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_size)"
5204   "cvtsi2s<MODEF:ssemodefsuffix><SSEMODEI24:rex64suffix>\t{%1, %0|%0, %1}"
5205   [(set_attr "type" "sseicvt")
5206    (set_attr "mode" "<MODEF:MODE>")
5207    (set_attr "athlon_decode" "double,direct")
5208    (set_attr "amdfam10_decode" "vector,double")
5209    (set_attr "fp_int_src" "true")])
5210
5211 (define_split
5212   [(set (match_operand:MODEF 0 "register_operand" "")
5213         (float:MODEF (match_operand:SSEMODEI24 1 "nonimmediate_operand" "")))
5214    (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5215   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5216    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5217    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_size)
5218    && reload_completed
5219    && (SSE_REG_P (operands[0])
5220        || (GET_CODE (operands[0]) == SUBREG
5221            && SSE_REG_P (operands[0])))"
5222   [(set (match_dup 0) (float:MODEF (match_dup 1)))]
5223   "")
5224
5225 (define_insn "*float<SSEMODEI24:mode><MODEF:mode>2_sse_nointerunit"
5226   [(set (match_operand:MODEF 0 "register_operand" "=x")
5227         (float:MODEF
5228           (match_operand:SSEMODEI24 1 "memory_operand" "m")))]
5229   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5230    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5231    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_size)"
5232   "cvtsi2s<MODEF:ssemodefsuffix><SSEMODEI24:rex64suffix>\t{%1, %0|%0, %1}"
5233   [(set_attr "type" "sseicvt")
5234    (set_attr "mode" "<MODEF:MODE>")
5235    (set_attr "athlon_decode" "direct")
5236    (set_attr "amdfam10_decode" "double")
5237    (set_attr "fp_int_src" "true")])
5238
5239 (define_split
5240   [(set (match_operand:MODEF 0 "register_operand" "")
5241         (float:MODEF (match_operand:SSEMODEI24 1 "register_operand" "")))
5242    (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5243   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5244    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5245    && !(TARGET_INTER_UNIT_CONVERSIONS || optimize_size)
5246    && reload_completed
5247    && (SSE_REG_P (operands[0])
5248        || (GET_CODE (operands[0]) == SUBREG
5249            && SSE_REG_P (operands[0])))"
5250   [(set (match_dup 2) (match_dup 1))
5251    (set (match_dup 0) (float:MODEF (match_dup 2)))]
5252   "")
5253
5254 (define_split
5255   [(set (match_operand:MODEF 0 "register_operand" "")
5256         (float:MODEF (match_operand:SSEMODEI24 1 "memory_operand" "")))
5257    (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5258   "(<SSEMODEI24:MODE>mode != DImode || TARGET_64BIT)
5259    && SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
5260    && reload_completed
5261    && (SSE_REG_P (operands[0])
5262        || (GET_CODE (operands[0]) == SUBREG
5263            && SSE_REG_P (operands[0])))"
5264   [(set (match_dup 0) (float:MODEF (match_dup 1)))]
5265   "")
5266
5267 (define_insn "*float<SSEMODEI24:mode><X87MODEF:mode>2_i387_with_temp"
5268   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5269         (float:X87MODEF
5270           (match_operand:SSEMODEI24 1 "nonimmediate_operand" "m,?r")))
5271   (clobber (match_operand:SSEMODEI24 2 "memory_operand" "=X,m"))]
5272   "TARGET_80387"
5273   "@
5274    fild%z1\t%1
5275    #"
5276   [(set_attr "type" "fmov,multi")
5277    (set_attr "mode" "<X87MODEF:MODE>")
5278    (set_attr "unit" "*,i387")
5279    (set_attr "fp_int_src" "true")])
5280
5281 (define_insn "*float<SSEMODEI24:mode><X87MODEF:mode>2_i387"
5282   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
5283         (float:X87MODEF
5284           (match_operand:SSEMODEI24 1 "memory_operand" "m")))]
5285   "TARGET_80387"
5286   "fild%z1\t%1"
5287   [(set_attr "type" "fmov")
5288    (set_attr "mode" "<X87MODEF:MODE>")
5289    (set_attr "fp_int_src" "true")])
5290
5291 (define_split
5292   [(set (match_operand:X87MODEF 0 "register_operand" "")
5293         (float:X87MODEF (match_operand:SSEMODEI24 1 "register_operand" "")))
5294    (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5295   "TARGET_80387
5296    && reload_completed
5297    && FP_REG_P (operands[0])"
5298   [(set (match_dup 2) (match_dup 1))
5299    (set (match_dup 0) (float:X87MODEF (match_dup 2)))]
5300   "")
5301
5302 (define_split
5303   [(set (match_operand:X87MODEF 0 "register_operand" "")
5304         (float:X87MODEF (match_operand:SSEMODEI24 1 "memory_operand" "")))
5305    (clobber (match_operand:SSEMODEI24 2 "memory_operand" ""))]
5306   "TARGET_80387
5307    && reload_completed
5308    && FP_REG_P (operands[0])"
5309   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))]
5310   "")
5311
5312 ;; Avoid store forwarding (partial memory) stall penalty
5313 ;; by passing DImode value through XMM registers.  */
5314
5315 (define_insn "floatdi<X87MODEF:mode>2_i387_with_xmm"
5316   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5317         (float:X87MODEF
5318           (match_operand:DI 1 "nonimmediate_operand" "m,?r")))
5319    (clobber (match_scratch:V4SI 3 "=X,x"))
5320    (clobber (match_scratch:V4SI 4 "=X,x"))
5321    (clobber (match_operand:DI 2 "memory_operand" "=X,m"))]
5322   "TARGET_80387 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5323    && !TARGET_64BIT && !optimize_size"
5324   "#"
5325   [(set_attr "type" "multi")
5326    (set_attr "mode" "<X87MODEF:MODE>")
5327    (set_attr "unit" "i387")
5328    (set_attr "fp_int_src" "true")])
5329
5330 (define_split
5331   [(set (match_operand:X87MODEF 0 "register_operand" "")
5332         (float:X87MODEF (match_operand:DI 1 "register_operand" "")))
5333    (clobber (match_scratch:V4SI 3 ""))
5334    (clobber (match_scratch:V4SI 4 ""))
5335    (clobber (match_operand:DI 2 "memory_operand" ""))]
5336   "TARGET_80387 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5337    && !TARGET_64BIT && !optimize_size
5338    && reload_completed
5339    && FP_REG_P (operands[0])"
5340   [(set (match_dup 2) (match_dup 3))
5341    (set (match_dup 0) (float:X87MODEF (match_dup 2)))]
5342 {
5343   /* The DImode arrived in a pair of integral registers (e.g. %edx:%eax).
5344      Assemble the 64-bit DImode value in an xmm register.  */
5345   emit_insn (gen_sse2_loadld (operands[3], CONST0_RTX (V4SImode),
5346                               gen_rtx_SUBREG (SImode, operands[1], 0)));
5347   emit_insn (gen_sse2_loadld (operands[4], CONST0_RTX (V4SImode),
5348                               gen_rtx_SUBREG (SImode, operands[1], 4)));
5349   emit_insn (gen_sse2_punpckldq (operands[3], operands[3], operands[4]));
5350
5351   operands[3] = gen_rtx_REG (DImode, REGNO (operands[3]));
5352 })
5353
5354 (define_split
5355   [(set (match_operand:X87MODEF 0 "register_operand" "")
5356         (float:X87MODEF (match_operand:DI 1 "memory_operand" "")))
5357    (clobber (match_scratch:V4SI 3 ""))
5358    (clobber (match_scratch:V4SI 4 ""))
5359    (clobber (match_operand:DI 2 "memory_operand" ""))]
5360   "TARGET_80387 && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES
5361    && !TARGET_64BIT && !optimize_size
5362    && reload_completed
5363    && FP_REG_P (operands[0])"
5364   [(set (match_dup 0) (float:X87MODEF (match_dup 1)))]
5365   "")
5366
5367 ;; Avoid store forwarding (partial memory) stall penalty by extending
5368 ;; SImode value to DImode through XMM register instead of pushing two
5369 ;; SImode values to stack. Note that even !TARGET_INTER_UNIT_MOVES
5370 ;; targets benefit from this optimization. Also note that fild
5371 ;; loads from memory only.
5372
5373 (define_insn "*floatunssi<mode>2_1"
5374   [(set (match_operand:X87MODEF 0 "register_operand" "=f,f")
5375         (unsigned_float:X87MODEF
5376           (match_operand:SI 1 "nonimmediate_operand" "x,m")))
5377    (clobber (match_operand:DI 2 "memory_operand" "=m,m"))
5378    (clobber (match_scratch:SI 3 "=X,x"))]
5379   "!TARGET_64BIT
5380    && TARGET_80387 && TARGET_SSE"
5381   "#"
5382   [(set_attr "type" "multi")
5383    (set_attr "mode" "<MODE>")])
5384
5385 (define_split
5386   [(set (match_operand:X87MODEF 0 "register_operand" "")
5387         (unsigned_float:X87MODEF
5388           (match_operand:SI 1 "register_operand" "")))
5389    (clobber (match_operand:DI 2 "memory_operand" ""))
5390    (clobber (match_scratch:SI 3 ""))]
5391   "!TARGET_64BIT
5392    && TARGET_80387 && TARGET_SSE
5393    && reload_completed"
5394   [(set (match_dup 2) (match_dup 1))
5395    (set (match_dup 0)
5396         (float:X87MODEF (match_dup 2)))]
5397   "operands[1] = simplify_gen_subreg (DImode, operands[1], SImode, 0);")
5398
5399 (define_split
5400   [(set (match_operand:X87MODEF 0 "register_operand" "")
5401         (unsigned_float:X87MODEF
5402           (match_operand:SI 1 "memory_operand" "")))
5403    (clobber (match_operand:DI 2 "memory_operand" ""))
5404    (clobber (match_scratch:SI 3 ""))]
5405   "!TARGET_64BIT
5406    && TARGET_80387 && TARGET_SSE
5407    && reload_completed"
5408   [(set (match_dup 2) (match_dup 3))
5409    (set (match_dup 0)
5410         (float:X87MODEF (match_dup 2)))]
5411 {
5412   emit_move_insn (operands[3], operands[1]);
5413   operands[3] = simplify_gen_subreg (DImode, operands[3], SImode, 0);
5414 })
5415
5416 (define_expand "floatunssi<mode>2"
5417   [(parallel
5418      [(set (match_operand:X87MODEF 0 "register_operand" "")
5419            (unsigned_float:X87MODEF
5420              (match_operand:SI 1 "nonimmediate_operand" "")))
5421       (clobber (match_dup 2))
5422       (clobber (match_scratch:SI 3 ""))])]
5423   "!TARGET_64BIT
5424    && ((TARGET_80387 && TARGET_SSE)
5425        || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
5426 {
5427   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
5428     {
5429       ix86_expand_convert_uns_si<mode>_sse (operands[0], operands[1]);
5430       DONE;
5431     }
5432   else
5433     {
5434       int slot = virtuals_instantiated ? SLOT_TEMP : SLOT_VIRTUAL;
5435       operands[2] = assign_386_stack_local (DImode, slot);
5436     }
5437 })
5438
5439 (define_expand "floatunsdisf2"
5440   [(use (match_operand:SF 0 "register_operand" ""))
5441    (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5442   "TARGET_64BIT && TARGET_SSE_MATH"
5443   "x86_emit_floatuns (operands); DONE;")
5444
5445 (define_expand "floatunsdidf2"
5446   [(use (match_operand:DF 0 "register_operand" ""))
5447    (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5448   "(TARGET_64BIT || TARGET_KEEPS_VECTOR_ALIGNED_STACK)
5449    && TARGET_SSE2 && TARGET_SSE_MATH"
5450 {
5451   if (TARGET_64BIT)
5452     x86_emit_floatuns (operands);
5453   else
5454     ix86_expand_convert_uns_didf_sse (operands[0], operands[1]);
5455   DONE;
5456 })
5457 \f
5458 ;; Add instructions
5459
5460 ;; %%% splits for addditi3
5461
5462 (define_expand "addti3"
5463   [(set (match_operand:TI 0 "nonimmediate_operand" "")
5464         (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
5465                  (match_operand:TI 2 "x86_64_general_operand" "")))
5466    (clobber (reg:CC FLAGS_REG))]
5467   "TARGET_64BIT"
5468   "ix86_expand_binary_operator (PLUS, TImode, operands); DONE;")
5469
5470 (define_insn "*addti3_1"
5471   [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o")
5472         (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0,0")
5473                  (match_operand:TI 2 "x86_64_general_operand" "roe,re")))
5474    (clobber (reg:CC FLAGS_REG))]
5475   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, TImode, operands)"
5476   "#")
5477
5478 (define_split
5479   [(set (match_operand:TI 0 "nonimmediate_operand" "")
5480         (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
5481                  (match_operand:TI 2 "x86_64_general_operand" "")))
5482    (clobber (reg:CC FLAGS_REG))]
5483   "TARGET_64BIT && reload_completed"
5484   [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
5485                                           UNSPEC_ADD_CARRY))
5486               (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))])
5487    (parallel [(set (match_dup 3)
5488                    (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
5489                                      (match_dup 4))
5490                             (match_dup 5)))
5491               (clobber (reg:CC FLAGS_REG))])]
5492   "split_ti (&operands[0], 3, &operands[0], &operands[3]);")
5493
5494 ;; %%% splits for addsidi3
5495 ;  [(set (match_operand:DI 0 "nonimmediate_operand" "")
5496 ;       (plus:DI (match_operand:DI 1 "general_operand" "")
5497 ;                (zero_extend:DI (match_operand:SI 2 "general_operand" ""))))]
5498
5499 (define_expand "adddi3"
5500   [(set (match_operand:DI 0 "nonimmediate_operand" "")
5501         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5502                  (match_operand:DI 2 "x86_64_general_operand" "")))
5503    (clobber (reg:CC FLAGS_REG))]
5504   ""
5505   "ix86_expand_binary_operator (PLUS, DImode, operands); DONE;")
5506
5507 (define_insn "*adddi3_1"
5508   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
5509         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5510                  (match_operand:DI 2 "general_operand" "roiF,riF")))
5511    (clobber (reg:CC FLAGS_REG))]
5512   "!TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5513   "#")
5514
5515 (define_split
5516   [(set (match_operand:DI 0 "nonimmediate_operand" "")
5517         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5518                  (match_operand:DI 2 "general_operand" "")))
5519    (clobber (reg:CC FLAGS_REG))]
5520   "!TARGET_64BIT && reload_completed"
5521   [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
5522                                           UNSPEC_ADD_CARRY))
5523               (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))])
5524    (parallel [(set (match_dup 3)
5525                    (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
5526                                      (match_dup 4))
5527                             (match_dup 5)))
5528               (clobber (reg:CC FLAGS_REG))])]
5529   "split_di (&operands[0], 3, &operands[0], &operands[3]);")
5530
5531 (define_insn "adddi3_carry_rex64"
5532   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
5533           (plus:DI (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
5534                             (match_operand:DI 1 "nonimmediate_operand" "%0,0"))
5535                    (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
5536    (clobber (reg:CC FLAGS_REG))]
5537   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5538   "adc{q}\t{%2, %0|%0, %2}"
5539   [(set_attr "type" "alu")
5540    (set_attr "pent_pair" "pu")
5541    (set_attr "mode" "DI")])
5542
5543 (define_insn "*adddi3_cc_rex64"
5544   [(set (reg:CC FLAGS_REG)
5545         (unspec:CC [(match_operand:DI 1 "nonimmediate_operand" "%0,0")
5546                     (match_operand:DI 2 "x86_64_general_operand" "re,rm")]
5547                    UNSPEC_ADD_CARRY))
5548    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
5549         (plus:DI (match_dup 1) (match_dup 2)))]
5550   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5551   "add{q}\t{%2, %0|%0, %2}"
5552   [(set_attr "type" "alu")
5553    (set_attr "mode" "DI")])
5554
5555 (define_insn "*<plusminus_insn><mode>3_cc_overflow"
5556   [(set (reg:CCC FLAGS_REG)
5557         (compare:CCC
5558             (plusminus:SWI
5559                 (match_operand:SWI 1 "nonimmediate_operand" "<comm>0,0")
5560                 (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))
5561             (match_dup 1)))
5562    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
5563         (plusminus:SWI (match_dup 1) (match_dup 2)))]
5564   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5565   "<plusminus_mnemonic>{<imodesuffix>}\t{%2, %0|%0, %2}"
5566   [(set_attr "type" "alu")
5567    (set_attr "mode" "<MODE>")])
5568
5569 (define_insn "*add<mode>3_cconly_overflow"
5570   [(set (reg:CCC FLAGS_REG)
5571         (compare:CCC
5572                 (plus:SWI (match_operand:SWI 1 "nonimmediate_operand" "%0")
5573                           (match_operand:SWI 2 "<general_operand>" "<r><i>m"))
5574                 (match_dup 1)))
5575    (clobber (match_scratch:SWI 0 "=<r>"))]
5576   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5577   "add{<imodesuffix>}\t{%2, %0|%0, %2}"
5578   [(set_attr "type" "alu")
5579    (set_attr "mode" "<MODE>")])
5580
5581 (define_insn "*sub<mode>3_cconly_overflow"
5582   [(set (reg:CCC FLAGS_REG)
5583         (compare:CCC
5584              (minus:SWI (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
5585                         (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m"))
5586              (match_dup 0)))]
5587   ""
5588   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
5589   [(set_attr "type" "icmp")
5590    (set_attr "mode" "<MODE>")])
5591
5592 (define_insn "*<plusminus_insn>si3_zext_cc_overflow"
5593   [(set (reg:CCC FLAGS_REG)
5594         (compare:CCC
5595             (plusminus:SI (match_operand:SI 1 "nonimmediate_operand" "<comm>0")
5596                           (match_operand:SI 2 "general_operand" "g"))
5597             (match_dup 1)))
5598    (set (match_operand:DI 0 "register_operand" "=r")
5599         (zero_extend:DI (plusminus:SI (match_dup 1) (match_dup 2))))]
5600   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
5601   "<plusminus_mnemonic>{l}\t{%2, %k0|%k0, %2}"
5602   [(set_attr "type" "alu")
5603    (set_attr "mode" "SI")])
5604
5605 (define_insn "addqi3_carry"
5606   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
5607           (plus:QI (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
5608                             (match_operand:QI 1 "nonimmediate_operand" "%0,0"))
5609                    (match_operand:QI 2 "general_operand" "qi,qm")))
5610    (clobber (reg:CC FLAGS_REG))]
5611   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5612   "adc{b}\t{%2, %0|%0, %2}"
5613   [(set_attr "type" "alu")
5614    (set_attr "pent_pair" "pu")
5615    (set_attr "mode" "QI")])
5616
5617 (define_insn "addhi3_carry"
5618   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
5619           (plus:HI (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
5620                             (match_operand:HI 1 "nonimmediate_operand" "%0,0"))
5621                    (match_operand:HI 2 "general_operand" "ri,rm")))
5622    (clobber (reg:CC FLAGS_REG))]
5623   "ix86_binary_operator_ok (PLUS, HImode, operands)"
5624   "adc{w}\t{%2, %0|%0, %2}"
5625   [(set_attr "type" "alu")
5626    (set_attr "pent_pair" "pu")
5627    (set_attr "mode" "HI")])
5628
5629 (define_insn "addsi3_carry"
5630   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
5631           (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
5632                             (match_operand:SI 1 "nonimmediate_operand" "%0,0"))
5633                    (match_operand:SI 2 "general_operand" "ri,rm")))
5634    (clobber (reg:CC FLAGS_REG))]
5635   "ix86_binary_operator_ok (PLUS, SImode, operands)"
5636   "adc{l}\t{%2, %0|%0, %2}"
5637   [(set_attr "type" "alu")
5638    (set_attr "pent_pair" "pu")
5639    (set_attr "mode" "SI")])
5640
5641 (define_insn "*addsi3_carry_zext"
5642   [(set (match_operand:DI 0 "register_operand" "=r")
5643           (zero_extend:DI
5644             (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
5645                               (match_operand:SI 1 "nonimmediate_operand" "%0"))
5646                      (match_operand:SI 2 "general_operand" "g"))))
5647    (clobber (reg:CC FLAGS_REG))]
5648   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5649   "adc{l}\t{%2, %k0|%k0, %2}"
5650   [(set_attr "type" "alu")
5651    (set_attr "pent_pair" "pu")
5652    (set_attr "mode" "SI")])
5653
5654 (define_insn "*addsi3_cc"
5655   [(set (reg:CC FLAGS_REG)
5656         (unspec:CC [(match_operand:SI 1 "nonimmediate_operand" "%0,0")
5657                     (match_operand:SI 2 "general_operand" "ri,rm")]
5658                    UNSPEC_ADD_CARRY))
5659    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
5660         (plus:SI (match_dup 1) (match_dup 2)))]
5661   "ix86_binary_operator_ok (PLUS, SImode, operands)"
5662   "add{l}\t{%2, %0|%0, %2}"
5663   [(set_attr "type" "alu")
5664    (set_attr "mode" "SI")])
5665
5666 (define_insn "addqi3_cc"
5667   [(set (reg:CC FLAGS_REG)
5668         (unspec:CC [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
5669                     (match_operand:QI 2 "general_operand" "qi,qm")]
5670                    UNSPEC_ADD_CARRY))
5671    (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
5672         (plus:QI (match_dup 1) (match_dup 2)))]
5673   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5674   "add{b}\t{%2, %0|%0, %2}"
5675   [(set_attr "type" "alu")
5676    (set_attr "mode" "QI")])
5677
5678 (define_expand "addsi3"
5679   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
5680                    (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
5681                             (match_operand:SI 2 "general_operand" "")))
5682               (clobber (reg:CC FLAGS_REG))])]
5683   ""
5684   "ix86_expand_binary_operator (PLUS, SImode, operands); DONE;")
5685
5686 (define_insn "*lea_1"
5687   [(set (match_operand:SI 0 "register_operand" "=r")
5688         (match_operand:SI 1 "no_seg_address_operand" "p"))]
5689   "!TARGET_64BIT"
5690   "lea{l}\t{%a1, %0|%0, %a1}"
5691   [(set_attr "type" "lea")
5692    (set_attr "mode" "SI")])
5693
5694 (define_insn "*lea_1_rex64"
5695   [(set (match_operand:SI 0 "register_operand" "=r")
5696         (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0))]
5697   "TARGET_64BIT"
5698   "lea{l}\t{%a1, %0|%0, %a1}"
5699   [(set_attr "type" "lea")
5700    (set_attr "mode" "SI")])
5701
5702 (define_insn "*lea_1_zext"
5703   [(set (match_operand:DI 0 "register_operand" "=r")
5704         (zero_extend:DI
5705          (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0)))]
5706   "TARGET_64BIT"
5707   "lea{l}\t{%a1, %k0|%k0, %a1}"
5708   [(set_attr "type" "lea")
5709    (set_attr "mode" "SI")])
5710
5711 (define_insn "*lea_2_rex64"
5712   [(set (match_operand:DI 0 "register_operand" "=r")
5713         (match_operand:DI 1 "no_seg_address_operand" "p"))]
5714   "TARGET_64BIT"
5715   "lea{q}\t{%a1, %0|%0, %a1}"
5716   [(set_attr "type" "lea")
5717    (set_attr "mode" "DI")])
5718
5719 ;; The lea patterns for non-Pmodes needs to be matched by several
5720 ;; insns converted to real lea by splitters.
5721
5722 (define_insn_and_split "*lea_general_1"
5723   [(set (match_operand 0 "register_operand" "=r")
5724         (plus (plus (match_operand 1 "index_register_operand" "l")
5725                     (match_operand 2 "register_operand" "r"))
5726               (match_operand 3 "immediate_operand" "i")))]
5727   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5728     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5729    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5730    && GET_MODE (operands[0]) == GET_MODE (operands[1])
5731    && GET_MODE (operands[0]) == GET_MODE (operands[2])
5732    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
5733        || GET_MODE (operands[3]) == VOIDmode)"
5734   "#"
5735   "&& reload_completed"
5736   [(const_int 0)]
5737 {
5738   rtx pat;
5739   operands[0] = gen_lowpart (SImode, operands[0]);
5740   operands[1] = gen_lowpart (Pmode, operands[1]);
5741   operands[2] = gen_lowpart (Pmode, operands[2]);
5742   operands[3] = gen_lowpart (Pmode, operands[3]);
5743   pat = gen_rtx_PLUS (Pmode, gen_rtx_PLUS (Pmode, operands[1], operands[2]),
5744                       operands[3]);
5745   if (Pmode != SImode)
5746     pat = gen_rtx_SUBREG (SImode, pat, 0);
5747   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5748   DONE;
5749 }
5750   [(set_attr "type" "lea")
5751    (set_attr "mode" "SI")])
5752
5753 (define_insn_and_split "*lea_general_1_zext"
5754   [(set (match_operand:DI 0 "register_operand" "=r")
5755         (zero_extend:DI
5756           (plus:SI (plus:SI (match_operand:SI 1 "index_register_operand" "l")
5757                             (match_operand:SI 2 "register_operand" "r"))
5758                    (match_operand:SI 3 "immediate_operand" "i"))))]
5759   "TARGET_64BIT"
5760   "#"
5761   "&& reload_completed"
5762   [(set (match_dup 0)
5763         (zero_extend:DI (subreg:SI (plus:DI (plus:DI (match_dup 1)
5764                                                      (match_dup 2))
5765                                             (match_dup 3)) 0)))]
5766 {
5767   operands[1] = gen_lowpart (Pmode, operands[1]);
5768   operands[2] = gen_lowpart (Pmode, operands[2]);
5769   operands[3] = gen_lowpart (Pmode, operands[3]);
5770 }
5771   [(set_attr "type" "lea")
5772    (set_attr "mode" "SI")])
5773
5774 (define_insn_and_split "*lea_general_2"
5775   [(set (match_operand 0 "register_operand" "=r")
5776         (plus (mult (match_operand 1 "index_register_operand" "l")
5777                     (match_operand 2 "const248_operand" "i"))
5778               (match_operand 3 "nonmemory_operand" "ri")))]
5779   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5780     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5781    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5782    && GET_MODE (operands[0]) == GET_MODE (operands[1])
5783    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
5784        || GET_MODE (operands[3]) == VOIDmode)"
5785   "#"
5786   "&& reload_completed"
5787   [(const_int 0)]
5788 {
5789   rtx pat;
5790   operands[0] = gen_lowpart (SImode, operands[0]);
5791   operands[1] = gen_lowpart (Pmode, operands[1]);
5792   operands[3] = gen_lowpart (Pmode, operands[3]);
5793   pat = gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], operands[2]),
5794                       operands[3]);
5795   if (Pmode != SImode)
5796     pat = gen_rtx_SUBREG (SImode, pat, 0);
5797   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5798   DONE;
5799 }
5800   [(set_attr "type" "lea")
5801    (set_attr "mode" "SI")])
5802
5803 (define_insn_and_split "*lea_general_2_zext"
5804   [(set (match_operand:DI 0 "register_operand" "=r")
5805         (zero_extend:DI
5806           (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "l")
5807                             (match_operand:SI 2 "const248_operand" "n"))
5808                    (match_operand:SI 3 "nonmemory_operand" "ri"))))]
5809   "TARGET_64BIT"
5810   "#"
5811   "&& reload_completed"
5812   [(set (match_dup 0)
5813         (zero_extend:DI (subreg:SI (plus:DI (mult:DI (match_dup 1)
5814                                                      (match_dup 2))
5815                                             (match_dup 3)) 0)))]
5816 {
5817   operands[1] = gen_lowpart (Pmode, operands[1]);
5818   operands[3] = gen_lowpart (Pmode, operands[3]);
5819 }
5820   [(set_attr "type" "lea")
5821    (set_attr "mode" "SI")])
5822
5823 (define_insn_and_split "*lea_general_3"
5824   [(set (match_operand 0 "register_operand" "=r")
5825         (plus (plus (mult (match_operand 1 "index_register_operand" "l")
5826                           (match_operand 2 "const248_operand" "i"))
5827                     (match_operand 3 "register_operand" "r"))
5828               (match_operand 4 "immediate_operand" "i")))]
5829   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5830     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5831    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5832    && GET_MODE (operands[0]) == GET_MODE (operands[1])
5833    && GET_MODE (operands[0]) == GET_MODE (operands[3])"
5834   "#"
5835   "&& reload_completed"
5836   [(const_int 0)]
5837 {
5838   rtx pat;
5839   operands[0] = gen_lowpart (SImode, operands[0]);
5840   operands[1] = gen_lowpart (Pmode, operands[1]);
5841   operands[3] = gen_lowpart (Pmode, operands[3]);
5842   operands[4] = gen_lowpart (Pmode, operands[4]);
5843   pat = gen_rtx_PLUS (Pmode,
5844                       gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1],
5845                                                          operands[2]),
5846                                     operands[3]),
5847                       operands[4]);
5848   if (Pmode != SImode)
5849     pat = gen_rtx_SUBREG (SImode, pat, 0);
5850   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5851   DONE;
5852 }
5853   [(set_attr "type" "lea")
5854    (set_attr "mode" "SI")])
5855
5856 (define_insn_and_split "*lea_general_3_zext"
5857   [(set (match_operand:DI 0 "register_operand" "=r")
5858         (zero_extend:DI
5859           (plus:SI (plus:SI (mult:SI
5860                               (match_operand:SI 1 "index_register_operand" "l")
5861                               (match_operand:SI 2 "const248_operand" "n"))
5862                             (match_operand:SI 3 "register_operand" "r"))
5863                    (match_operand:SI 4 "immediate_operand" "i"))))]
5864   "TARGET_64BIT"
5865   "#"
5866   "&& reload_completed"
5867   [(set (match_dup 0)
5868         (zero_extend:DI (subreg:SI (plus:DI (plus:DI (mult:DI (match_dup 1)
5869                                                               (match_dup 2))
5870                                                      (match_dup 3))
5871                                             (match_dup 4)) 0)))]
5872 {
5873   operands[1] = gen_lowpart (Pmode, operands[1]);
5874   operands[3] = gen_lowpart (Pmode, operands[3]);
5875   operands[4] = gen_lowpart (Pmode, operands[4]);
5876 }
5877   [(set_attr "type" "lea")
5878    (set_attr "mode" "SI")])
5879
5880 (define_insn "*adddi_1_rex64"
5881   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r")
5882         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,r")
5883                  (match_operand:DI 2 "x86_64_general_operand" "rme,re,le")))
5884    (clobber (reg:CC FLAGS_REG))]
5885   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5886 {
5887   switch (get_attr_type (insn))
5888     {
5889     case TYPE_LEA:
5890       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5891       return "lea{q}\t{%a2, %0|%0, %a2}";
5892
5893     case TYPE_INCDEC:
5894       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5895       if (operands[2] == const1_rtx)
5896         return "inc{q}\t%0";
5897       else
5898         {
5899           gcc_assert (operands[2] == constm1_rtx);
5900           return "dec{q}\t%0";
5901         }
5902
5903     default:
5904       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5905
5906       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5907          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5908       if (CONST_INT_P (operands[2])
5909           /* Avoid overflows.  */
5910           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5911           && (INTVAL (operands[2]) == 128
5912               || (INTVAL (operands[2]) < 0
5913                   && INTVAL (operands[2]) != -128)))
5914         {
5915           operands[2] = GEN_INT (-INTVAL (operands[2]));
5916           return "sub{q}\t{%2, %0|%0, %2}";
5917         }
5918       return "add{q}\t{%2, %0|%0, %2}";
5919     }
5920 }
5921   [(set (attr "type")
5922      (cond [(eq_attr "alternative" "2")
5923               (const_string "lea")
5924             ; Current assemblers are broken and do not allow @GOTOFF in
5925             ; ought but a memory context.
5926             (match_operand:DI 2 "pic_symbolic_operand" "")
5927               (const_string "lea")
5928             (match_operand:DI 2 "incdec_operand" "")
5929               (const_string "incdec")
5930            ]
5931            (const_string "alu")))
5932    (set_attr "mode" "DI")])
5933
5934 ;; Convert lea to the lea pattern to avoid flags dependency.
5935 (define_split
5936   [(set (match_operand:DI 0 "register_operand" "")
5937         (plus:DI (match_operand:DI 1 "register_operand" "")
5938                  (match_operand:DI 2 "x86_64_nonmemory_operand" "")))
5939    (clobber (reg:CC FLAGS_REG))]
5940   "TARGET_64BIT && reload_completed
5941    && true_regnum (operands[0]) != true_regnum (operands[1])"
5942   [(set (match_dup 0)
5943         (plus:DI (match_dup 1)
5944                  (match_dup 2)))]
5945   "")
5946
5947 (define_insn "*adddi_2_rex64"
5948   [(set (reg FLAGS_REG)
5949         (compare
5950           (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5951                    (match_operand:DI 2 "x86_64_general_operand" "rme,re"))
5952           (const_int 0)))
5953    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
5954         (plus:DI (match_dup 1) (match_dup 2)))]
5955   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5956    && ix86_binary_operator_ok (PLUS, DImode, operands)
5957    /* Current assemblers are broken and do not allow @GOTOFF in
5958       ought but a memory context.  */
5959    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5960 {
5961   switch (get_attr_type (insn))
5962     {
5963     case TYPE_INCDEC:
5964       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5965       if (operands[2] == const1_rtx)
5966         return "inc{q}\t%0";
5967       else
5968         {
5969           gcc_assert (operands[2] == constm1_rtx);
5970           return "dec{q}\t%0";
5971         }
5972
5973     default:
5974       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5975       /* ???? We ought to handle there the 32bit case too
5976          - do we need new constraint?  */
5977       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5978          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5979       if (CONST_INT_P (operands[2])
5980           /* Avoid overflows.  */
5981           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5982           && (INTVAL (operands[2]) == 128
5983               || (INTVAL (operands[2]) < 0
5984                   && INTVAL (operands[2]) != -128)))
5985         {
5986           operands[2] = GEN_INT (-INTVAL (operands[2]));
5987           return "sub{q}\t{%2, %0|%0, %2}";
5988         }
5989       return "add{q}\t{%2, %0|%0, %2}";
5990     }
5991 }
5992   [(set (attr "type")
5993      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5994         (const_string "incdec")
5995         (const_string "alu")))
5996    (set_attr "mode" "DI")])
5997
5998 (define_insn "*adddi_3_rex64"
5999   [(set (reg FLAGS_REG)
6000         (compare (neg:DI (match_operand:DI 2 "x86_64_general_operand" "rme"))
6001                  (match_operand:DI 1 "x86_64_general_operand" "%0")))
6002    (clobber (match_scratch:DI 0 "=r"))]
6003   "TARGET_64BIT
6004    && ix86_match_ccmode (insn, CCZmode)
6005    && !(MEM_P (operands[1]) && MEM_P (operands[2]))
6006    /* Current assemblers are broken and do not allow @GOTOFF in
6007       ought but a memory context.  */
6008    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6009 {
6010   switch (get_attr_type (insn))
6011     {
6012     case TYPE_INCDEC:
6013       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6014       if (operands[2] == const1_rtx)
6015         return "inc{q}\t%0";
6016       else
6017         {
6018           gcc_assert (operands[2] == constm1_rtx);
6019           return "dec{q}\t%0";
6020         }
6021
6022     default:
6023       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6024       /* ???? We ought to handle there the 32bit case too
6025          - do we need new constraint?  */
6026       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6027          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6028       if (CONST_INT_P (operands[2])
6029           /* Avoid overflows.  */
6030           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
6031           && (INTVAL (operands[2]) == 128
6032               || (INTVAL (operands[2]) < 0
6033                   && INTVAL (operands[2]) != -128)))
6034         {
6035           operands[2] = GEN_INT (-INTVAL (operands[2]));
6036           return "sub{q}\t{%2, %0|%0, %2}";
6037         }
6038       return "add{q}\t{%2, %0|%0, %2}";
6039     }
6040 }
6041   [(set (attr "type")
6042      (if_then_else (match_operand:DI 2 "incdec_operand" "")
6043         (const_string "incdec")
6044         (const_string "alu")))
6045    (set_attr "mode" "DI")])
6046
6047 ; For comparisons against 1, -1 and 128, we may generate better code
6048 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
6049 ; is matched then.  We can't accept general immediate, because for
6050 ; case of overflows,  the result is messed up.
6051 ; This pattern also don't hold of 0x8000000000000000, since the value overflows
6052 ; when negated.
6053 ; Also carry flag is reversed compared to cmp, so this conversion is valid
6054 ; only for comparisons not depending on it.
6055 (define_insn "*adddi_4_rex64"
6056   [(set (reg FLAGS_REG)
6057         (compare (match_operand:DI 1 "nonimmediate_operand" "0")
6058                  (match_operand:DI 2 "x86_64_immediate_operand" "e")))
6059    (clobber (match_scratch:DI 0 "=rm"))]
6060   "TARGET_64BIT
6061    &&  ix86_match_ccmode (insn, CCGCmode)"
6062 {
6063   switch (get_attr_type (insn))
6064     {
6065     case TYPE_INCDEC:
6066       if (operands[2] == constm1_rtx)
6067         return "inc{q}\t%0";
6068       else
6069         {
6070           gcc_assert (operands[2] == const1_rtx);
6071           return "dec{q}\t%0";
6072         }
6073
6074     default:
6075       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6076       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6077          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6078       if ((INTVAL (operands[2]) == -128
6079            || (INTVAL (operands[2]) > 0
6080                && INTVAL (operands[2]) != 128))
6081           /* Avoid overflows.  */
6082           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))))
6083         return "sub{q}\t{%2, %0|%0, %2}";
6084       operands[2] = GEN_INT (-INTVAL (operands[2]));
6085       return "add{q}\t{%2, %0|%0, %2}";
6086     }
6087 }
6088   [(set (attr "type")
6089      (if_then_else (match_operand:DI 2 "incdec_operand" "")
6090         (const_string "incdec")
6091         (const_string "alu")))
6092    (set_attr "mode" "DI")])
6093
6094 (define_insn "*adddi_5_rex64"
6095   [(set (reg FLAGS_REG)
6096         (compare
6097           (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
6098                    (match_operand:DI 2 "x86_64_general_operand" "rme"))
6099           (const_int 0)))
6100    (clobber (match_scratch:DI 0 "=r"))]
6101   "TARGET_64BIT
6102    && ix86_match_ccmode (insn, CCGOCmode)
6103    && !(MEM_P (operands[1]) && MEM_P (operands[2]))
6104    /* Current assemblers are broken and do not allow @GOTOFF in
6105       ought but a memory context.  */
6106    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6107 {
6108   switch (get_attr_type (insn))
6109     {
6110     case TYPE_INCDEC:
6111       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6112       if (operands[2] == const1_rtx)
6113         return "inc{q}\t%0";
6114       else
6115         {
6116           gcc_assert (operands[2] == constm1_rtx);
6117           return "dec{q}\t%0";
6118         }
6119
6120     default:
6121       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6122       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6123          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6124       if (CONST_INT_P (operands[2])
6125           /* Avoid overflows.  */
6126           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
6127           && (INTVAL (operands[2]) == 128
6128               || (INTVAL (operands[2]) < 0
6129                   && INTVAL (operands[2]) != -128)))
6130         {
6131           operands[2] = GEN_INT (-INTVAL (operands[2]));
6132           return "sub{q}\t{%2, %0|%0, %2}";
6133         }
6134       return "add{q}\t{%2, %0|%0, %2}";
6135     }
6136 }
6137   [(set (attr "type")
6138      (if_then_else (match_operand:DI 2 "incdec_operand" "")
6139         (const_string "incdec")
6140         (const_string "alu")))
6141    (set_attr "mode" "DI")])
6142
6143
6144 (define_insn "*addsi_1"
6145   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,rm,r")
6146         (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,r")
6147                  (match_operand:SI 2 "general_operand" "rmni,rni,lni")))
6148    (clobber (reg:CC FLAGS_REG))]
6149   "ix86_binary_operator_ok (PLUS, SImode, operands)"
6150 {
6151   switch (get_attr_type (insn))
6152     {
6153     case TYPE_LEA:
6154       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
6155       return "lea{l}\t{%a2, %0|%0, %a2}";
6156
6157     case TYPE_INCDEC:
6158       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6159       if (operands[2] == const1_rtx)
6160         return "inc{l}\t%0";
6161       else
6162         {
6163           gcc_assert (operands[2] == constm1_rtx);
6164           return "dec{l}\t%0";
6165         }
6166
6167     default:
6168       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6169
6170       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6171          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6172       if (CONST_INT_P (operands[2])
6173           && (INTVAL (operands[2]) == 128
6174               || (INTVAL (operands[2]) < 0
6175                   && INTVAL (operands[2]) != -128)))
6176         {
6177           operands[2] = GEN_INT (-INTVAL (operands[2]));
6178           return "sub{l}\t{%2, %0|%0, %2}";
6179         }
6180       return "add{l}\t{%2, %0|%0, %2}";
6181     }
6182 }
6183   [(set (attr "type")
6184      (cond [(eq_attr "alternative" "2")
6185               (const_string "lea")
6186             ; Current assemblers are broken and do not allow @GOTOFF in
6187             ; ought but a memory context.
6188             (match_operand:SI 2 "pic_symbolic_operand" "")
6189               (const_string "lea")
6190             (match_operand:SI 2 "incdec_operand" "")
6191               (const_string "incdec")
6192            ]
6193            (const_string "alu")))
6194    (set_attr "mode" "SI")])
6195
6196 ;; Convert lea to the lea pattern to avoid flags dependency.
6197 (define_split
6198   [(set (match_operand 0 "register_operand" "")
6199         (plus (match_operand 1 "register_operand" "")
6200               (match_operand 2 "nonmemory_operand" "")))
6201    (clobber (reg:CC FLAGS_REG))]
6202   "reload_completed
6203    && true_regnum (operands[0]) != true_regnum (operands[1])"
6204   [(const_int 0)]
6205 {
6206   rtx pat;
6207   /* In -fPIC mode the constructs like (const (unspec [symbol_ref]))
6208      may confuse gen_lowpart.  */
6209   if (GET_MODE (operands[0]) != Pmode)
6210     {
6211       operands[1] = gen_lowpart (Pmode, operands[1]);
6212       operands[2] = gen_lowpart (Pmode, operands[2]);
6213     }
6214   operands[0] = gen_lowpart (SImode, operands[0]);
6215   pat = gen_rtx_PLUS (Pmode, operands[1], operands[2]);
6216   if (Pmode != SImode)
6217     pat = gen_rtx_SUBREG (SImode, pat, 0);
6218   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6219   DONE;
6220 })
6221
6222 ;; It may seem that nonimmediate operand is proper one for operand 1.
6223 ;; The addsi_1 pattern allows nonimmediate operand at that place and
6224 ;; we take care in ix86_binary_operator_ok to not allow two memory
6225 ;; operands so proper swapping will be done in reload.  This allow
6226 ;; patterns constructed from addsi_1 to match.
6227 (define_insn "addsi_1_zext"
6228   [(set (match_operand:DI 0 "register_operand" "=r,r")
6229         (zero_extend:DI
6230           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r")
6231                    (match_operand:SI 2 "general_operand" "rmni,lni"))))
6232    (clobber (reg:CC FLAGS_REG))]
6233   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
6234 {
6235   switch (get_attr_type (insn))
6236     {
6237     case TYPE_LEA:
6238       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
6239       return "lea{l}\t{%a2, %k0|%k0, %a2}";
6240
6241     case TYPE_INCDEC:
6242       if (operands[2] == const1_rtx)
6243         return "inc{l}\t%k0";
6244       else
6245         {
6246           gcc_assert (operands[2] == constm1_rtx);
6247           return "dec{l}\t%k0";
6248         }
6249
6250     default:
6251       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6252          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6253       if (CONST_INT_P (operands[2])
6254           && (INTVAL (operands[2]) == 128
6255               || (INTVAL (operands[2]) < 0
6256                   && INTVAL (operands[2]) != -128)))
6257         {
6258           operands[2] = GEN_INT (-INTVAL (operands[2]));
6259           return "sub{l}\t{%2, %k0|%k0, %2}";
6260         }
6261       return "add{l}\t{%2, %k0|%k0, %2}";
6262     }
6263 }
6264   [(set (attr "type")
6265      (cond [(eq_attr "alternative" "1")
6266               (const_string "lea")
6267             ; Current assemblers are broken and do not allow @GOTOFF in
6268             ; ought but a memory context.
6269             (match_operand:SI 2 "pic_symbolic_operand" "")
6270               (const_string "lea")
6271             (match_operand:SI 2 "incdec_operand" "")
6272               (const_string "incdec")
6273            ]
6274            (const_string "alu")))
6275    (set_attr "mode" "SI")])
6276
6277 ;; Convert lea to the lea pattern to avoid flags dependency.
6278 (define_split
6279   [(set (match_operand:DI 0 "register_operand" "")
6280         (zero_extend:DI
6281           (plus:SI (match_operand:SI 1 "register_operand" "")
6282                    (match_operand:SI 2 "nonmemory_operand" ""))))
6283    (clobber (reg:CC FLAGS_REG))]
6284   "TARGET_64BIT && reload_completed
6285    && true_regnum (operands[0]) != true_regnum (operands[1])"
6286   [(set (match_dup 0)
6287         (zero_extend:DI (subreg:SI (plus:DI (match_dup 1) (match_dup 2)) 0)))]
6288 {
6289   operands[1] = gen_lowpart (Pmode, operands[1]);
6290   operands[2] = gen_lowpart (Pmode, operands[2]);
6291 })
6292
6293 (define_insn "*addsi_2"
6294   [(set (reg FLAGS_REG)
6295         (compare
6296           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
6297                    (match_operand:SI 2 "general_operand" "rmni,rni"))
6298           (const_int 0)))
6299    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
6300         (plus:SI (match_dup 1) (match_dup 2)))]
6301   "ix86_match_ccmode (insn, CCGOCmode)
6302    && ix86_binary_operator_ok (PLUS, SImode, operands)
6303    /* Current assemblers are broken and do not allow @GOTOFF in
6304       ought but a memory context.  */
6305    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6306 {
6307   switch (get_attr_type (insn))
6308     {
6309     case TYPE_INCDEC:
6310       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6311       if (operands[2] == const1_rtx)
6312         return "inc{l}\t%0";
6313       else
6314         {
6315           gcc_assert (operands[2] == constm1_rtx);
6316           return "dec{l}\t%0";
6317         }
6318
6319     default:
6320       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6321       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6322          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6323       if (CONST_INT_P (operands[2])
6324           && (INTVAL (operands[2]) == 128
6325               || (INTVAL (operands[2]) < 0
6326                   && INTVAL (operands[2]) != -128)))
6327         {
6328           operands[2] = GEN_INT (-INTVAL (operands[2]));
6329           return "sub{l}\t{%2, %0|%0, %2}";
6330         }
6331       return "add{l}\t{%2, %0|%0, %2}";
6332     }
6333 }
6334   [(set (attr "type")
6335      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6336         (const_string "incdec")
6337         (const_string "alu")))
6338    (set_attr "mode" "SI")])
6339
6340 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
6341 (define_insn "*addsi_2_zext"
6342   [(set (reg FLAGS_REG)
6343         (compare
6344           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
6345                    (match_operand:SI 2 "general_operand" "rmni"))
6346           (const_int 0)))
6347    (set (match_operand:DI 0 "register_operand" "=r")
6348         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
6349   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6350    && ix86_binary_operator_ok (PLUS, SImode, operands)
6351    /* Current assemblers are broken and do not allow @GOTOFF in
6352       ought but a memory context.  */
6353    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6354 {
6355   switch (get_attr_type (insn))
6356     {
6357     case TYPE_INCDEC:
6358       if (operands[2] == const1_rtx)
6359         return "inc{l}\t%k0";
6360       else
6361         {
6362           gcc_assert (operands[2] == constm1_rtx);
6363           return "dec{l}\t%k0";
6364         }
6365
6366     default:
6367       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6368          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6369       if (CONST_INT_P (operands[2])
6370           && (INTVAL (operands[2]) == 128
6371               || (INTVAL (operands[2]) < 0
6372                   && INTVAL (operands[2]) != -128)))
6373         {
6374           operands[2] = GEN_INT (-INTVAL (operands[2]));
6375           return "sub{l}\t{%2, %k0|%k0, %2}";
6376         }
6377       return "add{l}\t{%2, %k0|%k0, %2}";
6378     }
6379 }
6380   [(set (attr "type")
6381      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6382         (const_string "incdec")
6383         (const_string "alu")))
6384    (set_attr "mode" "SI")])
6385
6386 (define_insn "*addsi_3"
6387   [(set (reg FLAGS_REG)
6388         (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
6389                  (match_operand:SI 1 "nonimmediate_operand" "%0")))
6390    (clobber (match_scratch:SI 0 "=r"))]
6391   "ix86_match_ccmode (insn, CCZmode)
6392    && !(MEM_P (operands[1]) && MEM_P (operands[2]))
6393    /* Current assemblers are broken and do not allow @GOTOFF in
6394       ought but a memory context.  */
6395    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6396 {
6397   switch (get_attr_type (insn))
6398     {
6399     case TYPE_INCDEC:
6400       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6401       if (operands[2] == const1_rtx)
6402         return "inc{l}\t%0";
6403       else
6404         {
6405           gcc_assert (operands[2] == constm1_rtx);
6406           return "dec{l}\t%0";
6407         }
6408
6409     default:
6410       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6411       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6412          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6413       if (CONST_INT_P (operands[2])
6414           && (INTVAL (operands[2]) == 128
6415               || (INTVAL (operands[2]) < 0
6416                   && INTVAL (operands[2]) != -128)))
6417         {
6418           operands[2] = GEN_INT (-INTVAL (operands[2]));
6419           return "sub{l}\t{%2, %0|%0, %2}";
6420         }
6421       return "add{l}\t{%2, %0|%0, %2}";
6422     }
6423 }
6424   [(set (attr "type")
6425      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6426         (const_string "incdec")
6427         (const_string "alu")))
6428    (set_attr "mode" "SI")])
6429
6430 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
6431 (define_insn "*addsi_3_zext"
6432   [(set (reg FLAGS_REG)
6433         (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
6434                  (match_operand:SI 1 "nonimmediate_operand" "%0")))
6435    (set (match_operand:DI 0 "register_operand" "=r")
6436         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
6437   "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
6438    && ix86_binary_operator_ok (PLUS, SImode, operands)
6439    /* Current assemblers are broken and do not allow @GOTOFF in
6440       ought but a memory context.  */
6441    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6442 {
6443   switch (get_attr_type (insn))
6444     {
6445     case TYPE_INCDEC:
6446       if (operands[2] == const1_rtx)
6447         return "inc{l}\t%k0";
6448       else
6449         {
6450           gcc_assert (operands[2] == constm1_rtx);
6451           return "dec{l}\t%k0";
6452         }
6453
6454     default:
6455       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6456          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6457       if (CONST_INT_P (operands[2])
6458           && (INTVAL (operands[2]) == 128
6459               || (INTVAL (operands[2]) < 0
6460                   && INTVAL (operands[2]) != -128)))
6461         {
6462           operands[2] = GEN_INT (-INTVAL (operands[2]));
6463           return "sub{l}\t{%2, %k0|%k0, %2}";
6464         }
6465       return "add{l}\t{%2, %k0|%k0, %2}";
6466     }
6467 }
6468   [(set (attr "type")
6469      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6470         (const_string "incdec")
6471         (const_string "alu")))
6472    (set_attr "mode" "SI")])
6473
6474 ; For comparisons against 1, -1 and 128, we may generate better code
6475 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
6476 ; is matched then.  We can't accept general immediate, because for
6477 ; case of overflows,  the result is messed up.
6478 ; This pattern also don't hold of 0x80000000, since the value overflows
6479 ; when negated.
6480 ; Also carry flag is reversed compared to cmp, so this conversion is valid
6481 ; only for comparisons not depending on it.
6482 (define_insn "*addsi_4"
6483   [(set (reg FLAGS_REG)
6484         (compare (match_operand:SI 1 "nonimmediate_operand" "0")
6485                  (match_operand:SI 2 "const_int_operand" "n")))
6486    (clobber (match_scratch:SI 0 "=rm"))]
6487   "ix86_match_ccmode (insn, CCGCmode)
6488    && (INTVAL (operands[2]) & 0xffffffff) != 0x80000000"
6489 {
6490   switch (get_attr_type (insn))
6491     {
6492     case TYPE_INCDEC:
6493       if (operands[2] == constm1_rtx)
6494         return "inc{l}\t%0";
6495       else
6496         {
6497           gcc_assert (operands[2] == const1_rtx);
6498           return "dec{l}\t%0";
6499         }
6500
6501     default:
6502       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6503       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6504          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6505       if ((INTVAL (operands[2]) == -128
6506            || (INTVAL (operands[2]) > 0
6507                && INTVAL (operands[2]) != 128)))
6508         return "sub{l}\t{%2, %0|%0, %2}";
6509       operands[2] = GEN_INT (-INTVAL (operands[2]));
6510       return "add{l}\t{%2, %0|%0, %2}";
6511     }
6512 }
6513   [(set (attr "type")
6514      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6515         (const_string "incdec")
6516         (const_string "alu")))
6517    (set_attr "mode" "SI")])
6518
6519 (define_insn "*addsi_5"
6520   [(set (reg FLAGS_REG)
6521         (compare
6522           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
6523                    (match_operand:SI 2 "general_operand" "rmni"))
6524           (const_int 0)))
6525    (clobber (match_scratch:SI 0 "=r"))]
6526   "ix86_match_ccmode (insn, CCGOCmode)
6527    && !(MEM_P (operands[1]) && MEM_P (operands[2]))
6528    /* Current assemblers are broken and do not allow @GOTOFF in
6529       ought but a memory context.  */
6530    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6531 {
6532   switch (get_attr_type (insn))
6533     {
6534     case TYPE_INCDEC:
6535       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6536       if (operands[2] == const1_rtx)
6537         return "inc{l}\t%0";
6538       else
6539         {
6540           gcc_assert (operands[2] == constm1_rtx);
6541           return "dec{l}\t%0";
6542         }
6543
6544     default:
6545       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6546       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6547          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6548       if (CONST_INT_P (operands[2])
6549           && (INTVAL (operands[2]) == 128
6550               || (INTVAL (operands[2]) < 0
6551                   && INTVAL (operands[2]) != -128)))
6552         {
6553           operands[2] = GEN_INT (-INTVAL (operands[2]));
6554           return "sub{l}\t{%2, %0|%0, %2}";
6555         }
6556       return "add{l}\t{%2, %0|%0, %2}";
6557     }
6558 }
6559   [(set (attr "type")
6560      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6561         (const_string "incdec")
6562         (const_string "alu")))
6563    (set_attr "mode" "SI")])
6564
6565 (define_expand "addhi3"
6566   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
6567                    (plus:HI (match_operand:HI 1 "nonimmediate_operand" "")
6568                             (match_operand:HI 2 "general_operand" "")))
6569               (clobber (reg:CC FLAGS_REG))])]
6570   "TARGET_HIMODE_MATH"
6571   "ix86_expand_binary_operator (PLUS, HImode, operands); DONE;")
6572
6573 ;; %%% After Dave's SUBREG_BYTE stuff goes in, re-enable incb %ah
6574 ;; type optimizations enabled by define-splits.  This is not important
6575 ;; for PII, and in fact harmful because of partial register stalls.
6576
6577 (define_insn "*addhi_1_lea"
6578   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
6579         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r")
6580                  (match_operand:HI 2 "general_operand" "ri,rm,lni")))
6581    (clobber (reg:CC FLAGS_REG))]
6582   "!TARGET_PARTIAL_REG_STALL
6583    && ix86_binary_operator_ok (PLUS, HImode, operands)"
6584 {
6585   switch (get_attr_type (insn))
6586     {
6587     case TYPE_LEA:
6588       return "#";
6589     case TYPE_INCDEC:
6590       if (operands[2] == const1_rtx)
6591         return "inc{w}\t%0";
6592       else
6593         {
6594           gcc_assert (operands[2] == constm1_rtx);
6595           return "dec{w}\t%0";
6596         }
6597
6598     default:
6599       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6600          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6601       if (CONST_INT_P (operands[2])
6602           && (INTVAL (operands[2]) == 128
6603               || (INTVAL (operands[2]) < 0
6604                   && INTVAL (operands[2]) != -128)))
6605         {
6606           operands[2] = GEN_INT (-INTVAL (operands[2]));
6607           return "sub{w}\t{%2, %0|%0, %2}";
6608         }
6609       return "add{w}\t{%2, %0|%0, %2}";
6610     }
6611 }
6612   [(set (attr "type")
6613      (if_then_else (eq_attr "alternative" "2")
6614         (const_string "lea")
6615         (if_then_else (match_operand:HI 2 "incdec_operand" "")
6616            (const_string "incdec")
6617            (const_string "alu"))))
6618    (set_attr "mode" "HI,HI,SI")])
6619
6620 (define_insn "*addhi_1"
6621   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6622         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
6623                  (match_operand:HI 2 "general_operand" "ri,rm")))
6624    (clobber (reg:CC FLAGS_REG))]
6625   "TARGET_PARTIAL_REG_STALL
6626    && ix86_binary_operator_ok (PLUS, HImode, operands)"
6627 {
6628   switch (get_attr_type (insn))
6629     {
6630     case TYPE_INCDEC:
6631       if (operands[2] == const1_rtx)
6632         return "inc{w}\t%0";
6633       else
6634         {
6635           gcc_assert (operands[2] == constm1_rtx);
6636           return "dec{w}\t%0";
6637         }
6638
6639     default:
6640       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6641          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6642       if (CONST_INT_P (operands[2])
6643           && (INTVAL (operands[2]) == 128
6644               || (INTVAL (operands[2]) < 0
6645                   && INTVAL (operands[2]) != -128)))
6646         {
6647           operands[2] = GEN_INT (-INTVAL (operands[2]));
6648           return "sub{w}\t{%2, %0|%0, %2}";
6649         }
6650       return "add{w}\t{%2, %0|%0, %2}";
6651     }
6652 }
6653   [(set (attr "type")
6654      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6655         (const_string "incdec")
6656         (const_string "alu")))
6657    (set_attr "mode" "HI")])
6658
6659 (define_insn "*addhi_2"
6660   [(set (reg FLAGS_REG)
6661         (compare
6662           (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
6663                    (match_operand:HI 2 "general_operand" "rmni,rni"))
6664           (const_int 0)))
6665    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
6666         (plus:HI (match_dup 1) (match_dup 2)))]
6667   "ix86_match_ccmode (insn, CCGOCmode)
6668    && ix86_binary_operator_ok (PLUS, HImode, operands)"
6669 {
6670   switch (get_attr_type (insn))
6671     {
6672     case TYPE_INCDEC:
6673       if (operands[2] == const1_rtx)
6674         return "inc{w}\t%0";
6675       else
6676         {
6677           gcc_assert (operands[2] == constm1_rtx);
6678           return "dec{w}\t%0";
6679         }
6680
6681     default:
6682       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6683          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6684       if (CONST_INT_P (operands[2])
6685           && (INTVAL (operands[2]) == 128
6686               || (INTVAL (operands[2]) < 0
6687                   && INTVAL (operands[2]) != -128)))
6688         {
6689           operands[2] = GEN_INT (-INTVAL (operands[2]));
6690           return "sub{w}\t{%2, %0|%0, %2}";
6691         }
6692       return "add{w}\t{%2, %0|%0, %2}";
6693     }
6694 }
6695   [(set (attr "type")
6696      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6697         (const_string "incdec")
6698         (const_string "alu")))
6699    (set_attr "mode" "HI")])
6700
6701 (define_insn "*addhi_3"
6702   [(set (reg FLAGS_REG)
6703         (compare (neg:HI (match_operand:HI 2 "general_operand" "rmni"))
6704                  (match_operand:HI 1 "nonimmediate_operand" "%0")))
6705    (clobber (match_scratch:HI 0 "=r"))]
6706   "ix86_match_ccmode (insn, CCZmode)
6707    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6708 {
6709   switch (get_attr_type (insn))
6710     {
6711     case TYPE_INCDEC:
6712       if (operands[2] == const1_rtx)
6713         return "inc{w}\t%0";
6714       else
6715         {
6716           gcc_assert (operands[2] == constm1_rtx);
6717           return "dec{w}\t%0";
6718         }
6719
6720     default:
6721       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6722          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6723       if (CONST_INT_P (operands[2])
6724           && (INTVAL (operands[2]) == 128
6725               || (INTVAL (operands[2]) < 0
6726                   && INTVAL (operands[2]) != -128)))
6727         {
6728           operands[2] = GEN_INT (-INTVAL (operands[2]));
6729           return "sub{w}\t{%2, %0|%0, %2}";
6730         }
6731       return "add{w}\t{%2, %0|%0, %2}";
6732     }
6733 }
6734   [(set (attr "type")
6735      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6736         (const_string "incdec")
6737         (const_string "alu")))
6738    (set_attr "mode" "HI")])
6739
6740 ; See comments above addsi_4 for details.
6741 (define_insn "*addhi_4"
6742   [(set (reg FLAGS_REG)
6743         (compare (match_operand:HI 1 "nonimmediate_operand" "0")
6744                  (match_operand:HI 2 "const_int_operand" "n")))
6745    (clobber (match_scratch:HI 0 "=rm"))]
6746   "ix86_match_ccmode (insn, CCGCmode)
6747    && (INTVAL (operands[2]) & 0xffff) != 0x8000"
6748 {
6749   switch (get_attr_type (insn))
6750     {
6751     case TYPE_INCDEC:
6752       if (operands[2] == constm1_rtx)
6753         return "inc{w}\t%0";
6754       else
6755         {
6756           gcc_assert (operands[2] == const1_rtx);
6757           return "dec{w}\t%0";
6758         }
6759
6760     default:
6761       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6762       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6763          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6764       if ((INTVAL (operands[2]) == -128
6765            || (INTVAL (operands[2]) > 0
6766                && INTVAL (operands[2]) != 128)))
6767         return "sub{w}\t{%2, %0|%0, %2}";
6768       operands[2] = GEN_INT (-INTVAL (operands[2]));
6769       return "add{w}\t{%2, %0|%0, %2}";
6770     }
6771 }
6772   [(set (attr "type")
6773      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6774         (const_string "incdec")
6775         (const_string "alu")))
6776    (set_attr "mode" "SI")])
6777
6778
6779 (define_insn "*addhi_5"
6780   [(set (reg FLAGS_REG)
6781         (compare
6782           (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
6783                    (match_operand:HI 2 "general_operand" "rmni"))
6784           (const_int 0)))
6785    (clobber (match_scratch:HI 0 "=r"))]
6786   "ix86_match_ccmode (insn, CCGOCmode)
6787    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6788 {
6789   switch (get_attr_type (insn))
6790     {
6791     case TYPE_INCDEC:
6792       if (operands[2] == const1_rtx)
6793         return "inc{w}\t%0";
6794       else
6795         {
6796           gcc_assert (operands[2] == constm1_rtx);
6797           return "dec{w}\t%0";
6798         }
6799
6800     default:
6801       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6802          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6803       if (CONST_INT_P (operands[2])
6804           && (INTVAL (operands[2]) == 128
6805               || (INTVAL (operands[2]) < 0
6806                   && INTVAL (operands[2]) != -128)))
6807         {
6808           operands[2] = GEN_INT (-INTVAL (operands[2]));
6809           return "sub{w}\t{%2, %0|%0, %2}";
6810         }
6811       return "add{w}\t{%2, %0|%0, %2}";
6812     }
6813 }
6814   [(set (attr "type")
6815      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6816         (const_string "incdec")
6817         (const_string "alu")))
6818    (set_attr "mode" "HI")])
6819
6820 (define_expand "addqi3"
6821   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6822                    (plus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6823                             (match_operand:QI 2 "general_operand" "")))
6824               (clobber (reg:CC FLAGS_REG))])]
6825   "TARGET_QIMODE_MATH"
6826   "ix86_expand_binary_operator (PLUS, QImode, operands); DONE;")
6827
6828 ;; %%% Potential partial reg stall on alternative 2.  What to do?
6829 (define_insn "*addqi_1_lea"
6830   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r,r")
6831         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,r")
6832                  (match_operand:QI 2 "general_operand" "qn,qmn,rn,ln")))
6833    (clobber (reg:CC FLAGS_REG))]
6834   "!TARGET_PARTIAL_REG_STALL
6835    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6836 {
6837   int widen = (which_alternative == 2);
6838   switch (get_attr_type (insn))
6839     {
6840     case TYPE_LEA:
6841       return "#";
6842     case TYPE_INCDEC:
6843       if (operands[2] == const1_rtx)
6844         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6845       else
6846         {
6847           gcc_assert (operands[2] == constm1_rtx);
6848           return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6849         }
6850
6851     default:
6852       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6853          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6854       if (CONST_INT_P (operands[2])
6855           && (INTVAL (operands[2]) == 128
6856               || (INTVAL (operands[2]) < 0
6857                   && INTVAL (operands[2]) != -128)))
6858         {
6859           operands[2] = GEN_INT (-INTVAL (operands[2]));
6860           if (widen)
6861             return "sub{l}\t{%2, %k0|%k0, %2}";
6862           else
6863             return "sub{b}\t{%2, %0|%0, %2}";
6864         }
6865       if (widen)
6866         return "add{l}\t{%k2, %k0|%k0, %k2}";
6867       else
6868         return "add{b}\t{%2, %0|%0, %2}";
6869     }
6870 }
6871   [(set (attr "type")
6872      (if_then_else (eq_attr "alternative" "3")
6873         (const_string "lea")
6874         (if_then_else (match_operand:QI 2 "incdec_operand" "")
6875            (const_string "incdec")
6876            (const_string "alu"))))
6877    (set_attr "mode" "QI,QI,SI,SI")])
6878
6879 (define_insn "*addqi_1"
6880   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
6881         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
6882                  (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
6883    (clobber (reg:CC FLAGS_REG))]
6884   "TARGET_PARTIAL_REG_STALL
6885    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6886 {
6887   int widen = (which_alternative == 2);
6888   switch (get_attr_type (insn))
6889     {
6890     case TYPE_INCDEC:
6891       if (operands[2] == const1_rtx)
6892         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6893       else
6894         {
6895           gcc_assert (operands[2] == constm1_rtx);
6896           return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6897         }
6898
6899     default:
6900       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6901          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6902       if (CONST_INT_P (operands[2])
6903           && (INTVAL (operands[2]) == 128
6904               || (INTVAL (operands[2]) < 0
6905                   && INTVAL (operands[2]) != -128)))
6906         {
6907           operands[2] = GEN_INT (-INTVAL (operands[2]));
6908           if (widen)
6909             return "sub{l}\t{%2, %k0|%k0, %2}";
6910           else
6911             return "sub{b}\t{%2, %0|%0, %2}";
6912         }
6913       if (widen)
6914         return "add{l}\t{%k2, %k0|%k0, %k2}";
6915       else
6916         return "add{b}\t{%2, %0|%0, %2}";
6917     }
6918 }
6919   [(set (attr "type")
6920      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6921         (const_string "incdec")
6922         (const_string "alu")))
6923    (set_attr "mode" "QI,QI,SI")])
6924
6925 (define_insn "*addqi_1_slp"
6926   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6927         (plus:QI (match_dup 0)
6928                  (match_operand:QI 1 "general_operand" "qn,qnm")))
6929    (clobber (reg:CC FLAGS_REG))]
6930   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6931    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
6932 {
6933   switch (get_attr_type (insn))
6934     {
6935     case TYPE_INCDEC:
6936       if (operands[1] == const1_rtx)
6937         return "inc{b}\t%0";
6938       else
6939         {
6940           gcc_assert (operands[1] == constm1_rtx);
6941           return "dec{b}\t%0";
6942         }
6943
6944     default:
6945       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.  */
6946       if (CONST_INT_P (operands[1])
6947           && INTVAL (operands[1]) < 0)
6948         {
6949           operands[1] = GEN_INT (-INTVAL (operands[1]));
6950           return "sub{b}\t{%1, %0|%0, %1}";
6951         }
6952       return "add{b}\t{%1, %0|%0, %1}";
6953     }
6954 }
6955   [(set (attr "type")
6956      (if_then_else (match_operand:QI 1 "incdec_operand" "")
6957         (const_string "incdec")
6958         (const_string "alu1")))
6959    (set (attr "memory")
6960      (if_then_else (match_operand 1 "memory_operand" "")
6961         (const_string "load")
6962         (const_string "none")))
6963    (set_attr "mode" "QI")])
6964
6965 (define_insn "*addqi_2"
6966   [(set (reg FLAGS_REG)
6967         (compare
6968           (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
6969                    (match_operand:QI 2 "general_operand" "qmni,qni"))
6970           (const_int 0)))
6971    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
6972         (plus:QI (match_dup 1) (match_dup 2)))]
6973   "ix86_match_ccmode (insn, CCGOCmode)
6974    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6975 {
6976   switch (get_attr_type (insn))
6977     {
6978     case TYPE_INCDEC:
6979       if (operands[2] == const1_rtx)
6980         return "inc{b}\t%0";
6981       else
6982         {
6983           gcc_assert (operands[2] == constm1_rtx
6984                       || (CONST_INT_P (operands[2])
6985                           && INTVAL (operands[2]) == 255));
6986           return "dec{b}\t%0";
6987         }
6988
6989     default:
6990       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
6991       if (CONST_INT_P (operands[2])
6992           && INTVAL (operands[2]) < 0)
6993         {
6994           operands[2] = GEN_INT (-INTVAL (operands[2]));
6995           return "sub{b}\t{%2, %0|%0, %2}";
6996         }
6997       return "add{b}\t{%2, %0|%0, %2}";
6998     }
6999 }
7000   [(set (attr "type")
7001      (if_then_else (match_operand:QI 2 "incdec_operand" "")
7002         (const_string "incdec")
7003         (const_string "alu")))
7004    (set_attr "mode" "QI")])
7005
7006 (define_insn "*addqi_3"
7007   [(set (reg FLAGS_REG)
7008         (compare (neg:QI (match_operand:QI 2 "general_operand" "qmni"))
7009                  (match_operand:QI 1 "nonimmediate_operand" "%0")))
7010    (clobber (match_scratch:QI 0 "=q"))]
7011   "ix86_match_ccmode (insn, CCZmode)
7012    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7013 {
7014   switch (get_attr_type (insn))
7015     {
7016     case TYPE_INCDEC:
7017       if (operands[2] == const1_rtx)
7018         return "inc{b}\t%0";
7019       else
7020         {
7021           gcc_assert (operands[2] == constm1_rtx
7022                       || (CONST_INT_P (operands[2])
7023                           && INTVAL (operands[2]) == 255));
7024           return "dec{b}\t%0";
7025         }
7026
7027     default:
7028       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
7029       if (CONST_INT_P (operands[2])
7030           && INTVAL (operands[2]) < 0)
7031         {
7032           operands[2] = GEN_INT (-INTVAL (operands[2]));
7033           return "sub{b}\t{%2, %0|%0, %2}";
7034         }
7035       return "add{b}\t{%2, %0|%0, %2}";
7036     }
7037 }
7038   [(set (attr "type")
7039      (if_then_else (match_operand:QI 2 "incdec_operand" "")
7040         (const_string "incdec")
7041         (const_string "alu")))
7042    (set_attr "mode" "QI")])
7043
7044 ; See comments above addsi_4 for details.
7045 (define_insn "*addqi_4"
7046   [(set (reg FLAGS_REG)
7047         (compare (match_operand:QI 1 "nonimmediate_operand" "0")
7048                  (match_operand:QI 2 "const_int_operand" "n")))
7049    (clobber (match_scratch:QI 0 "=qm"))]
7050   "ix86_match_ccmode (insn, CCGCmode)
7051    && (INTVAL (operands[2]) & 0xff) != 0x80"
7052 {
7053   switch (get_attr_type (insn))
7054     {
7055     case TYPE_INCDEC:
7056       if (operands[2] == constm1_rtx
7057           || (CONST_INT_P (operands[2])
7058               && INTVAL (operands[2]) == 255))
7059         return "inc{b}\t%0";
7060       else
7061         {
7062           gcc_assert (operands[2] == const1_rtx);
7063           return "dec{b}\t%0";
7064         }
7065
7066     default:
7067       gcc_assert (rtx_equal_p (operands[0], operands[1]));
7068       if (INTVAL (operands[2]) < 0)
7069         {
7070           operands[2] = GEN_INT (-INTVAL (operands[2]));
7071           return "add{b}\t{%2, %0|%0, %2}";
7072         }
7073       return "sub{b}\t{%2, %0|%0, %2}";
7074     }
7075 }
7076   [(set (attr "type")
7077      (if_then_else (match_operand:HI 2 "incdec_operand" "")
7078         (const_string "incdec")
7079         (const_string "alu")))
7080    (set_attr "mode" "QI")])
7081
7082
7083 (define_insn "*addqi_5"
7084   [(set (reg FLAGS_REG)
7085         (compare
7086           (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
7087                    (match_operand:QI 2 "general_operand" "qmni"))
7088           (const_int 0)))
7089    (clobber (match_scratch:QI 0 "=q"))]
7090   "ix86_match_ccmode (insn, CCGOCmode)
7091    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7092 {
7093   switch (get_attr_type (insn))
7094     {
7095     case TYPE_INCDEC:
7096       if (operands[2] == const1_rtx)
7097         return "inc{b}\t%0";
7098       else
7099         {
7100           gcc_assert (operands[2] == constm1_rtx
7101                       || (CONST_INT_P (operands[2])
7102                           && INTVAL (operands[2]) == 255));
7103           return "dec{b}\t%0";
7104         }
7105
7106     default:
7107       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
7108       if (CONST_INT_P (operands[2])
7109           && INTVAL (operands[2]) < 0)
7110         {
7111           operands[2] = GEN_INT (-INTVAL (operands[2]));
7112           return "sub{b}\t{%2, %0|%0, %2}";
7113         }
7114       return "add{b}\t{%2, %0|%0, %2}";
7115     }
7116 }
7117   [(set (attr "type")
7118      (if_then_else (match_operand:QI 2 "incdec_operand" "")
7119         (const_string "incdec")
7120         (const_string "alu")))
7121    (set_attr "mode" "QI")])
7122
7123
7124 (define_insn "addqi_ext_1"
7125   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7126                          (const_int 8)
7127                          (const_int 8))
7128         (plus:SI
7129           (zero_extract:SI
7130             (match_operand 1 "ext_register_operand" "0")
7131             (const_int 8)
7132             (const_int 8))
7133           (match_operand:QI 2 "general_operand" "Qmn")))
7134    (clobber (reg:CC FLAGS_REG))]
7135   "!TARGET_64BIT"
7136 {
7137   switch (get_attr_type (insn))
7138     {
7139     case TYPE_INCDEC:
7140       if (operands[2] == const1_rtx)
7141         return "inc{b}\t%h0";
7142       else
7143         {
7144           gcc_assert (operands[2] == constm1_rtx
7145                       || (CONST_INT_P (operands[2])
7146                           && INTVAL (operands[2]) == 255));
7147           return "dec{b}\t%h0";
7148         }
7149
7150     default:
7151       return "add{b}\t{%2, %h0|%h0, %2}";
7152     }
7153 }
7154   [(set (attr "type")
7155      (if_then_else (match_operand:QI 2 "incdec_operand" "")
7156         (const_string "incdec")
7157         (const_string "alu")))
7158    (set_attr "mode" "QI")])
7159
7160 (define_insn "*addqi_ext_1_rex64"
7161   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7162                          (const_int 8)
7163                          (const_int 8))
7164         (plus:SI
7165           (zero_extract:SI
7166             (match_operand 1 "ext_register_operand" "0")
7167             (const_int 8)
7168             (const_int 8))
7169           (match_operand:QI 2 "nonmemory_operand" "Qn")))
7170    (clobber (reg:CC FLAGS_REG))]
7171   "TARGET_64BIT"
7172 {
7173   switch (get_attr_type (insn))
7174     {
7175     case TYPE_INCDEC:
7176       if (operands[2] == const1_rtx)
7177         return "inc{b}\t%h0";
7178       else
7179         {
7180           gcc_assert (operands[2] == constm1_rtx
7181                       || (CONST_INT_P (operands[2])
7182                           && INTVAL (operands[2]) == 255));
7183           return "dec{b}\t%h0";
7184         }
7185
7186     default:
7187       return "add{b}\t{%2, %h0|%h0, %2}";
7188     }
7189 }
7190   [(set (attr "type")
7191      (if_then_else (match_operand:QI 2 "incdec_operand" "")
7192         (const_string "incdec")
7193         (const_string "alu")))
7194    (set_attr "mode" "QI")])
7195
7196 (define_insn "*addqi_ext_2"
7197   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7198                          (const_int 8)
7199                          (const_int 8))
7200         (plus:SI
7201           (zero_extract:SI
7202             (match_operand 1 "ext_register_operand" "%0")
7203             (const_int 8)
7204             (const_int 8))
7205           (zero_extract:SI
7206             (match_operand 2 "ext_register_operand" "Q")
7207             (const_int 8)
7208             (const_int 8))))
7209    (clobber (reg:CC FLAGS_REG))]
7210   ""
7211   "add{b}\t{%h2, %h0|%h0, %h2}"
7212   [(set_attr "type" "alu")
7213    (set_attr "mode" "QI")])
7214
7215 ;; The patterns that match these are at the end of this file.
7216
7217 (define_expand "addxf3"
7218   [(set (match_operand:XF 0 "register_operand" "")
7219         (plus:XF (match_operand:XF 1 "register_operand" "")
7220                  (match_operand:XF 2 "register_operand" "")))]
7221   "TARGET_80387"
7222   "")
7223
7224 (define_expand "add<mode>3"
7225   [(set (match_operand:MODEF 0 "register_operand" "")
7226         (plus:MODEF (match_operand:MODEF 1 "register_operand" "")
7227                     (match_operand:MODEF 2 "nonimmediate_operand" "")))]
7228   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
7229   "")
7230 \f
7231 ;; Subtract instructions
7232
7233 ;; %%% splits for subditi3
7234
7235 (define_expand "subti3"
7236   [(parallel [(set (match_operand:TI 0 "nonimmediate_operand" "")
7237                    (minus:TI (match_operand:TI 1 "nonimmediate_operand" "")
7238                              (match_operand:TI 2 "x86_64_general_operand" "")))
7239               (clobber (reg:CC FLAGS_REG))])]
7240   "TARGET_64BIT"
7241   "ix86_expand_binary_operator (MINUS, TImode, operands); DONE;")
7242
7243 (define_insn "*subti3_1"
7244   [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o")
7245         (minus:TI (match_operand:TI 1 "nonimmediate_operand" "0,0")
7246                   (match_operand:TI 2 "x86_64_general_operand" "roe,re")))
7247    (clobber (reg:CC FLAGS_REG))]
7248   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, TImode, operands)"
7249   "#")
7250
7251 (define_split
7252   [(set (match_operand:TI 0 "nonimmediate_operand" "")
7253         (minus:TI (match_operand:TI 1 "nonimmediate_operand" "")
7254                   (match_operand:TI 2 "x86_64_general_operand" "")))
7255    (clobber (reg:CC FLAGS_REG))]
7256   "TARGET_64BIT && reload_completed"
7257   [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
7258               (set (match_dup 0) (minus:DI (match_dup 1) (match_dup 2)))])
7259    (parallel [(set (match_dup 3)
7260                    (minus:DI (match_dup 4)
7261                              (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
7262                                       (match_dup 5))))
7263               (clobber (reg:CC FLAGS_REG))])]
7264   "split_ti (&operands[0], 3, &operands[0], &operands[3]);")
7265
7266 ;; %%% splits for subsidi3
7267
7268 (define_expand "subdi3"
7269   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
7270                    (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
7271                              (match_operand:DI 2 "x86_64_general_operand" "")))
7272               (clobber (reg:CC FLAGS_REG))])]
7273   ""
7274   "ix86_expand_binary_operator (MINUS, DImode, operands); DONE;")
7275
7276 (define_insn "*subdi3_1"
7277   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
7278         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7279                   (match_operand:DI 2 "general_operand" "roiF,riF")))
7280    (clobber (reg:CC FLAGS_REG))]
7281   "!TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
7282   "#")
7283
7284 (define_split
7285   [(set (match_operand:DI 0 "nonimmediate_operand" "")
7286         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
7287                   (match_operand:DI 2 "general_operand" "")))
7288    (clobber (reg:CC FLAGS_REG))]
7289   "!TARGET_64BIT && reload_completed"
7290   [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
7291               (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 2)))])
7292    (parallel [(set (match_dup 3)
7293                    (minus:SI (match_dup 4)
7294                              (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
7295                                       (match_dup 5))))
7296               (clobber (reg:CC FLAGS_REG))])]
7297   "split_di (&operands[0], 3, &operands[0], &operands[3]);")
7298
7299 (define_insn "subdi3_carry_rex64"
7300   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7301           (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7302             (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
7303                (match_operand:DI 2 "x86_64_general_operand" "re,rm"))))
7304    (clobber (reg:CC FLAGS_REG))]
7305   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
7306   "sbb{q}\t{%2, %0|%0, %2}"
7307   [(set_attr "type" "alu")
7308    (set_attr "pent_pair" "pu")
7309    (set_attr "mode" "DI")])
7310
7311 (define_insn "*subdi_1_rex64"
7312   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7313         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7314                   (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
7315    (clobber (reg:CC FLAGS_REG))]
7316   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
7317   "sub{q}\t{%2, %0|%0, %2}"
7318   [(set_attr "type" "alu")
7319    (set_attr "mode" "DI")])
7320
7321 (define_insn "*subdi_2_rex64"
7322   [(set (reg FLAGS_REG)
7323         (compare
7324           (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7325                     (match_operand:DI 2 "x86_64_general_operand" "re,rm"))
7326           (const_int 0)))
7327    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7328         (minus:DI (match_dup 1) (match_dup 2)))]
7329   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
7330    && ix86_binary_operator_ok (MINUS, DImode, operands)"
7331   "sub{q}\t{%2, %0|%0, %2}"
7332   [(set_attr "type" "alu")
7333    (set_attr "mode" "DI")])
7334
7335 (define_insn "*subdi_3_rex63"
7336   [(set (reg FLAGS_REG)
7337         (compare (match_operand:DI 1 "nonimmediate_operand" "0,0")
7338                  (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
7339    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7340         (minus:DI (match_dup 1) (match_dup 2)))]
7341   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
7342    && ix86_binary_operator_ok (MINUS, SImode, operands)"
7343   "sub{q}\t{%2, %0|%0, %2}"
7344   [(set_attr "type" "alu")
7345    (set_attr "mode" "DI")])
7346
7347 (define_insn "subqi3_carry"
7348   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
7349           (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
7350             (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
7351                (match_operand:QI 2 "general_operand" "qi,qm"))))
7352    (clobber (reg:CC FLAGS_REG))]
7353   "ix86_binary_operator_ok (MINUS, QImode, operands)"
7354   "sbb{b}\t{%2, %0|%0, %2}"
7355   [(set_attr "type" "alu")
7356    (set_attr "pent_pair" "pu")
7357    (set_attr "mode" "QI")])
7358
7359 (define_insn "subhi3_carry"
7360   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7361           (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
7362             (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
7363                (match_operand:HI 2 "general_operand" "ri,rm"))))
7364    (clobber (reg:CC FLAGS_REG))]
7365   "ix86_binary_operator_ok (MINUS, HImode, operands)"
7366   "sbb{w}\t{%2, %0|%0, %2}"
7367   [(set_attr "type" "alu")
7368    (set_attr "pent_pair" "pu")
7369    (set_attr "mode" "HI")])
7370
7371 (define_insn "subsi3_carry"
7372   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7373           (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
7374             (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
7375                (match_operand:SI 2 "general_operand" "ri,rm"))))
7376    (clobber (reg:CC FLAGS_REG))]
7377   "ix86_binary_operator_ok (MINUS, SImode, operands)"
7378   "sbb{l}\t{%2, %0|%0, %2}"
7379   [(set_attr "type" "alu")
7380    (set_attr "pent_pair" "pu")
7381    (set_attr "mode" "SI")])
7382
7383 (define_insn "subsi3_carry_zext"
7384   [(set (match_operand:DI 0 "register_operand" "=r")
7385           (zero_extend:DI
7386             (minus:SI (match_operand:SI 1 "register_operand" "0")
7387               (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
7388                  (match_operand:SI 2 "general_operand" "g")))))
7389    (clobber (reg:CC FLAGS_REG))]
7390   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
7391   "sbb{l}\t{%2, %k0|%k0, %2}"
7392   [(set_attr "type" "alu")
7393    (set_attr "pent_pair" "pu")
7394    (set_attr "mode" "SI")])
7395
7396 (define_expand "subsi3"
7397   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
7398                    (minus:SI (match_operand:SI 1 "nonimmediate_operand" "")
7399                              (match_operand:SI 2 "general_operand" "")))
7400               (clobber (reg:CC FLAGS_REG))])]
7401   ""
7402   "ix86_expand_binary_operator (MINUS, SImode, operands); DONE;")
7403
7404 (define_insn "*subsi_1"
7405   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7406         (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
7407                   (match_operand:SI 2 "general_operand" "ri,rm")))
7408    (clobber (reg:CC FLAGS_REG))]
7409   "ix86_binary_operator_ok (MINUS, SImode, operands)"
7410   "sub{l}\t{%2, %0|%0, %2}"
7411   [(set_attr "type" "alu")
7412    (set_attr "mode" "SI")])
7413
7414 (define_insn "*subsi_1_zext"
7415   [(set (match_operand:DI 0 "register_operand" "=r")
7416         (zero_extend:DI
7417           (minus:SI (match_operand:SI 1 "register_operand" "0")
7418                     (match_operand:SI 2 "general_operand" "g"))))
7419    (clobber (reg:CC FLAGS_REG))]
7420   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
7421   "sub{l}\t{%2, %k0|%k0, %2}"
7422   [(set_attr "type" "alu")
7423    (set_attr "mode" "SI")])
7424
7425 (define_insn "*subsi_2"
7426   [(set (reg FLAGS_REG)
7427         (compare
7428           (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
7429                     (match_operand:SI 2 "general_operand" "ri,rm"))
7430           (const_int 0)))
7431    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7432         (minus:SI (match_dup 1) (match_dup 2)))]
7433   "ix86_match_ccmode (insn, CCGOCmode)
7434    && ix86_binary_operator_ok (MINUS, SImode, operands)"
7435   "sub{l}\t{%2, %0|%0, %2}"
7436   [(set_attr "type" "alu")
7437    (set_attr "mode" "SI")])
7438
7439 (define_insn "*subsi_2_zext"
7440   [(set (reg FLAGS_REG)
7441         (compare
7442           (minus:SI (match_operand:SI 1 "register_operand" "0")
7443                     (match_operand:SI 2 "general_operand" "g"))
7444           (const_int 0)))
7445    (set (match_operand:DI 0 "register_operand" "=r")
7446         (zero_extend:DI
7447           (minus:SI (match_dup 1)
7448                     (match_dup 2))))]
7449   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
7450    && ix86_binary_operator_ok (MINUS, SImode, operands)"
7451   "sub{l}\t{%2, %k0|%k0, %2}"
7452   [(set_attr "type" "alu")
7453    (set_attr "mode" "SI")])
7454
7455 (define_insn "*subsi_3"
7456   [(set (reg FLAGS_REG)
7457         (compare (match_operand:SI 1 "nonimmediate_operand" "0,0")
7458                  (match_operand:SI 2 "general_operand" "ri,rm")))
7459    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7460         (minus:SI (match_dup 1) (match_dup 2)))]
7461   "ix86_match_ccmode (insn, CCmode)
7462    && ix86_binary_operator_ok (MINUS, SImode, operands)"
7463   "sub{l}\t{%2, %0|%0, %2}"
7464   [(set_attr "type" "alu")
7465    (set_attr "mode" "SI")])
7466
7467 (define_insn "*subsi_3_zext"
7468   [(set (reg FLAGS_REG)
7469         (compare (match_operand:SI 1 "register_operand" "0")
7470                  (match_operand:SI 2 "general_operand" "g")))
7471    (set (match_operand:DI 0 "register_operand" "=r")
7472         (zero_extend:DI
7473           (minus:SI (match_dup 1)
7474                     (match_dup 2))))]
7475   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
7476    && ix86_binary_operator_ok (MINUS, SImode, operands)"
7477   "sub{l}\t{%2, %1|%1, %2}"
7478   [(set_attr "type" "alu")
7479    (set_attr "mode" "DI")])
7480
7481 (define_expand "subhi3"
7482   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
7483                    (minus:HI (match_operand:HI 1 "nonimmediate_operand" "")
7484                              (match_operand:HI 2 "general_operand" "")))
7485               (clobber (reg:CC FLAGS_REG))])]
7486   "TARGET_HIMODE_MATH"
7487   "ix86_expand_binary_operator (MINUS, HImode, operands); DONE;")
7488
7489 (define_insn "*subhi_1"
7490   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7491         (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
7492                   (match_operand:HI 2 "general_operand" "ri,rm")))
7493    (clobber (reg:CC FLAGS_REG))]
7494   "ix86_binary_operator_ok (MINUS, HImode, operands)"
7495   "sub{w}\t{%2, %0|%0, %2}"
7496   [(set_attr "type" "alu")
7497    (set_attr "mode" "HI")])
7498
7499 (define_insn "*subhi_2"
7500   [(set (reg FLAGS_REG)
7501         (compare
7502           (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
7503                     (match_operand:HI 2 "general_operand" "ri,rm"))
7504           (const_int 0)))
7505    (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7506         (minus:HI (match_dup 1) (match_dup 2)))]
7507   "ix86_match_ccmode (insn, CCGOCmode)
7508    && ix86_binary_operator_ok (MINUS, HImode, operands)"
7509   "sub{w}\t{%2, %0|%0, %2}"
7510   [(set_attr "type" "alu")
7511    (set_attr "mode" "HI")])
7512
7513 (define_insn "*subhi_3"
7514   [(set (reg FLAGS_REG)
7515         (compare (match_operand:HI 1 "nonimmediate_operand" "0,0")
7516                  (match_operand:HI 2 "general_operand" "ri,rm")))
7517    (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7518         (minus:HI (match_dup 1) (match_dup 2)))]
7519   "ix86_match_ccmode (insn, CCmode)
7520    && ix86_binary_operator_ok (MINUS, HImode, operands)"
7521   "sub{w}\t{%2, %0|%0, %2}"
7522   [(set_attr "type" "alu")
7523    (set_attr "mode" "HI")])
7524
7525 (define_expand "subqi3"
7526   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
7527                    (minus:QI (match_operand:QI 1 "nonimmediate_operand" "")
7528                              (match_operand:QI 2 "general_operand" "")))
7529               (clobber (reg:CC FLAGS_REG))])]
7530   "TARGET_QIMODE_MATH"
7531   "ix86_expand_binary_operator (MINUS, QImode, operands); DONE;")
7532
7533 (define_insn "*subqi_1"
7534   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
7535         (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
7536                   (match_operand:QI 2 "general_operand" "qn,qmn")))
7537    (clobber (reg:CC FLAGS_REG))]
7538   "ix86_binary_operator_ok (MINUS, QImode, operands)"
7539   "sub{b}\t{%2, %0|%0, %2}"
7540   [(set_attr "type" "alu")
7541    (set_attr "mode" "QI")])
7542
7543 (define_insn "*subqi_1_slp"
7544   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
7545         (minus:QI (match_dup 0)
7546                   (match_operand:QI 1 "general_operand" "qn,qmn")))
7547    (clobber (reg:CC FLAGS_REG))]
7548   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
7549    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7550   "sub{b}\t{%1, %0|%0, %1}"
7551   [(set_attr "type" "alu1")
7552    (set_attr "mode" "QI")])
7553
7554 (define_insn "*subqi_2"
7555   [(set (reg FLAGS_REG)
7556         (compare
7557           (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
7558                     (match_operand:QI 2 "general_operand" "qi,qm"))
7559           (const_int 0)))
7560    (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
7561         (minus:HI (match_dup 1) (match_dup 2)))]
7562   "ix86_match_ccmode (insn, CCGOCmode)
7563    && ix86_binary_operator_ok (MINUS, QImode, operands)"
7564   "sub{b}\t{%2, %0|%0, %2}"
7565   [(set_attr "type" "alu")
7566    (set_attr "mode" "QI")])
7567
7568 (define_insn "*subqi_3"
7569   [(set (reg FLAGS_REG)
7570         (compare (match_operand:QI 1 "nonimmediate_operand" "0,0")
7571                  (match_operand:QI 2 "general_operand" "qi,qm")))
7572    (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
7573         (minus:HI (match_dup 1) (match_dup 2)))]
7574   "ix86_match_ccmode (insn, CCmode)
7575    && ix86_binary_operator_ok (MINUS, QImode, operands)"
7576   "sub{b}\t{%2, %0|%0, %2}"
7577   [(set_attr "type" "alu")
7578    (set_attr "mode" "QI")])
7579
7580 ;; The patterns that match these are at the end of this file.
7581
7582 (define_expand "subxf3"
7583   [(set (match_operand:XF 0 "register_operand" "")
7584         (minus:XF (match_operand:XF 1 "register_operand" "")
7585                   (match_operand:XF 2 "register_operand" "")))]
7586   "TARGET_80387"
7587   "")
7588
7589 (define_expand "sub<mode>3"
7590   [(set (match_operand:MODEF 0 "register_operand" "")
7591         (minus:MODEF (match_operand:MODEF 1 "register_operand" "")
7592                      (match_operand:MODEF 2 "nonimmediate_operand" "")))]
7593   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
7594   "")
7595 \f
7596 ;; Multiply instructions
7597
7598 (define_expand "muldi3"
7599   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7600                    (mult:DI (match_operand:DI 1 "register_operand" "")
7601                             (match_operand:DI 2 "x86_64_general_operand" "")))
7602               (clobber (reg:CC FLAGS_REG))])]
7603   "TARGET_64BIT"
7604   "")
7605
7606 ;; On AMDFAM10
7607 ;; IMUL reg64, reg64, imm8      Direct
7608 ;; IMUL reg64, mem64, imm8      VectorPath
7609 ;; IMUL reg64, reg64, imm32     Direct
7610 ;; IMUL reg64, mem64, imm32     VectorPath
7611 ;; IMUL reg64, reg64            Direct
7612 ;; IMUL reg64, mem64            Direct
7613
7614 (define_insn "*muldi3_1_rex64"
7615   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
7616         (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%rm,rm,0")
7617                  (match_operand:DI 2 "x86_64_general_operand" "K,e,mr")))
7618    (clobber (reg:CC FLAGS_REG))]
7619   "TARGET_64BIT
7620    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7621   "@
7622    imul{q}\t{%2, %1, %0|%0, %1, %2}
7623    imul{q}\t{%2, %1, %0|%0, %1, %2}
7624    imul{q}\t{%2, %0|%0, %2}"
7625   [(set_attr "type" "imul")
7626    (set_attr "prefix_0f" "0,0,1")
7627    (set (attr "athlon_decode")
7628         (cond [(eq_attr "cpu" "athlon")
7629                   (const_string "vector")
7630                (eq_attr "alternative" "1")
7631                   (const_string "vector")
7632                (and (eq_attr "alternative" "2")
7633                     (match_operand 1 "memory_operand" ""))
7634                   (const_string "vector")]
7635               (const_string "direct")))
7636    (set (attr "amdfam10_decode")
7637         (cond [(and (eq_attr "alternative" "0,1")
7638                     (match_operand 1 "memory_operand" ""))
7639                   (const_string "vector")]
7640               (const_string "direct")))
7641    (set_attr "mode" "DI")])
7642
7643 (define_expand "mulsi3"
7644   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7645                    (mult:SI (match_operand:SI 1 "register_operand" "")
7646                             (match_operand:SI 2 "general_operand" "")))
7647               (clobber (reg:CC FLAGS_REG))])]
7648   ""
7649   "")
7650
7651 ;; On AMDFAM10
7652 ;; IMUL reg32, reg32, imm8      Direct
7653 ;; IMUL reg32, mem32, imm8      VectorPath
7654 ;; IMUL reg32, reg32, imm32     Direct
7655 ;; IMUL reg32, mem32, imm32     VectorPath
7656 ;; IMUL reg32, reg32            Direct
7657 ;; IMUL reg32, mem32            Direct
7658
7659 (define_insn "*mulsi3_1"
7660   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
7661         (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
7662                  (match_operand:SI 2 "general_operand" "K,i,mr")))
7663    (clobber (reg:CC FLAGS_REG))]
7664   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
7665   "@
7666    imul{l}\t{%2, %1, %0|%0, %1, %2}
7667    imul{l}\t{%2, %1, %0|%0, %1, %2}
7668    imul{l}\t{%2, %0|%0, %2}"
7669   [(set_attr "type" "imul")
7670    (set_attr "prefix_0f" "0,0,1")
7671    (set (attr "athlon_decode")
7672         (cond [(eq_attr "cpu" "athlon")
7673                   (const_string "vector")
7674                (eq_attr "alternative" "1")
7675                   (const_string "vector")
7676                (and (eq_attr "alternative" "2")
7677                     (match_operand 1 "memory_operand" ""))
7678                   (const_string "vector")]
7679               (const_string "direct")))
7680    (set (attr "amdfam10_decode")
7681         (cond [(and (eq_attr "alternative" "0,1")
7682                     (match_operand 1 "memory_operand" ""))
7683                   (const_string "vector")]
7684               (const_string "direct")))
7685    (set_attr "mode" "SI")])
7686
7687 (define_insn "*mulsi3_1_zext"
7688   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
7689         (zero_extend:DI
7690           (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
7691                    (match_operand:SI 2 "general_operand" "K,i,mr"))))
7692    (clobber (reg:CC FLAGS_REG))]
7693   "TARGET_64BIT
7694    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7695   "@
7696    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
7697    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
7698    imul{l}\t{%2, %k0|%k0, %2}"
7699   [(set_attr "type" "imul")
7700    (set_attr "prefix_0f" "0,0,1")
7701    (set (attr "athlon_decode")
7702         (cond [(eq_attr "cpu" "athlon")
7703                   (const_string "vector")
7704                (eq_attr "alternative" "1")
7705                   (const_string "vector")
7706                (and (eq_attr "alternative" "2")
7707                     (match_operand 1 "memory_operand" ""))
7708                   (const_string "vector")]
7709               (const_string "direct")))
7710    (set (attr "amdfam10_decode")
7711         (cond [(and (eq_attr "alternative" "0,1")
7712                     (match_operand 1 "memory_operand" ""))
7713                   (const_string "vector")]
7714               (const_string "direct")))
7715    (set_attr "mode" "SI")])
7716
7717 (define_expand "mulhi3"
7718   [(parallel [(set (match_operand:HI 0 "register_operand" "")
7719                    (mult:HI (match_operand:HI 1 "register_operand" "")
7720                             (match_operand:HI 2 "general_operand" "")))
7721               (clobber (reg:CC FLAGS_REG))])]
7722   "TARGET_HIMODE_MATH"
7723   "")
7724
7725 ;; On AMDFAM10
7726 ;; IMUL reg16, reg16, imm8      VectorPath
7727 ;; IMUL reg16, mem16, imm8      VectorPath
7728 ;; IMUL reg16, reg16, imm16     VectorPath
7729 ;; IMUL reg16, mem16, imm16     VectorPath
7730 ;; IMUL reg16, reg16            Direct
7731 ;; IMUL reg16, mem16            Direct
7732 (define_insn "*mulhi3_1"
7733   [(set (match_operand:HI 0 "register_operand" "=r,r,r")
7734         (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
7735                  (match_operand:HI 2 "general_operand" "K,i,mr")))
7736    (clobber (reg:CC FLAGS_REG))]
7737   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
7738   "@
7739    imul{w}\t{%2, %1, %0|%0, %1, %2}
7740    imul{w}\t{%2, %1, %0|%0, %1, %2}
7741    imul{w}\t{%2, %0|%0, %2}"
7742   [(set_attr "type" "imul")
7743    (set_attr "prefix_0f" "0,0,1")
7744    (set (attr "athlon_decode")
7745         (cond [(eq_attr "cpu" "athlon")
7746                   (const_string "vector")
7747                (eq_attr "alternative" "1,2")
7748                   (const_string "vector")]
7749               (const_string "direct")))
7750    (set (attr "amdfam10_decode")
7751         (cond [(eq_attr "alternative" "0,1")
7752                   (const_string "vector")]
7753               (const_string "direct")))
7754    (set_attr "mode" "HI")])
7755
7756 (define_expand "mulqi3"
7757   [(parallel [(set (match_operand:QI 0 "register_operand" "")
7758                    (mult:QI (match_operand:QI 1 "nonimmediate_operand" "")
7759                             (match_operand:QI 2 "register_operand" "")))
7760               (clobber (reg:CC FLAGS_REG))])]
7761   "TARGET_QIMODE_MATH"
7762   "")
7763
7764 ;;On AMDFAM10
7765 ;; MUL reg8     Direct
7766 ;; MUL mem8     Direct
7767
7768 (define_insn "*mulqi3_1"
7769   [(set (match_operand:QI 0 "register_operand" "=a")
7770         (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
7771                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
7772    (clobber (reg:CC FLAGS_REG))]
7773   "TARGET_QIMODE_MATH
7774    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7775   "mul{b}\t%2"
7776   [(set_attr "type" "imul")
7777    (set_attr "length_immediate" "0")
7778    (set (attr "athlon_decode")
7779      (if_then_else (eq_attr "cpu" "athlon")
7780         (const_string "vector")
7781         (const_string "direct")))
7782    (set_attr "amdfam10_decode" "direct")
7783    (set_attr "mode" "QI")])
7784
7785 (define_expand "umulqihi3"
7786   [(parallel [(set (match_operand:HI 0 "register_operand" "")
7787                    (mult:HI (zero_extend:HI
7788                               (match_operand:QI 1 "nonimmediate_operand" ""))
7789                             (zero_extend:HI
7790                               (match_operand:QI 2 "register_operand" ""))))
7791               (clobber (reg:CC FLAGS_REG))])]
7792   "TARGET_QIMODE_MATH"
7793   "")
7794
7795 (define_insn "*umulqihi3_1"
7796   [(set (match_operand:HI 0 "register_operand" "=a")
7797         (mult:HI (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
7798                  (zero_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
7799    (clobber (reg:CC FLAGS_REG))]
7800   "TARGET_QIMODE_MATH
7801    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7802   "mul{b}\t%2"
7803   [(set_attr "type" "imul")
7804    (set_attr "length_immediate" "0")
7805    (set (attr "athlon_decode")
7806      (if_then_else (eq_attr "cpu" "athlon")
7807         (const_string "vector")
7808         (const_string "direct")))
7809    (set_attr "amdfam10_decode" "direct")
7810    (set_attr "mode" "QI")])
7811
7812 (define_expand "mulqihi3"
7813   [(parallel [(set (match_operand:HI 0 "register_operand" "")
7814                    (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))
7815                             (sign_extend:HI (match_operand:QI 2 "register_operand" ""))))
7816               (clobber (reg:CC FLAGS_REG))])]
7817   "TARGET_QIMODE_MATH"
7818   "")
7819
7820 (define_insn "*mulqihi3_insn"
7821   [(set (match_operand:HI 0 "register_operand" "=a")
7822         (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
7823                  (sign_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
7824    (clobber (reg:CC FLAGS_REG))]
7825   "TARGET_QIMODE_MATH
7826    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7827   "imul{b}\t%2"
7828   [(set_attr "type" "imul")
7829    (set_attr "length_immediate" "0")
7830    (set (attr "athlon_decode")
7831      (if_then_else (eq_attr "cpu" "athlon")
7832         (const_string "vector")
7833         (const_string "direct")))
7834    (set_attr "amdfam10_decode" "direct")
7835    (set_attr "mode" "QI")])
7836
7837 (define_expand "umulditi3"
7838   [(parallel [(set (match_operand:TI 0 "register_operand" "")
7839                    (mult:TI (zero_extend:TI
7840                               (match_operand:DI 1 "nonimmediate_operand" ""))
7841                             (zero_extend:TI
7842                               (match_operand:DI 2 "register_operand" ""))))
7843               (clobber (reg:CC FLAGS_REG))])]
7844   "TARGET_64BIT"
7845   "")
7846
7847 (define_insn "*umulditi3_insn"
7848   [(set (match_operand:TI 0 "register_operand" "=A")
7849         (mult:TI (zero_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
7850                  (zero_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
7851    (clobber (reg:CC FLAGS_REG))]
7852   "TARGET_64BIT
7853    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7854   "mul{q}\t%2"
7855   [(set_attr "type" "imul")
7856    (set_attr "length_immediate" "0")
7857    (set (attr "athlon_decode")
7858      (if_then_else (eq_attr "cpu" "athlon")
7859         (const_string "vector")
7860         (const_string "double")))
7861    (set_attr "amdfam10_decode" "double")
7862    (set_attr "mode" "DI")])
7863
7864 ;; We can't use this pattern in 64bit mode, since it results in two separate 32bit registers
7865 (define_expand "umulsidi3"
7866   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7867                    (mult:DI (zero_extend:DI
7868                               (match_operand:SI 1 "nonimmediate_operand" ""))
7869                             (zero_extend:DI
7870                               (match_operand:SI 2 "register_operand" ""))))
7871               (clobber (reg:CC FLAGS_REG))])]
7872   "!TARGET_64BIT"
7873   "")
7874
7875 (define_insn "*umulsidi3_insn"
7876   [(set (match_operand:DI 0 "register_operand" "=A")
7877         (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7878                  (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7879    (clobber (reg:CC FLAGS_REG))]
7880   "!TARGET_64BIT
7881    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7882   "mul{l}\t%2"
7883   [(set_attr "type" "imul")
7884    (set_attr "length_immediate" "0")
7885    (set (attr "athlon_decode")
7886      (if_then_else (eq_attr "cpu" "athlon")
7887         (const_string "vector")
7888         (const_string "double")))
7889    (set_attr "amdfam10_decode" "double")
7890    (set_attr "mode" "SI")])
7891
7892 (define_expand "mulditi3"
7893   [(parallel [(set (match_operand:TI 0 "register_operand" "")
7894                    (mult:TI (sign_extend:TI
7895                               (match_operand:DI 1 "nonimmediate_operand" ""))
7896                             (sign_extend:TI
7897                               (match_operand:DI 2 "register_operand" ""))))
7898               (clobber (reg:CC FLAGS_REG))])]
7899   "TARGET_64BIT"
7900   "")
7901
7902 (define_insn "*mulditi3_insn"
7903   [(set (match_operand:TI 0 "register_operand" "=A")
7904         (mult:TI (sign_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
7905                  (sign_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
7906    (clobber (reg:CC FLAGS_REG))]
7907   "TARGET_64BIT
7908    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7909   "imul{q}\t%2"
7910   [(set_attr "type" "imul")
7911    (set_attr "length_immediate" "0")
7912    (set (attr "athlon_decode")
7913      (if_then_else (eq_attr "cpu" "athlon")
7914         (const_string "vector")
7915         (const_string "double")))
7916    (set_attr "amdfam10_decode" "double")
7917    (set_attr "mode" "DI")])
7918
7919 (define_expand "mulsidi3"
7920   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7921                    (mult:DI (sign_extend:DI
7922                               (match_operand:SI 1 "nonimmediate_operand" ""))
7923                             (sign_extend:DI
7924                               (match_operand:SI 2 "register_operand" ""))))
7925               (clobber (reg:CC FLAGS_REG))])]
7926   "!TARGET_64BIT"
7927   "")
7928
7929 (define_insn "*mulsidi3_insn"
7930   [(set (match_operand:DI 0 "register_operand" "=A")
7931         (mult:DI (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7932                  (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7933    (clobber (reg:CC FLAGS_REG))]
7934   "!TARGET_64BIT
7935    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7936   "imul{l}\t%2"
7937   [(set_attr "type" "imul")
7938    (set_attr "length_immediate" "0")
7939    (set (attr "athlon_decode")
7940      (if_then_else (eq_attr "cpu" "athlon")
7941         (const_string "vector")
7942         (const_string "double")))
7943    (set_attr "amdfam10_decode" "double")
7944    (set_attr "mode" "SI")])
7945
7946 (define_expand "umuldi3_highpart"
7947   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7948                    (truncate:DI
7949                      (lshiftrt:TI
7950                        (mult:TI (zero_extend:TI
7951                                   (match_operand:DI 1 "nonimmediate_operand" ""))
7952                                 (zero_extend:TI
7953                                   (match_operand:DI 2 "register_operand" "")))
7954                        (const_int 64))))
7955               (clobber (match_scratch:DI 3 ""))
7956               (clobber (reg:CC FLAGS_REG))])]
7957   "TARGET_64BIT"
7958   "")
7959
7960 (define_insn "*umuldi3_highpart_rex64"
7961   [(set (match_operand:DI 0 "register_operand" "=d")
7962         (truncate:DI
7963           (lshiftrt:TI
7964             (mult:TI (zero_extend:TI
7965                        (match_operand:DI 1 "nonimmediate_operand" "%a"))
7966                      (zero_extend:TI
7967                        (match_operand:DI 2 "nonimmediate_operand" "rm")))
7968             (const_int 64))))
7969    (clobber (match_scratch:DI 3 "=1"))
7970    (clobber (reg:CC FLAGS_REG))]
7971   "TARGET_64BIT
7972    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7973   "mul{q}\t%2"
7974   [(set_attr "type" "imul")
7975    (set_attr "length_immediate" "0")
7976    (set (attr "athlon_decode")
7977      (if_then_else (eq_attr "cpu" "athlon")
7978         (const_string "vector")
7979         (const_string "double")))
7980    (set_attr "amdfam10_decode" "double")
7981    (set_attr "mode" "DI")])
7982
7983 (define_expand "umulsi3_highpart"
7984   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7985                    (truncate:SI
7986                      (lshiftrt:DI
7987                        (mult:DI (zero_extend:DI
7988                                   (match_operand:SI 1 "nonimmediate_operand" ""))
7989                                 (zero_extend:DI
7990                                   (match_operand:SI 2 "register_operand" "")))
7991                        (const_int 32))))
7992               (clobber (match_scratch:SI 3 ""))
7993               (clobber (reg:CC FLAGS_REG))])]
7994   ""
7995   "")
7996
7997 (define_insn "*umulsi3_highpart_insn"
7998   [(set (match_operand:SI 0 "register_operand" "=d")
7999         (truncate:SI
8000           (lshiftrt:DI
8001             (mult:DI (zero_extend:DI
8002                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
8003                      (zero_extend:DI
8004                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
8005             (const_int 32))))
8006    (clobber (match_scratch:SI 3 "=1"))
8007    (clobber (reg:CC FLAGS_REG))]
8008   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
8009   "mul{l}\t%2"
8010   [(set_attr "type" "imul")
8011    (set_attr "length_immediate" "0")
8012    (set (attr "athlon_decode")
8013      (if_then_else (eq_attr "cpu" "athlon")
8014         (const_string "vector")
8015         (const_string "double")))
8016    (set_attr "amdfam10_decode" "double")
8017    (set_attr "mode" "SI")])
8018
8019 (define_insn "*umulsi3_highpart_zext"
8020   [(set (match_operand:DI 0 "register_operand" "=d")
8021         (zero_extend:DI (truncate:SI
8022           (lshiftrt:DI
8023             (mult:DI (zero_extend:DI
8024                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
8025                      (zero_extend:DI
8026                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
8027             (const_int 32)))))
8028    (clobber (match_scratch:SI 3 "=1"))
8029    (clobber (reg:CC FLAGS_REG))]
8030   "TARGET_64BIT
8031    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8032   "mul{l}\t%2"
8033   [(set_attr "type" "imul")
8034    (set_attr "length_immediate" "0")
8035    (set (attr "athlon_decode")
8036      (if_then_else (eq_attr "cpu" "athlon")
8037         (const_string "vector")
8038         (const_string "double")))
8039    (set_attr "amdfam10_decode" "double")
8040    (set_attr "mode" "SI")])
8041
8042 (define_expand "smuldi3_highpart"
8043   [(parallel [(set (match_operand:DI 0 "register_operand" "")
8044                    (truncate:DI
8045                      (lshiftrt:TI
8046                        (mult:TI (sign_extend:TI
8047                                   (match_operand:DI 1 "nonimmediate_operand" ""))
8048                                 (sign_extend:TI
8049                                   (match_operand:DI 2 "register_operand" "")))
8050                        (const_int 64))))
8051               (clobber (match_scratch:DI 3 ""))
8052               (clobber (reg:CC FLAGS_REG))])]
8053   "TARGET_64BIT"
8054   "")
8055
8056 (define_insn "*smuldi3_highpart_rex64"
8057   [(set (match_operand:DI 0 "register_operand" "=d")
8058         (truncate:DI
8059           (lshiftrt:TI
8060             (mult:TI (sign_extend:TI
8061                        (match_operand:DI 1 "nonimmediate_operand" "%a"))
8062                      (sign_extend:TI
8063                        (match_operand:DI 2 "nonimmediate_operand" "rm")))
8064             (const_int 64))))
8065    (clobber (match_scratch:DI 3 "=1"))
8066    (clobber (reg:CC FLAGS_REG))]
8067   "TARGET_64BIT
8068    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8069   "imul{q}\t%2"
8070   [(set_attr "type" "imul")
8071    (set (attr "athlon_decode")
8072      (if_then_else (eq_attr "cpu" "athlon")
8073         (const_string "vector")
8074         (const_string "double")))
8075    (set_attr "amdfam10_decode" "double")
8076    (set_attr "mode" "DI")])
8077
8078 (define_expand "smulsi3_highpart"
8079   [(parallel [(set (match_operand:SI 0 "register_operand" "")
8080                    (truncate:SI
8081                      (lshiftrt:DI
8082                        (mult:DI (sign_extend:DI
8083                                   (match_operand:SI 1 "nonimmediate_operand" ""))
8084                                 (sign_extend:DI
8085                                   (match_operand:SI 2 "register_operand" "")))
8086                        (const_int 32))))
8087               (clobber (match_scratch:SI 3 ""))
8088               (clobber (reg:CC FLAGS_REG))])]
8089   ""
8090   "")
8091
8092 (define_insn "*smulsi3_highpart_insn"
8093   [(set (match_operand:SI 0 "register_operand" "=d")
8094         (truncate:SI
8095           (lshiftrt:DI
8096             (mult:DI (sign_extend:DI
8097                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
8098                      (sign_extend:DI
8099                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
8100             (const_int 32))))
8101    (clobber (match_scratch:SI 3 "=1"))
8102    (clobber (reg:CC FLAGS_REG))]
8103   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
8104   "imul{l}\t%2"
8105   [(set_attr "type" "imul")
8106    (set (attr "athlon_decode")
8107      (if_then_else (eq_attr "cpu" "athlon")
8108         (const_string "vector")
8109         (const_string "double")))
8110    (set_attr "amdfam10_decode" "double")
8111    (set_attr "mode" "SI")])
8112
8113 (define_insn "*smulsi3_highpart_zext"
8114   [(set (match_operand:DI 0 "register_operand" "=d")
8115         (zero_extend:DI (truncate:SI
8116           (lshiftrt:DI
8117             (mult:DI (sign_extend:DI
8118                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
8119                      (sign_extend:DI
8120                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
8121             (const_int 32)))))
8122    (clobber (match_scratch:SI 3 "=1"))
8123    (clobber (reg:CC FLAGS_REG))]
8124   "TARGET_64BIT
8125    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8126   "imul{l}\t%2"
8127   [(set_attr "type" "imul")
8128    (set (attr "athlon_decode")
8129      (if_then_else (eq_attr "cpu" "athlon")
8130         (const_string "vector")
8131         (const_string "double")))
8132    (set_attr "amdfam10_decode" "double")
8133    (set_attr "mode" "SI")])
8134
8135 ;; The patterns that match these are at the end of this file.
8136
8137 (define_expand "mulxf3"
8138   [(set (match_operand:XF 0 "register_operand" "")
8139         (mult:XF (match_operand:XF 1 "register_operand" "")
8140                  (match_operand:XF 2 "register_operand" "")))]
8141   "TARGET_80387"
8142   "")
8143
8144 (define_expand "mul<mode>3"
8145   [(set (match_operand:MODEF 0 "register_operand" "")
8146         (mult:MODEF (match_operand:MODEF 1 "register_operand" "")
8147                     (match_operand:MODEF 2 "nonimmediate_operand" "")))]
8148   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
8149   "")
8150
8151 ;; SSE5 scalar multiply/add instructions are defined in sse.md.
8152
8153 \f
8154 ;; Divide instructions
8155
8156 (define_insn "divqi3"
8157   [(set (match_operand:QI 0 "register_operand" "=a")
8158         (div:QI (match_operand:HI 1 "register_operand" "0")
8159                 (match_operand:QI 2 "nonimmediate_operand" "qm")))
8160    (clobber (reg:CC FLAGS_REG))]
8161   "TARGET_QIMODE_MATH"
8162   "idiv{b}\t%2"
8163   [(set_attr "type" "idiv")
8164    (set_attr "mode" "QI")])
8165
8166 (define_insn "udivqi3"
8167   [(set (match_operand:QI 0 "register_operand" "=a")
8168         (udiv:QI (match_operand:HI 1 "register_operand" "0")
8169                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
8170    (clobber (reg:CC FLAGS_REG))]
8171   "TARGET_QIMODE_MATH"
8172   "div{b}\t%2"
8173   [(set_attr "type" "idiv")
8174    (set_attr "mode" "QI")])
8175
8176 ;; The patterns that match these are at the end of this file.
8177
8178 (define_expand "divxf3"
8179   [(set (match_operand:XF 0 "register_operand" "")
8180         (div:XF (match_operand:XF 1 "register_operand" "")
8181                 (match_operand:XF 2 "register_operand" "")))]
8182   "TARGET_80387"
8183   "")
8184
8185 (define_expand "divdf3"
8186   [(set (match_operand:DF 0 "register_operand" "")
8187         (div:DF (match_operand:DF 1 "register_operand" "")
8188                 (match_operand:DF 2 "nonimmediate_operand" "")))]
8189    "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
8190    "")
8191
8192 (define_expand "divsf3"
8193   [(set (match_operand:SF 0 "register_operand" "")
8194         (div:SF (match_operand:SF 1 "register_operand" "")
8195                 (match_operand:SF 2 "nonimmediate_operand" "")))]
8196   "TARGET_80387 || TARGET_SSE_MATH"
8197 {
8198   if (TARGET_SSE_MATH && TARGET_RECIP && !optimize_size
8199       && flag_finite_math_only && !flag_trapping_math
8200       && flag_unsafe_math_optimizations)
8201     {
8202       ix86_emit_swdivsf (operands[0], operands[1],
8203                          operands[2], SFmode);
8204       DONE;
8205     }
8206 })
8207 \f
8208 ;; Remainder instructions.
8209
8210 (define_expand "divmoddi4"
8211   [(parallel [(set (match_operand:DI 0 "register_operand" "")
8212                    (div:DI (match_operand:DI 1 "register_operand" "")
8213                            (match_operand:DI 2 "nonimmediate_operand" "")))
8214               (set (match_operand:DI 3 "register_operand" "")
8215                    (mod:DI (match_dup 1) (match_dup 2)))
8216               (clobber (reg:CC FLAGS_REG))])]
8217   "TARGET_64BIT"
8218   "")
8219
8220 ;; Allow to come the parameter in eax or edx to avoid extra moves.
8221 ;; Penalize eax case slightly because it results in worse scheduling
8222 ;; of code.
8223 (define_insn "*divmoddi4_nocltd_rex64"
8224   [(set (match_operand:DI 0 "register_operand" "=&a,?a")
8225         (div:DI (match_operand:DI 2 "register_operand" "1,0")
8226                 (match_operand:DI 3 "nonimmediate_operand" "rm,rm")))
8227    (set (match_operand:DI 1 "register_operand" "=&d,&d")
8228         (mod:DI (match_dup 2) (match_dup 3)))
8229    (clobber (reg:CC FLAGS_REG))]
8230   "TARGET_64BIT && !optimize_size && !TARGET_USE_CLTD"
8231   "#"
8232   [(set_attr "type" "multi")])
8233
8234 (define_insn "*divmoddi4_cltd_rex64"
8235   [(set (match_operand:DI 0 "register_operand" "=a")
8236         (div:DI (match_operand:DI 2 "register_operand" "a")
8237                 (match_operand:DI 3 "nonimmediate_operand" "rm")))
8238    (set (match_operand:DI 1 "register_operand" "=&d")
8239         (mod:DI (match_dup 2) (match_dup 3)))
8240    (clobber (reg:CC FLAGS_REG))]
8241   "TARGET_64BIT && (optimize_size || TARGET_USE_CLTD)"
8242   "#"
8243   [(set_attr "type" "multi")])
8244
8245 (define_insn "*divmoddi_noext_rex64"
8246   [(set (match_operand:DI 0 "register_operand" "=a")
8247         (div:DI (match_operand:DI 1 "register_operand" "0")
8248                 (match_operand:DI 2 "nonimmediate_operand" "rm")))
8249    (set (match_operand:DI 3 "register_operand" "=d")
8250         (mod:DI (match_dup 1) (match_dup 2)))
8251    (use (match_operand:DI 4 "register_operand" "3"))
8252    (clobber (reg:CC FLAGS_REG))]
8253   "TARGET_64BIT"
8254   "idiv{q}\t%2"
8255   [(set_attr "type" "idiv")
8256    (set_attr "mode" "DI")])
8257
8258 (define_split
8259   [(set (match_operand:DI 0 "register_operand" "")
8260         (div:DI (match_operand:DI 1 "register_operand" "")
8261                 (match_operand:DI 2 "nonimmediate_operand" "")))
8262    (set (match_operand:DI 3 "register_operand" "")
8263         (mod:DI (match_dup 1) (match_dup 2)))
8264    (clobber (reg:CC FLAGS_REG))]
8265   "TARGET_64BIT && reload_completed"
8266   [(parallel [(set (match_dup 3)
8267                    (ashiftrt:DI (match_dup 4) (const_int 63)))
8268               (clobber (reg:CC FLAGS_REG))])
8269    (parallel [(set (match_dup 0)
8270                    (div:DI (reg:DI 0) (match_dup 2)))
8271               (set (match_dup 3)
8272                    (mod:DI (reg:DI 0) (match_dup 2)))
8273               (use (match_dup 3))
8274               (clobber (reg:CC FLAGS_REG))])]
8275 {
8276   /* Avoid use of cltd in favor of a mov+shift.  */
8277   if (!TARGET_USE_CLTD && !optimize_size)
8278     {
8279       if (true_regnum (operands[1]))
8280         emit_move_insn (operands[0], operands[1]);
8281       else
8282         emit_move_insn (operands[3], operands[1]);
8283       operands[4] = operands[3];
8284     }
8285   else
8286     {
8287       gcc_assert (!true_regnum (operands[1]));
8288       operands[4] = operands[1];
8289     }
8290 })
8291
8292
8293 (define_expand "divmodsi4"
8294   [(parallel [(set (match_operand:SI 0 "register_operand" "")
8295                    (div:SI (match_operand:SI 1 "register_operand" "")
8296                            (match_operand:SI 2 "nonimmediate_operand" "")))
8297               (set (match_operand:SI 3 "register_operand" "")
8298                    (mod:SI (match_dup 1) (match_dup 2)))
8299               (clobber (reg:CC FLAGS_REG))])]
8300   ""
8301   "")
8302
8303 ;; Allow to come the parameter in eax or edx to avoid extra moves.
8304 ;; Penalize eax case slightly because it results in worse scheduling
8305 ;; of code.
8306 (define_insn "*divmodsi4_nocltd"
8307   [(set (match_operand:SI 0 "register_operand" "=&a,?a")
8308         (div:SI (match_operand:SI 2 "register_operand" "1,0")
8309                 (match_operand:SI 3 "nonimmediate_operand" "rm,rm")))
8310    (set (match_operand:SI 1 "register_operand" "=&d,&d")
8311         (mod:SI (match_dup 2) (match_dup 3)))
8312    (clobber (reg:CC FLAGS_REG))]
8313   "!optimize_size && !TARGET_USE_CLTD"
8314   "#"
8315   [(set_attr "type" "multi")])
8316
8317 (define_insn "*divmodsi4_cltd"
8318   [(set (match_operand:SI 0 "register_operand" "=a")
8319         (div:SI (match_operand:SI 2 "register_operand" "a")
8320                 (match_operand:SI 3 "nonimmediate_operand" "rm")))
8321    (set (match_operand:SI 1 "register_operand" "=&d")
8322         (mod:SI (match_dup 2) (match_dup 3)))
8323    (clobber (reg:CC FLAGS_REG))]
8324   "optimize_size || TARGET_USE_CLTD"
8325   "#"
8326   [(set_attr "type" "multi")])
8327
8328 (define_insn "*divmodsi_noext"
8329   [(set (match_operand:SI 0 "register_operand" "=a")
8330         (div:SI (match_operand:SI 1 "register_operand" "0")
8331                 (match_operand:SI 2 "nonimmediate_operand" "rm")))
8332    (set (match_operand:SI 3 "register_operand" "=d")
8333         (mod:SI (match_dup 1) (match_dup 2)))
8334    (use (match_operand:SI 4 "register_operand" "3"))
8335    (clobber (reg:CC FLAGS_REG))]
8336   ""
8337   "idiv{l}\t%2"
8338   [(set_attr "type" "idiv")
8339    (set_attr "mode" "SI")])
8340
8341 (define_split
8342   [(set (match_operand:SI 0 "register_operand" "")
8343         (div:SI (match_operand:SI 1 "register_operand" "")
8344                 (match_operand:SI 2 "nonimmediate_operand" "")))
8345    (set (match_operand:SI 3 "register_operand" "")
8346         (mod:SI (match_dup 1) (match_dup 2)))
8347    (clobber (reg:CC FLAGS_REG))]
8348   "reload_completed"
8349   [(parallel [(set (match_dup 3)
8350                    (ashiftrt:SI (match_dup 4) (const_int 31)))
8351               (clobber (reg:CC FLAGS_REG))])
8352    (parallel [(set (match_dup 0)
8353                    (div:SI (reg:SI 0) (match_dup 2)))
8354               (set (match_dup 3)
8355                    (mod:SI (reg:SI 0) (match_dup 2)))
8356               (use (match_dup 3))
8357               (clobber (reg:CC FLAGS_REG))])]
8358 {
8359   /* Avoid use of cltd in favor of a mov+shift.  */
8360   if (!TARGET_USE_CLTD && !optimize_size)
8361     {
8362       if (true_regnum (operands[1]))
8363         emit_move_insn (operands[0], operands[1]);
8364       else
8365         emit_move_insn (operands[3], operands[1]);
8366       operands[4] = operands[3];
8367     }
8368   else
8369     {
8370       gcc_assert (!true_regnum (operands[1]));
8371       operands[4] = operands[1];
8372     }
8373 })
8374 ;; %%% Split me.
8375 (define_insn "divmodhi4"
8376   [(set (match_operand:HI 0 "register_operand" "=a")
8377         (div:HI (match_operand:HI 1 "register_operand" "0")
8378                 (match_operand:HI 2 "nonimmediate_operand" "rm")))
8379    (set (match_operand:HI 3 "register_operand" "=&d")
8380         (mod:HI (match_dup 1) (match_dup 2)))
8381    (clobber (reg:CC FLAGS_REG))]
8382   "TARGET_HIMODE_MATH"
8383   "cwtd\;idiv{w}\t%2"
8384   [(set_attr "type" "multi")
8385    (set_attr "length_immediate" "0")
8386    (set_attr "mode" "SI")])
8387
8388 (define_insn "udivmoddi4"
8389   [(set (match_operand:DI 0 "register_operand" "=a")
8390         (udiv:DI (match_operand:DI 1 "register_operand" "0")
8391                  (match_operand:DI 2 "nonimmediate_operand" "rm")))
8392    (set (match_operand:DI 3 "register_operand" "=&d")
8393         (umod:DI (match_dup 1) (match_dup 2)))
8394    (clobber (reg:CC FLAGS_REG))]
8395   "TARGET_64BIT"
8396   "xor{q}\t%3, %3\;div{q}\t%2"
8397   [(set_attr "type" "multi")
8398    (set_attr "length_immediate" "0")
8399    (set_attr "mode" "DI")])
8400
8401 (define_insn "*udivmoddi4_noext"
8402   [(set (match_operand:DI 0 "register_operand" "=a")
8403         (udiv:DI (match_operand:DI 1 "register_operand" "0")
8404                  (match_operand:DI 2 "nonimmediate_operand" "rm")))
8405    (set (match_operand:DI 3 "register_operand" "=d")
8406         (umod:DI (match_dup 1) (match_dup 2)))
8407    (use (match_dup 3))
8408    (clobber (reg:CC FLAGS_REG))]
8409   "TARGET_64BIT"
8410   "div{q}\t%2"
8411   [(set_attr "type" "idiv")
8412    (set_attr "mode" "DI")])
8413
8414 (define_split
8415   [(set (match_operand:DI 0 "register_operand" "")
8416         (udiv:DI (match_operand:DI 1 "register_operand" "")
8417                  (match_operand:DI 2 "nonimmediate_operand" "")))
8418    (set (match_operand:DI 3 "register_operand" "")
8419         (umod:DI (match_dup 1) (match_dup 2)))
8420    (clobber (reg:CC FLAGS_REG))]
8421   "TARGET_64BIT && reload_completed"
8422   [(set (match_dup 3) (const_int 0))
8423    (parallel [(set (match_dup 0)
8424                    (udiv:DI (match_dup 1) (match_dup 2)))
8425               (set (match_dup 3)
8426                    (umod:DI (match_dup 1) (match_dup 2)))
8427               (use (match_dup 3))
8428               (clobber (reg:CC FLAGS_REG))])]
8429   "")
8430
8431 (define_insn "udivmodsi4"
8432   [(set (match_operand:SI 0 "register_operand" "=a")
8433         (udiv:SI (match_operand:SI 1 "register_operand" "0")
8434                  (match_operand:SI 2 "nonimmediate_operand" "rm")))
8435    (set (match_operand:SI 3 "register_operand" "=&d")
8436         (umod:SI (match_dup 1) (match_dup 2)))
8437    (clobber (reg:CC FLAGS_REG))]
8438   ""
8439   "xor{l}\t%3, %3\;div{l}\t%2"
8440   [(set_attr "type" "multi")
8441    (set_attr "length_immediate" "0")
8442    (set_attr "mode" "SI")])
8443
8444 (define_insn "*udivmodsi4_noext"
8445   [(set (match_operand:SI 0 "register_operand" "=a")
8446         (udiv:SI (match_operand:SI 1 "register_operand" "0")
8447                  (match_operand:SI 2 "nonimmediate_operand" "rm")))
8448    (set (match_operand:SI 3 "register_operand" "=d")
8449         (umod:SI (match_dup 1) (match_dup 2)))
8450    (use (match_dup 3))
8451    (clobber (reg:CC FLAGS_REG))]
8452   ""
8453   "div{l}\t%2"
8454   [(set_attr "type" "idiv")
8455    (set_attr "mode" "SI")])
8456
8457 (define_split
8458   [(set (match_operand:SI 0 "register_operand" "")
8459         (udiv:SI (match_operand:SI 1 "register_operand" "")
8460                  (match_operand:SI 2 "nonimmediate_operand" "")))
8461    (set (match_operand:SI 3 "register_operand" "")
8462         (umod:SI (match_dup 1) (match_dup 2)))
8463    (clobber (reg:CC FLAGS_REG))]
8464   "reload_completed"
8465   [(set (match_dup 3) (const_int 0))
8466    (parallel [(set (match_dup 0)
8467                    (udiv:SI (match_dup 1) (match_dup 2)))
8468               (set (match_dup 3)
8469                    (umod:SI (match_dup 1) (match_dup 2)))
8470               (use (match_dup 3))
8471               (clobber (reg:CC FLAGS_REG))])]
8472   "")
8473
8474 (define_expand "udivmodhi4"
8475   [(set (match_dup 4) (const_int 0))
8476    (parallel [(set (match_operand:HI 0 "register_operand" "")
8477                    (udiv:HI (match_operand:HI 1 "register_operand" "")
8478                             (match_operand:HI 2 "nonimmediate_operand" "")))
8479               (set (match_operand:HI 3 "register_operand" "")
8480                    (umod:HI (match_dup 1) (match_dup 2)))
8481               (use (match_dup 4))
8482               (clobber (reg:CC FLAGS_REG))])]
8483   "TARGET_HIMODE_MATH"
8484   "operands[4] = gen_reg_rtx (HImode);")
8485
8486 (define_insn "*udivmodhi_noext"
8487   [(set (match_operand:HI 0 "register_operand" "=a")
8488         (udiv:HI (match_operand:HI 1 "register_operand" "0")
8489                  (match_operand:HI 2 "nonimmediate_operand" "rm")))
8490    (set (match_operand:HI 3 "register_operand" "=d")
8491         (umod:HI (match_dup 1) (match_dup 2)))
8492    (use (match_operand:HI 4 "register_operand" "3"))
8493    (clobber (reg:CC FLAGS_REG))]
8494   ""
8495   "div{w}\t%2"
8496   [(set_attr "type" "idiv")
8497    (set_attr "mode" "HI")])
8498
8499 ;; We cannot use div/idiv for double division, because it causes
8500 ;; "division by zero" on the overflow and that's not what we expect
8501 ;; from truncate.  Because true (non truncating) double division is
8502 ;; never generated, we can't create this insn anyway.
8503 ;
8504 ;(define_insn ""
8505 ;  [(set (match_operand:SI 0 "register_operand" "=a")
8506 ;       (truncate:SI
8507 ;         (udiv:DI (match_operand:DI 1 "register_operand" "A")
8508 ;                  (zero_extend:DI
8509 ;                    (match_operand:SI 2 "nonimmediate_operand" "rm")))))
8510 ;   (set (match_operand:SI 3 "register_operand" "=d")
8511 ;       (truncate:SI
8512 ;         (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
8513 ;   (clobber (reg:CC FLAGS_REG))]
8514 ;  ""
8515 ;  "div{l}\t{%2, %0|%0, %2}"
8516 ;  [(set_attr "type" "idiv")])
8517 \f
8518 ;;- Logical AND instructions
8519
8520 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
8521 ;; Note that this excludes ah.
8522
8523 (define_insn "*testdi_1_rex64"
8524   [(set (reg FLAGS_REG)
8525         (compare
8526           (and:DI (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
8527                   (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
8528           (const_int 0)))]
8529   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8530    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8531   "@
8532    test{l}\t{%k1, %k0|%k0, %k1}
8533    test{l}\t{%k1, %k0|%k0, %k1}
8534    test{q}\t{%1, %0|%0, %1}
8535    test{q}\t{%1, %0|%0, %1}
8536    test{q}\t{%1, %0|%0, %1}"
8537   [(set_attr "type" "test")
8538    (set_attr "modrm" "0,1,0,1,1")
8539    (set_attr "mode" "SI,SI,DI,DI,DI")
8540    (set_attr "pent_pair" "uv,np,uv,np,uv")])
8541
8542 (define_insn "testsi_1"
8543   [(set (reg FLAGS_REG)
8544         (compare
8545           (and:SI (match_operand:SI 0 "nonimmediate_operand" "%!*a,r,rm")
8546                   (match_operand:SI 1 "general_operand" "in,in,rin"))
8547           (const_int 0)))]
8548   "ix86_match_ccmode (insn, CCNOmode)
8549    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8550   "test{l}\t{%1, %0|%0, %1}"
8551   [(set_attr "type" "test")
8552    (set_attr "modrm" "0,1,1")
8553    (set_attr "mode" "SI")
8554    (set_attr "pent_pair" "uv,np,uv")])
8555
8556 (define_expand "testsi_ccno_1"
8557   [(set (reg:CCNO FLAGS_REG)
8558         (compare:CCNO
8559           (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
8560                   (match_operand:SI 1 "nonmemory_operand" ""))
8561           (const_int 0)))]
8562   ""
8563   "")
8564
8565 (define_insn "*testhi_1"
8566   [(set (reg FLAGS_REG)
8567         (compare (and:HI (match_operand:HI 0 "nonimmediate_operand" "%!*a,r,rm")
8568                          (match_operand:HI 1 "general_operand" "n,n,rn"))
8569                  (const_int 0)))]
8570   "ix86_match_ccmode (insn, CCNOmode)
8571    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8572   "test{w}\t{%1, %0|%0, %1}"
8573   [(set_attr "type" "test")
8574    (set_attr "modrm" "0,1,1")
8575    (set_attr "mode" "HI")
8576    (set_attr "pent_pair" "uv,np,uv")])
8577
8578 (define_expand "testqi_ccz_1"
8579   [(set (reg:CCZ FLAGS_REG)
8580         (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
8581                              (match_operand:QI 1 "nonmemory_operand" ""))
8582                  (const_int 0)))]
8583   ""
8584   "")
8585
8586 (define_insn "*testqi_1_maybe_si"
8587   [(set (reg FLAGS_REG)
8588         (compare
8589           (and:QI
8590             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
8591             (match_operand:QI 1 "general_operand" "n,n,qn,n"))
8592           (const_int 0)))]
8593    "!(MEM_P (operands[0]) && MEM_P (operands[1]))
8594     && ix86_match_ccmode (insn,
8595                          CONST_INT_P (operands[1])
8596                          && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
8597 {
8598   if (which_alternative == 3)
8599     {
8600       if (CONST_INT_P (operands[1]) && INTVAL (operands[1]) < 0)
8601         operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
8602       return "test{l}\t{%1, %k0|%k0, %1}";
8603     }
8604   return "test{b}\t{%1, %0|%0, %1}";
8605 }
8606   [(set_attr "type" "test")
8607    (set_attr "modrm" "0,1,1,1")
8608    (set_attr "mode" "QI,QI,QI,SI")
8609    (set_attr "pent_pair" "uv,np,uv,np")])
8610
8611 (define_insn "*testqi_1"
8612   [(set (reg FLAGS_REG)
8613         (compare
8614           (and:QI
8615             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm")
8616             (match_operand:QI 1 "general_operand" "n,n,qn"))
8617           (const_int 0)))]
8618   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
8619    && ix86_match_ccmode (insn, CCNOmode)"
8620   "test{b}\t{%1, %0|%0, %1}"
8621   [(set_attr "type" "test")
8622    (set_attr "modrm" "0,1,1")
8623    (set_attr "mode" "QI")
8624    (set_attr "pent_pair" "uv,np,uv")])
8625
8626 (define_expand "testqi_ext_ccno_0"
8627   [(set (reg:CCNO FLAGS_REG)
8628         (compare:CCNO
8629           (and:SI
8630             (zero_extract:SI
8631               (match_operand 0 "ext_register_operand" "")
8632               (const_int 8)
8633               (const_int 8))
8634             (match_operand 1 "const_int_operand" ""))
8635           (const_int 0)))]
8636   ""
8637   "")
8638
8639 (define_insn "*testqi_ext_0"
8640   [(set (reg FLAGS_REG)
8641         (compare
8642           (and:SI
8643             (zero_extract:SI
8644               (match_operand 0 "ext_register_operand" "Q")
8645               (const_int 8)
8646               (const_int 8))
8647             (match_operand 1 "const_int_operand" "n"))
8648           (const_int 0)))]
8649   "ix86_match_ccmode (insn, CCNOmode)"
8650   "test{b}\t{%1, %h0|%h0, %1}"
8651   [(set_attr "type" "test")
8652    (set_attr "mode" "QI")
8653    (set_attr "length_immediate" "1")
8654    (set_attr "pent_pair" "np")])
8655
8656 (define_insn "*testqi_ext_1"
8657   [(set (reg FLAGS_REG)
8658         (compare
8659           (and:SI
8660             (zero_extract:SI
8661               (match_operand 0 "ext_register_operand" "Q")
8662               (const_int 8)
8663               (const_int 8))
8664             (zero_extend:SI
8665               (match_operand:QI 1 "general_operand" "Qm")))
8666           (const_int 0)))]
8667   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8668    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8669   "test{b}\t{%1, %h0|%h0, %1}"
8670   [(set_attr "type" "test")
8671    (set_attr "mode" "QI")])
8672
8673 (define_insn "*testqi_ext_1_rex64"
8674   [(set (reg FLAGS_REG)
8675         (compare
8676           (and:SI
8677             (zero_extract:SI
8678               (match_operand 0 "ext_register_operand" "Q")
8679               (const_int 8)
8680               (const_int 8))
8681             (zero_extend:SI
8682               (match_operand:QI 1 "register_operand" "Q")))
8683           (const_int 0)))]
8684   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
8685   "test{b}\t{%1, %h0|%h0, %1}"
8686   [(set_attr "type" "test")
8687    (set_attr "mode" "QI")])
8688
8689 (define_insn "*testqi_ext_2"
8690   [(set (reg FLAGS_REG)
8691         (compare
8692           (and:SI
8693             (zero_extract:SI
8694               (match_operand 0 "ext_register_operand" "Q")
8695               (const_int 8)
8696               (const_int 8))
8697             (zero_extract:SI
8698               (match_operand 1 "ext_register_operand" "Q")
8699               (const_int 8)
8700               (const_int 8)))
8701           (const_int 0)))]
8702   "ix86_match_ccmode (insn, CCNOmode)"
8703   "test{b}\t{%h1, %h0|%h0, %h1}"
8704   [(set_attr "type" "test")
8705    (set_attr "mode" "QI")])
8706
8707 ;; Combine likes to form bit extractions for some tests.  Humor it.
8708 (define_insn "*testqi_ext_3"
8709   [(set (reg FLAGS_REG)
8710         (compare (zero_extract:SI
8711                    (match_operand 0 "nonimmediate_operand" "rm")
8712                    (match_operand:SI 1 "const_int_operand" "")
8713                    (match_operand:SI 2 "const_int_operand" ""))
8714                  (const_int 0)))]
8715   "ix86_match_ccmode (insn, CCNOmode)
8716    && INTVAL (operands[1]) > 0
8717    && INTVAL (operands[2]) >= 0
8718    && INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
8719    && (GET_MODE (operands[0]) == SImode
8720        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
8721        || GET_MODE (operands[0]) == HImode
8722        || GET_MODE (operands[0]) == QImode)"
8723   "#")
8724
8725 (define_insn "*testqi_ext_3_rex64"
8726   [(set (reg FLAGS_REG)
8727         (compare (zero_extract:DI
8728                    (match_operand 0 "nonimmediate_operand" "rm")
8729                    (match_operand:DI 1 "const_int_operand" "")
8730                    (match_operand:DI 2 "const_int_operand" ""))
8731                  (const_int 0)))]
8732   "TARGET_64BIT
8733    && ix86_match_ccmode (insn, CCNOmode)
8734    && INTVAL (operands[1]) > 0
8735    && INTVAL (operands[2]) >= 0
8736    /* Ensure that resulting mask is zero or sign extended operand.  */
8737    && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
8738        || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
8739            && INTVAL (operands[1]) > 32))
8740    && (GET_MODE (operands[0]) == SImode
8741        || GET_MODE (operands[0]) == DImode
8742        || GET_MODE (operands[0]) == HImode
8743        || GET_MODE (operands[0]) == QImode)"
8744   "#")
8745
8746 (define_split
8747   [(set (match_operand 0 "flags_reg_operand" "")
8748         (match_operator 1 "compare_operator"
8749           [(zero_extract
8750              (match_operand 2 "nonimmediate_operand" "")
8751              (match_operand 3 "const_int_operand" "")
8752              (match_operand 4 "const_int_operand" ""))
8753            (const_int 0)]))]
8754   "ix86_match_ccmode (insn, CCNOmode)"
8755   [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
8756 {
8757   rtx val = operands[2];
8758   HOST_WIDE_INT len = INTVAL (operands[3]);
8759   HOST_WIDE_INT pos = INTVAL (operands[4]);
8760   HOST_WIDE_INT mask;
8761   enum machine_mode mode, submode;
8762
8763   mode = GET_MODE (val);
8764   if (MEM_P (val))
8765     {
8766       /* ??? Combine likes to put non-volatile mem extractions in QImode
8767          no matter the size of the test.  So find a mode that works.  */
8768       if (! MEM_VOLATILE_P (val))
8769         {
8770           mode = smallest_mode_for_size (pos + len, MODE_INT);
8771           val = adjust_address (val, mode, 0);
8772         }
8773     }
8774   else if (GET_CODE (val) == SUBREG
8775            && (submode = GET_MODE (SUBREG_REG (val)),
8776                GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
8777            && pos + len <= GET_MODE_BITSIZE (submode))
8778     {
8779       /* Narrow a paradoxical subreg to prevent partial register stalls.  */
8780       mode = submode;
8781       val = SUBREG_REG (val);
8782     }
8783   else if (mode == HImode && pos + len <= 8)
8784     {
8785       /* Small HImode tests can be converted to QImode.  */
8786       mode = QImode;
8787       val = gen_lowpart (QImode, val);
8788     }
8789
8790   if (len == HOST_BITS_PER_WIDE_INT)
8791     mask = -1;
8792   else
8793     mask = ((HOST_WIDE_INT)1 << len) - 1;
8794   mask <<= pos;
8795
8796   operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
8797 })
8798
8799 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
8800 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
8801 ;; this is relatively important trick.
8802 ;; Do the conversion only post-reload to avoid limiting of the register class
8803 ;; to QI regs.
8804 (define_split
8805   [(set (match_operand 0 "flags_reg_operand" "")
8806         (match_operator 1 "compare_operator"
8807           [(and (match_operand 2 "register_operand" "")
8808                 (match_operand 3 "const_int_operand" ""))
8809            (const_int 0)]))]
8810    "reload_completed
8811     && QI_REG_P (operands[2])
8812     && GET_MODE (operands[2]) != QImode
8813     && ((ix86_match_ccmode (insn, CCZmode)
8814          && !(INTVAL (operands[3]) & ~(255 << 8)))
8815         || (ix86_match_ccmode (insn, CCNOmode)
8816             && !(INTVAL (operands[3]) & ~(127 << 8))))"
8817   [(set (match_dup 0)
8818         (match_op_dup 1
8819           [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
8820                    (match_dup 3))
8821            (const_int 0)]))]
8822   "operands[2] = gen_lowpart (SImode, operands[2]);
8823    operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);")
8824
8825 (define_split
8826   [(set (match_operand 0 "flags_reg_operand" "")
8827         (match_operator 1 "compare_operator"
8828           [(and (match_operand 2 "nonimmediate_operand" "")
8829                 (match_operand 3 "const_int_operand" ""))
8830            (const_int 0)]))]
8831    "reload_completed
8832     && GET_MODE (operands[2]) != QImode
8833     && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
8834     && ((ix86_match_ccmode (insn, CCZmode)
8835          && !(INTVAL (operands[3]) & ~255))
8836         || (ix86_match_ccmode (insn, CCNOmode)
8837             && !(INTVAL (operands[3]) & ~127)))"
8838   [(set (match_dup 0)
8839         (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
8840                          (const_int 0)]))]
8841   "operands[2] = gen_lowpart (QImode, operands[2]);
8842    operands[3] = gen_lowpart (QImode, operands[3]);")
8843
8844
8845 ;; %%% This used to optimize known byte-wide and operations to memory,
8846 ;; and sometimes to QImode registers.  If this is considered useful,
8847 ;; it should be done with splitters.
8848
8849 (define_expand "anddi3"
8850   [(set (match_operand:DI 0 "nonimmediate_operand" "")
8851         (and:DI (match_operand:DI 1 "nonimmediate_operand" "")
8852                 (match_operand:DI 2 "x86_64_szext_general_operand" "")))
8853    (clobber (reg:CC FLAGS_REG))]
8854   "TARGET_64BIT"
8855   "ix86_expand_binary_operator (AND, DImode, operands); DONE;")
8856
8857 (define_insn "*anddi_1_rex64"
8858   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
8859         (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
8860                 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
8861    (clobber (reg:CC FLAGS_REG))]
8862   "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
8863 {
8864   switch (get_attr_type (insn))
8865     {
8866     case TYPE_IMOVX:
8867       {
8868         enum machine_mode mode;
8869
8870         gcc_assert (CONST_INT_P (operands[2]));
8871         if (INTVAL (operands[2]) == 0xff)
8872           mode = QImode;
8873         else
8874           {
8875             gcc_assert (INTVAL (operands[2]) == 0xffff);
8876             mode = HImode;
8877           }
8878
8879         operands[1] = gen_lowpart (mode, operands[1]);
8880         if (mode == QImode)
8881           return "movz{bq|x}\t{%1,%0|%0, %1}";
8882         else
8883           return "movz{wq|x}\t{%1,%0|%0, %1}";
8884       }
8885
8886     default:
8887       gcc_assert (rtx_equal_p (operands[0], operands[1]));
8888       if (get_attr_mode (insn) == MODE_SI)
8889         return "and{l}\t{%k2, %k0|%k0, %k2}";
8890       else
8891         return "and{q}\t{%2, %0|%0, %2}";
8892     }
8893 }
8894   [(set_attr "type" "alu,alu,alu,imovx")
8895    (set_attr "length_immediate" "*,*,*,0")
8896    (set_attr "mode" "SI,DI,DI,DI")])
8897
8898 (define_insn "*anddi_2"
8899   [(set (reg FLAGS_REG)
8900         (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
8901                          (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
8902                  (const_int 0)))
8903    (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
8904         (and:DI (match_dup 1) (match_dup 2)))]
8905   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8906    && ix86_binary_operator_ok (AND, DImode, operands)"
8907   "@
8908    and{l}\t{%k2, %k0|%k0, %k2}
8909    and{q}\t{%2, %0|%0, %2}
8910    and{q}\t{%2, %0|%0, %2}"
8911   [(set_attr "type" "alu")
8912    (set_attr "mode" "SI,DI,DI")])
8913
8914 (define_expand "andsi3"
8915   [(set (match_operand:SI 0 "nonimmediate_operand" "")
8916         (and:SI (match_operand:SI 1 "nonimmediate_operand" "")
8917                 (match_operand:SI 2 "general_operand" "")))
8918    (clobber (reg:CC FLAGS_REG))]
8919   ""
8920   "ix86_expand_binary_operator (AND, SImode, operands); DONE;")
8921
8922 (define_insn "*andsi_1"
8923   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
8924         (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
8925                 (match_operand:SI 2 "general_operand" "ri,rm,L")))
8926    (clobber (reg:CC FLAGS_REG))]
8927   "ix86_binary_operator_ok (AND, SImode, operands)"
8928 {
8929   switch (get_attr_type (insn))
8930     {
8931     case TYPE_IMOVX:
8932       {
8933         enum machine_mode mode;
8934
8935         gcc_assert (CONST_INT_P (operands[2]));
8936         if (INTVAL (operands[2]) == 0xff)
8937           mode = QImode;
8938         else
8939           {
8940             gcc_assert (INTVAL (operands[2]) == 0xffff);
8941             mode = HImode;
8942           }
8943
8944         operands[1] = gen_lowpart (mode, operands[1]);
8945         if (mode == QImode)
8946           return "movz{bl|x}\t{%1,%0|%0, %1}";
8947         else
8948           return "movz{wl|x}\t{%1,%0|%0, %1}";
8949       }
8950
8951     default:
8952       gcc_assert (rtx_equal_p (operands[0], operands[1]));
8953       return "and{l}\t{%2, %0|%0, %2}";
8954     }
8955 }
8956   [(set_attr "type" "alu,alu,imovx")
8957    (set_attr "length_immediate" "*,*,0")
8958    (set_attr "mode" "SI")])
8959
8960 (define_split
8961   [(set (match_operand 0 "register_operand" "")
8962         (and (match_dup 0)
8963              (const_int -65536)))
8964    (clobber (reg:CC FLAGS_REG))]
8965   "optimize_size || (TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)"
8966   [(set (strict_low_part (match_dup 1)) (const_int 0))]
8967   "operands[1] = gen_lowpart (HImode, operands[0]);")
8968
8969 (define_split
8970   [(set (match_operand 0 "ext_register_operand" "")
8971         (and (match_dup 0)
8972              (const_int -256)))
8973    (clobber (reg:CC FLAGS_REG))]
8974   "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8975   [(set (strict_low_part (match_dup 1)) (const_int 0))]
8976   "operands[1] = gen_lowpart (QImode, operands[0]);")
8977
8978 (define_split
8979   [(set (match_operand 0 "ext_register_operand" "")
8980         (and (match_dup 0)
8981              (const_int -65281)))
8982    (clobber (reg:CC FLAGS_REG))]
8983   "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8984   [(parallel [(set (zero_extract:SI (match_dup 0)
8985                                     (const_int 8)
8986                                     (const_int 8))
8987                    (xor:SI
8988                      (zero_extract:SI (match_dup 0)
8989                                       (const_int 8)
8990                                       (const_int 8))
8991                      (zero_extract:SI (match_dup 0)
8992                                       (const_int 8)
8993                                       (const_int 8))))
8994               (clobber (reg:CC FLAGS_REG))])]
8995   "operands[0] = gen_lowpart (SImode, operands[0]);")
8996
8997 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8998 (define_insn "*andsi_1_zext"
8999   [(set (match_operand:DI 0 "register_operand" "=r")
9000         (zero_extend:DI
9001           (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9002                   (match_operand:SI 2 "general_operand" "g"))))
9003    (clobber (reg:CC FLAGS_REG))]
9004   "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
9005   "and{l}\t{%2, %k0|%k0, %2}"
9006   [(set_attr "type" "alu")
9007    (set_attr "mode" "SI")])
9008
9009 (define_insn "*andsi_2"
9010   [(set (reg FLAGS_REG)
9011         (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9012                          (match_operand:SI 2 "general_operand" "g,ri"))
9013                  (const_int 0)))
9014    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
9015         (and:SI (match_dup 1) (match_dup 2)))]
9016   "ix86_match_ccmode (insn, CCNOmode)
9017    && ix86_binary_operator_ok (AND, SImode, operands)"
9018   "and{l}\t{%2, %0|%0, %2}"
9019   [(set_attr "type" "alu")
9020    (set_attr "mode" "SI")])
9021
9022 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9023 (define_insn "*andsi_2_zext"
9024   [(set (reg FLAGS_REG)
9025         (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9026                          (match_operand:SI 2 "general_operand" "g"))
9027                  (const_int 0)))
9028    (set (match_operand:DI 0 "register_operand" "=r")
9029         (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
9030   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9031    && ix86_binary_operator_ok (AND, SImode, operands)"
9032   "and{l}\t{%2, %k0|%k0, %2}"
9033   [(set_attr "type" "alu")
9034    (set_attr "mode" "SI")])
9035
9036 (define_expand "andhi3"
9037   [(set (match_operand:HI 0 "nonimmediate_operand" "")
9038         (and:HI (match_operand:HI 1 "nonimmediate_operand" "")
9039                 (match_operand:HI 2 "general_operand" "")))
9040    (clobber (reg:CC FLAGS_REG))]
9041   "TARGET_HIMODE_MATH"
9042   "ix86_expand_binary_operator (AND, HImode, operands); DONE;")
9043
9044 (define_insn "*andhi_1"
9045   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
9046         (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
9047                 (match_operand:HI 2 "general_operand" "ri,rm,L")))
9048    (clobber (reg:CC FLAGS_REG))]
9049   "ix86_binary_operator_ok (AND, HImode, operands)"
9050 {
9051   switch (get_attr_type (insn))
9052     {
9053     case TYPE_IMOVX:
9054       gcc_assert (CONST_INT_P (operands[2]));
9055       gcc_assert (INTVAL (operands[2]) == 0xff);
9056       return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
9057
9058     default:
9059       gcc_assert (rtx_equal_p (operands[0], operands[1]));
9060
9061       return "and{w}\t{%2, %0|%0, %2}";
9062     }
9063 }
9064   [(set_attr "type" "alu,alu,imovx")
9065    (set_attr "length_immediate" "*,*,0")
9066    (set_attr "mode" "HI,HI,SI")])
9067
9068 (define_insn "*andhi_2"
9069   [(set (reg FLAGS_REG)
9070         (compare (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9071                          (match_operand:HI 2 "general_operand" "g,ri"))
9072                  (const_int 0)))
9073    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
9074         (and:HI (match_dup 1) (match_dup 2)))]
9075   "ix86_match_ccmode (insn, CCNOmode)
9076    && ix86_binary_operator_ok (AND, HImode, operands)"
9077   "and{w}\t{%2, %0|%0, %2}"
9078   [(set_attr "type" "alu")
9079    (set_attr "mode" "HI")])
9080
9081 (define_expand "andqi3"
9082   [(set (match_operand:QI 0 "nonimmediate_operand" "")
9083         (and:QI (match_operand:QI 1 "nonimmediate_operand" "")
9084                 (match_operand:QI 2 "general_operand" "")))
9085    (clobber (reg:CC FLAGS_REG))]
9086   "TARGET_QIMODE_MATH"
9087   "ix86_expand_binary_operator (AND, QImode, operands); DONE;")
9088
9089 ;; %%% Potential partial reg stall on alternative 2.  What to do?
9090 (define_insn "*andqi_1"
9091   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
9092         (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9093                 (match_operand:QI 2 "general_operand" "qi,qmi,ri")))
9094    (clobber (reg:CC FLAGS_REG))]
9095   "ix86_binary_operator_ok (AND, QImode, operands)"
9096   "@
9097    and{b}\t{%2, %0|%0, %2}
9098    and{b}\t{%2, %0|%0, %2}
9099    and{l}\t{%k2, %k0|%k0, %k2}"
9100   [(set_attr "type" "alu")
9101    (set_attr "mode" "QI,QI,SI")])
9102
9103 (define_insn "*andqi_1_slp"
9104   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
9105         (and:QI (match_dup 0)
9106                 (match_operand:QI 1 "general_operand" "qi,qmi")))
9107    (clobber (reg:CC FLAGS_REG))]
9108   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9109    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9110   "and{b}\t{%1, %0|%0, %1}"
9111   [(set_attr "type" "alu1")
9112    (set_attr "mode" "QI")])
9113
9114 (define_insn "*andqi_2_maybe_si"
9115   [(set (reg FLAGS_REG)
9116         (compare (and:QI
9117                       (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9118                       (match_operand:QI 2 "general_operand" "qim,qi,i"))
9119                  (const_int 0)))
9120    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
9121         (and:QI (match_dup 1) (match_dup 2)))]
9122   "ix86_binary_operator_ok (AND, QImode, operands)
9123    && ix86_match_ccmode (insn,
9124                          CONST_INT_P (operands[2])
9125                          && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
9126 {
9127   if (which_alternative == 2)
9128     {
9129       if (CONST_INT_P (operands[2]) && INTVAL (operands[2]) < 0)
9130         operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
9131       return "and{l}\t{%2, %k0|%k0, %2}";
9132     }
9133   return "and{b}\t{%2, %0|%0, %2}";
9134 }
9135   [(set_attr "type" "alu")
9136    (set_attr "mode" "QI,QI,SI")])
9137
9138 (define_insn "*andqi_2"
9139   [(set (reg FLAGS_REG)
9140         (compare (and:QI
9141                    (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9142                    (match_operand:QI 2 "general_operand" "qim,qi"))
9143                  (const_int 0)))
9144    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9145         (and:QI (match_dup 1) (match_dup 2)))]
9146   "ix86_match_ccmode (insn, CCNOmode)
9147    && ix86_binary_operator_ok (AND, QImode, operands)"
9148   "and{b}\t{%2, %0|%0, %2}"
9149   [(set_attr "type" "alu")
9150    (set_attr "mode" "QI")])
9151
9152 (define_insn "*andqi_2_slp"
9153   [(set (reg FLAGS_REG)
9154         (compare (and:QI
9155                    (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9156                    (match_operand:QI 1 "nonimmediate_operand" "qmi,qi"))
9157                  (const_int 0)))
9158    (set (strict_low_part (match_dup 0))
9159         (and:QI (match_dup 0) (match_dup 1)))]
9160   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9161    && ix86_match_ccmode (insn, CCNOmode)
9162    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9163   "and{b}\t{%1, %0|%0, %1}"
9164   [(set_attr "type" "alu1")
9165    (set_attr "mode" "QI")])
9166
9167 ;; ??? A bug in recog prevents it from recognizing a const_int as an
9168 ;; operand to zero_extend in andqi_ext_1.  It was checking explicitly
9169 ;; for a QImode operand, which of course failed.
9170
9171 (define_insn "andqi_ext_0"
9172   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9173                          (const_int 8)
9174                          (const_int 8))
9175         (and:SI
9176           (zero_extract:SI
9177             (match_operand 1 "ext_register_operand" "0")
9178             (const_int 8)
9179             (const_int 8))
9180           (match_operand 2 "const_int_operand" "n")))
9181    (clobber (reg:CC FLAGS_REG))]
9182   ""
9183   "and{b}\t{%2, %h0|%h0, %2}"
9184   [(set_attr "type" "alu")
9185    (set_attr "length_immediate" "1")
9186    (set_attr "mode" "QI")])
9187
9188 ;; Generated by peephole translating test to and.  This shows up
9189 ;; often in fp comparisons.
9190
9191 (define_insn "*andqi_ext_0_cc"
9192   [(set (reg FLAGS_REG)
9193         (compare
9194           (and:SI
9195             (zero_extract:SI
9196               (match_operand 1 "ext_register_operand" "0")
9197               (const_int 8)
9198               (const_int 8))
9199             (match_operand 2 "const_int_operand" "n"))
9200           (const_int 0)))
9201    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9202                          (const_int 8)
9203                          (const_int 8))
9204         (and:SI
9205           (zero_extract:SI
9206             (match_dup 1)
9207             (const_int 8)
9208             (const_int 8))
9209           (match_dup 2)))]
9210   "ix86_match_ccmode (insn, CCNOmode)"
9211   "and{b}\t{%2, %h0|%h0, %2}"
9212   [(set_attr "type" "alu")
9213    (set_attr "length_immediate" "1")
9214    (set_attr "mode" "QI")])
9215
9216 (define_insn "*andqi_ext_1"
9217   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9218                          (const_int 8)
9219                          (const_int 8))
9220         (and:SI
9221           (zero_extract:SI
9222             (match_operand 1 "ext_register_operand" "0")
9223             (const_int 8)
9224             (const_int 8))
9225           (zero_extend:SI
9226             (match_operand:QI 2 "general_operand" "Qm"))))
9227    (clobber (reg:CC FLAGS_REG))]
9228   "!TARGET_64BIT"
9229   "and{b}\t{%2, %h0|%h0, %2}"
9230   [(set_attr "type" "alu")
9231    (set_attr "length_immediate" "0")
9232    (set_attr "mode" "QI")])
9233
9234 (define_insn "*andqi_ext_1_rex64"
9235   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9236                          (const_int 8)
9237                          (const_int 8))
9238         (and:SI
9239           (zero_extract:SI
9240             (match_operand 1 "ext_register_operand" "0")
9241             (const_int 8)
9242             (const_int 8))
9243           (zero_extend:SI
9244             (match_operand 2 "ext_register_operand" "Q"))))
9245    (clobber (reg:CC FLAGS_REG))]
9246   "TARGET_64BIT"
9247   "and{b}\t{%2, %h0|%h0, %2}"
9248   [(set_attr "type" "alu")
9249    (set_attr "length_immediate" "0")
9250    (set_attr "mode" "QI")])
9251
9252 (define_insn "*andqi_ext_2"
9253   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9254                          (const_int 8)
9255                          (const_int 8))
9256         (and:SI
9257           (zero_extract:SI
9258             (match_operand 1 "ext_register_operand" "%0")
9259             (const_int 8)
9260             (const_int 8))
9261           (zero_extract:SI
9262             (match_operand 2 "ext_register_operand" "Q")
9263             (const_int 8)
9264             (const_int 8))))
9265    (clobber (reg:CC FLAGS_REG))]
9266   ""
9267   "and{b}\t{%h2, %h0|%h0, %h2}"
9268   [(set_attr "type" "alu")
9269    (set_attr "length_immediate" "0")
9270    (set_attr "mode" "QI")])
9271
9272 ;; Convert wide AND instructions with immediate operand to shorter QImode
9273 ;; equivalents when possible.
9274 ;; Don't do the splitting with memory operands, since it introduces risk
9275 ;; of memory mismatch stalls.  We may want to do the splitting for optimizing
9276 ;; for size, but that can (should?) be handled by generic code instead.
9277 (define_split
9278   [(set (match_operand 0 "register_operand" "")
9279         (and (match_operand 1 "register_operand" "")
9280              (match_operand 2 "const_int_operand" "")))
9281    (clobber (reg:CC FLAGS_REG))]
9282    "reload_completed
9283     && QI_REG_P (operands[0])
9284     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9285     && !(~INTVAL (operands[2]) & ~(255 << 8))
9286     && GET_MODE (operands[0]) != QImode"
9287   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9288                    (and:SI (zero_extract:SI (match_dup 1)
9289                                             (const_int 8) (const_int 8))
9290                            (match_dup 2)))
9291               (clobber (reg:CC FLAGS_REG))])]
9292   "operands[0] = gen_lowpart (SImode, operands[0]);
9293    operands[1] = gen_lowpart (SImode, operands[1]);
9294    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9295
9296 ;; Since AND can be encoded with sign extended immediate, this is only
9297 ;; profitable when 7th bit is not set.
9298 (define_split
9299   [(set (match_operand 0 "register_operand" "")
9300         (and (match_operand 1 "general_operand" "")
9301              (match_operand 2 "const_int_operand" "")))
9302    (clobber (reg:CC FLAGS_REG))]
9303    "reload_completed
9304     && ANY_QI_REG_P (operands[0])
9305     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9306     && !(~INTVAL (operands[2]) & ~255)
9307     && !(INTVAL (operands[2]) & 128)
9308     && GET_MODE (operands[0]) != QImode"
9309   [(parallel [(set (strict_low_part (match_dup 0))
9310                    (and:QI (match_dup 1)
9311                            (match_dup 2)))
9312               (clobber (reg:CC FLAGS_REG))])]
9313   "operands[0] = gen_lowpart (QImode, operands[0]);
9314    operands[1] = gen_lowpart (QImode, operands[1]);
9315    operands[2] = gen_lowpart (QImode, operands[2]);")
9316 \f
9317 ;; Logical inclusive OR instructions
9318
9319 ;; %%% This used to optimize known byte-wide and operations to memory.
9320 ;; If this is considered useful, it should be done with splitters.
9321
9322 (define_expand "iordi3"
9323   [(set (match_operand:DI 0 "nonimmediate_operand" "")
9324         (ior:DI (match_operand:DI 1 "nonimmediate_operand" "")
9325                 (match_operand:DI 2 "x86_64_general_operand" "")))
9326    (clobber (reg:CC FLAGS_REG))]
9327   "TARGET_64BIT"
9328   "ix86_expand_binary_operator (IOR, DImode, operands); DONE;")
9329
9330 (define_insn "*iordi_1_rex64"
9331   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
9332         (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9333                 (match_operand:DI 2 "x86_64_general_operand" "re,rme")))
9334    (clobber (reg:CC FLAGS_REG))]
9335   "TARGET_64BIT
9336    && ix86_binary_operator_ok (IOR, DImode, operands)"
9337   "or{q}\t{%2, %0|%0, %2}"
9338   [(set_attr "type" "alu")
9339    (set_attr "mode" "DI")])
9340
9341 (define_insn "*iordi_2_rex64"
9342   [(set (reg FLAGS_REG)
9343         (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9344                          (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
9345                  (const_int 0)))
9346    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
9347         (ior:DI (match_dup 1) (match_dup 2)))]
9348   "TARGET_64BIT
9349    && ix86_match_ccmode (insn, CCNOmode)
9350    && ix86_binary_operator_ok (IOR, DImode, operands)"
9351   "or{q}\t{%2, %0|%0, %2}"
9352   [(set_attr "type" "alu")
9353    (set_attr "mode" "DI")])
9354
9355 (define_insn "*iordi_3_rex64"
9356   [(set (reg FLAGS_REG)
9357         (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
9358                          (match_operand:DI 2 "x86_64_general_operand" "rem"))
9359                  (const_int 0)))
9360    (clobber (match_scratch:DI 0 "=r"))]
9361   "TARGET_64BIT
9362    && ix86_match_ccmode (insn, CCNOmode)
9363    && ix86_binary_operator_ok (IOR, DImode, operands)"
9364   "or{q}\t{%2, %0|%0, %2}"
9365   [(set_attr "type" "alu")
9366    (set_attr "mode" "DI")])
9367
9368
9369 (define_expand "iorsi3"
9370   [(set (match_operand:SI 0 "nonimmediate_operand" "")
9371         (ior:SI (match_operand:SI 1 "nonimmediate_operand" "")
9372                 (match_operand:SI 2 "general_operand" "")))
9373    (clobber (reg:CC FLAGS_REG))]
9374   ""
9375   "ix86_expand_binary_operator (IOR, SImode, operands); DONE;")
9376
9377 (define_insn "*iorsi_1"
9378   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
9379         (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9380                 (match_operand:SI 2 "general_operand" "ri,g")))
9381    (clobber (reg:CC FLAGS_REG))]
9382   "ix86_binary_operator_ok (IOR, SImode, operands)"
9383   "or{l}\t{%2, %0|%0, %2}"
9384   [(set_attr "type" "alu")
9385    (set_attr "mode" "SI")])
9386
9387 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9388 (define_insn "*iorsi_1_zext"
9389   [(set (match_operand:DI 0 "register_operand" "=r")
9390         (zero_extend:DI
9391           (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9392                   (match_operand:SI 2 "general_operand" "g"))))
9393    (clobber (reg:CC FLAGS_REG))]
9394   "TARGET_64BIT && ix86_binary_operator_ok (IOR, SImode, operands)"
9395   "or{l}\t{%2, %k0|%k0, %2}"
9396   [(set_attr "type" "alu")
9397    (set_attr "mode" "SI")])
9398
9399 (define_insn "*iorsi_1_zext_imm"
9400   [(set (match_operand:DI 0 "register_operand" "=r")
9401         (ior:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
9402                 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
9403    (clobber (reg:CC FLAGS_REG))]
9404   "TARGET_64BIT"
9405   "or{l}\t{%2, %k0|%k0, %2}"
9406   [(set_attr "type" "alu")
9407    (set_attr "mode" "SI")])
9408
9409 (define_insn "*iorsi_2"
9410   [(set (reg FLAGS_REG)
9411         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9412                          (match_operand:SI 2 "general_operand" "g,ri"))
9413                  (const_int 0)))
9414    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
9415         (ior:SI (match_dup 1) (match_dup 2)))]
9416   "ix86_match_ccmode (insn, CCNOmode)
9417    && ix86_binary_operator_ok (IOR, SImode, operands)"
9418   "or{l}\t{%2, %0|%0, %2}"
9419   [(set_attr "type" "alu")
9420    (set_attr "mode" "SI")])
9421
9422 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9423 ;; ??? Special case for immediate operand is missing - it is tricky.
9424 (define_insn "*iorsi_2_zext"
9425   [(set (reg FLAGS_REG)
9426         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9427                          (match_operand:SI 2 "general_operand" "g"))
9428                  (const_int 0)))
9429    (set (match_operand:DI 0 "register_operand" "=r")
9430         (zero_extend:DI (ior:SI (match_dup 1) (match_dup 2))))]
9431   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9432    && ix86_binary_operator_ok (IOR, SImode, operands)"
9433   "or{l}\t{%2, %k0|%k0, %2}"
9434   [(set_attr "type" "alu")
9435    (set_attr "mode" "SI")])
9436
9437 (define_insn "*iorsi_2_zext_imm"
9438   [(set (reg FLAGS_REG)
9439         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9440                          (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
9441                  (const_int 0)))
9442    (set (match_operand:DI 0 "register_operand" "=r")
9443         (ior:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
9444   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9445    && ix86_binary_operator_ok (IOR, SImode, operands)"
9446   "or{l}\t{%2, %k0|%k0, %2}"
9447   [(set_attr "type" "alu")
9448    (set_attr "mode" "SI")])
9449
9450 (define_insn "*iorsi_3"
9451   [(set (reg FLAGS_REG)
9452         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9453                          (match_operand:SI 2 "general_operand" "g"))
9454                  (const_int 0)))
9455    (clobber (match_scratch:SI 0 "=r"))]
9456   "ix86_match_ccmode (insn, CCNOmode)
9457    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9458   "or{l}\t{%2, %0|%0, %2}"
9459   [(set_attr "type" "alu")
9460    (set_attr "mode" "SI")])
9461
9462 (define_expand "iorhi3"
9463   [(set (match_operand:HI 0 "nonimmediate_operand" "")
9464         (ior:HI (match_operand:HI 1 "nonimmediate_operand" "")
9465                 (match_operand:HI 2 "general_operand" "")))
9466    (clobber (reg:CC FLAGS_REG))]
9467   "TARGET_HIMODE_MATH"
9468   "ix86_expand_binary_operator (IOR, HImode, operands); DONE;")
9469
9470 (define_insn "*iorhi_1"
9471   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
9472         (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9473                 (match_operand:HI 2 "general_operand" "g,ri")))
9474    (clobber (reg:CC FLAGS_REG))]
9475   "ix86_binary_operator_ok (IOR, HImode, operands)"
9476   "or{w}\t{%2, %0|%0, %2}"
9477   [(set_attr "type" "alu")
9478    (set_attr "mode" "HI")])
9479
9480 (define_insn "*iorhi_2"
9481   [(set (reg FLAGS_REG)
9482         (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9483                          (match_operand:HI 2 "general_operand" "g,ri"))
9484                  (const_int 0)))
9485    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
9486         (ior:HI (match_dup 1) (match_dup 2)))]
9487   "ix86_match_ccmode (insn, CCNOmode)
9488    && ix86_binary_operator_ok (IOR, HImode, operands)"
9489   "or{w}\t{%2, %0|%0, %2}"
9490   [(set_attr "type" "alu")
9491    (set_attr "mode" "HI")])
9492
9493 (define_insn "*iorhi_3"
9494   [(set (reg FLAGS_REG)
9495         (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
9496                          (match_operand:HI 2 "general_operand" "g"))
9497                  (const_int 0)))
9498    (clobber (match_scratch:HI 0 "=r"))]
9499   "ix86_match_ccmode (insn, CCNOmode)
9500    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9501   "or{w}\t{%2, %0|%0, %2}"
9502   [(set_attr "type" "alu")
9503    (set_attr "mode" "HI")])
9504
9505 (define_expand "iorqi3"
9506   [(set (match_operand:QI 0 "nonimmediate_operand" "")
9507         (ior:QI (match_operand:QI 1 "nonimmediate_operand" "")
9508                 (match_operand:QI 2 "general_operand" "")))
9509    (clobber (reg:CC FLAGS_REG))]
9510   "TARGET_QIMODE_MATH"
9511   "ix86_expand_binary_operator (IOR, QImode, operands); DONE;")
9512
9513 ;; %%% Potential partial reg stall on alternative 2.  What to do?
9514 (define_insn "*iorqi_1"
9515   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
9516         (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9517                 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
9518    (clobber (reg:CC FLAGS_REG))]
9519   "ix86_binary_operator_ok (IOR, QImode, operands)"
9520   "@
9521    or{b}\t{%2, %0|%0, %2}
9522    or{b}\t{%2, %0|%0, %2}
9523    or{l}\t{%k2, %k0|%k0, %k2}"
9524   [(set_attr "type" "alu")
9525    (set_attr "mode" "QI,QI,SI")])
9526
9527 (define_insn "*iorqi_1_slp"
9528   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
9529         (ior:QI (match_dup 0)
9530                 (match_operand:QI 1 "general_operand" "qmi,qi")))
9531    (clobber (reg:CC FLAGS_REG))]
9532   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9533    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9534   "or{b}\t{%1, %0|%0, %1}"
9535   [(set_attr "type" "alu1")
9536    (set_attr "mode" "QI")])
9537
9538 (define_insn "*iorqi_2"
9539   [(set (reg FLAGS_REG)
9540         (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9541                          (match_operand:QI 2 "general_operand" "qim,qi"))
9542                  (const_int 0)))
9543    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9544         (ior:QI (match_dup 1) (match_dup 2)))]
9545   "ix86_match_ccmode (insn, CCNOmode)
9546    && ix86_binary_operator_ok (IOR, QImode, operands)"
9547   "or{b}\t{%2, %0|%0, %2}"
9548   [(set_attr "type" "alu")
9549    (set_attr "mode" "QI")])
9550
9551 (define_insn "*iorqi_2_slp"
9552   [(set (reg FLAGS_REG)
9553         (compare (ior:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9554                          (match_operand:QI 1 "general_operand" "qim,qi"))
9555                  (const_int 0)))
9556    (set (strict_low_part (match_dup 0))
9557         (ior:QI (match_dup 0) (match_dup 1)))]
9558   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9559    && ix86_match_ccmode (insn, CCNOmode)
9560    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9561   "or{b}\t{%1, %0|%0, %1}"
9562   [(set_attr "type" "alu1")
9563    (set_attr "mode" "QI")])
9564
9565 (define_insn "*iorqi_3"
9566   [(set (reg FLAGS_REG)
9567         (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
9568                          (match_operand:QI 2 "general_operand" "qim"))
9569                  (const_int 0)))
9570    (clobber (match_scratch:QI 0 "=q"))]
9571   "ix86_match_ccmode (insn, CCNOmode)
9572    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9573   "or{b}\t{%2, %0|%0, %2}"
9574   [(set_attr "type" "alu")
9575    (set_attr "mode" "QI")])
9576
9577 (define_insn "iorqi_ext_0"
9578   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9579                          (const_int 8)
9580                          (const_int 8))
9581         (ior:SI
9582           (zero_extract:SI
9583             (match_operand 1 "ext_register_operand" "0")
9584             (const_int 8)
9585             (const_int 8))
9586           (match_operand 2 "const_int_operand" "n")))
9587    (clobber (reg:CC FLAGS_REG))]
9588   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9589   "or{b}\t{%2, %h0|%h0, %2}"
9590   [(set_attr "type" "alu")
9591    (set_attr "length_immediate" "1")
9592    (set_attr "mode" "QI")])
9593
9594 (define_insn "*iorqi_ext_1"
9595   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9596                          (const_int 8)
9597                          (const_int 8))
9598         (ior:SI
9599           (zero_extract:SI
9600             (match_operand 1 "ext_register_operand" "0")
9601             (const_int 8)
9602             (const_int 8))
9603           (zero_extend:SI
9604             (match_operand:QI 2 "general_operand" "Qm"))))
9605    (clobber (reg:CC FLAGS_REG))]
9606   "!TARGET_64BIT
9607    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9608   "or{b}\t{%2, %h0|%h0, %2}"
9609   [(set_attr "type" "alu")
9610    (set_attr "length_immediate" "0")
9611    (set_attr "mode" "QI")])
9612
9613 (define_insn "*iorqi_ext_1_rex64"
9614   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9615                          (const_int 8)
9616                          (const_int 8))
9617         (ior:SI
9618           (zero_extract:SI
9619             (match_operand 1 "ext_register_operand" "0")
9620             (const_int 8)
9621             (const_int 8))
9622           (zero_extend:SI
9623             (match_operand 2 "ext_register_operand" "Q"))))
9624    (clobber (reg:CC FLAGS_REG))]
9625   "TARGET_64BIT
9626    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9627   "or{b}\t{%2, %h0|%h0, %2}"
9628   [(set_attr "type" "alu")
9629    (set_attr "length_immediate" "0")
9630    (set_attr "mode" "QI")])
9631
9632 (define_insn "*iorqi_ext_2"
9633   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9634                          (const_int 8)
9635                          (const_int 8))
9636         (ior:SI
9637           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
9638                            (const_int 8)
9639                            (const_int 8))
9640           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
9641                            (const_int 8)
9642                            (const_int 8))))
9643    (clobber (reg:CC FLAGS_REG))]
9644   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9645   "ior{b}\t{%h2, %h0|%h0, %h2}"
9646   [(set_attr "type" "alu")
9647    (set_attr "length_immediate" "0")
9648    (set_attr "mode" "QI")])
9649
9650 (define_split
9651   [(set (match_operand 0 "register_operand" "")
9652         (ior (match_operand 1 "register_operand" "")
9653              (match_operand 2 "const_int_operand" "")))
9654    (clobber (reg:CC FLAGS_REG))]
9655    "reload_completed
9656     && QI_REG_P (operands[0])
9657     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9658     && !(INTVAL (operands[2]) & ~(255 << 8))
9659     && GET_MODE (operands[0]) != QImode"
9660   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9661                    (ior:SI (zero_extract:SI (match_dup 1)
9662                                             (const_int 8) (const_int 8))
9663                            (match_dup 2)))
9664               (clobber (reg:CC FLAGS_REG))])]
9665   "operands[0] = gen_lowpart (SImode, operands[0]);
9666    operands[1] = gen_lowpart (SImode, operands[1]);
9667    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9668
9669 ;; Since OR can be encoded with sign extended immediate, this is only
9670 ;; profitable when 7th bit is set.
9671 (define_split
9672   [(set (match_operand 0 "register_operand" "")
9673         (ior (match_operand 1 "general_operand" "")
9674              (match_operand 2 "const_int_operand" "")))
9675    (clobber (reg:CC FLAGS_REG))]
9676    "reload_completed
9677     && ANY_QI_REG_P (operands[0])
9678     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9679     && !(INTVAL (operands[2]) & ~255)
9680     && (INTVAL (operands[2]) & 128)
9681     && GET_MODE (operands[0]) != QImode"
9682   [(parallel [(set (strict_low_part (match_dup 0))
9683                    (ior:QI (match_dup 1)
9684                            (match_dup 2)))
9685               (clobber (reg:CC FLAGS_REG))])]
9686   "operands[0] = gen_lowpart (QImode, operands[0]);
9687    operands[1] = gen_lowpart (QImode, operands[1]);
9688    operands[2] = gen_lowpart (QImode, operands[2]);")
9689 \f
9690 ;; Logical XOR instructions
9691
9692 ;; %%% This used to optimize known byte-wide and operations to memory.
9693 ;; If this is considered useful, it should be done with splitters.
9694
9695 (define_expand "xordi3"
9696   [(set (match_operand:DI 0 "nonimmediate_operand" "")
9697         (xor:DI (match_operand:DI 1 "nonimmediate_operand" "")
9698                 (match_operand:DI 2 "x86_64_general_operand" "")))
9699    (clobber (reg:CC FLAGS_REG))]
9700   "TARGET_64BIT"
9701   "ix86_expand_binary_operator (XOR, DImode, operands); DONE;")
9702
9703 (define_insn "*xordi_1_rex64"
9704   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
9705         (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9706                 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
9707    (clobber (reg:CC FLAGS_REG))]
9708   "TARGET_64BIT
9709    && ix86_binary_operator_ok (XOR, DImode, operands)"
9710   "xor{q}\t{%2, %0|%0, %2}"
9711   [(set_attr "type" "alu")
9712    (set_attr "mode" "DI")])
9713
9714 (define_insn "*xordi_2_rex64"
9715   [(set (reg FLAGS_REG)
9716         (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9717                          (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
9718                  (const_int 0)))
9719    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
9720         (xor:DI (match_dup 1) (match_dup 2)))]
9721   "TARGET_64BIT
9722    && ix86_match_ccmode (insn, CCNOmode)
9723    && ix86_binary_operator_ok (XOR, DImode, operands)"
9724   "xor{q}\t{%2, %0|%0, %2}"
9725   [(set_attr "type" "alu")
9726    (set_attr "mode" "DI")])
9727
9728 (define_insn "*xordi_3_rex64"
9729   [(set (reg FLAGS_REG)
9730         (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
9731                          (match_operand:DI 2 "x86_64_general_operand" "rem"))
9732                  (const_int 0)))
9733    (clobber (match_scratch:DI 0 "=r"))]
9734   "TARGET_64BIT
9735    && ix86_match_ccmode (insn, CCNOmode)
9736    && ix86_binary_operator_ok (XOR, DImode, operands)"
9737   "xor{q}\t{%2, %0|%0, %2}"
9738   [(set_attr "type" "alu")
9739    (set_attr "mode" "DI")])
9740
9741 (define_expand "xorsi3"
9742   [(set (match_operand:SI 0 "nonimmediate_operand" "")
9743         (xor:SI (match_operand:SI 1 "nonimmediate_operand" "")
9744                 (match_operand:SI 2 "general_operand" "")))
9745    (clobber (reg:CC FLAGS_REG))]
9746   ""
9747   "ix86_expand_binary_operator (XOR, SImode, operands); DONE;")
9748
9749 (define_insn "*xorsi_1"
9750   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
9751         (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9752                 (match_operand:SI 2 "general_operand" "ri,rm")))
9753    (clobber (reg:CC FLAGS_REG))]
9754   "ix86_binary_operator_ok (XOR, SImode, operands)"
9755   "xor{l}\t{%2, %0|%0, %2}"
9756   [(set_attr "type" "alu")
9757    (set_attr "mode" "SI")])
9758
9759 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9760 ;; Add speccase for immediates
9761 (define_insn "*xorsi_1_zext"
9762   [(set (match_operand:DI 0 "register_operand" "=r")
9763         (zero_extend:DI
9764           (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9765                   (match_operand:SI 2 "general_operand" "g"))))
9766    (clobber (reg:CC FLAGS_REG))]
9767   "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
9768   "xor{l}\t{%2, %k0|%k0, %2}"
9769   [(set_attr "type" "alu")
9770    (set_attr "mode" "SI")])
9771
9772 (define_insn "*xorsi_1_zext_imm"
9773   [(set (match_operand:DI 0 "register_operand" "=r")
9774         (xor:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
9775                 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
9776    (clobber (reg:CC FLAGS_REG))]
9777   "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
9778   "xor{l}\t{%2, %k0|%k0, %2}"
9779   [(set_attr "type" "alu")
9780    (set_attr "mode" "SI")])
9781
9782 (define_insn "*xorsi_2"
9783   [(set (reg FLAGS_REG)
9784         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9785                          (match_operand:SI 2 "general_operand" "g,ri"))
9786                  (const_int 0)))
9787    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
9788         (xor:SI (match_dup 1) (match_dup 2)))]
9789   "ix86_match_ccmode (insn, CCNOmode)
9790    && ix86_binary_operator_ok (XOR, SImode, operands)"
9791   "xor{l}\t{%2, %0|%0, %2}"
9792   [(set_attr "type" "alu")
9793    (set_attr "mode" "SI")])
9794
9795 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9796 ;; ??? Special case for immediate operand is missing - it is tricky.
9797 (define_insn "*xorsi_2_zext"
9798   [(set (reg FLAGS_REG)
9799         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9800                          (match_operand:SI 2 "general_operand" "g"))
9801                  (const_int 0)))
9802    (set (match_operand:DI 0 "register_operand" "=r")
9803         (zero_extend:DI (xor:SI (match_dup 1) (match_dup 2))))]
9804   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9805    && ix86_binary_operator_ok (XOR, SImode, operands)"
9806   "xor{l}\t{%2, %k0|%k0, %2}"
9807   [(set_attr "type" "alu")
9808    (set_attr "mode" "SI")])
9809
9810 (define_insn "*xorsi_2_zext_imm"
9811   [(set (reg FLAGS_REG)
9812         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9813                          (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
9814                  (const_int 0)))
9815    (set (match_operand:DI 0 "register_operand" "=r")
9816         (xor:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
9817   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9818    && ix86_binary_operator_ok (XOR, SImode, operands)"
9819   "xor{l}\t{%2, %k0|%k0, %2}"
9820   [(set_attr "type" "alu")
9821    (set_attr "mode" "SI")])
9822
9823 (define_insn "*xorsi_3"
9824   [(set (reg FLAGS_REG)
9825         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9826                          (match_operand:SI 2 "general_operand" "g"))
9827                  (const_int 0)))
9828    (clobber (match_scratch:SI 0 "=r"))]
9829   "ix86_match_ccmode (insn, CCNOmode)
9830    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9831   "xor{l}\t{%2, %0|%0, %2}"
9832   [(set_attr "type" "alu")
9833    (set_attr "mode" "SI")])
9834
9835 (define_expand "xorhi3"
9836   [(set (match_operand:HI 0 "nonimmediate_operand" "")
9837         (xor:HI (match_operand:HI 1 "nonimmediate_operand" "")
9838                 (match_operand:HI 2 "general_operand" "")))
9839    (clobber (reg:CC FLAGS_REG))]
9840   "TARGET_HIMODE_MATH"
9841   "ix86_expand_binary_operator (XOR, HImode, operands); DONE;")
9842
9843 (define_insn "*xorhi_1"
9844   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
9845         (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9846                 (match_operand:HI 2 "general_operand" "g,ri")))
9847    (clobber (reg:CC FLAGS_REG))]
9848   "ix86_binary_operator_ok (XOR, HImode, operands)"
9849   "xor{w}\t{%2, %0|%0, %2}"
9850   [(set_attr "type" "alu")
9851    (set_attr "mode" "HI")])
9852
9853 (define_insn "*xorhi_2"
9854   [(set (reg FLAGS_REG)
9855         (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9856                          (match_operand:HI 2 "general_operand" "g,ri"))
9857                  (const_int 0)))
9858    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
9859         (xor:HI (match_dup 1) (match_dup 2)))]
9860   "ix86_match_ccmode (insn, CCNOmode)
9861    && ix86_binary_operator_ok (XOR, HImode, operands)"
9862   "xor{w}\t{%2, %0|%0, %2}"
9863   [(set_attr "type" "alu")
9864    (set_attr "mode" "HI")])
9865
9866 (define_insn "*xorhi_3"
9867   [(set (reg FLAGS_REG)
9868         (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
9869                          (match_operand:HI 2 "general_operand" "g"))
9870                  (const_int 0)))
9871    (clobber (match_scratch:HI 0 "=r"))]
9872   "ix86_match_ccmode (insn, CCNOmode)
9873    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9874   "xor{w}\t{%2, %0|%0, %2}"
9875   [(set_attr "type" "alu")
9876    (set_attr "mode" "HI")])
9877
9878 (define_expand "xorqi3"
9879   [(set (match_operand:QI 0 "nonimmediate_operand" "")
9880         (xor:QI (match_operand:QI 1 "nonimmediate_operand" "")
9881                 (match_operand:QI 2 "general_operand" "")))
9882    (clobber (reg:CC FLAGS_REG))]
9883   "TARGET_QIMODE_MATH"
9884   "ix86_expand_binary_operator (XOR, QImode, operands); DONE;")
9885
9886 ;; %%% Potential partial reg stall on alternative 2.  What to do?
9887 (define_insn "*xorqi_1"
9888   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
9889         (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9890                 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
9891    (clobber (reg:CC FLAGS_REG))]
9892   "ix86_binary_operator_ok (XOR, QImode, operands)"
9893   "@
9894    xor{b}\t{%2, %0|%0, %2}
9895    xor{b}\t{%2, %0|%0, %2}
9896    xor{l}\t{%k2, %k0|%k0, %k2}"
9897   [(set_attr "type" "alu")
9898    (set_attr "mode" "QI,QI,SI")])
9899
9900 (define_insn "*xorqi_1_slp"
9901   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
9902         (xor:QI (match_dup 0)
9903                 (match_operand:QI 1 "general_operand" "qi,qmi")))
9904    (clobber (reg:CC FLAGS_REG))]
9905   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9906    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9907   "xor{b}\t{%1, %0|%0, %1}"
9908   [(set_attr "type" "alu1")
9909    (set_attr "mode" "QI")])
9910
9911 (define_insn "xorqi_ext_0"
9912   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9913                          (const_int 8)
9914                          (const_int 8))
9915         (xor:SI
9916           (zero_extract:SI
9917             (match_operand 1 "ext_register_operand" "0")
9918             (const_int 8)
9919             (const_int 8))
9920           (match_operand 2 "const_int_operand" "n")))
9921    (clobber (reg:CC FLAGS_REG))]
9922   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9923   "xor{b}\t{%2, %h0|%h0, %2}"
9924   [(set_attr "type" "alu")
9925    (set_attr "length_immediate" "1")
9926    (set_attr "mode" "QI")])
9927
9928 (define_insn "*xorqi_ext_1"
9929   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9930                          (const_int 8)
9931                          (const_int 8))
9932         (xor:SI
9933           (zero_extract:SI
9934             (match_operand 1 "ext_register_operand" "0")
9935             (const_int 8)
9936             (const_int 8))
9937           (zero_extend:SI
9938             (match_operand:QI 2 "general_operand" "Qm"))))
9939    (clobber (reg:CC FLAGS_REG))]
9940   "!TARGET_64BIT
9941    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9942   "xor{b}\t{%2, %h0|%h0, %2}"
9943   [(set_attr "type" "alu")
9944    (set_attr "length_immediate" "0")
9945    (set_attr "mode" "QI")])
9946
9947 (define_insn "*xorqi_ext_1_rex64"
9948   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9949                          (const_int 8)
9950                          (const_int 8))
9951         (xor:SI
9952           (zero_extract:SI
9953             (match_operand 1 "ext_register_operand" "0")
9954             (const_int 8)
9955             (const_int 8))
9956           (zero_extend:SI
9957             (match_operand 2 "ext_register_operand" "Q"))))
9958    (clobber (reg:CC FLAGS_REG))]
9959   "TARGET_64BIT
9960    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9961   "xor{b}\t{%2, %h0|%h0, %2}"
9962   [(set_attr "type" "alu")
9963    (set_attr "length_immediate" "0")
9964    (set_attr "mode" "QI")])
9965
9966 (define_insn "*xorqi_ext_2"
9967   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9968                          (const_int 8)
9969                          (const_int 8))
9970         (xor:SI
9971           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
9972                            (const_int 8)
9973                            (const_int 8))
9974           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
9975                            (const_int 8)
9976                            (const_int 8))))
9977    (clobber (reg:CC FLAGS_REG))]
9978   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9979   "xor{b}\t{%h2, %h0|%h0, %h2}"
9980   [(set_attr "type" "alu")
9981    (set_attr "length_immediate" "0")
9982    (set_attr "mode" "QI")])
9983
9984 (define_insn "*xorqi_cc_1"
9985   [(set (reg FLAGS_REG)
9986         (compare
9987           (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9988                   (match_operand:QI 2 "general_operand" "qim,qi"))
9989           (const_int 0)))
9990    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9991         (xor:QI (match_dup 1) (match_dup 2)))]
9992   "ix86_match_ccmode (insn, CCNOmode)
9993    && ix86_binary_operator_ok (XOR, QImode, operands)"
9994   "xor{b}\t{%2, %0|%0, %2}"
9995   [(set_attr "type" "alu")
9996    (set_attr "mode" "QI")])
9997
9998 (define_insn "*xorqi_2_slp"
9999   [(set (reg FLAGS_REG)
10000         (compare (xor:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
10001                          (match_operand:QI 1 "general_operand" "qim,qi"))
10002                  (const_int 0)))
10003    (set (strict_low_part (match_dup 0))
10004         (xor:QI (match_dup 0) (match_dup 1)))]
10005   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
10006    && ix86_match_ccmode (insn, CCNOmode)
10007    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
10008   "xor{b}\t{%1, %0|%0, %1}"
10009   [(set_attr "type" "alu1")
10010    (set_attr "mode" "QI")])
10011
10012 (define_insn "*xorqi_cc_2"
10013   [(set (reg FLAGS_REG)
10014         (compare
10015           (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
10016                   (match_operand:QI 2 "general_operand" "qim"))
10017           (const_int 0)))
10018    (clobber (match_scratch:QI 0 "=q"))]
10019   "ix86_match_ccmode (insn, CCNOmode)
10020    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
10021   "xor{b}\t{%2, %0|%0, %2}"
10022   [(set_attr "type" "alu")
10023    (set_attr "mode" "QI")])
10024
10025 (define_insn "*xorqi_cc_ext_1"
10026   [(set (reg FLAGS_REG)
10027         (compare
10028           (xor:SI
10029             (zero_extract:SI
10030               (match_operand 1 "ext_register_operand" "0")
10031               (const_int 8)
10032               (const_int 8))
10033             (match_operand:QI 2 "general_operand" "qmn"))
10034           (const_int 0)))
10035    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
10036                          (const_int 8)
10037                          (const_int 8))
10038         (xor:SI
10039           (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
10040           (match_dup 2)))]
10041   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
10042   "xor{b}\t{%2, %h0|%h0, %2}"
10043   [(set_attr "type" "alu")
10044    (set_attr "mode" "QI")])
10045
10046 (define_insn "*xorqi_cc_ext_1_rex64"
10047   [(set (reg FLAGS_REG)
10048         (compare
10049           (xor:SI
10050             (zero_extract:SI
10051               (match_operand 1 "ext_register_operand" "0")
10052               (const_int 8)
10053               (const_int 8))
10054             (match_operand:QI 2 "nonmemory_operand" "Qn"))
10055           (const_int 0)))
10056    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
10057                          (const_int 8)
10058                          (const_int 8))
10059         (xor:SI
10060           (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
10061           (match_dup 2)))]
10062   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
10063   "xor{b}\t{%2, %h0|%h0, %2}"
10064   [(set_attr "type" "alu")
10065    (set_attr "mode" "QI")])
10066
10067 (define_expand "xorqi_cc_ext_1"
10068   [(parallel [
10069      (set (reg:CCNO FLAGS_REG)
10070           (compare:CCNO
10071             (xor:SI
10072               (zero_extract:SI
10073                 (match_operand 1 "ext_register_operand" "")
10074                 (const_int 8)
10075                 (const_int 8))
10076               (match_operand:QI 2 "general_operand" ""))
10077             (const_int 0)))
10078      (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
10079                            (const_int 8)
10080                            (const_int 8))
10081           (xor:SI
10082             (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
10083             (match_dup 2)))])]
10084   ""
10085   "")
10086
10087 (define_split
10088   [(set (match_operand 0 "register_operand" "")
10089         (xor (match_operand 1 "register_operand" "")
10090              (match_operand 2 "const_int_operand" "")))
10091    (clobber (reg:CC FLAGS_REG))]
10092    "reload_completed
10093     && QI_REG_P (operands[0])
10094     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
10095     && !(INTVAL (operands[2]) & ~(255 << 8))
10096     && GET_MODE (operands[0]) != QImode"
10097   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
10098                    (xor:SI (zero_extract:SI (match_dup 1)
10099                                             (const_int 8) (const_int 8))
10100                            (match_dup 2)))
10101               (clobber (reg:CC FLAGS_REG))])]
10102   "operands[0] = gen_lowpart (SImode, operands[0]);
10103    operands[1] = gen_lowpart (SImode, operands[1]);
10104    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
10105
10106 ;; Since XOR can be encoded with sign extended immediate, this is only
10107 ;; profitable when 7th bit is set.
10108 (define_split
10109   [(set (match_operand 0 "register_operand" "")
10110         (xor (match_operand 1 "general_operand" "")
10111              (match_operand 2 "const_int_operand" "")))
10112    (clobber (reg:CC FLAGS_REG))]
10113    "reload_completed
10114     && ANY_QI_REG_P (operands[0])
10115     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
10116     && !(INTVAL (operands[2]) & ~255)
10117     && (INTVAL (operands[2]) & 128)
10118     && GET_MODE (operands[0]) != QImode"
10119   [(parallel [(set (strict_low_part (match_dup 0))
10120                    (xor:QI (match_dup 1)
10121                            (match_dup 2)))
10122               (clobber (reg:CC FLAGS_REG))])]
10123   "operands[0] = gen_lowpart (QImode, operands[0]);
10124    operands[1] = gen_lowpart (QImode, operands[1]);
10125    operands[2] = gen_lowpart (QImode, operands[2]);")
10126 \f
10127 ;; Negation instructions
10128
10129 (define_expand "negti2"
10130   [(parallel [(set (match_operand:TI 0 "nonimmediate_operand" "")
10131                    (neg:TI (match_operand:TI 1 "nonimmediate_operand" "")))
10132               (clobber (reg:CC FLAGS_REG))])]
10133   "TARGET_64BIT"
10134   "ix86_expand_unary_operator (NEG, TImode, operands); DONE;")
10135
10136 (define_insn "*negti2_1"
10137   [(set (match_operand:TI 0 "nonimmediate_operand" "=ro")
10138         (neg:TI (match_operand:TI 1 "nonimmediate_operand" "0")))
10139    (clobber (reg:CC FLAGS_REG))]
10140   "TARGET_64BIT
10141    && ix86_unary_operator_ok (NEG, TImode, operands)"
10142   "#")
10143
10144 (define_split
10145   [(set (match_operand:TI 0 "nonimmediate_operand" "")
10146         (neg:TI (match_operand:TI 1 "nonimmediate_operand" "")))
10147    (clobber (reg:CC FLAGS_REG))]
10148   "TARGET_64BIT && reload_completed"
10149   [(parallel
10150     [(set (reg:CCZ FLAGS_REG)
10151           (compare:CCZ (neg:DI (match_dup 1)) (const_int 0)))
10152      (set (match_dup 0) (neg:DI (match_dup 1)))])
10153    (parallel
10154     [(set (match_dup 2)
10155           (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
10156                             (match_dup 3))
10157                    (const_int 0)))
10158      (clobber (reg:CC FLAGS_REG))])
10159    (parallel
10160     [(set (match_dup 2)
10161           (neg:DI (match_dup 2)))
10162      (clobber (reg:CC FLAGS_REG))])]
10163   "split_ti (&operands[0], 2, &operands[0], &operands[2]);")
10164
10165 (define_expand "negdi2"
10166   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
10167                    (neg:DI (match_operand:DI 1 "nonimmediate_operand" "")))
10168               (clobber (reg:CC FLAGS_REG))])]
10169   ""
10170   "ix86_expand_unary_operator (NEG, DImode, operands); DONE;")
10171
10172 (define_insn "*negdi2_1"
10173   [(set (match_operand:DI 0 "nonimmediate_operand" "=ro")
10174         (neg:DI (match_operand:DI 1 "general_operand" "0")))
10175    (clobber (reg:CC FLAGS_REG))]
10176   "!TARGET_64BIT
10177    && ix86_unary_operator_ok (NEG, DImode, operands)"
10178   "#")
10179
10180 (define_split
10181   [(set (match_operand:DI 0 "nonimmediate_operand" "")
10182         (neg:DI (match_operand:DI 1 "general_operand" "")))
10183    (clobber (reg:CC FLAGS_REG))]
10184   "!TARGET_64BIT && reload_completed"
10185   [(parallel
10186     [(set (reg:CCZ FLAGS_REG)
10187           (compare:CCZ (neg:SI (match_dup 1)) (const_int 0)))
10188      (set (match_dup 0) (neg:SI (match_dup 1)))])
10189    (parallel
10190     [(set (match_dup 2)
10191           (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
10192                             (match_dup 3))
10193                    (const_int 0)))
10194      (clobber (reg:CC FLAGS_REG))])
10195    (parallel
10196     [(set (match_dup 2)
10197           (neg:SI (match_dup 2)))
10198      (clobber (reg:CC FLAGS_REG))])]
10199   "split_di (&operands[0], 2, &operands[0], &operands[2]);");
10200
10201 (define_insn "*negdi2_1_rex64"
10202   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10203         (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0")))
10204    (clobber (reg:CC FLAGS_REG))]
10205   "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
10206   "neg{q}\t%0"
10207   [(set_attr "type" "negnot")
10208    (set_attr "mode" "DI")])
10209
10210 ;; The problem with neg is that it does not perform (compare x 0),
10211 ;; it really performs (compare 0 x), which leaves us with the zero
10212 ;; flag being the only useful item.
10213
10214 (define_insn "*negdi2_cmpz_rex64"
10215   [(set (reg:CCZ FLAGS_REG)
10216         (compare:CCZ (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
10217                      (const_int 0)))
10218    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10219         (neg:DI (match_dup 1)))]
10220   "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
10221   "neg{q}\t%0"
10222   [(set_attr "type" "negnot")
10223    (set_attr "mode" "DI")])
10224
10225
10226 (define_expand "negsi2"
10227   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
10228                    (neg:SI (match_operand:SI 1 "nonimmediate_operand" "")))
10229               (clobber (reg:CC FLAGS_REG))])]
10230   ""
10231   "ix86_expand_unary_operator (NEG, SImode, operands); DONE;")
10232
10233 (define_insn "*negsi2_1"
10234   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10235         (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0")))
10236    (clobber (reg:CC FLAGS_REG))]
10237   "ix86_unary_operator_ok (NEG, SImode, operands)"
10238   "neg{l}\t%0"
10239   [(set_attr "type" "negnot")
10240    (set_attr "mode" "SI")])
10241
10242 ;; Combine is quite creative about this pattern.
10243 (define_insn "*negsi2_1_zext"
10244   [(set (match_operand:DI 0 "register_operand" "=r")
10245         (lshiftrt:DI (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
10246                                         (const_int 32)))
10247                      (const_int 32)))
10248    (clobber (reg:CC FLAGS_REG))]
10249   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
10250   "neg{l}\t%k0"
10251   [(set_attr "type" "negnot")
10252    (set_attr "mode" "SI")])
10253
10254 ;; The problem with neg is that it does not perform (compare x 0),
10255 ;; it really performs (compare 0 x), which leaves us with the zero
10256 ;; flag being the only useful item.
10257
10258 (define_insn "*negsi2_cmpz"
10259   [(set (reg:CCZ FLAGS_REG)
10260         (compare:CCZ (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
10261                      (const_int 0)))
10262    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10263         (neg:SI (match_dup 1)))]
10264   "ix86_unary_operator_ok (NEG, SImode, operands)"
10265   "neg{l}\t%0"
10266   [(set_attr "type" "negnot")
10267    (set_attr "mode" "SI")])
10268
10269 (define_insn "*negsi2_cmpz_zext"
10270   [(set (reg:CCZ FLAGS_REG)
10271         (compare:CCZ (lshiftrt:DI
10272                        (neg:DI (ashift:DI
10273                                  (match_operand:DI 1 "register_operand" "0")
10274                                  (const_int 32)))
10275                        (const_int 32))
10276                      (const_int 0)))
10277    (set (match_operand:DI 0 "register_operand" "=r")
10278         (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
10279                                         (const_int 32)))
10280                      (const_int 32)))]
10281   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
10282   "neg{l}\t%k0"
10283   [(set_attr "type" "negnot")
10284    (set_attr "mode" "SI")])
10285
10286 (define_expand "neghi2"
10287   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
10288                    (neg:HI (match_operand:HI 1 "nonimmediate_operand" "")))
10289               (clobber (reg:CC FLAGS_REG))])]
10290   "TARGET_HIMODE_MATH"
10291   "ix86_expand_unary_operator (NEG, HImode, operands); DONE;")
10292
10293 (define_insn "*neghi2_1"
10294   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10295         (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0")))
10296    (clobber (reg:CC FLAGS_REG))]
10297   "ix86_unary_operator_ok (NEG, HImode, operands)"
10298   "neg{w}\t%0"
10299   [(set_attr "type" "negnot")
10300    (set_attr "mode" "HI")])
10301
10302 (define_insn "*neghi2_cmpz"
10303   [(set (reg:CCZ FLAGS_REG)
10304         (compare:CCZ (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
10305                      (const_int 0)))
10306    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10307         (neg:HI (match_dup 1)))]
10308   "ix86_unary_operator_ok (NEG, HImode, operands)"
10309   "neg{w}\t%0"
10310   [(set_attr "type" "negnot")
10311    (set_attr "mode" "HI")])
10312
10313 (define_expand "negqi2"
10314   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
10315                    (neg:QI (match_operand:QI 1 "nonimmediate_operand" "")))
10316               (clobber (reg:CC FLAGS_REG))])]
10317   "TARGET_QIMODE_MATH"
10318   "ix86_expand_unary_operator (NEG, QImode, operands); DONE;")
10319
10320 (define_insn "*negqi2_1"
10321   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10322         (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0")))
10323    (clobber (reg:CC FLAGS_REG))]
10324   "ix86_unary_operator_ok (NEG, QImode, operands)"
10325   "neg{b}\t%0"
10326   [(set_attr "type" "negnot")
10327    (set_attr "mode" "QI")])
10328
10329 (define_insn "*negqi2_cmpz"
10330   [(set (reg:CCZ FLAGS_REG)
10331         (compare:CCZ (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
10332                      (const_int 0)))
10333    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10334         (neg:QI (match_dup 1)))]
10335   "ix86_unary_operator_ok (NEG, QImode, operands)"
10336   "neg{b}\t%0"
10337   [(set_attr "type" "negnot")
10338    (set_attr "mode" "QI")])
10339
10340 ;; Changing of sign for FP values is doable using integer unit too.
10341
10342 (define_expand "<code><mode>2"
10343   [(set (match_operand:X87MODEF 0 "register_operand" "")
10344         (absneg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "")))]
10345   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
10346   "ix86_expand_fp_absneg_operator (<CODE>, <MODE>mode, operands); DONE;")
10347
10348 (define_insn "*absneg<mode>2_mixed"
10349   [(set (match_operand:MODEF 0 "register_operand" "=x,x,f,!r")
10350         (match_operator:MODEF 3 "absneg_operator"
10351           [(match_operand:MODEF 1 "register_operand" "0,x,0,0")]))
10352    (use (match_operand:<ssevecmode> 2 "nonimmediate_operand" "xm,0,X,X"))
10353    (clobber (reg:CC FLAGS_REG))]
10354   "TARGET_MIX_SSE_I387 && SSE_FLOAT_MODE_P (<MODE>mode)"
10355   "#")
10356
10357 (define_insn "*absneg<mode>2_sse"
10358   [(set (match_operand:MODEF 0 "register_operand" "=x,x,!r")
10359         (match_operator:MODEF 3 "absneg_operator"
10360           [(match_operand:MODEF 1 "register_operand" "0 ,x,0")]))
10361    (use (match_operand:<ssevecmode> 2 "register_operand" "xm,0,X"))
10362    (clobber (reg:CC FLAGS_REG))]
10363   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
10364   "#")
10365
10366 (define_insn "*absneg<mode>2_i387"
10367   [(set (match_operand:X87MODEF 0 "register_operand" "=f,!r")
10368         (match_operator:X87MODEF 3 "absneg_operator"
10369           [(match_operand:X87MODEF 1 "register_operand" "0,0")]))
10370    (use (match_operand 2 "" ""))
10371    (clobber (reg:CC FLAGS_REG))]
10372   "TARGET_80387 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
10373   "#")
10374
10375 (define_expand "<code>tf2"
10376   [(set (match_operand:TF 0 "register_operand" "")
10377         (absneg:TF (match_operand:TF 1 "register_operand" "")))]
10378   "TARGET_64BIT"
10379   "ix86_expand_fp_absneg_operator (<CODE>, TFmode, operands); DONE;")
10380
10381 (define_insn "*absnegtf2_sse"
10382   [(set (match_operand:TF 0 "register_operand" "=x,x")
10383         (match_operator:TF 3 "absneg_operator"
10384           [(match_operand:TF 1 "register_operand" "0,x")]))
10385    (use (match_operand:TF 2 "nonimmediate_operand" "xm,0"))
10386    (clobber (reg:CC FLAGS_REG))]
10387   "TARGET_64BIT"
10388   "#")
10389
10390 ;; Splitters for fp abs and neg.
10391
10392 (define_split
10393   [(set (match_operand 0 "fp_register_operand" "")
10394         (match_operator 1 "absneg_operator" [(match_dup 0)]))
10395    (use (match_operand 2 "" ""))
10396    (clobber (reg:CC FLAGS_REG))]
10397   "reload_completed"
10398   [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))])
10399
10400 (define_split
10401   [(set (match_operand 0 "register_operand" "")
10402         (match_operator 3 "absneg_operator"
10403           [(match_operand 1 "register_operand" "")]))
10404    (use (match_operand 2 "nonimmediate_operand" ""))
10405    (clobber (reg:CC FLAGS_REG))]
10406   "reload_completed && SSE_REG_P (operands[0])"
10407   [(set (match_dup 0) (match_dup 3))]
10408 {
10409   enum machine_mode mode = GET_MODE (operands[0]);
10410   enum machine_mode vmode = GET_MODE (operands[2]);
10411   rtx tmp;
10412
10413   operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0);
10414   operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0);
10415   if (operands_match_p (operands[0], operands[2]))
10416     {
10417       tmp = operands[1];
10418       operands[1] = operands[2];
10419       operands[2] = tmp;
10420     }
10421   if (GET_CODE (operands[3]) == ABS)
10422     tmp = gen_rtx_AND (vmode, operands[1], operands[2]);
10423   else
10424     tmp = gen_rtx_XOR (vmode, operands[1], operands[2]);
10425   operands[3] = tmp;
10426 })
10427
10428 (define_split
10429   [(set (match_operand:SF 0 "register_operand" "")
10430         (match_operator:SF 1 "absneg_operator" [(match_dup 0)]))
10431    (use (match_operand:V4SF 2 "" ""))
10432    (clobber (reg:CC FLAGS_REG))]
10433   "reload_completed"
10434   [(parallel [(set (match_dup 0) (match_dup 1))
10435               (clobber (reg:CC FLAGS_REG))])]
10436 {
10437   rtx tmp;
10438   operands[0] = gen_lowpart (SImode, operands[0]);
10439   if (GET_CODE (operands[1]) == ABS)
10440     {
10441       tmp = gen_int_mode (0x7fffffff, SImode);
10442       tmp = gen_rtx_AND (SImode, operands[0], tmp);
10443     }
10444   else
10445     {
10446       tmp = gen_int_mode (0x80000000, SImode);
10447       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
10448     }
10449   operands[1] = tmp;
10450 })
10451
10452 (define_split
10453   [(set (match_operand:DF 0 "register_operand" "")
10454         (match_operator:DF 1 "absneg_operator" [(match_dup 0)]))
10455    (use (match_operand 2 "" ""))
10456    (clobber (reg:CC FLAGS_REG))]
10457   "reload_completed"
10458   [(parallel [(set (match_dup 0) (match_dup 1))
10459               (clobber (reg:CC FLAGS_REG))])]
10460 {
10461   rtx tmp;
10462   if (TARGET_64BIT)
10463     {
10464       tmp = gen_lowpart (DImode, operands[0]);
10465       tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63));
10466       operands[0] = tmp;
10467
10468       if (GET_CODE (operands[1]) == ABS)
10469         tmp = const0_rtx;
10470       else
10471         tmp = gen_rtx_NOT (DImode, tmp);
10472     }
10473   else
10474     {
10475       operands[0] = gen_highpart (SImode, operands[0]);
10476       if (GET_CODE (operands[1]) == ABS)
10477         {
10478           tmp = gen_int_mode (0x7fffffff, SImode);
10479           tmp = gen_rtx_AND (SImode, operands[0], tmp);
10480         }
10481       else
10482         {
10483           tmp = gen_int_mode (0x80000000, SImode);
10484           tmp = gen_rtx_XOR (SImode, operands[0], tmp);
10485         }
10486     }
10487   operands[1] = tmp;
10488 })
10489
10490 (define_split
10491   [(set (match_operand:XF 0 "register_operand" "")
10492         (match_operator:XF 1 "absneg_operator" [(match_dup 0)]))
10493    (use (match_operand 2 "" ""))
10494    (clobber (reg:CC FLAGS_REG))]
10495   "reload_completed"
10496   [(parallel [(set (match_dup 0) (match_dup 1))
10497               (clobber (reg:CC FLAGS_REG))])]
10498 {
10499   rtx tmp;
10500   operands[0] = gen_rtx_REG (SImode,
10501                              true_regnum (operands[0])
10502                              + (TARGET_64BIT ? 1 : 2));
10503   if (GET_CODE (operands[1]) == ABS)
10504     {
10505       tmp = GEN_INT (0x7fff);
10506       tmp = gen_rtx_AND (SImode, operands[0], tmp);
10507     }
10508   else
10509     {
10510       tmp = GEN_INT (0x8000);
10511       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
10512     }
10513   operands[1] = tmp;
10514 })
10515
10516 ;; Conditionalize these after reload. If they match before reload, we
10517 ;; lose the clobber and ability to use integer instructions.
10518
10519 (define_insn "*<code><mode>2_1"
10520   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
10521         (absneg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "0")))]
10522   "TARGET_80387
10523    && (reload_completed
10524        || !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
10525   "f<absnegprefix>"
10526   [(set_attr "type" "fsgn")
10527    (set_attr "mode" "<MODE>")])
10528
10529 (define_insn "*<code>extendsfdf2"
10530   [(set (match_operand:DF 0 "register_operand" "=f")
10531         (absneg:DF (float_extend:DF
10532                      (match_operand:SF 1 "register_operand" "0"))))]
10533   "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
10534   "f<absnegprefix>"
10535   [(set_attr "type" "fsgn")
10536    (set_attr "mode" "DF")])
10537
10538 (define_insn "*<code>extendsfxf2"
10539   [(set (match_operand:XF 0 "register_operand" "=f")
10540         (absneg:XF (float_extend:XF
10541                      (match_operand:SF 1 "register_operand" "0"))))]
10542   "TARGET_80387"
10543   "f<absnegprefix>"
10544   [(set_attr "type" "fsgn")
10545    (set_attr "mode" "XF")])
10546
10547 (define_insn "*<code>extenddfxf2"
10548   [(set (match_operand:XF 0 "register_operand" "=f")
10549         (absneg:XF (float_extend:XF
10550                       (match_operand:DF 1 "register_operand" "0"))))]
10551   "TARGET_80387"
10552   "f<absnegprefix>"
10553   [(set_attr "type" "fsgn")
10554    (set_attr "mode" "XF")])
10555
10556 ;; Copysign instructions
10557
10558 (define_mode_iterator CSGNMODE [SF DF TF])
10559 (define_mode_attr CSGNVMODE [(SF "V4SF") (DF "V2DF") (TF "TF")])
10560
10561 (define_expand "copysign<mode>3"
10562   [(match_operand:CSGNMODE 0 "register_operand" "")
10563    (match_operand:CSGNMODE 1 "nonmemory_operand" "")
10564    (match_operand:CSGNMODE 2 "register_operand" "")]
10565   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
10566    || (TARGET_64BIT && (<MODE>mode == TFmode))"
10567 {
10568   ix86_expand_copysign (operands);
10569   DONE;
10570 })
10571
10572 (define_insn_and_split "copysign<mode>3_const"
10573   [(set (match_operand:CSGNMODE 0 "register_operand" "=x")
10574         (unspec:CSGNMODE
10575           [(match_operand:<CSGNVMODE> 1 "vector_move_operand" "xmC")
10576            (match_operand:CSGNMODE 2 "register_operand" "0")
10577            (match_operand:<CSGNVMODE> 3 "nonimmediate_operand" "xm")]
10578           UNSPEC_COPYSIGN))]
10579   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
10580    || (TARGET_64BIT && (<MODE>mode == TFmode))"
10581   "#"
10582   "&& reload_completed"
10583   [(const_int 0)]
10584 {
10585   ix86_split_copysign_const (operands);
10586   DONE;
10587 })
10588
10589 (define_insn "copysign<mode>3_var"
10590   [(set (match_operand:CSGNMODE 0 "register_operand" "=x,x,x,x,x")
10591         (unspec:CSGNMODE
10592           [(match_operand:CSGNMODE 2 "register_operand" "x,0,0,x,x")
10593            (match_operand:CSGNMODE 3 "register_operand" "1,1,x,1,x")
10594            (match_operand:<CSGNVMODE> 4 "nonimmediate_operand" "X,xm,xm,0,0")
10595            (match_operand:<CSGNVMODE> 5 "nonimmediate_operand" "0,xm,1,xm,1")]
10596           UNSPEC_COPYSIGN))
10597    (clobber (match_scratch:<CSGNVMODE> 1 "=x,x,x,x,x"))]
10598   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
10599    || (TARGET_64BIT && (<MODE>mode == TFmode))"
10600   "#")
10601
10602 (define_split
10603   [(set (match_operand:CSGNMODE 0 "register_operand" "")
10604         (unspec:CSGNMODE
10605           [(match_operand:CSGNMODE 2 "register_operand" "")
10606            (match_operand:CSGNMODE 3 "register_operand" "")
10607            (match_operand:<CSGNVMODE> 4 "" "")
10608            (match_operand:<CSGNVMODE> 5 "" "")]
10609           UNSPEC_COPYSIGN))
10610    (clobber (match_scratch:<CSGNVMODE> 1 ""))]
10611   "((SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
10612     || (TARGET_64BIT && (<MODE>mode == TFmode)))
10613    && reload_completed"
10614   [(const_int 0)]
10615 {
10616   ix86_split_copysign_var (operands);
10617   DONE;
10618 })
10619 \f
10620 ;; One complement instructions
10621
10622 (define_expand "one_cmpldi2"
10623   [(set (match_operand:DI 0 "nonimmediate_operand" "")
10624         (not:DI (match_operand:DI 1 "nonimmediate_operand" "")))]
10625   "TARGET_64BIT"
10626   "ix86_expand_unary_operator (NOT, DImode, operands); DONE;")
10627
10628 (define_insn "*one_cmpldi2_1_rex64"
10629   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10630         (not:DI (match_operand:DI 1 "nonimmediate_operand" "0")))]
10631   "TARGET_64BIT && ix86_unary_operator_ok (NOT, DImode, operands)"
10632   "not{q}\t%0"
10633   [(set_attr "type" "negnot")
10634    (set_attr "mode" "DI")])
10635
10636 (define_insn "*one_cmpldi2_2_rex64"
10637   [(set (reg FLAGS_REG)
10638         (compare (not:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
10639                  (const_int 0)))
10640    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10641         (not:DI (match_dup 1)))]
10642   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10643    && ix86_unary_operator_ok (NOT, DImode, operands)"
10644   "#"
10645   [(set_attr "type" "alu1")
10646    (set_attr "mode" "DI")])
10647
10648 (define_split
10649   [(set (match_operand 0 "flags_reg_operand" "")
10650         (match_operator 2 "compare_operator"
10651           [(not:DI (match_operand:DI 3 "nonimmediate_operand" ""))
10652            (const_int 0)]))
10653    (set (match_operand:DI 1 "nonimmediate_operand" "")
10654         (not:DI (match_dup 3)))]
10655   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
10656   [(parallel [(set (match_dup 0)
10657                    (match_op_dup 2
10658                      [(xor:DI (match_dup 3) (const_int -1))
10659                       (const_int 0)]))
10660               (set (match_dup 1)
10661                    (xor:DI (match_dup 3) (const_int -1)))])]
10662   "")
10663
10664 (define_expand "one_cmplsi2"
10665   [(set (match_operand:SI 0 "nonimmediate_operand" "")
10666         (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
10667   ""
10668   "ix86_expand_unary_operator (NOT, SImode, operands); DONE;")
10669
10670 (define_insn "*one_cmplsi2_1"
10671   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10672         (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))]
10673   "ix86_unary_operator_ok (NOT, SImode, operands)"
10674   "not{l}\t%0"
10675   [(set_attr "type" "negnot")
10676    (set_attr "mode" "SI")])
10677
10678 ;; ??? Currently never generated - xor is used instead.
10679 (define_insn "*one_cmplsi2_1_zext"
10680   [(set (match_operand:DI 0 "register_operand" "=r")
10681         (zero_extend:DI (not:SI (match_operand:SI 1 "register_operand" "0"))))]
10682   "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
10683   "not{l}\t%k0"
10684   [(set_attr "type" "negnot")
10685    (set_attr "mode" "SI")])
10686
10687 (define_insn "*one_cmplsi2_2"
10688   [(set (reg FLAGS_REG)
10689         (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
10690                  (const_int 0)))
10691    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10692         (not:SI (match_dup 1)))]
10693   "ix86_match_ccmode (insn, CCNOmode)
10694    && ix86_unary_operator_ok (NOT, SImode, operands)"
10695   "#"
10696   [(set_attr "type" "alu1")
10697    (set_attr "mode" "SI")])
10698
10699 (define_split
10700   [(set (match_operand 0 "flags_reg_operand" "")
10701         (match_operator 2 "compare_operator"
10702           [(not:SI (match_operand:SI 3 "nonimmediate_operand" ""))
10703            (const_int 0)]))
10704    (set (match_operand:SI 1 "nonimmediate_operand" "")
10705         (not:SI (match_dup 3)))]
10706   "ix86_match_ccmode (insn, CCNOmode)"
10707   [(parallel [(set (match_dup 0)
10708                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
10709                                     (const_int 0)]))
10710               (set (match_dup 1)
10711                    (xor:SI (match_dup 3) (const_int -1)))])]
10712   "")
10713
10714 ;; ??? Currently never generated - xor is used instead.
10715 (define_insn "*one_cmplsi2_2_zext"
10716   [(set (reg FLAGS_REG)
10717         (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
10718                  (const_int 0)))
10719    (set (match_operand:DI 0 "register_operand" "=r")
10720         (zero_extend:DI (not:SI (match_dup 1))))]
10721   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10722    && ix86_unary_operator_ok (NOT, SImode, operands)"
10723   "#"
10724   [(set_attr "type" "alu1")
10725    (set_attr "mode" "SI")])
10726
10727 (define_split
10728   [(set (match_operand 0 "flags_reg_operand" "")
10729         (match_operator 2 "compare_operator"
10730           [(not:SI (match_operand:SI 3 "register_operand" ""))
10731            (const_int 0)]))
10732    (set (match_operand:DI 1 "register_operand" "")
10733         (zero_extend:DI (not:SI (match_dup 3))))]
10734   "ix86_match_ccmode (insn, CCNOmode)"
10735   [(parallel [(set (match_dup 0)
10736                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
10737                                     (const_int 0)]))
10738               (set (match_dup 1)
10739                    (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])]
10740   "")
10741
10742 (define_expand "one_cmplhi2"
10743   [(set (match_operand:HI 0 "nonimmediate_operand" "")
10744         (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
10745   "TARGET_HIMODE_MATH"
10746   "ix86_expand_unary_operator (NOT, HImode, operands); DONE;")
10747
10748 (define_insn "*one_cmplhi2_1"
10749   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10750         (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))]
10751   "ix86_unary_operator_ok (NOT, HImode, operands)"
10752   "not{w}\t%0"
10753   [(set_attr "type" "negnot")
10754    (set_attr "mode" "HI")])
10755
10756 (define_insn "*one_cmplhi2_2"
10757   [(set (reg FLAGS_REG)
10758         (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
10759                  (const_int 0)))
10760    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10761         (not:HI (match_dup 1)))]
10762   "ix86_match_ccmode (insn, CCNOmode)
10763    && ix86_unary_operator_ok (NEG, HImode, operands)"
10764   "#"
10765   [(set_attr "type" "alu1")
10766    (set_attr "mode" "HI")])
10767
10768 (define_split
10769   [(set (match_operand 0 "flags_reg_operand" "")
10770         (match_operator 2 "compare_operator"
10771           [(not:HI (match_operand:HI 3 "nonimmediate_operand" ""))
10772            (const_int 0)]))
10773    (set (match_operand:HI 1 "nonimmediate_operand" "")
10774         (not:HI (match_dup 3)))]
10775   "ix86_match_ccmode (insn, CCNOmode)"
10776   [(parallel [(set (match_dup 0)
10777                    (match_op_dup 2 [(xor:HI (match_dup 3) (const_int -1))
10778                                     (const_int 0)]))
10779               (set (match_dup 1)
10780                    (xor:HI (match_dup 3) (const_int -1)))])]
10781   "")
10782
10783 ;; %%% Potential partial reg stall on alternative 1.  What to do?
10784 (define_expand "one_cmplqi2"
10785   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10786         (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
10787   "TARGET_QIMODE_MATH"
10788   "ix86_expand_unary_operator (NOT, QImode, operands); DONE;")
10789
10790 (define_insn "*one_cmplqi2_1"
10791   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10792         (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
10793   "ix86_unary_operator_ok (NOT, QImode, operands)"
10794   "@
10795    not{b}\t%0
10796    not{l}\t%k0"
10797   [(set_attr "type" "negnot")
10798    (set_attr "mode" "QI,SI")])
10799
10800 (define_insn "*one_cmplqi2_2"
10801   [(set (reg FLAGS_REG)
10802         (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
10803                  (const_int 0)))
10804    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10805         (not:QI (match_dup 1)))]
10806   "ix86_match_ccmode (insn, CCNOmode)
10807    && ix86_unary_operator_ok (NOT, QImode, operands)"
10808   "#"
10809   [(set_attr "type" "alu1")
10810    (set_attr "mode" "QI")])
10811
10812 (define_split
10813   [(set (match_operand 0 "flags_reg_operand" "")
10814         (match_operator 2 "compare_operator"
10815           [(not:QI (match_operand:QI 3 "nonimmediate_operand" ""))
10816            (const_int 0)]))
10817    (set (match_operand:QI 1 "nonimmediate_operand" "")
10818         (not:QI (match_dup 3)))]
10819   "ix86_match_ccmode (insn, CCNOmode)"
10820   [(parallel [(set (match_dup 0)
10821                    (match_op_dup 2 [(xor:QI (match_dup 3) (const_int -1))
10822                                     (const_int 0)]))
10823               (set (match_dup 1)
10824                    (xor:QI (match_dup 3) (const_int -1)))])]
10825   "")
10826 \f
10827 ;; Arithmetic shift instructions
10828
10829 ;; DImode shifts are implemented using the i386 "shift double" opcode,
10830 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem".  If the shift count
10831 ;; is variable, then the count is in %cl and the "imm" operand is dropped
10832 ;; from the assembler input.
10833 ;;
10834 ;; This instruction shifts the target reg/mem as usual, but instead of
10835 ;; shifting in zeros, bits are shifted in from reg operand.  If the insn
10836 ;; is a left shift double, bits are taken from the high order bits of
10837 ;; reg, else if the insn is a shift right double, bits are taken from the
10838 ;; low order bits of reg.  So if %eax is "1234" and %edx is "5678",
10839 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
10840 ;;
10841 ;; Since sh[lr]d does not change the `reg' operand, that is done
10842 ;; separately, making all shifts emit pairs of shift double and normal
10843 ;; shift.  Since sh[lr]d does not shift more than 31 bits, and we wish to
10844 ;; support a 63 bit shift, each shift where the count is in a reg expands
10845 ;; to a pair of shifts, a branch, a shift by 32 and a label.
10846 ;;
10847 ;; If the shift count is a constant, we need never emit more than one
10848 ;; shift pair, instead using moves and sign extension for counts greater
10849 ;; than 31.
10850
10851 (define_expand "ashlti3"
10852   [(parallel [(set (match_operand:TI 0 "register_operand" "")
10853                    (ashift:TI (match_operand:TI 1 "register_operand" "")
10854                               (match_operand:QI 2 "nonmemory_operand" "")))
10855               (clobber (reg:CC FLAGS_REG))])]
10856   "TARGET_64BIT"
10857 {
10858   if (! immediate_operand (operands[2], QImode))
10859     {
10860       emit_insn (gen_ashlti3_1 (operands[0], operands[1], operands[2]));
10861       DONE;
10862     }
10863   ix86_expand_binary_operator (ASHIFT, TImode, operands);
10864   DONE;
10865 })
10866
10867 (define_insn "ashlti3_1"
10868   [(set (match_operand:TI 0 "register_operand" "=r")
10869         (ashift:TI (match_operand:TI 1 "register_operand" "0")
10870                    (match_operand:QI 2 "register_operand" "c")))
10871    (clobber (match_scratch:DI 3 "=&r"))
10872    (clobber (reg:CC FLAGS_REG))]
10873   "TARGET_64BIT"
10874   "#"
10875   [(set_attr "type" "multi")])
10876
10877 ;; This pattern must be defined before *ashlti3_2 to prevent
10878 ;; combine pass from converting sse2_ashlti3 to *ashlti3_2.
10879
10880 (define_insn "sse2_ashlti3"
10881   [(set (match_operand:TI 0 "register_operand" "=x")
10882         (ashift:TI (match_operand:TI 1 "register_operand" "0")
10883                    (match_operand:SI 2 "const_0_to_255_mul_8_operand" "n")))]
10884   "TARGET_SSE2"
10885 {
10886   operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
10887   return "pslldq\t{%2, %0|%0, %2}";
10888 }
10889   [(set_attr "type" "sseishft")
10890    (set_attr "prefix_data16" "1")
10891    (set_attr "mode" "TI")])
10892
10893 (define_insn "*ashlti3_2"
10894   [(set (match_operand:TI 0 "register_operand" "=r")
10895         (ashift:TI (match_operand:TI 1 "register_operand" "0")
10896                    (match_operand:QI 2 "immediate_operand" "O")))
10897    (clobber (reg:CC FLAGS_REG))]
10898   "TARGET_64BIT"
10899   "#"
10900   [(set_attr "type" "multi")])
10901
10902 (define_split
10903   [(set (match_operand:TI 0 "register_operand" "")
10904         (ashift:TI (match_operand:TI 1 "nonmemory_operand" "")
10905                    (match_operand:QI 2 "register_operand" "")))
10906    (clobber (match_scratch:DI 3 ""))
10907    (clobber (reg:CC FLAGS_REG))]
10908   "TARGET_64BIT && reload_completed"
10909   [(const_int 0)]
10910   "ix86_split_ashl (operands, operands[3], TImode); DONE;")
10911
10912 (define_split
10913   [(set (match_operand:TI 0 "register_operand" "")
10914         (ashift:TI (match_operand:TI 1 "register_operand" "")
10915                    (match_operand:QI 2 "immediate_operand" "")))
10916    (clobber (reg:CC FLAGS_REG))]
10917   "TARGET_64BIT && reload_completed"
10918   [(const_int 0)]
10919   "ix86_split_ashl (operands, NULL_RTX, TImode); DONE;")
10920
10921 (define_insn "x86_64_shld"
10922   [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m,r*m")
10923         (ior:DI (ashift:DI (match_dup 0)
10924                   (match_operand:QI 2 "nonmemory_operand" "J,c"))
10925                 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r,r")
10926                   (minus:QI (const_int 64) (match_dup 2)))))
10927    (clobber (reg:CC FLAGS_REG))]
10928   "TARGET_64BIT"
10929   "@
10930    shld{q}\t{%2, %1, %0|%0, %1, %2}
10931    shld{q}\t{%s2%1, %0|%0, %1, %2}"
10932   [(set_attr "type" "ishift")
10933    (set_attr "prefix_0f" "1")
10934    (set_attr "mode" "DI")
10935    (set_attr "athlon_decode" "vector")
10936    (set_attr "amdfam10_decode" "vector")])
10937
10938 (define_expand "x86_64_shift_adj"
10939   [(set (reg:CCZ FLAGS_REG)
10940         (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
10941                              (const_int 64))
10942                      (const_int 0)))
10943    (set (match_operand:DI 0 "register_operand" "")
10944         (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10945                          (match_operand:DI 1 "register_operand" "")
10946                          (match_dup 0)))
10947    (set (match_dup 1)
10948         (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10949                          (match_operand:DI 3 "register_operand" "r")
10950                          (match_dup 1)))]
10951   "TARGET_64BIT"
10952   "")
10953
10954 (define_expand "ashldi3"
10955   [(set (match_operand:DI 0 "shiftdi_operand" "")
10956         (ashift:DI (match_operand:DI 1 "ashldi_input_operand" "")
10957                    (match_operand:QI 2 "nonmemory_operand" "")))]
10958   ""
10959   "ix86_expand_binary_operator (ASHIFT, DImode, operands); DONE;")
10960
10961 (define_insn "*ashldi3_1_rex64"
10962   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
10963         (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0,l")
10964                    (match_operand:QI 2 "nonmemory_operand" "cJ,M")))
10965    (clobber (reg:CC FLAGS_REG))]
10966   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10967 {
10968   switch (get_attr_type (insn))
10969     {
10970     case TYPE_ALU:
10971       gcc_assert (operands[2] == const1_rtx);
10972       gcc_assert (rtx_equal_p (operands[0], operands[1]));
10973       return "add{q}\t%0, %0";
10974
10975     case TYPE_LEA:
10976       gcc_assert (CONST_INT_P (operands[2]));
10977       gcc_assert ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) <= 3);
10978       operands[1] = gen_rtx_MULT (DImode, operands[1],
10979                                   GEN_INT (1 << INTVAL (operands[2])));
10980       return "lea{q}\t{%a1, %0|%0, %a1}";
10981
10982     default:
10983       if (REG_P (operands[2]))
10984         return "sal{q}\t{%b2, %0|%0, %b2}";
10985       else if (operands[2] == const1_rtx
10986                && (TARGET_SHIFT1 || optimize_size))
10987         return "sal{q}\t%0";
10988       else
10989         return "sal{q}\t{%2, %0|%0, %2}";
10990     }
10991 }
10992   [(set (attr "type")
10993      (cond [(eq_attr "alternative" "1")
10994               (const_string "lea")
10995             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10996                           (const_int 0))
10997                       (match_operand 0 "register_operand" ""))
10998                  (match_operand 2 "const1_operand" ""))
10999               (const_string "alu")
11000            ]
11001            (const_string "ishift")))
11002    (set_attr "mode" "DI")])
11003
11004 ;; Convert lea to the lea pattern to avoid flags dependency.
11005 (define_split
11006   [(set (match_operand:DI 0 "register_operand" "")
11007         (ashift:DI (match_operand:DI 1 "index_register_operand" "")
11008                    (match_operand:QI 2 "immediate_operand" "")))
11009    (clobber (reg:CC FLAGS_REG))]
11010   "TARGET_64BIT && reload_completed
11011    && true_regnum (operands[0]) != true_regnum (operands[1])"
11012   [(set (match_dup 0)
11013         (mult:DI (match_dup 1)
11014                  (match_dup 2)))]
11015   "operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);")
11016
11017 ;; This pattern can't accept a variable shift count, since shifts by
11018 ;; zero don't affect the flags.  We assume that shifts by constant
11019 ;; zero are optimized away.
11020 (define_insn "*ashldi3_cmp_rex64"
11021   [(set (reg FLAGS_REG)
11022         (compare
11023           (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11024                      (match_operand:QI 2 "immediate_operand" "e"))
11025           (const_int 0)))
11026    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11027         (ashift:DI (match_dup 1) (match_dup 2)))]
11028   "TARGET_64BIT
11029    && (optimize_size
11030        || !TARGET_PARTIAL_FLAG_REG_STALL
11031        || (operands[2] == const1_rtx
11032            && (TARGET_SHIFT1
11033                || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
11034    && ix86_match_ccmode (insn, CCGOCmode)
11035    && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
11036 {
11037   switch (get_attr_type (insn))
11038     {
11039     case TYPE_ALU:
11040       gcc_assert (operands[2] == const1_rtx);
11041       return "add{q}\t%0, %0";
11042
11043     default:
11044       if (REG_P (operands[2]))
11045         return "sal{q}\t{%b2, %0|%0, %b2}";
11046       else if (operands[2] == const1_rtx
11047                && (TARGET_SHIFT1 || optimize_size))
11048         return "sal{q}\t%0";
11049       else
11050         return "sal{q}\t{%2, %0|%0, %2}";
11051     }
11052 }
11053   [(set (attr "type")
11054      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11055                           (const_int 0))
11056                       (match_operand 0 "register_operand" ""))
11057                  (match_operand 2 "const1_operand" ""))
11058               (const_string "alu")
11059            ]
11060            (const_string "ishift")))
11061    (set_attr "mode" "DI")])
11062
11063 (define_insn "*ashldi3_cconly_rex64"
11064   [(set (reg FLAGS_REG)
11065         (compare
11066           (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11067                      (match_operand:QI 2 "immediate_operand" "e"))
11068           (const_int 0)))
11069    (clobber (match_scratch:DI 0 "=r"))]
11070   "TARGET_64BIT
11071    && (optimize_size
11072        || !TARGET_PARTIAL_FLAG_REG_STALL
11073        || (operands[2] == const1_rtx
11074            && (TARGET_SHIFT1
11075                || TARGET_DOUBLE_WITH_ADD)))
11076    && ix86_match_ccmode (insn, CCGOCmode)
11077    && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
11078 {
11079   switch (get_attr_type (insn))
11080     {
11081     case TYPE_ALU:
11082       gcc_assert (operands[2] == const1_rtx);
11083       return "add{q}\t%0, %0";
11084
11085     default:
11086       if (REG_P (operands[2]))
11087         return "sal{q}\t{%b2, %0|%0, %b2}";
11088       else if (operands[2] == const1_rtx
11089                && (TARGET_SHIFT1 || optimize_size))
11090         return "sal{q}\t%0";
11091       else
11092         return "sal{q}\t{%2, %0|%0, %2}";
11093     }
11094 }
11095   [(set (attr "type")
11096      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11097                           (const_int 0))
11098                       (match_operand 0 "register_operand" ""))
11099                  (match_operand 2 "const1_operand" ""))
11100               (const_string "alu")
11101            ]
11102            (const_string "ishift")))
11103    (set_attr "mode" "DI")])
11104
11105 (define_insn "*ashldi3_1"
11106   [(set (match_operand:DI 0 "register_operand" "=&r,r")
11107         (ashift:DI (match_operand:DI 1 "reg_or_pm1_operand" "n,0")
11108                    (match_operand:QI 2 "nonmemory_operand" "Jc,Jc")))
11109    (clobber (reg:CC FLAGS_REG))]
11110   "!TARGET_64BIT"
11111   "#"
11112   [(set_attr "type" "multi")])
11113
11114 ;; By default we don't ask for a scratch register, because when DImode
11115 ;; values are manipulated, registers are already at a premium.  But if
11116 ;; we have one handy, we won't turn it away.
11117 (define_peephole2
11118   [(match_scratch:SI 3 "r")
11119    (parallel [(set (match_operand:DI 0 "register_operand" "")
11120                    (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
11121                               (match_operand:QI 2 "nonmemory_operand" "")))
11122               (clobber (reg:CC FLAGS_REG))])
11123    (match_dup 3)]
11124   "!TARGET_64BIT && TARGET_CMOVE"
11125   [(const_int 0)]
11126   "ix86_split_ashl (operands, operands[3], DImode); DONE;")
11127
11128 (define_split
11129   [(set (match_operand:DI 0 "register_operand" "")
11130         (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
11131                    (match_operand:QI 2 "nonmemory_operand" "")))
11132    (clobber (reg:CC FLAGS_REG))]
11133   "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
11134                      ? epilogue_completed : reload_completed)"
11135   [(const_int 0)]
11136   "ix86_split_ashl (operands, NULL_RTX, DImode); DONE;")
11137
11138 (define_insn "x86_shld_1"
11139   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
11140         (ior:SI (ashift:SI (match_dup 0)
11141                   (match_operand:QI 2 "nonmemory_operand" "I,c"))
11142                 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
11143                   (minus:QI (const_int 32) (match_dup 2)))))
11144    (clobber (reg:CC FLAGS_REG))]
11145   ""
11146   "@
11147    shld{l}\t{%2, %1, %0|%0, %1, %2}
11148    shld{l}\t{%s2%1, %0|%0, %1, %2}"
11149   [(set_attr "type" "ishift")
11150    (set_attr "prefix_0f" "1")
11151    (set_attr "mode" "SI")
11152    (set_attr "pent_pair" "np")
11153    (set_attr "athlon_decode" "vector")
11154    (set_attr "amdfam10_decode" "vector")])
11155
11156 (define_expand "x86_shift_adj_1"
11157   [(set (reg:CCZ FLAGS_REG)
11158         (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
11159                              (const_int 32))
11160                      (const_int 0)))
11161    (set (match_operand:SI 0 "register_operand" "")
11162         (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
11163                          (match_operand:SI 1 "register_operand" "")
11164                          (match_dup 0)))
11165    (set (match_dup 1)
11166         (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
11167                          (match_operand:SI 3 "register_operand" "r")
11168                          (match_dup 1)))]
11169   "TARGET_CMOVE"
11170   "")
11171
11172 (define_expand "x86_shift_adj_2"
11173   [(use (match_operand:SI 0 "register_operand" ""))
11174    (use (match_operand:SI 1 "register_operand" ""))
11175    (use (match_operand:QI 2 "register_operand" ""))]
11176   ""
11177 {
11178   rtx label = gen_label_rtx ();
11179   rtx tmp;
11180
11181   emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
11182
11183   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
11184   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
11185   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
11186                               gen_rtx_LABEL_REF (VOIDmode, label),
11187                               pc_rtx);
11188   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
11189   JUMP_LABEL (tmp) = label;
11190
11191   emit_move_insn (operands[0], operands[1]);
11192   ix86_expand_clear (operands[1]);
11193
11194   emit_label (label);
11195   LABEL_NUSES (label) = 1;
11196
11197   DONE;
11198 })
11199
11200 (define_expand "ashlsi3"
11201   [(set (match_operand:SI 0 "nonimmediate_operand" "")
11202         (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
11203                    (match_operand:QI 2 "nonmemory_operand" "")))
11204    (clobber (reg:CC FLAGS_REG))]
11205   ""
11206   "ix86_expand_binary_operator (ASHIFT, SImode, operands); DONE;")
11207
11208 (define_insn "*ashlsi3_1"
11209   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
11210         (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l")
11211                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
11212    (clobber (reg:CC FLAGS_REG))]
11213   "ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11214 {
11215   switch (get_attr_type (insn))
11216     {
11217     case TYPE_ALU:
11218       gcc_assert (operands[2] == const1_rtx);
11219       gcc_assert (rtx_equal_p (operands[0], operands[1]));
11220       return "add{l}\t%0, %0";
11221
11222     case TYPE_LEA:
11223       return "#";
11224
11225     default:
11226       if (REG_P (operands[2]))
11227         return "sal{l}\t{%b2, %0|%0, %b2}";
11228       else if (operands[2] == const1_rtx
11229                && (TARGET_SHIFT1 || optimize_size))
11230         return "sal{l}\t%0";
11231       else
11232         return "sal{l}\t{%2, %0|%0, %2}";
11233     }
11234 }
11235   [(set (attr "type")
11236      (cond [(eq_attr "alternative" "1")
11237               (const_string "lea")
11238             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11239                           (const_int 0))
11240                       (match_operand 0 "register_operand" ""))
11241                  (match_operand 2 "const1_operand" ""))
11242               (const_string "alu")
11243            ]
11244            (const_string "ishift")))
11245    (set_attr "mode" "SI")])
11246
11247 ;; Convert lea to the lea pattern to avoid flags dependency.
11248 (define_split
11249   [(set (match_operand 0 "register_operand" "")
11250         (ashift (match_operand 1 "index_register_operand" "")
11251                 (match_operand:QI 2 "const_int_operand" "")))
11252    (clobber (reg:CC FLAGS_REG))]
11253   "reload_completed
11254    && true_regnum (operands[0]) != true_regnum (operands[1])
11255    && GET_MODE_SIZE (GET_MODE (operands[0])) <= 4"
11256   [(const_int 0)]
11257 {
11258   rtx pat;
11259   enum machine_mode mode = GET_MODE (operands[0]);
11260
11261   if (GET_MODE_SIZE (mode) < 4)
11262     operands[0] = gen_lowpart (SImode, operands[0]);
11263   if (mode != Pmode)
11264     operands[1] = gen_lowpart (Pmode, operands[1]);
11265   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
11266
11267   pat = gen_rtx_MULT (Pmode, operands[1], operands[2]);
11268   if (Pmode != SImode)
11269     pat = gen_rtx_SUBREG (SImode, pat, 0);
11270   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
11271   DONE;
11272 })
11273
11274 ;; Rare case of shifting RSP is handled by generating move and shift
11275 (define_split
11276   [(set (match_operand 0 "register_operand" "")
11277         (ashift (match_operand 1 "register_operand" "")
11278                 (match_operand:QI 2 "const_int_operand" "")))
11279    (clobber (reg:CC FLAGS_REG))]
11280   "reload_completed
11281    && true_regnum (operands[0]) != true_regnum (operands[1])"
11282   [(const_int 0)]
11283 {
11284   rtx pat, clob;
11285   emit_move_insn (operands[0], operands[1]);
11286   pat = gen_rtx_SET (VOIDmode, operands[0],
11287                      gen_rtx_ASHIFT (GET_MODE (operands[0]),
11288                                      operands[0], operands[2]));
11289   clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
11290   emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, pat, clob)));
11291   DONE;
11292 })
11293
11294 (define_insn "*ashlsi3_1_zext"
11295   [(set (match_operand:DI 0 "register_operand" "=r,r")
11296         (zero_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "0,l")
11297                         (match_operand:QI 2 "nonmemory_operand" "cI,M"))))
11298    (clobber (reg:CC FLAGS_REG))]
11299   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11300 {
11301   switch (get_attr_type (insn))
11302     {
11303     case TYPE_ALU:
11304       gcc_assert (operands[2] == const1_rtx);
11305       return "add{l}\t%k0, %k0";
11306
11307     case TYPE_LEA:
11308       return "#";
11309
11310     default:
11311       if (REG_P (operands[2]))
11312         return "sal{l}\t{%b2, %k0|%k0, %b2}";
11313       else if (operands[2] == const1_rtx
11314                && (TARGET_SHIFT1 || optimize_size))
11315         return "sal{l}\t%k0";
11316       else
11317         return "sal{l}\t{%2, %k0|%k0, %2}";
11318     }
11319 }
11320   [(set (attr "type")
11321      (cond [(eq_attr "alternative" "1")
11322               (const_string "lea")
11323             (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11324                      (const_int 0))
11325                  (match_operand 2 "const1_operand" ""))
11326               (const_string "alu")
11327            ]
11328            (const_string "ishift")))
11329    (set_attr "mode" "SI")])
11330
11331 ;; Convert lea to the lea pattern to avoid flags dependency.
11332 (define_split
11333   [(set (match_operand:DI 0 "register_operand" "")
11334         (zero_extend:DI (ashift (match_operand 1 "register_operand" "")
11335                                 (match_operand:QI 2 "const_int_operand" ""))))
11336    (clobber (reg:CC FLAGS_REG))]
11337   "TARGET_64BIT && reload_completed
11338    && true_regnum (operands[0]) != true_regnum (operands[1])"
11339   [(set (match_dup 0) (zero_extend:DI
11340                         (subreg:SI (mult:SI (match_dup 1)
11341                                             (match_dup 2)) 0)))]
11342 {
11343   operands[1] = gen_lowpart (Pmode, operands[1]);
11344   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
11345 })
11346
11347 ;; This pattern can't accept a variable shift count, since shifts by
11348 ;; zero don't affect the flags.  We assume that shifts by constant
11349 ;; zero are optimized away.
11350 (define_insn "*ashlsi3_cmp"
11351   [(set (reg FLAGS_REG)
11352         (compare
11353           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11354                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11355           (const_int 0)))
11356    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11357         (ashift:SI (match_dup 1) (match_dup 2)))]
11358    "(optimize_size
11359      || !TARGET_PARTIAL_FLAG_REG_STALL
11360      || (operands[2] == const1_rtx
11361          && (TARGET_SHIFT1
11362              || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
11363    && ix86_match_ccmode (insn, CCGOCmode)
11364    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11365 {
11366   switch (get_attr_type (insn))
11367     {
11368     case TYPE_ALU:
11369       gcc_assert (operands[2] == const1_rtx);
11370       return "add{l}\t%0, %0";
11371
11372     default:
11373       if (REG_P (operands[2]))
11374         return "sal{l}\t{%b2, %0|%0, %b2}";
11375       else if (operands[2] == const1_rtx
11376                && (TARGET_SHIFT1 || optimize_size))
11377         return "sal{l}\t%0";
11378       else
11379         return "sal{l}\t{%2, %0|%0, %2}";
11380     }
11381 }
11382   [(set (attr "type")
11383      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11384                           (const_int 0))
11385                       (match_operand 0 "register_operand" ""))
11386                  (match_operand 2 "const1_operand" ""))
11387               (const_string "alu")
11388            ]
11389            (const_string "ishift")))
11390    (set_attr "mode" "SI")])
11391
11392 (define_insn "*ashlsi3_cconly"
11393   [(set (reg FLAGS_REG)
11394         (compare
11395           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11396                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11397           (const_int 0)))
11398    (clobber (match_scratch:SI 0 "=r"))]
11399   "(optimize_size
11400     || !TARGET_PARTIAL_FLAG_REG_STALL
11401     || (operands[2] == const1_rtx
11402         && (TARGET_SHIFT1
11403             || TARGET_DOUBLE_WITH_ADD)))
11404    && ix86_match_ccmode (insn, CCGOCmode)
11405    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11406 {
11407   switch (get_attr_type (insn))
11408     {
11409     case TYPE_ALU:
11410       gcc_assert (operands[2] == const1_rtx);
11411       return "add{l}\t%0, %0";
11412
11413     default:
11414       if (REG_P (operands[2]))
11415         return "sal{l}\t{%b2, %0|%0, %b2}";
11416       else if (operands[2] == const1_rtx
11417                && (TARGET_SHIFT1 || optimize_size))
11418         return "sal{l}\t%0";
11419       else
11420         return "sal{l}\t{%2, %0|%0, %2}";
11421     }
11422 }
11423   [(set (attr "type")
11424      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11425                           (const_int 0))
11426                       (match_operand 0 "register_operand" ""))
11427                  (match_operand 2 "const1_operand" ""))
11428               (const_string "alu")
11429            ]
11430            (const_string "ishift")))
11431    (set_attr "mode" "SI")])
11432
11433 (define_insn "*ashlsi3_cmp_zext"
11434   [(set (reg FLAGS_REG)
11435         (compare
11436           (ashift:SI (match_operand:SI 1 "register_operand" "0")
11437                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11438           (const_int 0)))
11439    (set (match_operand:DI 0 "register_operand" "=r")
11440         (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
11441   "TARGET_64BIT
11442    && (optimize_size
11443        || !TARGET_PARTIAL_FLAG_REG_STALL
11444        || (operands[2] == const1_rtx
11445            && (TARGET_SHIFT1
11446                || TARGET_DOUBLE_WITH_ADD)))
11447    && ix86_match_ccmode (insn, CCGOCmode)
11448    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11449 {
11450   switch (get_attr_type (insn))
11451     {
11452     case TYPE_ALU:
11453       gcc_assert (operands[2] == const1_rtx);
11454       return "add{l}\t%k0, %k0";
11455
11456     default:
11457       if (REG_P (operands[2]))
11458         return "sal{l}\t{%b2, %k0|%k0, %b2}";
11459       else if (operands[2] == const1_rtx
11460                && (TARGET_SHIFT1 || optimize_size))
11461         return "sal{l}\t%k0";
11462       else
11463         return "sal{l}\t{%2, %k0|%k0, %2}";
11464     }
11465 }
11466   [(set (attr "type")
11467      (cond [(and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11468                      (const_int 0))
11469                  (match_operand 2 "const1_operand" ""))
11470               (const_string "alu")
11471            ]
11472            (const_string "ishift")))
11473    (set_attr "mode" "SI")])
11474
11475 (define_expand "ashlhi3"
11476   [(set (match_operand:HI 0 "nonimmediate_operand" "")
11477         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "")
11478                    (match_operand:QI 2 "nonmemory_operand" "")))
11479    (clobber (reg:CC FLAGS_REG))]
11480   "TARGET_HIMODE_MATH"
11481   "ix86_expand_binary_operator (ASHIFT, HImode, operands); DONE;")
11482
11483 (define_insn "*ashlhi3_1_lea"
11484   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
11485         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
11486                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
11487    (clobber (reg:CC FLAGS_REG))]
11488   "!TARGET_PARTIAL_REG_STALL
11489    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11490 {
11491   switch (get_attr_type (insn))
11492     {
11493     case TYPE_LEA:
11494       return "#";
11495     case TYPE_ALU:
11496       gcc_assert (operands[2] == const1_rtx);
11497       return "add{w}\t%0, %0";
11498
11499     default:
11500       if (REG_P (operands[2]))
11501         return "sal{w}\t{%b2, %0|%0, %b2}";
11502       else if (operands[2] == const1_rtx
11503                && (TARGET_SHIFT1 || optimize_size))
11504         return "sal{w}\t%0";
11505       else
11506         return "sal{w}\t{%2, %0|%0, %2}";
11507     }
11508 }
11509   [(set (attr "type")
11510      (cond [(eq_attr "alternative" "1")
11511               (const_string "lea")
11512             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11513                           (const_int 0))
11514                       (match_operand 0 "register_operand" ""))
11515                  (match_operand 2 "const1_operand" ""))
11516               (const_string "alu")
11517            ]
11518            (const_string "ishift")))
11519    (set_attr "mode" "HI,SI")])
11520
11521 (define_insn "*ashlhi3_1"
11522   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11523         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11524                    (match_operand:QI 2 "nonmemory_operand" "cI")))
11525    (clobber (reg:CC FLAGS_REG))]
11526   "TARGET_PARTIAL_REG_STALL
11527    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11528 {
11529   switch (get_attr_type (insn))
11530     {
11531     case TYPE_ALU:
11532       gcc_assert (operands[2] == const1_rtx);
11533       return "add{w}\t%0, %0";
11534
11535     default:
11536       if (REG_P (operands[2]))
11537         return "sal{w}\t{%b2, %0|%0, %b2}";
11538       else if (operands[2] == const1_rtx
11539                && (TARGET_SHIFT1 || optimize_size))
11540         return "sal{w}\t%0";
11541       else
11542         return "sal{w}\t{%2, %0|%0, %2}";
11543     }
11544 }
11545   [(set (attr "type")
11546      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11547                           (const_int 0))
11548                       (match_operand 0 "register_operand" ""))
11549                  (match_operand 2 "const1_operand" ""))
11550               (const_string "alu")
11551            ]
11552            (const_string "ishift")))
11553    (set_attr "mode" "HI")])
11554
11555 ;; This pattern can't accept a variable shift count, since shifts by
11556 ;; zero don't affect the flags.  We assume that shifts by constant
11557 ;; zero are optimized away.
11558 (define_insn "*ashlhi3_cmp"
11559   [(set (reg FLAGS_REG)
11560         (compare
11561           (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11562                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11563           (const_int 0)))
11564    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11565         (ashift:HI (match_dup 1) (match_dup 2)))]
11566   "(optimize_size
11567     || !TARGET_PARTIAL_FLAG_REG_STALL
11568     || (operands[2] == const1_rtx
11569         && (TARGET_SHIFT1
11570             || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
11571    && ix86_match_ccmode (insn, CCGOCmode)
11572    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11573 {
11574   switch (get_attr_type (insn))
11575     {
11576     case TYPE_ALU:
11577       gcc_assert (operands[2] == const1_rtx);
11578       return "add{w}\t%0, %0";
11579
11580     default:
11581       if (REG_P (operands[2]))
11582         return "sal{w}\t{%b2, %0|%0, %b2}";
11583       else if (operands[2] == const1_rtx
11584                && (TARGET_SHIFT1 || optimize_size))
11585         return "sal{w}\t%0";
11586       else
11587         return "sal{w}\t{%2, %0|%0, %2}";
11588     }
11589 }
11590   [(set (attr "type")
11591      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11592                           (const_int 0))
11593                       (match_operand 0 "register_operand" ""))
11594                  (match_operand 2 "const1_operand" ""))
11595               (const_string "alu")
11596            ]
11597            (const_string "ishift")))
11598    (set_attr "mode" "HI")])
11599
11600 (define_insn "*ashlhi3_cconly"
11601   [(set (reg FLAGS_REG)
11602         (compare
11603           (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11604                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11605           (const_int 0)))
11606    (clobber (match_scratch:HI 0 "=r"))]
11607   "(optimize_size
11608     || !TARGET_PARTIAL_FLAG_REG_STALL
11609     || (operands[2] == const1_rtx
11610         && (TARGET_SHIFT1
11611             || TARGET_DOUBLE_WITH_ADD)))
11612    && ix86_match_ccmode (insn, CCGOCmode)
11613    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11614 {
11615   switch (get_attr_type (insn))
11616     {
11617     case TYPE_ALU:
11618       gcc_assert (operands[2] == const1_rtx);
11619       return "add{w}\t%0, %0";
11620
11621     default:
11622       if (REG_P (operands[2]))
11623         return "sal{w}\t{%b2, %0|%0, %b2}";
11624       else if (operands[2] == const1_rtx
11625                && (TARGET_SHIFT1 || optimize_size))
11626         return "sal{w}\t%0";
11627       else
11628         return "sal{w}\t{%2, %0|%0, %2}";
11629     }
11630 }
11631   [(set (attr "type")
11632      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11633                           (const_int 0))
11634                       (match_operand 0 "register_operand" ""))
11635                  (match_operand 2 "const1_operand" ""))
11636               (const_string "alu")
11637            ]
11638            (const_string "ishift")))
11639    (set_attr "mode" "HI")])
11640
11641 (define_expand "ashlqi3"
11642   [(set (match_operand:QI 0 "nonimmediate_operand" "")
11643         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "")
11644                    (match_operand:QI 2 "nonmemory_operand" "")))
11645    (clobber (reg:CC FLAGS_REG))]
11646   "TARGET_QIMODE_MATH"
11647   "ix86_expand_binary_operator (ASHIFT, QImode, operands); DONE;")
11648
11649 ;; %%% Potential partial reg stall on alternative 2.  What to do?
11650
11651 (define_insn "*ashlqi3_1_lea"
11652   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r")
11653         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
11654                    (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
11655    (clobber (reg:CC FLAGS_REG))]
11656   "!TARGET_PARTIAL_REG_STALL
11657    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11658 {
11659   switch (get_attr_type (insn))
11660     {
11661     case TYPE_LEA:
11662       return "#";
11663     case TYPE_ALU:
11664       gcc_assert (operands[2] == const1_rtx);
11665       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
11666         return "add{l}\t%k0, %k0";
11667       else
11668         return "add{b}\t%0, %0";
11669
11670     default:
11671       if (REG_P (operands[2]))
11672         {
11673           if (get_attr_mode (insn) == MODE_SI)
11674             return "sal{l}\t{%b2, %k0|%k0, %b2}";
11675           else
11676             return "sal{b}\t{%b2, %0|%0, %b2}";
11677         }
11678       else if (operands[2] == const1_rtx
11679                && (TARGET_SHIFT1 || optimize_size))
11680         {
11681           if (get_attr_mode (insn) == MODE_SI)
11682             return "sal{l}\t%0";
11683           else
11684             return "sal{b}\t%0";
11685         }
11686       else
11687         {
11688           if (get_attr_mode (insn) == MODE_SI)
11689             return "sal{l}\t{%2, %k0|%k0, %2}";
11690           else
11691             return "sal{b}\t{%2, %0|%0, %2}";
11692         }
11693     }
11694 }
11695   [(set (attr "type")
11696      (cond [(eq_attr "alternative" "2")
11697               (const_string "lea")
11698             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11699                           (const_int 0))
11700                       (match_operand 0 "register_operand" ""))
11701                  (match_operand 2 "const1_operand" ""))
11702               (const_string "alu")
11703            ]
11704            (const_string "ishift")))
11705    (set_attr "mode" "QI,SI,SI")])
11706
11707 (define_insn "*ashlqi3_1"
11708   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
11709         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11710                    (match_operand:QI 2 "nonmemory_operand" "cI,cI")))
11711    (clobber (reg:CC FLAGS_REG))]
11712   "TARGET_PARTIAL_REG_STALL
11713    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11714 {
11715   switch (get_attr_type (insn))
11716     {
11717     case TYPE_ALU:
11718       gcc_assert (operands[2] == const1_rtx);
11719       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
11720         return "add{l}\t%k0, %k0";
11721       else
11722         return "add{b}\t%0, %0";
11723
11724     default:
11725       if (REG_P (operands[2]))
11726         {
11727           if (get_attr_mode (insn) == MODE_SI)
11728             return "sal{l}\t{%b2, %k0|%k0, %b2}";
11729           else
11730             return "sal{b}\t{%b2, %0|%0, %b2}";
11731         }
11732       else if (operands[2] == const1_rtx
11733                && (TARGET_SHIFT1 || optimize_size))
11734         {
11735           if (get_attr_mode (insn) == MODE_SI)
11736             return "sal{l}\t%0";
11737           else
11738             return "sal{b}\t%0";
11739         }
11740       else
11741         {
11742           if (get_attr_mode (insn) == MODE_SI)
11743             return "sal{l}\t{%2, %k0|%k0, %2}";
11744           else
11745             return "sal{b}\t{%2, %0|%0, %2}";
11746         }
11747     }
11748 }
11749   [(set (attr "type")
11750      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11751                           (const_int 0))
11752                       (match_operand 0 "register_operand" ""))
11753                  (match_operand 2 "const1_operand" ""))
11754               (const_string "alu")
11755            ]
11756            (const_string "ishift")))
11757    (set_attr "mode" "QI,SI")])
11758
11759 ;; This pattern can't accept a variable shift count, since shifts by
11760 ;; zero don't affect the flags.  We assume that shifts by constant
11761 ;; zero are optimized away.
11762 (define_insn "*ashlqi3_cmp"
11763   [(set (reg FLAGS_REG)
11764         (compare
11765           (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11766                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11767           (const_int 0)))
11768    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11769         (ashift:QI (match_dup 1) (match_dup 2)))]
11770   "(optimize_size
11771     || !TARGET_PARTIAL_FLAG_REG_STALL
11772     || (operands[2] == const1_rtx
11773         && (TARGET_SHIFT1
11774             || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
11775    && ix86_match_ccmode (insn, CCGOCmode)
11776    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11777 {
11778   switch (get_attr_type (insn))
11779     {
11780     case TYPE_ALU:
11781       gcc_assert (operands[2] == const1_rtx);
11782       return "add{b}\t%0, %0";
11783
11784     default:
11785       if (REG_P (operands[2]))
11786         return "sal{b}\t{%b2, %0|%0, %b2}";
11787       else if (operands[2] == const1_rtx
11788                && (TARGET_SHIFT1 || optimize_size))
11789         return "sal{b}\t%0";
11790       else
11791         return "sal{b}\t{%2, %0|%0, %2}";
11792     }
11793 }
11794   [(set (attr "type")
11795      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11796                           (const_int 0))
11797                       (match_operand 0 "register_operand" ""))
11798                  (match_operand 2 "const1_operand" ""))
11799               (const_string "alu")
11800            ]
11801            (const_string "ishift")))
11802    (set_attr "mode" "QI")])
11803
11804 (define_insn "*ashlqi3_cconly"
11805   [(set (reg FLAGS_REG)
11806         (compare
11807           (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11808                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11809           (const_int 0)))
11810    (clobber (match_scratch:QI 0 "=q"))]
11811   "(optimize_size
11812     || !TARGET_PARTIAL_FLAG_REG_STALL
11813     || (operands[2] == const1_rtx
11814         && (TARGET_SHIFT1
11815             || TARGET_DOUBLE_WITH_ADD)))
11816    && ix86_match_ccmode (insn, CCGOCmode)
11817    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11818 {
11819   switch (get_attr_type (insn))
11820     {
11821     case TYPE_ALU:
11822       gcc_assert (operands[2] == const1_rtx);
11823       return "add{b}\t%0, %0";
11824
11825     default:
11826       if (REG_P (operands[2]))
11827         return "sal{b}\t{%b2, %0|%0, %b2}";
11828       else if (operands[2] == const1_rtx
11829                && (TARGET_SHIFT1 || optimize_size))
11830         return "sal{b}\t%0";
11831       else
11832         return "sal{b}\t{%2, %0|%0, %2}";
11833     }
11834 }
11835   [(set (attr "type")
11836      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11837                           (const_int 0))
11838                       (match_operand 0 "register_operand" ""))
11839                  (match_operand 2 "const1_operand" ""))
11840               (const_string "alu")
11841            ]
11842            (const_string "ishift")))
11843    (set_attr "mode" "QI")])
11844
11845 ;; See comment above `ashldi3' about how this works.
11846
11847 (define_expand "ashrti3"
11848   [(parallel [(set (match_operand:TI 0 "register_operand" "")
11849                    (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
11850                                 (match_operand:QI 2 "nonmemory_operand" "")))
11851               (clobber (reg:CC FLAGS_REG))])]
11852   "TARGET_64BIT"
11853 {
11854   if (! immediate_operand (operands[2], QImode))
11855     {
11856       emit_insn (gen_ashrti3_1 (operands[0], operands[1], operands[2]));
11857       DONE;
11858     }
11859   ix86_expand_binary_operator (ASHIFTRT, TImode, operands);
11860   DONE;
11861 })
11862
11863 (define_insn "ashrti3_1"
11864   [(set (match_operand:TI 0 "register_operand" "=r")
11865         (ashiftrt:TI (match_operand:TI 1 "register_operand" "0")
11866                      (match_operand:QI 2 "register_operand" "c")))
11867    (clobber (match_scratch:DI 3 "=&r"))
11868    (clobber (reg:CC FLAGS_REG))]
11869   "TARGET_64BIT"
11870   "#"
11871   [(set_attr "type" "multi")])
11872
11873 (define_insn "*ashrti3_2"
11874   [(set (match_operand:TI 0 "register_operand" "=r")
11875         (ashiftrt:TI (match_operand:TI 1 "register_operand" "0")
11876                      (match_operand:QI 2 "immediate_operand" "O")))
11877    (clobber (reg:CC FLAGS_REG))]
11878   "TARGET_64BIT"
11879   "#"
11880   [(set_attr "type" "multi")])
11881
11882 (define_split
11883   [(set (match_operand:TI 0 "register_operand" "")
11884         (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
11885                      (match_operand:QI 2 "register_operand" "")))
11886    (clobber (match_scratch:DI 3 ""))
11887    (clobber (reg:CC FLAGS_REG))]
11888   "TARGET_64BIT && reload_completed"
11889   [(const_int 0)]
11890   "ix86_split_ashr (operands, operands[3], TImode); DONE;")
11891
11892 (define_split
11893   [(set (match_operand:TI 0 "register_operand" "")
11894         (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
11895                      (match_operand:QI 2 "immediate_operand" "")))
11896    (clobber (reg:CC FLAGS_REG))]
11897   "TARGET_64BIT && reload_completed"
11898   [(const_int 0)]
11899   "ix86_split_ashr (operands, NULL_RTX, TImode); DONE;")
11900
11901 (define_insn "x86_64_shrd"
11902   [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m,r*m")
11903         (ior:DI (ashiftrt:DI (match_dup 0)
11904                   (match_operand:QI 2 "nonmemory_operand" "J,c"))
11905                 (ashift:DI (match_operand:DI 1 "register_operand" "r,r")
11906                   (minus:QI (const_int 64) (match_dup 2)))))
11907    (clobber (reg:CC FLAGS_REG))]
11908   "TARGET_64BIT"
11909   "@
11910    shrd{q}\t{%2, %1, %0|%0, %1, %2}
11911    shrd{q}\t{%s2%1, %0|%0, %1, %2}"
11912   [(set_attr "type" "ishift")
11913    (set_attr "prefix_0f" "1")
11914    (set_attr "mode" "DI")
11915    (set_attr "athlon_decode" "vector")
11916    (set_attr "amdfam10_decode" "vector")])
11917
11918 (define_expand "ashrdi3"
11919   [(set (match_operand:DI 0 "shiftdi_operand" "")
11920         (ashiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
11921                      (match_operand:QI 2 "nonmemory_operand" "")))]
11922   ""
11923   "ix86_expand_binary_operator (ASHIFTRT, DImode, operands); DONE;")
11924
11925 (define_insn "*ashrdi3_63_rex64"
11926   [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
11927         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
11928                      (match_operand:DI 2 "const_int_operand" "i,i")))
11929    (clobber (reg:CC FLAGS_REG))]
11930   "TARGET_64BIT && INTVAL (operands[2]) == 63
11931    && (TARGET_USE_CLTD || optimize_size)
11932    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11933   "@
11934    {cqto|cqo}
11935    sar{q}\t{%2, %0|%0, %2}"
11936   [(set_attr "type" "imovx,ishift")
11937    (set_attr "prefix_0f" "0,*")
11938    (set_attr "length_immediate" "0,*")
11939    (set_attr "modrm" "0,1")
11940    (set_attr "mode" "DI")])
11941
11942 (define_insn "*ashrdi3_1_one_bit_rex64"
11943   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11944         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11945                      (match_operand:QI 2 "const1_operand" "")))
11946    (clobber (reg:CC FLAGS_REG))]
11947   "TARGET_64BIT
11948    && (TARGET_SHIFT1 || optimize_size)
11949    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11950   "sar{q}\t%0"
11951   [(set_attr "type" "ishift")
11952    (set (attr "length")
11953      (if_then_else (match_operand:DI 0 "register_operand" "")
11954         (const_string "2")
11955         (const_string "*")))])
11956
11957 (define_insn "*ashrdi3_1_rex64"
11958   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11959         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11960                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
11961    (clobber (reg:CC FLAGS_REG))]
11962   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11963   "@
11964    sar{q}\t{%2, %0|%0, %2}
11965    sar{q}\t{%b2, %0|%0, %b2}"
11966   [(set_attr "type" "ishift")
11967    (set_attr "mode" "DI")])
11968
11969 ;; This pattern can't accept a variable shift count, since shifts by
11970 ;; zero don't affect the flags.  We assume that shifts by constant
11971 ;; zero are optimized away.
11972 (define_insn "*ashrdi3_one_bit_cmp_rex64"
11973   [(set (reg FLAGS_REG)
11974         (compare
11975           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11976                        (match_operand:QI 2 "const1_operand" ""))
11977           (const_int 0)))
11978    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11979         (ashiftrt:DI (match_dup 1) (match_dup 2)))]
11980   "TARGET_64BIT
11981    && (TARGET_SHIFT1 || optimize_size)
11982    && ix86_match_ccmode (insn, CCGOCmode)
11983    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11984   "sar{q}\t%0"
11985   [(set_attr "type" "ishift")
11986    (set (attr "length")
11987      (if_then_else (match_operand:DI 0 "register_operand" "")
11988         (const_string "2")
11989         (const_string "*")))])
11990
11991 (define_insn "*ashrdi3_one_bit_cconly_rex64"
11992   [(set (reg FLAGS_REG)
11993         (compare
11994           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11995                        (match_operand:QI 2 "const1_operand" ""))
11996           (const_int 0)))
11997    (clobber (match_scratch:DI 0 "=r"))]
11998   "TARGET_64BIT
11999    && (TARGET_SHIFT1 || optimize_size)
12000    && ix86_match_ccmode (insn, CCGOCmode)
12001    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
12002   "sar{q}\t%0"
12003   [(set_attr "type" "ishift")
12004    (set_attr "length" "2")])
12005
12006 ;; This pattern can't accept a variable shift count, since shifts by
12007 ;; zero don't affect the flags.  We assume that shifts by constant
12008 ;; zero are optimized away.
12009 (define_insn "*ashrdi3_cmp_rex64"
12010   [(set (reg FLAGS_REG)
12011         (compare
12012           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12013                        (match_operand:QI 2 "const_int_operand" "n"))
12014           (const_int 0)))
12015    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12016         (ashiftrt:DI (match_dup 1) (match_dup 2)))]
12017   "TARGET_64BIT
12018    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12019    && ix86_match_ccmode (insn, CCGOCmode)
12020    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
12021   "sar{q}\t{%2, %0|%0, %2}"
12022   [(set_attr "type" "ishift")
12023    (set_attr "mode" "DI")])
12024
12025 (define_insn "*ashrdi3_cconly_rex64"
12026   [(set (reg FLAGS_REG)
12027         (compare
12028           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12029                        (match_operand:QI 2 "const_int_operand" "n"))
12030           (const_int 0)))
12031    (clobber (match_scratch:DI 0 "=r"))]
12032   "TARGET_64BIT
12033    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12034    && ix86_match_ccmode (insn, CCGOCmode)
12035    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
12036   "sar{q}\t{%2, %0|%0, %2}"
12037   [(set_attr "type" "ishift")
12038    (set_attr "mode" "DI")])
12039
12040 (define_insn "*ashrdi3_1"
12041   [(set (match_operand:DI 0 "register_operand" "=r")
12042         (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
12043                      (match_operand:QI 2 "nonmemory_operand" "Jc")))
12044    (clobber (reg:CC FLAGS_REG))]
12045   "!TARGET_64BIT"
12046   "#"
12047   [(set_attr "type" "multi")])
12048
12049 ;; By default we don't ask for a scratch register, because when DImode
12050 ;; values are manipulated, registers are already at a premium.  But if
12051 ;; we have one handy, we won't turn it away.
12052 (define_peephole2
12053   [(match_scratch:SI 3 "r")
12054    (parallel [(set (match_operand:DI 0 "register_operand" "")
12055                    (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
12056                                 (match_operand:QI 2 "nonmemory_operand" "")))
12057               (clobber (reg:CC FLAGS_REG))])
12058    (match_dup 3)]
12059   "!TARGET_64BIT && TARGET_CMOVE"
12060   [(const_int 0)]
12061   "ix86_split_ashr (operands, operands[3], DImode); DONE;")
12062
12063 (define_split
12064   [(set (match_operand:DI 0 "register_operand" "")
12065         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
12066                      (match_operand:QI 2 "nonmemory_operand" "")))
12067    (clobber (reg:CC FLAGS_REG))]
12068   "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
12069                      ? epilogue_completed : reload_completed)"
12070   [(const_int 0)]
12071   "ix86_split_ashr (operands, NULL_RTX, DImode); DONE;")
12072
12073 (define_insn "x86_shrd_1"
12074   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
12075         (ior:SI (ashiftrt:SI (match_dup 0)
12076                   (match_operand:QI 2 "nonmemory_operand" "I,c"))
12077                 (ashift:SI (match_operand:SI 1 "register_operand" "r,r")
12078                   (minus:QI (const_int 32) (match_dup 2)))))
12079    (clobber (reg:CC FLAGS_REG))]
12080   ""
12081   "@
12082    shrd{l}\t{%2, %1, %0|%0, %1, %2}
12083    shrd{l}\t{%s2%1, %0|%0, %1, %2}"
12084   [(set_attr "type" "ishift")
12085    (set_attr "prefix_0f" "1")
12086    (set_attr "pent_pair" "np")
12087    (set_attr "mode" "SI")])
12088
12089 (define_expand "x86_shift_adj_3"
12090   [(use (match_operand:SI 0 "register_operand" ""))
12091    (use (match_operand:SI 1 "register_operand" ""))
12092    (use (match_operand:QI 2 "register_operand" ""))]
12093   ""
12094 {
12095   rtx label = gen_label_rtx ();
12096   rtx tmp;
12097
12098   emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
12099
12100   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
12101   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
12102   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
12103                               gen_rtx_LABEL_REF (VOIDmode, label),
12104                               pc_rtx);
12105   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
12106   JUMP_LABEL (tmp) = label;
12107
12108   emit_move_insn (operands[0], operands[1]);
12109   emit_insn (gen_ashrsi3_31 (operands[1], operands[1], GEN_INT (31)));
12110
12111   emit_label (label);
12112   LABEL_NUSES (label) = 1;
12113
12114   DONE;
12115 })
12116
12117 (define_insn "ashrsi3_31"
12118   [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
12119         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
12120                      (match_operand:SI 2 "const_int_operand" "i,i")))
12121    (clobber (reg:CC FLAGS_REG))]
12122   "INTVAL (operands[2]) == 31 && (TARGET_USE_CLTD || optimize_size)
12123    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12124   "@
12125    {cltd|cdq}
12126    sar{l}\t{%2, %0|%0, %2}"
12127   [(set_attr "type" "imovx,ishift")
12128    (set_attr "prefix_0f" "0,*")
12129    (set_attr "length_immediate" "0,*")
12130    (set_attr "modrm" "0,1")
12131    (set_attr "mode" "SI")])
12132
12133 (define_insn "*ashrsi3_31_zext"
12134   [(set (match_operand:DI 0 "register_operand" "=*d,r")
12135         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
12136                                      (match_operand:SI 2 "const_int_operand" "i,i"))))
12137    (clobber (reg:CC FLAGS_REG))]
12138   "TARGET_64BIT && (TARGET_USE_CLTD || optimize_size)
12139    && INTVAL (operands[2]) == 31
12140    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12141   "@
12142    {cltd|cdq}
12143    sar{l}\t{%2, %k0|%k0, %2}"
12144   [(set_attr "type" "imovx,ishift")
12145    (set_attr "prefix_0f" "0,*")
12146    (set_attr "length_immediate" "0,*")
12147    (set_attr "modrm" "0,1")
12148    (set_attr "mode" "SI")])
12149
12150 (define_expand "ashrsi3"
12151   [(set (match_operand:SI 0 "nonimmediate_operand" "")
12152         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
12153                      (match_operand:QI 2 "nonmemory_operand" "")))
12154    (clobber (reg:CC FLAGS_REG))]
12155   ""
12156   "ix86_expand_binary_operator (ASHIFTRT, SImode, operands); DONE;")
12157
12158 (define_insn "*ashrsi3_1_one_bit"
12159   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12160         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12161                      (match_operand:QI 2 "const1_operand" "")))
12162    (clobber (reg:CC FLAGS_REG))]
12163   "(TARGET_SHIFT1 || optimize_size)
12164    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12165   "sar{l}\t%0"
12166   [(set_attr "type" "ishift")
12167    (set (attr "length")
12168      (if_then_else (match_operand:SI 0 "register_operand" "")
12169         (const_string "2")
12170         (const_string "*")))])
12171
12172 (define_insn "*ashrsi3_1_one_bit_zext"
12173   [(set (match_operand:DI 0 "register_operand" "=r")
12174         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
12175                                      (match_operand:QI 2 "const1_operand" ""))))
12176    (clobber (reg:CC FLAGS_REG))]
12177   "TARGET_64BIT
12178    && (TARGET_SHIFT1 || optimize_size)
12179    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12180   "sar{l}\t%k0"
12181   [(set_attr "type" "ishift")
12182    (set_attr "length" "2")])
12183
12184 (define_insn "*ashrsi3_1"
12185   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12186         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12187                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12188    (clobber (reg:CC FLAGS_REG))]
12189   "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12190   "@
12191    sar{l}\t{%2, %0|%0, %2}
12192    sar{l}\t{%b2, %0|%0, %b2}"
12193   [(set_attr "type" "ishift")
12194    (set_attr "mode" "SI")])
12195
12196 (define_insn "*ashrsi3_1_zext"
12197   [(set (match_operand:DI 0 "register_operand" "=r,r")
12198         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0")
12199                                      (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12200    (clobber (reg:CC FLAGS_REG))]
12201   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12202   "@
12203    sar{l}\t{%2, %k0|%k0, %2}
12204    sar{l}\t{%b2, %k0|%k0, %b2}"
12205   [(set_attr "type" "ishift")
12206    (set_attr "mode" "SI")])
12207
12208 ;; This pattern can't accept a variable shift count, since shifts by
12209 ;; zero don't affect the flags.  We assume that shifts by constant
12210 ;; zero are optimized away.
12211 (define_insn "*ashrsi3_one_bit_cmp"
12212   [(set (reg FLAGS_REG)
12213         (compare
12214           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12215                        (match_operand:QI 2 "const1_operand" ""))
12216           (const_int 0)))
12217    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12218         (ashiftrt:SI (match_dup 1) (match_dup 2)))]
12219   "(TARGET_SHIFT1 || optimize_size)
12220    && ix86_match_ccmode (insn, CCGOCmode)
12221    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12222   "sar{l}\t%0"
12223   [(set_attr "type" "ishift")
12224    (set (attr "length")
12225      (if_then_else (match_operand:SI 0 "register_operand" "")
12226         (const_string "2")
12227         (const_string "*")))])
12228
12229 (define_insn "*ashrsi3_one_bit_cconly"
12230   [(set (reg FLAGS_REG)
12231         (compare
12232           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12233                        (match_operand:QI 2 "const1_operand" ""))
12234           (const_int 0)))
12235    (clobber (match_scratch:SI 0 "=r"))]
12236   "(TARGET_SHIFT1 || optimize_size)
12237    && ix86_match_ccmode (insn, CCGOCmode)
12238    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12239   "sar{l}\t%0"
12240   [(set_attr "type" "ishift")
12241    (set_attr "length" "2")])
12242
12243 (define_insn "*ashrsi3_one_bit_cmp_zext"
12244   [(set (reg FLAGS_REG)
12245         (compare
12246           (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
12247                        (match_operand:QI 2 "const1_operand" ""))
12248           (const_int 0)))
12249    (set (match_operand:DI 0 "register_operand" "=r")
12250         (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
12251   "TARGET_64BIT
12252    && (TARGET_SHIFT1 || optimize_size)
12253    && ix86_match_ccmode (insn, CCmode)
12254    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12255   "sar{l}\t%k0"
12256   [(set_attr "type" "ishift")
12257    (set_attr "length" "2")])
12258
12259 ;; This pattern can't accept a variable shift count, since shifts by
12260 ;; zero don't affect the flags.  We assume that shifts by constant
12261 ;; zero are optimized away.
12262 (define_insn "*ashrsi3_cmp"
12263   [(set (reg FLAGS_REG)
12264         (compare
12265           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12266                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12267           (const_int 0)))
12268    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12269         (ashiftrt:SI (match_dup 1) (match_dup 2)))]
12270   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12271    && ix86_match_ccmode (insn, CCGOCmode)
12272    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12273   "sar{l}\t{%2, %0|%0, %2}"
12274   [(set_attr "type" "ishift")
12275    (set_attr "mode" "SI")])
12276
12277 (define_insn "*ashrsi3_cconly"
12278   [(set (reg FLAGS_REG)
12279         (compare
12280           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12281                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12282           (const_int 0)))
12283    (clobber (match_scratch:SI 0 "=r"))]
12284   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12285    && ix86_match_ccmode (insn, CCGOCmode)
12286    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12287   "sar{l}\t{%2, %0|%0, %2}"
12288   [(set_attr "type" "ishift")
12289    (set_attr "mode" "SI")])
12290
12291 (define_insn "*ashrsi3_cmp_zext"
12292   [(set (reg FLAGS_REG)
12293         (compare
12294           (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
12295                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12296           (const_int 0)))
12297    (set (match_operand:DI 0 "register_operand" "=r")
12298         (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
12299   "TARGET_64BIT
12300    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12301    && ix86_match_ccmode (insn, CCGOCmode)
12302    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12303   "sar{l}\t{%2, %k0|%k0, %2}"
12304   [(set_attr "type" "ishift")
12305    (set_attr "mode" "SI")])
12306
12307 (define_expand "ashrhi3"
12308   [(set (match_operand:HI 0 "nonimmediate_operand" "")
12309         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
12310                      (match_operand:QI 2 "nonmemory_operand" "")))
12311    (clobber (reg:CC FLAGS_REG))]
12312   "TARGET_HIMODE_MATH"
12313   "ix86_expand_binary_operator (ASHIFTRT, HImode, operands); DONE;")
12314
12315 (define_insn "*ashrhi3_1_one_bit"
12316   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12317         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12318                      (match_operand:QI 2 "const1_operand" "")))
12319    (clobber (reg:CC FLAGS_REG))]
12320   "(TARGET_SHIFT1 || optimize_size)
12321    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12322   "sar{w}\t%0"
12323   [(set_attr "type" "ishift")
12324    (set (attr "length")
12325      (if_then_else (match_operand 0 "register_operand" "")
12326         (const_string "2")
12327         (const_string "*")))])
12328
12329 (define_insn "*ashrhi3_1"
12330   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12331         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12332                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12333    (clobber (reg:CC FLAGS_REG))]
12334   "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12335   "@
12336    sar{w}\t{%2, %0|%0, %2}
12337    sar{w}\t{%b2, %0|%0, %b2}"
12338   [(set_attr "type" "ishift")
12339    (set_attr "mode" "HI")])
12340
12341 ;; This pattern can't accept a variable shift count, since shifts by
12342 ;; zero don't affect the flags.  We assume that shifts by constant
12343 ;; zero are optimized away.
12344 (define_insn "*ashrhi3_one_bit_cmp"
12345   [(set (reg FLAGS_REG)
12346         (compare
12347           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12348                        (match_operand:QI 2 "const1_operand" ""))
12349           (const_int 0)))
12350    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12351         (ashiftrt:HI (match_dup 1) (match_dup 2)))]
12352   "(TARGET_SHIFT1 || optimize_size)
12353    && ix86_match_ccmode (insn, CCGOCmode)
12354    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12355   "sar{w}\t%0"
12356   [(set_attr "type" "ishift")
12357    (set (attr "length")
12358      (if_then_else (match_operand 0 "register_operand" "")
12359         (const_string "2")
12360         (const_string "*")))])
12361
12362 (define_insn "*ashrhi3_one_bit_cconly"
12363   [(set (reg FLAGS_REG)
12364         (compare
12365           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12366                        (match_operand:QI 2 "const1_operand" ""))
12367           (const_int 0)))
12368    (clobber (match_scratch:HI 0 "=r"))]
12369   "(TARGET_SHIFT1 || optimize_size)
12370    && ix86_match_ccmode (insn, CCGOCmode)
12371    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12372   "sar{w}\t%0"
12373   [(set_attr "type" "ishift")
12374    (set_attr "length" "2")])
12375
12376 ;; This pattern can't accept a variable shift count, since shifts by
12377 ;; zero don't affect the flags.  We assume that shifts by constant
12378 ;; zero are optimized away.
12379 (define_insn "*ashrhi3_cmp"
12380   [(set (reg FLAGS_REG)
12381         (compare
12382           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12383                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12384           (const_int 0)))
12385    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12386         (ashiftrt:HI (match_dup 1) (match_dup 2)))]
12387   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12388    && ix86_match_ccmode (insn, CCGOCmode)
12389    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12390   "sar{w}\t{%2, %0|%0, %2}"
12391   [(set_attr "type" "ishift")
12392    (set_attr "mode" "HI")])
12393
12394 (define_insn "*ashrhi3_cconly"
12395   [(set (reg FLAGS_REG)
12396         (compare
12397           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12398                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12399           (const_int 0)))
12400    (clobber (match_scratch:HI 0 "=r"))]
12401   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12402    && ix86_match_ccmode (insn, CCGOCmode)
12403    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12404   "sar{w}\t{%2, %0|%0, %2}"
12405   [(set_attr "type" "ishift")
12406    (set_attr "mode" "HI")])
12407
12408 (define_expand "ashrqi3"
12409   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12410         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
12411                      (match_operand:QI 2 "nonmemory_operand" "")))
12412    (clobber (reg:CC FLAGS_REG))]
12413   "TARGET_QIMODE_MATH"
12414   "ix86_expand_binary_operator (ASHIFTRT, QImode, operands); DONE;")
12415
12416 (define_insn "*ashrqi3_1_one_bit"
12417   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12418         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12419                      (match_operand:QI 2 "const1_operand" "")))
12420    (clobber (reg:CC FLAGS_REG))]
12421   "(TARGET_SHIFT1 || optimize_size)
12422    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12423   "sar{b}\t%0"
12424   [(set_attr "type" "ishift")
12425    (set (attr "length")
12426      (if_then_else (match_operand 0 "register_operand" "")
12427         (const_string "2")
12428         (const_string "*")))])
12429
12430 (define_insn "*ashrqi3_1_one_bit_slp"
12431   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12432         (ashiftrt:QI (match_dup 0)
12433                      (match_operand:QI 1 "const1_operand" "")))
12434    (clobber (reg:CC FLAGS_REG))]
12435   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12436    && (TARGET_SHIFT1 || optimize_size)
12437    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12438   "sar{b}\t%0"
12439   [(set_attr "type" "ishift1")
12440    (set (attr "length")
12441      (if_then_else (match_operand 0 "register_operand" "")
12442         (const_string "2")
12443         (const_string "*")))])
12444
12445 (define_insn "*ashrqi3_1"
12446   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12447         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12448                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12449    (clobber (reg:CC FLAGS_REG))]
12450   "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12451   "@
12452    sar{b}\t{%2, %0|%0, %2}
12453    sar{b}\t{%b2, %0|%0, %b2}"
12454   [(set_attr "type" "ishift")
12455    (set_attr "mode" "QI")])
12456
12457 (define_insn "*ashrqi3_1_slp"
12458   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12459         (ashiftrt:QI (match_dup 0)
12460                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
12461    (clobber (reg:CC FLAGS_REG))]
12462   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12463    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
12464   "@
12465    sar{b}\t{%1, %0|%0, %1}
12466    sar{b}\t{%b1, %0|%0, %b1}"
12467   [(set_attr "type" "ishift1")
12468    (set_attr "mode" "QI")])
12469
12470 ;; This pattern can't accept a variable shift count, since shifts by
12471 ;; zero don't affect the flags.  We assume that shifts by constant
12472 ;; zero are optimized away.
12473 (define_insn "*ashrqi3_one_bit_cmp"
12474   [(set (reg FLAGS_REG)
12475         (compare
12476           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12477                        (match_operand:QI 2 "const1_operand" "I"))
12478           (const_int 0)))
12479    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12480         (ashiftrt:QI (match_dup 1) (match_dup 2)))]
12481   "(TARGET_SHIFT1 || optimize_size)
12482    && ix86_match_ccmode (insn, CCGOCmode)
12483    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12484   "sar{b}\t%0"
12485   [(set_attr "type" "ishift")
12486    (set (attr "length")
12487      (if_then_else (match_operand 0 "register_operand" "")
12488         (const_string "2")
12489         (const_string "*")))])
12490
12491 (define_insn "*ashrqi3_one_bit_cconly"
12492   [(set (reg FLAGS_REG)
12493         (compare
12494           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12495                        (match_operand:QI 2 "const1_operand" "I"))
12496           (const_int 0)))
12497    (clobber (match_scratch:QI 0 "=q"))]
12498   "(TARGET_SHIFT1 || optimize_size)
12499    && ix86_match_ccmode (insn, CCGOCmode)
12500    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12501   "sar{b}\t%0"
12502   [(set_attr "type" "ishift")
12503    (set_attr "length" "2")])
12504
12505 ;; This pattern can't accept a variable shift count, since shifts by
12506 ;; zero don't affect the flags.  We assume that shifts by constant
12507 ;; zero are optimized away.
12508 (define_insn "*ashrqi3_cmp"
12509   [(set (reg FLAGS_REG)
12510         (compare
12511           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12512                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12513           (const_int 0)))
12514    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12515         (ashiftrt:QI (match_dup 1) (match_dup 2)))]
12516   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12517    && ix86_match_ccmode (insn, CCGOCmode)
12518    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12519   "sar{b}\t{%2, %0|%0, %2}"
12520   [(set_attr "type" "ishift")
12521    (set_attr "mode" "QI")])
12522
12523 (define_insn "*ashrqi3_cconly"
12524   [(set (reg FLAGS_REG)
12525         (compare
12526           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12527                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12528           (const_int 0)))
12529    (clobber (match_scratch:QI 0 "=q"))]
12530   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12531    && ix86_match_ccmode (insn, CCGOCmode)
12532    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12533   "sar{b}\t{%2, %0|%0, %2}"
12534   [(set_attr "type" "ishift")
12535    (set_attr "mode" "QI")])
12536
12537 \f
12538 ;; Logical shift instructions
12539
12540 ;; See comment above `ashldi3' about how this works.
12541
12542 (define_expand "lshrti3"
12543   [(parallel [(set (match_operand:TI 0 "register_operand" "")
12544                    (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
12545                                 (match_operand:QI 2 "nonmemory_operand" "")))
12546               (clobber (reg:CC FLAGS_REG))])]
12547   "TARGET_64BIT"
12548 {
12549   if (! immediate_operand (operands[2], QImode))
12550     {
12551       emit_insn (gen_lshrti3_1 (operands[0], operands[1], operands[2]));
12552       DONE;
12553     }
12554   ix86_expand_binary_operator (LSHIFTRT, TImode, operands);
12555   DONE;
12556 })
12557
12558 (define_insn "lshrti3_1"
12559   [(set (match_operand:TI 0 "register_operand" "=r")
12560         (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
12561                      (match_operand:QI 2 "register_operand" "c")))
12562    (clobber (match_scratch:DI 3 "=&r"))
12563    (clobber (reg:CC FLAGS_REG))]
12564   "TARGET_64BIT"
12565   "#"
12566   [(set_attr "type" "multi")])
12567
12568 ;; This pattern must be defined before *lshrti3_2 to prevent
12569 ;; combine pass from converting sse2_lshrti3 to *lshrti3_2.
12570
12571 (define_insn "sse2_lshrti3"
12572   [(set (match_operand:TI 0 "register_operand" "=x")
12573         (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
12574                      (match_operand:SI 2 "const_0_to_255_mul_8_operand" "n")))]
12575   "TARGET_SSE2"
12576 {
12577   operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
12578   return "psrldq\t{%2, %0|%0, %2}";
12579 }
12580   [(set_attr "type" "sseishft")
12581    (set_attr "prefix_data16" "1")
12582    (set_attr "mode" "TI")])
12583
12584 (define_insn "*lshrti3_2"
12585   [(set (match_operand:TI 0 "register_operand" "=r")
12586         (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
12587                      (match_operand:QI 2 "immediate_operand" "O")))
12588    (clobber (reg:CC FLAGS_REG))]
12589   "TARGET_64BIT"
12590   "#"
12591   [(set_attr "type" "multi")])
12592
12593 (define_split
12594   [(set (match_operand:TI 0 "register_operand" "")
12595         (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
12596                      (match_operand:QI 2 "register_operand" "")))
12597    (clobber (match_scratch:DI 3 ""))
12598    (clobber (reg:CC FLAGS_REG))]
12599   "TARGET_64BIT && reload_completed"
12600   [(const_int 0)]
12601   "ix86_split_lshr (operands, operands[3], TImode); DONE;")
12602
12603 (define_split
12604   [(set (match_operand:TI 0 "register_operand" "")
12605         (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
12606                      (match_operand:QI 2 "immediate_operand" "")))
12607    (clobber (reg:CC FLAGS_REG))]
12608   "TARGET_64BIT && reload_completed"
12609   [(const_int 0)]
12610   "ix86_split_lshr (operands, NULL_RTX, TImode); DONE;")
12611
12612 (define_expand "lshrdi3"
12613   [(set (match_operand:DI 0 "shiftdi_operand" "")
12614         (lshiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
12615                      (match_operand:QI 2 "nonmemory_operand" "")))]
12616   ""
12617   "ix86_expand_binary_operator (LSHIFTRT, DImode, operands); DONE;")
12618
12619 (define_insn "*lshrdi3_1_one_bit_rex64"
12620   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12621         (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12622                      (match_operand:QI 2 "const1_operand" "")))
12623    (clobber (reg:CC FLAGS_REG))]
12624   "TARGET_64BIT
12625    && (TARGET_SHIFT1 || optimize_size)
12626    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12627   "shr{q}\t%0"
12628   [(set_attr "type" "ishift")
12629    (set (attr "length")
12630      (if_then_else (match_operand:DI 0 "register_operand" "")
12631         (const_string "2")
12632         (const_string "*")))])
12633
12634 (define_insn "*lshrdi3_1_rex64"
12635   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
12636         (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
12637                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
12638    (clobber (reg:CC FLAGS_REG))]
12639   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12640   "@
12641    shr{q}\t{%2, %0|%0, %2}
12642    shr{q}\t{%b2, %0|%0, %b2}"
12643   [(set_attr "type" "ishift")
12644    (set_attr "mode" "DI")])
12645
12646 ;; This pattern can't accept a variable shift count, since shifts by
12647 ;; zero don't affect the flags.  We assume that shifts by constant
12648 ;; zero are optimized away.
12649 (define_insn "*lshrdi3_cmp_one_bit_rex64"
12650   [(set (reg FLAGS_REG)
12651         (compare
12652           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12653                        (match_operand:QI 2 "const1_operand" ""))
12654           (const_int 0)))
12655    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12656         (lshiftrt:DI (match_dup 1) (match_dup 2)))]
12657   "TARGET_64BIT
12658    && (TARGET_SHIFT1 || optimize_size)
12659    && ix86_match_ccmode (insn, CCGOCmode)
12660    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12661   "shr{q}\t%0"
12662   [(set_attr "type" "ishift")
12663    (set (attr "length")
12664      (if_then_else (match_operand:DI 0 "register_operand" "")
12665         (const_string "2")
12666         (const_string "*")))])
12667
12668 (define_insn "*lshrdi3_cconly_one_bit_rex64"
12669   [(set (reg FLAGS_REG)
12670         (compare
12671           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12672                        (match_operand:QI 2 "const1_operand" ""))
12673           (const_int 0)))
12674    (clobber (match_scratch:DI 0 "=r"))]
12675   "TARGET_64BIT
12676    && (TARGET_SHIFT1 || optimize_size)
12677    && ix86_match_ccmode (insn, CCGOCmode)
12678    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12679   "shr{q}\t%0"
12680   [(set_attr "type" "ishift")
12681    (set_attr "length" "2")])
12682
12683 ;; This pattern can't accept a variable shift count, since shifts by
12684 ;; zero don't affect the flags.  We assume that shifts by constant
12685 ;; zero are optimized away.
12686 (define_insn "*lshrdi3_cmp_rex64"
12687   [(set (reg FLAGS_REG)
12688         (compare
12689           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12690                        (match_operand:QI 2 "const_int_operand" "e"))
12691           (const_int 0)))
12692    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12693         (lshiftrt:DI (match_dup 1) (match_dup 2)))]
12694   "TARGET_64BIT
12695    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12696    && ix86_match_ccmode (insn, CCGOCmode)
12697    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12698   "shr{q}\t{%2, %0|%0, %2}"
12699   [(set_attr "type" "ishift")
12700    (set_attr "mode" "DI")])
12701
12702 (define_insn "*lshrdi3_cconly_rex64"
12703   [(set (reg FLAGS_REG)
12704         (compare
12705           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12706                        (match_operand:QI 2 "const_int_operand" "e"))
12707           (const_int 0)))
12708    (clobber (match_scratch:DI 0 "=r"))]
12709   "TARGET_64BIT
12710    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12711    && ix86_match_ccmode (insn, CCGOCmode)
12712    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12713   "shr{q}\t{%2, %0|%0, %2}"
12714   [(set_attr "type" "ishift")
12715    (set_attr "mode" "DI")])
12716
12717 (define_insn "*lshrdi3_1"
12718   [(set (match_operand:DI 0 "register_operand" "=r")
12719         (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
12720                      (match_operand:QI 2 "nonmemory_operand" "Jc")))
12721    (clobber (reg:CC FLAGS_REG))]
12722   "!TARGET_64BIT"
12723   "#"
12724   [(set_attr "type" "multi")])
12725
12726 ;; By default we don't ask for a scratch register, because when DImode
12727 ;; values are manipulated, registers are already at a premium.  But if
12728 ;; we have one handy, we won't turn it away.
12729 (define_peephole2
12730   [(match_scratch:SI 3 "r")
12731    (parallel [(set (match_operand:DI 0 "register_operand" "")
12732                    (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
12733                                 (match_operand:QI 2 "nonmemory_operand" "")))
12734               (clobber (reg:CC FLAGS_REG))])
12735    (match_dup 3)]
12736   "!TARGET_64BIT && TARGET_CMOVE"
12737   [(const_int 0)]
12738   "ix86_split_lshr (operands, operands[3], DImode); DONE;")
12739
12740 (define_split
12741   [(set (match_operand:DI 0 "register_operand" "")
12742         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
12743                      (match_operand:QI 2 "nonmemory_operand" "")))
12744    (clobber (reg:CC FLAGS_REG))]
12745   "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
12746                      ? epilogue_completed : reload_completed)"
12747   [(const_int 0)]
12748   "ix86_split_lshr (operands, NULL_RTX, DImode); DONE;")
12749
12750 (define_expand "lshrsi3"
12751   [(set (match_operand:SI 0 "nonimmediate_operand" "")
12752         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
12753                      (match_operand:QI 2 "nonmemory_operand" "")))
12754    (clobber (reg:CC FLAGS_REG))]
12755   ""
12756   "ix86_expand_binary_operator (LSHIFTRT, SImode, operands); DONE;")
12757
12758 (define_insn "*lshrsi3_1_one_bit"
12759   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12760         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12761                      (match_operand:QI 2 "const1_operand" "")))
12762    (clobber (reg:CC FLAGS_REG))]
12763   "(TARGET_SHIFT1 || optimize_size)
12764    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12765   "shr{l}\t%0"
12766   [(set_attr "type" "ishift")
12767    (set (attr "length")
12768      (if_then_else (match_operand:SI 0 "register_operand" "")
12769         (const_string "2")
12770         (const_string "*")))])
12771
12772 (define_insn "*lshrsi3_1_one_bit_zext"
12773   [(set (match_operand:DI 0 "register_operand" "=r")
12774         (lshiftrt:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "0"))
12775                      (match_operand:QI 2 "const1_operand" "")))
12776    (clobber (reg:CC FLAGS_REG))]
12777   "TARGET_64BIT
12778    && (TARGET_SHIFT1 || optimize_size)
12779    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12780   "shr{l}\t%k0"
12781   [(set_attr "type" "ishift")
12782    (set_attr "length" "2")])
12783
12784 (define_insn "*lshrsi3_1"
12785   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12786         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12787                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12788    (clobber (reg:CC FLAGS_REG))]
12789   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12790   "@
12791    shr{l}\t{%2, %0|%0, %2}
12792    shr{l}\t{%b2, %0|%0, %b2}"
12793   [(set_attr "type" "ishift")
12794    (set_attr "mode" "SI")])
12795
12796 (define_insn "*lshrsi3_1_zext"
12797   [(set (match_operand:DI 0 "register_operand" "=r,r")
12798         (zero_extend:DI
12799           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12800                        (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12801    (clobber (reg:CC FLAGS_REG))]
12802   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12803   "@
12804    shr{l}\t{%2, %k0|%k0, %2}
12805    shr{l}\t{%b2, %k0|%k0, %b2}"
12806   [(set_attr "type" "ishift")
12807    (set_attr "mode" "SI")])
12808
12809 ;; This pattern can't accept a variable shift count, since shifts by
12810 ;; zero don't affect the flags.  We assume that shifts by constant
12811 ;; zero are optimized away.
12812 (define_insn "*lshrsi3_one_bit_cmp"
12813   [(set (reg FLAGS_REG)
12814         (compare
12815           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12816                        (match_operand:QI 2 "const1_operand" ""))
12817           (const_int 0)))
12818    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12819         (lshiftrt:SI (match_dup 1) (match_dup 2)))]
12820   "(TARGET_SHIFT1 || optimize_size)
12821    && ix86_match_ccmode (insn, CCGOCmode)
12822    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12823   "shr{l}\t%0"
12824   [(set_attr "type" "ishift")
12825    (set (attr "length")
12826      (if_then_else (match_operand:SI 0 "register_operand" "")
12827         (const_string "2")
12828         (const_string "*")))])
12829
12830 (define_insn "*lshrsi3_one_bit_cconly"
12831   [(set (reg FLAGS_REG)
12832         (compare
12833           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12834                        (match_operand:QI 2 "const1_operand" ""))
12835           (const_int 0)))
12836    (clobber (match_scratch:SI 0 "=r"))]
12837   "(TARGET_SHIFT1 || optimize_size)
12838    && ix86_match_ccmode (insn, CCGOCmode)
12839    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12840   "shr{l}\t%0"
12841   [(set_attr "type" "ishift")
12842    (set_attr "length" "2")])
12843
12844 (define_insn "*lshrsi3_cmp_one_bit_zext"
12845   [(set (reg FLAGS_REG)
12846         (compare
12847           (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
12848                        (match_operand:QI 2 "const1_operand" ""))
12849           (const_int 0)))
12850    (set (match_operand:DI 0 "register_operand" "=r")
12851         (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
12852   "TARGET_64BIT
12853    && (TARGET_SHIFT1 || optimize_size)
12854    && ix86_match_ccmode (insn, CCGOCmode)
12855    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12856   "shr{l}\t%k0"
12857   [(set_attr "type" "ishift")
12858    (set_attr "length" "2")])
12859
12860 ;; This pattern can't accept a variable shift count, since shifts by
12861 ;; zero don't affect the flags.  We assume that shifts by constant
12862 ;; zero are optimized away.
12863 (define_insn "*lshrsi3_cmp"
12864   [(set (reg FLAGS_REG)
12865         (compare
12866           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12867                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12868           (const_int 0)))
12869    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12870         (lshiftrt:SI (match_dup 1) (match_dup 2)))]
12871   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12872    && ix86_match_ccmode (insn, CCGOCmode)
12873    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12874   "shr{l}\t{%2, %0|%0, %2}"
12875   [(set_attr "type" "ishift")
12876    (set_attr "mode" "SI")])
12877
12878 (define_insn "*lshrsi3_cconly"
12879   [(set (reg FLAGS_REG)
12880       (compare
12881         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12882                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
12883         (const_int 0)))
12884    (clobber (match_scratch:SI 0 "=r"))]
12885   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12886    && ix86_match_ccmode (insn, CCGOCmode)
12887    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12888   "shr{l}\t{%2, %0|%0, %2}"
12889   [(set_attr "type" "ishift")
12890    (set_attr "mode" "SI")])
12891
12892 (define_insn "*lshrsi3_cmp_zext"
12893   [(set (reg FLAGS_REG)
12894         (compare
12895           (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
12896                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12897           (const_int 0)))
12898    (set (match_operand:DI 0 "register_operand" "=r")
12899         (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
12900   "TARGET_64BIT
12901    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12902    && ix86_match_ccmode (insn, CCGOCmode)
12903    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12904   "shr{l}\t{%2, %k0|%k0, %2}"
12905   [(set_attr "type" "ishift")
12906    (set_attr "mode" "SI")])
12907
12908 (define_expand "lshrhi3"
12909   [(set (match_operand:HI 0 "nonimmediate_operand" "")
12910         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
12911                      (match_operand:QI 2 "nonmemory_operand" "")))
12912    (clobber (reg:CC FLAGS_REG))]
12913   "TARGET_HIMODE_MATH"
12914   "ix86_expand_binary_operator (LSHIFTRT, HImode, operands); DONE;")
12915
12916 (define_insn "*lshrhi3_1_one_bit"
12917   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12918         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12919                      (match_operand:QI 2 "const1_operand" "")))
12920    (clobber (reg:CC FLAGS_REG))]
12921   "(TARGET_SHIFT1 || optimize_size)
12922    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12923   "shr{w}\t%0"
12924   [(set_attr "type" "ishift")
12925    (set (attr "length")
12926      (if_then_else (match_operand 0 "register_operand" "")
12927         (const_string "2")
12928         (const_string "*")))])
12929
12930 (define_insn "*lshrhi3_1"
12931   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12932         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12933                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12934    (clobber (reg:CC FLAGS_REG))]
12935   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12936   "@
12937    shr{w}\t{%2, %0|%0, %2}
12938    shr{w}\t{%b2, %0|%0, %b2}"
12939   [(set_attr "type" "ishift")
12940    (set_attr "mode" "HI")])
12941
12942 ;; This pattern can't accept a variable shift count, since shifts by
12943 ;; zero don't affect the flags.  We assume that shifts by constant
12944 ;; zero are optimized away.
12945 (define_insn "*lshrhi3_one_bit_cmp"
12946   [(set (reg FLAGS_REG)
12947         (compare
12948           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12949                        (match_operand:QI 2 "const1_operand" ""))
12950           (const_int 0)))
12951    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12952         (lshiftrt:HI (match_dup 1) (match_dup 2)))]
12953   "(TARGET_SHIFT1 || optimize_size)
12954    && ix86_match_ccmode (insn, CCGOCmode)
12955    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12956   "shr{w}\t%0"
12957   [(set_attr "type" "ishift")
12958    (set (attr "length")
12959      (if_then_else (match_operand:SI 0 "register_operand" "")
12960         (const_string "2")
12961         (const_string "*")))])
12962
12963 (define_insn "*lshrhi3_one_bit_cconly"
12964   [(set (reg FLAGS_REG)
12965         (compare
12966           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12967                        (match_operand:QI 2 "const1_operand" ""))
12968           (const_int 0)))
12969    (clobber (match_scratch:HI 0 "=r"))]
12970   "(TARGET_SHIFT1 || optimize_size)
12971    && ix86_match_ccmode (insn, CCGOCmode)
12972    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12973   "shr{w}\t%0"
12974   [(set_attr "type" "ishift")
12975    (set_attr "length" "2")])
12976
12977 ;; This pattern can't accept a variable shift count, since shifts by
12978 ;; zero don't affect the flags.  We assume that shifts by constant
12979 ;; zero are optimized away.
12980 (define_insn "*lshrhi3_cmp"
12981   [(set (reg FLAGS_REG)
12982         (compare
12983           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12984                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12985           (const_int 0)))
12986    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12987         (lshiftrt:HI (match_dup 1) (match_dup 2)))]
12988   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12989    && ix86_match_ccmode (insn, CCGOCmode)
12990    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12991   "shr{w}\t{%2, %0|%0, %2}"
12992   [(set_attr "type" "ishift")
12993    (set_attr "mode" "HI")])
12994
12995 (define_insn "*lshrhi3_cconly"
12996   [(set (reg FLAGS_REG)
12997         (compare
12998           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12999                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
13000           (const_int 0)))
13001    (clobber (match_scratch:HI 0 "=r"))]
13002   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
13003    && ix86_match_ccmode (insn, CCGOCmode)
13004    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
13005   "shr{w}\t{%2, %0|%0, %2}"
13006   [(set_attr "type" "ishift")
13007    (set_attr "mode" "HI")])
13008
13009 (define_expand "lshrqi3"
13010   [(set (match_operand:QI 0 "nonimmediate_operand" "")
13011         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
13012                      (match_operand:QI 2 "nonmemory_operand" "")))
13013    (clobber (reg:CC FLAGS_REG))]
13014   "TARGET_QIMODE_MATH"
13015   "ix86_expand_binary_operator (LSHIFTRT, QImode, operands); DONE;")
13016
13017 (define_insn "*lshrqi3_1_one_bit"
13018   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13019         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13020                      (match_operand:QI 2 "const1_operand" "")))
13021    (clobber (reg:CC FLAGS_REG))]
13022   "(TARGET_SHIFT1 || optimize_size)
13023    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13024   "shr{b}\t%0"
13025   [(set_attr "type" "ishift")
13026    (set (attr "length")
13027      (if_then_else (match_operand 0 "register_operand" "")
13028         (const_string "2")
13029         (const_string "*")))])
13030
13031 (define_insn "*lshrqi3_1_one_bit_slp"
13032   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
13033         (lshiftrt:QI (match_dup 0)
13034                      (match_operand:QI 1 "const1_operand" "")))
13035    (clobber (reg:CC FLAGS_REG))]
13036   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13037    && (TARGET_SHIFT1 || optimize_size)"
13038   "shr{b}\t%0"
13039   [(set_attr "type" "ishift1")
13040    (set (attr "length")
13041      (if_then_else (match_operand 0 "register_operand" "")
13042         (const_string "2")
13043         (const_string "*")))])
13044
13045 (define_insn "*lshrqi3_1"
13046   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
13047         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
13048                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
13049    (clobber (reg:CC FLAGS_REG))]
13050   "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13051   "@
13052    shr{b}\t{%2, %0|%0, %2}
13053    shr{b}\t{%b2, %0|%0, %b2}"
13054   [(set_attr "type" "ishift")
13055    (set_attr "mode" "QI")])
13056
13057 (define_insn "*lshrqi3_1_slp"
13058   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
13059         (lshiftrt:QI (match_dup 0)
13060                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
13061    (clobber (reg:CC FLAGS_REG))]
13062   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13063    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
13064   "@
13065    shr{b}\t{%1, %0|%0, %1}
13066    shr{b}\t{%b1, %0|%0, %b1}"
13067   [(set_attr "type" "ishift1")
13068    (set_attr "mode" "QI")])
13069
13070 ;; This pattern can't accept a variable shift count, since shifts by
13071 ;; zero don't affect the flags.  We assume that shifts by constant
13072 ;; zero are optimized away.
13073 (define_insn "*lshrqi2_one_bit_cmp"
13074   [(set (reg FLAGS_REG)
13075         (compare
13076           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13077                        (match_operand:QI 2 "const1_operand" ""))
13078           (const_int 0)))
13079    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13080         (lshiftrt:QI (match_dup 1) (match_dup 2)))]
13081   "(TARGET_SHIFT1 || optimize_size)
13082    && ix86_match_ccmode (insn, CCGOCmode)
13083    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13084   "shr{b}\t%0"
13085   [(set_attr "type" "ishift")
13086    (set (attr "length")
13087      (if_then_else (match_operand:SI 0 "register_operand" "")
13088         (const_string "2")
13089         (const_string "*")))])
13090
13091 (define_insn "*lshrqi2_one_bit_cconly"
13092   [(set (reg FLAGS_REG)
13093         (compare
13094           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13095                        (match_operand:QI 2 "const1_operand" ""))
13096           (const_int 0)))
13097    (clobber (match_scratch:QI 0 "=q"))]
13098   "(TARGET_SHIFT1 || optimize_size)
13099    && ix86_match_ccmode (insn, CCGOCmode)
13100    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13101   "shr{b}\t%0"
13102   [(set_attr "type" "ishift")
13103    (set_attr "length" "2")])
13104
13105 ;; This pattern can't accept a variable shift count, since shifts by
13106 ;; zero don't affect the flags.  We assume that shifts by constant
13107 ;; zero are optimized away.
13108 (define_insn "*lshrqi2_cmp"
13109   [(set (reg FLAGS_REG)
13110         (compare
13111           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13112                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
13113           (const_int 0)))
13114    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13115         (lshiftrt:QI (match_dup 1) (match_dup 2)))]
13116   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
13117    && ix86_match_ccmode (insn, CCGOCmode)
13118    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13119   "shr{b}\t{%2, %0|%0, %2}"
13120   [(set_attr "type" "ishift")
13121    (set_attr "mode" "QI")])
13122
13123 (define_insn "*lshrqi2_cconly"
13124   [(set (reg FLAGS_REG)
13125         (compare
13126           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13127                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
13128           (const_int 0)))
13129    (clobber (match_scratch:QI 0 "=q"))]
13130   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
13131    && ix86_match_ccmode (insn, CCGOCmode)
13132    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13133   "shr{b}\t{%2, %0|%0, %2}"
13134   [(set_attr "type" "ishift")
13135    (set_attr "mode" "QI")])
13136 \f
13137 ;; Rotate instructions
13138
13139 (define_expand "rotldi3"
13140   [(set (match_operand:DI 0 "shiftdi_operand" "")
13141         (rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
13142                    (match_operand:QI 2 "nonmemory_operand" "")))
13143    (clobber (reg:CC FLAGS_REG))]
13144  ""
13145 {
13146   if (TARGET_64BIT)
13147     {
13148       ix86_expand_binary_operator (ROTATE, DImode, operands);
13149       DONE;
13150     }
13151   if (!const_1_to_31_operand (operands[2], VOIDmode))
13152     FAIL;
13153   emit_insn (gen_ix86_rotldi3 (operands[0], operands[1], operands[2]));
13154   DONE;
13155 })
13156
13157 ;; Implement rotation using two double-precision shift instructions
13158 ;; and a scratch register.
13159 (define_insn_and_split "ix86_rotldi3"
13160  [(set (match_operand:DI 0 "register_operand" "=r")
13161        (rotate:DI (match_operand:DI 1 "register_operand" "0")
13162                   (match_operand:QI 2 "const_1_to_31_operand" "I")))
13163   (clobber (reg:CC FLAGS_REG))
13164   (clobber (match_scratch:SI 3 "=&r"))]
13165  "!TARGET_64BIT"
13166  ""
13167  "&& reload_completed"
13168  [(set (match_dup 3) (match_dup 4))
13169   (parallel
13170    [(set (match_dup 4)
13171          (ior:SI (ashift:SI (match_dup 4) (match_dup 2))
13172                  (lshiftrt:SI (match_dup 5)
13173                               (minus:QI (const_int 32) (match_dup 2)))))
13174     (clobber (reg:CC FLAGS_REG))])
13175   (parallel
13176    [(set (match_dup 5)
13177          (ior:SI (ashift:SI (match_dup 5) (match_dup 2))
13178                  (lshiftrt:SI (match_dup 3)
13179                               (minus:QI (const_int 32) (match_dup 2)))))
13180     (clobber (reg:CC FLAGS_REG))])]
13181  "split_di (&operands[0], 1, &operands[4], &operands[5]);")
13182
13183 (define_insn "*rotlsi3_1_one_bit_rex64"
13184   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
13185         (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13186                    (match_operand:QI 2 "const1_operand" "")))
13187    (clobber (reg:CC FLAGS_REG))]
13188   "TARGET_64BIT
13189    && (TARGET_SHIFT1 || optimize_size)
13190    && ix86_binary_operator_ok (ROTATE, DImode, operands)"
13191   "rol{q}\t%0"
13192   [(set_attr "type" "rotate")
13193    (set (attr "length")
13194      (if_then_else (match_operand:DI 0 "register_operand" "")
13195         (const_string "2")
13196         (const_string "*")))])
13197
13198 (define_insn "*rotldi3_1_rex64"
13199   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
13200         (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
13201                    (match_operand:QI 2 "nonmemory_operand" "e,c")))
13202    (clobber (reg:CC FLAGS_REG))]
13203   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)"
13204   "@
13205    rol{q}\t{%2, %0|%0, %2}
13206    rol{q}\t{%b2, %0|%0, %b2}"
13207   [(set_attr "type" "rotate")
13208    (set_attr "mode" "DI")])
13209
13210 (define_expand "rotlsi3"
13211   [(set (match_operand:SI 0 "nonimmediate_operand" "")
13212         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
13213                    (match_operand:QI 2 "nonmemory_operand" "")))
13214    (clobber (reg:CC FLAGS_REG))]
13215   ""
13216   "ix86_expand_binary_operator (ROTATE, SImode, operands); DONE;")
13217
13218 (define_insn "*rotlsi3_1_one_bit"
13219   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
13220         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13221                    (match_operand:QI 2 "const1_operand" "")))
13222    (clobber (reg:CC FLAGS_REG))]
13223   "(TARGET_SHIFT1 || optimize_size)
13224    && ix86_binary_operator_ok (ROTATE, SImode, operands)"
13225   "rol{l}\t%0"
13226   [(set_attr "type" "rotate")
13227    (set (attr "length")
13228      (if_then_else (match_operand:SI 0 "register_operand" "")
13229         (const_string "2")
13230         (const_string "*")))])
13231
13232 (define_insn "*rotlsi3_1_one_bit_zext"
13233   [(set (match_operand:DI 0 "register_operand" "=r")
13234         (zero_extend:DI
13235           (rotate:SI (match_operand:SI 1 "register_operand" "0")
13236                      (match_operand:QI 2 "const1_operand" ""))))
13237    (clobber (reg:CC FLAGS_REG))]
13238   "TARGET_64BIT
13239    && (TARGET_SHIFT1 || optimize_size)
13240    && ix86_binary_operator_ok (ROTATE, SImode, operands)"
13241   "rol{l}\t%k0"
13242   [(set_attr "type" "rotate")
13243    (set_attr "length" "2")])
13244
13245 (define_insn "*rotlsi3_1"
13246   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
13247         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
13248                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
13249    (clobber (reg:CC FLAGS_REG))]
13250   "ix86_binary_operator_ok (ROTATE, SImode, operands)"
13251   "@
13252    rol{l}\t{%2, %0|%0, %2}
13253    rol{l}\t{%b2, %0|%0, %b2}"
13254   [(set_attr "type" "rotate")
13255    (set_attr "mode" "SI")])
13256
13257 (define_insn "*rotlsi3_1_zext"
13258   [(set (match_operand:DI 0 "register_operand" "=r,r")
13259         (zero_extend:DI
13260           (rotate:SI (match_operand:SI 1 "register_operand" "0,0")
13261                      (match_operand:QI 2 "nonmemory_operand" "I,c"))))
13262    (clobber (reg:CC FLAGS_REG))]
13263   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)"
13264   "@
13265    rol{l}\t{%2, %k0|%k0, %2}
13266    rol{l}\t{%b2, %k0|%k0, %b2}"
13267   [(set_attr "type" "rotate")
13268    (set_attr "mode" "SI")])
13269
13270 (define_expand "rotlhi3"
13271   [(set (match_operand:HI 0 "nonimmediate_operand" "")
13272         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "")
13273                    (match_operand:QI 2 "nonmemory_operand" "")))
13274    (clobber (reg:CC FLAGS_REG))]
13275   "TARGET_HIMODE_MATH"
13276   "ix86_expand_binary_operator (ROTATE, HImode, operands); DONE;")
13277
13278 (define_insn "*rotlhi3_1_one_bit"
13279   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
13280         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0")
13281                    (match_operand:QI 2 "const1_operand" "")))
13282    (clobber (reg:CC FLAGS_REG))]
13283   "(TARGET_SHIFT1 || optimize_size)
13284    && ix86_binary_operator_ok (ROTATE, HImode, operands)"
13285   "rol{w}\t%0"
13286   [(set_attr "type" "rotate")
13287    (set (attr "length")
13288      (if_then_else (match_operand 0 "register_operand" "")
13289         (const_string "2")
13290         (const_string "*")))])
13291
13292 (define_insn "*rotlhi3_1"
13293   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
13294         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
13295                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
13296    (clobber (reg:CC FLAGS_REG))]
13297   "ix86_binary_operator_ok (ROTATE, HImode, operands)"
13298   "@
13299    rol{w}\t{%2, %0|%0, %2}
13300    rol{w}\t{%b2, %0|%0, %b2}"
13301   [(set_attr "type" "rotate")
13302    (set_attr "mode" "HI")])
13303
13304 (define_split
13305  [(set (match_operand:HI 0 "register_operand" "")
13306        (rotate:HI (match_dup 0) (const_int 8)))
13307   (clobber (reg:CC FLAGS_REG))]
13308  "reload_completed"
13309  [(parallel [(set (strict_low_part (match_dup 0))
13310                   (bswap:HI (match_dup 0)))
13311              (clobber (reg:CC FLAGS_REG))])]
13312  "")
13313
13314 (define_expand "rotlqi3"
13315   [(set (match_operand:QI 0 "nonimmediate_operand" "")
13316         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "")
13317                    (match_operand:QI 2 "nonmemory_operand" "")))
13318    (clobber (reg:CC FLAGS_REG))]
13319   "TARGET_QIMODE_MATH"
13320   "ix86_expand_binary_operator (ROTATE, QImode, operands); DONE;")
13321
13322 (define_insn "*rotlqi3_1_one_bit_slp"
13323   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
13324         (rotate:QI (match_dup 0)
13325                    (match_operand:QI 1 "const1_operand" "")))
13326    (clobber (reg:CC FLAGS_REG))]
13327   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13328    && (TARGET_SHIFT1 || optimize_size)"
13329   "rol{b}\t%0"
13330   [(set_attr "type" "rotate1")
13331    (set (attr "length")
13332      (if_then_else (match_operand 0 "register_operand" "")
13333         (const_string "2")
13334         (const_string "*")))])
13335
13336 (define_insn "*rotlqi3_1_one_bit"
13337   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13338         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13339                    (match_operand:QI 2 "const1_operand" "")))
13340    (clobber (reg:CC FLAGS_REG))]
13341   "(TARGET_SHIFT1 || optimize_size)
13342    && ix86_binary_operator_ok (ROTATE, QImode, operands)"
13343   "rol{b}\t%0"
13344   [(set_attr "type" "rotate")
13345    (set (attr "length")
13346      (if_then_else (match_operand 0 "register_operand" "")
13347         (const_string "2")
13348         (const_string "*")))])
13349
13350 (define_insn "*rotlqi3_1_slp"
13351   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
13352         (rotate:QI (match_dup 0)
13353                    (match_operand:QI 1 "nonmemory_operand" "I,c")))
13354    (clobber (reg:CC FLAGS_REG))]
13355   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13356    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
13357   "@
13358    rol{b}\t{%1, %0|%0, %1}
13359    rol{b}\t{%b1, %0|%0, %b1}"
13360   [(set_attr "type" "rotate1")
13361    (set_attr "mode" "QI")])
13362
13363 (define_insn "*rotlqi3_1"
13364   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
13365         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
13366                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
13367    (clobber (reg:CC FLAGS_REG))]
13368   "ix86_binary_operator_ok (ROTATE, QImode, operands)"
13369   "@
13370    rol{b}\t{%2, %0|%0, %2}
13371    rol{b}\t{%b2, %0|%0, %b2}"
13372   [(set_attr "type" "rotate")
13373    (set_attr "mode" "QI")])
13374
13375 (define_expand "rotrdi3"
13376   [(set (match_operand:DI 0 "shiftdi_operand" "")
13377         (rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
13378                    (match_operand:QI 2 "nonmemory_operand" "")))
13379    (clobber (reg:CC FLAGS_REG))]
13380  ""
13381 {
13382   if (TARGET_64BIT)
13383     {
13384       ix86_expand_binary_operator (ROTATERT, DImode, operands);
13385       DONE;
13386     }
13387   if (!const_1_to_31_operand (operands[2], VOIDmode))
13388     FAIL;
13389   emit_insn (gen_ix86_rotrdi3 (operands[0], operands[1], operands[2]));
13390   DONE;
13391 })
13392
13393 ;; Implement rotation using two double-precision shift instructions
13394 ;; and a scratch register.
13395 (define_insn_and_split "ix86_rotrdi3"
13396  [(set (match_operand:DI 0 "register_operand" "=r")
13397        (rotatert:DI (match_operand:DI 1 "register_operand" "0")
13398                     (match_operand:QI 2 "const_1_to_31_operand" "I")))
13399   (clobber (reg:CC FLAGS_REG))
13400   (clobber (match_scratch:SI 3 "=&r"))]
13401  "!TARGET_64BIT"
13402  ""
13403  "&& reload_completed"
13404  [(set (match_dup 3) (match_dup 4))
13405   (parallel
13406    [(set (match_dup 4)
13407          (ior:SI (ashiftrt:SI (match_dup 4) (match_dup 2))
13408                  (ashift:SI (match_dup 5)
13409                             (minus:QI (const_int 32) (match_dup 2)))))
13410     (clobber (reg:CC FLAGS_REG))])
13411   (parallel
13412    [(set (match_dup 5)
13413          (ior:SI (ashiftrt:SI (match_dup 5) (match_dup 2))
13414                  (ashift:SI (match_dup 3)
13415                             (minus:QI (const_int 32) (match_dup 2)))))
13416     (clobber (reg:CC FLAGS_REG))])]
13417  "split_di (&operands[0], 1, &operands[4], &operands[5]);")
13418
13419 (define_insn "*rotrdi3_1_one_bit_rex64"
13420   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
13421         (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13422                      (match_operand:QI 2 "const1_operand" "")))
13423    (clobber (reg:CC FLAGS_REG))]
13424   "TARGET_64BIT
13425    && (TARGET_SHIFT1 || optimize_size)
13426    && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
13427   "ror{q}\t%0"
13428   [(set_attr "type" "rotate")
13429    (set (attr "length")
13430      (if_then_else (match_operand:DI 0 "register_operand" "")
13431         (const_string "2")
13432         (const_string "*")))])
13433
13434 (define_insn "*rotrdi3_1_rex64"
13435   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
13436         (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
13437                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
13438    (clobber (reg:CC FLAGS_REG))]
13439   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
13440   "@
13441    ror{q}\t{%2, %0|%0, %2}
13442    ror{q}\t{%b2, %0|%0, %b2}"
13443   [(set_attr "type" "rotate")
13444    (set_attr "mode" "DI")])
13445
13446 (define_expand "rotrsi3"
13447   [(set (match_operand:SI 0 "nonimmediate_operand" "")
13448         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
13449                      (match_operand:QI 2 "nonmemory_operand" "")))
13450    (clobber (reg:CC FLAGS_REG))]
13451   ""
13452   "ix86_expand_binary_operator (ROTATERT, SImode, operands); DONE;")
13453
13454 (define_insn "*rotrsi3_1_one_bit"
13455   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
13456         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13457                      (match_operand:QI 2 "const1_operand" "")))
13458    (clobber (reg:CC FLAGS_REG))]
13459   "(TARGET_SHIFT1 || optimize_size)
13460    && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13461   "ror{l}\t%0"
13462   [(set_attr "type" "rotate")
13463    (set (attr "length")
13464      (if_then_else (match_operand:SI 0 "register_operand" "")
13465         (const_string "2")
13466         (const_string "*")))])
13467
13468 (define_insn "*rotrsi3_1_one_bit_zext"
13469   [(set (match_operand:DI 0 "register_operand" "=r")
13470         (zero_extend:DI
13471           (rotatert:SI (match_operand:SI 1 "register_operand" "0")
13472                        (match_operand:QI 2 "const1_operand" ""))))
13473    (clobber (reg:CC FLAGS_REG))]
13474   "TARGET_64BIT
13475    && (TARGET_SHIFT1 || optimize_size)
13476    && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13477   "ror{l}\t%k0"
13478   [(set_attr "type" "rotate")
13479    (set (attr "length")
13480      (if_then_else (match_operand:SI 0 "register_operand" "")
13481         (const_string "2")
13482         (const_string "*")))])
13483
13484 (define_insn "*rotrsi3_1"
13485   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
13486         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
13487                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
13488    (clobber (reg:CC FLAGS_REG))]
13489   "ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13490   "@
13491    ror{l}\t{%2, %0|%0, %2}
13492    ror{l}\t{%b2, %0|%0, %b2}"
13493   [(set_attr "type" "rotate")
13494    (set_attr "mode" "SI")])
13495
13496 (define_insn "*rotrsi3_1_zext"
13497   [(set (match_operand:DI 0 "register_operand" "=r,r")
13498         (zero_extend:DI
13499           (rotatert:SI (match_operand:SI 1 "register_operand" "0,0")
13500                        (match_operand:QI 2 "nonmemory_operand" "I,c"))))
13501    (clobber (reg:CC FLAGS_REG))]
13502   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13503   "@
13504    ror{l}\t{%2, %k0|%k0, %2}
13505    ror{l}\t{%b2, %k0|%k0, %b2}"
13506   [(set_attr "type" "rotate")
13507    (set_attr "mode" "SI")])
13508
13509 (define_expand "rotrhi3"
13510   [(set (match_operand:HI 0 "nonimmediate_operand" "")
13511         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "")
13512                      (match_operand:QI 2 "nonmemory_operand" "")))
13513    (clobber (reg:CC FLAGS_REG))]
13514   "TARGET_HIMODE_MATH"
13515   "ix86_expand_binary_operator (ROTATERT, HImode, operands); DONE;")
13516
13517 (define_insn "*rotrhi3_one_bit"
13518   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
13519         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0")
13520                      (match_operand:QI 2 "const1_operand" "")))
13521    (clobber (reg:CC FLAGS_REG))]
13522   "(TARGET_SHIFT1 || optimize_size)
13523    && ix86_binary_operator_ok (ROTATERT, HImode, operands)"
13524   "ror{w}\t%0"
13525   [(set_attr "type" "rotate")
13526    (set (attr "length")
13527      (if_then_else (match_operand 0 "register_operand" "")
13528         (const_string "2")
13529         (const_string "*")))])
13530
13531 (define_insn "*rotrhi3_1"
13532   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
13533         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
13534                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
13535    (clobber (reg:CC FLAGS_REG))]
13536   "ix86_binary_operator_ok (ROTATERT, HImode, operands)"
13537   "@
13538    ror{w}\t{%2, %0|%0, %2}
13539    ror{w}\t{%b2, %0|%0, %b2}"
13540   [(set_attr "type" "rotate")
13541    (set_attr "mode" "HI")])
13542
13543 (define_split
13544  [(set (match_operand:HI 0 "register_operand" "")
13545        (rotatert:HI (match_dup 0) (const_int 8)))
13546   (clobber (reg:CC FLAGS_REG))]
13547  "reload_completed"
13548  [(parallel [(set (strict_low_part (match_dup 0))
13549                   (bswap:HI (match_dup 0)))
13550              (clobber (reg:CC FLAGS_REG))])]
13551  "")
13552
13553 (define_expand "rotrqi3"
13554   [(set (match_operand:QI 0 "nonimmediate_operand" "")
13555         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "")
13556                      (match_operand:QI 2 "nonmemory_operand" "")))
13557    (clobber (reg:CC FLAGS_REG))]
13558   "TARGET_QIMODE_MATH"
13559   "ix86_expand_binary_operator (ROTATERT, QImode, operands); DONE;")
13560
13561 (define_insn "*rotrqi3_1_one_bit"
13562   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13563         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13564                      (match_operand:QI 2 "const1_operand" "")))
13565    (clobber (reg:CC FLAGS_REG))]
13566   "(TARGET_SHIFT1 || optimize_size)
13567    && ix86_binary_operator_ok (ROTATERT, QImode, operands)"
13568   "ror{b}\t%0"
13569   [(set_attr "type" "rotate")
13570    (set (attr "length")
13571      (if_then_else (match_operand 0 "register_operand" "")
13572         (const_string "2")
13573         (const_string "*")))])
13574
13575 (define_insn "*rotrqi3_1_one_bit_slp"
13576   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
13577         (rotatert:QI (match_dup 0)
13578                      (match_operand:QI 1 "const1_operand" "")))
13579    (clobber (reg:CC FLAGS_REG))]
13580   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13581    && (TARGET_SHIFT1 || optimize_size)"
13582   "ror{b}\t%0"
13583   [(set_attr "type" "rotate1")
13584    (set (attr "length")
13585      (if_then_else (match_operand 0 "register_operand" "")
13586         (const_string "2")
13587         (const_string "*")))])
13588
13589 (define_insn "*rotrqi3_1"
13590   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
13591         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
13592                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
13593    (clobber (reg:CC FLAGS_REG))]
13594   "ix86_binary_operator_ok (ROTATERT, QImode, operands)"
13595   "@
13596    ror{b}\t{%2, %0|%0, %2}
13597    ror{b}\t{%b2, %0|%0, %b2}"
13598   [(set_attr "type" "rotate")
13599    (set_attr "mode" "QI")])
13600
13601 (define_insn "*rotrqi3_1_slp"
13602   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
13603         (rotatert:QI (match_dup 0)
13604                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
13605    (clobber (reg:CC FLAGS_REG))]
13606   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13607    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
13608   "@
13609    ror{b}\t{%1, %0|%0, %1}
13610    ror{b}\t{%b1, %0|%0, %b1}"
13611   [(set_attr "type" "rotate1")
13612    (set_attr "mode" "QI")])
13613 \f
13614 ;; Bit set / bit test instructions
13615
13616 (define_expand "extv"
13617   [(set (match_operand:SI 0 "register_operand" "")
13618         (sign_extract:SI (match_operand:SI 1 "register_operand" "")
13619                          (match_operand:SI 2 "const8_operand" "")
13620                          (match_operand:SI 3 "const8_operand" "")))]
13621   ""
13622 {
13623   /* Handle extractions from %ah et al.  */
13624   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
13625     FAIL;
13626
13627   /* From mips.md: extract_bit_field doesn't verify that our source
13628      matches the predicate, so check it again here.  */
13629   if (! ext_register_operand (operands[1], VOIDmode))
13630     FAIL;
13631 })
13632
13633 (define_expand "extzv"
13634   [(set (match_operand:SI 0 "register_operand" "")
13635         (zero_extract:SI (match_operand 1 "ext_register_operand" "")
13636                          (match_operand:SI 2 "const8_operand" "")
13637                          (match_operand:SI 3 "const8_operand" "")))]
13638   ""
13639 {
13640   /* Handle extractions from %ah et al.  */
13641   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
13642     FAIL;
13643
13644   /* From mips.md: extract_bit_field doesn't verify that our source
13645      matches the predicate, so check it again here.  */
13646   if (! ext_register_operand (operands[1], VOIDmode))
13647     FAIL;
13648 })
13649
13650 (define_expand "insv"
13651   [(set (zero_extract (match_operand 0 "ext_register_operand" "")
13652                       (match_operand 1 "const8_operand" "")
13653                       (match_operand 2 "const8_operand" ""))
13654         (match_operand 3 "register_operand" ""))]
13655   ""
13656 {
13657   /* Handle insertions to %ah et al.  */
13658   if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
13659     FAIL;
13660
13661   /* From mips.md: insert_bit_field doesn't verify that our source
13662      matches the predicate, so check it again here.  */
13663   if (! ext_register_operand (operands[0], VOIDmode))
13664     FAIL;
13665
13666   if (TARGET_64BIT)
13667     emit_insn (gen_movdi_insv_1_rex64 (operands[0], operands[3]));
13668   else
13669     emit_insn (gen_movsi_insv_1 (operands[0], operands[3]));
13670
13671   DONE;
13672 })
13673
13674 ;; %%% bts, btr, btc, bt.
13675 ;; In general these instructions are *slow* when applied to memory,
13676 ;; since they enforce atomic operation.  When applied to registers,
13677 ;; it depends on the cpu implementation.  They're never faster than
13678 ;; the corresponding and/ior/xor operations, so with 32-bit there's
13679 ;; no point.  But in 64-bit, we can't hold the relevant immediates
13680 ;; within the instruction itself, so operating on bits in the high
13681 ;; 32-bits of a register becomes easier.
13682 ;;
13683 ;; These are slow on Nocona, but fast on Athlon64.  We do require the use
13684 ;; of btrq and btcq for corner cases of post-reload expansion of absdf and
13685 ;; negdf respectively, so they can never be disabled entirely.
13686
13687 (define_insn "*btsq"
13688   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
13689                          (const_int 1)
13690                          (match_operand:DI 1 "const_0_to_63_operand" ""))
13691         (const_int 1))
13692    (clobber (reg:CC FLAGS_REG))]
13693   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
13694   "bts{q}\t{%1, %0|%0, %1}"
13695   [(set_attr "type" "alu1")])
13696
13697 (define_insn "*btrq"
13698   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
13699                          (const_int 1)
13700                          (match_operand:DI 1 "const_0_to_63_operand" ""))
13701         (const_int 0))
13702    (clobber (reg:CC FLAGS_REG))]
13703   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
13704   "btr{q}\t{%1, %0|%0, %1}"
13705   [(set_attr "type" "alu1")])
13706
13707 (define_insn "*btcq"
13708   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
13709                          (const_int 1)
13710                          (match_operand:DI 1 "const_0_to_63_operand" ""))
13711         (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
13712    (clobber (reg:CC FLAGS_REG))]
13713   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
13714   "btc{q}\t{%1, %0|%0, %1}"
13715   [(set_attr "type" "alu1")])
13716
13717 ;; Allow Nocona to avoid these instructions if a register is available.
13718
13719 (define_peephole2
13720   [(match_scratch:DI 2 "r")
13721    (parallel [(set (zero_extract:DI
13722                      (match_operand:DI 0 "register_operand" "")
13723                      (const_int 1)
13724                      (match_operand:DI 1 "const_0_to_63_operand" ""))
13725                    (const_int 1))
13726               (clobber (reg:CC FLAGS_REG))])]
13727   "TARGET_64BIT && !TARGET_USE_BT"
13728   [(const_int 0)]
13729 {
13730   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
13731   rtx op1;
13732
13733   if (HOST_BITS_PER_WIDE_INT >= 64)
13734     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13735   else if (i < HOST_BITS_PER_WIDE_INT)
13736     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13737   else
13738     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
13739
13740   op1 = immed_double_const (lo, hi, DImode);
13741   if (i >= 31)
13742     {
13743       emit_move_insn (operands[2], op1);
13744       op1 = operands[2];
13745     }
13746
13747   emit_insn (gen_iordi3 (operands[0], operands[0], op1));
13748   DONE;
13749 })
13750
13751 (define_peephole2
13752   [(match_scratch:DI 2 "r")
13753    (parallel [(set (zero_extract:DI
13754                      (match_operand:DI 0 "register_operand" "")
13755                      (const_int 1)
13756                      (match_operand:DI 1 "const_0_to_63_operand" ""))
13757                    (const_int 0))
13758               (clobber (reg:CC FLAGS_REG))])]
13759   "TARGET_64BIT && !TARGET_USE_BT"
13760   [(const_int 0)]
13761 {
13762   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
13763   rtx op1;
13764
13765   if (HOST_BITS_PER_WIDE_INT >= 64)
13766     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13767   else if (i < HOST_BITS_PER_WIDE_INT)
13768     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13769   else
13770     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
13771
13772   op1 = immed_double_const (~lo, ~hi, DImode);
13773   if (i >= 32)
13774     {
13775       emit_move_insn (operands[2], op1);
13776       op1 = operands[2];
13777     }
13778
13779   emit_insn (gen_anddi3 (operands[0], operands[0], op1));
13780   DONE;
13781 })
13782
13783 (define_peephole2
13784   [(match_scratch:DI 2 "r")
13785    (parallel [(set (zero_extract:DI
13786                      (match_operand:DI 0 "register_operand" "")
13787                      (const_int 1)
13788                      (match_operand:DI 1 "const_0_to_63_operand" ""))
13789               (not:DI (zero_extract:DI
13790                         (match_dup 0) (const_int 1) (match_dup 1))))
13791               (clobber (reg:CC FLAGS_REG))])]
13792   "TARGET_64BIT && !TARGET_USE_BT"
13793   [(const_int 0)]
13794 {
13795   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
13796   rtx op1;
13797
13798   if (HOST_BITS_PER_WIDE_INT >= 64)
13799     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13800   else if (i < HOST_BITS_PER_WIDE_INT)
13801     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13802   else
13803     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
13804
13805   op1 = immed_double_const (lo, hi, DImode);
13806   if (i >= 31)
13807     {
13808       emit_move_insn (operands[2], op1);
13809       op1 = operands[2];
13810     }
13811
13812   emit_insn (gen_xordi3 (operands[0], operands[0], op1));
13813   DONE;
13814 })
13815
13816 (define_insn "*btdi_rex64"
13817   [(set (reg:CCC FLAGS_REG)
13818         (compare:CCC
13819           (zero_extract:DI
13820             (match_operand:DI 0 "register_operand" "r")
13821             (const_int 1)
13822             (match_operand:DI 1 "register_operand" "r"))
13823           (const_int 0)))]
13824   "TARGET_64BIT && (TARGET_USE_BT || optimize_size)"
13825   "bt{q}\t{%1, %0|%0, %1}"
13826   [(set_attr "type" "alu1")])
13827
13828 (define_insn "*btsi"
13829   [(set (reg:CCC FLAGS_REG)
13830         (compare:CCC
13831           (zero_extract:SI
13832             (match_operand:SI 0 "register_operand" "r")
13833             (const_int 1)
13834             (match_operand:SI 1 "register_operand" "r"))
13835           (const_int 0)))]
13836   "TARGET_USE_BT || optimize_size"
13837   "bt{l}\t{%1, %0|%0, %1}"
13838   [(set_attr "type" "alu1")])
13839 \f
13840 ;; Store-flag instructions.
13841
13842 ;; For all sCOND expanders, also expand the compare or test insn that
13843 ;; generates cc0.  Generate an equality comparison if `seq' or `sne'.
13844
13845 ;; %%% Do the expansion to SImode.  If PII, do things the xor+setcc way
13846 ;; to avoid partial register stalls.  Otherwise do things the setcc+movzx
13847 ;; way, which can later delete the movzx if only QImode is needed.
13848
13849 (define_expand "s<code>"
13850   [(set (match_operand:QI 0 "register_operand" "")
13851         (int_cond:QI (reg:CC FLAGS_REG) (const_int 0)))]
13852   ""
13853   "if (ix86_expand_setcc (<CODE>, operands[0])) DONE; else FAIL;")
13854
13855 (define_expand "s<code>"
13856   [(set (match_operand:QI 0 "register_operand" "")
13857         (fp_cond:QI (reg:CC FLAGS_REG) (const_int 0)))]
13858   "TARGET_80387 || TARGET_SSE"
13859   "if (ix86_expand_setcc (<CODE>, operands[0])) DONE; else FAIL;")
13860
13861 (define_insn "*setcc_1"
13862   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13863         (match_operator:QI 1 "ix86_comparison_operator"
13864           [(reg FLAGS_REG) (const_int 0)]))]
13865   ""
13866   "set%C1\t%0"
13867   [(set_attr "type" "setcc")
13868    (set_attr "mode" "QI")])
13869
13870 (define_insn "*setcc_2"
13871   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
13872         (match_operator:QI 1 "ix86_comparison_operator"
13873           [(reg FLAGS_REG) (const_int 0)]))]
13874   ""
13875   "set%C1\t%0"
13876   [(set_attr "type" "setcc")
13877    (set_attr "mode" "QI")])
13878
13879 ;; In general it is not safe to assume too much about CCmode registers,
13880 ;; so simplify-rtx stops when it sees a second one.  Under certain
13881 ;; conditions this is safe on x86, so help combine not create
13882 ;;
13883 ;;      seta    %al
13884 ;;      testb   %al, %al
13885 ;;      sete    %al
13886
13887 (define_split
13888   [(set (match_operand:QI 0 "nonimmediate_operand" "")
13889         (ne:QI (match_operator 1 "ix86_comparison_operator"
13890                  [(reg FLAGS_REG) (const_int 0)])
13891             (const_int 0)))]
13892   ""
13893   [(set (match_dup 0) (match_dup 1))]
13894 {
13895   PUT_MODE (operands[1], QImode);
13896 })
13897
13898 (define_split
13899   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
13900         (ne:QI (match_operator 1 "ix86_comparison_operator"
13901                  [(reg FLAGS_REG) (const_int 0)])
13902             (const_int 0)))]
13903   ""
13904   [(set (match_dup 0) (match_dup 1))]
13905 {
13906   PUT_MODE (operands[1], QImode);
13907 })
13908
13909 (define_split
13910   [(set (match_operand:QI 0 "nonimmediate_operand" "")
13911         (eq:QI (match_operator 1 "ix86_comparison_operator"
13912                  [(reg FLAGS_REG) (const_int 0)])
13913             (const_int 0)))]
13914   ""
13915   [(set (match_dup 0) (match_dup 1))]
13916 {
13917   rtx new_op1 = copy_rtx (operands[1]);
13918   operands[1] = new_op1;
13919   PUT_MODE (new_op1, QImode);
13920   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
13921                                              GET_MODE (XEXP (new_op1, 0))));
13922
13923   /* Make sure that (a) the CCmode we have for the flags is strong
13924      enough for the reversed compare or (b) we have a valid FP compare.  */
13925   if (! ix86_comparison_operator (new_op1, VOIDmode))
13926     FAIL;
13927 })
13928
13929 (define_split
13930   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
13931         (eq:QI (match_operator 1 "ix86_comparison_operator"
13932                  [(reg FLAGS_REG) (const_int 0)])
13933             (const_int 0)))]
13934   ""
13935   [(set (match_dup 0) (match_dup 1))]
13936 {
13937   rtx new_op1 = copy_rtx (operands[1]);
13938   operands[1] = new_op1;
13939   PUT_MODE (new_op1, QImode);
13940   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
13941                                              GET_MODE (XEXP (new_op1, 0))));
13942
13943   /* Make sure that (a) the CCmode we have for the flags is strong
13944      enough for the reversed compare or (b) we have a valid FP compare.  */
13945   if (! ix86_comparison_operator (new_op1, VOIDmode))
13946     FAIL;
13947 })
13948
13949 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
13950 ;; subsequent logical operations are used to imitate conditional moves.
13951 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
13952 ;; it directly.
13953
13954 (define_insn "*sse_setcc<mode>"
13955   [(set (match_operand:MODEF 0 "register_operand" "=x")
13956         (match_operator:MODEF 1 "sse_comparison_operator"
13957           [(match_operand:MODEF 2 "register_operand" "0")
13958            (match_operand:MODEF 3 "nonimmediate_operand" "xm")]))]
13959   "SSE_FLOAT_MODE_P (<MODE>mode) && !TARGET_SSE5"
13960   "cmp%D1s<ssemodefsuffix>\t{%3, %0|%0, %3}"
13961   [(set_attr "type" "ssecmp")
13962    (set_attr "mode" "<MODE>")])
13963
13964 (define_insn "*sse5_setcc<mode>"
13965   [(set (match_operand:MODEF 0 "register_operand" "=x")
13966         (match_operator:MODEF 1 "sse5_comparison_float_operator"
13967           [(match_operand:MODEF 2 "register_operand" "x")
13968            (match_operand:MODEF 3 "nonimmediate_operand" "xm")]))]
13969   "TARGET_SSE5"
13970   "com%Y1s<ssemodefsuffix>\t{%3, %2, %0|%0, %2, %3}"
13971   [(set_attr "type" "sse4arg")
13972    (set_attr "mode" "<MODE>")])
13973
13974 \f
13975 ;; Basic conditional jump instructions.
13976 ;; We ignore the overflow flag for signed branch instructions.
13977
13978 ;; For all bCOND expanders, also expand the compare or test insn that
13979 ;; generates reg FLAGS_REG.  Generate an equality comparison if `beq' or `bne'.
13980
13981 (define_expand "b<code>"
13982   [(set (pc)
13983         (if_then_else (int_cond:CC (reg:CC FLAGS_REG)
13984                                    (const_int 0))
13985                       (label_ref (match_operand 0 ""))
13986                       (pc)))]
13987   ""
13988   "ix86_expand_branch (<CODE>, operands[0]); DONE;")
13989
13990 (define_expand "b<code>"
13991   [(set (pc)
13992         (if_then_else (fp_cond:CC (reg:CC FLAGS_REG)
13993                                   (const_int 0))
13994                       (label_ref (match_operand 0 ""))
13995                       (pc)))]
13996   "TARGET_80387 || TARGET_SSE_MATH"
13997   "ix86_expand_branch (<CODE>, operands[0]); DONE;")
13998
13999 (define_insn "*jcc_1"
14000   [(set (pc)
14001         (if_then_else (match_operator 1 "ix86_comparison_operator"
14002                                       [(reg FLAGS_REG) (const_int 0)])
14003                       (label_ref (match_operand 0 "" ""))
14004                       (pc)))]
14005   ""
14006   "%+j%C1\t%l0"
14007   [(set_attr "type" "ibr")
14008    (set_attr "modrm" "0")
14009    (set (attr "length")
14010            (if_then_else (and (ge (minus (match_dup 0) (pc))
14011                                   (const_int -126))
14012                               (lt (minus (match_dup 0) (pc))
14013                                   (const_int 128)))
14014              (const_int 2)
14015              (const_int 6)))])
14016
14017 (define_insn "*jcc_2"
14018   [(set (pc)
14019         (if_then_else (match_operator 1 "ix86_comparison_operator"
14020                                       [(reg FLAGS_REG) (const_int 0)])
14021                       (pc)
14022                       (label_ref (match_operand 0 "" ""))))]
14023   ""
14024   "%+j%c1\t%l0"
14025   [(set_attr "type" "ibr")
14026    (set_attr "modrm" "0")
14027    (set (attr "length")
14028            (if_then_else (and (ge (minus (match_dup 0) (pc))
14029                                   (const_int -126))
14030                               (lt (minus (match_dup 0) (pc))
14031                                   (const_int 128)))
14032              (const_int 2)
14033              (const_int 6)))])
14034
14035 ;; In general it is not safe to assume too much about CCmode registers,
14036 ;; so simplify-rtx stops when it sees a second one.  Under certain
14037 ;; conditions this is safe on x86, so help combine not create
14038 ;;
14039 ;;      seta    %al
14040 ;;      testb   %al, %al
14041 ;;      je      Lfoo
14042
14043 (define_split
14044   [(set (pc)
14045         (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
14046                                       [(reg FLAGS_REG) (const_int 0)])
14047                           (const_int 0))
14048                       (label_ref (match_operand 1 "" ""))
14049                       (pc)))]
14050   ""
14051   [(set (pc)
14052         (if_then_else (match_dup 0)
14053                       (label_ref (match_dup 1))
14054                       (pc)))]
14055 {
14056   PUT_MODE (operands[0], VOIDmode);
14057 })
14058
14059 (define_split
14060   [(set (pc)
14061         (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
14062                                       [(reg FLAGS_REG) (const_int 0)])
14063                           (const_int 0))
14064                       (label_ref (match_operand 1 "" ""))
14065                       (pc)))]
14066   ""
14067   [(set (pc)
14068         (if_then_else (match_dup 0)
14069                       (label_ref (match_dup 1))
14070                       (pc)))]
14071 {
14072   rtx new_op0 = copy_rtx (operands[0]);
14073   operands[0] = new_op0;
14074   PUT_MODE (new_op0, VOIDmode);
14075   PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0),
14076                                              GET_MODE (XEXP (new_op0, 0))));
14077
14078   /* Make sure that (a) the CCmode we have for the flags is strong
14079      enough for the reversed compare or (b) we have a valid FP compare.  */
14080   if (! ix86_comparison_operator (new_op0, VOIDmode))
14081     FAIL;
14082 })
14083
14084 ;; zero_extend in SImode is correct, since this is what combine pass
14085 ;; generates from shift insn with QImode operand.  Actually, the mode of
14086 ;; operand 2 (bit offset operand) doesn't matter since bt insn takes
14087 ;; appropriate modulo of the bit offset value.
14088
14089 (define_insn_and_split "*jcc_btdi_rex64"
14090   [(set (pc)
14091         (if_then_else (match_operator 0 "bt_comparison_operator"
14092                         [(zero_extract:DI
14093                            (match_operand:DI 1 "register_operand" "r")
14094                            (const_int 1)
14095                            (zero_extend:SI
14096                              (match_operand:QI 2 "register_operand" "r")))
14097                          (const_int 0)])
14098                       (label_ref (match_operand 3 "" ""))
14099                       (pc)))]
14100   "TARGET_64BIT && (TARGET_USE_BT || optimize_size)"
14101   "#"
14102   "&& 1"
14103   [(set (reg:CCC FLAGS_REG)
14104         (compare:CCC
14105           (zero_extract:DI
14106             (match_dup 1)
14107             (const_int 1)
14108             (match_dup 2))
14109           (const_int 0)))
14110    (set (pc)
14111         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
14112                       (label_ref (match_dup 3))
14113                       (pc)))]
14114 {
14115   operands[2] = simplify_gen_subreg (DImode, operands[2], QImode, 0);
14116
14117   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
14118 })
14119
14120 (define_insn_and_split "*jcc_btsi"
14121   [(set (pc)
14122         (if_then_else (match_operator 0 "bt_comparison_operator"
14123                         [(zero_extract:SI
14124                            (match_operand:SI 1 "register_operand" "r")
14125                            (const_int 1)
14126                            (zero_extend:SI
14127                              (match_operand:QI 2 "register_operand" "r")))
14128                          (const_int 0)])
14129                       (label_ref (match_operand 3 "" ""))
14130                       (pc)))]
14131   "TARGET_USE_BT || optimize_size"
14132   "#"
14133   "&& 1"
14134   [(set (reg:CCC FLAGS_REG)
14135         (compare:CCC
14136           (zero_extract:SI
14137             (match_dup 1)
14138             (const_int 1)
14139             (match_dup 2))
14140           (const_int 0)))
14141    (set (pc)
14142         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
14143                       (label_ref (match_dup 3))
14144                       (pc)))]
14145 {
14146   operands[2] = simplify_gen_subreg (SImode, operands[2], QImode, 0);
14147
14148   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
14149 })
14150
14151 (define_insn_and_split "*jcc_btsi_1"
14152   [(set (pc)
14153         (if_then_else (match_operator 0 "bt_comparison_operator"
14154                         [(and:SI
14155                            (lshiftrt:SI
14156                              (match_operand:SI 1 "register_operand" "r")
14157                              (match_operand:QI 2 "register_operand" "r"))
14158                            (const_int 1))
14159                          (const_int 0)])
14160                       (label_ref (match_operand 3 "" ""))
14161                       (pc)))]
14162   "TARGET_USE_BT || optimize_size"
14163   "#"
14164   "&& 1"
14165   [(set (reg:CCC FLAGS_REG)
14166         (compare:CCC
14167           (zero_extract:SI
14168             (match_dup 1)
14169             (const_int 1)
14170             (match_dup 2))
14171           (const_int 0)))
14172    (set (pc)
14173         (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
14174                       (label_ref (match_dup 3))
14175                       (pc)))]
14176 {
14177   operands[2] = simplify_gen_subreg (SImode, operands[2], QImode, 0);
14178
14179   PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
14180 })
14181
14182 ;; Define combination compare-and-branch fp compare instructions to use
14183 ;; during early optimization.  Splitting the operation apart early makes
14184 ;; for bad code when we want to reverse the operation.
14185
14186 (define_insn "*fp_jcc_1_mixed"
14187   [(set (pc)
14188         (if_then_else (match_operator 0 "comparison_operator"
14189                         [(match_operand 1 "register_operand" "f,x")
14190                          (match_operand 2 "nonimmediate_operand" "f,xm")])
14191           (label_ref (match_operand 3 "" ""))
14192           (pc)))
14193    (clobber (reg:CCFP FPSR_REG))
14194    (clobber (reg:CCFP FLAGS_REG))]
14195   "TARGET_MIX_SSE_I387
14196    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14197    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14198    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14199   "#")
14200
14201 (define_insn "*fp_jcc_1_sse"
14202   [(set (pc)
14203         (if_then_else (match_operator 0 "comparison_operator"
14204                         [(match_operand 1 "register_operand" "x")
14205                          (match_operand 2 "nonimmediate_operand" "xm")])
14206           (label_ref (match_operand 3 "" ""))
14207           (pc)))
14208    (clobber (reg:CCFP FPSR_REG))
14209    (clobber (reg:CCFP FLAGS_REG))]
14210   "TARGET_SSE_MATH
14211    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14212    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14213    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14214   "#")
14215
14216 (define_insn "*fp_jcc_1_387"
14217   [(set (pc)
14218         (if_then_else (match_operator 0 "comparison_operator"
14219                         [(match_operand 1 "register_operand" "f")
14220                          (match_operand 2 "register_operand" "f")])
14221           (label_ref (match_operand 3 "" ""))
14222           (pc)))
14223    (clobber (reg:CCFP FPSR_REG))
14224    (clobber (reg:CCFP FLAGS_REG))]
14225   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14226    && TARGET_CMOVE
14227    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14228    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14229   "#")
14230
14231 (define_insn "*fp_jcc_2_mixed"
14232   [(set (pc)
14233         (if_then_else (match_operator 0 "comparison_operator"
14234                         [(match_operand 1 "register_operand" "f,x")
14235                          (match_operand 2 "nonimmediate_operand" "f,xm")])
14236           (pc)
14237           (label_ref (match_operand 3 "" ""))))
14238    (clobber (reg:CCFP FPSR_REG))
14239    (clobber (reg:CCFP FLAGS_REG))]
14240   "TARGET_MIX_SSE_I387
14241    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14242    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14243    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14244   "#")
14245
14246 (define_insn "*fp_jcc_2_sse"
14247   [(set (pc)
14248         (if_then_else (match_operator 0 "comparison_operator"
14249                         [(match_operand 1 "register_operand" "x")
14250                          (match_operand 2 "nonimmediate_operand" "xm")])
14251           (pc)
14252           (label_ref (match_operand 3 "" ""))))
14253    (clobber (reg:CCFP FPSR_REG))
14254    (clobber (reg:CCFP FLAGS_REG))]
14255   "TARGET_SSE_MATH
14256    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14257    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14258    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14259   "#")
14260
14261 (define_insn "*fp_jcc_2_387"
14262   [(set (pc)
14263         (if_then_else (match_operator 0 "comparison_operator"
14264                         [(match_operand 1 "register_operand" "f")
14265                          (match_operand 2 "register_operand" "f")])
14266           (pc)
14267           (label_ref (match_operand 3 "" ""))))
14268    (clobber (reg:CCFP FPSR_REG))
14269    (clobber (reg:CCFP FLAGS_REG))]
14270   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14271    && TARGET_CMOVE
14272    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14273    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14274   "#")
14275
14276 (define_insn "*fp_jcc_3_387"
14277   [(set (pc)
14278         (if_then_else (match_operator 0 "comparison_operator"
14279                         [(match_operand 1 "register_operand" "f")
14280                          (match_operand 2 "nonimmediate_operand" "fm")])
14281           (label_ref (match_operand 3 "" ""))
14282           (pc)))
14283    (clobber (reg:CCFP FPSR_REG))
14284    (clobber (reg:CCFP FLAGS_REG))
14285    (clobber (match_scratch:HI 4 "=a"))]
14286   "TARGET_80387
14287    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
14288    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14289    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
14290    && SELECT_CC_MODE (GET_CODE (operands[0]),
14291                       operands[1], operands[2]) == CCFPmode
14292    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14293   "#")
14294
14295 (define_insn "*fp_jcc_4_387"
14296   [(set (pc)
14297         (if_then_else (match_operator 0 "comparison_operator"
14298                         [(match_operand 1 "register_operand" "f")
14299                          (match_operand 2 "nonimmediate_operand" "fm")])
14300           (pc)
14301           (label_ref (match_operand 3 "" ""))))
14302    (clobber (reg:CCFP FPSR_REG))
14303    (clobber (reg:CCFP FLAGS_REG))
14304    (clobber (match_scratch:HI 4 "=a"))]
14305   "TARGET_80387
14306    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
14307    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14308    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
14309    && SELECT_CC_MODE (GET_CODE (operands[0]),
14310                       operands[1], operands[2]) == CCFPmode
14311    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14312   "#")
14313
14314 (define_insn "*fp_jcc_5_387"
14315   [(set (pc)
14316         (if_then_else (match_operator 0 "comparison_operator"
14317                         [(match_operand 1 "register_operand" "f")
14318                          (match_operand 2 "register_operand" "f")])
14319           (label_ref (match_operand 3 "" ""))
14320           (pc)))
14321    (clobber (reg:CCFP FPSR_REG))
14322    (clobber (reg:CCFP FLAGS_REG))
14323    (clobber (match_scratch:HI 4 "=a"))]
14324   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14325    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14326    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14327   "#")
14328
14329 (define_insn "*fp_jcc_6_387"
14330   [(set (pc)
14331         (if_then_else (match_operator 0 "comparison_operator"
14332                         [(match_operand 1 "register_operand" "f")
14333                          (match_operand 2 "register_operand" "f")])
14334           (pc)
14335           (label_ref (match_operand 3 "" ""))))
14336    (clobber (reg:CCFP FPSR_REG))
14337    (clobber (reg:CCFP FLAGS_REG))
14338    (clobber (match_scratch:HI 4 "=a"))]
14339   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14340    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14341    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14342   "#")
14343
14344 (define_insn "*fp_jcc_7_387"
14345   [(set (pc)
14346         (if_then_else (match_operator 0 "comparison_operator"
14347                         [(match_operand 1 "register_operand" "f")
14348                          (match_operand 2 "const0_operand" "X")])
14349           (label_ref (match_operand 3 "" ""))
14350           (pc)))
14351    (clobber (reg:CCFP FPSR_REG))
14352    (clobber (reg:CCFP FLAGS_REG))
14353    (clobber (match_scratch:HI 4 "=a"))]
14354   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14355    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14356    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
14357    && SELECT_CC_MODE (GET_CODE (operands[0]),
14358                       operands[1], operands[2]) == CCFPmode
14359    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14360   "#")
14361
14362 ;; The order of operands in *fp_jcc_8_387 is forced by combine in
14363 ;; simplify_comparison () function. Float operator is treated as RTX_OBJ
14364 ;; with a precedence over other operators and is always put in the first
14365 ;; place. Swap condition and operands to match ficom instruction.
14366
14367 (define_insn "*fp_jcc_8<mode>_387"
14368   [(set (pc)
14369         (if_then_else (match_operator 0 "comparison_operator"
14370                         [(match_operator 1 "float_operator"
14371                            [(match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r")])
14372                            (match_operand 3 "register_operand" "f,f")])
14373           (label_ref (match_operand 4 "" ""))
14374           (pc)))
14375    (clobber (reg:CCFP FPSR_REG))
14376    (clobber (reg:CCFP FLAGS_REG))
14377    (clobber (match_scratch:HI 5 "=a,a"))]
14378   "X87_FLOAT_MODE_P (GET_MODE (operands[3]))
14379    && (TARGET_USE_<MODE>MODE_FIOP || optimize_size)
14380    && GET_MODE (operands[1]) == GET_MODE (operands[3])
14381    && !ix86_use_fcomi_compare (swap_condition (GET_CODE (operands[0])))
14382    && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode
14383    && ix86_fp_jump_nontrivial_p (swap_condition (GET_CODE (operands[0])))"
14384   "#")
14385
14386 (define_split
14387   [(set (pc)
14388         (if_then_else (match_operator 0 "comparison_operator"
14389                         [(match_operand 1 "register_operand" "")
14390                          (match_operand 2 "nonimmediate_operand" "")])
14391           (match_operand 3 "" "")
14392           (match_operand 4 "" "")))
14393    (clobber (reg:CCFP FPSR_REG))
14394    (clobber (reg:CCFP FLAGS_REG))]
14395   "reload_completed"
14396   [(const_int 0)]
14397 {
14398   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
14399                         operands[3], operands[4], NULL_RTX, NULL_RTX);
14400   DONE;
14401 })
14402
14403 (define_split
14404   [(set (pc)
14405         (if_then_else (match_operator 0 "comparison_operator"
14406                         [(match_operand 1 "register_operand" "")
14407                          (match_operand 2 "general_operand" "")])
14408           (match_operand 3 "" "")
14409           (match_operand 4 "" "")))
14410    (clobber (reg:CCFP FPSR_REG))
14411    (clobber (reg:CCFP FLAGS_REG))
14412    (clobber (match_scratch:HI 5 "=a"))]
14413   "reload_completed"
14414   [(const_int 0)]
14415 {
14416   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
14417                         operands[3], operands[4], operands[5], NULL_RTX);
14418   DONE;
14419 })
14420
14421 (define_split
14422   [(set (pc)
14423         (if_then_else (match_operator 0 "comparison_operator"
14424                         [(match_operator 1 "float_operator"
14425                            [(match_operand:X87MODEI12 2 "memory_operand" "")])
14426                            (match_operand 3 "register_operand" "")])
14427           (match_operand 4 "" "")
14428           (match_operand 5 "" "")))
14429    (clobber (reg:CCFP FPSR_REG))
14430    (clobber (reg:CCFP FLAGS_REG))
14431    (clobber (match_scratch:HI 6 "=a"))]
14432   "reload_completed"
14433   [(const_int 0)]
14434 {
14435   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]);
14436   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
14437                         operands[3], operands[7],
14438                         operands[4], operands[5], operands[6], NULL_RTX);
14439   DONE;
14440 })
14441
14442 ;; %%% Kill this when reload knows how to do it.
14443 (define_split
14444   [(set (pc)
14445         (if_then_else (match_operator 0 "comparison_operator"
14446                         [(match_operator 1 "float_operator"
14447                            [(match_operand:X87MODEI12 2 "register_operand" "")])
14448                            (match_operand 3 "register_operand" "")])
14449           (match_operand 4 "" "")
14450           (match_operand 5 "" "")))
14451    (clobber (reg:CCFP FPSR_REG))
14452    (clobber (reg:CCFP FLAGS_REG))
14453    (clobber (match_scratch:HI 6 "=a"))]
14454   "reload_completed"
14455   [(const_int 0)]
14456 {
14457   operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
14458   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]);
14459   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
14460                         operands[3], operands[7],
14461                         operands[4], operands[5], operands[6], operands[2]);
14462   DONE;
14463 })
14464 \f
14465 ;; Unconditional and other jump instructions
14466
14467 (define_insn "jump"
14468   [(set (pc)
14469         (label_ref (match_operand 0 "" "")))]
14470   ""
14471   "jmp\t%l0"
14472   [(set_attr "type" "ibr")
14473    (set (attr "length")
14474            (if_then_else (and (ge (minus (match_dup 0) (pc))
14475                                   (const_int -126))
14476                               (lt (minus (match_dup 0) (pc))
14477                                   (const_int 128)))
14478              (const_int 2)
14479              (const_int 5)))
14480    (set_attr "modrm" "0")])
14481
14482 (define_expand "indirect_jump"
14483   [(set (pc) (match_operand 0 "nonimmediate_operand" ""))]
14484   ""
14485   "")
14486
14487 (define_insn "*indirect_jump"
14488   [(set (pc) (match_operand:P 0 "nonimmediate_operand" "rm"))]
14489   ""
14490   "jmp\t%A0"
14491   [(set_attr "type" "ibr")
14492    (set_attr "length_immediate" "0")])
14493
14494 (define_expand "tablejump"
14495   [(parallel [(set (pc) (match_operand 0 "nonimmediate_operand" ""))
14496               (use (label_ref (match_operand 1 "" "")))])]
14497   ""
14498 {
14499   /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
14500      relative.  Convert the relative address to an absolute address.  */
14501   if (flag_pic)
14502     {
14503       rtx op0, op1;
14504       enum rtx_code code;
14505
14506       /* We can't use @GOTOFF for text labels on VxWorks;
14507          see gotoff_operand.  */
14508       if (TARGET_64BIT || TARGET_VXWORKS_RTP)
14509         {
14510           code = PLUS;
14511           op0 = operands[0];
14512           op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
14513         }
14514       else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
14515         {
14516           code = PLUS;
14517           op0 = operands[0];
14518           op1 = pic_offset_table_rtx;
14519         }
14520       else
14521         {
14522           code = MINUS;
14523           op0 = pic_offset_table_rtx;
14524           op1 = operands[0];
14525         }
14526
14527       operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
14528                                          OPTAB_DIRECT);
14529     }
14530 })
14531
14532 (define_insn "*tablejump_1"
14533   [(set (pc) (match_operand:P 0 "nonimmediate_operand" "rm"))
14534    (use (label_ref (match_operand 1 "" "")))]
14535   ""
14536   "jmp\t%A0"
14537   [(set_attr "type" "ibr")
14538    (set_attr "length_immediate" "0")])
14539 \f
14540 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
14541
14542 (define_peephole2
14543   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
14544    (set (match_operand:QI 1 "register_operand" "")
14545         (match_operator:QI 2 "ix86_comparison_operator"
14546           [(reg FLAGS_REG) (const_int 0)]))
14547    (set (match_operand 3 "q_regs_operand" "")
14548         (zero_extend (match_dup 1)))]
14549   "(peep2_reg_dead_p (3, operands[1])
14550     || operands_match_p (operands[1], operands[3]))
14551    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
14552   [(set (match_dup 4) (match_dup 0))
14553    (set (strict_low_part (match_dup 5))
14554         (match_dup 2))]
14555 {
14556   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
14557   operands[5] = gen_lowpart (QImode, operands[3]);
14558   ix86_expand_clear (operands[3]);
14559 })
14560
14561 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
14562
14563 (define_peephole2
14564   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
14565    (set (match_operand:QI 1 "register_operand" "")
14566         (match_operator:QI 2 "ix86_comparison_operator"
14567           [(reg FLAGS_REG) (const_int 0)]))
14568    (parallel [(set (match_operand 3 "q_regs_operand" "")
14569                    (zero_extend (match_dup 1)))
14570               (clobber (reg:CC FLAGS_REG))])]
14571   "(peep2_reg_dead_p (3, operands[1])
14572     || operands_match_p (operands[1], operands[3]))
14573    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
14574   [(set (match_dup 4) (match_dup 0))
14575    (set (strict_low_part (match_dup 5))
14576         (match_dup 2))]
14577 {
14578   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
14579   operands[5] = gen_lowpart (QImode, operands[3]);
14580   ix86_expand_clear (operands[3]);
14581 })
14582 \f
14583 ;; Call instructions.
14584
14585 ;; The predicates normally associated with named expanders are not properly
14586 ;; checked for calls.  This is a bug in the generic code, but it isn't that
14587 ;; easy to fix.  Ignore it for now and be prepared to fix things up.
14588
14589 ;; Call subroutine returning no value.
14590
14591 (define_expand "call_pop"
14592   [(parallel [(call (match_operand:QI 0 "" "")
14593                     (match_operand:SI 1 "" ""))
14594               (set (reg:SI SP_REG)
14595                    (plus:SI (reg:SI SP_REG)
14596                             (match_operand:SI 3 "" "")))])]
14597   "!TARGET_64BIT"
14598 {
14599   ix86_expand_call (NULL, operands[0], operands[1], operands[2], operands[3], 0);
14600   DONE;
14601 })
14602
14603 (define_insn "*call_pop_0"
14604   [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" ""))
14605          (match_operand:SI 1 "" ""))
14606    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
14607                             (match_operand:SI 2 "immediate_operand" "")))]
14608   "!TARGET_64BIT"
14609 {
14610   if (SIBLING_CALL_P (insn))
14611     return "jmp\t%P0";
14612   else
14613     return "call\t%P0";
14614 }
14615   [(set_attr "type" "call")])
14616
14617 (define_insn "*call_pop_1"
14618   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
14619          (match_operand:SI 1 "" ""))
14620    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
14621                             (match_operand:SI 2 "immediate_operand" "i")))]
14622   "!TARGET_64BIT"
14623 {
14624   if (constant_call_address_operand (operands[0], Pmode))
14625     {
14626       if (SIBLING_CALL_P (insn))
14627         return "jmp\t%P0";
14628       else
14629         return "call\t%P0";
14630     }
14631   if (SIBLING_CALL_P (insn))
14632     return "jmp\t%A0";
14633   else
14634     return "call\t%A0";
14635 }
14636   [(set_attr "type" "call")])
14637
14638 (define_expand "call"
14639   [(call (match_operand:QI 0 "" "")
14640          (match_operand 1 "" ""))
14641    (use (match_operand 2 "" ""))]
14642   ""
14643 {
14644   ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 0);
14645   DONE;
14646 })
14647
14648 (define_expand "sibcall"
14649   [(call (match_operand:QI 0 "" "")
14650          (match_operand 1 "" ""))
14651    (use (match_operand 2 "" ""))]
14652   ""
14653 {
14654   ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 1);
14655   DONE;
14656 })
14657
14658 (define_insn "*call_0"
14659   [(call (mem:QI (match_operand 0 "constant_call_address_operand" ""))
14660          (match_operand 1 "" ""))]
14661   ""
14662 {
14663   if (SIBLING_CALL_P (insn))
14664     return "jmp\t%P0";
14665   else
14666     return "call\t%P0";
14667 }
14668   [(set_attr "type" "call")])
14669
14670 (define_insn "*call_1"
14671   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
14672          (match_operand 1 "" ""))]
14673   "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
14674 {
14675   if (constant_call_address_operand (operands[0], Pmode))
14676     return "call\t%P0";
14677   return "call\t%A0";
14678 }
14679   [(set_attr "type" "call")])
14680
14681 (define_insn "*sibcall_1"
14682   [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "s,c,d,a"))
14683          (match_operand 1 "" ""))]
14684   "SIBLING_CALL_P (insn) && !TARGET_64BIT"
14685 {
14686   if (constant_call_address_operand (operands[0], Pmode))
14687     return "jmp\t%P0";
14688   return "jmp\t%A0";
14689 }
14690   [(set_attr "type" "call")])
14691
14692 (define_insn "*call_1_rex64"
14693   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rsm"))
14694          (match_operand 1 "" ""))]
14695   "!SIBLING_CALL_P (insn) && TARGET_64BIT
14696    && ix86_cmodel != CM_LARGE && ix86_cmodel != CM_LARGE_PIC"
14697 {
14698   if (constant_call_address_operand (operands[0], Pmode))
14699     return "call\t%P0";
14700   return "call\t%A0";
14701 }
14702   [(set_attr "type" "call")])
14703
14704 (define_insn "*call_1_rex64_large"
14705   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rm"))
14706          (match_operand 1 "" ""))]
14707   "!SIBLING_CALL_P (insn) && TARGET_64BIT"
14708   "call\t%A0"
14709   [(set_attr "type" "call")])
14710
14711 (define_insn "*sibcall_1_rex64"
14712   [(call (mem:QI (match_operand:DI 0 "constant_call_address_operand" ""))
14713          (match_operand 1 "" ""))]
14714   "SIBLING_CALL_P (insn) && TARGET_64BIT"
14715   "jmp\t%P0"
14716   [(set_attr "type" "call")])
14717
14718 (define_insn "*sibcall_1_rex64_v"
14719   [(call (mem:QI (reg:DI R11_REG))
14720          (match_operand 0 "" ""))]
14721   "SIBLING_CALL_P (insn) && TARGET_64BIT"
14722   "jmp\t{*%%}r11"
14723   [(set_attr "type" "call")])
14724
14725
14726 ;; Call subroutine, returning value in operand 0
14727
14728 (define_expand "call_value_pop"
14729   [(parallel [(set (match_operand 0 "" "")
14730                    (call (match_operand:QI 1 "" "")
14731                          (match_operand:SI 2 "" "")))
14732               (set (reg:SI SP_REG)
14733                    (plus:SI (reg:SI SP_REG)
14734                             (match_operand:SI 4 "" "")))])]
14735   "!TARGET_64BIT"
14736 {
14737   ix86_expand_call (operands[0], operands[1], operands[2],
14738                     operands[3], operands[4], 0);
14739   DONE;
14740 })
14741
14742 (define_expand "call_value"
14743   [(set (match_operand 0 "" "")
14744         (call (match_operand:QI 1 "" "")
14745               (match_operand:SI 2 "" "")))
14746    (use (match_operand:SI 3 "" ""))]
14747   ;; Operand 2 not used on the i386.
14748   ""
14749 {
14750   ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 0);
14751   DONE;
14752 })
14753
14754 (define_expand "sibcall_value"
14755   [(set (match_operand 0 "" "")
14756         (call (match_operand:QI 1 "" "")
14757               (match_operand:SI 2 "" "")))
14758    (use (match_operand:SI 3 "" ""))]
14759   ;; Operand 2 not used on the i386.
14760   ""
14761 {
14762   ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 1);
14763   DONE;
14764 })
14765
14766 ;; Call subroutine returning any type.
14767
14768 (define_expand "untyped_call"
14769   [(parallel [(call (match_operand 0 "" "")
14770                     (const_int 0))
14771               (match_operand 1 "" "")
14772               (match_operand 2 "" "")])]
14773   ""
14774 {
14775   int i;
14776
14777   /* In order to give reg-stack an easier job in validating two
14778      coprocessor registers as containing a possible return value,
14779      simply pretend the untyped call returns a complex long double
14780      value.  */
14781
14782   ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
14783                      ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
14784                     operands[0], const0_rtx,
14785                     GEN_INT ((DEFAULT_ABI == SYSV_ABI ? X86_64_SSE_REGPARM_MAX
14786                                                       : X64_SSE_REGPARM_MAX)
14787                              - 1),
14788                     NULL, 0);
14789
14790   for (i = 0; i < XVECLEN (operands[2], 0); i++)
14791     {
14792       rtx set = XVECEXP (operands[2], 0, i);
14793       emit_move_insn (SET_DEST (set), SET_SRC (set));
14794     }
14795
14796   /* The optimizer does not know that the call sets the function value
14797      registers we stored in the result block.  We avoid problems by
14798      claiming that all hard registers are used and clobbered at this
14799      point.  */
14800   emit_insn (gen_blockage ());
14801
14802   DONE;
14803 })
14804 \f
14805 ;; Prologue and epilogue instructions
14806
14807 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
14808 ;; all of memory.  This blocks insns from being moved across this point.
14809
14810 (define_insn "blockage"
14811   [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
14812   ""
14813   ""
14814   [(set_attr "length" "0")])
14815
14816 ;; As USE insns aren't meaningful after reload, this is used instead
14817 ;; to prevent deleting instructions setting registers for PIC code
14818 (define_insn "prologue_use"
14819   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_PROLOGUE_USE)]
14820   ""
14821   ""
14822   [(set_attr "length" "0")])
14823
14824 ;; Insn emitted into the body of a function to return from a function.
14825 ;; This is only done if the function's epilogue is known to be simple.
14826 ;; See comments for ix86_can_use_return_insn_p in i386.c.
14827
14828 (define_expand "return"
14829   [(return)]
14830   "ix86_can_use_return_insn_p ()"
14831 {
14832   if (crtl->args.pops_args)
14833     {
14834       rtx popc = GEN_INT (crtl->args.pops_args);
14835       emit_jump_insn (gen_return_pop_internal (popc));
14836       DONE;
14837     }
14838 })
14839
14840 (define_insn "return_internal"
14841   [(return)]
14842   "reload_completed"
14843   "ret"
14844   [(set_attr "length" "1")
14845    (set_attr "length_immediate" "0")
14846    (set_attr "modrm" "0")])
14847
14848 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
14849 ;; instruction Athlon and K8 have.
14850
14851 (define_insn "return_internal_long"
14852   [(return)
14853    (unspec [(const_int 0)] UNSPEC_REP)]
14854   "reload_completed"
14855   "rep\;ret"
14856   [(set_attr "length" "1")
14857    (set_attr "length_immediate" "0")
14858    (set_attr "prefix_rep" "1")
14859    (set_attr "modrm" "0")])
14860
14861 (define_insn "return_pop_internal"
14862   [(return)
14863    (use (match_operand:SI 0 "const_int_operand" ""))]
14864   "reload_completed"
14865   "ret\t%0"
14866   [(set_attr "length" "3")
14867    (set_attr "length_immediate" "2")
14868    (set_attr "modrm" "0")])
14869
14870 (define_insn "return_indirect_internal"
14871   [(return)
14872    (use (match_operand:SI 0 "register_operand" "r"))]
14873   "reload_completed"
14874   "jmp\t%A0"
14875   [(set_attr "type" "ibr")
14876    (set_attr "length_immediate" "0")])
14877
14878 (define_insn "nop"
14879   [(const_int 0)]
14880   ""
14881   "nop"
14882   [(set_attr "length" "1")
14883    (set_attr "length_immediate" "0")
14884    (set_attr "modrm" "0")])
14885
14886 ;; Align to 16-byte boundary, max skip in op0.  Used to avoid
14887 ;; branch prediction penalty for the third jump in a 16-byte
14888 ;; block on K8.
14889
14890 (define_insn "align"
14891   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
14892   ""
14893 {
14894 #ifdef ASM_OUTPUT_MAX_SKIP_ALIGN
14895   ASM_OUTPUT_MAX_SKIP_ALIGN (asm_out_file, 4, (int)INTVAL (operands[0]));
14896 #else
14897   /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
14898      The align insn is used to avoid 3 jump instructions in the row to improve
14899      branch prediction and the benefits hardly outweigh the cost of extra 8
14900      nops on the average inserted by full alignment pseudo operation.  */
14901 #endif
14902   return "";
14903 }
14904   [(set_attr "length" "16")])
14905
14906 (define_expand "prologue"
14907   [(const_int 0)]
14908   ""
14909   "ix86_expand_prologue (); DONE;")
14910
14911 (define_insn "set_got"
14912   [(set (match_operand:SI 0 "register_operand" "=r")
14913         (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
14914    (clobber (reg:CC FLAGS_REG))]
14915   "!TARGET_64BIT"
14916   { return output_set_got (operands[0], NULL_RTX); }
14917   [(set_attr "type" "multi")
14918    (set_attr "length" "12")])
14919
14920 (define_insn "set_got_labelled"
14921   [(set (match_operand:SI 0 "register_operand" "=r")
14922         (unspec:SI [(label_ref (match_operand 1 "" ""))]
14923          UNSPEC_SET_GOT))
14924    (clobber (reg:CC FLAGS_REG))]
14925   "!TARGET_64BIT"
14926   { return output_set_got (operands[0], operands[1]); }
14927   [(set_attr "type" "multi")
14928    (set_attr "length" "12")])
14929
14930 (define_insn "set_got_rex64"
14931   [(set (match_operand:DI 0 "register_operand" "=r")
14932         (unspec:DI [(const_int 0)] UNSPEC_SET_GOT))]
14933   "TARGET_64BIT"
14934   "lea{q}\t{_GLOBAL_OFFSET_TABLE_(%%rip), %0|%0, _GLOBAL_OFFSET_TABLE_[rip]}"
14935   [(set_attr "type" "lea")
14936    (set_attr "length" "6")])
14937
14938 (define_insn "set_rip_rex64"
14939   [(set (match_operand:DI 0 "register_operand" "=r")
14940         (unspec:DI [(match_operand:DI 1 "" "")] UNSPEC_SET_RIP))]
14941   "TARGET_64BIT"
14942   "lea{q}\t{%l1(%%rip), %0|%0, %l1[rip]}"
14943   [(set_attr "type" "lea")
14944    (set_attr "length" "6")])
14945
14946 (define_insn "set_got_offset_rex64"
14947   [(set (match_operand:DI 0 "register_operand" "=r")
14948         (unspec:DI [(match_operand:DI 1 "" "")] UNSPEC_SET_GOT_OFFSET))]
14949   "TARGET_64BIT"
14950   "movabs{q}\t{$_GLOBAL_OFFSET_TABLE_-%l1, %0|%0, OFFSET FLAT:_GLOBAL_OFFSET_TABLE_-%l1}"
14951   [(set_attr "type" "imov")
14952    (set_attr "length" "11")])
14953
14954 (define_expand "epilogue"
14955   [(const_int 0)]
14956   ""
14957   "ix86_expand_epilogue (1); DONE;")
14958
14959 (define_expand "sibcall_epilogue"
14960   [(const_int 0)]
14961   ""
14962   "ix86_expand_epilogue (0); DONE;")
14963
14964 (define_expand "eh_return"
14965   [(use (match_operand 0 "register_operand" ""))]
14966   ""
14967 {
14968   rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
14969
14970   /* Tricky bit: we write the address of the handler to which we will
14971      be returning into someone else's stack frame, one word below the
14972      stack address we wish to restore.  */
14973   tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
14974   tmp = plus_constant (tmp, -UNITS_PER_WORD);
14975   tmp = gen_rtx_MEM (Pmode, tmp);
14976   emit_move_insn (tmp, ra);
14977
14978   if (Pmode == SImode)
14979     emit_jump_insn (gen_eh_return_si (sa));
14980   else
14981     emit_jump_insn (gen_eh_return_di (sa));
14982   emit_barrier ();
14983   DONE;
14984 })
14985
14986 (define_insn_and_split "eh_return_<mode>"
14987   [(set (pc)
14988         (unspec [(match_operand:P 0 "register_operand" "c")]
14989                  UNSPEC_EH_RETURN))]
14990   ""
14991   "#"
14992   "reload_completed"
14993   [(const_int 0)]
14994   "ix86_expand_epilogue (2); DONE;")
14995
14996 (define_insn "leave"
14997   [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4)))
14998    (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG)))
14999    (clobber (mem:BLK (scratch)))]
15000   "!TARGET_64BIT"
15001   "leave"
15002   [(set_attr "type" "leave")])
15003
15004 (define_insn "leave_rex64"
15005   [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8)))
15006    (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG)))
15007    (clobber (mem:BLK (scratch)))]
15008   "TARGET_64BIT"
15009   "leave"
15010   [(set_attr "type" "leave")])
15011 \f
15012 (define_expand "ffssi2"
15013   [(parallel
15014      [(set (match_operand:SI 0 "register_operand" "")
15015            (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "")))
15016       (clobber (match_scratch:SI 2 ""))
15017       (clobber (reg:CC FLAGS_REG))])]
15018   ""
15019 {
15020   if (TARGET_CMOVE)
15021     {
15022       emit_insn (gen_ffs_cmove (operands[0], operands[1]));
15023       DONE;
15024     }
15025 })
15026
15027 (define_expand "ffs_cmove"
15028   [(set (match_dup 2) (const_int -1))
15029    (parallel [(set (reg:CCZ FLAGS_REG)
15030                    (compare:CCZ (match_operand:SI 1 "register_operand" "")
15031                                 (const_int 0)))
15032               (set (match_operand:SI 0 "nonimmediate_operand" "")
15033                    (ctz:SI (match_dup 1)))])
15034    (set (match_dup 0) (if_then_else:SI
15035                         (eq (reg:CCZ FLAGS_REG) (const_int 0))
15036                         (match_dup 2)
15037                         (match_dup 0)))
15038    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
15039               (clobber (reg:CC FLAGS_REG))])]
15040   "TARGET_CMOVE"
15041   "operands[2] = gen_reg_rtx (SImode);")
15042
15043 (define_insn_and_split "*ffs_no_cmove"
15044   [(set (match_operand:SI 0 "nonimmediate_operand" "=r")
15045         (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
15046    (clobber (match_scratch:SI 2 "=&q"))
15047    (clobber (reg:CC FLAGS_REG))]
15048   "!TARGET_CMOVE"
15049   "#"
15050   "&& reload_completed"
15051   [(parallel [(set (reg:CCZ FLAGS_REG)
15052                    (compare:CCZ (match_dup 1) (const_int 0)))
15053               (set (match_dup 0) (ctz:SI (match_dup 1)))])
15054    (set (strict_low_part (match_dup 3))
15055         (eq:QI (reg:CCZ FLAGS_REG) (const_int 0)))
15056    (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
15057               (clobber (reg:CC FLAGS_REG))])
15058    (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
15059               (clobber (reg:CC FLAGS_REG))])
15060    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
15061               (clobber (reg:CC FLAGS_REG))])]
15062 {
15063   operands[3] = gen_lowpart (QImode, operands[2]);
15064   ix86_expand_clear (operands[2]);
15065 })
15066
15067 (define_insn "*ffssi_1"
15068   [(set (reg:CCZ FLAGS_REG)
15069         (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "rm")
15070                      (const_int 0)))
15071    (set (match_operand:SI 0 "register_operand" "=r")
15072         (ctz:SI (match_dup 1)))]
15073   ""
15074   "bsf{l}\t{%1, %0|%0, %1}"
15075   [(set_attr "prefix_0f" "1")])
15076
15077 (define_expand "ffsdi2"
15078   [(set (match_dup 2) (const_int -1))
15079    (parallel [(set (reg:CCZ FLAGS_REG)
15080                    (compare:CCZ (match_operand:DI 1 "register_operand" "")
15081                                 (const_int 0)))
15082               (set (match_operand:DI 0 "nonimmediate_operand" "")
15083                    (ctz:DI (match_dup 1)))])
15084    (set (match_dup 0) (if_then_else:DI
15085                         (eq (reg:CCZ FLAGS_REG) (const_int 0))
15086                         (match_dup 2)
15087                         (match_dup 0)))
15088    (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (const_int 1)))
15089               (clobber (reg:CC FLAGS_REG))])]
15090   "TARGET_64BIT"
15091   "operands[2] = gen_reg_rtx (DImode);")
15092
15093 (define_insn "*ffsdi_1"
15094   [(set (reg:CCZ FLAGS_REG)
15095         (compare:CCZ (match_operand:DI 1 "nonimmediate_operand" "rm")
15096                      (const_int 0)))
15097    (set (match_operand:DI 0 "register_operand" "=r")
15098         (ctz:DI (match_dup 1)))]
15099   "TARGET_64BIT"
15100   "bsf{q}\t{%1, %0|%0, %1}"
15101   [(set_attr "prefix_0f" "1")])
15102
15103 (define_insn "ctzsi2"
15104   [(set (match_operand:SI 0 "register_operand" "=r")
15105         (ctz:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
15106    (clobber (reg:CC FLAGS_REG))]
15107   ""
15108   "bsf{l}\t{%1, %0|%0, %1}"
15109   [(set_attr "prefix_0f" "1")])
15110
15111 (define_insn "ctzdi2"
15112   [(set (match_operand:DI 0 "register_operand" "=r")
15113         (ctz:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
15114    (clobber (reg:CC FLAGS_REG))]
15115   "TARGET_64BIT"
15116   "bsf{q}\t{%1, %0|%0, %1}"
15117   [(set_attr "prefix_0f" "1")])
15118
15119 (define_expand "clzsi2"
15120   [(parallel
15121      [(set (match_operand:SI 0 "register_operand" "")
15122            (minus:SI (const_int 31)
15123                      (clz:SI (match_operand:SI 1 "nonimmediate_operand" ""))))
15124       (clobber (reg:CC FLAGS_REG))])
15125    (parallel
15126      [(set (match_dup 0) (xor:SI (match_dup 0) (const_int 31)))
15127       (clobber (reg:CC FLAGS_REG))])]
15128   ""
15129 {
15130   if (TARGET_ABM)
15131     {
15132       emit_insn (gen_clzsi2_abm (operands[0], operands[1]));
15133       DONE;
15134     }
15135 })
15136
15137 (define_insn "clzsi2_abm"
15138   [(set (match_operand:SI 0 "register_operand" "=r")
15139         (clz:SI (match_operand:SI 1 "nonimmediate_operand" "")))
15140    (clobber (reg:CC FLAGS_REG))]
15141   "TARGET_ABM"
15142   "lzcnt{l}\t{%1, %0|%0, %1}"
15143   [(set_attr "prefix_rep" "1")
15144    (set_attr "type" "bitmanip")
15145    (set_attr "mode" "SI")])
15146
15147 (define_insn "*bsr"
15148   [(set (match_operand:SI 0 "register_operand" "=r")
15149         (minus:SI (const_int 31)
15150                   (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
15151    (clobber (reg:CC FLAGS_REG))]
15152   ""
15153   "bsr{l}\t{%1, %0|%0, %1}"
15154   [(set_attr "prefix_0f" "1")
15155    (set_attr "mode" "SI")])
15156
15157 (define_insn "popcountsi2"
15158   [(set (match_operand:SI 0 "register_operand" "=r")
15159         (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "")))
15160    (clobber (reg:CC FLAGS_REG))]
15161   "TARGET_POPCNT"
15162   "popcnt{l}\t{%1, %0|%0, %1}"
15163   [(set_attr "prefix_rep" "1")
15164    (set_attr "type" "bitmanip")
15165    (set_attr "mode" "SI")])
15166
15167 (define_insn "*popcountsi2_cmp"
15168   [(set (reg FLAGS_REG)
15169         (compare
15170           (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))
15171           (const_int 0)))
15172    (set (match_operand:SI 0 "register_operand" "=r")
15173         (popcount:SI (match_dup 1)))]
15174   "TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
15175   "popcnt{l}\t{%1, %0|%0, %1}"
15176   [(set_attr "prefix_rep" "1")
15177    (set_attr "type" "bitmanip")
15178    (set_attr "mode" "SI")])
15179
15180 (define_insn "*popcountsi2_cmp_zext"
15181   [(set (reg FLAGS_REG)
15182         (compare
15183           (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))
15184           (const_int 0)))
15185    (set (match_operand:DI 0 "register_operand" "=r")
15186         (zero_extend:DI(popcount:SI (match_dup 1))))]
15187   "TARGET_64BIT && TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
15188   "popcnt{l}\t{%1, %0|%0, %1}"
15189   [(set_attr "prefix_rep" "1")
15190    (set_attr "type" "bitmanip")
15191    (set_attr "mode" "SI")])
15192
15193 (define_expand "bswapsi2"
15194   [(set (match_operand:SI 0 "register_operand" "")
15195         (bswap:SI (match_operand:SI 1 "register_operand" "")))]
15196   ""
15197 {
15198   if (!TARGET_BSWAP)
15199     {
15200       rtx x = operands[0];
15201
15202       emit_move_insn (x, operands[1]);
15203       emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
15204       emit_insn (gen_rotlsi3 (x, x, GEN_INT (16)));
15205       emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
15206       DONE;
15207     }
15208 })
15209
15210 (define_insn "*bswapsi_1"
15211   [(set (match_operand:SI 0 "register_operand" "=r")
15212         (bswap:SI (match_operand:SI 1 "register_operand" "0")))]
15213   "TARGET_BSWAP"
15214   "bswap\t%0"
15215   [(set_attr "prefix_0f" "1")
15216    (set_attr "length" "2")])
15217
15218 (define_insn "*bswaphi_lowpart_1"
15219   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+Q,r"))
15220         (bswap:HI (match_dup 0)))
15221    (clobber (reg:CC FLAGS_REG))]
15222   "TARGET_USE_XCHGB || optimize_size"
15223   "@
15224     xchg{b}\t{%h0, %b0|%b0, %h0}
15225     rol{w}\t{$8, %0|%0, 8}"
15226   [(set_attr "length" "2,4")
15227    (set_attr "mode" "QI,HI")])
15228
15229 (define_insn "bswaphi_lowpart"
15230   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
15231         (bswap:HI (match_dup 0)))
15232    (clobber (reg:CC FLAGS_REG))]
15233   ""
15234   "rol{w}\t{$8, %0|%0, 8}"
15235   [(set_attr "length" "4")
15236    (set_attr "mode" "HI")])
15237
15238 (define_insn "bswapdi2"
15239   [(set (match_operand:DI 0 "register_operand" "=r")
15240         (bswap:DI (match_operand:DI 1 "register_operand" "0")))]
15241   "TARGET_64BIT"
15242   "bswap\t%0"
15243   [(set_attr "prefix_0f" "1")
15244    (set_attr "length" "3")])
15245
15246 (define_expand "clzdi2"
15247   [(parallel
15248      [(set (match_operand:DI 0 "register_operand" "")
15249            (minus:DI (const_int 63)
15250                      (clz:DI (match_operand:DI 1 "nonimmediate_operand" ""))))
15251       (clobber (reg:CC FLAGS_REG))])
15252    (parallel
15253      [(set (match_dup 0) (xor:DI (match_dup 0) (const_int 63)))
15254       (clobber (reg:CC FLAGS_REG))])]
15255   "TARGET_64BIT"
15256 {
15257   if (TARGET_ABM)
15258     {
15259       emit_insn (gen_clzdi2_abm (operands[0], operands[1]));
15260       DONE;
15261     }
15262 })
15263
15264 (define_insn "clzdi2_abm"
15265   [(set (match_operand:DI 0 "register_operand" "=r")
15266         (clz:DI (match_operand:DI 1 "nonimmediate_operand" "")))
15267    (clobber (reg:CC FLAGS_REG))]
15268   "TARGET_64BIT && TARGET_ABM"
15269   "lzcnt{q}\t{%1, %0|%0, %1}"
15270   [(set_attr "prefix_rep" "1")
15271    (set_attr "type" "bitmanip")
15272    (set_attr "mode" "DI")])
15273
15274 (define_insn "*bsr_rex64"
15275   [(set (match_operand:DI 0 "register_operand" "=r")
15276         (minus:DI (const_int 63)
15277                   (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))))
15278    (clobber (reg:CC FLAGS_REG))]
15279   "TARGET_64BIT"
15280   "bsr{q}\t{%1, %0|%0, %1}"
15281   [(set_attr "prefix_0f" "1")
15282    (set_attr "mode" "DI")])
15283
15284 (define_insn "popcountdi2"
15285   [(set (match_operand:DI 0 "register_operand" "=r")
15286         (popcount:DI (match_operand:DI 1 "nonimmediate_operand" "")))
15287    (clobber (reg:CC FLAGS_REG))]
15288   "TARGET_64BIT && TARGET_POPCNT"
15289   "popcnt{q}\t{%1, %0|%0, %1}"
15290   [(set_attr "prefix_rep" "1")
15291    (set_attr "type" "bitmanip")
15292    (set_attr "mode" "DI")])
15293
15294 (define_insn "*popcountdi2_cmp"
15295   [(set (reg FLAGS_REG)
15296         (compare
15297           (popcount:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))
15298           (const_int 0)))
15299    (set (match_operand:DI 0 "register_operand" "=r")
15300         (popcount:DI (match_dup 1)))]
15301   "TARGET_64BIT && TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
15302   "popcnt{q}\t{%1, %0|%0, %1}"
15303   [(set_attr "prefix_rep" "1")
15304    (set_attr "type" "bitmanip")
15305    (set_attr "mode" "DI")])
15306
15307 (define_expand "clzhi2"
15308   [(parallel
15309      [(set (match_operand:HI 0 "register_operand" "")
15310            (minus:HI (const_int 15)
15311                      (clz:HI (match_operand:HI 1 "nonimmediate_operand" ""))))
15312       (clobber (reg:CC FLAGS_REG))])
15313    (parallel
15314      [(set (match_dup 0) (xor:HI (match_dup 0) (const_int 15)))
15315       (clobber (reg:CC FLAGS_REG))])]
15316   ""
15317 {
15318   if (TARGET_ABM)
15319     {
15320       emit_insn (gen_clzhi2_abm (operands[0], operands[1]));
15321       DONE;
15322     }
15323 })
15324
15325 (define_insn "clzhi2_abm"
15326   [(set (match_operand:HI 0 "register_operand" "=r")
15327         (clz:HI (match_operand:HI 1 "nonimmediate_operand" "")))
15328    (clobber (reg:CC FLAGS_REG))]
15329   "TARGET_ABM"
15330   "lzcnt{w}\t{%1, %0|%0, %1}"
15331   [(set_attr "prefix_rep" "1")
15332    (set_attr "type" "bitmanip")
15333    (set_attr "mode" "HI")])
15334
15335 (define_insn "*bsrhi"
15336   [(set (match_operand:HI 0 "register_operand" "=r")
15337         (minus:HI (const_int 15)
15338                   (clz:HI (match_operand:HI 1 "nonimmediate_operand" "rm"))))
15339    (clobber (reg:CC FLAGS_REG))]
15340   ""
15341   "bsr{w}\t{%1, %0|%0, %1}"
15342   [(set_attr "prefix_0f" "1")
15343    (set_attr "mode" "HI")])
15344
15345 (define_insn "popcounthi2"
15346   [(set (match_operand:HI 0 "register_operand" "=r")
15347         (popcount:HI (match_operand:HI 1 "nonimmediate_operand" "")))
15348    (clobber (reg:CC FLAGS_REG))]
15349   "TARGET_POPCNT"
15350   "popcnt{w}\t{%1, %0|%0, %1}"
15351   [(set_attr "prefix_rep" "1")
15352    (set_attr "type" "bitmanip")
15353    (set_attr "mode" "HI")])
15354
15355 (define_insn "*popcounthi2_cmp"
15356   [(set (reg FLAGS_REG)
15357         (compare
15358           (popcount:HI (match_operand:HI 1 "nonimmediate_operand" "rm"))
15359           (const_int 0)))
15360    (set (match_operand:HI 0 "register_operand" "=r")
15361         (popcount:HI (match_dup 1)))]
15362   "TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
15363   "popcnt{w}\t{%1, %0|%0, %1}"
15364   [(set_attr "prefix_rep" "1")
15365    (set_attr "type" "bitmanip")
15366    (set_attr "mode" "HI")])
15367
15368 (define_expand "paritydi2"
15369   [(set (match_operand:DI 0 "register_operand" "")
15370         (parity:DI (match_operand:DI 1 "register_operand" "")))]
15371   "! TARGET_POPCNT"
15372 {
15373   rtx scratch = gen_reg_rtx (QImode);
15374   rtx cond;
15375
15376   emit_insn (gen_paritydi2_cmp (NULL_RTX, NULL_RTX,
15377                                 NULL_RTX, operands[1]));
15378
15379   cond = gen_rtx_fmt_ee (ORDERED, QImode,
15380                          gen_rtx_REG (CCmode, FLAGS_REG),
15381                          const0_rtx);
15382   emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
15383
15384   if (TARGET_64BIT)
15385     emit_insn (gen_zero_extendqidi2 (operands[0], scratch));
15386   else
15387     {
15388       rtx tmp = gen_reg_rtx (SImode);
15389
15390       emit_insn (gen_zero_extendqisi2 (tmp, scratch));
15391       emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
15392     }
15393   DONE;
15394 })
15395
15396 (define_insn_and_split "paritydi2_cmp"
15397   [(set (reg:CC FLAGS_REG)
15398         (parity:CC (match_operand:DI 3 "register_operand" "0")))
15399    (clobber (match_scratch:DI 0 "=r"))
15400    (clobber (match_scratch:SI 1 "=&r"))
15401    (clobber (match_scratch:HI 2 "=Q"))]
15402   "! TARGET_POPCNT"
15403   "#"
15404   "&& reload_completed"
15405   [(parallel
15406      [(set (match_dup 1)
15407            (xor:SI (match_dup 1) (match_dup 4)))
15408       (clobber (reg:CC FLAGS_REG))])
15409    (parallel
15410      [(set (reg:CC FLAGS_REG)
15411            (parity:CC (match_dup 1)))
15412       (clobber (match_dup 1))
15413       (clobber (match_dup 2))])]
15414 {
15415   operands[4] = gen_lowpart (SImode, operands[3]);
15416
15417   if (TARGET_64BIT)
15418     {
15419       emit_move_insn (operands[1], gen_lowpart (SImode, operands[3]));
15420       emit_insn (gen_lshrdi3 (operands[3], operands[3], GEN_INT (32)));
15421     }
15422   else
15423     operands[1] = gen_highpart (SImode, operands[3]);
15424 })
15425
15426 (define_expand "paritysi2"
15427   [(set (match_operand:SI 0 "register_operand" "")
15428         (parity:SI (match_operand:SI 1 "register_operand" "")))]
15429   "! TARGET_POPCNT"
15430 {
15431   rtx scratch = gen_reg_rtx (QImode);
15432   rtx cond;
15433
15434   emit_insn (gen_paritysi2_cmp (NULL_RTX, NULL_RTX, operands[1]));
15435
15436   cond = gen_rtx_fmt_ee (ORDERED, QImode,
15437                          gen_rtx_REG (CCmode, FLAGS_REG),
15438                          const0_rtx);
15439   emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
15440
15441   emit_insn (gen_zero_extendqisi2 (operands[0], scratch));
15442   DONE;
15443 })
15444
15445 (define_insn_and_split "paritysi2_cmp"
15446   [(set (reg:CC FLAGS_REG)
15447         (parity:CC (match_operand:SI 2 "register_operand" "0")))
15448    (clobber (match_scratch:SI 0 "=r"))
15449    (clobber (match_scratch:HI 1 "=&Q"))]
15450   "! TARGET_POPCNT"
15451   "#"
15452   "&& reload_completed"
15453   [(parallel
15454      [(set (match_dup 1)
15455            (xor:HI (match_dup 1) (match_dup 3)))
15456       (clobber (reg:CC FLAGS_REG))])
15457    (parallel
15458      [(set (reg:CC FLAGS_REG)
15459            (parity:CC (match_dup 1)))
15460       (clobber (match_dup 1))])]
15461 {
15462   operands[3] = gen_lowpart (HImode, operands[2]);
15463
15464   emit_move_insn (operands[1], gen_lowpart (HImode, operands[2]));
15465   emit_insn (gen_lshrsi3 (operands[2], operands[2], GEN_INT (16)));
15466 })
15467
15468 (define_insn "*parityhi2_cmp"
15469   [(set (reg:CC FLAGS_REG)
15470         (parity:CC (match_operand:HI 1 "register_operand" "0")))
15471    (clobber (match_scratch:HI 0 "=Q"))]
15472   "! TARGET_POPCNT"
15473   "xor{b}\t{%h0, %b0|%b0, %h0}"
15474   [(set_attr "length" "2")
15475    (set_attr "mode" "HI")])
15476
15477 (define_insn "*parityqi2_cmp"
15478   [(set (reg:CC FLAGS_REG)
15479         (parity:CC (match_operand:QI 0 "register_operand" "q")))]
15480   "! TARGET_POPCNT"
15481   "test{b}\t%0, %0"
15482   [(set_attr "length" "2")
15483    (set_attr "mode" "QI")])
15484 \f
15485 ;; Thread-local storage patterns for ELF.
15486 ;;
15487 ;; Note that these code sequences must appear exactly as shown
15488 ;; in order to allow linker relaxation.
15489
15490 (define_insn "*tls_global_dynamic_32_gnu"
15491   [(set (match_operand:SI 0 "register_operand" "=a")
15492         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
15493                     (match_operand:SI 2 "tls_symbolic_operand" "")
15494                     (match_operand:SI 3 "call_insn_operand" "")]
15495                     UNSPEC_TLS_GD))
15496    (clobber (match_scratch:SI 4 "=d"))
15497    (clobber (match_scratch:SI 5 "=c"))
15498    (clobber (reg:CC FLAGS_REG))]
15499   "!TARGET_64BIT && TARGET_GNU_TLS"
15500   "lea{l}\t{%a2@TLSGD(,%1,1), %0|%0, %a2@TLSGD[%1*1]}\;call\t%P3"
15501   [(set_attr "type" "multi")
15502    (set_attr "length" "12")])
15503
15504 (define_insn "*tls_global_dynamic_32_sun"
15505   [(set (match_operand:SI 0 "register_operand" "=a")
15506         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
15507                     (match_operand:SI 2 "tls_symbolic_operand" "")
15508                     (match_operand:SI 3 "call_insn_operand" "")]
15509                     UNSPEC_TLS_GD))
15510    (clobber (match_scratch:SI 4 "=d"))
15511    (clobber (match_scratch:SI 5 "=c"))
15512    (clobber (reg:CC FLAGS_REG))]
15513   "!TARGET_64BIT && TARGET_SUN_TLS"
15514   "lea{l}\t{%a2@DTLNDX(%1), %4|%4, %a2@DTLNDX[%1]}
15515         push{l}\t%4\;call\t%a2@TLSPLT\;pop{l}\t%4\;nop"
15516   [(set_attr "type" "multi")
15517    (set_attr "length" "14")])
15518
15519 (define_expand "tls_global_dynamic_32"
15520   [(parallel [(set (match_operand:SI 0 "register_operand" "")
15521                    (unspec:SI
15522                     [(match_dup 2)
15523                      (match_operand:SI 1 "tls_symbolic_operand" "")
15524                      (match_dup 3)]
15525                     UNSPEC_TLS_GD))
15526               (clobber (match_scratch:SI 4 ""))
15527               (clobber (match_scratch:SI 5 ""))
15528               (clobber (reg:CC FLAGS_REG))])]
15529   ""
15530 {
15531   if (flag_pic)
15532     operands[2] = pic_offset_table_rtx;
15533   else
15534     {
15535       operands[2] = gen_reg_rtx (Pmode);
15536       emit_insn (gen_set_got (operands[2]));
15537     }
15538   if (TARGET_GNU2_TLS)
15539     {
15540        emit_insn (gen_tls_dynamic_gnu2_32
15541                   (operands[0], operands[1], operands[2]));
15542        DONE;
15543     }
15544   operands[3] = ix86_tls_get_addr ();
15545 })
15546
15547 (define_insn "*tls_global_dynamic_64"
15548   [(set (match_operand:DI 0 "register_operand" "=a")
15549         (call:DI (mem:QI (match_operand:DI 2 "call_insn_operand" ""))
15550                  (match_operand:DI 3 "" "")))
15551    (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
15552               UNSPEC_TLS_GD)]
15553   "TARGET_64BIT"
15554   ".byte\t0x66\;lea{q}\t{%a1@TLSGD(%%rip), %%rdi|rdi, %a1@TLSGD[rip]}\;.word\t0x6666\;rex64\;call\t%P2"
15555   [(set_attr "type" "multi")
15556    (set_attr "length" "16")])
15557
15558 (define_expand "tls_global_dynamic_64"
15559   [(parallel [(set (match_operand:DI 0 "register_operand" "")
15560                    (call:DI (mem:QI (match_dup 2)) (const_int 0)))
15561               (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
15562                          UNSPEC_TLS_GD)])]
15563   ""
15564 {
15565   if (TARGET_GNU2_TLS)
15566     {
15567        emit_insn (gen_tls_dynamic_gnu2_64
15568                   (operands[0], operands[1]));
15569        DONE;
15570     }
15571   operands[2] = ix86_tls_get_addr ();
15572 })
15573
15574 (define_insn "*tls_local_dynamic_base_32_gnu"
15575   [(set (match_operand:SI 0 "register_operand" "=a")
15576         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
15577                     (match_operand:SI 2 "call_insn_operand" "")]
15578                    UNSPEC_TLS_LD_BASE))
15579    (clobber (match_scratch:SI 3 "=d"))
15580    (clobber (match_scratch:SI 4 "=c"))
15581    (clobber (reg:CC FLAGS_REG))]
15582   "!TARGET_64BIT && TARGET_GNU_TLS"
15583   "lea{l}\t{%&@TLSLDM(%1), %0|%0, %&@TLSLDM[%1]}\;call\t%P2"
15584   [(set_attr "type" "multi")
15585    (set_attr "length" "11")])
15586
15587 (define_insn "*tls_local_dynamic_base_32_sun"
15588   [(set (match_operand:SI 0 "register_operand" "=a")
15589         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
15590                     (match_operand:SI 2 "call_insn_operand" "")]
15591                    UNSPEC_TLS_LD_BASE))
15592    (clobber (match_scratch:SI 3 "=d"))
15593    (clobber (match_scratch:SI 4 "=c"))
15594    (clobber (reg:CC FLAGS_REG))]
15595   "!TARGET_64BIT && TARGET_SUN_TLS"
15596   "lea{l}\t{%&@TMDNX(%1), %3|%3, %&@TMDNX[%1]}
15597         push{l}\t%3\;call\t%&@TLSPLT\;pop{l}\t%3"
15598   [(set_attr "type" "multi")
15599    (set_attr "length" "13")])
15600
15601 (define_expand "tls_local_dynamic_base_32"
15602   [(parallel [(set (match_operand:SI 0 "register_operand" "")
15603                    (unspec:SI [(match_dup 1) (match_dup 2)]
15604                               UNSPEC_TLS_LD_BASE))
15605               (clobber (match_scratch:SI 3 ""))
15606               (clobber (match_scratch:SI 4 ""))
15607               (clobber (reg:CC FLAGS_REG))])]
15608   ""
15609 {
15610   if (flag_pic)
15611     operands[1] = pic_offset_table_rtx;
15612   else
15613     {
15614       operands[1] = gen_reg_rtx (Pmode);
15615       emit_insn (gen_set_got (operands[1]));
15616     }
15617   if (TARGET_GNU2_TLS)
15618     {
15619        emit_insn (gen_tls_dynamic_gnu2_32
15620                   (operands[0], ix86_tls_module_base (), operands[1]));
15621        DONE;
15622     }
15623   operands[2] = ix86_tls_get_addr ();
15624 })
15625
15626 (define_insn "*tls_local_dynamic_base_64"
15627   [(set (match_operand:DI 0 "register_operand" "=a")
15628         (call:DI (mem:QI (match_operand:DI 1 "call_insn_operand" ""))
15629                  (match_operand:DI 2 "" "")))
15630    (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
15631   "TARGET_64BIT"
15632   "lea{q}\t{%&@TLSLD(%%rip), %%rdi|rdi, %&@TLSLD[rip]}\;call\t%P1"
15633   [(set_attr "type" "multi")
15634    (set_attr "length" "12")])
15635
15636 (define_expand "tls_local_dynamic_base_64"
15637   [(parallel [(set (match_operand:DI 0 "register_operand" "")
15638                    (call:DI (mem:QI (match_dup 1)) (const_int 0)))
15639               (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])]
15640   ""
15641 {
15642   if (TARGET_GNU2_TLS)
15643     {
15644        emit_insn (gen_tls_dynamic_gnu2_64
15645                   (operands[0], ix86_tls_module_base ()));
15646        DONE;
15647     }
15648   operands[1] = ix86_tls_get_addr ();
15649 })
15650
15651 ;; Local dynamic of a single variable is a lose.  Show combine how
15652 ;; to convert that back to global dynamic.
15653
15654 (define_insn_and_split "*tls_local_dynamic_32_once"
15655   [(set (match_operand:SI 0 "register_operand" "=a")
15656         (plus:SI (unspec:SI [(match_operand:SI 1 "register_operand" "b")
15657                              (match_operand:SI 2 "call_insn_operand" "")]
15658                             UNSPEC_TLS_LD_BASE)
15659                  (const:SI (unspec:SI
15660                             [(match_operand:SI 3 "tls_symbolic_operand" "")]
15661                             UNSPEC_DTPOFF))))
15662    (clobber (match_scratch:SI 4 "=d"))
15663    (clobber (match_scratch:SI 5 "=c"))
15664    (clobber (reg:CC FLAGS_REG))]
15665   ""
15666   "#"
15667   ""
15668   [(parallel [(set (match_dup 0)
15669                    (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
15670                               UNSPEC_TLS_GD))
15671               (clobber (match_dup 4))
15672               (clobber (match_dup 5))
15673               (clobber (reg:CC FLAGS_REG))])]
15674   "")
15675
15676 ;; Load and add the thread base pointer from %gs:0.
15677
15678 (define_insn "*load_tp_si"
15679   [(set (match_operand:SI 0 "register_operand" "=r")
15680         (unspec:SI [(const_int 0)] UNSPEC_TP))]
15681   "!TARGET_64BIT"
15682   "mov{l}\t{%%gs:0, %0|%0, DWORD PTR gs:0}"
15683   [(set_attr "type" "imov")
15684    (set_attr "modrm" "0")
15685    (set_attr "length" "7")
15686    (set_attr "memory" "load")
15687    (set_attr "imm_disp" "false")])
15688
15689 (define_insn "*add_tp_si"
15690   [(set (match_operand:SI 0 "register_operand" "=r")
15691         (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
15692                  (match_operand:SI 1 "register_operand" "0")))
15693    (clobber (reg:CC FLAGS_REG))]
15694   "!TARGET_64BIT"
15695   "add{l}\t{%%gs:0, %0|%0, DWORD PTR gs:0}"
15696   [(set_attr "type" "alu")
15697    (set_attr "modrm" "0")
15698    (set_attr "length" "7")
15699    (set_attr "memory" "load")
15700    (set_attr "imm_disp" "false")])
15701
15702 (define_insn "*load_tp_di"
15703   [(set (match_operand:DI 0 "register_operand" "=r")
15704         (unspec:DI [(const_int 0)] UNSPEC_TP))]
15705   "TARGET_64BIT"
15706   "mov{q}\t{%%fs:0, %0|%0, QWORD PTR fs:0}"
15707   [(set_attr "type" "imov")
15708    (set_attr "modrm" "0")
15709    (set_attr "length" "7")
15710    (set_attr "memory" "load")
15711    (set_attr "imm_disp" "false")])
15712
15713 (define_insn "*add_tp_di"
15714   [(set (match_operand:DI 0 "register_operand" "=r")
15715         (plus:DI (unspec:DI [(const_int 0)] UNSPEC_TP)
15716                  (match_operand:DI 1 "register_operand" "0")))
15717    (clobber (reg:CC FLAGS_REG))]
15718   "TARGET_64BIT"
15719   "add{q}\t{%%fs:0, %0|%0, QWORD PTR fs:0}"
15720   [(set_attr "type" "alu")
15721    (set_attr "modrm" "0")
15722    (set_attr "length" "7")
15723    (set_attr "memory" "load")
15724    (set_attr "imm_disp" "false")])
15725
15726 ;; GNU2 TLS patterns can be split.
15727
15728 (define_expand "tls_dynamic_gnu2_32"
15729   [(set (match_dup 3)
15730         (plus:SI (match_operand:SI 2 "register_operand" "")
15731                  (const:SI
15732                   (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")]
15733                              UNSPEC_TLSDESC))))
15734    (parallel
15735     [(set (match_operand:SI 0 "register_operand" "")
15736           (unspec:SI [(match_dup 1) (match_dup 3)
15737                       (match_dup 2) (reg:SI SP_REG)]
15738                       UNSPEC_TLSDESC))
15739      (clobber (reg:CC FLAGS_REG))])]
15740   "!TARGET_64BIT && TARGET_GNU2_TLS"
15741 {
15742   operands[3] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
15743   ix86_tls_descriptor_calls_expanded_in_cfun = true;
15744 })
15745
15746 (define_insn "*tls_dynamic_lea_32"
15747   [(set (match_operand:SI 0 "register_operand" "=r")
15748         (plus:SI (match_operand:SI 1 "register_operand" "b")
15749                  (const:SI
15750                   (unspec:SI [(match_operand:SI 2 "tls_symbolic_operand" "")]
15751                               UNSPEC_TLSDESC))))]
15752   "!TARGET_64BIT && TARGET_GNU2_TLS"
15753   "lea{l}\t{%a2@TLSDESC(%1), %0|%0, %a2@TLSDESC[%1]}"
15754   [(set_attr "type" "lea")
15755    (set_attr "mode" "SI")
15756    (set_attr "length" "6")
15757    (set_attr "length_address" "4")])
15758
15759 (define_insn "*tls_dynamic_call_32"
15760   [(set (match_operand:SI 0 "register_operand" "=a")
15761         (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")
15762                     (match_operand:SI 2 "register_operand" "0")
15763                     ;; we have to make sure %ebx still points to the GOT
15764                     (match_operand:SI 3 "register_operand" "b")
15765                     (reg:SI SP_REG)]
15766                    UNSPEC_TLSDESC))
15767    (clobber (reg:CC FLAGS_REG))]
15768   "!TARGET_64BIT && TARGET_GNU2_TLS"
15769   "call\t{*%a1@TLSCALL(%2)|[DWORD PTR [%2+%a1@TLSCALL]]}"
15770   [(set_attr "type" "call")
15771    (set_attr "length" "2")
15772    (set_attr "length_address" "0")])
15773
15774 (define_insn_and_split "*tls_dynamic_gnu2_combine_32"
15775   [(set (match_operand:SI 0 "register_operand" "=&a")
15776         (plus:SI
15777          (unspec:SI [(match_operand:SI 3 "tls_modbase_operand" "")
15778                      (match_operand:SI 4 "" "")
15779                      (match_operand:SI 2 "register_operand" "b")
15780                      (reg:SI SP_REG)]
15781                     UNSPEC_TLSDESC)
15782          (const:SI (unspec:SI
15783                     [(match_operand:SI 1 "tls_symbolic_operand" "")]
15784                     UNSPEC_DTPOFF))))
15785    (clobber (reg:CC FLAGS_REG))]
15786   "!TARGET_64BIT && TARGET_GNU2_TLS"
15787   "#"
15788   ""
15789   [(set (match_dup 0) (match_dup 5))]
15790 {
15791   operands[5] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
15792   emit_insn (gen_tls_dynamic_gnu2_32 (operands[5], operands[1], operands[2]));
15793 })
15794
15795 (define_expand "tls_dynamic_gnu2_64"
15796   [(set (match_dup 2)
15797         (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
15798                    UNSPEC_TLSDESC))
15799    (parallel
15800     [(set (match_operand:DI 0 "register_operand" "")
15801           (unspec:DI [(match_dup 1) (match_dup 2) (reg:DI SP_REG)]
15802                      UNSPEC_TLSDESC))
15803      (clobber (reg:CC FLAGS_REG))])]
15804   "TARGET_64BIT && TARGET_GNU2_TLS"
15805 {
15806   operands[2] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
15807   ix86_tls_descriptor_calls_expanded_in_cfun = true;
15808 })
15809
15810 (define_insn "*tls_dynamic_lea_64"
15811   [(set (match_operand:DI 0 "register_operand" "=r")
15812         (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
15813                    UNSPEC_TLSDESC))]
15814   "TARGET_64BIT && TARGET_GNU2_TLS"
15815   "lea{q}\t{%a1@TLSDESC(%%rip), %0|%0, %a1@TLSDESC[rip]}"
15816   [(set_attr "type" "lea")
15817    (set_attr "mode" "DI")
15818    (set_attr "length" "7")
15819    (set_attr "length_address" "4")])
15820
15821 (define_insn "*tls_dynamic_call_64"
15822   [(set (match_operand:DI 0 "register_operand" "=a")
15823         (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")
15824                     (match_operand:DI 2 "register_operand" "0")
15825                     (reg:DI SP_REG)]
15826                    UNSPEC_TLSDESC))
15827    (clobber (reg:CC FLAGS_REG))]
15828   "TARGET_64BIT && TARGET_GNU2_TLS"
15829   "call\t{*%a1@TLSCALL(%2)|[QWORD PTR [%2+%a1@TLSCALL]]}"
15830   [(set_attr "type" "call")
15831    (set_attr "length" "2")
15832    (set_attr "length_address" "0")])
15833
15834 (define_insn_and_split "*tls_dynamic_gnu2_combine_64"
15835   [(set (match_operand:DI 0 "register_operand" "=&a")
15836         (plus:DI
15837          (unspec:DI [(match_operand:DI 2 "tls_modbase_operand" "")
15838                      (match_operand:DI 3 "" "")
15839                      (reg:DI SP_REG)]
15840                     UNSPEC_TLSDESC)
15841          (const:DI (unspec:DI
15842                     [(match_operand:DI 1 "tls_symbolic_operand" "")]
15843                     UNSPEC_DTPOFF))))
15844    (clobber (reg:CC FLAGS_REG))]
15845   "TARGET_64BIT && TARGET_GNU2_TLS"
15846   "#"
15847   ""
15848   [(set (match_dup 0) (match_dup 4))]
15849 {
15850   operands[4] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
15851   emit_insn (gen_tls_dynamic_gnu2_64 (operands[4], operands[1]));
15852 })
15853
15854 ;;
15855 \f
15856 ;; These patterns match the binary 387 instructions for addM3, subM3,
15857 ;; mulM3 and divM3.  There are three patterns for each of DFmode and
15858 ;; SFmode.  The first is the normal insn, the second the same insn but
15859 ;; with one operand a conversion, and the third the same insn but with
15860 ;; the other operand a conversion.  The conversion may be SFmode or
15861 ;; SImode if the target mode DFmode, but only SImode if the target mode
15862 ;; is SFmode.
15863
15864 ;; Gcc is slightly more smart about handling normal two address instructions
15865 ;; so use special patterns for add and mull.
15866
15867 (define_insn "*fop_<mode>_comm_mixed"
15868   [(set (match_operand:MODEF 0 "register_operand" "=f,x")
15869         (match_operator:MODEF 3 "binary_fp_operator"
15870           [(match_operand:MODEF 1 "nonimmediate_operand" "%0,0")
15871            (match_operand:MODEF 2 "nonimmediate_operand" "fm,xm")]))]
15872   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
15873    && COMMUTATIVE_ARITH_P (operands[3])
15874    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
15875   "* return output_387_binary_op (insn, operands);"
15876   [(set (attr "type")
15877         (if_then_else (eq_attr "alternative" "1")
15878            (if_then_else (match_operand:MODEF 3 "mult_operator" "")
15879               (const_string "ssemul")
15880               (const_string "sseadd"))
15881            (if_then_else (match_operand:MODEF 3 "mult_operator" "")
15882               (const_string "fmul")
15883               (const_string "fop"))))
15884    (set_attr "mode" "<MODE>")])
15885
15886 (define_insn "*fop_<mode>_comm_sse"
15887   [(set (match_operand:MODEF 0 "register_operand" "=x")
15888         (match_operator:MODEF 3 "binary_fp_operator"
15889           [(match_operand:MODEF 1 "nonimmediate_operand" "%0")
15890            (match_operand:MODEF 2 "nonimmediate_operand" "xm")]))]
15891   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15892    && COMMUTATIVE_ARITH_P (operands[3])
15893    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
15894   "* return output_387_binary_op (insn, operands);"
15895   [(set (attr "type")
15896         (if_then_else (match_operand:MODEF 3 "mult_operator" "")
15897            (const_string "ssemul")
15898            (const_string "sseadd")))
15899    (set_attr "mode" "<MODE>")])
15900
15901 (define_insn "*fop_<mode>_comm_i387"
15902   [(set (match_operand:MODEF 0 "register_operand" "=f")
15903         (match_operator:MODEF 3 "binary_fp_operator"
15904           [(match_operand:MODEF 1 "nonimmediate_operand" "%0")
15905            (match_operand:MODEF 2 "nonimmediate_operand" "fm")]))]
15906   "TARGET_80387
15907    && COMMUTATIVE_ARITH_P (operands[3])
15908    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
15909   "* return output_387_binary_op (insn, operands);"
15910   [(set (attr "type")
15911         (if_then_else (match_operand:MODEF 3 "mult_operator" "")
15912            (const_string "fmul")
15913            (const_string "fop")))
15914    (set_attr "mode" "<MODE>")])
15915
15916 (define_insn "*fop_<mode>_1_mixed"
15917   [(set (match_operand:MODEF 0 "register_operand" "=f,f,x")
15918         (match_operator:MODEF 3 "binary_fp_operator"
15919           [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm,0")
15920            (match_operand:MODEF 2 "nonimmediate_operand" "fm,0,xm")]))]
15921   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_MIX_SSE_I387
15922    && !COMMUTATIVE_ARITH_P (operands[3])
15923    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
15924   "* return output_387_binary_op (insn, operands);"
15925   [(set (attr "type")
15926         (cond [(and (eq_attr "alternative" "2")
15927                     (match_operand:MODEF 3 "mult_operator" ""))
15928                  (const_string "ssemul")
15929                (and (eq_attr "alternative" "2")
15930                     (match_operand:MODEF 3 "div_operator" ""))
15931                  (const_string "ssediv")
15932                (eq_attr "alternative" "2")
15933                  (const_string "sseadd")
15934                (match_operand:MODEF 3 "mult_operator" "")
15935                  (const_string "fmul")
15936                (match_operand:MODEF 3 "div_operator" "")
15937                  (const_string "fdiv")
15938               ]
15939               (const_string "fop")))
15940    (set_attr "mode" "<MODE>")])
15941
15942 (define_insn "*rcpsf2_sse"
15943   [(set (match_operand:SF 0 "register_operand" "=x")
15944         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
15945                    UNSPEC_RCP))]
15946   "TARGET_SSE_MATH"
15947   "rcpss\t{%1, %0|%0, %1}"
15948   [(set_attr "type" "sse")
15949    (set_attr "mode" "SF")])
15950
15951 (define_insn "*fop_<mode>_1_sse"
15952   [(set (match_operand:MODEF 0 "register_operand" "=x")
15953         (match_operator:MODEF 3 "binary_fp_operator"
15954           [(match_operand:MODEF 1 "register_operand" "0")
15955            (match_operand:MODEF 2 "nonimmediate_operand" "xm")]))]
15956   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
15957    && !COMMUTATIVE_ARITH_P (operands[3])"
15958   "* return output_387_binary_op (insn, operands);"
15959   [(set (attr "type")
15960         (cond [(match_operand:MODEF 3 "mult_operator" "")
15961                  (const_string "ssemul")
15962                (match_operand:MODEF 3 "div_operator" "")
15963                  (const_string "ssediv")
15964               ]
15965               (const_string "sseadd")))
15966    (set_attr "mode" "<MODE>")])
15967
15968 ;; This pattern is not fully shadowed by the pattern above.
15969 (define_insn "*fop_<mode>_1_i387"
15970   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
15971         (match_operator:MODEF 3 "binary_fp_operator"
15972           [(match_operand:MODEF 1 "nonimmediate_operand" "0,fm")
15973            (match_operand:MODEF 2 "nonimmediate_operand" "fm,0")]))]
15974   "TARGET_80387 && !TARGET_SSE_MATH
15975    && !COMMUTATIVE_ARITH_P (operands[3])
15976    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
15977   "* return output_387_binary_op (insn, operands);"
15978   [(set (attr "type")
15979         (cond [(match_operand:MODEF 3 "mult_operator" "")
15980                  (const_string "fmul")
15981                (match_operand:MODEF 3 "div_operator" "")
15982                  (const_string "fdiv")
15983               ]
15984               (const_string "fop")))
15985    (set_attr "mode" "<MODE>")])
15986
15987 ;; ??? Add SSE splitters for these!
15988 (define_insn "*fop_<MODEF:mode>_2_i387"
15989   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
15990         (match_operator:MODEF 3 "binary_fp_operator"
15991           [(float:MODEF
15992              (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
15993            (match_operand:MODEF 2 "register_operand" "0,0")]))]
15994   "TARGET_80387 && !TARGET_SSE_MATH
15995    && (TARGET_USE_<X87MODEI12:MODE>MODE_FIOP || optimize_size)"
15996   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
15997   [(set (attr "type")
15998         (cond [(match_operand:MODEF 3 "mult_operator" "")
15999                  (const_string "fmul")
16000                (match_operand:MODEF 3 "div_operator" "")
16001                  (const_string "fdiv")
16002               ]
16003               (const_string "fop")))
16004    (set_attr "fp_int_src" "true")
16005    (set_attr "mode" "<X87MODEI12:MODE>")])
16006
16007 (define_insn "*fop_<MODEF:mode>_3_i387"
16008   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
16009         (match_operator:MODEF 3 "binary_fp_operator"
16010           [(match_operand:MODEF 1 "register_operand" "0,0")
16011            (float:MODEF
16012              (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
16013   "TARGET_80387 && !TARGET_SSE_MATH
16014    && (TARGET_USE_<X87MODEI12:MODE>MODE_FIOP || optimize_size)"
16015   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16016   [(set (attr "type")
16017         (cond [(match_operand:MODEF 3 "mult_operator" "")
16018                  (const_string "fmul")
16019                (match_operand:MODEF 3 "div_operator" "")
16020                  (const_string "fdiv")
16021               ]
16022               (const_string "fop")))
16023    (set_attr "fp_int_src" "true")
16024    (set_attr "mode" "<MODE>")])
16025
16026 (define_insn "*fop_df_4_i387"
16027   [(set (match_operand:DF 0 "register_operand" "=f,f")
16028         (match_operator:DF 3 "binary_fp_operator"
16029            [(float_extend:DF
16030              (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
16031             (match_operand:DF 2 "register_operand" "0,f")]))]
16032   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
16033    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16034   "* return output_387_binary_op (insn, operands);"
16035   [(set (attr "type")
16036         (cond [(match_operand:DF 3 "mult_operator" "")
16037                  (const_string "fmul")
16038                (match_operand:DF 3 "div_operator" "")
16039                  (const_string "fdiv")
16040               ]
16041               (const_string "fop")))
16042    (set_attr "mode" "SF")])
16043
16044 (define_insn "*fop_df_5_i387"
16045   [(set (match_operand:DF 0 "register_operand" "=f,f")
16046         (match_operator:DF 3 "binary_fp_operator"
16047           [(match_operand:DF 1 "register_operand" "0,f")
16048            (float_extend:DF
16049             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
16050   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
16051   "* return output_387_binary_op (insn, operands);"
16052   [(set (attr "type")
16053         (cond [(match_operand:DF 3 "mult_operator" "")
16054                  (const_string "fmul")
16055                (match_operand:DF 3 "div_operator" "")
16056                  (const_string "fdiv")
16057               ]
16058               (const_string "fop")))
16059    (set_attr "mode" "SF")])
16060
16061 (define_insn "*fop_df_6_i387"
16062   [(set (match_operand:DF 0 "register_operand" "=f,f")
16063         (match_operator:DF 3 "binary_fp_operator"
16064           [(float_extend:DF
16065             (match_operand:SF 1 "register_operand" "0,f"))
16066            (float_extend:DF
16067             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
16068   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
16069   "* return output_387_binary_op (insn, operands);"
16070   [(set (attr "type")
16071         (cond [(match_operand:DF 3 "mult_operator" "")
16072                  (const_string "fmul")
16073                (match_operand:DF 3 "div_operator" "")
16074                  (const_string "fdiv")
16075               ]
16076               (const_string "fop")))
16077    (set_attr "mode" "SF")])
16078
16079 (define_insn "*fop_xf_comm_i387"
16080   [(set (match_operand:XF 0 "register_operand" "=f")
16081         (match_operator:XF 3 "binary_fp_operator"
16082                         [(match_operand:XF 1 "register_operand" "%0")
16083                          (match_operand:XF 2 "register_operand" "f")]))]
16084   "TARGET_80387
16085    && COMMUTATIVE_ARITH_P (operands[3])"
16086   "* return output_387_binary_op (insn, operands);"
16087   [(set (attr "type")
16088         (if_then_else (match_operand:XF 3 "mult_operator" "")
16089            (const_string "fmul")
16090            (const_string "fop")))
16091    (set_attr "mode" "XF")])
16092
16093 (define_insn "*fop_xf_1_i387"
16094   [(set (match_operand:XF 0 "register_operand" "=f,f")
16095         (match_operator:XF 3 "binary_fp_operator"
16096                         [(match_operand:XF 1 "register_operand" "0,f")
16097                          (match_operand:XF 2 "register_operand" "f,0")]))]
16098   "TARGET_80387
16099    && !COMMUTATIVE_ARITH_P (operands[3])"
16100   "* return output_387_binary_op (insn, operands);"
16101   [(set (attr "type")
16102         (cond [(match_operand:XF 3 "mult_operator" "")
16103                  (const_string "fmul")
16104                (match_operand:XF 3 "div_operator" "")
16105                  (const_string "fdiv")
16106               ]
16107               (const_string "fop")))
16108    (set_attr "mode" "XF")])
16109
16110 (define_insn "*fop_xf_2_i387"
16111   [(set (match_operand:XF 0 "register_operand" "=f,f")
16112         (match_operator:XF 3 "binary_fp_operator"
16113           [(float:XF
16114              (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
16115            (match_operand:XF 2 "register_operand" "0,0")]))]
16116   "TARGET_80387 && (TARGET_USE_<MODE>MODE_FIOP || optimize_size)"
16117   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16118   [(set (attr "type")
16119         (cond [(match_operand:XF 3 "mult_operator" "")
16120                  (const_string "fmul")
16121                (match_operand:XF 3 "div_operator" "")
16122                  (const_string "fdiv")
16123               ]
16124               (const_string "fop")))
16125    (set_attr "fp_int_src" "true")
16126    (set_attr "mode" "<MODE>")])
16127
16128 (define_insn "*fop_xf_3_i387"
16129   [(set (match_operand:XF 0 "register_operand" "=f,f")
16130         (match_operator:XF 3 "binary_fp_operator"
16131           [(match_operand:XF 1 "register_operand" "0,0")
16132            (float:XF
16133              (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
16134   "TARGET_80387 && (TARGET_USE_<MODE>MODE_FIOP || optimize_size)"
16135   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16136   [(set (attr "type")
16137         (cond [(match_operand:XF 3 "mult_operator" "")
16138                  (const_string "fmul")
16139                (match_operand:XF 3 "div_operator" "")
16140                  (const_string "fdiv")
16141               ]
16142               (const_string "fop")))
16143    (set_attr "fp_int_src" "true")
16144    (set_attr "mode" "<MODE>")])
16145
16146 (define_insn "*fop_xf_4_i387"
16147   [(set (match_operand:XF 0 "register_operand" "=f,f")
16148         (match_operator:XF 3 "binary_fp_operator"
16149            [(float_extend:XF
16150               (match_operand:MODEF 1 "nonimmediate_operand" "fm,0"))
16151             (match_operand:XF 2 "register_operand" "0,f")]))]
16152   "TARGET_80387"
16153   "* return output_387_binary_op (insn, operands);"
16154   [(set (attr "type")
16155         (cond [(match_operand:XF 3 "mult_operator" "")
16156                  (const_string "fmul")
16157                (match_operand:XF 3 "div_operator" "")
16158                  (const_string "fdiv")
16159               ]
16160               (const_string "fop")))
16161    (set_attr "mode" "<MODE>")])
16162
16163 (define_insn "*fop_xf_5_i387"
16164   [(set (match_operand:XF 0 "register_operand" "=f,f")
16165         (match_operator:XF 3 "binary_fp_operator"
16166           [(match_operand:XF 1 "register_operand" "0,f")
16167            (float_extend:XF
16168              (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
16169   "TARGET_80387"
16170   "* return output_387_binary_op (insn, operands);"
16171   [(set (attr "type")
16172         (cond [(match_operand:XF 3 "mult_operator" "")
16173                  (const_string "fmul")
16174                (match_operand:XF 3 "div_operator" "")
16175                  (const_string "fdiv")
16176               ]
16177               (const_string "fop")))
16178    (set_attr "mode" "<MODE>")])
16179
16180 (define_insn "*fop_xf_6_i387"
16181   [(set (match_operand:XF 0 "register_operand" "=f,f")
16182         (match_operator:XF 3 "binary_fp_operator"
16183           [(float_extend:XF
16184              (match_operand:MODEF 1 "register_operand" "0,f"))
16185            (float_extend:XF
16186              (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
16187   "TARGET_80387"
16188   "* return output_387_binary_op (insn, operands);"
16189   [(set (attr "type")
16190         (cond [(match_operand:XF 3 "mult_operator" "")
16191                  (const_string "fmul")
16192                (match_operand:XF 3 "div_operator" "")
16193                  (const_string "fdiv")
16194               ]
16195               (const_string "fop")))
16196    (set_attr "mode" "<MODE>")])
16197
16198 (define_split
16199   [(set (match_operand 0 "register_operand" "")
16200         (match_operator 3 "binary_fp_operator"
16201            [(float (match_operand:X87MODEI12 1 "register_operand" ""))
16202             (match_operand 2 "register_operand" "")]))]
16203   "reload_completed
16204    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))"
16205   [(const_int 0)]
16206 {
16207   operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
16208   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
16209   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
16210                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
16211                                           GET_MODE (operands[3]),
16212                                           operands[4],
16213                                           operands[2])));
16214   ix86_free_from_memory (GET_MODE (operands[1]));
16215   DONE;
16216 })
16217
16218 (define_split
16219   [(set (match_operand 0 "register_operand" "")
16220         (match_operator 3 "binary_fp_operator"
16221            [(match_operand 1 "register_operand" "")
16222             (float (match_operand:X87MODEI12 2 "register_operand" ""))]))]
16223   "reload_completed
16224    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))"
16225   [(const_int 0)]
16226 {
16227   operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
16228   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
16229   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
16230                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
16231                                           GET_MODE (operands[3]),
16232                                           operands[1],
16233                                           operands[4])));
16234   ix86_free_from_memory (GET_MODE (operands[2]));
16235   DONE;
16236 })
16237 \f
16238 ;; FPU special functions.
16239
16240 ;; This pattern implements a no-op XFmode truncation for
16241 ;; all fancy i386 XFmode math functions.
16242
16243 (define_insn "truncxf<mode>2_i387_noop_unspec"
16244   [(set (match_operand:MODEF 0 "register_operand" "=f")
16245         (unspec:MODEF [(match_operand:XF 1 "register_operand" "f")]
16246         UNSPEC_TRUNC_NOOP))]
16247   "TARGET_USE_FANCY_MATH_387"
16248   "* return output_387_reg_move (insn, operands);"
16249   [(set_attr "type" "fmov")
16250    (set_attr "mode" "<MODE>")])
16251
16252 (define_insn "sqrtxf2"
16253   [(set (match_operand:XF 0 "register_operand" "=f")
16254         (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
16255   "TARGET_USE_FANCY_MATH_387"
16256   "fsqrt"
16257   [(set_attr "type" "fpspc")
16258    (set_attr "mode" "XF")
16259    (set_attr "athlon_decode" "direct")
16260    (set_attr "amdfam10_decode" "direct")])
16261
16262 (define_insn "sqrt_extend<mode>xf2_i387"
16263   [(set (match_operand:XF 0 "register_operand" "=f")
16264         (sqrt:XF
16265           (float_extend:XF
16266             (match_operand:MODEF 1 "register_operand" "0"))))]
16267   "TARGET_USE_FANCY_MATH_387"
16268   "fsqrt"
16269   [(set_attr "type" "fpspc")
16270    (set_attr "mode" "XF")
16271    (set_attr "athlon_decode" "direct")
16272    (set_attr "amdfam10_decode" "direct")])
16273
16274 (define_insn "*rsqrtsf2_sse"
16275   [(set (match_operand:SF 0 "register_operand" "=x")
16276         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
16277                    UNSPEC_RSQRT))]
16278   "TARGET_SSE_MATH"
16279   "rsqrtss\t{%1, %0|%0, %1}"
16280   [(set_attr "type" "sse")
16281    (set_attr "mode" "SF")])
16282
16283 (define_expand "rsqrtsf2"
16284   [(set (match_operand:SF 0 "register_operand" "")
16285         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "")]
16286                    UNSPEC_RSQRT))]
16287   "TARGET_SSE_MATH"
16288 {
16289   ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 1);
16290   DONE;
16291 })
16292
16293 (define_insn "*sqrt<mode>2_sse"
16294   [(set (match_operand:MODEF 0 "register_operand" "=x")
16295         (sqrt:MODEF
16296           (match_operand:MODEF 1 "nonimmediate_operand" "xm")))]
16297   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16298   "sqrts<ssemodefsuffix>\t{%1, %0|%0, %1}"
16299   [(set_attr "type" "sse")
16300    (set_attr "mode" "<MODE>")
16301    (set_attr "athlon_decode" "*")
16302    (set_attr "amdfam10_decode" "*")])
16303
16304 (define_expand "sqrt<mode>2"
16305   [(set (match_operand:MODEF 0 "register_operand" "")
16306         (sqrt:MODEF
16307           (match_operand:MODEF 1 "nonimmediate_operand" "")))]
16308   "TARGET_USE_FANCY_MATH_387
16309    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
16310 {
16311   if (<MODE>mode == SFmode
16312       && TARGET_SSE_MATH && TARGET_RECIP && !optimize_size
16313       && flag_finite_math_only && !flag_trapping_math
16314       && flag_unsafe_math_optimizations)
16315     {
16316       ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 0);
16317       DONE;
16318     }
16319
16320   if (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
16321     {
16322       rtx op0 = gen_reg_rtx (XFmode);
16323       rtx op1 = force_reg (<MODE>mode, operands[1]);
16324
16325       emit_insn (gen_sqrt_extend<mode>xf2_i387 (op0, op1));
16326       emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op0));
16327       DONE;
16328    }
16329 })
16330
16331 (define_insn "fpremxf4_i387"
16332   [(set (match_operand:XF 0 "register_operand" "=f")
16333         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
16334                     (match_operand:XF 3 "register_operand" "1")]
16335                    UNSPEC_FPREM_F))
16336    (set (match_operand:XF 1 "register_operand" "=u")
16337         (unspec:XF [(match_dup 2) (match_dup 3)]
16338                    UNSPEC_FPREM_U))
16339    (set (reg:CCFP FPSR_REG)
16340         (unspec:CCFP [(match_dup 2) (match_dup 3)]
16341                      UNSPEC_C2_FLAG))]
16342   "TARGET_USE_FANCY_MATH_387"
16343   "fprem"
16344   [(set_attr "type" "fpspc")
16345    (set_attr "mode" "XF")])
16346
16347 (define_expand "fmodxf3"
16348   [(use (match_operand:XF 0 "register_operand" ""))
16349    (use (match_operand:XF 1 "general_operand" ""))
16350    (use (match_operand:XF 2 "general_operand" ""))]
16351   "TARGET_USE_FANCY_MATH_387"
16352 {
16353   rtx label = gen_label_rtx ();
16354
16355   rtx op1 = gen_reg_rtx (XFmode);
16356   rtx op2 = gen_reg_rtx (XFmode);
16357
16358   emit_move_insn (op1, operands[1]);
16359   emit_move_insn (op2, operands[2]);
16360
16361   emit_label (label);
16362   emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
16363   ix86_emit_fp_unordered_jump (label);
16364   LABEL_NUSES (label) = 1;
16365
16366   emit_move_insn (operands[0], op1);
16367   DONE;
16368 })
16369
16370 (define_expand "fmod<mode>3"
16371   [(use (match_operand:MODEF 0 "register_operand" ""))
16372    (use (match_operand:MODEF 1 "general_operand" ""))
16373    (use (match_operand:MODEF 2 "general_operand" ""))]
16374   "TARGET_USE_FANCY_MATH_387"
16375 {
16376   rtx label = gen_label_rtx ();
16377
16378   rtx op1 = gen_reg_rtx (XFmode);
16379   rtx op2 = gen_reg_rtx (XFmode);
16380
16381   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
16382   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
16383
16384   emit_label (label);
16385   emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
16386   ix86_emit_fp_unordered_jump (label);
16387   LABEL_NUSES (label) = 1;
16388
16389   /* Truncate the result properly for strict SSE math.  */
16390   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
16391       && !TARGET_MIX_SSE_I387)
16392     emit_insn (gen_truncxf<mode>2 (operands[0], op1));
16393   else
16394     emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op1));
16395
16396   DONE;
16397 })
16398
16399 (define_insn "fprem1xf4_i387"
16400   [(set (match_operand:XF 0 "register_operand" "=f")
16401         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
16402                     (match_operand:XF 3 "register_operand" "1")]
16403                    UNSPEC_FPREM1_F))
16404    (set (match_operand:XF 1 "register_operand" "=u")
16405         (unspec:XF [(match_dup 2) (match_dup 3)]
16406                    UNSPEC_FPREM1_U))
16407    (set (reg:CCFP FPSR_REG)
16408         (unspec:CCFP [(match_dup 2) (match_dup 3)]
16409                      UNSPEC_C2_FLAG))]
16410   "TARGET_USE_FANCY_MATH_387"
16411   "fprem1"
16412   [(set_attr "type" "fpspc")
16413    (set_attr "mode" "XF")])
16414
16415 (define_expand "remainderxf3"
16416   [(use (match_operand:XF 0 "register_operand" ""))
16417    (use (match_operand:XF 1 "general_operand" ""))
16418    (use (match_operand:XF 2 "general_operand" ""))]
16419   "TARGET_USE_FANCY_MATH_387"
16420 {
16421   rtx label = gen_label_rtx ();
16422
16423   rtx op1 = gen_reg_rtx (XFmode);
16424   rtx op2 = gen_reg_rtx (XFmode);
16425
16426   emit_move_insn (op1, operands[1]);
16427   emit_move_insn (op2, operands[2]);
16428
16429   emit_label (label);
16430   emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
16431   ix86_emit_fp_unordered_jump (label);
16432   LABEL_NUSES (label) = 1;
16433
16434   emit_move_insn (operands[0], op1);
16435   DONE;
16436 })
16437
16438 (define_expand "remainder<mode>3"
16439   [(use (match_operand:MODEF 0 "register_operand" ""))
16440    (use (match_operand:MODEF 1 "general_operand" ""))
16441    (use (match_operand:MODEF 2 "general_operand" ""))]
16442   "TARGET_USE_FANCY_MATH_387"
16443 {
16444   rtx label = gen_label_rtx ();
16445
16446   rtx op1 = gen_reg_rtx (XFmode);
16447   rtx op2 = gen_reg_rtx (XFmode);
16448
16449   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
16450   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
16451
16452   emit_label (label);
16453
16454   emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
16455   ix86_emit_fp_unordered_jump (label);
16456   LABEL_NUSES (label) = 1;
16457
16458   /* Truncate the result properly for strict SSE math.  */
16459   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
16460       && !TARGET_MIX_SSE_I387)
16461     emit_insn (gen_truncxf<mode>2 (operands[0], op1));
16462   else
16463     emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op1));
16464
16465   DONE;
16466 })
16467
16468 (define_insn "*sinxf2_i387"
16469   [(set (match_operand:XF 0 "register_operand" "=f")
16470         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
16471   "TARGET_USE_FANCY_MATH_387
16472    && flag_unsafe_math_optimizations"
16473   "fsin"
16474   [(set_attr "type" "fpspc")
16475    (set_attr "mode" "XF")])
16476
16477 (define_insn "*sin_extend<mode>xf2_i387"
16478   [(set (match_operand:XF 0 "register_operand" "=f")
16479         (unspec:XF [(float_extend:XF
16480                       (match_operand:MODEF 1 "register_operand" "0"))]
16481                    UNSPEC_SIN))]
16482   "TARGET_USE_FANCY_MATH_387
16483    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16484        || TARGET_MIX_SSE_I387)
16485    && flag_unsafe_math_optimizations"
16486   "fsin"
16487   [(set_attr "type" "fpspc")
16488    (set_attr "mode" "XF")])
16489
16490 (define_insn "*cosxf2_i387"
16491   [(set (match_operand:XF 0 "register_operand" "=f")
16492         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
16493   "TARGET_USE_FANCY_MATH_387
16494    && flag_unsafe_math_optimizations"
16495   "fcos"
16496   [(set_attr "type" "fpspc")
16497    (set_attr "mode" "XF")])
16498
16499 (define_insn "*cos_extend<mode>xf2_i387"
16500   [(set (match_operand:XF 0 "register_operand" "=f")
16501         (unspec:XF [(float_extend:XF
16502                       (match_operand:MODEF 1 "register_operand" "0"))]
16503                    UNSPEC_COS))]
16504   "TARGET_USE_FANCY_MATH_387
16505    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16506        || TARGET_MIX_SSE_I387)
16507    && flag_unsafe_math_optimizations"
16508   "fcos"
16509   [(set_attr "type" "fpspc")
16510    (set_attr "mode" "XF")])
16511
16512 ;; When sincos pattern is defined, sin and cos builtin functions will be
16513 ;; expanded to sincos pattern with one of its outputs left unused.
16514 ;; CSE pass will figure out if two sincos patterns can be combined,
16515 ;; otherwise sincos pattern will be split back to sin or cos pattern,
16516 ;; depending on the unused output.
16517
16518 (define_insn "sincosxf3"
16519   [(set (match_operand:XF 0 "register_operand" "=f")
16520         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
16521                    UNSPEC_SINCOS_COS))
16522    (set (match_operand:XF 1 "register_operand" "=u")
16523         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
16524   "TARGET_USE_FANCY_MATH_387
16525    && flag_unsafe_math_optimizations"
16526   "fsincos"
16527   [(set_attr "type" "fpspc")
16528    (set_attr "mode" "XF")])
16529
16530 (define_split
16531   [(set (match_operand:XF 0 "register_operand" "")
16532         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
16533                    UNSPEC_SINCOS_COS))
16534    (set (match_operand:XF 1 "register_operand" "")
16535         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
16536   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
16537    && !(reload_completed || reload_in_progress)"
16538   [(set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_SIN))]
16539   "")
16540
16541 (define_split
16542   [(set (match_operand:XF 0 "register_operand" "")
16543         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
16544                    UNSPEC_SINCOS_COS))
16545    (set (match_operand:XF 1 "register_operand" "")
16546         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
16547   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
16548    && !(reload_completed || reload_in_progress)"
16549   [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))]
16550   "")
16551
16552 (define_insn "sincos_extend<mode>xf3_i387"
16553   [(set (match_operand:XF 0 "register_operand" "=f")
16554         (unspec:XF [(float_extend:XF
16555                       (match_operand:MODEF 2 "register_operand" "0"))]
16556                    UNSPEC_SINCOS_COS))
16557    (set (match_operand:XF 1 "register_operand" "=u")
16558         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
16559   "TARGET_USE_FANCY_MATH_387
16560    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16561        || TARGET_MIX_SSE_I387)
16562    && flag_unsafe_math_optimizations"
16563   "fsincos"
16564   [(set_attr "type" "fpspc")
16565    (set_attr "mode" "XF")])
16566
16567 (define_split
16568   [(set (match_operand:XF 0 "register_operand" "")
16569         (unspec:XF [(float_extend:XF
16570                       (match_operand:MODEF 2 "register_operand" ""))]
16571                    UNSPEC_SINCOS_COS))
16572    (set (match_operand:XF 1 "register_operand" "")
16573         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
16574   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
16575    && !(reload_completed || reload_in_progress)"
16576   [(set (match_dup 1) (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SIN))]
16577   "")
16578
16579 (define_split
16580   [(set (match_operand:XF 0 "register_operand" "")
16581         (unspec:XF [(float_extend:XF
16582                       (match_operand:MODEF 2 "register_operand" ""))]
16583                    UNSPEC_SINCOS_COS))
16584    (set (match_operand:XF 1 "register_operand" "")
16585         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
16586   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
16587    && !(reload_completed || reload_in_progress)"
16588   [(set (match_dup 0) (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_COS))]
16589   "")
16590
16591 (define_expand "sincos<mode>3"
16592   [(use (match_operand:MODEF 0 "register_operand" ""))
16593    (use (match_operand:MODEF 1 "register_operand" ""))
16594    (use (match_operand:MODEF 2 "register_operand" ""))]
16595   "TARGET_USE_FANCY_MATH_387
16596    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16597        || TARGET_MIX_SSE_I387)
16598    && flag_unsafe_math_optimizations"
16599 {
16600   rtx op0 = gen_reg_rtx (XFmode);
16601   rtx op1 = gen_reg_rtx (XFmode);
16602
16603   emit_insn (gen_sincos_extend<mode>xf3_i387 (op0, op1, operands[2]));
16604   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16605   emit_insn (gen_truncxf<mode>2_i387_noop (operands[1], op1));
16606   DONE;
16607 })
16608
16609 (define_insn "fptanxf4_i387"
16610   [(set (match_operand:XF 0 "register_operand" "=f")
16611         (match_operand:XF 3 "const_double_operand" "F"))
16612    (set (match_operand:XF 1 "register_operand" "=u")
16613         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
16614                    UNSPEC_TAN))]
16615   "TARGET_USE_FANCY_MATH_387
16616    && flag_unsafe_math_optimizations
16617    && standard_80387_constant_p (operands[3]) == 2"
16618   "fptan"
16619   [(set_attr "type" "fpspc")
16620    (set_attr "mode" "XF")])
16621
16622 (define_insn "fptan_extend<mode>xf4_i387"
16623   [(set (match_operand:MODEF 0 "register_operand" "=f")
16624         (match_operand:MODEF 3 "const_double_operand" "F"))
16625    (set (match_operand:XF 1 "register_operand" "=u")
16626         (unspec:XF [(float_extend:XF
16627                       (match_operand:MODEF 2 "register_operand" "0"))]
16628                    UNSPEC_TAN))]
16629   "TARGET_USE_FANCY_MATH_387
16630    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16631        || TARGET_MIX_SSE_I387)
16632    && flag_unsafe_math_optimizations
16633    && standard_80387_constant_p (operands[3]) == 2"
16634   "fptan"
16635   [(set_attr "type" "fpspc")
16636    (set_attr "mode" "XF")])
16637
16638 (define_expand "tanxf2"
16639   [(use (match_operand:XF 0 "register_operand" ""))
16640    (use (match_operand:XF 1 "register_operand" ""))]
16641   "TARGET_USE_FANCY_MATH_387
16642    && flag_unsafe_math_optimizations"
16643 {
16644   rtx one = gen_reg_rtx (XFmode);
16645   rtx op2 = CONST1_RTX (XFmode); /* fld1 */
16646
16647   emit_insn (gen_fptanxf4_i387 (one, operands[0], operands[1], op2));
16648   DONE;
16649 })
16650
16651 (define_expand "tan<mode>2"
16652   [(use (match_operand:MODEF 0 "register_operand" ""))
16653    (use (match_operand:MODEF 1 "register_operand" ""))]
16654   "TARGET_USE_FANCY_MATH_387
16655    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16656        || TARGET_MIX_SSE_I387)
16657    && flag_unsafe_math_optimizations"
16658 {
16659   rtx op0 = gen_reg_rtx (XFmode);
16660
16661   rtx one = gen_reg_rtx (<MODE>mode);
16662   rtx op2 = CONST1_RTX (<MODE>mode); /* fld1 */
16663
16664   emit_insn (gen_fptan_extend<mode>xf4_i387 (one, op0,
16665                                              operands[1], op2));
16666   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16667   DONE;
16668 })
16669
16670 (define_insn "*fpatanxf3_i387"
16671   [(set (match_operand:XF 0 "register_operand" "=f")
16672         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
16673                     (match_operand:XF 2 "register_operand" "u")]
16674                    UNSPEC_FPATAN))
16675    (clobber (match_scratch:XF 3 "=2"))]
16676   "TARGET_USE_FANCY_MATH_387
16677    && flag_unsafe_math_optimizations"
16678   "fpatan"
16679   [(set_attr "type" "fpspc")
16680    (set_attr "mode" "XF")])
16681
16682 (define_insn "fpatan_extend<mode>xf3_i387"
16683   [(set (match_operand:XF 0 "register_operand" "=f")
16684         (unspec:XF [(float_extend:XF
16685                       (match_operand:MODEF 1 "register_operand" "0"))
16686                     (float_extend:XF
16687                       (match_operand:MODEF 2 "register_operand" "u"))]
16688                    UNSPEC_FPATAN))
16689    (clobber (match_scratch:XF 3 "=2"))]
16690   "TARGET_USE_FANCY_MATH_387
16691    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16692        || TARGET_MIX_SSE_I387)
16693    && flag_unsafe_math_optimizations"
16694   "fpatan"
16695   [(set_attr "type" "fpspc")
16696    (set_attr "mode" "XF")])
16697
16698 (define_expand "atan2xf3"
16699   [(parallel [(set (match_operand:XF 0 "register_operand" "")
16700                    (unspec:XF [(match_operand:XF 2 "register_operand" "")
16701                                (match_operand:XF 1 "register_operand" "")]
16702                               UNSPEC_FPATAN))
16703               (clobber (match_scratch:XF 3 ""))])]
16704   "TARGET_USE_FANCY_MATH_387
16705    && flag_unsafe_math_optimizations"
16706   "")
16707
16708 (define_expand "atan2<mode>3"
16709   [(use (match_operand:MODEF 0 "register_operand" ""))
16710    (use (match_operand:MODEF 1 "register_operand" ""))
16711    (use (match_operand:MODEF 2 "register_operand" ""))]
16712   "TARGET_USE_FANCY_MATH_387
16713    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16714        || TARGET_MIX_SSE_I387)
16715    && flag_unsafe_math_optimizations"
16716 {
16717   rtx op0 = gen_reg_rtx (XFmode);
16718
16719   emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, operands[2], operands[1]));
16720   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16721   DONE;
16722 })
16723
16724 (define_expand "atanxf2"
16725   [(parallel [(set (match_operand:XF 0 "register_operand" "")
16726                    (unspec:XF [(match_dup 2)
16727                                (match_operand:XF 1 "register_operand" "")]
16728                               UNSPEC_FPATAN))
16729               (clobber (match_scratch:XF 3 ""))])]
16730   "TARGET_USE_FANCY_MATH_387
16731    && flag_unsafe_math_optimizations"
16732 {
16733   operands[2] = gen_reg_rtx (XFmode);
16734   emit_move_insn (operands[2], CONST1_RTX (XFmode));  /* fld1 */
16735 })
16736
16737 (define_expand "atan<mode>2"
16738   [(use (match_operand:MODEF 0 "register_operand" ""))
16739    (use (match_operand:MODEF 1 "register_operand" ""))]
16740   "TARGET_USE_FANCY_MATH_387
16741    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16742        || TARGET_MIX_SSE_I387)
16743    && flag_unsafe_math_optimizations"
16744 {
16745   rtx op0 = gen_reg_rtx (XFmode);
16746
16747   rtx op2 = gen_reg_rtx (<MODE>mode);
16748   emit_move_insn (op2, CONST1_RTX (<MODE>mode));  /* fld1 */
16749
16750   emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, op2, operands[1]));
16751   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16752   DONE;
16753 })
16754
16755 (define_expand "asinxf2"
16756   [(set (match_dup 2)
16757         (mult:XF (match_operand:XF 1 "register_operand" "")
16758                  (match_dup 1)))
16759    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
16760    (set (match_dup 5) (sqrt:XF (match_dup 4)))
16761    (parallel [(set (match_operand:XF 0 "register_operand" "")
16762                    (unspec:XF [(match_dup 5) (match_dup 1)]
16763                               UNSPEC_FPATAN))
16764               (clobber (match_scratch:XF 6 ""))])]
16765   "TARGET_USE_FANCY_MATH_387
16766    && flag_unsafe_math_optimizations && !optimize_size"
16767 {
16768   int i;
16769
16770   for (i = 2; i < 6; i++)
16771     operands[i] = gen_reg_rtx (XFmode);
16772
16773   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
16774 })
16775
16776 (define_expand "asin<mode>2"
16777   [(use (match_operand:MODEF 0 "register_operand" ""))
16778    (use (match_operand:MODEF 1 "general_operand" ""))]
16779  "TARGET_USE_FANCY_MATH_387
16780    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16781        || TARGET_MIX_SSE_I387)
16782    && flag_unsafe_math_optimizations && !optimize_size"
16783 {
16784   rtx op0 = gen_reg_rtx (XFmode);
16785   rtx op1 = gen_reg_rtx (XFmode);
16786
16787   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
16788   emit_insn (gen_asinxf2 (op0, op1));
16789   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16790   DONE;
16791 })
16792
16793 (define_expand "acosxf2"
16794   [(set (match_dup 2)
16795         (mult:XF (match_operand:XF 1 "register_operand" "")
16796                  (match_dup 1)))
16797    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
16798    (set (match_dup 5) (sqrt:XF (match_dup 4)))
16799    (parallel [(set (match_operand:XF 0 "register_operand" "")
16800                    (unspec:XF [(match_dup 1) (match_dup 5)]
16801                               UNSPEC_FPATAN))
16802               (clobber (match_scratch:XF 6 ""))])]
16803   "TARGET_USE_FANCY_MATH_387
16804    && flag_unsafe_math_optimizations && !optimize_size"
16805 {
16806   int i;
16807
16808   for (i = 2; i < 6; i++)
16809     operands[i] = gen_reg_rtx (XFmode);
16810
16811   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
16812 })
16813
16814 (define_expand "acos<mode>2"
16815   [(use (match_operand:MODEF 0 "register_operand" ""))
16816    (use (match_operand:MODEF 1 "general_operand" ""))]
16817  "TARGET_USE_FANCY_MATH_387
16818    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16819        || TARGET_MIX_SSE_I387)
16820    && flag_unsafe_math_optimizations && !optimize_size"
16821 {
16822   rtx op0 = gen_reg_rtx (XFmode);
16823   rtx op1 = gen_reg_rtx (XFmode);
16824
16825   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
16826   emit_insn (gen_acosxf2 (op0, op1));
16827   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16828   DONE;
16829 })
16830
16831 (define_insn "fyl2xxf3_i387"
16832   [(set (match_operand:XF 0 "register_operand" "=f")
16833         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
16834                     (match_operand:XF 2 "register_operand" "u")]
16835                    UNSPEC_FYL2X))
16836    (clobber (match_scratch:XF 3 "=2"))]
16837   "TARGET_USE_FANCY_MATH_387
16838    && flag_unsafe_math_optimizations"
16839   "fyl2x"
16840   [(set_attr "type" "fpspc")
16841    (set_attr "mode" "XF")])
16842
16843 (define_insn "fyl2x_extend<mode>xf3_i387"
16844   [(set (match_operand:XF 0 "register_operand" "=f")
16845         (unspec:XF [(float_extend:XF
16846                       (match_operand:MODEF 1 "register_operand" "0"))
16847                     (match_operand:XF 2 "register_operand" "u")]
16848                    UNSPEC_FYL2X))
16849    (clobber (match_scratch:XF 3 "=2"))]
16850   "TARGET_USE_FANCY_MATH_387
16851    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16852        || TARGET_MIX_SSE_I387)
16853    && flag_unsafe_math_optimizations"
16854   "fyl2x"
16855   [(set_attr "type" "fpspc")
16856    (set_attr "mode" "XF")])
16857
16858 (define_expand "logxf2"
16859   [(parallel [(set (match_operand:XF 0 "register_operand" "")
16860                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
16861                                (match_dup 2)] UNSPEC_FYL2X))
16862               (clobber (match_scratch:XF 3 ""))])]
16863   "TARGET_USE_FANCY_MATH_387
16864    && flag_unsafe_math_optimizations"
16865 {
16866   operands[2] = gen_reg_rtx (XFmode);
16867   emit_move_insn (operands[2], standard_80387_constant_rtx (4)); /* fldln2 */
16868 })
16869
16870 (define_expand "log<mode>2"
16871   [(use (match_operand:MODEF 0 "register_operand" ""))
16872    (use (match_operand:MODEF 1 "register_operand" ""))]
16873   "TARGET_USE_FANCY_MATH_387
16874    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16875        || TARGET_MIX_SSE_I387)
16876    && flag_unsafe_math_optimizations"
16877 {
16878   rtx op0 = gen_reg_rtx (XFmode);
16879
16880   rtx op2 = gen_reg_rtx (XFmode);
16881   emit_move_insn (op2, standard_80387_constant_rtx (4)); /* fldln2 */
16882
16883   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
16884   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16885   DONE;
16886 })
16887
16888 (define_expand "log10xf2"
16889   [(parallel [(set (match_operand:XF 0 "register_operand" "")
16890                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
16891                                (match_dup 2)] UNSPEC_FYL2X))
16892               (clobber (match_scratch:XF 3 ""))])]
16893   "TARGET_USE_FANCY_MATH_387
16894    && flag_unsafe_math_optimizations"
16895 {
16896   operands[2] = gen_reg_rtx (XFmode);
16897   emit_move_insn (operands[2], standard_80387_constant_rtx (3)); /* fldlg2 */
16898 })
16899
16900 (define_expand "log10<mode>2"
16901   [(use (match_operand:MODEF 0 "register_operand" ""))
16902    (use (match_operand:MODEF 1 "register_operand" ""))]
16903   "TARGET_USE_FANCY_MATH_387
16904    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16905        || TARGET_MIX_SSE_I387)
16906    && flag_unsafe_math_optimizations"
16907 {
16908   rtx op0 = gen_reg_rtx (XFmode);
16909
16910   rtx op2 = gen_reg_rtx (XFmode);
16911   emit_move_insn (op2, standard_80387_constant_rtx (3)); /* fldlg2 */
16912
16913   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
16914   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16915   DONE;
16916 })
16917
16918 (define_expand "log2xf2"
16919   [(parallel [(set (match_operand:XF 0 "register_operand" "")
16920                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
16921                                (match_dup 2)] UNSPEC_FYL2X))
16922               (clobber (match_scratch:XF 3 ""))])]
16923   "TARGET_USE_FANCY_MATH_387
16924    && flag_unsafe_math_optimizations"
16925 {
16926   operands[2] = gen_reg_rtx (XFmode);
16927   emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
16928 })
16929
16930 (define_expand "log2<mode>2"
16931   [(use (match_operand:MODEF 0 "register_operand" ""))
16932    (use (match_operand:MODEF 1 "register_operand" ""))]
16933   "TARGET_USE_FANCY_MATH_387
16934    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16935        || TARGET_MIX_SSE_I387)
16936    && flag_unsafe_math_optimizations"
16937 {
16938   rtx op0 = gen_reg_rtx (XFmode);
16939
16940   rtx op2 = gen_reg_rtx (XFmode);
16941   emit_move_insn (op2, CONST1_RTX (XFmode)); /* fld1 */
16942
16943   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
16944   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16945   DONE;
16946 })
16947
16948 (define_insn "fyl2xp1xf3_i387"
16949   [(set (match_operand:XF 0 "register_operand" "=f")
16950         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
16951                     (match_operand:XF 2 "register_operand" "u")]
16952                    UNSPEC_FYL2XP1))
16953    (clobber (match_scratch:XF 3 "=2"))]
16954   "TARGET_USE_FANCY_MATH_387
16955    && flag_unsafe_math_optimizations"
16956   "fyl2xp1"
16957   [(set_attr "type" "fpspc")
16958    (set_attr "mode" "XF")])
16959
16960 (define_insn "fyl2xp1_extend<mode>xf3_i387"
16961   [(set (match_operand:XF 0 "register_operand" "=f")
16962         (unspec:XF [(float_extend:XF
16963                       (match_operand:MODEF 1 "register_operand" "0"))
16964                     (match_operand:XF 2 "register_operand" "u")]
16965                    UNSPEC_FYL2XP1))
16966    (clobber (match_scratch:XF 3 "=2"))]
16967   "TARGET_USE_FANCY_MATH_387
16968    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16969        || TARGET_MIX_SSE_I387)
16970    && flag_unsafe_math_optimizations"
16971   "fyl2xp1"
16972   [(set_attr "type" "fpspc")
16973    (set_attr "mode" "XF")])
16974
16975 (define_expand "log1pxf2"
16976   [(use (match_operand:XF 0 "register_operand" ""))
16977    (use (match_operand:XF 1 "register_operand" ""))]
16978   "TARGET_USE_FANCY_MATH_387
16979    && flag_unsafe_math_optimizations && !optimize_size"
16980 {
16981   ix86_emit_i387_log1p (operands[0], operands[1]);
16982   DONE;
16983 })
16984
16985 (define_expand "log1p<mode>2"
16986   [(use (match_operand:MODEF 0 "register_operand" ""))
16987    (use (match_operand:MODEF 1 "register_operand" ""))]
16988   "TARGET_USE_FANCY_MATH_387
16989    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16990        || TARGET_MIX_SSE_I387)
16991    && flag_unsafe_math_optimizations && !optimize_size"
16992 {
16993   rtx op0 = gen_reg_rtx (XFmode);
16994
16995   operands[1] = gen_rtx_FLOAT_EXTEND (XFmode, operands[1]);
16996
16997   ix86_emit_i387_log1p (op0, operands[1]);
16998   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16999   DONE;
17000 })
17001
17002 (define_insn "fxtractxf3_i387"
17003   [(set (match_operand:XF 0 "register_operand" "=f")
17004         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
17005                    UNSPEC_XTRACT_FRACT))
17006    (set (match_operand:XF 1 "register_operand" "=u")
17007         (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]
17008   "TARGET_USE_FANCY_MATH_387
17009    && flag_unsafe_math_optimizations"
17010   "fxtract"
17011   [(set_attr "type" "fpspc")
17012    (set_attr "mode" "XF")])
17013
17014 (define_insn "fxtract_extend<mode>xf3_i387"
17015   [(set (match_operand:XF 0 "register_operand" "=f")
17016         (unspec:XF [(float_extend:XF
17017                       (match_operand:MODEF 2 "register_operand" "0"))]
17018                    UNSPEC_XTRACT_FRACT))
17019    (set (match_operand:XF 1 "register_operand" "=u")
17020         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_XTRACT_EXP))]
17021   "TARGET_USE_FANCY_MATH_387
17022    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17023        || TARGET_MIX_SSE_I387)
17024    && flag_unsafe_math_optimizations"
17025   "fxtract"
17026   [(set_attr "type" "fpspc")
17027    (set_attr "mode" "XF")])
17028
17029 (define_expand "logbxf2"
17030   [(parallel [(set (match_dup 2)
17031                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
17032                               UNSPEC_XTRACT_FRACT))
17033               (set (match_operand:XF 0 "register_operand" "")
17034                    (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
17035   "TARGET_USE_FANCY_MATH_387
17036    && flag_unsafe_math_optimizations"
17037 {
17038   operands[2] = gen_reg_rtx (XFmode);
17039 })
17040
17041 (define_expand "logb<mode>2"
17042   [(use (match_operand:MODEF 0 "register_operand" ""))
17043    (use (match_operand:MODEF 1 "register_operand" ""))]
17044   "TARGET_USE_FANCY_MATH_387
17045    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17046        || TARGET_MIX_SSE_I387)
17047    && flag_unsafe_math_optimizations"
17048 {
17049   rtx op0 = gen_reg_rtx (XFmode);
17050   rtx op1 = gen_reg_rtx (XFmode);
17051
17052   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
17053   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op1));
17054   DONE;
17055 })
17056
17057 (define_expand "ilogbxf2"
17058   [(use (match_operand:SI 0 "register_operand" ""))
17059    (use (match_operand:XF 1 "register_operand" ""))]
17060   "TARGET_USE_FANCY_MATH_387
17061    && flag_unsafe_math_optimizations && !optimize_size"
17062 {
17063   rtx op0 = gen_reg_rtx (XFmode);
17064   rtx op1 = gen_reg_rtx (XFmode);
17065
17066   emit_insn (gen_fxtractxf3_i387 (op0, op1, operands[1]));
17067   emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
17068   DONE;
17069 })
17070
17071 (define_expand "ilogb<mode>2"
17072   [(use (match_operand:SI 0 "register_operand" ""))
17073    (use (match_operand:MODEF 1 "register_operand" ""))]
17074   "TARGET_USE_FANCY_MATH_387
17075    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17076        || TARGET_MIX_SSE_I387)
17077    && flag_unsafe_math_optimizations && !optimize_size"
17078 {
17079   rtx op0 = gen_reg_rtx (XFmode);
17080   rtx op1 = gen_reg_rtx (XFmode);
17081
17082   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
17083   emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
17084   DONE;
17085 })
17086
17087 (define_insn "*f2xm1xf2_i387"
17088   [(set (match_operand:XF 0 "register_operand" "=f")
17089         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17090                    UNSPEC_F2XM1))]
17091   "TARGET_USE_FANCY_MATH_387
17092    && flag_unsafe_math_optimizations"
17093   "f2xm1"
17094   [(set_attr "type" "fpspc")
17095    (set_attr "mode" "XF")])
17096
17097 (define_insn "*fscalexf4_i387"
17098   [(set (match_operand:XF 0 "register_operand" "=f")
17099         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
17100                     (match_operand:XF 3 "register_operand" "1")]
17101                    UNSPEC_FSCALE_FRACT))
17102    (set (match_operand:XF 1 "register_operand" "=u")
17103         (unspec:XF [(match_dup 2) (match_dup 3)]
17104                    UNSPEC_FSCALE_EXP))]
17105   "TARGET_USE_FANCY_MATH_387
17106    && flag_unsafe_math_optimizations"
17107   "fscale"
17108   [(set_attr "type" "fpspc")
17109    (set_attr "mode" "XF")])
17110
17111 (define_expand "expNcorexf3"
17112   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
17113                                (match_operand:XF 2 "register_operand" "")))
17114    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
17115    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
17116    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
17117    (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
17118    (parallel [(set (match_operand:XF 0 "register_operand" "")
17119                    (unspec:XF [(match_dup 8) (match_dup 4)]
17120                               UNSPEC_FSCALE_FRACT))
17121               (set (match_dup 9)
17122                    (unspec:XF [(match_dup 8) (match_dup 4)]
17123                               UNSPEC_FSCALE_EXP))])]
17124   "TARGET_USE_FANCY_MATH_387
17125    && flag_unsafe_math_optimizations && !optimize_size"
17126 {
17127   int i;
17128
17129   for (i = 3; i < 10; i++)
17130     operands[i] = gen_reg_rtx (XFmode);
17131
17132   emit_move_insn (operands[7], CONST1_RTX (XFmode));  /* fld1 */
17133 })
17134
17135 (define_expand "expxf2"
17136   [(use (match_operand:XF 0 "register_operand" ""))
17137    (use (match_operand:XF 1 "register_operand" ""))]
17138   "TARGET_USE_FANCY_MATH_387
17139    && flag_unsafe_math_optimizations && !optimize_size"
17140 {
17141   rtx op2 = gen_reg_rtx (XFmode);
17142   emit_move_insn (op2, standard_80387_constant_rtx (5)); /* fldl2e */
17143
17144   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
17145   DONE;
17146 })
17147
17148 (define_expand "exp<mode>2"
17149   [(use (match_operand:MODEF 0 "register_operand" ""))
17150    (use (match_operand:MODEF 1 "general_operand" ""))]
17151  "TARGET_USE_FANCY_MATH_387
17152    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17153        || TARGET_MIX_SSE_I387)
17154    && flag_unsafe_math_optimizations && !optimize_size"
17155 {
17156   rtx op0 = gen_reg_rtx (XFmode);
17157   rtx op1 = gen_reg_rtx (XFmode);
17158
17159   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17160   emit_insn (gen_expxf2 (op0, op1));
17161   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17162   DONE;
17163 })
17164
17165 (define_expand "exp10xf2"
17166   [(use (match_operand:XF 0 "register_operand" ""))
17167    (use (match_operand:XF 1 "register_operand" ""))]
17168   "TARGET_USE_FANCY_MATH_387
17169    && flag_unsafe_math_optimizations && !optimize_size"
17170 {
17171   rtx op2 = gen_reg_rtx (XFmode);
17172   emit_move_insn (op2, standard_80387_constant_rtx (6)); /* fldl2t */
17173
17174   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
17175   DONE;
17176 })
17177
17178 (define_expand "exp10<mode>2"
17179   [(use (match_operand:MODEF 0 "register_operand" ""))
17180    (use (match_operand:MODEF 1 "general_operand" ""))]
17181  "TARGET_USE_FANCY_MATH_387
17182    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17183        || TARGET_MIX_SSE_I387)
17184    && flag_unsafe_math_optimizations && !optimize_size"
17185 {
17186   rtx op0 = gen_reg_rtx (XFmode);
17187   rtx op1 = gen_reg_rtx (XFmode);
17188
17189   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17190   emit_insn (gen_exp10xf2 (op0, op1));
17191   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17192   DONE;
17193 })
17194
17195 (define_expand "exp2xf2"
17196   [(use (match_operand:XF 0 "register_operand" ""))
17197    (use (match_operand:XF 1 "register_operand" ""))]
17198   "TARGET_USE_FANCY_MATH_387
17199    && flag_unsafe_math_optimizations && !optimize_size"
17200 {
17201   rtx op2 = gen_reg_rtx (XFmode);
17202   emit_move_insn (op2, CONST1_RTX (XFmode));  /* fld1 */
17203
17204   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
17205   DONE;
17206 })
17207
17208 (define_expand "exp2<mode>2"
17209   [(use (match_operand:MODEF 0 "register_operand" ""))
17210    (use (match_operand:MODEF 1 "general_operand" ""))]
17211  "TARGET_USE_FANCY_MATH_387
17212    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17213        || TARGET_MIX_SSE_I387)
17214    && flag_unsafe_math_optimizations && !optimize_size"
17215 {
17216   rtx op0 = gen_reg_rtx (XFmode);
17217   rtx op1 = gen_reg_rtx (XFmode);
17218
17219   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17220   emit_insn (gen_exp2xf2 (op0, op1));
17221   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17222   DONE;
17223 })
17224
17225 (define_expand "expm1xf2"
17226   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
17227                                (match_dup 2)))
17228    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
17229    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
17230    (set (match_dup 9) (float_extend:XF (match_dup 13)))
17231    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
17232    (parallel [(set (match_dup 7)
17233                    (unspec:XF [(match_dup 6) (match_dup 4)]
17234                               UNSPEC_FSCALE_FRACT))
17235               (set (match_dup 8)
17236                    (unspec:XF [(match_dup 6) (match_dup 4)]
17237                               UNSPEC_FSCALE_EXP))])
17238    (parallel [(set (match_dup 10)
17239                    (unspec:XF [(match_dup 9) (match_dup 8)]
17240                               UNSPEC_FSCALE_FRACT))
17241               (set (match_dup 11)
17242                    (unspec:XF [(match_dup 9) (match_dup 8)]
17243                               UNSPEC_FSCALE_EXP))])
17244    (set (match_dup 12) (minus:XF (match_dup 10)
17245                                  (float_extend:XF (match_dup 13))))
17246    (set (match_operand:XF 0 "register_operand" "")
17247         (plus:XF (match_dup 12) (match_dup 7)))]
17248   "TARGET_USE_FANCY_MATH_387
17249    && flag_unsafe_math_optimizations && !optimize_size"
17250 {
17251   int i;
17252
17253   for (i = 2; i < 13; i++)
17254     operands[i] = gen_reg_rtx (XFmode);
17255
17256   operands[13]
17257     = validize_mem (force_const_mem (SFmode, CONST1_RTX (SFmode))); /* fld1 */
17258
17259   emit_move_insn (operands[2], standard_80387_constant_rtx (5)); /* fldl2e */
17260 })
17261
17262 (define_expand "expm1<mode>2"
17263   [(use (match_operand:MODEF 0 "register_operand" ""))
17264    (use (match_operand:MODEF 1 "general_operand" ""))]
17265  "TARGET_USE_FANCY_MATH_387
17266    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17267        || TARGET_MIX_SSE_I387)
17268    && flag_unsafe_math_optimizations && !optimize_size"
17269 {
17270   rtx op0 = gen_reg_rtx (XFmode);
17271   rtx op1 = gen_reg_rtx (XFmode);
17272
17273   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17274   emit_insn (gen_expm1xf2 (op0, op1));
17275   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17276   DONE;
17277 })
17278
17279 (define_expand "ldexpxf3"
17280   [(set (match_dup 3)
17281         (float:XF (match_operand:SI 2 "register_operand" "")))
17282    (parallel [(set (match_operand:XF 0 " register_operand" "")
17283                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
17284                                (match_dup 3)]
17285                               UNSPEC_FSCALE_FRACT))
17286               (set (match_dup 4)
17287                    (unspec:XF [(match_dup 1) (match_dup 3)]
17288                               UNSPEC_FSCALE_EXP))])]
17289   "TARGET_USE_FANCY_MATH_387
17290    && flag_unsafe_math_optimizations && !optimize_size"
17291 {
17292   operands[3] = gen_reg_rtx (XFmode);
17293   operands[4] = gen_reg_rtx (XFmode);
17294 })
17295
17296 (define_expand "ldexp<mode>3"
17297   [(use (match_operand:MODEF 0 "register_operand" ""))
17298    (use (match_operand:MODEF 1 "general_operand" ""))
17299    (use (match_operand:SI 2 "register_operand" ""))]
17300  "TARGET_USE_FANCY_MATH_387
17301    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17302        || TARGET_MIX_SSE_I387)
17303    && flag_unsafe_math_optimizations && !optimize_size"
17304 {
17305   rtx op0 = gen_reg_rtx (XFmode);
17306   rtx op1 = gen_reg_rtx (XFmode);
17307
17308   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17309   emit_insn (gen_ldexpxf3 (op0, op1, operands[2]));
17310   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17311   DONE;
17312 })
17313
17314 (define_expand "scalbxf3"
17315   [(parallel [(set (match_operand:XF 0 " register_operand" "")
17316                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
17317                                (match_operand:XF 2 "register_operand" "")]
17318                               UNSPEC_FSCALE_FRACT))
17319               (set (match_dup 3)
17320                    (unspec:XF [(match_dup 1) (match_dup 2)]
17321                               UNSPEC_FSCALE_EXP))])]
17322   "TARGET_USE_FANCY_MATH_387
17323    && flag_unsafe_math_optimizations && !optimize_size"
17324 {
17325   operands[3] = gen_reg_rtx (XFmode);
17326 })
17327
17328 (define_expand "scalb<mode>3"
17329   [(use (match_operand:MODEF 0 "register_operand" ""))
17330    (use (match_operand:MODEF 1 "general_operand" ""))
17331    (use (match_operand:MODEF 2 "register_operand" ""))]
17332  "TARGET_USE_FANCY_MATH_387
17333    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17334        || TARGET_MIX_SSE_I387)
17335    && flag_unsafe_math_optimizations && !optimize_size"
17336 {
17337   rtx op0 = gen_reg_rtx (XFmode);
17338   rtx op1 = gen_reg_rtx (XFmode);
17339   rtx op2 = gen_reg_rtx (XFmode);
17340
17341   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17342   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
17343   emit_insn (gen_scalbxf3 (op0, op1, op2));
17344   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17345   DONE;
17346 })
17347 \f
17348
17349 (define_insn "sse4_1_round<mode>2"
17350   [(set (match_operand:MODEF 0 "register_operand" "=x")
17351         (unspec:MODEF [(match_operand:MODEF 1 "register_operand" "x")
17352                        (match_operand:SI 2 "const_0_to_15_operand" "n")]
17353                       UNSPEC_ROUND))]
17354   "TARGET_ROUND"
17355   "rounds<ssemodefsuffix>\t{%2, %1, %0|%0, %1, %2}"
17356   [(set_attr "type" "ssecvt")
17357    (set_attr "prefix_extra" "1")
17358    (set_attr "mode" "<MODE>")])
17359
17360 (define_insn "rintxf2"
17361   [(set (match_operand:XF 0 "register_operand" "=f")
17362         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17363                    UNSPEC_FRNDINT))]
17364   "TARGET_USE_FANCY_MATH_387
17365    && flag_unsafe_math_optimizations"
17366   "frndint"
17367   [(set_attr "type" "fpspc")
17368    (set_attr "mode" "XF")])
17369
17370 (define_expand "rint<mode>2"
17371   [(use (match_operand:MODEF 0 "register_operand" ""))
17372    (use (match_operand:MODEF 1 "register_operand" ""))]
17373   "(TARGET_USE_FANCY_MATH_387
17374     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17375         || TARGET_MIX_SSE_I387)
17376     && flag_unsafe_math_optimizations)
17377    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17378        && !flag_trapping_math
17379        && (TARGET_ROUND || !optimize_size))"
17380 {
17381   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17382       && !flag_trapping_math
17383       && (TARGET_ROUND || !optimize_size))
17384     {
17385       if (TARGET_ROUND)
17386         emit_insn (gen_sse4_1_round<mode>2
17387                    (operands[0], operands[1], GEN_INT (0x04)));
17388       else
17389         ix86_expand_rint (operand0, operand1);
17390     }
17391   else
17392     {
17393       rtx op0 = gen_reg_rtx (XFmode);
17394       rtx op1 = gen_reg_rtx (XFmode);
17395
17396       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17397       emit_insn (gen_rintxf2 (op0, op1));
17398
17399       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17400     }
17401   DONE;
17402 })
17403
17404 (define_expand "round<mode>2"
17405   [(match_operand:MODEF 0 "register_operand" "")
17406    (match_operand:MODEF 1 "nonimmediate_operand" "")]
17407   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17408    && !flag_trapping_math && !flag_rounding_math
17409    && !optimize_size"
17410 {
17411   if (TARGET_64BIT || (<MODE>mode != DFmode))
17412     ix86_expand_round (operand0, operand1);
17413   else
17414     ix86_expand_rounddf_32 (operand0, operand1);
17415   DONE;
17416 })
17417
17418 (define_insn_and_split "*fistdi2_1"
17419   [(set (match_operand:DI 0 "nonimmediate_operand" "")
17420         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17421                    UNSPEC_FIST))]
17422   "TARGET_USE_FANCY_MATH_387
17423    && !(reload_completed || reload_in_progress)"
17424   "#"
17425   "&& 1"
17426   [(const_int 0)]
17427 {
17428   if (memory_operand (operands[0], VOIDmode))
17429     emit_insn (gen_fistdi2 (operands[0], operands[1]));
17430   else
17431     {
17432       operands[2] = assign_386_stack_local (DImode, SLOT_TEMP);
17433       emit_insn (gen_fistdi2_with_temp (operands[0], operands[1],
17434                                          operands[2]));
17435     }
17436   DONE;
17437 }
17438   [(set_attr "type" "fpspc")
17439    (set_attr "mode" "DI")])
17440
17441 (define_insn "fistdi2"
17442   [(set (match_operand:DI 0 "memory_operand" "=m")
17443         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
17444                    UNSPEC_FIST))
17445    (clobber (match_scratch:XF 2 "=&1f"))]
17446   "TARGET_USE_FANCY_MATH_387"
17447   "* return output_fix_trunc (insn, operands, 0);"
17448   [(set_attr "type" "fpspc")
17449    (set_attr "mode" "DI")])
17450
17451 (define_insn "fistdi2_with_temp"
17452   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
17453         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
17454                    UNSPEC_FIST))
17455    (clobber (match_operand:DI 2 "memory_operand" "=X,m"))
17456    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
17457   "TARGET_USE_FANCY_MATH_387"
17458   "#"
17459   [(set_attr "type" "fpspc")
17460    (set_attr "mode" "DI")])
17461
17462 (define_split
17463   [(set (match_operand:DI 0 "register_operand" "")
17464         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17465                    UNSPEC_FIST))
17466    (clobber (match_operand:DI 2 "memory_operand" ""))
17467    (clobber (match_scratch 3 ""))]
17468   "reload_completed"
17469   [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
17470               (clobber (match_dup 3))])
17471    (set (match_dup 0) (match_dup 2))]
17472   "")
17473
17474 (define_split
17475   [(set (match_operand:DI 0 "memory_operand" "")
17476         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17477                    UNSPEC_FIST))
17478    (clobber (match_operand:DI 2 "memory_operand" ""))
17479    (clobber (match_scratch 3 ""))]
17480   "reload_completed"
17481   [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
17482               (clobber (match_dup 3))])]
17483   "")
17484
17485 (define_insn_and_split "*fist<mode>2_1"
17486   [(set (match_operand:X87MODEI12 0 "register_operand" "")
17487         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17488                            UNSPEC_FIST))]
17489   "TARGET_USE_FANCY_MATH_387
17490    && !(reload_completed || reload_in_progress)"
17491   "#"
17492   "&& 1"
17493   [(const_int 0)]
17494 {
17495   operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
17496   emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1],
17497                                         operands[2]));
17498   DONE;
17499 }
17500   [(set_attr "type" "fpspc")
17501    (set_attr "mode" "<MODE>")])
17502
17503 (define_insn "fist<mode>2"
17504   [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
17505         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
17506                            UNSPEC_FIST))]
17507   "TARGET_USE_FANCY_MATH_387"
17508   "* return output_fix_trunc (insn, operands, 0);"
17509   [(set_attr "type" "fpspc")
17510    (set_attr "mode" "<MODE>")])
17511
17512 (define_insn "fist<mode>2_with_temp"
17513   [(set (match_operand:X87MODEI12 0 "register_operand" "=r")
17514         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
17515                            UNSPEC_FIST))
17516    (clobber (match_operand:X87MODEI12 2 "memory_operand" "=m"))]
17517   "TARGET_USE_FANCY_MATH_387"
17518   "#"
17519   [(set_attr "type" "fpspc")
17520    (set_attr "mode" "<MODE>")])
17521
17522 (define_split
17523   [(set (match_operand:X87MODEI12 0 "register_operand" "")
17524         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17525                            UNSPEC_FIST))
17526    (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
17527   "reload_completed"
17528   [(set (match_dup 2) (unspec:X87MODEI12 [(match_dup 1)] UNSPEC_FIST))
17529    (set (match_dup 0) (match_dup 2))]
17530   "")
17531
17532 (define_split
17533   [(set (match_operand:X87MODEI12 0 "memory_operand" "")
17534         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17535                            UNSPEC_FIST))
17536    (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
17537   "reload_completed"
17538   [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)] UNSPEC_FIST))]
17539   "")
17540
17541 (define_expand "lrintxf<mode>2"
17542   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
17543      (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
17544                       UNSPEC_FIST))]
17545   "TARGET_USE_FANCY_MATH_387"
17546   "")
17547
17548 (define_expand "lrint<MODEF:mode><SSEMODEI24:mode>2"
17549   [(set (match_operand:SSEMODEI24 0 "nonimmediate_operand" "")
17550      (unspec:SSEMODEI24 [(match_operand:MODEF 1 "register_operand" "")]
17551                         UNSPEC_FIX_NOTRUNC))]
17552   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
17553    && ((<SSEMODEI24:MODE>mode != DImode) || TARGET_64BIT)"
17554   "")
17555
17556 (define_expand "lround<MODEF:mode><SSEMODEI24:mode>2"
17557   [(match_operand:SSEMODEI24 0 "nonimmediate_operand" "")
17558    (match_operand:MODEF 1 "register_operand" "")]
17559   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
17560    && ((<SSEMODEI24:MODE>mode != DImode) || TARGET_64BIT)
17561    && !flag_trapping_math && !flag_rounding_math
17562    && !optimize_size"
17563 {
17564   ix86_expand_lround (operand0, operand1);
17565   DONE;
17566 })
17567
17568 ;; Rounding mode control word calculation could clobber FLAGS_REG.
17569 (define_insn_and_split "frndintxf2_floor"
17570   [(set (match_operand:XF 0 "register_operand" "")
17571         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
17572          UNSPEC_FRNDINT_FLOOR))
17573    (clobber (reg:CC FLAGS_REG))]
17574   "TARGET_USE_FANCY_MATH_387
17575    && flag_unsafe_math_optimizations
17576    && !(reload_completed || reload_in_progress)"
17577   "#"
17578   "&& 1"
17579   [(const_int 0)]
17580 {
17581   ix86_optimize_mode_switching[I387_FLOOR] = 1;
17582
17583   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17584   operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
17585
17586   emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1],
17587                                         operands[2], operands[3]));
17588   DONE;
17589 }
17590   [(set_attr "type" "frndint")
17591    (set_attr "i387_cw" "floor")
17592    (set_attr "mode" "XF")])
17593
17594 (define_insn "frndintxf2_floor_i387"
17595   [(set (match_operand:XF 0 "register_operand" "=f")
17596         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17597          UNSPEC_FRNDINT_FLOOR))
17598    (use (match_operand:HI 2 "memory_operand" "m"))
17599    (use (match_operand:HI 3 "memory_operand" "m"))]
17600   "TARGET_USE_FANCY_MATH_387
17601    && flag_unsafe_math_optimizations"
17602   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
17603   [(set_attr "type" "frndint")
17604    (set_attr "i387_cw" "floor")
17605    (set_attr "mode" "XF")])
17606
17607 (define_expand "floorxf2"
17608   [(use (match_operand:XF 0 "register_operand" ""))
17609    (use (match_operand:XF 1 "register_operand" ""))]
17610   "TARGET_USE_FANCY_MATH_387
17611    && flag_unsafe_math_optimizations && !optimize_size"
17612 {
17613   emit_insn (gen_frndintxf2_floor (operands[0], operands[1]));
17614   DONE;
17615 })
17616
17617 (define_expand "floor<mode>2"
17618   [(use (match_operand:MODEF 0 "register_operand" ""))
17619    (use (match_operand:MODEF 1 "register_operand" ""))]
17620   "(TARGET_USE_FANCY_MATH_387
17621     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17622         || TARGET_MIX_SSE_I387)
17623     && flag_unsafe_math_optimizations && !optimize_size)
17624    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17625        && !flag_trapping_math
17626        && (TARGET_ROUND || !optimize_size))"
17627 {
17628   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17629       && !flag_trapping_math
17630       && (TARGET_ROUND || !optimize_size))
17631     {
17632       if (TARGET_ROUND)
17633         emit_insn (gen_sse4_1_round<mode>2
17634                    (operands[0], operands[1], GEN_INT (0x01)));
17635       else if (TARGET_64BIT || (<MODE>mode != DFmode))
17636         ix86_expand_floorceil (operand0, operand1, true);
17637       else
17638         ix86_expand_floorceildf_32 (operand0, operand1, true);
17639     }
17640   else
17641     {
17642       rtx op0 = gen_reg_rtx (XFmode);
17643       rtx op1 = gen_reg_rtx (XFmode);
17644
17645       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17646       emit_insn (gen_frndintxf2_floor (op0, op1));
17647
17648       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17649     }
17650   DONE;
17651 })
17652
17653 (define_insn_and_split "*fist<mode>2_floor_1"
17654   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
17655         (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
17656          UNSPEC_FIST_FLOOR))
17657    (clobber (reg:CC FLAGS_REG))]
17658   "TARGET_USE_FANCY_MATH_387
17659    && flag_unsafe_math_optimizations
17660    && !(reload_completed || reload_in_progress)"
17661   "#"
17662   "&& 1"
17663   [(const_int 0)]
17664 {
17665   ix86_optimize_mode_switching[I387_FLOOR] = 1;
17666
17667   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17668   operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
17669   if (memory_operand (operands[0], VOIDmode))
17670     emit_insn (gen_fist<mode>2_floor (operands[0], operands[1],
17671                                       operands[2], operands[3]));
17672   else
17673     {
17674       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
17675       emit_insn (gen_fist<mode>2_floor_with_temp (operands[0], operands[1],
17676                                                   operands[2], operands[3],
17677                                                   operands[4]));
17678     }
17679   DONE;
17680 }
17681   [(set_attr "type" "fistp")
17682    (set_attr "i387_cw" "floor")
17683    (set_attr "mode" "<MODE>")])
17684
17685 (define_insn "fistdi2_floor"
17686   [(set (match_operand:DI 0 "memory_operand" "=m")
17687         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
17688          UNSPEC_FIST_FLOOR))
17689    (use (match_operand:HI 2 "memory_operand" "m"))
17690    (use (match_operand:HI 3 "memory_operand" "m"))
17691    (clobber (match_scratch:XF 4 "=&1f"))]
17692   "TARGET_USE_FANCY_MATH_387
17693    && flag_unsafe_math_optimizations"
17694   "* return output_fix_trunc (insn, operands, 0);"
17695   [(set_attr "type" "fistp")
17696    (set_attr "i387_cw" "floor")
17697    (set_attr "mode" "DI")])
17698
17699 (define_insn "fistdi2_floor_with_temp"
17700   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
17701         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
17702          UNSPEC_FIST_FLOOR))
17703    (use (match_operand:HI 2 "memory_operand" "m,m"))
17704    (use (match_operand:HI 3 "memory_operand" "m,m"))
17705    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
17706    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
17707   "TARGET_USE_FANCY_MATH_387
17708    && flag_unsafe_math_optimizations"
17709   "#"
17710   [(set_attr "type" "fistp")
17711    (set_attr "i387_cw" "floor")
17712    (set_attr "mode" "DI")])
17713
17714 (define_split
17715   [(set (match_operand:DI 0 "register_operand" "")
17716         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17717          UNSPEC_FIST_FLOOR))
17718    (use (match_operand:HI 2 "memory_operand" ""))
17719    (use (match_operand:HI 3 "memory_operand" ""))
17720    (clobber (match_operand:DI 4 "memory_operand" ""))
17721    (clobber (match_scratch 5 ""))]
17722   "reload_completed"
17723   [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
17724               (use (match_dup 2))
17725               (use (match_dup 3))
17726               (clobber (match_dup 5))])
17727    (set (match_dup 0) (match_dup 4))]
17728   "")
17729
17730 (define_split
17731   [(set (match_operand:DI 0 "memory_operand" "")
17732         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17733          UNSPEC_FIST_FLOOR))
17734    (use (match_operand:HI 2 "memory_operand" ""))
17735    (use (match_operand:HI 3 "memory_operand" ""))
17736    (clobber (match_operand:DI 4 "memory_operand" ""))
17737    (clobber (match_scratch 5 ""))]
17738   "reload_completed"
17739   [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
17740               (use (match_dup 2))
17741               (use (match_dup 3))
17742               (clobber (match_dup 5))])]
17743   "")
17744
17745 (define_insn "fist<mode>2_floor"
17746   [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
17747         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
17748          UNSPEC_FIST_FLOOR))
17749    (use (match_operand:HI 2 "memory_operand" "m"))
17750    (use (match_operand:HI 3 "memory_operand" "m"))]
17751   "TARGET_USE_FANCY_MATH_387
17752    && flag_unsafe_math_optimizations"
17753   "* return output_fix_trunc (insn, operands, 0);"
17754   [(set_attr "type" "fistp")
17755    (set_attr "i387_cw" "floor")
17756    (set_attr "mode" "<MODE>")])
17757
17758 (define_insn "fist<mode>2_floor_with_temp"
17759   [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
17760         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
17761          UNSPEC_FIST_FLOOR))
17762    (use (match_operand:HI 2 "memory_operand" "m,m"))
17763    (use (match_operand:HI 3 "memory_operand" "m,m"))
17764    (clobber (match_operand:X87MODEI12 4 "memory_operand" "=X,m"))]
17765   "TARGET_USE_FANCY_MATH_387
17766    && flag_unsafe_math_optimizations"
17767   "#"
17768   [(set_attr "type" "fistp")
17769    (set_attr "i387_cw" "floor")
17770    (set_attr "mode" "<MODE>")])
17771
17772 (define_split
17773   [(set (match_operand:X87MODEI12 0 "register_operand" "")
17774         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17775          UNSPEC_FIST_FLOOR))
17776    (use (match_operand:HI 2 "memory_operand" ""))
17777    (use (match_operand:HI 3 "memory_operand" ""))
17778    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
17779   "reload_completed"
17780   [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
17781                                   UNSPEC_FIST_FLOOR))
17782               (use (match_dup 2))
17783               (use (match_dup 3))])
17784    (set (match_dup 0) (match_dup 4))]
17785   "")
17786
17787 (define_split
17788   [(set (match_operand:X87MODEI12 0 "memory_operand" "")
17789         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17790          UNSPEC_FIST_FLOOR))
17791    (use (match_operand:HI 2 "memory_operand" ""))
17792    (use (match_operand:HI 3 "memory_operand" ""))
17793    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
17794   "reload_completed"
17795   [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
17796                                   UNSPEC_FIST_FLOOR))
17797               (use (match_dup 2))
17798               (use (match_dup 3))])]
17799   "")
17800
17801 (define_expand "lfloorxf<mode>2"
17802   [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
17803                    (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
17804                     UNSPEC_FIST_FLOOR))
17805               (clobber (reg:CC FLAGS_REG))])]
17806   "TARGET_USE_FANCY_MATH_387
17807    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
17808    && flag_unsafe_math_optimizations"
17809   "")
17810
17811 (define_expand "lfloor<mode>di2"
17812   [(match_operand:DI 0 "nonimmediate_operand" "")
17813    (match_operand:MODEF 1 "register_operand" "")]
17814   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH && TARGET_64BIT
17815    && !flag_trapping_math
17816    && !optimize_size"
17817 {
17818   ix86_expand_lfloorceil (operand0, operand1, true);
17819   DONE;
17820 })
17821
17822 (define_expand "lfloor<mode>si2"
17823   [(match_operand:SI 0 "nonimmediate_operand" "")
17824    (match_operand:MODEF 1 "register_operand" "")]
17825   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17826    && !flag_trapping_math
17827    && (!optimize_size || !TARGET_64BIT)"
17828 {
17829   ix86_expand_lfloorceil (operand0, operand1, true);
17830   DONE;
17831 })
17832
17833 ;; Rounding mode control word calculation could clobber FLAGS_REG.
17834 (define_insn_and_split "frndintxf2_ceil"
17835   [(set (match_operand:XF 0 "register_operand" "")
17836         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
17837          UNSPEC_FRNDINT_CEIL))
17838    (clobber (reg:CC FLAGS_REG))]
17839   "TARGET_USE_FANCY_MATH_387
17840    && flag_unsafe_math_optimizations
17841    && !(reload_completed || reload_in_progress)"
17842   "#"
17843   "&& 1"
17844   [(const_int 0)]
17845 {
17846   ix86_optimize_mode_switching[I387_CEIL] = 1;
17847
17848   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17849   operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
17850
17851   emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1],
17852                                        operands[2], operands[3]));
17853   DONE;
17854 }
17855   [(set_attr "type" "frndint")
17856    (set_attr "i387_cw" "ceil")
17857    (set_attr "mode" "XF")])
17858
17859 (define_insn "frndintxf2_ceil_i387"
17860   [(set (match_operand:XF 0 "register_operand" "=f")
17861         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17862          UNSPEC_FRNDINT_CEIL))
17863    (use (match_operand:HI 2 "memory_operand" "m"))
17864    (use (match_operand:HI 3 "memory_operand" "m"))]
17865   "TARGET_USE_FANCY_MATH_387
17866    && flag_unsafe_math_optimizations"
17867   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
17868   [(set_attr "type" "frndint")
17869    (set_attr "i387_cw" "ceil")
17870    (set_attr "mode" "XF")])
17871
17872 (define_expand "ceilxf2"
17873   [(use (match_operand:XF 0 "register_operand" ""))
17874    (use (match_operand:XF 1 "register_operand" ""))]
17875   "TARGET_USE_FANCY_MATH_387
17876    && flag_unsafe_math_optimizations && !optimize_size"
17877 {
17878   emit_insn (gen_frndintxf2_ceil (operands[0], operands[1]));
17879   DONE;
17880 })
17881
17882 (define_expand "ceil<mode>2"
17883   [(use (match_operand:MODEF 0 "register_operand" ""))
17884    (use (match_operand:MODEF 1 "register_operand" ""))]
17885   "(TARGET_USE_FANCY_MATH_387
17886     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17887         || TARGET_MIX_SSE_I387)
17888     && flag_unsafe_math_optimizations && !optimize_size)
17889    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17890        && !flag_trapping_math
17891        && (TARGET_ROUND || !optimize_size))"
17892 {
17893   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17894       && !flag_trapping_math
17895       && (TARGET_ROUND || !optimize_size))
17896     {
17897       if (TARGET_ROUND)
17898         emit_insn (gen_sse4_1_round<mode>2
17899                    (operands[0], operands[1], GEN_INT (0x02)));
17900       else if (TARGET_64BIT || (<MODE>mode != DFmode))
17901         ix86_expand_floorceil (operand0, operand1, false);
17902       else
17903         ix86_expand_floorceildf_32 (operand0, operand1, false);
17904     }
17905   else
17906     {
17907       rtx op0 = gen_reg_rtx (XFmode);
17908       rtx op1 = gen_reg_rtx (XFmode);
17909
17910       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17911       emit_insn (gen_frndintxf2_ceil (op0, op1));
17912
17913       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17914     }
17915   DONE;
17916 })
17917
17918 (define_insn_and_split "*fist<mode>2_ceil_1"
17919   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
17920         (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
17921          UNSPEC_FIST_CEIL))
17922    (clobber (reg:CC FLAGS_REG))]
17923   "TARGET_USE_FANCY_MATH_387
17924    && flag_unsafe_math_optimizations
17925    && !(reload_completed || reload_in_progress)"
17926   "#"
17927   "&& 1"
17928   [(const_int 0)]
17929 {
17930   ix86_optimize_mode_switching[I387_CEIL] = 1;
17931
17932   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17933   operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
17934   if (memory_operand (operands[0], VOIDmode))
17935     emit_insn (gen_fist<mode>2_ceil (operands[0], operands[1],
17936                                      operands[2], operands[3]));
17937   else
17938     {
17939       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
17940       emit_insn (gen_fist<mode>2_ceil_with_temp (operands[0], operands[1],
17941                                                  operands[2], operands[3],
17942                                                  operands[4]));
17943     }
17944   DONE;
17945 }
17946   [(set_attr "type" "fistp")
17947    (set_attr "i387_cw" "ceil")
17948    (set_attr "mode" "<MODE>")])
17949
17950 (define_insn "fistdi2_ceil"
17951   [(set (match_operand:DI 0 "memory_operand" "=m")
17952         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
17953          UNSPEC_FIST_CEIL))
17954    (use (match_operand:HI 2 "memory_operand" "m"))
17955    (use (match_operand:HI 3 "memory_operand" "m"))
17956    (clobber (match_scratch:XF 4 "=&1f"))]
17957   "TARGET_USE_FANCY_MATH_387
17958    && flag_unsafe_math_optimizations"
17959   "* return output_fix_trunc (insn, operands, 0);"
17960   [(set_attr "type" "fistp")
17961    (set_attr "i387_cw" "ceil")
17962    (set_attr "mode" "DI")])
17963
17964 (define_insn "fistdi2_ceil_with_temp"
17965   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
17966         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
17967          UNSPEC_FIST_CEIL))
17968    (use (match_operand:HI 2 "memory_operand" "m,m"))
17969    (use (match_operand:HI 3 "memory_operand" "m,m"))
17970    (clobber (match_operand:DI 4 "memory_operand" "=X,m"))
17971    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
17972   "TARGET_USE_FANCY_MATH_387
17973    && flag_unsafe_math_optimizations"
17974   "#"
17975   [(set_attr "type" "fistp")
17976    (set_attr "i387_cw" "ceil")
17977    (set_attr "mode" "DI")])
17978
17979 (define_split
17980   [(set (match_operand:DI 0 "register_operand" "")
17981         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17982          UNSPEC_FIST_CEIL))
17983    (use (match_operand:HI 2 "memory_operand" ""))
17984    (use (match_operand:HI 3 "memory_operand" ""))
17985    (clobber (match_operand:DI 4 "memory_operand" ""))
17986    (clobber (match_scratch 5 ""))]
17987   "reload_completed"
17988   [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
17989               (use (match_dup 2))
17990               (use (match_dup 3))
17991               (clobber (match_dup 5))])
17992    (set (match_dup 0) (match_dup 4))]
17993   "")
17994
17995 (define_split
17996   [(set (match_operand:DI 0 "memory_operand" "")
17997         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17998          UNSPEC_FIST_CEIL))
17999    (use (match_operand:HI 2 "memory_operand" ""))
18000    (use (match_operand:HI 3 "memory_operand" ""))
18001    (clobber (match_operand:DI 4 "memory_operand" ""))
18002    (clobber (match_scratch 5 ""))]
18003   "reload_completed"
18004   [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
18005               (use (match_dup 2))
18006               (use (match_dup 3))
18007               (clobber (match_dup 5))])]
18008   "")
18009
18010 (define_insn "fist<mode>2_ceil"
18011   [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
18012         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
18013          UNSPEC_FIST_CEIL))
18014    (use (match_operand:HI 2 "memory_operand" "m"))
18015    (use (match_operand:HI 3 "memory_operand" "m"))]
18016   "TARGET_USE_FANCY_MATH_387
18017    && flag_unsafe_math_optimizations"
18018   "* return output_fix_trunc (insn, operands, 0);"
18019   [(set_attr "type" "fistp")
18020    (set_attr "i387_cw" "ceil")
18021    (set_attr "mode" "<MODE>")])
18022
18023 (define_insn "fist<mode>2_ceil_with_temp"
18024   [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
18025         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
18026          UNSPEC_FIST_CEIL))
18027    (use (match_operand:HI 2 "memory_operand" "m,m"))
18028    (use (match_operand:HI 3 "memory_operand" "m,m"))
18029    (clobber (match_operand:X87MODEI12 4 "memory_operand" "=X,m"))]
18030   "TARGET_USE_FANCY_MATH_387
18031    && flag_unsafe_math_optimizations"
18032   "#"
18033   [(set_attr "type" "fistp")
18034    (set_attr "i387_cw" "ceil")
18035    (set_attr "mode" "<MODE>")])
18036
18037 (define_split
18038   [(set (match_operand:X87MODEI12 0 "register_operand" "")
18039         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18040          UNSPEC_FIST_CEIL))
18041    (use (match_operand:HI 2 "memory_operand" ""))
18042    (use (match_operand:HI 3 "memory_operand" ""))
18043    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
18044   "reload_completed"
18045   [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
18046                                   UNSPEC_FIST_CEIL))
18047               (use (match_dup 2))
18048               (use (match_dup 3))])
18049    (set (match_dup 0) (match_dup 4))]
18050   "")
18051
18052 (define_split
18053   [(set (match_operand:X87MODEI12 0 "memory_operand" "")
18054         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18055          UNSPEC_FIST_CEIL))
18056    (use (match_operand:HI 2 "memory_operand" ""))
18057    (use (match_operand:HI 3 "memory_operand" ""))
18058    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
18059   "reload_completed"
18060   [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
18061                                   UNSPEC_FIST_CEIL))
18062               (use (match_dup 2))
18063               (use (match_dup 3))])]
18064   "")
18065
18066 (define_expand "lceilxf<mode>2"
18067   [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
18068                    (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
18069                     UNSPEC_FIST_CEIL))
18070               (clobber (reg:CC FLAGS_REG))])]
18071   "TARGET_USE_FANCY_MATH_387
18072    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
18073    && flag_unsafe_math_optimizations"
18074   "")
18075
18076 (define_expand "lceil<mode>di2"
18077   [(match_operand:DI 0 "nonimmediate_operand" "")
18078    (match_operand:MODEF 1 "register_operand" "")]
18079   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH && TARGET_64BIT
18080    && !flag_trapping_math"
18081 {
18082   ix86_expand_lfloorceil (operand0, operand1, false);
18083   DONE;
18084 })
18085
18086 (define_expand "lceil<mode>si2"
18087   [(match_operand:SI 0 "nonimmediate_operand" "")
18088    (match_operand:MODEF 1 "register_operand" "")]
18089   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18090    && !flag_trapping_math"
18091 {
18092   ix86_expand_lfloorceil (operand0, operand1, false);
18093   DONE;
18094 })
18095
18096 ;; Rounding mode control word calculation could clobber FLAGS_REG.
18097 (define_insn_and_split "frndintxf2_trunc"
18098   [(set (match_operand:XF 0 "register_operand" "")
18099         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
18100          UNSPEC_FRNDINT_TRUNC))
18101    (clobber (reg:CC FLAGS_REG))]
18102   "TARGET_USE_FANCY_MATH_387
18103    && flag_unsafe_math_optimizations
18104    && !(reload_completed || reload_in_progress)"
18105   "#"
18106   "&& 1"
18107   [(const_int 0)]
18108 {
18109   ix86_optimize_mode_switching[I387_TRUNC] = 1;
18110
18111   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18112   operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
18113
18114   emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1],
18115                                         operands[2], operands[3]));
18116   DONE;
18117 }
18118   [(set_attr "type" "frndint")
18119    (set_attr "i387_cw" "trunc")
18120    (set_attr "mode" "XF")])
18121
18122 (define_insn "frndintxf2_trunc_i387"
18123   [(set (match_operand:XF 0 "register_operand" "=f")
18124         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
18125          UNSPEC_FRNDINT_TRUNC))
18126    (use (match_operand:HI 2 "memory_operand" "m"))
18127    (use (match_operand:HI 3 "memory_operand" "m"))]
18128   "TARGET_USE_FANCY_MATH_387
18129    && flag_unsafe_math_optimizations"
18130   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
18131   [(set_attr "type" "frndint")
18132    (set_attr "i387_cw" "trunc")
18133    (set_attr "mode" "XF")])
18134
18135 (define_expand "btruncxf2"
18136   [(use (match_operand:XF 0 "register_operand" ""))
18137    (use (match_operand:XF 1 "register_operand" ""))]
18138   "TARGET_USE_FANCY_MATH_387
18139    && flag_unsafe_math_optimizations && !optimize_size"
18140 {
18141   emit_insn (gen_frndintxf2_trunc (operands[0], operands[1]));
18142   DONE;
18143 })
18144
18145 (define_expand "btrunc<mode>2"
18146   [(use (match_operand:MODEF 0 "register_operand" ""))
18147    (use (match_operand:MODEF 1 "register_operand" ""))]
18148   "(TARGET_USE_FANCY_MATH_387
18149     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18150         || TARGET_MIX_SSE_I387)
18151     && flag_unsafe_math_optimizations && !optimize_size)
18152    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18153        && !flag_trapping_math
18154        && (TARGET_ROUND || !optimize_size))"
18155 {
18156   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18157       && !flag_trapping_math
18158       && (TARGET_ROUND || !optimize_size))
18159     {
18160       if (TARGET_ROUND)
18161         emit_insn (gen_sse4_1_round<mode>2
18162                    (operands[0], operands[1], GEN_INT (0x03)));
18163       else if (TARGET_64BIT || (<MODE>mode != DFmode))
18164         ix86_expand_trunc (operand0, operand1);
18165       else
18166         ix86_expand_truncdf_32 (operand0, operand1);
18167     }
18168   else
18169     {
18170       rtx op0 = gen_reg_rtx (XFmode);
18171       rtx op1 = gen_reg_rtx (XFmode);
18172
18173       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18174       emit_insn (gen_frndintxf2_trunc (op0, op1));
18175
18176       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18177     }
18178   DONE;
18179 })
18180
18181 ;; Rounding mode control word calculation could clobber FLAGS_REG.
18182 (define_insn_and_split "frndintxf2_mask_pm"
18183   [(set (match_operand:XF 0 "register_operand" "")
18184         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
18185          UNSPEC_FRNDINT_MASK_PM))
18186    (clobber (reg:CC FLAGS_REG))]
18187   "TARGET_USE_FANCY_MATH_387
18188    && flag_unsafe_math_optimizations
18189    && !(reload_completed || reload_in_progress)"
18190   "#"
18191   "&& 1"
18192   [(const_int 0)]
18193 {
18194   ix86_optimize_mode_switching[I387_MASK_PM] = 1;
18195
18196   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18197   operands[3] = assign_386_stack_local (HImode, SLOT_CW_MASK_PM);
18198
18199   emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1],
18200                                           operands[2], operands[3]));
18201   DONE;
18202 }
18203   [(set_attr "type" "frndint")
18204    (set_attr "i387_cw" "mask_pm")
18205    (set_attr "mode" "XF")])
18206
18207 (define_insn "frndintxf2_mask_pm_i387"
18208   [(set (match_operand:XF 0 "register_operand" "=f")
18209         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
18210          UNSPEC_FRNDINT_MASK_PM))
18211    (use (match_operand:HI 2 "memory_operand" "m"))
18212    (use (match_operand:HI 3 "memory_operand" "m"))]
18213   "TARGET_USE_FANCY_MATH_387
18214    && flag_unsafe_math_optimizations"
18215   "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2"
18216   [(set_attr "type" "frndint")
18217    (set_attr "i387_cw" "mask_pm")
18218    (set_attr "mode" "XF")])
18219
18220 (define_expand "nearbyintxf2"
18221   [(use (match_operand:XF 0 "register_operand" ""))
18222    (use (match_operand:XF 1 "register_operand" ""))]
18223   "TARGET_USE_FANCY_MATH_387
18224    && flag_unsafe_math_optimizations"
18225 {
18226   emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1]));
18227
18228   DONE;
18229 })
18230
18231 (define_expand "nearbyint<mode>2"
18232   [(use (match_operand:MODEF 0 "register_operand" ""))
18233    (use (match_operand:MODEF 1 "register_operand" ""))]
18234   "TARGET_USE_FANCY_MATH_387
18235    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18236        || TARGET_MIX_SSE_I387)
18237    && flag_unsafe_math_optimizations"
18238 {
18239   rtx op0 = gen_reg_rtx (XFmode);
18240   rtx op1 = gen_reg_rtx (XFmode);
18241
18242   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18243   emit_insn (gen_frndintxf2_mask_pm (op0, op1));
18244
18245   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18246   DONE;
18247 })
18248
18249 (define_insn "fxam<mode>2_i387"
18250   [(set (match_operand:HI 0 "register_operand" "=a")
18251         (unspec:HI
18252           [(match_operand:X87MODEF 1 "register_operand" "f")]
18253           UNSPEC_FXAM))]
18254   "TARGET_USE_FANCY_MATH_387"
18255   "fxam\n\tfnstsw\t%0"
18256   [(set_attr "type" "multi")
18257    (set_attr "unit" "i387")
18258    (set_attr "mode" "<MODE>")])
18259
18260 (define_expand "isinf<mode>2"
18261   [(use (match_operand:SI 0 "register_operand" ""))
18262    (use (match_operand:X87MODEF 1 "register_operand" ""))]
18263   "TARGET_USE_FANCY_MATH_387
18264    && TARGET_C99_FUNCTIONS
18265    && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
18266 {
18267   rtx mask = GEN_INT (0x45);
18268   rtx val = GEN_INT (0x05);
18269
18270   rtx cond;
18271
18272   rtx scratch = gen_reg_rtx (HImode);
18273   rtx res = gen_reg_rtx (QImode);
18274
18275   emit_insn (gen_fxam<mode>2_i387 (scratch, operands[1]));
18276   emit_insn (gen_andqi_ext_0 (scratch, scratch, mask));
18277   emit_insn (gen_cmpqi_ext_3 (scratch, val));
18278   cond = gen_rtx_fmt_ee (EQ, QImode,
18279                          gen_rtx_REG (CCmode, FLAGS_REG),
18280                          const0_rtx);
18281   emit_insn (gen_rtx_SET (VOIDmode, res, cond));
18282   emit_insn (gen_zero_extendqisi2 (operands[0], res));
18283   DONE;
18284 })
18285
18286 (define_expand "signbit<mode>2"
18287   [(use (match_operand:SI 0 "register_operand" ""))
18288    (use (match_operand:X87MODEF 1 "register_operand" ""))]
18289   "TARGET_USE_FANCY_MATH_387
18290    && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
18291 {
18292   rtx mask = GEN_INT (0x0200);
18293
18294   rtx scratch = gen_reg_rtx (HImode);
18295
18296   emit_insn (gen_fxam<mode>2_i387 (scratch, operands[1]));
18297   emit_insn (gen_andsi3 (operands[0], gen_lowpart (SImode, scratch), mask));
18298   DONE;
18299 })
18300 \f
18301 ;; Block operation instructions
18302
18303 (define_insn "cld"
18304   [(unspec_volatile [(const_int 0)] UNSPECV_CLD)]
18305   ""
18306   "cld"
18307   [(set_attr "length" "1")
18308    (set_attr "length_immediate" "0")
18309    (set_attr "modrm" "0")])
18310
18311 (define_expand "movmemsi"
18312   [(use (match_operand:BLK 0 "memory_operand" ""))
18313    (use (match_operand:BLK 1 "memory_operand" ""))
18314    (use (match_operand:SI 2 "nonmemory_operand" ""))
18315    (use (match_operand:SI 3 "const_int_operand" ""))
18316    (use (match_operand:SI 4 "const_int_operand" ""))
18317    (use (match_operand:SI 5 "const_int_operand" ""))]
18318   ""
18319 {
18320  if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3],
18321                          operands[4], operands[5]))
18322    DONE;
18323  else
18324    FAIL;
18325 })
18326
18327 (define_expand "movmemdi"
18328   [(use (match_operand:BLK 0 "memory_operand" ""))
18329    (use (match_operand:BLK 1 "memory_operand" ""))
18330    (use (match_operand:DI 2 "nonmemory_operand" ""))
18331    (use (match_operand:DI 3 "const_int_operand" ""))
18332    (use (match_operand:SI 4 "const_int_operand" ""))
18333    (use (match_operand:SI 5 "const_int_operand" ""))]
18334   "TARGET_64BIT"
18335 {
18336  if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3],
18337                          operands[4], operands[5]))
18338    DONE;
18339  else
18340    FAIL;
18341 })
18342
18343 ;; Most CPUs don't like single string operations
18344 ;; Handle this case here to simplify previous expander.
18345
18346 (define_expand "strmov"
18347   [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
18348    (set (match_operand 1 "memory_operand" "") (match_dup 4))
18349    (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
18350               (clobber (reg:CC FLAGS_REG))])
18351    (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
18352               (clobber (reg:CC FLAGS_REG))])]
18353   ""
18354 {
18355   rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
18356
18357   /* If .md ever supports :P for Pmode, these can be directly
18358      in the pattern above.  */
18359   operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
18360   operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
18361
18362   /* Can't use this if the user has appropriated esi or edi.  */
18363   if ((TARGET_SINGLE_STRINGOP || optimize_size)
18364       && !(fixed_regs[SI_REG] || fixed_regs[DI_REG]))
18365     {
18366       emit_insn (gen_strmov_singleop (operands[0], operands[1],
18367                                       operands[2], operands[3],
18368                                       operands[5], operands[6]));
18369       DONE;
18370     }
18371
18372   operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
18373 })
18374
18375 (define_expand "strmov_singleop"
18376   [(parallel [(set (match_operand 1 "memory_operand" "")
18377                    (match_operand 3 "memory_operand" ""))
18378               (set (match_operand 0 "register_operand" "")
18379                    (match_operand 4 "" ""))
18380               (set (match_operand 2 "register_operand" "")
18381                    (match_operand 5 "" ""))])]
18382   "TARGET_SINGLE_STRINGOP || optimize_size"
18383   "ix86_current_function_needs_cld = 1;")
18384
18385 (define_insn "*strmovdi_rex_1"
18386   [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
18387         (mem:DI (match_operand:DI 3 "register_operand" "1")))
18388    (set (match_operand:DI 0 "register_operand" "=D")
18389         (plus:DI (match_dup 2)
18390                  (const_int 8)))
18391    (set (match_operand:DI 1 "register_operand" "=S")
18392         (plus:DI (match_dup 3)
18393                  (const_int 8)))]
18394   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18395   "movsq"
18396   [(set_attr "type" "str")
18397    (set_attr "mode" "DI")
18398    (set_attr "memory" "both")])
18399
18400 (define_insn "*strmovsi_1"
18401   [(set (mem:SI (match_operand:SI 2 "register_operand" "0"))
18402         (mem:SI (match_operand:SI 3 "register_operand" "1")))
18403    (set (match_operand:SI 0 "register_operand" "=D")
18404         (plus:SI (match_dup 2)
18405                  (const_int 4)))
18406    (set (match_operand:SI 1 "register_operand" "=S")
18407         (plus:SI (match_dup 3)
18408                  (const_int 4)))]
18409   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18410   "movs{l|d}"
18411   [(set_attr "type" "str")
18412    (set_attr "mode" "SI")
18413    (set_attr "memory" "both")])
18414
18415 (define_insn "*strmovsi_rex_1"
18416   [(set (mem:SI (match_operand:DI 2 "register_operand" "0"))
18417         (mem:SI (match_operand:DI 3 "register_operand" "1")))
18418    (set (match_operand:DI 0 "register_operand" "=D")
18419         (plus:DI (match_dup 2)
18420                  (const_int 4)))
18421    (set (match_operand:DI 1 "register_operand" "=S")
18422         (plus:DI (match_dup 3)
18423                  (const_int 4)))]
18424   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18425   "movs{l|d}"
18426   [(set_attr "type" "str")
18427    (set_attr "mode" "SI")
18428    (set_attr "memory" "both")])
18429
18430 (define_insn "*strmovhi_1"
18431   [(set (mem:HI (match_operand:SI 2 "register_operand" "0"))
18432         (mem:HI (match_operand:SI 3 "register_operand" "1")))
18433    (set (match_operand:SI 0 "register_operand" "=D")
18434         (plus:SI (match_dup 2)
18435                  (const_int 2)))
18436    (set (match_operand:SI 1 "register_operand" "=S")
18437         (plus:SI (match_dup 3)
18438                  (const_int 2)))]
18439   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18440   "movsw"
18441   [(set_attr "type" "str")
18442    (set_attr "memory" "both")
18443    (set_attr "mode" "HI")])
18444
18445 (define_insn "*strmovhi_rex_1"
18446   [(set (mem:HI (match_operand:DI 2 "register_operand" "0"))
18447         (mem:HI (match_operand:DI 3 "register_operand" "1")))
18448    (set (match_operand:DI 0 "register_operand" "=D")
18449         (plus:DI (match_dup 2)
18450                  (const_int 2)))
18451    (set (match_operand:DI 1 "register_operand" "=S")
18452         (plus:DI (match_dup 3)
18453                  (const_int 2)))]
18454   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18455   "movsw"
18456   [(set_attr "type" "str")
18457    (set_attr "memory" "both")
18458    (set_attr "mode" "HI")])
18459
18460 (define_insn "*strmovqi_1"
18461   [(set (mem:QI (match_operand:SI 2 "register_operand" "0"))
18462         (mem:QI (match_operand:SI 3 "register_operand" "1")))
18463    (set (match_operand:SI 0 "register_operand" "=D")
18464         (plus:SI (match_dup 2)
18465                  (const_int 1)))
18466    (set (match_operand:SI 1 "register_operand" "=S")
18467         (plus:SI (match_dup 3)
18468                  (const_int 1)))]
18469   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18470   "movsb"
18471   [(set_attr "type" "str")
18472    (set_attr "memory" "both")
18473    (set_attr "mode" "QI")])
18474
18475 (define_insn "*strmovqi_rex_1"
18476   [(set (mem:QI (match_operand:DI 2 "register_operand" "0"))
18477         (mem:QI (match_operand:DI 3 "register_operand" "1")))
18478    (set (match_operand:DI 0 "register_operand" "=D")
18479         (plus:DI (match_dup 2)
18480                  (const_int 1)))
18481    (set (match_operand:DI 1 "register_operand" "=S")
18482         (plus:DI (match_dup 3)
18483                  (const_int 1)))]
18484   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18485   "movsb"
18486   [(set_attr "type" "str")
18487    (set_attr "memory" "both")
18488    (set_attr "mode" "QI")])
18489
18490 (define_expand "rep_mov"
18491   [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
18492               (set (match_operand 0 "register_operand" "")
18493                    (match_operand 5 "" ""))
18494               (set (match_operand 2 "register_operand" "")
18495                    (match_operand 6 "" ""))
18496               (set (match_operand 1 "memory_operand" "")
18497                    (match_operand 3 "memory_operand" ""))
18498               (use (match_dup 4))])]
18499   ""
18500   "ix86_current_function_needs_cld = 1;")
18501
18502 (define_insn "*rep_movdi_rex64"
18503   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
18504    (set (match_operand:DI 0 "register_operand" "=D")
18505         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
18506                             (const_int 3))
18507                  (match_operand:DI 3 "register_operand" "0")))
18508    (set (match_operand:DI 1 "register_operand" "=S")
18509         (plus:DI (ashift:DI (match_dup 5) (const_int 3))
18510                  (match_operand:DI 4 "register_operand" "1")))
18511    (set (mem:BLK (match_dup 3))
18512         (mem:BLK (match_dup 4)))
18513    (use (match_dup 5))]
18514   "TARGET_64BIT"
18515   "rep movsq"
18516   [(set_attr "type" "str")
18517    (set_attr "prefix_rep" "1")
18518    (set_attr "memory" "both")
18519    (set_attr "mode" "DI")])
18520
18521 (define_insn "*rep_movsi"
18522   [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
18523    (set (match_operand:SI 0 "register_operand" "=D")
18524         (plus:SI (ashift:SI (match_operand:SI 5 "register_operand" "2")
18525                             (const_int 2))
18526                  (match_operand:SI 3 "register_operand" "0")))
18527    (set (match_operand:SI 1 "register_operand" "=S")
18528         (plus:SI (ashift:SI (match_dup 5) (const_int 2))
18529                  (match_operand:SI 4 "register_operand" "1")))
18530    (set (mem:BLK (match_dup 3))
18531         (mem:BLK (match_dup 4)))
18532    (use (match_dup 5))]
18533   "!TARGET_64BIT"
18534   "rep movs{l|d}"
18535   [(set_attr "type" "str")
18536    (set_attr "prefix_rep" "1")
18537    (set_attr "memory" "both")
18538    (set_attr "mode" "SI")])
18539
18540 (define_insn "*rep_movsi_rex64"
18541   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
18542    (set (match_operand:DI 0 "register_operand" "=D")
18543         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
18544                             (const_int 2))
18545                  (match_operand:DI 3 "register_operand" "0")))
18546    (set (match_operand:DI 1 "register_operand" "=S")
18547         (plus:DI (ashift:DI (match_dup 5) (const_int 2))
18548                  (match_operand:DI 4 "register_operand" "1")))
18549    (set (mem:BLK (match_dup 3))
18550         (mem:BLK (match_dup 4)))
18551    (use (match_dup 5))]
18552   "TARGET_64BIT"
18553   "rep movs{l|d}"
18554   [(set_attr "type" "str")
18555    (set_attr "prefix_rep" "1")
18556    (set_attr "memory" "both")
18557    (set_attr "mode" "SI")])
18558
18559 (define_insn "*rep_movqi"
18560   [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
18561    (set (match_operand:SI 0 "register_operand" "=D")
18562         (plus:SI (match_operand:SI 3 "register_operand" "0")
18563                  (match_operand:SI 5 "register_operand" "2")))
18564    (set (match_operand:SI 1 "register_operand" "=S")
18565         (plus:SI (match_operand:SI 4 "register_operand" "1") (match_dup 5)))
18566    (set (mem:BLK (match_dup 3))
18567         (mem:BLK (match_dup 4)))
18568    (use (match_dup 5))]
18569   "!TARGET_64BIT"
18570   "rep movsb"
18571   [(set_attr "type" "str")
18572    (set_attr "prefix_rep" "1")
18573    (set_attr "memory" "both")
18574    (set_attr "mode" "SI")])
18575
18576 (define_insn "*rep_movqi_rex64"
18577   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
18578    (set (match_operand:DI 0 "register_operand" "=D")
18579         (plus:DI (match_operand:DI 3 "register_operand" "0")
18580                  (match_operand:DI 5 "register_operand" "2")))
18581    (set (match_operand:DI 1 "register_operand" "=S")
18582         (plus:DI (match_operand:DI 4 "register_operand" "1") (match_dup 5)))
18583    (set (mem:BLK (match_dup 3))
18584         (mem:BLK (match_dup 4)))
18585    (use (match_dup 5))]
18586   "TARGET_64BIT"
18587   "rep movsb"
18588   [(set_attr "type" "str")
18589    (set_attr "prefix_rep" "1")
18590    (set_attr "memory" "both")
18591    (set_attr "mode" "SI")])
18592
18593 (define_expand "setmemsi"
18594    [(use (match_operand:BLK 0 "memory_operand" ""))
18595     (use (match_operand:SI 1 "nonmemory_operand" ""))
18596     (use (match_operand 2 "const_int_operand" ""))
18597     (use (match_operand 3 "const_int_operand" ""))
18598     (use (match_operand:SI 4 "const_int_operand" ""))
18599     (use (match_operand:SI 5 "const_int_operand" ""))]
18600   ""
18601 {
18602  if (ix86_expand_setmem (operands[0], operands[1],
18603                          operands[2], operands[3],
18604                          operands[4], operands[5]))
18605    DONE;
18606  else
18607    FAIL;
18608 })
18609
18610 (define_expand "setmemdi"
18611    [(use (match_operand:BLK 0 "memory_operand" ""))
18612     (use (match_operand:DI 1 "nonmemory_operand" ""))
18613     (use (match_operand 2 "const_int_operand" ""))
18614     (use (match_operand 3 "const_int_operand" ""))
18615     (use (match_operand 4 "const_int_operand" ""))
18616     (use (match_operand 5 "const_int_operand" ""))]
18617   "TARGET_64BIT"
18618 {
18619  if (ix86_expand_setmem (operands[0], operands[1],
18620                          operands[2], operands[3],
18621                          operands[4], operands[5]))
18622    DONE;
18623  else
18624    FAIL;
18625 })
18626
18627 ;; Most CPUs don't like single string operations
18628 ;; Handle this case here to simplify previous expander.
18629
18630 (define_expand "strset"
18631   [(set (match_operand 1 "memory_operand" "")
18632         (match_operand 2 "register_operand" ""))
18633    (parallel [(set (match_operand 0 "register_operand" "")
18634                    (match_dup 3))
18635               (clobber (reg:CC FLAGS_REG))])]
18636   ""
18637 {
18638   if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
18639     operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
18640
18641   /* If .md ever supports :P for Pmode, this can be directly
18642      in the pattern above.  */
18643   operands[3] = gen_rtx_PLUS (Pmode, operands[0],
18644                               GEN_INT (GET_MODE_SIZE (GET_MODE
18645                                                       (operands[2]))));
18646   if (TARGET_SINGLE_STRINGOP || optimize_size)
18647     {
18648       emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
18649                                       operands[3]));
18650       DONE;
18651     }
18652 })
18653
18654 (define_expand "strset_singleop"
18655   [(parallel [(set (match_operand 1 "memory_operand" "")
18656                    (match_operand 2 "register_operand" ""))
18657               (set (match_operand 0 "register_operand" "")
18658                    (match_operand 3 "" ""))])]
18659   "TARGET_SINGLE_STRINGOP || optimize_size"
18660   "ix86_current_function_needs_cld = 1;")
18661
18662 (define_insn "*strsetdi_rex_1"
18663   [(set (mem:DI (match_operand:DI 1 "register_operand" "0"))
18664         (match_operand:DI 2 "register_operand" "a"))
18665    (set (match_operand:DI 0 "register_operand" "=D")
18666         (plus:DI (match_dup 1)
18667                  (const_int 8)))]
18668   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18669   "stosq"
18670   [(set_attr "type" "str")
18671    (set_attr "memory" "store")
18672    (set_attr "mode" "DI")])
18673
18674 (define_insn "*strsetsi_1"
18675   [(set (mem:SI (match_operand:SI 1 "register_operand" "0"))
18676         (match_operand:SI 2 "register_operand" "a"))
18677    (set (match_operand:SI 0 "register_operand" "=D")
18678         (plus:SI (match_dup 1)
18679                  (const_int 4)))]
18680   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18681   "stos{l|d}"
18682   [(set_attr "type" "str")
18683    (set_attr "memory" "store")
18684    (set_attr "mode" "SI")])
18685
18686 (define_insn "*strsetsi_rex_1"
18687   [(set (mem:SI (match_operand:DI 1 "register_operand" "0"))
18688         (match_operand:SI 2 "register_operand" "a"))
18689    (set (match_operand:DI 0 "register_operand" "=D")
18690         (plus:DI (match_dup 1)
18691                  (const_int 4)))]
18692   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18693   "stos{l|d}"
18694   [(set_attr "type" "str")
18695    (set_attr "memory" "store")
18696    (set_attr "mode" "SI")])
18697
18698 (define_insn "*strsethi_1"
18699   [(set (mem:HI (match_operand:SI 1 "register_operand" "0"))
18700         (match_operand:HI 2 "register_operand" "a"))
18701    (set (match_operand:SI 0 "register_operand" "=D")
18702         (plus:SI (match_dup 1)
18703                  (const_int 2)))]
18704   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18705   "stosw"
18706   [(set_attr "type" "str")
18707    (set_attr "memory" "store")
18708    (set_attr "mode" "HI")])
18709
18710 (define_insn "*strsethi_rex_1"
18711   [(set (mem:HI (match_operand:DI 1 "register_operand" "0"))
18712         (match_operand:HI 2 "register_operand" "a"))
18713    (set (match_operand:DI 0 "register_operand" "=D")
18714         (plus:DI (match_dup 1)
18715                  (const_int 2)))]
18716   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18717   "stosw"
18718   [(set_attr "type" "str")
18719    (set_attr "memory" "store")
18720    (set_attr "mode" "HI")])
18721
18722 (define_insn "*strsetqi_1"
18723   [(set (mem:QI (match_operand:SI 1 "register_operand" "0"))
18724         (match_operand:QI 2 "register_operand" "a"))
18725    (set (match_operand:SI 0 "register_operand" "=D")
18726         (plus:SI (match_dup 1)
18727                  (const_int 1)))]
18728   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18729   "stosb"
18730   [(set_attr "type" "str")
18731    (set_attr "memory" "store")
18732    (set_attr "mode" "QI")])
18733
18734 (define_insn "*strsetqi_rex_1"
18735   [(set (mem:QI (match_operand:DI 1 "register_operand" "0"))
18736         (match_operand:QI 2 "register_operand" "a"))
18737    (set (match_operand:DI 0 "register_operand" "=D")
18738         (plus:DI (match_dup 1)
18739                  (const_int 1)))]
18740   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18741   "stosb"
18742   [(set_attr "type" "str")
18743    (set_attr "memory" "store")
18744    (set_attr "mode" "QI")])
18745
18746 (define_expand "rep_stos"
18747   [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
18748               (set (match_operand 0 "register_operand" "")
18749                    (match_operand 4 "" ""))
18750               (set (match_operand 2 "memory_operand" "") (const_int 0))
18751               (use (match_operand 3 "register_operand" ""))
18752               (use (match_dup 1))])]
18753   ""
18754   "ix86_current_function_needs_cld = 1;")
18755
18756 (define_insn "*rep_stosdi_rex64"
18757   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
18758    (set (match_operand:DI 0 "register_operand" "=D")
18759         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
18760                             (const_int 3))
18761                  (match_operand:DI 3 "register_operand" "0")))
18762    (set (mem:BLK (match_dup 3))
18763         (const_int 0))
18764    (use (match_operand:DI 2 "register_operand" "a"))
18765    (use (match_dup 4))]
18766   "TARGET_64BIT"
18767   "rep stosq"
18768   [(set_attr "type" "str")
18769    (set_attr "prefix_rep" "1")
18770    (set_attr "memory" "store")
18771    (set_attr "mode" "DI")])
18772
18773 (define_insn "*rep_stossi"
18774   [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
18775    (set (match_operand:SI 0 "register_operand" "=D")
18776         (plus:SI (ashift:SI (match_operand:SI 4 "register_operand" "1")
18777                             (const_int 2))
18778                  (match_operand:SI 3 "register_operand" "0")))
18779    (set (mem:BLK (match_dup 3))
18780         (const_int 0))
18781    (use (match_operand:SI 2 "register_operand" "a"))
18782    (use (match_dup 4))]
18783   "!TARGET_64BIT"
18784   "rep stos{l|d}"
18785   [(set_attr "type" "str")
18786    (set_attr "prefix_rep" "1")
18787    (set_attr "memory" "store")
18788    (set_attr "mode" "SI")])
18789
18790 (define_insn "*rep_stossi_rex64"
18791   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
18792    (set (match_operand:DI 0 "register_operand" "=D")
18793         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
18794                             (const_int 2))
18795                  (match_operand:DI 3 "register_operand" "0")))
18796    (set (mem:BLK (match_dup 3))
18797         (const_int 0))
18798    (use (match_operand:SI 2 "register_operand" "a"))
18799    (use (match_dup 4))]
18800   "TARGET_64BIT"
18801   "rep stos{l|d}"
18802   [(set_attr "type" "str")
18803    (set_attr "prefix_rep" "1")
18804    (set_attr "memory" "store")
18805    (set_attr "mode" "SI")])
18806
18807 (define_insn "*rep_stosqi"
18808   [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
18809    (set (match_operand:SI 0 "register_operand" "=D")
18810         (plus:SI (match_operand:SI 3 "register_operand" "0")
18811                  (match_operand:SI 4 "register_operand" "1")))
18812    (set (mem:BLK (match_dup 3))
18813         (const_int 0))
18814    (use (match_operand:QI 2 "register_operand" "a"))
18815    (use (match_dup 4))]
18816   "!TARGET_64BIT"
18817   "rep stosb"
18818   [(set_attr "type" "str")
18819    (set_attr "prefix_rep" "1")
18820    (set_attr "memory" "store")
18821    (set_attr "mode" "QI")])
18822
18823 (define_insn "*rep_stosqi_rex64"
18824   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
18825    (set (match_operand:DI 0 "register_operand" "=D")
18826         (plus:DI (match_operand:DI 3 "register_operand" "0")
18827                  (match_operand:DI 4 "register_operand" "1")))
18828    (set (mem:BLK (match_dup 3))
18829         (const_int 0))
18830    (use (match_operand:QI 2 "register_operand" "a"))
18831    (use (match_dup 4))]
18832   "TARGET_64BIT"
18833   "rep stosb"
18834   [(set_attr "type" "str")
18835    (set_attr "prefix_rep" "1")
18836    (set_attr "memory" "store")
18837    (set_attr "mode" "QI")])
18838
18839 (define_expand "cmpstrnsi"
18840   [(set (match_operand:SI 0 "register_operand" "")
18841         (compare:SI (match_operand:BLK 1 "general_operand" "")
18842                     (match_operand:BLK 2 "general_operand" "")))
18843    (use (match_operand 3 "general_operand" ""))
18844    (use (match_operand 4 "immediate_operand" ""))]
18845   "! optimize_size || TARGET_INLINE_ALL_STRINGOPS"
18846 {
18847   rtx addr1, addr2, out, outlow, count, countreg, align;
18848
18849   /* Can't use this if the user has appropriated esi or edi.  */
18850   if (fixed_regs[SI_REG] || fixed_regs[DI_REG])
18851     FAIL;
18852
18853   out = operands[0];
18854   if (!REG_P (out))
18855     out = gen_reg_rtx (SImode);
18856
18857   addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
18858   addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
18859   if (addr1 != XEXP (operands[1], 0))
18860     operands[1] = replace_equiv_address_nv (operands[1], addr1);
18861   if (addr2 != XEXP (operands[2], 0))
18862     operands[2] = replace_equiv_address_nv (operands[2], addr2);
18863
18864   count = operands[3];
18865   countreg = ix86_zero_extend_to_Pmode (count);
18866
18867   /* %%% Iff we are testing strict equality, we can use known alignment
18868      to good advantage.  This may be possible with combine, particularly
18869      once cc0 is dead.  */
18870   align = operands[4];
18871
18872   if (CONST_INT_P (count))
18873     {
18874       if (INTVAL (count) == 0)
18875         {
18876           emit_move_insn (operands[0], const0_rtx);
18877           DONE;
18878         }
18879       emit_insn (gen_cmpstrnqi_nz_1 (addr1, addr2, countreg, align,
18880                                      operands[1], operands[2]));
18881     }
18882   else
18883     {
18884       if (TARGET_64BIT)
18885         emit_insn (gen_cmpdi_1_rex64 (countreg, countreg));
18886       else
18887         emit_insn (gen_cmpsi_1 (countreg, countreg));
18888       emit_insn (gen_cmpstrnqi_1 (addr1, addr2, countreg, align,
18889                                   operands[1], operands[2]));
18890     }
18891
18892   outlow = gen_lowpart (QImode, out);
18893   emit_insn (gen_cmpintqi (outlow));
18894   emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
18895
18896   if (operands[0] != out)
18897     emit_move_insn (operands[0], out);
18898
18899   DONE;
18900 })
18901
18902 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
18903
18904 (define_expand "cmpintqi"
18905   [(set (match_dup 1)
18906         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
18907    (set (match_dup 2)
18908         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
18909    (parallel [(set (match_operand:QI 0 "register_operand" "")
18910                    (minus:QI (match_dup 1)
18911                              (match_dup 2)))
18912               (clobber (reg:CC FLAGS_REG))])]
18913   ""
18914   "operands[1] = gen_reg_rtx (QImode);
18915    operands[2] = gen_reg_rtx (QImode);")
18916
18917 ;; memcmp recognizers.  The `cmpsb' opcode does nothing if the count is
18918 ;; zero.  Emit extra code to make sure that a zero-length compare is EQ.
18919
18920 (define_expand "cmpstrnqi_nz_1"
18921   [(parallel [(set (reg:CC FLAGS_REG)
18922                    (compare:CC (match_operand 4 "memory_operand" "")
18923                                (match_operand 5 "memory_operand" "")))
18924               (use (match_operand 2 "register_operand" ""))
18925               (use (match_operand:SI 3 "immediate_operand" ""))
18926               (clobber (match_operand 0 "register_operand" ""))
18927               (clobber (match_operand 1 "register_operand" ""))
18928               (clobber (match_dup 2))])]
18929   ""
18930   "ix86_current_function_needs_cld = 1;")
18931
18932 (define_insn "*cmpstrnqi_nz_1"
18933   [(set (reg:CC FLAGS_REG)
18934         (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
18935                     (mem:BLK (match_operand:SI 5 "register_operand" "1"))))
18936    (use (match_operand:SI 6 "register_operand" "2"))
18937    (use (match_operand:SI 3 "immediate_operand" "i"))
18938    (clobber (match_operand:SI 0 "register_operand" "=S"))
18939    (clobber (match_operand:SI 1 "register_operand" "=D"))
18940    (clobber (match_operand:SI 2 "register_operand" "=c"))]
18941   "!TARGET_64BIT"
18942   "repz cmpsb"
18943   [(set_attr "type" "str")
18944    (set_attr "mode" "QI")
18945    (set_attr "prefix_rep" "1")])
18946
18947 (define_insn "*cmpstrnqi_nz_rex_1"
18948   [(set (reg:CC FLAGS_REG)
18949         (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
18950                     (mem:BLK (match_operand:DI 5 "register_operand" "1"))))
18951    (use (match_operand:DI 6 "register_operand" "2"))
18952    (use (match_operand:SI 3 "immediate_operand" "i"))
18953    (clobber (match_operand:DI 0 "register_operand" "=S"))
18954    (clobber (match_operand:DI 1 "register_operand" "=D"))
18955    (clobber (match_operand:DI 2 "register_operand" "=c"))]
18956   "TARGET_64BIT"
18957   "repz cmpsb"
18958   [(set_attr "type" "str")
18959    (set_attr "mode" "QI")
18960    (set_attr "prefix_rep" "1")])
18961
18962 ;; The same, but the count is not known to not be zero.
18963
18964 (define_expand "cmpstrnqi_1"
18965   [(parallel [(set (reg:CC FLAGS_REG)
18966                 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
18967                                      (const_int 0))
18968                   (compare:CC (match_operand 4 "memory_operand" "")
18969                               (match_operand 5 "memory_operand" ""))
18970                   (const_int 0)))
18971               (use (match_operand:SI 3 "immediate_operand" ""))
18972               (use (reg:CC FLAGS_REG))
18973               (clobber (match_operand 0 "register_operand" ""))
18974               (clobber (match_operand 1 "register_operand" ""))
18975               (clobber (match_dup 2))])]
18976   ""
18977   "ix86_current_function_needs_cld = 1;")
18978
18979 (define_insn "*cmpstrnqi_1"
18980   [(set (reg:CC FLAGS_REG)
18981         (if_then_else:CC (ne (match_operand:SI 6 "register_operand" "2")
18982                              (const_int 0))
18983           (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
18984                       (mem:BLK (match_operand:SI 5 "register_operand" "1")))
18985           (const_int 0)))
18986    (use (match_operand:SI 3 "immediate_operand" "i"))
18987    (use (reg:CC FLAGS_REG))
18988    (clobber (match_operand:SI 0 "register_operand" "=S"))
18989    (clobber (match_operand:SI 1 "register_operand" "=D"))
18990    (clobber (match_operand:SI 2 "register_operand" "=c"))]
18991   "!TARGET_64BIT"
18992   "repz cmpsb"
18993   [(set_attr "type" "str")
18994    (set_attr "mode" "QI")
18995    (set_attr "prefix_rep" "1")])
18996
18997 (define_insn "*cmpstrnqi_rex_1"
18998   [(set (reg:CC FLAGS_REG)
18999         (if_then_else:CC (ne (match_operand:DI 6 "register_operand" "2")
19000                              (const_int 0))
19001           (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
19002                       (mem:BLK (match_operand:DI 5 "register_operand" "1")))
19003           (const_int 0)))
19004    (use (match_operand:SI 3 "immediate_operand" "i"))
19005    (use (reg:CC FLAGS_REG))
19006    (clobber (match_operand:DI 0 "register_operand" "=S"))
19007    (clobber (match_operand:DI 1 "register_operand" "=D"))
19008    (clobber (match_operand:DI 2 "register_operand" "=c"))]
19009   "TARGET_64BIT"
19010   "repz cmpsb"
19011   [(set_attr "type" "str")
19012    (set_attr "mode" "QI")
19013    (set_attr "prefix_rep" "1")])
19014
19015 (define_expand "strlensi"
19016   [(set (match_operand:SI 0 "register_operand" "")
19017         (unspec:SI [(match_operand:BLK 1 "general_operand" "")
19018                     (match_operand:QI 2 "immediate_operand" "")
19019                     (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
19020   ""
19021 {
19022  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
19023    DONE;
19024  else
19025    FAIL;
19026 })
19027
19028 (define_expand "strlendi"
19029   [(set (match_operand:DI 0 "register_operand" "")
19030         (unspec:DI [(match_operand:BLK 1 "general_operand" "")
19031                     (match_operand:QI 2 "immediate_operand" "")
19032                     (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
19033   ""
19034 {
19035  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
19036    DONE;
19037  else
19038    FAIL;
19039 })
19040
19041 (define_expand "strlenqi_1"
19042   [(parallel [(set (match_operand 0 "register_operand" "") (match_operand 2 "" ""))
19043               (clobber (match_operand 1 "register_operand" ""))
19044               (clobber (reg:CC FLAGS_REG))])]
19045   ""
19046   "ix86_current_function_needs_cld = 1;")
19047
19048 (define_insn "*strlenqi_1"
19049   [(set (match_operand:SI 0 "register_operand" "=&c")
19050         (unspec:SI [(mem:BLK (match_operand:SI 5 "register_operand" "1"))
19051                     (match_operand:QI 2 "register_operand" "a")
19052                     (match_operand:SI 3 "immediate_operand" "i")
19053                     (match_operand:SI 4 "register_operand" "0")] UNSPEC_SCAS))
19054    (clobber (match_operand:SI 1 "register_operand" "=D"))
19055    (clobber (reg:CC FLAGS_REG))]
19056   "!TARGET_64BIT"
19057   "repnz scasb"
19058   [(set_attr "type" "str")
19059    (set_attr "mode" "QI")
19060    (set_attr "prefix_rep" "1")])
19061
19062 (define_insn "*strlenqi_rex_1"
19063   [(set (match_operand:DI 0 "register_operand" "=&c")
19064         (unspec:DI [(mem:BLK (match_operand:DI 5 "register_operand" "1"))
19065                     (match_operand:QI 2 "register_operand" "a")
19066                     (match_operand:DI 3 "immediate_operand" "i")
19067                     (match_operand:DI 4 "register_operand" "0")] UNSPEC_SCAS))
19068    (clobber (match_operand:DI 1 "register_operand" "=D"))
19069    (clobber (reg:CC FLAGS_REG))]
19070   "TARGET_64BIT"
19071   "repnz scasb"
19072   [(set_attr "type" "str")
19073    (set_attr "mode" "QI")
19074    (set_attr "prefix_rep" "1")])
19075
19076 ;; Peephole optimizations to clean up after cmpstrn*.  This should be
19077 ;; handled in combine, but it is not currently up to the task.
19078 ;; When used for their truth value, the cmpstrn* expanders generate
19079 ;; code like this:
19080 ;;
19081 ;;   repz cmpsb
19082 ;;   seta       %al
19083 ;;   setb       %dl
19084 ;;   cmpb       %al, %dl
19085 ;;   jcc        label
19086 ;;
19087 ;; The intermediate three instructions are unnecessary.
19088
19089 ;; This one handles cmpstrn*_nz_1...
19090 (define_peephole2
19091   [(parallel[
19092      (set (reg:CC FLAGS_REG)
19093           (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
19094                       (mem:BLK (match_operand 5 "register_operand" ""))))
19095      (use (match_operand 6 "register_operand" ""))
19096      (use (match_operand:SI 3 "immediate_operand" ""))
19097      (clobber (match_operand 0 "register_operand" ""))
19098      (clobber (match_operand 1 "register_operand" ""))
19099      (clobber (match_operand 2 "register_operand" ""))])
19100    (set (match_operand:QI 7 "register_operand" "")
19101         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
19102    (set (match_operand:QI 8 "register_operand" "")
19103         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
19104    (set (reg FLAGS_REG)
19105         (compare (match_dup 7) (match_dup 8)))
19106   ]
19107   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
19108   [(parallel[
19109      (set (reg:CC FLAGS_REG)
19110           (compare:CC (mem:BLK (match_dup 4))
19111                       (mem:BLK (match_dup 5))))
19112      (use (match_dup 6))
19113      (use (match_dup 3))
19114      (clobber (match_dup 0))
19115      (clobber (match_dup 1))
19116      (clobber (match_dup 2))])]
19117   "")
19118
19119 ;; ...and this one handles cmpstrn*_1.
19120 (define_peephole2
19121   [(parallel[
19122      (set (reg:CC FLAGS_REG)
19123           (if_then_else:CC (ne (match_operand 6 "register_operand" "")
19124                                (const_int 0))
19125             (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
19126                         (mem:BLK (match_operand 5 "register_operand" "")))
19127             (const_int 0)))
19128      (use (match_operand:SI 3 "immediate_operand" ""))
19129      (use (reg:CC FLAGS_REG))
19130      (clobber (match_operand 0 "register_operand" ""))
19131      (clobber (match_operand 1 "register_operand" ""))
19132      (clobber (match_operand 2 "register_operand" ""))])
19133    (set (match_operand:QI 7 "register_operand" "")
19134         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
19135    (set (match_operand:QI 8 "register_operand" "")
19136         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
19137    (set (reg FLAGS_REG)
19138         (compare (match_dup 7) (match_dup 8)))
19139   ]
19140   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
19141   [(parallel[
19142      (set (reg:CC FLAGS_REG)
19143           (if_then_else:CC (ne (match_dup 6)
19144                                (const_int 0))
19145             (compare:CC (mem:BLK (match_dup 4))
19146                         (mem:BLK (match_dup 5)))
19147             (const_int 0)))
19148      (use (match_dup 3))
19149      (use (reg:CC FLAGS_REG))
19150      (clobber (match_dup 0))
19151      (clobber (match_dup 1))
19152      (clobber (match_dup 2))])]
19153   "")
19154
19155
19156 \f
19157 ;; Conditional move instructions.
19158
19159 (define_expand "movdicc"
19160   [(set (match_operand:DI 0 "register_operand" "")
19161         (if_then_else:DI (match_operand 1 "comparison_operator" "")
19162                          (match_operand:DI 2 "general_operand" "")
19163                          (match_operand:DI 3 "general_operand" "")))]
19164   "TARGET_64BIT"
19165   "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
19166
19167 (define_insn "x86_movdicc_0_m1_rex64"
19168   [(set (match_operand:DI 0 "register_operand" "=r")
19169         (if_then_else:DI (match_operand 1 "ix86_carry_flag_operator" "")
19170           (const_int -1)
19171           (const_int 0)))
19172    (clobber (reg:CC FLAGS_REG))]
19173   "TARGET_64BIT"
19174   "sbb{q}\t%0, %0"
19175   ; Since we don't have the proper number of operands for an alu insn,
19176   ; fill in all the blanks.
19177   [(set_attr "type" "alu")
19178    (set_attr "pent_pair" "pu")
19179    (set_attr "memory" "none")
19180    (set_attr "imm_disp" "false")
19181    (set_attr "mode" "DI")
19182    (set_attr "length_immediate" "0")])
19183
19184 (define_insn "*x86_movdicc_0_m1_se"
19185   [(set (match_operand:DI 0 "register_operand" "=r")
19186         (sign_extract:DI (match_operand 1 "ix86_carry_flag_operator" "")
19187                          (const_int 1)
19188                          (const_int 0)))
19189    (clobber (reg:CC FLAGS_REG))]
19190   ""
19191   "sbb{q}\t%0, %0"
19192   [(set_attr "type" "alu")
19193    (set_attr "pent_pair" "pu")
19194    (set_attr "memory" "none")
19195    (set_attr "imm_disp" "false")
19196    (set_attr "mode" "DI")
19197    (set_attr "length_immediate" "0")])
19198
19199 (define_insn "*movdicc_c_rex64"
19200   [(set (match_operand:DI 0 "register_operand" "=r,r")
19201         (if_then_else:DI (match_operator 1 "ix86_comparison_operator"
19202                                 [(reg FLAGS_REG) (const_int 0)])
19203                       (match_operand:DI 2 "nonimmediate_operand" "rm,0")
19204                       (match_operand:DI 3 "nonimmediate_operand" "0,rm")))]
19205   "TARGET_64BIT && TARGET_CMOVE
19206    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19207   "@
19208    cmov%O2%C1\t{%2, %0|%0, %2}
19209    cmov%O2%c1\t{%3, %0|%0, %3}"
19210   [(set_attr "type" "icmov")
19211    (set_attr "mode" "DI")])
19212
19213 (define_expand "movsicc"
19214   [(set (match_operand:SI 0 "register_operand" "")
19215         (if_then_else:SI (match_operand 1 "comparison_operator" "")
19216                          (match_operand:SI 2 "general_operand" "")
19217                          (match_operand:SI 3 "general_operand" "")))]
19218   ""
19219   "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
19220
19221 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
19222 ;; the register first winds up with `sbbl $0,reg', which is also weird.
19223 ;; So just document what we're doing explicitly.
19224
19225 (define_insn "x86_movsicc_0_m1"
19226   [(set (match_operand:SI 0 "register_operand" "=r")
19227         (if_then_else:SI (match_operand 1 "ix86_carry_flag_operator" "")
19228           (const_int -1)
19229           (const_int 0)))
19230    (clobber (reg:CC FLAGS_REG))]
19231   ""
19232   "sbb{l}\t%0, %0"
19233   ; Since we don't have the proper number of operands for an alu insn,
19234   ; fill in all the blanks.
19235   [(set_attr "type" "alu")
19236    (set_attr "pent_pair" "pu")
19237    (set_attr "memory" "none")
19238    (set_attr "imm_disp" "false")
19239    (set_attr "mode" "SI")
19240    (set_attr "length_immediate" "0")])
19241
19242 (define_insn "*x86_movsicc_0_m1_se"
19243   [(set (match_operand:SI 0 "register_operand" "=r")
19244         (sign_extract:SI (match_operand 1 "ix86_carry_flag_operator" "")
19245                          (const_int 1)
19246                          (const_int 0)))
19247    (clobber (reg:CC FLAGS_REG))]
19248   ""
19249   "sbb{l}\t%0, %0"
19250   [(set_attr "type" "alu")
19251    (set_attr "pent_pair" "pu")
19252    (set_attr "memory" "none")
19253    (set_attr "imm_disp" "false")
19254    (set_attr "mode" "SI")
19255    (set_attr "length_immediate" "0")])
19256
19257 (define_insn "*movsicc_noc"
19258   [(set (match_operand:SI 0 "register_operand" "=r,r")
19259         (if_then_else:SI (match_operator 1 "ix86_comparison_operator"
19260                                 [(reg FLAGS_REG) (const_int 0)])
19261                       (match_operand:SI 2 "nonimmediate_operand" "rm,0")
19262                       (match_operand:SI 3 "nonimmediate_operand" "0,rm")))]
19263   "TARGET_CMOVE
19264    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19265   "@
19266    cmov%O2%C1\t{%2, %0|%0, %2}
19267    cmov%O2%c1\t{%3, %0|%0, %3}"
19268   [(set_attr "type" "icmov")
19269    (set_attr "mode" "SI")])
19270
19271 (define_expand "movhicc"
19272   [(set (match_operand:HI 0 "register_operand" "")
19273         (if_then_else:HI (match_operand 1 "comparison_operator" "")
19274                          (match_operand:HI 2 "general_operand" "")
19275                          (match_operand:HI 3 "general_operand" "")))]
19276   "TARGET_HIMODE_MATH"
19277   "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
19278
19279 (define_insn "*movhicc_noc"
19280   [(set (match_operand:HI 0 "register_operand" "=r,r")
19281         (if_then_else:HI (match_operator 1 "ix86_comparison_operator"
19282                                 [(reg FLAGS_REG) (const_int 0)])
19283                       (match_operand:HI 2 "nonimmediate_operand" "rm,0")
19284                       (match_operand:HI 3 "nonimmediate_operand" "0,rm")))]
19285   "TARGET_CMOVE
19286    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19287   "@
19288    cmov%O2%C1\t{%2, %0|%0, %2}
19289    cmov%O2%c1\t{%3, %0|%0, %3}"
19290   [(set_attr "type" "icmov")
19291    (set_attr "mode" "HI")])
19292
19293 (define_expand "movqicc"
19294   [(set (match_operand:QI 0 "register_operand" "")
19295         (if_then_else:QI (match_operand 1 "comparison_operator" "")
19296                          (match_operand:QI 2 "general_operand" "")
19297                          (match_operand:QI 3 "general_operand" "")))]
19298   "TARGET_QIMODE_MATH"
19299   "if (ix86_expand_int_movcc (operands)) DONE; else FAIL;")
19300
19301 (define_insn_and_split "*movqicc_noc"
19302   [(set (match_operand:QI 0 "register_operand" "=r,r")
19303         (if_then_else:QI (match_operator 1 "ix86_comparison_operator"
19304                                 [(match_operand 4 "flags_reg_operand" "")
19305                                  (const_int 0)])
19306                       (match_operand:QI 2 "register_operand" "r,0")
19307                       (match_operand:QI 3 "register_operand" "0,r")))]
19308   "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
19309   "#"
19310   "&& reload_completed"
19311   [(set (match_dup 0)
19312         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
19313                       (match_dup 2)
19314                       (match_dup 3)))]
19315   "operands[0] = gen_lowpart (SImode, operands[0]);
19316    operands[2] = gen_lowpart (SImode, operands[2]);
19317    operands[3] = gen_lowpart (SImode, operands[3]);"
19318   [(set_attr "type" "icmov")
19319    (set_attr "mode" "SI")])
19320
19321 (define_expand "mov<mode>cc"
19322   [(set (match_operand:X87MODEF 0 "register_operand" "")
19323         (if_then_else:X87MODEF
19324           (match_operand 1 "comparison_operator" "")
19325           (match_operand:X87MODEF 2 "register_operand" "")
19326           (match_operand:X87MODEF 3 "register_operand" "")))]
19327   "(TARGET_80387 && TARGET_CMOVE)
19328    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
19329   "if (ix86_expand_fp_movcc (operands)) DONE; else FAIL;")
19330
19331 (define_insn "*movsfcc_1_387"
19332   [(set (match_operand:SF 0 "register_operand" "=f,f,r,r")
19333         (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
19334                                 [(reg FLAGS_REG) (const_int 0)])
19335                       (match_operand:SF 2 "nonimmediate_operand" "f,0,rm,0")
19336                       (match_operand:SF 3 "nonimmediate_operand" "0,f,0,rm")))]
19337   "TARGET_80387 && TARGET_CMOVE
19338    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19339   "@
19340    fcmov%F1\t{%2, %0|%0, %2}
19341    fcmov%f1\t{%3, %0|%0, %3}
19342    cmov%O2%C1\t{%2, %0|%0, %2}
19343    cmov%O2%c1\t{%3, %0|%0, %3}"
19344   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
19345    (set_attr "mode" "SF,SF,SI,SI")])
19346
19347 (define_insn "*movdfcc_1"
19348   [(set (match_operand:DF 0 "register_operand" "=f,f,&r,&r")
19349         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
19350                                 [(reg FLAGS_REG) (const_int 0)])
19351                       (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
19352                       (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
19353   "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
19354    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19355   "@
19356    fcmov%F1\t{%2, %0|%0, %2}
19357    fcmov%f1\t{%3, %0|%0, %3}
19358    #
19359    #"
19360   [(set_attr "type" "fcmov,fcmov,multi,multi")
19361    (set_attr "mode" "DF")])
19362
19363 (define_insn "*movdfcc_1_rex64"
19364   [(set (match_operand:DF 0 "register_operand" "=f,f,r,r")
19365         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
19366                                 [(reg FLAGS_REG) (const_int 0)])
19367                       (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
19368                       (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
19369   "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
19370    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19371   "@
19372    fcmov%F1\t{%2, %0|%0, %2}
19373    fcmov%f1\t{%3, %0|%0, %3}
19374    cmov%O2%C1\t{%2, %0|%0, %2}
19375    cmov%O2%c1\t{%3, %0|%0, %3}"
19376   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
19377    (set_attr "mode" "DF")])
19378
19379 (define_split
19380   [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand" "")
19381         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
19382                                 [(match_operand 4 "flags_reg_operand" "")
19383                                  (const_int 0)])
19384                       (match_operand:DF 2 "nonimmediate_operand" "")
19385                       (match_operand:DF 3 "nonimmediate_operand" "")))]
19386   "!TARGET_64BIT && reload_completed"
19387   [(set (match_dup 2)
19388         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
19389                       (match_dup 5)
19390                       (match_dup 6)))
19391    (set (match_dup 3)
19392         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
19393                       (match_dup 7)
19394                       (match_dup 8)))]
19395   "split_di (&operands[2], 2, &operands[5], &operands[7]);
19396    split_di (&operands[0], 1, &operands[2], &operands[3]);")
19397
19398 (define_insn "*movxfcc_1"
19399   [(set (match_operand:XF 0 "register_operand" "=f,f")
19400         (if_then_else:XF (match_operator 1 "fcmov_comparison_operator"
19401                                 [(reg FLAGS_REG) (const_int 0)])
19402                       (match_operand:XF 2 "register_operand" "f,0")
19403                       (match_operand:XF 3 "register_operand" "0,f")))]
19404   "TARGET_80387 && TARGET_CMOVE"
19405   "@
19406    fcmov%F1\t{%2, %0|%0, %2}
19407    fcmov%f1\t{%3, %0|%0, %3}"
19408   [(set_attr "type" "fcmov")
19409    (set_attr "mode" "XF")])
19410
19411 ;; All moves in SSE5 pcmov instructions are 128 bits and hence we restrict
19412 ;; the scalar versions to have only XMM registers as operands.
19413
19414 ;; SSE5 conditional move
19415 (define_insn "*sse5_pcmov_<mode>"
19416   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
19417         (if_then_else:MODEF
19418           (match_operand:MODEF 1 "register_operand" "x,0")
19419           (match_operand:MODEF 2 "register_operand" "0,x")
19420           (match_operand:MODEF 3 "register_operand" "x,x")))]
19421   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1)"
19422   "pcmov\t{%1, %3, %2, %0|%0, %2, %3, %1}"
19423   [(set_attr "type" "sse4arg")])
19424
19425 ;; These versions of the min/max patterns are intentionally ignorant of
19426 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
19427 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
19428 ;; are undefined in this condition, we're certain this is correct.
19429
19430 (define_insn "<code><mode>3"
19431   [(set (match_operand:MODEF 0 "register_operand" "=x")
19432         (smaxmin:MODEF
19433           (match_operand:MODEF 1 "nonimmediate_operand" "%0")
19434           (match_operand:MODEF 2 "nonimmediate_operand" "xm")))]
19435   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
19436   "<maxminfprefix>s<ssemodefsuffix>\t{%2, %0|%0, %2}"
19437   [(set_attr "type" "sseadd")
19438    (set_attr "mode" "<MODE>")])
19439
19440 ;; These versions of the min/max patterns implement exactly the operations
19441 ;;   min = (op1 < op2 ? op1 : op2)
19442 ;;   max = (!(op1 < op2) ? op1 : op2)
19443 ;; Their operands are not commutative, and thus they may be used in the
19444 ;; presence of -0.0 and NaN.
19445
19446 (define_insn "*ieee_smin<mode>3"
19447   [(set (match_operand:MODEF 0 "register_operand" "=x")
19448         (unspec:MODEF
19449           [(match_operand:MODEF 1 "register_operand" "0")
19450            (match_operand:MODEF 2 "nonimmediate_operand" "xm")]
19451          UNSPEC_IEEE_MIN))]
19452   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
19453   "mins<ssemodefsuffix>\t{%2, %0|%0, %2}"
19454   [(set_attr "type" "sseadd")
19455    (set_attr "mode" "<MODE>")])
19456
19457 (define_insn "*ieee_smax<mode>3"
19458   [(set (match_operand:MODEF 0 "register_operand" "=x")
19459         (unspec:MODEF
19460           [(match_operand:MODEF 1 "register_operand" "0")
19461            (match_operand:MODEF 2 "nonimmediate_operand" "xm")]
19462          UNSPEC_IEEE_MAX))]
19463   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
19464   "maxs<ssemodefsuffix>\t{%2, %0|%0, %2}"
19465   [(set_attr "type" "sseadd")
19466    (set_attr "mode" "<MODE>")])
19467
19468 ;; Make two stack loads independent:
19469 ;;   fld aa              fld aa
19470 ;;   fld %st(0)     ->   fld bb
19471 ;;   fmul bb             fmul %st(1), %st
19472 ;;
19473 ;; Actually we only match the last two instructions for simplicity.
19474 (define_peephole2
19475   [(set (match_operand 0 "fp_register_operand" "")
19476         (match_operand 1 "fp_register_operand" ""))
19477    (set (match_dup 0)
19478         (match_operator 2 "binary_fp_operator"
19479            [(match_dup 0)
19480             (match_operand 3 "memory_operand" "")]))]
19481   "REGNO (operands[0]) != REGNO (operands[1])"
19482   [(set (match_dup 0) (match_dup 3))
19483    (set (match_dup 0) (match_dup 4))]
19484
19485   ;; The % modifier is not operational anymore in peephole2's, so we have to
19486   ;; swap the operands manually in the case of addition and multiplication.
19487   "if (COMMUTATIVE_ARITH_P (operands[2]))
19488      operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), GET_MODE (operands[2]),
19489                                  operands[0], operands[1]);
19490    else
19491      operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), GET_MODE (operands[2]),
19492                                  operands[1], operands[0]);")
19493
19494 ;; Conditional addition patterns
19495 (define_expand "add<mode>cc"
19496   [(match_operand:SWI 0 "register_operand" "")
19497    (match_operand 1 "comparison_operator" "")
19498    (match_operand:SWI 2 "register_operand" "")
19499    (match_operand:SWI 3 "const_int_operand" "")]
19500   ""
19501   "if (ix86_expand_int_addcc (operands)) DONE; else FAIL;")
19502
19503 \f
19504 ;; Misc patterns (?)
19505
19506 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
19507 ;; Otherwise there will be nothing to keep
19508 ;;
19509 ;; [(set (reg ebp) (reg esp))]
19510 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
19511 ;;  (clobber (eflags)]
19512 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
19513 ;;
19514 ;; in proper program order.
19515 (define_insn "pro_epilogue_adjust_stack_1"
19516   [(set (match_operand:SI 0 "register_operand" "=r,r")
19517         (plus:SI (match_operand:SI 1 "register_operand" "0,r")
19518                  (match_operand:SI 2 "immediate_operand" "i,i")))
19519    (clobber (reg:CC FLAGS_REG))
19520    (clobber (mem:BLK (scratch)))]
19521   "!TARGET_64BIT"
19522 {
19523   switch (get_attr_type (insn))
19524     {
19525     case TYPE_IMOV:
19526       return "mov{l}\t{%1, %0|%0, %1}";
19527
19528     case TYPE_ALU:
19529       if (CONST_INT_P (operands[2])
19530           && (INTVAL (operands[2]) == 128
19531               || (INTVAL (operands[2]) < 0
19532                   && INTVAL (operands[2]) != -128)))
19533         {
19534           operands[2] = GEN_INT (-INTVAL (operands[2]));
19535           return "sub{l}\t{%2, %0|%0, %2}";
19536         }
19537       return "add{l}\t{%2, %0|%0, %2}";
19538
19539     case TYPE_LEA:
19540       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
19541       return "lea{l}\t{%a2, %0|%0, %a2}";
19542
19543     default:
19544       gcc_unreachable ();
19545     }
19546 }
19547   [(set (attr "type")
19548         (cond [(eq_attr "alternative" "0")
19549                  (const_string "alu")
19550                (match_operand:SI 2 "const0_operand" "")
19551                  (const_string "imov")
19552               ]
19553               (const_string "lea")))
19554    (set_attr "mode" "SI")])
19555
19556 (define_insn "pro_epilogue_adjust_stack_rex64"
19557   [(set (match_operand:DI 0 "register_operand" "=r,r")
19558         (plus:DI (match_operand:DI 1 "register_operand" "0,r")
19559                  (match_operand:DI 2 "x86_64_immediate_operand" "e,e")))
19560    (clobber (reg:CC FLAGS_REG))
19561    (clobber (mem:BLK (scratch)))]
19562   "TARGET_64BIT"
19563 {
19564   switch (get_attr_type (insn))
19565     {
19566     case TYPE_IMOV:
19567       return "mov{q}\t{%1, %0|%0, %1}";
19568
19569     case TYPE_ALU:
19570       if (CONST_INT_P (operands[2])
19571           /* Avoid overflows.  */
19572           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
19573           && (INTVAL (operands[2]) == 128
19574               || (INTVAL (operands[2]) < 0
19575                   && INTVAL (operands[2]) != -128)))
19576         {
19577           operands[2] = GEN_INT (-INTVAL (operands[2]));
19578           return "sub{q}\t{%2, %0|%0, %2}";
19579         }
19580       return "add{q}\t{%2, %0|%0, %2}";
19581
19582     case TYPE_LEA:
19583       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
19584       return "lea{q}\t{%a2, %0|%0, %a2}";
19585
19586     default:
19587       gcc_unreachable ();
19588     }
19589 }
19590   [(set (attr "type")
19591         (cond [(eq_attr "alternative" "0")
19592                  (const_string "alu")
19593                (match_operand:DI 2 "const0_operand" "")
19594                  (const_string "imov")
19595               ]
19596               (const_string "lea")))
19597    (set_attr "mode" "DI")])
19598
19599 (define_insn "pro_epilogue_adjust_stack_rex64_2"
19600   [(set (match_operand:DI 0 "register_operand" "=r,r")
19601         (plus:DI (match_operand:DI 1 "register_operand" "0,r")
19602                  (match_operand:DI 3 "immediate_operand" "i,i")))
19603    (use (match_operand:DI 2 "register_operand" "r,r"))
19604    (clobber (reg:CC FLAGS_REG))
19605    (clobber (mem:BLK (scratch)))]
19606   "TARGET_64BIT"
19607 {
19608   switch (get_attr_type (insn))
19609     {
19610     case TYPE_ALU:
19611       return "add{q}\t{%2, %0|%0, %2}";
19612
19613     case TYPE_LEA:
19614       operands[2] = gen_rtx_PLUS (DImode, operands[1], operands[2]);
19615       return "lea{q}\t{%a2, %0|%0, %a2}";
19616
19617     default:
19618       gcc_unreachable ();
19619     }
19620 }
19621   [(set_attr "type" "alu,lea")
19622    (set_attr "mode" "DI")])
19623
19624 (define_insn "allocate_stack_worker_32"
19625   [(set (match_operand:SI 0 "register_operand" "+a")
19626         (unspec_volatile:SI [(match_dup 0)] UNSPECV_STACK_PROBE))
19627    (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0)))
19628    (clobber (reg:CC FLAGS_REG))]
19629   "!TARGET_64BIT && TARGET_STACK_PROBE"
19630   "call\t___chkstk"
19631   [(set_attr "type" "multi")
19632    (set_attr "length" "5")])
19633
19634 (define_insn "allocate_stack_worker_64"
19635   [(set (match_operand:DI 0 "register_operand" "+a")
19636         (unspec_volatile:DI [(match_dup 0)] UNSPECV_STACK_PROBE))
19637    (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0)))
19638    (clobber (reg:DI R10_REG))
19639    (clobber (reg:DI R11_REG))
19640    (clobber (reg:CC FLAGS_REG))]
19641   "TARGET_64BIT && TARGET_STACK_PROBE"
19642   "call\t___chkstk"
19643   [(set_attr "type" "multi")
19644    (set_attr "length" "5")])
19645
19646 (define_expand "allocate_stack"
19647   [(match_operand 0 "register_operand" "")
19648    (match_operand 1 "general_operand" "")]
19649   "TARGET_STACK_PROBE"
19650 {
19651   rtx x;
19652
19653 #ifndef CHECK_STACK_LIMIT
19654 #define CHECK_STACK_LIMIT 0
19655 #endif
19656
19657   if (CHECK_STACK_LIMIT && CONST_INT_P (operands[1])
19658       && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
19659     {
19660       x = expand_simple_binop (Pmode, MINUS, stack_pointer_rtx, operands[1],
19661                                stack_pointer_rtx, 0, OPTAB_DIRECT);
19662       if (x != stack_pointer_rtx)
19663         emit_move_insn (stack_pointer_rtx, x);
19664     }
19665   else
19666     {
19667       x = copy_to_mode_reg (Pmode, operands[1]);
19668       if (TARGET_64BIT)
19669         x = gen_allocate_stack_worker_64 (x);
19670       else
19671         x = gen_allocate_stack_worker_32 (x);
19672       emit_insn (x);
19673     }
19674
19675   emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
19676   DONE;
19677 })
19678
19679 (define_expand "builtin_setjmp_receiver"
19680   [(label_ref (match_operand 0 "" ""))]
19681   "!TARGET_64BIT && flag_pic"
19682 {
19683   if (TARGET_MACHO)
19684     {
19685       rtx xops[3];
19686       rtx picreg = gen_rtx_REG (Pmode, PIC_OFFSET_TABLE_REGNUM);
19687       rtx label_rtx = gen_label_rtx ();
19688       emit_insn (gen_set_got_labelled (pic_offset_table_rtx, label_rtx));
19689       xops[0] = xops[1] = picreg;
19690       xops[2] = gen_rtx_CONST (SImode,
19691                   gen_rtx_MINUS (SImode,
19692                     gen_rtx_LABEL_REF (SImode, label_rtx),
19693                     gen_rtx_SYMBOL_REF (SImode, GOT_SYMBOL_NAME)));
19694       ix86_expand_binary_operator (MINUS, SImode, xops);
19695     }
19696   else
19697     emit_insn (gen_set_got (pic_offset_table_rtx));
19698   DONE;
19699 })
19700 \f
19701 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
19702
19703 (define_split
19704   [(set (match_operand 0 "register_operand" "")
19705         (match_operator 3 "promotable_binary_operator"
19706            [(match_operand 1 "register_operand" "")
19707             (match_operand 2 "aligned_operand" "")]))
19708    (clobber (reg:CC FLAGS_REG))]
19709   "! TARGET_PARTIAL_REG_STALL && reload_completed
19710    && ((GET_MODE (operands[0]) == HImode
19711         && ((!optimize_size && !TARGET_FAST_PREFIX)
19712             /* ??? next two lines just !satisfies_constraint_K (...) */
19713             || !CONST_INT_P (operands[2])
19714             || satisfies_constraint_K (operands[2])))
19715        || (GET_MODE (operands[0]) == QImode
19716            && (TARGET_PROMOTE_QImode || optimize_size)))"
19717   [(parallel [(set (match_dup 0)
19718                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
19719               (clobber (reg:CC FLAGS_REG))])]
19720   "operands[0] = gen_lowpart (SImode, operands[0]);
19721    operands[1] = gen_lowpart (SImode, operands[1]);
19722    if (GET_CODE (operands[3]) != ASHIFT)
19723      operands[2] = gen_lowpart (SImode, operands[2]);
19724    PUT_MODE (operands[3], SImode);")
19725
19726 ; Promote the QImode tests, as i386 has encoding of the AND
19727 ; instruction with 32-bit sign-extended immediate and thus the
19728 ; instruction size is unchanged, except in the %eax case for
19729 ; which it is increased by one byte, hence the ! optimize_size.
19730 (define_split
19731   [(set (match_operand 0 "flags_reg_operand" "")
19732         (match_operator 2 "compare_operator"
19733           [(and (match_operand 3 "aligned_operand" "")
19734                 (match_operand 4 "const_int_operand" ""))
19735            (const_int 0)]))
19736    (set (match_operand 1 "register_operand" "")
19737         (and (match_dup 3) (match_dup 4)))]
19738   "! TARGET_PARTIAL_REG_STALL && reload_completed
19739    && ! optimize_size
19740    && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
19741        || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))
19742    /* Ensure that the operand will remain sign-extended immediate.  */
19743    && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)"
19744   [(parallel [(set (match_dup 0)
19745                    (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
19746                                     (const_int 0)]))
19747               (set (match_dup 1)
19748                    (and:SI (match_dup 3) (match_dup 4)))])]
19749 {
19750   operands[4]
19751     = gen_int_mode (INTVAL (operands[4])
19752                     & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
19753   operands[1] = gen_lowpart (SImode, operands[1]);
19754   operands[3] = gen_lowpart (SImode, operands[3]);
19755 })
19756
19757 ; Don't promote the QImode tests, as i386 doesn't have encoding of
19758 ; the TEST instruction with 32-bit sign-extended immediate and thus
19759 ; the instruction size would at least double, which is not what we
19760 ; want even with ! optimize_size.
19761 (define_split
19762   [(set (match_operand 0 "flags_reg_operand" "")
19763         (match_operator 1 "compare_operator"
19764           [(and (match_operand:HI 2 "aligned_operand" "")
19765                 (match_operand:HI 3 "const_int_operand" ""))
19766            (const_int 0)]))]
19767   "! TARGET_PARTIAL_REG_STALL && reload_completed
19768    && ! TARGET_FAST_PREFIX
19769    && ! optimize_size
19770    /* Ensure that the operand will remain sign-extended immediate.  */
19771    && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)"
19772   [(set (match_dup 0)
19773         (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
19774                          (const_int 0)]))]
19775 {
19776   operands[3]
19777     = gen_int_mode (INTVAL (operands[3])
19778                     & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
19779   operands[2] = gen_lowpart (SImode, operands[2]);
19780 })
19781
19782 (define_split
19783   [(set (match_operand 0 "register_operand" "")
19784         (neg (match_operand 1 "register_operand" "")))
19785    (clobber (reg:CC FLAGS_REG))]
19786   "! TARGET_PARTIAL_REG_STALL && reload_completed
19787    && (GET_MODE (operands[0]) == HImode
19788        || (GET_MODE (operands[0]) == QImode
19789            && (TARGET_PROMOTE_QImode || optimize_size)))"
19790   [(parallel [(set (match_dup 0)
19791                    (neg:SI (match_dup 1)))
19792               (clobber (reg:CC FLAGS_REG))])]
19793   "operands[0] = gen_lowpart (SImode, operands[0]);
19794    operands[1] = gen_lowpart (SImode, operands[1]);")
19795
19796 (define_split
19797   [(set (match_operand 0 "register_operand" "")
19798         (not (match_operand 1 "register_operand" "")))]
19799   "! TARGET_PARTIAL_REG_STALL && reload_completed
19800    && (GET_MODE (operands[0]) == HImode
19801        || (GET_MODE (operands[0]) == QImode
19802            && (TARGET_PROMOTE_QImode || optimize_size)))"
19803   [(set (match_dup 0)
19804         (not:SI (match_dup 1)))]
19805   "operands[0] = gen_lowpart (SImode, operands[0]);
19806    operands[1] = gen_lowpart (SImode, operands[1]);")
19807
19808 (define_split
19809   [(set (match_operand 0 "register_operand" "")
19810         (if_then_else (match_operator 1 "comparison_operator"
19811                                 [(reg FLAGS_REG) (const_int 0)])
19812                       (match_operand 2 "register_operand" "")
19813                       (match_operand 3 "register_operand" "")))]
19814   "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE
19815    && (GET_MODE (operands[0]) == HImode
19816        || (GET_MODE (operands[0]) == QImode
19817            && (TARGET_PROMOTE_QImode || optimize_size)))"
19818   [(set (match_dup 0)
19819         (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
19820   "operands[0] = gen_lowpart (SImode, operands[0]);
19821    operands[2] = gen_lowpart (SImode, operands[2]);
19822    operands[3] = gen_lowpart (SImode, operands[3]);")
19823
19824 \f
19825 ;; RTL Peephole optimizations, run before sched2.  These primarily look to
19826 ;; transform a complex memory operation into two memory to register operations.
19827
19828 ;; Don't push memory operands
19829 (define_peephole2
19830   [(set (match_operand:SI 0 "push_operand" "")
19831         (match_operand:SI 1 "memory_operand" ""))
19832    (match_scratch:SI 2 "r")]
19833   "!optimize_size && !TARGET_PUSH_MEMORY
19834    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
19835   [(set (match_dup 2) (match_dup 1))
19836    (set (match_dup 0) (match_dup 2))]
19837   "")
19838
19839 (define_peephole2
19840   [(set (match_operand:DI 0 "push_operand" "")
19841         (match_operand:DI 1 "memory_operand" ""))
19842    (match_scratch:DI 2 "r")]
19843   "!optimize_size && !TARGET_PUSH_MEMORY
19844    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
19845   [(set (match_dup 2) (match_dup 1))
19846    (set (match_dup 0) (match_dup 2))]
19847   "")
19848
19849 ;; We need to handle SFmode only, because DFmode and XFmode is split to
19850 ;; SImode pushes.
19851 (define_peephole2
19852   [(set (match_operand:SF 0 "push_operand" "")
19853         (match_operand:SF 1 "memory_operand" ""))
19854    (match_scratch:SF 2 "r")]
19855   "!optimize_size && !TARGET_PUSH_MEMORY
19856    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
19857   [(set (match_dup 2) (match_dup 1))
19858    (set (match_dup 0) (match_dup 2))]
19859   "")
19860
19861 (define_peephole2
19862   [(set (match_operand:HI 0 "push_operand" "")
19863         (match_operand:HI 1 "memory_operand" ""))
19864    (match_scratch:HI 2 "r")]
19865   "!optimize_size && !TARGET_PUSH_MEMORY
19866    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
19867   [(set (match_dup 2) (match_dup 1))
19868    (set (match_dup 0) (match_dup 2))]
19869   "")
19870
19871 (define_peephole2
19872   [(set (match_operand:QI 0 "push_operand" "")
19873         (match_operand:QI 1 "memory_operand" ""))
19874    (match_scratch:QI 2 "q")]
19875   "!optimize_size && !TARGET_PUSH_MEMORY
19876    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
19877   [(set (match_dup 2) (match_dup 1))
19878    (set (match_dup 0) (match_dup 2))]
19879   "")
19880
19881 ;; Don't move an immediate directly to memory when the instruction
19882 ;; gets too big.
19883 (define_peephole2
19884   [(match_scratch:SI 1 "r")
19885    (set (match_operand:SI 0 "memory_operand" "")
19886         (const_int 0))]
19887   "! optimize_size
19888    && ! TARGET_USE_MOV0
19889    && TARGET_SPLIT_LONG_MOVES
19890    && get_attr_length (insn) >= ix86_cost->large_insn
19891    && peep2_regno_dead_p (0, FLAGS_REG)"
19892   [(parallel [(set (match_dup 1) (const_int 0))
19893               (clobber (reg:CC FLAGS_REG))])
19894    (set (match_dup 0) (match_dup 1))]
19895   "")
19896
19897 (define_peephole2
19898   [(match_scratch:HI 1 "r")
19899    (set (match_operand:HI 0 "memory_operand" "")
19900         (const_int 0))]
19901   "! optimize_size
19902    && ! TARGET_USE_MOV0
19903    && TARGET_SPLIT_LONG_MOVES
19904    && get_attr_length (insn) >= ix86_cost->large_insn
19905    && peep2_regno_dead_p (0, FLAGS_REG)"
19906   [(parallel [(set (match_dup 2) (const_int 0))
19907               (clobber (reg:CC FLAGS_REG))])
19908    (set (match_dup 0) (match_dup 1))]
19909   "operands[2] = gen_lowpart (SImode, operands[1]);")
19910
19911 (define_peephole2
19912   [(match_scratch:QI 1 "q")
19913    (set (match_operand:QI 0 "memory_operand" "")
19914         (const_int 0))]
19915   "! optimize_size
19916    && ! TARGET_USE_MOV0
19917    && TARGET_SPLIT_LONG_MOVES
19918    && get_attr_length (insn) >= ix86_cost->large_insn
19919    && peep2_regno_dead_p (0, FLAGS_REG)"
19920   [(parallel [(set (match_dup 2) (const_int 0))
19921               (clobber (reg:CC FLAGS_REG))])
19922    (set (match_dup 0) (match_dup 1))]
19923   "operands[2] = gen_lowpart (SImode, operands[1]);")
19924
19925 (define_peephole2
19926   [(match_scratch:SI 2 "r")
19927    (set (match_operand:SI 0 "memory_operand" "")
19928         (match_operand:SI 1 "immediate_operand" ""))]
19929   "! optimize_size
19930    && TARGET_SPLIT_LONG_MOVES
19931    && get_attr_length (insn) >= ix86_cost->large_insn"
19932   [(set (match_dup 2) (match_dup 1))
19933    (set (match_dup 0) (match_dup 2))]
19934   "")
19935
19936 (define_peephole2
19937   [(match_scratch:HI 2 "r")
19938    (set (match_operand:HI 0 "memory_operand" "")
19939         (match_operand:HI 1 "immediate_operand" ""))]
19940   "! optimize_size
19941    && TARGET_SPLIT_LONG_MOVES
19942    && get_attr_length (insn) >= ix86_cost->large_insn"
19943   [(set (match_dup 2) (match_dup 1))
19944    (set (match_dup 0) (match_dup 2))]
19945   "")
19946
19947 (define_peephole2
19948   [(match_scratch:QI 2 "q")
19949    (set (match_operand:QI 0 "memory_operand" "")
19950         (match_operand:QI 1 "immediate_operand" ""))]
19951   "! optimize_size
19952    && TARGET_SPLIT_LONG_MOVES
19953    && get_attr_length (insn) >= ix86_cost->large_insn"
19954   [(set (match_dup 2) (match_dup 1))
19955    (set (match_dup 0) (match_dup 2))]
19956   "")
19957
19958 ;; Don't compare memory with zero, load and use a test instead.
19959 (define_peephole2
19960   [(set (match_operand 0 "flags_reg_operand" "")
19961         (match_operator 1 "compare_operator"
19962           [(match_operand:SI 2 "memory_operand" "")
19963            (const_int 0)]))
19964    (match_scratch:SI 3 "r")]
19965   " ! optimize_size && ix86_match_ccmode (insn, CCNOmode)"
19966   [(set (match_dup 3) (match_dup 2))
19967    (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))]
19968   "")
19969
19970 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer.
19971 ;; Don't split NOTs with a displacement operand, because resulting XOR
19972 ;; will not be pairable anyway.
19973 ;;
19974 ;; On AMD K6, NOT is vector decoded with memory operand that cannot be
19975 ;; represented using a modRM byte.  The XOR replacement is long decoded,
19976 ;; so this split helps here as well.
19977 ;;
19978 ;; Note: Can't do this as a regular split because we can't get proper
19979 ;; lifetime information then.
19980
19981 (define_peephole2
19982   [(set (match_operand:SI 0 "nonimmediate_operand" "")
19983         (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
19984   "!optimize_size
19985    && ((TARGET_NOT_UNPAIRABLE
19986         && (!MEM_P (operands[0])
19987             || !memory_displacement_operand (operands[0], SImode)))
19988        || (TARGET_NOT_VECTORMODE && long_memory_operand (operands[0], SImode)))
19989    && peep2_regno_dead_p (0, FLAGS_REG)"
19990   [(parallel [(set (match_dup 0)
19991                    (xor:SI (match_dup 1) (const_int -1)))
19992               (clobber (reg:CC FLAGS_REG))])]
19993   "")
19994
19995 (define_peephole2
19996   [(set (match_operand:HI 0 "nonimmediate_operand" "")
19997         (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
19998   "!optimize_size
19999    && ((TARGET_NOT_UNPAIRABLE
20000         && (!MEM_P (operands[0])
20001             || !memory_displacement_operand (operands[0], HImode)))
20002        || (TARGET_NOT_VECTORMODE && long_memory_operand (operands[0], HImode)))
20003    && peep2_regno_dead_p (0, FLAGS_REG)"
20004   [(parallel [(set (match_dup 0)
20005                    (xor:HI (match_dup 1) (const_int -1)))
20006               (clobber (reg:CC FLAGS_REG))])]
20007   "")
20008
20009 (define_peephole2
20010   [(set (match_operand:QI 0 "nonimmediate_operand" "")
20011         (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
20012   "!optimize_size
20013    && ((TARGET_NOT_UNPAIRABLE
20014         && (!MEM_P (operands[0])
20015             || !memory_displacement_operand (operands[0], QImode)))
20016        || (TARGET_NOT_VECTORMODE && long_memory_operand (operands[0], QImode)))
20017    && peep2_regno_dead_p (0, FLAGS_REG)"
20018   [(parallel [(set (match_dup 0)
20019                    (xor:QI (match_dup 1) (const_int -1)))
20020               (clobber (reg:CC FLAGS_REG))])]
20021   "")
20022
20023 ;; Non pairable "test imm, reg" instructions can be translated to
20024 ;; "and imm, reg" if reg dies.  The "and" form is also shorter (one
20025 ;; byte opcode instead of two, have a short form for byte operands),
20026 ;; so do it for other CPUs as well.  Given that the value was dead,
20027 ;; this should not create any new dependencies.  Pass on the sub-word
20028 ;; versions if we're concerned about partial register stalls.
20029
20030 (define_peephole2
20031   [(set (match_operand 0 "flags_reg_operand" "")
20032         (match_operator 1 "compare_operator"
20033           [(and:SI (match_operand:SI 2 "register_operand" "")
20034                    (match_operand:SI 3 "immediate_operand" ""))
20035            (const_int 0)]))]
20036   "ix86_match_ccmode (insn, CCNOmode)
20037    && (true_regnum (operands[2]) != AX_REG
20038        || satisfies_constraint_K (operands[3]))
20039    && peep2_reg_dead_p (1, operands[2])"
20040   [(parallel
20041      [(set (match_dup 0)
20042            (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
20043                             (const_int 0)]))
20044       (set (match_dup 2)
20045            (and:SI (match_dup 2) (match_dup 3)))])]
20046   "")
20047
20048 ;; We don't need to handle HImode case, because it will be promoted to SImode
20049 ;; on ! TARGET_PARTIAL_REG_STALL
20050
20051 (define_peephole2
20052   [(set (match_operand 0 "flags_reg_operand" "")
20053         (match_operator 1 "compare_operator"
20054           [(and:QI (match_operand:QI 2 "register_operand" "")
20055                    (match_operand:QI 3 "immediate_operand" ""))
20056            (const_int 0)]))]
20057   "! TARGET_PARTIAL_REG_STALL
20058    && ix86_match_ccmode (insn, CCNOmode)
20059    && true_regnum (operands[2]) != AX_REG
20060    && peep2_reg_dead_p (1, operands[2])"
20061   [(parallel
20062      [(set (match_dup 0)
20063            (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
20064                             (const_int 0)]))
20065       (set (match_dup 2)
20066            (and:QI (match_dup 2) (match_dup 3)))])]
20067   "")
20068
20069 (define_peephole2
20070   [(set (match_operand 0 "flags_reg_operand" "")
20071         (match_operator 1 "compare_operator"
20072           [(and:SI
20073              (zero_extract:SI
20074                (match_operand 2 "ext_register_operand" "")
20075                (const_int 8)
20076                (const_int 8))
20077              (match_operand 3 "const_int_operand" ""))
20078            (const_int 0)]))]
20079   "! TARGET_PARTIAL_REG_STALL
20080    && ix86_match_ccmode (insn, CCNOmode)
20081    && true_regnum (operands[2]) != AX_REG
20082    && peep2_reg_dead_p (1, operands[2])"
20083   [(parallel [(set (match_dup 0)
20084                    (match_op_dup 1
20085                      [(and:SI
20086                         (zero_extract:SI
20087                           (match_dup 2)
20088                           (const_int 8)
20089                           (const_int 8))
20090                         (match_dup 3))
20091                       (const_int 0)]))
20092               (set (zero_extract:SI (match_dup 2)
20093                                     (const_int 8)
20094                                     (const_int 8))
20095                    (and:SI
20096                      (zero_extract:SI
20097                        (match_dup 2)
20098                        (const_int 8)
20099                        (const_int 8))
20100                      (match_dup 3)))])]
20101   "")
20102
20103 ;; Don't do logical operations with memory inputs.
20104 (define_peephole2
20105   [(match_scratch:SI 2 "r")
20106    (parallel [(set (match_operand:SI 0 "register_operand" "")
20107                    (match_operator:SI 3 "arith_or_logical_operator"
20108                      [(match_dup 0)
20109                       (match_operand:SI 1 "memory_operand" "")]))
20110               (clobber (reg:CC FLAGS_REG))])]
20111   "! optimize_size && ! TARGET_READ_MODIFY"
20112   [(set (match_dup 2) (match_dup 1))
20113    (parallel [(set (match_dup 0)
20114                    (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
20115               (clobber (reg:CC FLAGS_REG))])]
20116   "")
20117
20118 (define_peephole2
20119   [(match_scratch:SI 2 "r")
20120    (parallel [(set (match_operand:SI 0 "register_operand" "")
20121                    (match_operator:SI 3 "arith_or_logical_operator"
20122                      [(match_operand:SI 1 "memory_operand" "")
20123                       (match_dup 0)]))
20124               (clobber (reg:CC FLAGS_REG))])]
20125   "! optimize_size && ! TARGET_READ_MODIFY"
20126   [(set (match_dup 2) (match_dup 1))
20127    (parallel [(set (match_dup 0)
20128                    (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
20129               (clobber (reg:CC FLAGS_REG))])]
20130   "")
20131
20132 ; Don't do logical operations with memory outputs
20133 ;
20134 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
20135 ; instruction into two 1-uop insns plus a 2-uop insn.  That last has
20136 ; the same decoder scheduling characteristics as the original.
20137
20138 (define_peephole2
20139   [(match_scratch:SI 2 "r")
20140    (parallel [(set (match_operand:SI 0 "memory_operand" "")
20141                    (match_operator:SI 3 "arith_or_logical_operator"
20142                      [(match_dup 0)
20143                       (match_operand:SI 1 "nonmemory_operand" "")]))
20144               (clobber (reg:CC FLAGS_REG))])]
20145   "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
20146   [(set (match_dup 2) (match_dup 0))
20147    (parallel [(set (match_dup 2)
20148                    (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
20149               (clobber (reg:CC FLAGS_REG))])
20150    (set (match_dup 0) (match_dup 2))]
20151   "")
20152
20153 (define_peephole2
20154   [(match_scratch:SI 2 "r")
20155    (parallel [(set (match_operand:SI 0 "memory_operand" "")
20156                    (match_operator:SI 3 "arith_or_logical_operator"
20157                      [(match_operand:SI 1 "nonmemory_operand" "")
20158                       (match_dup 0)]))
20159               (clobber (reg:CC FLAGS_REG))])]
20160   "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
20161   [(set (match_dup 2) (match_dup 0))
20162    (parallel [(set (match_dup 2)
20163                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
20164               (clobber (reg:CC FLAGS_REG))])
20165    (set (match_dup 0) (match_dup 2))]
20166   "")
20167
20168 ;; Attempt to always use XOR for zeroing registers.
20169 (define_peephole2
20170   [(set (match_operand 0 "register_operand" "")
20171         (match_operand 1 "const0_operand" ""))]
20172   "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD
20173    && (! TARGET_USE_MOV0 || optimize_size)
20174    && GENERAL_REG_P (operands[0])
20175    && peep2_regno_dead_p (0, FLAGS_REG)"
20176   [(parallel [(set (match_dup 0) (const_int 0))
20177               (clobber (reg:CC FLAGS_REG))])]
20178 {
20179   operands[0] = gen_lowpart (word_mode, operands[0]);
20180 })
20181
20182 (define_peephole2
20183   [(set (strict_low_part (match_operand 0 "register_operand" ""))
20184         (const_int 0))]
20185   "(GET_MODE (operands[0]) == QImode
20186     || GET_MODE (operands[0]) == HImode)
20187    && (! TARGET_USE_MOV0 || optimize_size)
20188    && peep2_regno_dead_p (0, FLAGS_REG)"
20189   [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
20190               (clobber (reg:CC FLAGS_REG))])])
20191
20192 ;; For HI and SI modes, or $-1,reg is smaller than mov $-1,reg.
20193 (define_peephole2
20194   [(set (match_operand 0 "register_operand" "")
20195         (const_int -1))]
20196   "(GET_MODE (operands[0]) == HImode
20197     || GET_MODE (operands[0]) == SImode
20198     || (GET_MODE (operands[0]) == DImode && TARGET_64BIT))
20199    && (optimize_size || TARGET_MOVE_M1_VIA_OR)
20200    && peep2_regno_dead_p (0, FLAGS_REG)"
20201   [(parallel [(set (match_dup 0) (const_int -1))
20202               (clobber (reg:CC FLAGS_REG))])]
20203   "operands[0] = gen_lowpart (GET_MODE (operands[0]) == DImode ? DImode : SImode,
20204                               operands[0]);")
20205
20206 ;; Attempt to convert simple leas to adds. These can be created by
20207 ;; move expanders.
20208 (define_peephole2
20209   [(set (match_operand:SI 0 "register_operand" "")
20210         (plus:SI (match_dup 0)
20211                  (match_operand:SI 1 "nonmemory_operand" "")))]
20212   "peep2_regno_dead_p (0, FLAGS_REG)"
20213   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
20214               (clobber (reg:CC FLAGS_REG))])]
20215   "")
20216
20217 (define_peephole2
20218   [(set (match_operand:SI 0 "register_operand" "")
20219         (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
20220                             (match_operand:DI 2 "nonmemory_operand" "")) 0))]
20221   "peep2_regno_dead_p (0, FLAGS_REG) && REGNO (operands[0]) == REGNO (operands[1])"
20222   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
20223               (clobber (reg:CC FLAGS_REG))])]
20224   "operands[2] = gen_lowpart (SImode, operands[2]);")
20225
20226 (define_peephole2
20227   [(set (match_operand:DI 0 "register_operand" "")
20228         (plus:DI (match_dup 0)
20229                  (match_operand:DI 1 "x86_64_general_operand" "")))]
20230   "peep2_regno_dead_p (0, FLAGS_REG)"
20231   [(parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
20232               (clobber (reg:CC FLAGS_REG))])]
20233   "")
20234
20235 (define_peephole2
20236   [(set (match_operand:SI 0 "register_operand" "")
20237         (mult:SI (match_dup 0)
20238                  (match_operand:SI 1 "const_int_operand" "")))]
20239   "exact_log2 (INTVAL (operands[1])) >= 0
20240    && peep2_regno_dead_p (0, FLAGS_REG)"
20241   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
20242               (clobber (reg:CC FLAGS_REG))])]
20243   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
20244
20245 (define_peephole2
20246   [(set (match_operand:DI 0 "register_operand" "")
20247         (mult:DI (match_dup 0)
20248                  (match_operand:DI 1 "const_int_operand" "")))]
20249   "exact_log2 (INTVAL (operands[1])) >= 0
20250    && peep2_regno_dead_p (0, FLAGS_REG)"
20251   [(parallel [(set (match_dup 0) (ashift:DI (match_dup 0) (match_dup 2)))
20252               (clobber (reg:CC FLAGS_REG))])]
20253   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
20254
20255 (define_peephole2
20256   [(set (match_operand:SI 0 "register_operand" "")
20257         (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
20258                    (match_operand:DI 2 "const_int_operand" "")) 0))]
20259   "exact_log2 (INTVAL (operands[2])) >= 0
20260    && REGNO (operands[0]) == REGNO (operands[1])
20261    && peep2_regno_dead_p (0, FLAGS_REG)"
20262   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
20263               (clobber (reg:CC FLAGS_REG))])]
20264   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
20265
20266 ;; The ESP adjustments can be done by the push and pop instructions.  Resulting
20267 ;; code is shorter, since push is only 1 byte, while add imm, %esp 3 bytes.  On
20268 ;; many CPUs it is also faster, since special hardware to avoid esp
20269 ;; dependencies is present.
20270
20271 ;; While some of these conversions may be done using splitters, we use peepholes
20272 ;; in order to allow combine_stack_adjustments pass to see nonobfuscated RTL.
20273
20274 ;; Convert prologue esp subtractions to push.
20275 ;; We need register to push.  In order to keep verify_flow_info happy we have
20276 ;; two choices
20277 ;; - use scratch and clobber it in order to avoid dependencies
20278 ;; - use already live register
20279 ;; We can't use the second way right now, since there is no reliable way how to
20280 ;; verify that given register is live.  First choice will also most likely in
20281 ;; fewer dependencies.  On the place of esp adjustments it is very likely that
20282 ;; call clobbered registers are dead.  We may want to use base pointer as an
20283 ;; alternative when no register is available later.
20284
20285 (define_peephole2
20286   [(match_scratch:SI 0 "r")
20287    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
20288               (clobber (reg:CC FLAGS_REG))
20289               (clobber (mem:BLK (scratch)))])]
20290   "optimize_size || !TARGET_SUB_ESP_4"
20291   [(clobber (match_dup 0))
20292    (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
20293               (clobber (mem:BLK (scratch)))])])
20294
20295 (define_peephole2
20296   [(match_scratch:SI 0 "r")
20297    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
20298               (clobber (reg:CC FLAGS_REG))
20299               (clobber (mem:BLK (scratch)))])]
20300   "optimize_size || !TARGET_SUB_ESP_8"
20301   [(clobber (match_dup 0))
20302    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
20303    (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
20304               (clobber (mem:BLK (scratch)))])])
20305
20306 ;; Convert esp subtractions to push.
20307 (define_peephole2
20308   [(match_scratch:SI 0 "r")
20309    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
20310               (clobber (reg:CC FLAGS_REG))])]
20311   "optimize_size || !TARGET_SUB_ESP_4"
20312   [(clobber (match_dup 0))
20313    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
20314
20315 (define_peephole2
20316   [(match_scratch:SI 0 "r")
20317    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
20318               (clobber (reg:CC FLAGS_REG))])]
20319   "optimize_size || !TARGET_SUB_ESP_8"
20320   [(clobber (match_dup 0))
20321    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
20322    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
20323
20324 ;; Convert epilogue deallocator to pop.
20325 (define_peephole2
20326   [(match_scratch:SI 0 "r")
20327    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
20328               (clobber (reg:CC FLAGS_REG))
20329               (clobber (mem:BLK (scratch)))])]
20330   "optimize_size || !TARGET_ADD_ESP_4"
20331   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20332               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
20333               (clobber (mem:BLK (scratch)))])]
20334   "")
20335
20336 ;; Two pops case is tricky, since pop causes dependency on destination register.
20337 ;; We use two registers if available.
20338 (define_peephole2
20339   [(match_scratch:SI 0 "r")
20340    (match_scratch:SI 1 "r")
20341    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
20342               (clobber (reg:CC FLAGS_REG))
20343               (clobber (mem:BLK (scratch)))])]
20344   "optimize_size || !TARGET_ADD_ESP_8"
20345   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20346               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
20347               (clobber (mem:BLK (scratch)))])
20348    (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
20349               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
20350   "")
20351
20352 (define_peephole2
20353   [(match_scratch:SI 0 "r")
20354    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
20355               (clobber (reg:CC FLAGS_REG))
20356               (clobber (mem:BLK (scratch)))])]
20357   "optimize_size"
20358   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20359               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
20360               (clobber (mem:BLK (scratch)))])
20361    (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20362               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
20363   "")
20364
20365 ;; Convert esp additions to pop.
20366 (define_peephole2
20367   [(match_scratch:SI 0 "r")
20368    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
20369               (clobber (reg:CC FLAGS_REG))])]
20370   ""
20371   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20372               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
20373   "")
20374
20375 ;; Two pops case is tricky, since pop causes dependency on destination register.
20376 ;; We use two registers if available.
20377 (define_peephole2
20378   [(match_scratch:SI 0 "r")
20379    (match_scratch:SI 1 "r")
20380    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
20381               (clobber (reg:CC FLAGS_REG))])]
20382   ""
20383   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20384               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
20385    (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
20386               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
20387   "")
20388
20389 (define_peephole2
20390   [(match_scratch:SI 0 "r")
20391    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
20392               (clobber (reg:CC FLAGS_REG))])]
20393   "optimize_size"
20394   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20395               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
20396    (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20397               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
20398   "")
20399 \f
20400 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
20401 ;; required and register dies.  Similarly for 128 to plus -128.
20402 (define_peephole2
20403   [(set (match_operand 0 "flags_reg_operand" "")
20404         (match_operator 1 "compare_operator"
20405           [(match_operand 2 "register_operand" "")
20406            (match_operand 3 "const_int_operand" "")]))]
20407   "(INTVAL (operands[3]) == -1
20408     || INTVAL (operands[3]) == 1
20409     || INTVAL (operands[3]) == 128)
20410    && ix86_match_ccmode (insn, CCGCmode)
20411    && peep2_reg_dead_p (1, operands[2])"
20412   [(parallel [(set (match_dup 0)
20413                    (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
20414               (clobber (match_dup 2))])]
20415   "")
20416 \f
20417 (define_peephole2
20418   [(match_scratch:DI 0 "r")
20419    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
20420               (clobber (reg:CC FLAGS_REG))
20421               (clobber (mem:BLK (scratch)))])]
20422   "optimize_size || !TARGET_SUB_ESP_4"
20423   [(clobber (match_dup 0))
20424    (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
20425               (clobber (mem:BLK (scratch)))])])
20426
20427 (define_peephole2
20428   [(match_scratch:DI 0 "r")
20429    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
20430               (clobber (reg:CC FLAGS_REG))
20431               (clobber (mem:BLK (scratch)))])]
20432   "optimize_size || !TARGET_SUB_ESP_8"
20433   [(clobber (match_dup 0))
20434    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
20435    (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
20436               (clobber (mem:BLK (scratch)))])])
20437
20438 ;; Convert esp subtractions to push.
20439 (define_peephole2
20440   [(match_scratch:DI 0 "r")
20441    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
20442               (clobber (reg:CC FLAGS_REG))])]
20443   "optimize_size || !TARGET_SUB_ESP_4"
20444   [(clobber (match_dup 0))
20445    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
20446
20447 (define_peephole2
20448   [(match_scratch:DI 0 "r")
20449    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
20450               (clobber (reg:CC FLAGS_REG))])]
20451   "optimize_size || !TARGET_SUB_ESP_8"
20452   [(clobber (match_dup 0))
20453    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
20454    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
20455
20456 ;; Convert epilogue deallocator to pop.
20457 (define_peephole2
20458   [(match_scratch:DI 0 "r")
20459    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
20460               (clobber (reg:CC FLAGS_REG))
20461               (clobber (mem:BLK (scratch)))])]
20462   "optimize_size || !TARGET_ADD_ESP_4"
20463   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20464               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
20465               (clobber (mem:BLK (scratch)))])]
20466   "")
20467
20468 ;; Two pops case is tricky, since pop causes dependency on destination register.
20469 ;; We use two registers if available.
20470 (define_peephole2
20471   [(match_scratch:DI 0 "r")
20472    (match_scratch:DI 1 "r")
20473    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
20474               (clobber (reg:CC FLAGS_REG))
20475               (clobber (mem:BLK (scratch)))])]
20476   "optimize_size || !TARGET_ADD_ESP_8"
20477   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20478               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
20479               (clobber (mem:BLK (scratch)))])
20480    (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
20481               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
20482   "")
20483
20484 (define_peephole2
20485   [(match_scratch:DI 0 "r")
20486    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
20487               (clobber (reg:CC FLAGS_REG))
20488               (clobber (mem:BLK (scratch)))])]
20489   "optimize_size"
20490   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20491               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
20492               (clobber (mem:BLK (scratch)))])
20493    (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20494               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
20495   "")
20496
20497 ;; Convert esp additions to pop.
20498 (define_peephole2
20499   [(match_scratch:DI 0 "r")
20500    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
20501               (clobber (reg:CC FLAGS_REG))])]
20502   ""
20503   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20504               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
20505   "")
20506
20507 ;; Two pops case is tricky, since pop causes dependency on destination register.
20508 ;; We use two registers if available.
20509 (define_peephole2
20510   [(match_scratch:DI 0 "r")
20511    (match_scratch:DI 1 "r")
20512    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
20513               (clobber (reg:CC FLAGS_REG))])]
20514   ""
20515   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20516               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
20517    (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
20518               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
20519   "")
20520
20521 (define_peephole2
20522   [(match_scratch:DI 0 "r")
20523    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
20524               (clobber (reg:CC FLAGS_REG))])]
20525   "optimize_size"
20526   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20527               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
20528    (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20529               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
20530   "")
20531 \f
20532 ;; Convert imul by three, five and nine into lea
20533 (define_peephole2
20534   [(parallel
20535     [(set (match_operand:SI 0 "register_operand" "")
20536           (mult:SI (match_operand:SI 1 "register_operand" "")
20537                    (match_operand:SI 2 "const_int_operand" "")))
20538      (clobber (reg:CC FLAGS_REG))])]
20539   "INTVAL (operands[2]) == 3
20540    || INTVAL (operands[2]) == 5
20541    || INTVAL (operands[2]) == 9"
20542   [(set (match_dup 0)
20543         (plus:SI (mult:SI (match_dup 1) (match_dup 2))
20544                  (match_dup 1)))]
20545   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
20546
20547 (define_peephole2
20548   [(parallel
20549     [(set (match_operand:SI 0 "register_operand" "")
20550           (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
20551                    (match_operand:SI 2 "const_int_operand" "")))
20552      (clobber (reg:CC FLAGS_REG))])]
20553   "!optimize_size
20554    && (INTVAL (operands[2]) == 3
20555        || INTVAL (operands[2]) == 5
20556        || INTVAL (operands[2]) == 9)"
20557   [(set (match_dup 0) (match_dup 1))
20558    (set (match_dup 0)
20559         (plus:SI (mult:SI (match_dup 0) (match_dup 2))
20560                  (match_dup 0)))]
20561   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
20562
20563 (define_peephole2
20564   [(parallel
20565     [(set (match_operand:DI 0 "register_operand" "")
20566           (mult:DI (match_operand:DI 1 "register_operand" "")
20567                    (match_operand:DI 2 "const_int_operand" "")))
20568      (clobber (reg:CC FLAGS_REG))])]
20569   "TARGET_64BIT
20570    && (INTVAL (operands[2]) == 3
20571        || INTVAL (operands[2]) == 5
20572        || INTVAL (operands[2]) == 9)"
20573   [(set (match_dup 0)
20574         (plus:DI (mult:DI (match_dup 1) (match_dup 2))
20575                  (match_dup 1)))]
20576   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
20577
20578 (define_peephole2
20579   [(parallel
20580     [(set (match_operand:DI 0 "register_operand" "")
20581           (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
20582                    (match_operand:DI 2 "const_int_operand" "")))
20583      (clobber (reg:CC FLAGS_REG))])]
20584   "TARGET_64BIT
20585    && !optimize_size
20586    && (INTVAL (operands[2]) == 3
20587        || INTVAL (operands[2]) == 5
20588        || INTVAL (operands[2]) == 9)"
20589   [(set (match_dup 0) (match_dup 1))
20590    (set (match_dup 0)
20591         (plus:DI (mult:DI (match_dup 0) (match_dup 2))
20592                  (match_dup 0)))]
20593   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
20594
20595 ;; Imul $32bit_imm, mem, reg is vector decoded, while
20596 ;; imul $32bit_imm, reg, reg is direct decoded.
20597 (define_peephole2
20598   [(match_scratch:DI 3 "r")
20599    (parallel [(set (match_operand:DI 0 "register_operand" "")
20600                    (mult:DI (match_operand:DI 1 "memory_operand" "")
20601                             (match_operand:DI 2 "immediate_operand" "")))
20602               (clobber (reg:CC FLAGS_REG))])]
20603   "TARGET_SLOW_IMUL_IMM32_MEM && !optimize_size
20604    && !satisfies_constraint_K (operands[2])"
20605   [(set (match_dup 3) (match_dup 1))
20606    (parallel [(set (match_dup 0) (mult:DI (match_dup 3) (match_dup 2)))
20607               (clobber (reg:CC FLAGS_REG))])]
20608 "")
20609
20610 (define_peephole2
20611   [(match_scratch:SI 3 "r")
20612    (parallel [(set (match_operand:SI 0 "register_operand" "")
20613                    (mult:SI (match_operand:SI 1 "memory_operand" "")
20614                             (match_operand:SI 2 "immediate_operand" "")))
20615               (clobber (reg:CC FLAGS_REG))])]
20616   "TARGET_SLOW_IMUL_IMM32_MEM && !optimize_size
20617    && !satisfies_constraint_K (operands[2])"
20618   [(set (match_dup 3) (match_dup 1))
20619    (parallel [(set (match_dup 0) (mult:SI (match_dup 3) (match_dup 2)))
20620               (clobber (reg:CC FLAGS_REG))])]
20621 "")
20622
20623 (define_peephole2
20624   [(match_scratch:SI 3 "r")
20625    (parallel [(set (match_operand:DI 0 "register_operand" "")
20626                    (zero_extend:DI
20627                      (mult:SI (match_operand:SI 1 "memory_operand" "")
20628                               (match_operand:SI 2 "immediate_operand" ""))))
20629               (clobber (reg:CC FLAGS_REG))])]
20630   "TARGET_SLOW_IMUL_IMM32_MEM && !optimize_size
20631    && !satisfies_constraint_K (operands[2])"
20632   [(set (match_dup 3) (match_dup 1))
20633    (parallel [(set (match_dup 0) (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
20634               (clobber (reg:CC FLAGS_REG))])]
20635 "")
20636
20637 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
20638 ;; Convert it into imul reg, reg
20639 ;; It would be better to force assembler to encode instruction using long
20640 ;; immediate, but there is apparently no way to do so.
20641 (define_peephole2
20642   [(parallel [(set (match_operand:DI 0 "register_operand" "")
20643                    (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
20644                             (match_operand:DI 2 "const_int_operand" "")))
20645               (clobber (reg:CC FLAGS_REG))])
20646    (match_scratch:DI 3 "r")]
20647   "TARGET_SLOW_IMUL_IMM8 && !optimize_size
20648    && satisfies_constraint_K (operands[2])"
20649   [(set (match_dup 3) (match_dup 2))
20650    (parallel [(set (match_dup 0) (mult:DI (match_dup 0) (match_dup 3)))
20651               (clobber (reg:CC FLAGS_REG))])]
20652 {
20653   if (!rtx_equal_p (operands[0], operands[1]))
20654     emit_move_insn (operands[0], operands[1]);
20655 })
20656
20657 (define_peephole2
20658   [(parallel [(set (match_operand:SI 0 "register_operand" "")
20659                    (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
20660                             (match_operand:SI 2 "const_int_operand" "")))
20661               (clobber (reg:CC FLAGS_REG))])
20662    (match_scratch:SI 3 "r")]
20663   "TARGET_SLOW_IMUL_IMM8 && !optimize_size
20664    && satisfies_constraint_K (operands[2])"
20665   [(set (match_dup 3) (match_dup 2))
20666    (parallel [(set (match_dup 0) (mult:SI (match_dup 0) (match_dup 3)))
20667               (clobber (reg:CC FLAGS_REG))])]
20668 {
20669   if (!rtx_equal_p (operands[0], operands[1]))
20670     emit_move_insn (operands[0], operands[1]);
20671 })
20672
20673 (define_peephole2
20674   [(parallel [(set (match_operand:HI 0 "register_operand" "")
20675                    (mult:HI (match_operand:HI 1 "nonimmediate_operand" "")
20676                             (match_operand:HI 2 "immediate_operand" "")))
20677               (clobber (reg:CC FLAGS_REG))])
20678    (match_scratch:HI 3 "r")]
20679   "TARGET_SLOW_IMUL_IMM8 && !optimize_size"
20680   [(set (match_dup 3) (match_dup 2))
20681    (parallel [(set (match_dup 0) (mult:HI (match_dup 0) (match_dup 3)))
20682               (clobber (reg:CC FLAGS_REG))])]
20683 {
20684   if (!rtx_equal_p (operands[0], operands[1]))
20685     emit_move_insn (operands[0], operands[1]);
20686 })
20687
20688 ;; After splitting up read-modify operations, array accesses with memory
20689 ;; operands might end up in form:
20690 ;;  sall    $2, %eax
20691 ;;  movl    4(%esp), %edx
20692 ;;  addl    %edx, %eax
20693 ;; instead of pre-splitting:
20694 ;;  sall    $2, %eax
20695 ;;  addl    4(%esp), %eax
20696 ;; Turn it into:
20697 ;;  movl    4(%esp), %edx
20698 ;;  leal    (%edx,%eax,4), %eax
20699
20700 (define_peephole2
20701   [(parallel [(set (match_operand 0 "register_operand" "")
20702                    (ashift (match_operand 1 "register_operand" "")
20703                            (match_operand 2 "const_int_operand" "")))
20704                (clobber (reg:CC FLAGS_REG))])
20705    (set (match_operand 3 "register_operand")
20706         (match_operand 4 "x86_64_general_operand" ""))
20707    (parallel [(set (match_operand 5 "register_operand" "")
20708                    (plus (match_operand 6 "register_operand" "")
20709                          (match_operand 7 "register_operand" "")))
20710                    (clobber (reg:CC FLAGS_REG))])]
20711   "INTVAL (operands[2]) >= 0 && INTVAL (operands[2]) <= 3
20712    /* Validate MODE for lea.  */
20713    && ((!TARGET_PARTIAL_REG_STALL
20714         && (GET_MODE (operands[0]) == QImode
20715             || GET_MODE (operands[0]) == HImode))
20716        || GET_MODE (operands[0]) == SImode
20717        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
20718    /* We reorder load and the shift.  */
20719    && !rtx_equal_p (operands[1], operands[3])
20720    && !reg_overlap_mentioned_p (operands[0], operands[4])
20721    /* Last PLUS must consist of operand 0 and 3.  */
20722    && !rtx_equal_p (operands[0], operands[3])
20723    && (rtx_equal_p (operands[3], operands[6])
20724        || rtx_equal_p (operands[3], operands[7]))
20725    && (rtx_equal_p (operands[0], operands[6])
20726        || rtx_equal_p (operands[0], operands[7]))
20727    /* The intermediate operand 0 must die or be same as output.  */
20728    && (rtx_equal_p (operands[0], operands[5])
20729        || peep2_reg_dead_p (3, operands[0]))"
20730   [(set (match_dup 3) (match_dup 4))
20731    (set (match_dup 0) (match_dup 1))]
20732 {
20733   enum machine_mode mode = GET_MODE (operands[5]) == DImode ? DImode : SImode;
20734   int scale = 1 << INTVAL (operands[2]);
20735   rtx index = gen_lowpart (Pmode, operands[1]);
20736   rtx base = gen_lowpart (Pmode, operands[3]);
20737   rtx dest = gen_lowpart (mode, operands[5]);
20738
20739   operands[1] = gen_rtx_PLUS (Pmode, base,
20740                               gen_rtx_MULT (Pmode, index, GEN_INT (scale)));
20741   if (mode != Pmode)
20742     operands[1] = gen_rtx_SUBREG (mode, operands[1], 0);
20743   operands[0] = dest;
20744 })
20745 \f
20746 ;; Call-value patterns last so that the wildcard operand does not
20747 ;; disrupt insn-recog's switch tables.
20748
20749 (define_insn "*call_value_pop_0"
20750   [(set (match_operand 0 "" "")
20751         (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
20752               (match_operand:SI 2 "" "")))
20753    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
20754                             (match_operand:SI 3 "immediate_operand" "")))]
20755   "!TARGET_64BIT"
20756 {
20757   if (SIBLING_CALL_P (insn))
20758     return "jmp\t%P1";
20759   else
20760     return "call\t%P1";
20761 }
20762   [(set_attr "type" "callv")])
20763
20764 (define_insn "*call_value_pop_1"
20765   [(set (match_operand 0 "" "")
20766         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
20767               (match_operand:SI 2 "" "")))
20768    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
20769                             (match_operand:SI 3 "immediate_operand" "i")))]
20770   "!TARGET_64BIT"
20771 {
20772   if (constant_call_address_operand (operands[1], Pmode))
20773     {
20774       if (SIBLING_CALL_P (insn))
20775         return "jmp\t%P1";
20776       else
20777         return "call\t%P1";
20778     }
20779   if (SIBLING_CALL_P (insn))
20780     return "jmp\t%A1";
20781   else
20782     return "call\t%A1";
20783 }
20784   [(set_attr "type" "callv")])
20785
20786 (define_insn "*call_value_0"
20787   [(set (match_operand 0 "" "")
20788         (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
20789               (match_operand:SI 2 "" "")))]
20790   "!TARGET_64BIT"
20791 {
20792   if (SIBLING_CALL_P (insn))
20793     return "jmp\t%P1";
20794   else
20795     return "call\t%P1";
20796 }
20797   [(set_attr "type" "callv")])
20798
20799 (define_insn "*call_value_0_rex64"
20800   [(set (match_operand 0 "" "")
20801         (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
20802               (match_operand:DI 2 "const_int_operand" "")))]
20803   "TARGET_64BIT"
20804 {
20805   if (SIBLING_CALL_P (insn))
20806     return "jmp\t%P1";
20807   else
20808     return "call\t%P1";
20809 }
20810   [(set_attr "type" "callv")])
20811
20812 (define_insn "*call_value_1"
20813   [(set (match_operand 0 "" "")
20814         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
20815               (match_operand:SI 2 "" "")))]
20816   "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
20817 {
20818   if (constant_call_address_operand (operands[1], Pmode))
20819     return "call\t%P1";
20820   return "call\t%A1";
20821 }
20822   [(set_attr "type" "callv")])
20823
20824 (define_insn "*sibcall_value_1"
20825   [(set (match_operand 0 "" "")
20826         (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "s,c,d,a"))
20827               (match_operand:SI 2 "" "")))]
20828   "SIBLING_CALL_P (insn) && !TARGET_64BIT"
20829 {
20830   if (constant_call_address_operand (operands[1], Pmode))
20831     return "jmp\t%P1";
20832   return "jmp\t%A1";
20833 }
20834   [(set_attr "type" "callv")])
20835
20836 (define_insn "*call_value_1_rex64"
20837   [(set (match_operand 0 "" "")
20838         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rsm"))
20839               (match_operand:DI 2 "" "")))]
20840   "!SIBLING_CALL_P (insn) && TARGET_64BIT
20841    && ix86_cmodel != CM_LARGE && ix86_cmodel != CM_LARGE_PIC"
20842 {
20843   if (constant_call_address_operand (operands[1], Pmode))
20844     return "call\t%P1";
20845   return "call\t%A1";
20846 }
20847   [(set_attr "type" "callv")])
20848
20849 (define_insn "*call_value_1_rex64_large"
20850   [(set (match_operand 0 "" "")
20851         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rm"))
20852               (match_operand:DI 2 "" "")))]
20853   "!SIBLING_CALL_P (insn) && TARGET_64BIT"
20854   "call\t%A1"
20855   [(set_attr "type" "callv")])
20856
20857 (define_insn "*sibcall_value_1_rex64"
20858   [(set (match_operand 0 "" "")
20859         (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
20860               (match_operand:DI 2 "" "")))]
20861   "SIBLING_CALL_P (insn) && TARGET_64BIT"
20862   "jmp\t%P1"
20863   [(set_attr "type" "callv")])
20864
20865 (define_insn "*sibcall_value_1_rex64_v"
20866   [(set (match_operand 0 "" "")
20867         (call (mem:QI (reg:DI R11_REG))
20868               (match_operand:DI 1 "" "")))]
20869   "SIBLING_CALL_P (insn) && TARGET_64BIT"
20870   "jmp\t{*%%}r11"
20871   [(set_attr "type" "callv")])
20872 \f
20873 ;; We used to use "int $5", in honor of #BR which maps to interrupt vector 5.
20874 ;; That, however, is usually mapped by the OS to SIGSEGV, which is often
20875 ;; caught for use by garbage collectors and the like.  Using an insn that
20876 ;; maps to SIGILL makes it more likely the program will rightfully die.
20877 ;; Keeping with tradition, "6" is in honor of #UD.
20878 (define_insn "trap"
20879   [(trap_if (const_int 1) (const_int 6))]
20880   ""
20881   { return ASM_SHORT "0x0b0f"; }
20882   [(set_attr "length" "2")])
20883
20884 (define_expand "sse_prologue_save"
20885   [(parallel [(set (match_operand:BLK 0 "" "")
20886                    (unspec:BLK [(reg:DI 21)
20887                                 (reg:DI 22)
20888                                 (reg:DI 23)
20889                                 (reg:DI 24)
20890                                 (reg:DI 25)
20891                                 (reg:DI 26)
20892                                 (reg:DI 27)
20893                                 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
20894               (use (match_operand:DI 1 "register_operand" ""))
20895               (use (match_operand:DI 2 "immediate_operand" ""))
20896               (use (label_ref:DI (match_operand 3 "" "")))])]
20897   "TARGET_64BIT"
20898   "")
20899
20900 (define_insn "*sse_prologue_save_insn"
20901   [(set (mem:BLK (plus:DI (match_operand:DI 0 "register_operand" "R")
20902                           (match_operand:DI 4 "const_int_operand" "n")))
20903         (unspec:BLK [(reg:DI 21)
20904                      (reg:DI 22)
20905                      (reg:DI 23)
20906                      (reg:DI 24)
20907                      (reg:DI 25)
20908                      (reg:DI 26)
20909                      (reg:DI 27)
20910                      (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
20911    (use (match_operand:DI 1 "register_operand" "r"))
20912    (use (match_operand:DI 2 "const_int_operand" "i"))
20913    (use (label_ref:DI (match_operand 3 "" "X")))]
20914   "TARGET_64BIT
20915    && INTVAL (operands[4]) + X86_64_SSE_REGPARM_MAX * 16 - 16 < 128
20916    && INTVAL (operands[4]) + INTVAL (operands[2]) * 16 >= -128"
20917 {
20918   int i;
20919   operands[0] = gen_rtx_MEM (Pmode,
20920                              gen_rtx_PLUS (Pmode, operands[0], operands[4]));
20921   output_asm_insn ("jmp\t%A1", operands);
20922   for (i = X86_64_SSE_REGPARM_MAX - 1; i >= INTVAL (operands[2]); i--)
20923     {
20924       operands[4] = adjust_address (operands[0], DImode, i*16);
20925       operands[5] = gen_rtx_REG (TImode, SSE_REGNO (i));
20926       PUT_MODE (operands[4], TImode);
20927       if (GET_CODE (XEXP (operands[0], 0)) != PLUS)
20928         output_asm_insn ("rex", operands);
20929       output_asm_insn ("movaps\t{%5, %4|%4, %5}", operands);
20930     }
20931   (*targetm.asm_out.internal_label) (asm_out_file, "L",
20932                                      CODE_LABEL_NUMBER (operands[3]));
20933   return "";
20934 }
20935   [(set_attr "type" "other")
20936    (set_attr "length_immediate" "0")
20937    (set_attr "length_address" "0")
20938    (set_attr "length" "34")
20939    (set_attr "memory" "store")
20940    (set_attr "modrm" "0")
20941    (set_attr "mode" "DI")])
20942
20943 (define_expand "prefetch"
20944   [(prefetch (match_operand 0 "address_operand" "")
20945              (match_operand:SI 1 "const_int_operand" "")
20946              (match_operand:SI 2 "const_int_operand" ""))]
20947   "TARGET_PREFETCH_SSE || TARGET_3DNOW"
20948 {
20949   int rw = INTVAL (operands[1]);
20950   int locality = INTVAL (operands[2]);
20951
20952   gcc_assert (rw == 0 || rw == 1);
20953   gcc_assert (locality >= 0 && locality <= 3);
20954   gcc_assert (GET_MODE (operands[0]) == Pmode
20955               || GET_MODE (operands[0]) == VOIDmode);
20956
20957   /* Use 3dNOW prefetch in case we are asking for write prefetch not
20958      supported by SSE counterpart or the SSE prefetch is not available
20959      (K6 machines).  Otherwise use SSE prefetch as it allows specifying
20960      of locality.  */
20961   if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
20962     operands[2] = GEN_INT (3);
20963   else
20964     operands[1] = const0_rtx;
20965 })
20966
20967 (define_insn "*prefetch_sse"
20968   [(prefetch (match_operand:SI 0 "address_operand" "p")
20969              (const_int 0)
20970              (match_operand:SI 1 "const_int_operand" ""))]
20971   "TARGET_PREFETCH_SSE && !TARGET_64BIT"
20972 {
20973   static const char * const patterns[4] = {
20974    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
20975   };
20976
20977   int locality = INTVAL (operands[1]);
20978   gcc_assert (locality >= 0 && locality <= 3);
20979
20980   return patterns[locality];
20981 }
20982   [(set_attr "type" "sse")
20983    (set_attr "memory" "none")])
20984
20985 (define_insn "*prefetch_sse_rex"
20986   [(prefetch (match_operand:DI 0 "address_operand" "p")
20987              (const_int 0)
20988              (match_operand:SI 1 "const_int_operand" ""))]
20989   "TARGET_PREFETCH_SSE && TARGET_64BIT"
20990 {
20991   static const char * const patterns[4] = {
20992    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
20993   };
20994
20995   int locality = INTVAL (operands[1]);
20996   gcc_assert (locality >= 0 && locality <= 3);
20997
20998   return patterns[locality];
20999 }
21000   [(set_attr "type" "sse")
21001    (set_attr "memory" "none")])
21002
21003 (define_insn "*prefetch_3dnow"
21004   [(prefetch (match_operand:SI 0 "address_operand" "p")
21005              (match_operand:SI 1 "const_int_operand" "n")
21006              (const_int 3))]
21007   "TARGET_3DNOW && !TARGET_64BIT"
21008 {
21009   if (INTVAL (operands[1]) == 0)
21010     return "prefetch\t%a0";
21011   else
21012     return "prefetchw\t%a0";
21013 }
21014   [(set_attr "type" "mmx")
21015    (set_attr "memory" "none")])
21016
21017 (define_insn "*prefetch_3dnow_rex"
21018   [(prefetch (match_operand:DI 0 "address_operand" "p")
21019              (match_operand:SI 1 "const_int_operand" "n")
21020              (const_int 3))]
21021   "TARGET_3DNOW && TARGET_64BIT"
21022 {
21023   if (INTVAL (operands[1]) == 0)
21024     return "prefetch\t%a0";
21025   else
21026     return "prefetchw\t%a0";
21027 }
21028   [(set_attr "type" "mmx")
21029    (set_attr "memory" "none")])
21030
21031 (define_expand "stack_protect_set"
21032   [(match_operand 0 "memory_operand" "")
21033    (match_operand 1 "memory_operand" "")]
21034   ""
21035 {
21036 #ifdef TARGET_THREAD_SSP_OFFSET
21037   if (TARGET_64BIT)
21038     emit_insn (gen_stack_tls_protect_set_di (operands[0],
21039                                         GEN_INT (TARGET_THREAD_SSP_OFFSET)));
21040   else
21041     emit_insn (gen_stack_tls_protect_set_si (operands[0],
21042                                         GEN_INT (TARGET_THREAD_SSP_OFFSET)));
21043 #else
21044   if (TARGET_64BIT)
21045     emit_insn (gen_stack_protect_set_di (operands[0], operands[1]));
21046   else
21047     emit_insn (gen_stack_protect_set_si (operands[0], operands[1]));
21048 #endif
21049   DONE;
21050 })
21051
21052 (define_insn "stack_protect_set_si"
21053   [(set (match_operand:SI 0 "memory_operand" "=m")
21054         (unspec:SI [(match_operand:SI 1 "memory_operand" "m")] UNSPEC_SP_SET))
21055    (set (match_scratch:SI 2 "=&r") (const_int 0))
21056    (clobber (reg:CC FLAGS_REG))]
21057   ""
21058   "mov{l}\t{%1, %2|%2, %1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
21059   [(set_attr "type" "multi")])
21060
21061 (define_insn "stack_protect_set_di"
21062   [(set (match_operand:DI 0 "memory_operand" "=m")
21063         (unspec:DI [(match_operand:DI 1 "memory_operand" "m")] UNSPEC_SP_SET))
21064    (set (match_scratch:DI 2 "=&r") (const_int 0))
21065    (clobber (reg:CC FLAGS_REG))]
21066   "TARGET_64BIT"
21067   "mov{q}\t{%1, %2|%2, %1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
21068   [(set_attr "type" "multi")])
21069
21070 (define_insn "stack_tls_protect_set_si"
21071   [(set (match_operand:SI 0 "memory_operand" "=m")
21072         (unspec:SI [(match_operand:SI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
21073    (set (match_scratch:SI 2 "=&r") (const_int 0))
21074    (clobber (reg:CC FLAGS_REG))]
21075   ""
21076   "mov{l}\t{%%gs:%P1, %2|%2, DWORD PTR gs:%P1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
21077   [(set_attr "type" "multi")])
21078
21079 (define_insn "stack_tls_protect_set_di"
21080   [(set (match_operand:DI 0 "memory_operand" "=m")
21081         (unspec:DI [(match_operand:DI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
21082    (set (match_scratch:DI 2 "=&r") (const_int 0))
21083    (clobber (reg:CC FLAGS_REG))]
21084   "TARGET_64BIT"
21085   {
21086      /* The kernel uses a different segment register for performance reasons; a
21087         system call would not have to trash the userspace segment register,
21088         which would be expensive */
21089      if (ix86_cmodel != CM_KERNEL)
21090         return "mov{q}\t{%%fs:%P1, %2|%2, QWORD PTR fs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2";
21091      else
21092         return "mov{q}\t{%%gs:%P1, %2|%2, QWORD PTR gs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2";
21093   }
21094   [(set_attr "type" "multi")])
21095
21096 (define_expand "stack_protect_test"
21097   [(match_operand 0 "memory_operand" "")
21098    (match_operand 1 "memory_operand" "")
21099    (match_operand 2 "" "")]
21100   ""
21101 {
21102   rtx flags = gen_rtx_REG (CCZmode, FLAGS_REG);
21103   ix86_compare_op0 = operands[0];
21104   ix86_compare_op1 = operands[1];
21105   ix86_compare_emitted = flags;
21106
21107 #ifdef TARGET_THREAD_SSP_OFFSET
21108   if (TARGET_64BIT)
21109     emit_insn (gen_stack_tls_protect_test_di (flags, operands[0],
21110                                         GEN_INT (TARGET_THREAD_SSP_OFFSET)));
21111   else
21112     emit_insn (gen_stack_tls_protect_test_si (flags, operands[0],
21113                                         GEN_INT (TARGET_THREAD_SSP_OFFSET)));
21114 #else
21115   if (TARGET_64BIT)
21116     emit_insn (gen_stack_protect_test_di (flags, operands[0], operands[1]));
21117   else
21118     emit_insn (gen_stack_protect_test_si (flags, operands[0], operands[1]));
21119 #endif
21120   emit_jump_insn (gen_beq (operands[2]));
21121   DONE;
21122 })
21123
21124 (define_insn "stack_protect_test_si"
21125   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
21126         (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
21127                      (match_operand:SI 2 "memory_operand" "m")]
21128                     UNSPEC_SP_TEST))
21129    (clobber (match_scratch:SI 3 "=&r"))]
21130   ""
21131   "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%2, %3|%3, %2}"
21132   [(set_attr "type" "multi")])
21133
21134 (define_insn "stack_protect_test_di"
21135   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
21136         (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
21137                      (match_operand:DI 2 "memory_operand" "m")]
21138                     UNSPEC_SP_TEST))
21139    (clobber (match_scratch:DI 3 "=&r"))]
21140   "TARGET_64BIT"
21141   "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%2, %3|%3, %2}"
21142   [(set_attr "type" "multi")])
21143
21144 (define_insn "stack_tls_protect_test_si"
21145   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
21146         (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
21147                      (match_operand:SI 2 "const_int_operand" "i")]
21148                     UNSPEC_SP_TLS_TEST))
21149    (clobber (match_scratch:SI 3 "=r"))]
21150   ""
21151   "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%%gs:%P2, %3|%3, DWORD PTR gs:%P2}"
21152   [(set_attr "type" "multi")])
21153
21154 (define_insn "stack_tls_protect_test_di"
21155   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
21156         (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
21157                      (match_operand:DI 2 "const_int_operand" "i")]
21158                     UNSPEC_SP_TLS_TEST))
21159    (clobber (match_scratch:DI 3 "=r"))]
21160   "TARGET_64BIT"
21161   {
21162      /* The kernel uses a different segment register for performance reasons; a
21163         system call would not have to trash the userspace segment register,
21164         which would be expensive */
21165      if (ix86_cmodel != CM_KERNEL)
21166         return "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%fs:%P2, %3|%3, QWORD PTR fs:%P2}";
21167      else
21168         return "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%gs:%P2, %3|%3, QWORD PTR gs:%P2}";
21169   }
21170   [(set_attr "type" "multi")])
21171
21172 (define_mode_iterator CRC32MODE [QI HI SI])
21173 (define_mode_attr crc32modesuffix [(QI "b") (HI "w") (SI "l")])
21174 (define_mode_attr crc32modeconstraint [(QI "qm") (HI "rm") (SI "rm")])
21175
21176 (define_insn "sse4_2_crc32<mode>"
21177   [(set (match_operand:SI 0 "register_operand" "=r")
21178         (unspec:SI
21179           [(match_operand:SI 1 "register_operand" "0")
21180            (match_operand:CRC32MODE 2 "nonimmediate_operand" "<crc32modeconstraint>")]
21181           UNSPEC_CRC32))]
21182   "TARGET_SSE4_2"
21183   "crc32<crc32modesuffix>\t{%2, %0|%0, %2}"
21184   [(set_attr "type" "sselog1")
21185    (set_attr "prefix_rep" "1")
21186    (set_attr "prefix_extra" "1")
21187    (set_attr "mode" "SI")])
21188
21189 (define_insn "sse4_2_crc32di"
21190   [(set (match_operand:DI 0 "register_operand" "=r")
21191         (unspec:DI
21192           [(match_operand:DI 1 "register_operand" "0")
21193            (match_operand:DI 2 "nonimmediate_operand" "rm")]
21194           UNSPEC_CRC32))]
21195   "TARGET_SSE4_2 && TARGET_64BIT"
21196   "crc32q\t{%2, %0|%0, %2}"
21197   [(set_attr "type" "sselog1")
21198    (set_attr "prefix_rep" "1")
21199    (set_attr "prefix_extra" "1")
21200    (set_attr "mode" "DI")])
21201
21202 (include "mmx.md")
21203 (include "sse.md")
21204 (include "sync.md")