OSDN Git Service

84911ff5c2337194a5b54a389f1cf3b77b59a33e
[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_NOP                  48)     ; prevents combiner cleverness
99    (UNSPEC_PFRCP                49)
100    (UNSPEC_PFRCPIT1             40)
101    (UNSPEC_PFRCPIT2             41)
102    (UNSPEC_PFRSQRT              42)
103    (UNSPEC_PFRSQIT1             43)
104    (UNSPEC_MFENCE               44)
105    (UNSPEC_LFENCE               45)
106    (UNSPEC_PSADBW               46)
107    (UNSPEC_LDDQU                47)
108
109    ; Generic math support
110    (UNSPEC_COPYSIGN             50)
111    (UNSPEC_IEEE_MIN             51)     ; not commutative
112    (UNSPEC_IEEE_MAX             52)     ; not commutative
113
114    ; x87 Floating point
115    (UNSPEC_SIN                  60)
116    (UNSPEC_COS                  61)
117    (UNSPEC_FPATAN               62)
118    (UNSPEC_FYL2X                63)
119    (UNSPEC_FYL2XP1              64)
120    (UNSPEC_FRNDINT              65)
121    (UNSPEC_FIST                 66)
122    (UNSPEC_F2XM1                67)
123    (UNSPEC_TAN                  68)
124    (UNSPEC_FXAM                 69)
125
126    ; x87 Rounding
127    (UNSPEC_FRNDINT_FLOOR        70)
128    (UNSPEC_FRNDINT_CEIL         71)
129    (UNSPEC_FRNDINT_TRUNC        72)
130    (UNSPEC_FRNDINT_MASK_PM      73)
131    (UNSPEC_FIST_FLOOR           74)
132    (UNSPEC_FIST_CEIL            75)
133
134    ; x87 Double output FP
135    (UNSPEC_SINCOS_COS           80)
136    (UNSPEC_SINCOS_SIN           81)
137    (UNSPEC_XTRACT_FRACT         84)
138    (UNSPEC_XTRACT_EXP           85)
139    (UNSPEC_FSCALE_FRACT         86)
140    (UNSPEC_FSCALE_EXP           87)
141    (UNSPEC_FPREM_F              88)
142    (UNSPEC_FPREM_U              89)
143    (UNSPEC_FPREM1_F             90)
144    (UNSPEC_FPREM1_U             91)
145
146    (UNSPEC_C2_FLAG              95)
147
148    ; SSP patterns
149    (UNSPEC_SP_SET               100)
150    (UNSPEC_SP_TEST              101)
151    (UNSPEC_SP_TLS_SET           102)
152    (UNSPEC_SP_TLS_TEST          103)
153
154    ; SSSE3
155    (UNSPEC_PSHUFB               120)
156    (UNSPEC_PSIGN                121)
157    (UNSPEC_PALIGNR              122)
158
159    ; For SSE4A support
160    (UNSPEC_EXTRQI               130)
161    (UNSPEC_EXTRQ                131)
162    (UNSPEC_INSERTQI             132)
163    (UNSPEC_INSERTQ              133)
164
165    ; For SSE4.1 support
166    (UNSPEC_BLENDV               134)
167    (UNSPEC_INSERTPS             135)
168    (UNSPEC_DP                   136)
169    (UNSPEC_MOVNTDQA             137)
170    (UNSPEC_MPSADBW              138)
171    (UNSPEC_PHMINPOSUW           139)
172    (UNSPEC_PTEST                140)
173    (UNSPEC_ROUND                141)
174
175    ; For SSE4.2 support
176    (UNSPEC_CRC32                143)
177    (UNSPEC_PCMPESTR             144)
178    (UNSPEC_PCMPISTR             145)
179
180    ;; For SSE5
181    (UNSPEC_SSE5_INTRINSIC       150)
182    (UNSPEC_SSE5_UNSIGNED_CMP    151)
183    (UNSPEC_SSE5_TRUEFALSE       152)
184    (UNSPEC_SSE5_PERMUTE         153)
185    (UNSPEC_SSE5_ASHIFT          154)
186    (UNSPEC_SSE5_LSHIFT          155)
187    (UNSPEC_FRCZ                 156)
188    (UNSPEC_CVTPH2PS             157)
189    (UNSPEC_CVTPS2PH             158)
190   ])
191
192 (define_constants
193   [(UNSPECV_BLOCKAGE            0)
194    (UNSPECV_STACK_PROBE         1)
195    (UNSPECV_EMMS                2)
196    (UNSPECV_LDMXCSR             3)
197    (UNSPECV_STMXCSR             4)
198    (UNSPECV_FEMMS               5)
199    (UNSPECV_CLFLUSH             6)
200    (UNSPECV_ALIGN               7)
201    (UNSPECV_MONITOR             8)
202    (UNSPECV_MWAIT               9)
203    (UNSPECV_CMPXCHG_1           10)
204    (UNSPECV_CMPXCHG_2           11)
205    (UNSPECV_XCHG                12)
206    (UNSPECV_LOCK                13)
207    (UNSPECV_PROLOGUE_USE        14)
208   ])
209
210 ;; Constants to represent pcomtrue/pcomfalse variants
211 (define_constants
212   [(PCOM_FALSE                  0)
213    (PCOM_TRUE                   1)
214    (COM_FALSE_S                 2)
215    (COM_FALSE_P                 3)
216    (COM_TRUE_S                  4)
217    (COM_TRUE_P                  5)
218   ])
219
220 ;; Registers by name.
221 (define_constants
222   [(AX_REG                       0)
223    (DX_REG                       1)
224    (CX_REG                       2)
225    (SI_REG                       4)
226    (DI_REG                       5)
227    (BP_REG                       6)
228    (SP_REG                       7)
229    (FLAGS_REG                   17)
230    (FPSR_REG                    18)
231    (FPCR_REG                    19)
232    (R10_REG                     39)
233    (R11_REG                     40)
234   ])
235
236 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
237 ;; from i386.c.
238
239 ;; In C guard expressions, put expressions which may be compile-time
240 ;; constants first.  This allows for better optimization.  For
241 ;; example, write "TARGET_64BIT && reload_completed", not
242 ;; "reload_completed && TARGET_64BIT".
243
244 \f
245 ;; Processor type.  This attribute must exactly match the processor_type
246 ;; enumeration in i386.h.
247 (define_attr "cpu" "i386,i486,pentium,pentiumpro,geode,k6,athlon,pentium4,k8,
248                     nocona,core2,generic32,generic64,amdfam10"
249   (const (symbol_ref "ix86_tune")))
250
251 ;; A basic instruction type.  Refinements due to arguments to be
252 ;; provided in other attributes.
253 (define_attr "type"
254   "other,multi,
255    alu,alu1,negnot,imov,imovx,lea,
256    incdec,ishift,ishift1,rotate,rotate1,imul,idiv,
257    icmp,test,ibr,setcc,icmov,
258    push,pop,call,callv,leave,
259    str,bitmanip,
260    fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint,
261    sselog,sselog1,sseiadd,sseiadd1,sseishft,sseimul,
262    sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,ssecvt1,sseicvt,ssediv,sseins,
263    ssemuladd,sse4arg,
264    mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft"
265   (const_string "other"))
266
267 ;; Main data type used by the insn
268 (define_attr "mode"
269   "unknown,none,QI,HI,SI,DI,SF,DF,XF,TI,V4SF,V2DF,V2SF,V1DF"
270   (const_string "unknown"))
271
272 ;; The CPU unit operations uses.
273 (define_attr "unit" "integer,i387,sse,mmx,unknown"
274   (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint")
275            (const_string "i387")
276          (eq_attr "type" "sselog,sselog1,sseiadd,sseiadd1,sseishft,sseimul,
277                           sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,
278                           ssecvt1,sseicvt,ssediv,sseins,ssemuladd,sse4arg")
279            (const_string "sse")
280          (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft")
281            (const_string "mmx")
282          (eq_attr "type" "other")
283            (const_string "unknown")]
284          (const_string "integer")))
285
286 ;; The (bounding maximum) length of an instruction immediate.
287 (define_attr "length_immediate" ""
288   (cond [(eq_attr "type" "incdec,setcc,icmov,str,lea,other,multi,idiv,leave,
289                           bitmanip")
290            (const_int 0)
291          (eq_attr "unit" "i387,sse,mmx")
292            (const_int 0)
293          (eq_attr "type" "alu,alu1,negnot,imovx,ishift,rotate,ishift1,rotate1,
294                           imul,icmp,push,pop")
295            (symbol_ref "ix86_attr_length_immediate_default(insn,1)")
296          (eq_attr "type" "imov,test")
297            (symbol_ref "ix86_attr_length_immediate_default(insn,0)")
298          (eq_attr "type" "call")
299            (if_then_else (match_operand 0 "constant_call_address_operand" "")
300              (const_int 4)
301              (const_int 0))
302          (eq_attr "type" "callv")
303            (if_then_else (match_operand 1 "constant_call_address_operand" "")
304              (const_int 4)
305              (const_int 0))
306          ;; We don't know the size before shorten_branches.  Expect
307          ;; the instruction to fit for better scheduling.
308          (eq_attr "type" "ibr")
309            (const_int 1)
310          ]
311          (symbol_ref "/* Update immediate_length and other attributes! */
312                       gcc_unreachable (),1")))
313
314 ;; The (bounding maximum) length of an instruction address.
315 (define_attr "length_address" ""
316   (cond [(eq_attr "type" "str,other,multi,fxch")
317            (const_int 0)
318          (and (eq_attr "type" "call")
319               (match_operand 0 "constant_call_address_operand" ""))
320              (const_int 0)
321          (and (eq_attr "type" "callv")
322               (match_operand 1 "constant_call_address_operand" ""))
323              (const_int 0)
324          ]
325          (symbol_ref "ix86_attr_length_address_default (insn)")))
326
327 ;; Set when length prefix is used.
328 (define_attr "prefix_data16" ""
329   (if_then_else (ior (eq_attr "mode" "HI")
330                      (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF")))
331     (const_int 1)
332     (const_int 0)))
333
334 ;; Set when string REP prefix is used.
335 (define_attr "prefix_rep" ""
336   (if_then_else (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF"))
337     (const_int 1)
338     (const_int 0)))
339
340 ;; Set when 0f opcode prefix is used.
341 (define_attr "prefix_0f" ""
342   (if_then_else
343     (ior (eq_attr "type" "imovx,setcc,icmov,bitmanip")
344          (eq_attr "unit" "sse,mmx"))
345     (const_int 1)
346     (const_int 0)))
347
348 ;; Set when REX opcode prefix is used.
349 (define_attr "prefix_rex" ""
350   (cond [(and (eq_attr "mode" "DI")
351               (eq_attr "type" "!push,pop,call,callv,leave,ibr"))
352            (const_int 1)
353          (and (eq_attr "mode" "QI")
354               (ne (symbol_ref "x86_extended_QIreg_mentioned_p (insn)")
355                   (const_int 0)))
356            (const_int 1)
357          (ne (symbol_ref "x86_extended_reg_mentioned_p (insn)")
358              (const_int 0))
359            (const_int 1)
360         ]
361         (const_int 0)))
362
363 ;; There are also additional prefixes in SSSE3.
364 (define_attr "prefix_extra" "" (const_int 0))
365
366 ;; Set when modrm byte is used.
367 (define_attr "modrm" ""
368   (cond [(eq_attr "type" "str,leave")
369            (const_int 0)
370          (eq_attr "unit" "i387")
371            (const_int 0)
372          (and (eq_attr "type" "incdec")
373               (ior (match_operand:SI 1 "register_operand" "")
374                    (match_operand:HI 1 "register_operand" "")))
375            (const_int 0)
376          (and (eq_attr "type" "push")
377               (not (match_operand 1 "memory_operand" "")))
378            (const_int 0)
379          (and (eq_attr "type" "pop")
380               (not (match_operand 0 "memory_operand" "")))
381            (const_int 0)
382          (and (eq_attr "type" "imov")
383               (ior (and (match_operand 0 "register_operand" "")
384                         (match_operand 1 "immediate_operand" ""))
385                    (ior (and (match_operand 0 "ax_reg_operand" "")
386                              (match_operand 1 "memory_displacement_only_operand" ""))
387                         (and (match_operand 0 "memory_displacement_only_operand" "")
388                              (match_operand 1 "ax_reg_operand" "")))))
389            (const_int 0)
390          (and (eq_attr "type" "call")
391               (match_operand 0 "constant_call_address_operand" ""))
392              (const_int 0)
393          (and (eq_attr "type" "callv")
394               (match_operand 1 "constant_call_address_operand" ""))
395              (const_int 0)
396          ]
397          (const_int 1)))
398
399 ;; The (bounding maximum) length of an instruction in bytes.
400 ;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences.
401 ;; Later we may want to split them and compute proper length as for
402 ;; other insns.
403 (define_attr "length" ""
404   (cond [(eq_attr "type" "other,multi,fistp,frndint")
405            (const_int 16)
406          (eq_attr "type" "fcmp")
407            (const_int 4)
408          (eq_attr "unit" "i387")
409            (plus (const_int 2)
410                  (plus (attr "prefix_data16")
411                        (attr "length_address")))]
412          (plus (plus (attr "modrm")
413                      (plus (attr "prefix_0f")
414                            (plus (attr "prefix_rex")
415                                  (plus (attr "prefix_extra")
416                                        (const_int 1)))))
417                (plus (attr "prefix_rep")
418                      (plus (attr "prefix_data16")
419                            (plus (attr "length_immediate")
420                                  (attr "length_address")))))))
421
422 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
423 ;; `store' if there is a simple memory reference therein, or `unknown'
424 ;; if the instruction is complex.
425
426 (define_attr "memory" "none,load,store,both,unknown"
427   (cond [(eq_attr "type" "other,multi,str")
428            (const_string "unknown")
429          (eq_attr "type" "lea,fcmov,fpspc")
430            (const_string "none")
431          (eq_attr "type" "fistp,leave")
432            (const_string "both")
433          (eq_attr "type" "frndint")
434            (const_string "load")
435          (eq_attr "type" "push")
436            (if_then_else (match_operand 1 "memory_operand" "")
437              (const_string "both")
438              (const_string "store"))
439          (eq_attr "type" "pop")
440            (if_then_else (match_operand 0 "memory_operand" "")
441              (const_string "both")
442              (const_string "load"))
443          (eq_attr "type" "setcc")
444            (if_then_else (match_operand 0 "memory_operand" "")
445              (const_string "store")
446              (const_string "none"))
447          (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp")
448            (if_then_else (ior (match_operand 0 "memory_operand" "")
449                               (match_operand 1 "memory_operand" ""))
450              (const_string "load")
451              (const_string "none"))
452          (eq_attr "type" "ibr")
453            (if_then_else (match_operand 0 "memory_operand" "")
454              (const_string "load")
455              (const_string "none"))
456          (eq_attr "type" "call")
457            (if_then_else (match_operand 0 "constant_call_address_operand" "")
458              (const_string "none")
459              (const_string "load"))
460          (eq_attr "type" "callv")
461            (if_then_else (match_operand 1 "constant_call_address_operand" "")
462              (const_string "none")
463              (const_string "load"))
464          (and (eq_attr "type" "alu1,negnot,ishift1,sselog1")
465               (match_operand 1 "memory_operand" ""))
466            (const_string "both")
467          (and (match_operand 0 "memory_operand" "")
468               (match_operand 1 "memory_operand" ""))
469            (const_string "both")
470          (match_operand 0 "memory_operand" "")
471            (const_string "store")
472          (match_operand 1 "memory_operand" "")
473            (const_string "load")
474          (and (eq_attr "type"
475                  "!alu1,negnot,ishift1,
476                    imov,imovx,icmp,test,bitmanip,
477                    fmov,fcmp,fsgn,
478                    sse,ssemov,ssecmp,ssecomi,ssecvt,ssecvt1,sseicvt,sselog1,
479                    sseiadd1,mmx,mmxmov,mmxcmp,mmxcvt")
480               (match_operand 2 "memory_operand" ""))
481            (const_string "load")
482          (and (eq_attr "type" "icmov,ssemuladd,sse4arg")
483               (match_operand 3 "memory_operand" ""))
484            (const_string "load")
485         ]
486         (const_string "none")))
487
488 ;; Indicates if an instruction has both an immediate and a displacement.
489
490 (define_attr "imm_disp" "false,true,unknown"
491   (cond [(eq_attr "type" "other,multi")
492            (const_string "unknown")
493          (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1")
494               (and (match_operand 0 "memory_displacement_operand" "")
495                    (match_operand 1 "immediate_operand" "")))
496            (const_string "true")
497          (and (eq_attr "type" "alu,ishift,rotate,imul,idiv")
498               (and (match_operand 0 "memory_displacement_operand" "")
499                    (match_operand 2 "immediate_operand" "")))
500            (const_string "true")
501         ]
502         (const_string "false")))
503
504 ;; Indicates if an FP operation has an integer source.
505
506 (define_attr "fp_int_src" "false,true"
507   (const_string "false"))
508
509 ;; Defines rounding mode of an FP operation.
510
511 (define_attr "i387_cw" "trunc,floor,ceil,mask_pm,uninitialized,any"
512   (const_string "any"))
513
514 ;; Describe a user's asm statement.
515 (define_asm_attributes
516   [(set_attr "length" "128")
517    (set_attr "type" "multi")])
518
519 (define_code_iterator plusminus [plus minus])
520
521 ;; Base name for define_insn and insn mnemonic.
522 (define_code_attr addsub [(plus "add") (minus "sub")])
523
524 ;; Mark commutative operators as such in constraints.
525 (define_code_attr comm [(plus "%") (minus "")])
526
527 ;; All single word integer modes.
528 (define_mode_iterator SWI [QI HI SI (DI "TARGET_64BIT")])
529
530 ;; Instruction suffix for integer modes.
531 (define_mode_attr imodesuffix [(QI "b") (HI "w") (SI "l") (DI "q")])
532
533 ;; Register class for integer modes.
534 (define_mode_attr r [(QI "q") (HI "r") (SI "r") (DI "r")])
535
536 ;; Immediate operand constraint for integer modes.
537 (define_mode_attr i [(QI "i") (HI "i") (SI "i") (DI "e")])
538
539 ;; General operand predicate for integer modes.
540 (define_mode_attr general_operand
541         [(QI "general_operand")
542          (HI "general_operand")
543          (SI "general_operand")
544          (DI "x86_64_general_operand")])
545
546 ;; SSE and x87 SFmode and DFmode floating point modes
547 (define_mode_iterator MODEF [SF DF])
548
549 ;; All x87 floating point modes
550 (define_mode_iterator X87MODEF [SF DF XF])
551
552 ;; All integer modes handled by x87 fisttp operator.
553 (define_mode_iterator X87MODEI [HI SI DI])
554
555 ;; All integer modes handled by integer x87 operators.
556 (define_mode_iterator X87MODEI12 [HI SI])
557
558 ;; All integer modes handled by SSE cvtts?2si* operators.
559 (define_mode_iterator SSEMODEI24 [SI DI])
560
561 ;; SSE asm suffix for floating point modes
562 (define_mode_attr ssemodefsuffix [(SF "s") (DF "d")])
563
564 ;; SSE vector mode corresponding to a scalar mode
565 (define_mode_attr ssevecmode
566   [(QI "V16QI") (HI "V8HI") (SI "V4SI") (DI "V2DI") (SF "V4SF") (DF "V2DF")])
567 \f
568 ;; Scheduling descriptions
569
570 (include "pentium.md")
571 (include "ppro.md")
572 (include "k6.md")
573 (include "athlon.md")
574 (include "geode.md")
575
576 \f
577 ;; Operand and operator predicates and constraints
578
579 (include "predicates.md")
580 (include "constraints.md")
581
582 \f
583 ;; Compare instructions.
584
585 ;; All compare insns have expanders that save the operands away without
586 ;; actually generating RTL.  The bCOND or sCOND (emitted immediately
587 ;; after the cmp) will actually emit the cmpM.
588
589 (define_expand "cmpti"
590   [(set (reg:CC FLAGS_REG)
591         (compare:CC (match_operand:TI 0 "nonimmediate_operand" "")
592                     (match_operand:TI 1 "x86_64_general_operand" "")))]
593   "TARGET_64BIT"
594 {
595   if (MEM_P (operands[0]) && MEM_P (operands[1]))
596     operands[0] = force_reg (TImode, operands[0]);
597   ix86_compare_op0 = operands[0];
598   ix86_compare_op1 = operands[1];
599   DONE;
600 })
601
602 (define_expand "cmpdi"
603   [(set (reg:CC FLAGS_REG)
604         (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
605                     (match_operand:DI 1 "x86_64_general_operand" "")))]
606   ""
607 {
608   if (MEM_P (operands[0]) && MEM_P (operands[1]))
609     operands[0] = force_reg (DImode, operands[0]);
610   ix86_compare_op0 = operands[0];
611   ix86_compare_op1 = operands[1];
612   DONE;
613 })
614
615 (define_expand "cmpsi"
616   [(set (reg:CC FLAGS_REG)
617         (compare:CC (match_operand:SI 0 "cmpsi_operand" "")
618                     (match_operand:SI 1 "general_operand" "")))]
619   ""
620 {
621   if (MEM_P (operands[0]) && MEM_P (operands[1]))
622     operands[0] = force_reg (SImode, operands[0]);
623   ix86_compare_op0 = operands[0];
624   ix86_compare_op1 = operands[1];
625   DONE;
626 })
627
628 (define_expand "cmphi"
629   [(set (reg:CC FLAGS_REG)
630         (compare:CC (match_operand:HI 0 "nonimmediate_operand" "")
631                     (match_operand:HI 1 "general_operand" "")))]
632   ""
633 {
634   if (MEM_P (operands[0]) && MEM_P (operands[1]))
635     operands[0] = force_reg (HImode, operands[0]);
636   ix86_compare_op0 = operands[0];
637   ix86_compare_op1 = operands[1];
638   DONE;
639 })
640
641 (define_expand "cmpqi"
642   [(set (reg:CC FLAGS_REG)
643         (compare:CC (match_operand:QI 0 "nonimmediate_operand" "")
644                     (match_operand:QI 1 "general_operand" "")))]
645   "TARGET_QIMODE_MATH"
646 {
647   if (MEM_P (operands[0]) && MEM_P (operands[1]))
648     operands[0] = force_reg (QImode, operands[0]);
649   ix86_compare_op0 = operands[0];
650   ix86_compare_op1 = operands[1];
651   DONE;
652 })
653
654 (define_insn "cmpdi_ccno_1_rex64"
655   [(set (reg FLAGS_REG)
656         (compare (match_operand:DI 0 "nonimmediate_operand" "r,?mr")
657                  (match_operand:DI 1 "const0_operand" "n,n")))]
658   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
659   "@
660    test{q}\t%0, %0
661    cmp{q}\t{%1, %0|%0, %1}"
662   [(set_attr "type" "test,icmp")
663    (set_attr "length_immediate" "0,1")
664    (set_attr "mode" "DI")])
665
666 (define_insn "*cmpdi_minus_1_rex64"
667   [(set (reg FLAGS_REG)
668         (compare (minus:DI (match_operand:DI 0 "nonimmediate_operand" "rm,r")
669                            (match_operand:DI 1 "x86_64_general_operand" "re,mr"))
670                  (const_int 0)))]
671   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)"
672   "cmp{q}\t{%1, %0|%0, %1}"
673   [(set_attr "type" "icmp")
674    (set_attr "mode" "DI")])
675
676 (define_expand "cmpdi_1_rex64"
677   [(set (reg:CC FLAGS_REG)
678         (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
679                     (match_operand:DI 1 "general_operand" "")))]
680   "TARGET_64BIT"
681   "")
682
683 (define_insn "cmpdi_1_insn_rex64"
684   [(set (reg FLAGS_REG)
685         (compare (match_operand:DI 0 "nonimmediate_operand" "mr,r")
686                  (match_operand:DI 1 "x86_64_general_operand" "re,mr")))]
687   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
688   "cmp{q}\t{%1, %0|%0, %1}"
689   [(set_attr "type" "icmp")
690    (set_attr "mode" "DI")])
691
692
693 (define_insn "*cmpsi_ccno_1"
694   [(set (reg FLAGS_REG)
695         (compare (match_operand:SI 0 "nonimmediate_operand" "r,?mr")
696                  (match_operand:SI 1 "const0_operand" "n,n")))]
697   "ix86_match_ccmode (insn, CCNOmode)"
698   "@
699    test{l}\t%0, %0
700    cmp{l}\t{%1, %0|%0, %1}"
701   [(set_attr "type" "test,icmp")
702    (set_attr "length_immediate" "0,1")
703    (set_attr "mode" "SI")])
704
705 (define_insn "*cmpsi_minus_1"
706   [(set (reg FLAGS_REG)
707         (compare (minus:SI (match_operand:SI 0 "nonimmediate_operand" "rm,r")
708                            (match_operand:SI 1 "general_operand" "ri,mr"))
709                  (const_int 0)))]
710   "ix86_match_ccmode (insn, CCGOCmode)"
711   "cmp{l}\t{%1, %0|%0, %1}"
712   [(set_attr "type" "icmp")
713    (set_attr "mode" "SI")])
714
715 (define_expand "cmpsi_1"
716   [(set (reg:CC FLAGS_REG)
717         (compare:CC (match_operand:SI 0 "nonimmediate_operand" "")
718                     (match_operand:SI 1 "general_operand" "")))]
719   ""
720   "")
721
722 (define_insn "*cmpsi_1_insn"
723   [(set (reg FLAGS_REG)
724         (compare (match_operand:SI 0 "nonimmediate_operand" "rm,r")
725                  (match_operand:SI 1 "general_operand" "ri,mr")))]
726   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
727     && ix86_match_ccmode (insn, CCmode)"
728   "cmp{l}\t{%1, %0|%0, %1}"
729   [(set_attr "type" "icmp")
730    (set_attr "mode" "SI")])
731
732 (define_insn "*cmphi_ccno_1"
733   [(set (reg FLAGS_REG)
734         (compare (match_operand:HI 0 "nonimmediate_operand" "r,?mr")
735                  (match_operand:HI 1 "const0_operand" "n,n")))]
736   "ix86_match_ccmode (insn, CCNOmode)"
737   "@
738    test{w}\t%0, %0
739    cmp{w}\t{%1, %0|%0, %1}"
740   [(set_attr "type" "test,icmp")
741    (set_attr "length_immediate" "0,1")
742    (set_attr "mode" "HI")])
743
744 (define_insn "*cmphi_minus_1"
745   [(set (reg FLAGS_REG)
746         (compare (minus:HI (match_operand:HI 0 "nonimmediate_operand" "rm,r")
747                            (match_operand:HI 1 "general_operand" "ri,mr"))
748                  (const_int 0)))]
749   "ix86_match_ccmode (insn, CCGOCmode)"
750   "cmp{w}\t{%1, %0|%0, %1}"
751   [(set_attr "type" "icmp")
752    (set_attr "mode" "HI")])
753
754 (define_insn "*cmphi_1"
755   [(set (reg FLAGS_REG)
756         (compare (match_operand:HI 0 "nonimmediate_operand" "rm,r")
757                  (match_operand:HI 1 "general_operand" "ri,mr")))]
758   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
759    && ix86_match_ccmode (insn, CCmode)"
760   "cmp{w}\t{%1, %0|%0, %1}"
761   [(set_attr "type" "icmp")
762    (set_attr "mode" "HI")])
763
764 (define_insn "*cmpqi_ccno_1"
765   [(set (reg FLAGS_REG)
766         (compare (match_operand:QI 0 "nonimmediate_operand" "q,?mq")
767                  (match_operand:QI 1 "const0_operand" "n,n")))]
768   "ix86_match_ccmode (insn, CCNOmode)"
769   "@
770    test{b}\t%0, %0
771    cmp{b}\t{$0, %0|%0, 0}"
772   [(set_attr "type" "test,icmp")
773    (set_attr "length_immediate" "0,1")
774    (set_attr "mode" "QI")])
775
776 (define_insn "*cmpqi_1"
777   [(set (reg FLAGS_REG)
778         (compare (match_operand:QI 0 "nonimmediate_operand" "qm,q")
779                  (match_operand:QI 1 "general_operand" "qi,mq")))]
780   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
781     && ix86_match_ccmode (insn, CCmode)"
782   "cmp{b}\t{%1, %0|%0, %1}"
783   [(set_attr "type" "icmp")
784    (set_attr "mode" "QI")])
785
786 (define_insn "*cmpqi_minus_1"
787   [(set (reg FLAGS_REG)
788         (compare (minus:QI (match_operand:QI 0 "nonimmediate_operand" "qm,q")
789                            (match_operand:QI 1 "general_operand" "qi,mq"))
790                  (const_int 0)))]
791   "ix86_match_ccmode (insn, CCGOCmode)"
792   "cmp{b}\t{%1, %0|%0, %1}"
793   [(set_attr "type" "icmp")
794    (set_attr "mode" "QI")])
795
796 (define_insn "*cmpqi_ext_1"
797   [(set (reg FLAGS_REG)
798         (compare
799           (match_operand:QI 0 "general_operand" "Qm")
800           (subreg:QI
801             (zero_extract:SI
802               (match_operand 1 "ext_register_operand" "Q")
803               (const_int 8)
804               (const_int 8)) 0)))]
805   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
806   "cmp{b}\t{%h1, %0|%0, %h1}"
807   [(set_attr "type" "icmp")
808    (set_attr "mode" "QI")])
809
810 (define_insn "*cmpqi_ext_1_rex64"
811   [(set (reg FLAGS_REG)
812         (compare
813           (match_operand:QI 0 "register_operand" "Q")
814           (subreg:QI
815             (zero_extract:SI
816               (match_operand 1 "ext_register_operand" "Q")
817               (const_int 8)
818               (const_int 8)) 0)))]
819   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
820   "cmp{b}\t{%h1, %0|%0, %h1}"
821   [(set_attr "type" "icmp")
822    (set_attr "mode" "QI")])
823
824 (define_insn "*cmpqi_ext_2"
825   [(set (reg FLAGS_REG)
826         (compare
827           (subreg:QI
828             (zero_extract:SI
829               (match_operand 0 "ext_register_operand" "Q")
830               (const_int 8)
831               (const_int 8)) 0)
832           (match_operand:QI 1 "const0_operand" "n")))]
833   "ix86_match_ccmode (insn, CCNOmode)"
834   "test{b}\t%h0, %h0"
835   [(set_attr "type" "test")
836    (set_attr "length_immediate" "0")
837    (set_attr "mode" "QI")])
838
839 (define_expand "cmpqi_ext_3"
840   [(set (reg:CC FLAGS_REG)
841         (compare:CC
842           (subreg:QI
843             (zero_extract:SI
844               (match_operand 0 "ext_register_operand" "")
845               (const_int 8)
846               (const_int 8)) 0)
847           (match_operand:QI 1 "general_operand" "")))]
848   ""
849   "")
850
851 (define_insn "cmpqi_ext_3_insn"
852   [(set (reg FLAGS_REG)
853         (compare
854           (subreg:QI
855             (zero_extract:SI
856               (match_operand 0 "ext_register_operand" "Q")
857               (const_int 8)
858               (const_int 8)) 0)
859           (match_operand:QI 1 "general_operand" "Qmn")))]
860   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
861   "cmp{b}\t{%1, %h0|%h0, %1}"
862   [(set_attr "type" "icmp")
863    (set_attr "mode" "QI")])
864
865 (define_insn "cmpqi_ext_3_insn_rex64"
866   [(set (reg FLAGS_REG)
867         (compare
868           (subreg:QI
869             (zero_extract:SI
870               (match_operand 0 "ext_register_operand" "Q")
871               (const_int 8)
872               (const_int 8)) 0)
873           (match_operand:QI 1 "nonmemory_operand" "Qn")))]
874   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
875   "cmp{b}\t{%1, %h0|%h0, %1}"
876   [(set_attr "type" "icmp")
877    (set_attr "mode" "QI")])
878
879 (define_insn "*cmpqi_ext_4"
880   [(set (reg FLAGS_REG)
881         (compare
882           (subreg:QI
883             (zero_extract:SI
884               (match_operand 0 "ext_register_operand" "Q")
885               (const_int 8)
886               (const_int 8)) 0)
887           (subreg:QI
888             (zero_extract:SI
889               (match_operand 1 "ext_register_operand" "Q")
890               (const_int 8)
891               (const_int 8)) 0)))]
892   "ix86_match_ccmode (insn, CCmode)"
893   "cmp{b}\t{%h1, %h0|%h0, %h1}"
894   [(set_attr "type" "icmp")
895    (set_attr "mode" "QI")])
896
897 ;; These implement float point compares.
898 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
899 ;; which would allow mix and match FP modes on the compares.  Which is what
900 ;; the old patterns did, but with many more of them.
901
902 (define_expand "cmpxf"
903   [(set (reg:CC FLAGS_REG)
904         (compare:CC (match_operand:XF 0 "nonmemory_operand" "")
905                     (match_operand:XF 1 "nonmemory_operand" "")))]
906   "TARGET_80387"
907 {
908   ix86_compare_op0 = operands[0];
909   ix86_compare_op1 = operands[1];
910   DONE;
911 })
912
913 (define_expand "cmp<mode>"
914   [(set (reg:CC FLAGS_REG)
915         (compare:CC (match_operand:MODEF 0 "cmp_fp_expander_operand" "")
916                     (match_operand:MODEF 1 "cmp_fp_expander_operand" "")))]
917   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
918 {
919   ix86_compare_op0 = operands[0];
920   ix86_compare_op1 = operands[1];
921   DONE;
922 })
923
924 ;; FP compares, step 1:
925 ;; Set the FP condition codes.
926 ;;
927 ;; CCFPmode     compare with exceptions
928 ;; CCFPUmode    compare with no exceptions
929
930 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
931 ;; used to manage the reg stack popping would not be preserved.
932
933 (define_insn "*cmpfp_0"
934   [(set (match_operand:HI 0 "register_operand" "=a")
935         (unspec:HI
936           [(compare:CCFP
937              (match_operand 1 "register_operand" "f")
938              (match_operand 2 "const0_operand" "X"))]
939         UNSPEC_FNSTSW))]
940   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
941    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
942   "* return output_fp_compare (insn, operands, 0, 0);"
943   [(set_attr "type" "multi")
944    (set_attr "unit" "i387")
945    (set (attr "mode")
946      (cond [(match_operand:SF 1 "" "")
947               (const_string "SF")
948             (match_operand:DF 1 "" "")
949               (const_string "DF")
950            ]
951            (const_string "XF")))])
952
953 (define_insn_and_split "*cmpfp_0_cc"
954   [(set (reg:CCFP FLAGS_REG)
955         (compare:CCFP
956           (match_operand 1 "register_operand" "f")
957           (match_operand 2 "const0_operand" "X")))
958    (clobber (match_operand:HI 0 "register_operand" "=a"))]
959   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
960    && TARGET_SAHF && !TARGET_CMOVE
961    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
962   "#"
963   "&& reload_completed"
964   [(set (match_dup 0)
965         (unspec:HI
966           [(compare:CCFP (match_dup 1)(match_dup 2))]
967         UNSPEC_FNSTSW))
968    (set (reg:CC FLAGS_REG)
969         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
970   ""
971   [(set_attr "type" "multi")
972    (set_attr "unit" "i387")
973    (set (attr "mode")
974      (cond [(match_operand:SF 1 "" "")
975               (const_string "SF")
976             (match_operand:DF 1 "" "")
977               (const_string "DF")
978            ]
979            (const_string "XF")))])
980
981 (define_insn "*cmpfp_xf"
982   [(set (match_operand:HI 0 "register_operand" "=a")
983         (unspec:HI
984           [(compare:CCFP
985              (match_operand:XF 1 "register_operand" "f")
986              (match_operand:XF 2 "register_operand" "f"))]
987           UNSPEC_FNSTSW))]
988   "TARGET_80387"
989   "* return output_fp_compare (insn, operands, 0, 0);"
990   [(set_attr "type" "multi")
991    (set_attr "unit" "i387")
992    (set_attr "mode" "XF")])
993
994 (define_insn_and_split "*cmpfp_xf_cc"
995   [(set (reg:CCFP FLAGS_REG)
996         (compare:CCFP
997           (match_operand:XF 1 "register_operand" "f")
998           (match_operand:XF 2 "register_operand" "f")))
999    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1000   "TARGET_80387
1001    && TARGET_SAHF && !TARGET_CMOVE"
1002   "#"
1003   "&& reload_completed"
1004   [(set (match_dup 0)
1005         (unspec:HI
1006           [(compare:CCFP (match_dup 1)(match_dup 2))]
1007         UNSPEC_FNSTSW))
1008    (set (reg:CC FLAGS_REG)
1009         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1010   ""
1011   [(set_attr "type" "multi")
1012    (set_attr "unit" "i387")
1013    (set_attr "mode" "XF")])
1014
1015 (define_insn "*cmpfp_<mode>"
1016   [(set (match_operand:HI 0 "register_operand" "=a")
1017         (unspec:HI
1018           [(compare:CCFP
1019              (match_operand:MODEF 1 "register_operand" "f")
1020              (match_operand:MODEF 2 "nonimmediate_operand" "fm"))]
1021           UNSPEC_FNSTSW))]
1022   "TARGET_80387"
1023   "* return output_fp_compare (insn, operands, 0, 0);"
1024   [(set_attr "type" "multi")
1025    (set_attr "unit" "i387")
1026    (set_attr "mode" "<MODE>")])
1027
1028 (define_insn_and_split "*cmpfp_<mode>_cc"
1029   [(set (reg:CCFP FLAGS_REG)
1030         (compare:CCFP
1031           (match_operand:MODEF 1 "register_operand" "f")
1032           (match_operand:MODEF 2 "nonimmediate_operand" "fm")))
1033    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1034   "TARGET_80387
1035    && TARGET_SAHF && !TARGET_CMOVE"
1036   "#"
1037   "&& reload_completed"
1038   [(set (match_dup 0)
1039         (unspec:HI
1040           [(compare:CCFP (match_dup 1)(match_dup 2))]
1041         UNSPEC_FNSTSW))
1042    (set (reg:CC FLAGS_REG)
1043         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1044   ""
1045   [(set_attr "type" "multi")
1046    (set_attr "unit" "i387")
1047    (set_attr "mode" "<MODE>")])
1048
1049 (define_insn "*cmpfp_u"
1050   [(set (match_operand:HI 0 "register_operand" "=a")
1051         (unspec:HI
1052           [(compare:CCFPU
1053              (match_operand 1 "register_operand" "f")
1054              (match_operand 2 "register_operand" "f"))]
1055           UNSPEC_FNSTSW))]
1056   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1057    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1058   "* return output_fp_compare (insn, operands, 0, 1);"
1059   [(set_attr "type" "multi")
1060    (set_attr "unit" "i387")
1061    (set (attr "mode")
1062      (cond [(match_operand:SF 1 "" "")
1063               (const_string "SF")
1064             (match_operand:DF 1 "" "")
1065               (const_string "DF")
1066            ]
1067            (const_string "XF")))])
1068
1069 (define_insn_and_split "*cmpfp_u_cc"
1070   [(set (reg:CCFPU FLAGS_REG)
1071         (compare:CCFPU
1072           (match_operand 1 "register_operand" "f")
1073           (match_operand 2 "register_operand" "f")))
1074    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1075   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1076    && TARGET_SAHF && !TARGET_CMOVE
1077    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1078   "#"
1079   "&& reload_completed"
1080   [(set (match_dup 0)
1081         (unspec:HI
1082           [(compare:CCFPU (match_dup 1)(match_dup 2))]
1083         UNSPEC_FNSTSW))
1084    (set (reg:CC FLAGS_REG)
1085         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1086   ""
1087   [(set_attr "type" "multi")
1088    (set_attr "unit" "i387")
1089    (set (attr "mode")
1090      (cond [(match_operand:SF 1 "" "")
1091               (const_string "SF")
1092             (match_operand:DF 1 "" "")
1093               (const_string "DF")
1094            ]
1095            (const_string "XF")))])
1096
1097 (define_insn "*cmpfp_<mode>"
1098   [(set (match_operand:HI 0 "register_operand" "=a")
1099         (unspec:HI
1100           [(compare:CCFP
1101              (match_operand 1 "register_operand" "f")
1102              (match_operator 3 "float_operator"
1103                [(match_operand:X87MODEI12 2 "memory_operand" "m")]))]
1104           UNSPEC_FNSTSW))]
1105   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1106    && TARGET_USE_<MODE>MODE_FIOP
1107    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1108   "* return output_fp_compare (insn, operands, 0, 0);"
1109   [(set_attr "type" "multi")
1110    (set_attr "unit" "i387")
1111    (set_attr "fp_int_src" "true")
1112    (set_attr "mode" "<MODE>")])
1113
1114 (define_insn_and_split "*cmpfp_<mode>_cc"
1115   [(set (reg:CCFP FLAGS_REG)
1116         (compare:CCFP
1117           (match_operand 1 "register_operand" "f")
1118           (match_operator 3 "float_operator"
1119             [(match_operand:X87MODEI12 2 "memory_operand" "m")])))
1120    (clobber (match_operand:HI 0 "register_operand" "=a"))]
1121   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
1122    && TARGET_SAHF && !TARGET_CMOVE
1123    && TARGET_USE_<MODE>MODE_FIOP
1124    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
1125   "#"
1126   "&& reload_completed"
1127   [(set (match_dup 0)
1128         (unspec:HI
1129           [(compare:CCFP
1130              (match_dup 1)
1131              (match_op_dup 3 [(match_dup 2)]))]
1132         UNSPEC_FNSTSW))
1133    (set (reg:CC FLAGS_REG)
1134         (unspec:CC [(match_dup 0)] UNSPEC_SAHF))]
1135   ""
1136   [(set_attr "type" "multi")
1137    (set_attr "unit" "i387")
1138    (set_attr "fp_int_src" "true")
1139    (set_attr "mode" "<MODE>")])
1140
1141 ;; FP compares, step 2
1142 ;; Move the fpsw to ax.
1143
1144 (define_insn "x86_fnstsw_1"
1145   [(set (match_operand:HI 0 "register_operand" "=a")
1146         (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))]
1147   "TARGET_80387"
1148   "fnstsw\t%0"
1149   [(set_attr "length" "2")
1150    (set_attr "mode" "SI")
1151    (set_attr "unit" "i387")])
1152
1153 ;; FP compares, step 3
1154 ;; Get ax into flags, general case.
1155
1156 (define_insn "x86_sahf_1"
1157   [(set (reg:CC FLAGS_REG)
1158         (unspec:CC [(match_operand:HI 0 "register_operand" "a")]
1159                    UNSPEC_SAHF))]
1160   "TARGET_SAHF"
1161 {
1162 #ifdef HAVE_AS_IX86_SAHF
1163   return "sahf";
1164 #else
1165   return ".byte\t0x9e";
1166 #endif
1167 }
1168   [(set_attr "length" "1")
1169    (set_attr "athlon_decode" "vector")
1170    (set_attr "amdfam10_decode" "direct")
1171    (set_attr "mode" "SI")])
1172
1173 ;; Pentium Pro can do steps 1 through 3 in one go.
1174 ;; comi*, ucomi*, fcomi*, ficomi*,fucomi* (i387 instructions set condition codes)
1175 (define_insn "*cmpfp_i_mixed"
1176   [(set (reg:CCFP FLAGS_REG)
1177         (compare:CCFP (match_operand 0 "register_operand" "f,x")
1178                       (match_operand 1 "nonimmediate_operand" "f,xm")))]
1179   "TARGET_MIX_SSE_I387
1180    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1181    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1182   "* return output_fp_compare (insn, operands, 1, 0);"
1183   [(set_attr "type" "fcmp,ssecomi")
1184    (set (attr "mode")
1185      (if_then_else (match_operand:SF 1 "" "")
1186         (const_string "SF")
1187         (const_string "DF")))
1188    (set_attr "athlon_decode" "vector")
1189    (set_attr "amdfam10_decode" "direct")])
1190
1191 (define_insn "*cmpfp_i_sse"
1192   [(set (reg:CCFP FLAGS_REG)
1193         (compare:CCFP (match_operand 0 "register_operand" "x")
1194                       (match_operand 1 "nonimmediate_operand" "xm")))]
1195   "TARGET_SSE_MATH
1196    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1197    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1198   "* return output_fp_compare (insn, operands, 1, 0);"
1199   [(set_attr "type" "ssecomi")
1200    (set (attr "mode")
1201      (if_then_else (match_operand:SF 1 "" "")
1202         (const_string "SF")
1203         (const_string "DF")))
1204    (set_attr "athlon_decode" "vector")
1205    (set_attr "amdfam10_decode" "direct")])
1206
1207 (define_insn "*cmpfp_i_i387"
1208   [(set (reg:CCFP FLAGS_REG)
1209         (compare:CCFP (match_operand 0 "register_operand" "f")
1210                       (match_operand 1 "register_operand" "f")))]
1211   "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1212    && TARGET_CMOVE
1213    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1214    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1215   "* return output_fp_compare (insn, operands, 1, 0);"
1216   [(set_attr "type" "fcmp")
1217    (set (attr "mode")
1218      (cond [(match_operand:SF 1 "" "")
1219               (const_string "SF")
1220             (match_operand:DF 1 "" "")
1221               (const_string "DF")
1222            ]
1223            (const_string "XF")))
1224    (set_attr "athlon_decode" "vector")
1225    (set_attr "amdfam10_decode" "direct")])
1226
1227 (define_insn "*cmpfp_iu_mixed"
1228   [(set (reg:CCFPU FLAGS_REG)
1229         (compare:CCFPU (match_operand 0 "register_operand" "f,x")
1230                        (match_operand 1 "nonimmediate_operand" "f,xm")))]
1231   "TARGET_MIX_SSE_I387
1232    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1233    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1234   "* return output_fp_compare (insn, operands, 1, 1);"
1235   [(set_attr "type" "fcmp,ssecomi")
1236    (set (attr "mode")
1237      (if_then_else (match_operand:SF 1 "" "")
1238         (const_string "SF")
1239         (const_string "DF")))
1240    (set_attr "athlon_decode" "vector")
1241    (set_attr "amdfam10_decode" "direct")])
1242
1243 (define_insn "*cmpfp_iu_sse"
1244   [(set (reg:CCFPU FLAGS_REG)
1245         (compare:CCFPU (match_operand 0 "register_operand" "x")
1246                        (match_operand 1 "nonimmediate_operand" "xm")))]
1247   "TARGET_SSE_MATH
1248    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1249    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1250   "* return output_fp_compare (insn, operands, 1, 1);"
1251   [(set_attr "type" "ssecomi")
1252    (set (attr "mode")
1253      (if_then_else (match_operand:SF 1 "" "")
1254         (const_string "SF")
1255         (const_string "DF")))
1256    (set_attr "athlon_decode" "vector")
1257    (set_attr "amdfam10_decode" "direct")])
1258
1259 (define_insn "*cmpfp_iu_387"
1260   [(set (reg:CCFPU FLAGS_REG)
1261         (compare:CCFPU (match_operand 0 "register_operand" "f")
1262                        (match_operand 1 "register_operand" "f")))]
1263   "X87_FLOAT_MODE_P (GET_MODE (operands[0]))
1264    && TARGET_CMOVE
1265    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[0])) && TARGET_SSE_MATH)
1266    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1267   "* return output_fp_compare (insn, operands, 1, 1);"
1268   [(set_attr "type" "fcmp")
1269    (set (attr "mode")
1270      (cond [(match_operand:SF 1 "" "")
1271               (const_string "SF")
1272             (match_operand:DF 1 "" "")
1273               (const_string "DF")
1274            ]
1275            (const_string "XF")))
1276    (set_attr "athlon_decode" "vector")
1277    (set_attr "amdfam10_decode" "direct")])
1278 \f
1279 ;; Move instructions.
1280
1281 ;; General case of fullword move.
1282
1283 (define_expand "movsi"
1284   [(set (match_operand:SI 0 "nonimmediate_operand" "")
1285         (match_operand:SI 1 "general_operand" ""))]
1286   ""
1287   "ix86_expand_move (SImode, operands); DONE;")
1288
1289 ;; Push/pop instructions.  They are separate since autoinc/dec is not a
1290 ;; general_operand.
1291 ;;
1292 ;; %%% We don't use a post-inc memory reference because x86 is not a
1293 ;; general AUTO_INC_DEC host, which impacts how it is treated in flow.
1294 ;; Changing this impacts compiler performance on other non-AUTO_INC_DEC
1295 ;; targets without our curiosities, and it is just as easy to represent
1296 ;; this differently.
1297
1298 (define_insn "*pushsi2"
1299   [(set (match_operand:SI 0 "push_operand" "=<")
1300         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1301   "!TARGET_64BIT"
1302   "push{l}\t%1"
1303   [(set_attr "type" "push")
1304    (set_attr "mode" "SI")])
1305
1306 ;; For 64BIT abi we always round up to 8 bytes.
1307 (define_insn "*pushsi2_rex64"
1308   [(set (match_operand:SI 0 "push_operand" "=X")
1309         (match_operand:SI 1 "nonmemory_no_elim_operand" "ri"))]
1310   "TARGET_64BIT"
1311   "push{q}\t%q1"
1312   [(set_attr "type" "push")
1313    (set_attr "mode" "SI")])
1314
1315 (define_insn "*pushsi2_prologue"
1316   [(set (match_operand:SI 0 "push_operand" "=<")
1317         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))
1318    (clobber (mem:BLK (scratch)))]
1319   "!TARGET_64BIT"
1320   "push{l}\t%1"
1321   [(set_attr "type" "push")
1322    (set_attr "mode" "SI")])
1323
1324 (define_insn "*popsi1_epilogue"
1325   [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1326         (mem:SI (reg:SI SP_REG)))
1327    (set (reg:SI SP_REG)
1328         (plus:SI (reg:SI SP_REG) (const_int 4)))
1329    (clobber (mem:BLK (scratch)))]
1330   "!TARGET_64BIT"
1331   "pop{l}\t%0"
1332   [(set_attr "type" "pop")
1333    (set_attr "mode" "SI")])
1334
1335 (define_insn "popsi1"
1336   [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1337         (mem:SI (reg:SI SP_REG)))
1338    (set (reg:SI SP_REG)
1339         (plus:SI (reg:SI SP_REG) (const_int 4)))]
1340   "!TARGET_64BIT"
1341   "pop{l}\t%0"
1342   [(set_attr "type" "pop")
1343    (set_attr "mode" "SI")])
1344
1345 (define_insn "*movsi_xor"
1346   [(set (match_operand:SI 0 "register_operand" "=r")
1347         (match_operand:SI 1 "const0_operand" "i"))
1348    (clobber (reg:CC FLAGS_REG))]
1349   "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1350   "xor{l}\t%0, %0"
1351   [(set_attr "type" "alu1")
1352    (set_attr "mode" "SI")
1353    (set_attr "length_immediate" "0")])
1354
1355 (define_insn "*movsi_or"
1356   [(set (match_operand:SI 0 "register_operand" "=r")
1357         (match_operand:SI 1 "immediate_operand" "i"))
1358    (clobber (reg:CC FLAGS_REG))]
1359   "reload_completed
1360    && operands[1] == constm1_rtx
1361    && (TARGET_MOVE_M1_VIA_OR || optimize_size)"
1362 {
1363   operands[1] = constm1_rtx;
1364   return "or{l}\t{%1, %0|%0, %1}";
1365 }
1366   [(set_attr "type" "alu1")
1367    (set_attr "mode" "SI")
1368    (set_attr "length_immediate" "1")])
1369
1370 (define_insn "*movsi_1"
1371   [(set (match_operand:SI 0 "nonimmediate_operand"
1372                         "=r  ,m  ,*y,*y,?rm,?*y,*x,*x,?r ,m ,?*Yi,*x")
1373         (match_operand:SI 1 "general_operand"
1374                         "rinm,rin,C ,*y,*y ,rm ,C ,*x,*Yi,*x,r   ,m "))]
1375   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1376 {
1377   switch (get_attr_type (insn))
1378     {
1379     case TYPE_SSELOG1:
1380       if (get_attr_mode (insn) == MODE_TI)
1381         return "pxor\t%0, %0";
1382       return "xorps\t%0, %0";
1383
1384     case TYPE_SSEMOV:
1385       switch (get_attr_mode (insn))
1386         {
1387         case MODE_TI:
1388           return "movdqa\t{%1, %0|%0, %1}";
1389         case MODE_V4SF:
1390           return "movaps\t{%1, %0|%0, %1}";
1391         case MODE_SI:
1392           return "movd\t{%1, %0|%0, %1}";
1393         case MODE_SF:
1394           return "movss\t{%1, %0|%0, %1}";
1395         default:
1396           gcc_unreachable ();
1397         }
1398
1399     case TYPE_MMXADD:
1400       return "pxor\t%0, %0";
1401
1402     case TYPE_MMXMOV:
1403       if (get_attr_mode (insn) == MODE_DI)
1404         return "movq\t{%1, %0|%0, %1}";
1405       return "movd\t{%1, %0|%0, %1}";
1406
1407     case TYPE_LEA:
1408       return "lea{l}\t{%1, %0|%0, %1}";
1409
1410     default:
1411       gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
1412       return "mov{l}\t{%1, %0|%0, %1}";
1413     }
1414 }
1415   [(set (attr "type")
1416      (cond [(eq_attr "alternative" "2")
1417               (const_string "mmxadd")
1418             (eq_attr "alternative" "3,4,5")
1419               (const_string "mmxmov")
1420             (eq_attr "alternative" "6")
1421               (const_string "sselog1")
1422             (eq_attr "alternative" "7,8,9,10,11")
1423               (const_string "ssemov")
1424             (match_operand:DI 1 "pic_32bit_operand" "")
1425               (const_string "lea")
1426            ]
1427            (const_string "imov")))
1428    (set (attr "mode")
1429      (cond [(eq_attr "alternative" "2,3")
1430               (const_string "DI")
1431             (eq_attr "alternative" "6,7")
1432               (if_then_else
1433                 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
1434                 (const_string "V4SF")
1435                 (const_string "TI"))
1436             (and (eq_attr "alternative" "8,9,10,11")
1437                  (eq (symbol_ref "TARGET_SSE2") (const_int 0)))
1438               (const_string "SF")
1439            ]
1440            (const_string "SI")))])
1441
1442 ;; Stores and loads of ax to arbitrary constant address.
1443 ;; We fake an second form of instruction to force reload to load address
1444 ;; into register when rax is not available
1445 (define_insn "*movabssi_1_rex64"
1446   [(set (mem:SI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1447         (match_operand:SI 1 "nonmemory_operand" "a,er"))]
1448   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1449   "@
1450    movabs{l}\t{%1, %P0|%P0, %1}
1451    mov{l}\t{%1, %a0|%a0, %1}"
1452   [(set_attr "type" "imov")
1453    (set_attr "modrm" "0,*")
1454    (set_attr "length_address" "8,0")
1455    (set_attr "length_immediate" "0,*")
1456    (set_attr "memory" "store")
1457    (set_attr "mode" "SI")])
1458
1459 (define_insn "*movabssi_2_rex64"
1460   [(set (match_operand:SI 0 "register_operand" "=a,r")
1461         (mem:SI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1462   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1463   "@
1464    movabs{l}\t{%P1, %0|%0, %P1}
1465    mov{l}\t{%a1, %0|%0, %a1}"
1466   [(set_attr "type" "imov")
1467    (set_attr "modrm" "0,*")
1468    (set_attr "length_address" "8,0")
1469    (set_attr "length_immediate" "0")
1470    (set_attr "memory" "load")
1471    (set_attr "mode" "SI")])
1472
1473 (define_insn "*swapsi"
1474   [(set (match_operand:SI 0 "register_operand" "+r")
1475         (match_operand:SI 1 "register_operand" "+r"))
1476    (set (match_dup 1)
1477         (match_dup 0))]
1478   ""
1479   "xchg{l}\t%1, %0"
1480   [(set_attr "type" "imov")
1481    (set_attr "mode" "SI")
1482    (set_attr "pent_pair" "np")
1483    (set_attr "athlon_decode" "vector")
1484    (set_attr "amdfam10_decode" "double")])
1485
1486 (define_expand "movhi"
1487   [(set (match_operand:HI 0 "nonimmediate_operand" "")
1488         (match_operand:HI 1 "general_operand" ""))]
1489   ""
1490   "ix86_expand_move (HImode, operands); DONE;")
1491
1492 (define_insn "*pushhi2"
1493   [(set (match_operand:HI 0 "push_operand" "=X")
1494         (match_operand:HI 1 "nonmemory_no_elim_operand" "rn"))]
1495   "!TARGET_64BIT"
1496   "push{l}\t%k1"
1497   [(set_attr "type" "push")
1498    (set_attr "mode" "SI")])
1499
1500 ;; For 64BIT abi we always round up to 8 bytes.
1501 (define_insn "*pushhi2_rex64"
1502   [(set (match_operand:HI 0 "push_operand" "=X")
1503         (match_operand:HI 1 "nonmemory_no_elim_operand" "ri"))]
1504   "TARGET_64BIT"
1505   "push{q}\t%q1"
1506   [(set_attr "type" "push")
1507    (set_attr "mode" "DI")])
1508
1509 (define_insn "*movhi_1"
1510   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
1511         (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
1512   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1513 {
1514   switch (get_attr_type (insn))
1515     {
1516     case TYPE_IMOVX:
1517       /* movzwl is faster than movw on p2 due to partial word stalls,
1518          though not as fast as an aligned movl.  */
1519       return "movz{wl|x}\t{%1, %k0|%k0, %1}";
1520     default:
1521       if (get_attr_mode (insn) == MODE_SI)
1522         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1523       else
1524         return "mov{w}\t{%1, %0|%0, %1}";
1525     }
1526 }
1527   [(set (attr "type")
1528      (cond [(ne (symbol_ref "optimize_size") (const_int 0))
1529               (const_string "imov")
1530             (and (eq_attr "alternative" "0")
1531                  (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1532                           (const_int 0))
1533                       (eq (symbol_ref "TARGET_HIMODE_MATH")
1534                           (const_int 0))))
1535               (const_string "imov")
1536             (and (eq_attr "alternative" "1,2")
1537                  (match_operand:HI 1 "aligned_operand" ""))
1538               (const_string "imov")
1539             (and (ne (symbol_ref "TARGET_MOVX")
1540                      (const_int 0))
1541                  (eq_attr "alternative" "0,2"))
1542               (const_string "imovx")
1543            ]
1544            (const_string "imov")))
1545     (set (attr "mode")
1546       (cond [(eq_attr "type" "imovx")
1547                (const_string "SI")
1548              (and (eq_attr "alternative" "1,2")
1549                   (match_operand:HI 1 "aligned_operand" ""))
1550                (const_string "SI")
1551              (and (eq_attr "alternative" "0")
1552                   (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1553                            (const_int 0))
1554                        (eq (symbol_ref "TARGET_HIMODE_MATH")
1555                            (const_int 0))))
1556                (const_string "SI")
1557             ]
1558             (const_string "HI")))])
1559
1560 ;; Stores and loads of ax to arbitrary constant address.
1561 ;; We fake an second form of instruction to force reload to load address
1562 ;; into register when rax is not available
1563 (define_insn "*movabshi_1_rex64"
1564   [(set (mem:HI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1565         (match_operand:HI 1 "nonmemory_operand" "a,er"))]
1566   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1567   "@
1568    movabs{w}\t{%1, %P0|%P0, %1}
1569    mov{w}\t{%1, %a0|%a0, %1}"
1570   [(set_attr "type" "imov")
1571    (set_attr "modrm" "0,*")
1572    (set_attr "length_address" "8,0")
1573    (set_attr "length_immediate" "0,*")
1574    (set_attr "memory" "store")
1575    (set_attr "mode" "HI")])
1576
1577 (define_insn "*movabshi_2_rex64"
1578   [(set (match_operand:HI 0 "register_operand" "=a,r")
1579         (mem:HI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1580   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1581   "@
1582    movabs{w}\t{%P1, %0|%0, %P1}
1583    mov{w}\t{%a1, %0|%0, %a1}"
1584   [(set_attr "type" "imov")
1585    (set_attr "modrm" "0,*")
1586    (set_attr "length_address" "8,0")
1587    (set_attr "length_immediate" "0")
1588    (set_attr "memory" "load")
1589    (set_attr "mode" "HI")])
1590
1591 (define_insn "*swaphi_1"
1592   [(set (match_operand:HI 0 "register_operand" "+r")
1593         (match_operand:HI 1 "register_operand" "+r"))
1594    (set (match_dup 1)
1595         (match_dup 0))]
1596   "!TARGET_PARTIAL_REG_STALL || optimize_size"
1597   "xchg{l}\t%k1, %k0"
1598   [(set_attr "type" "imov")
1599    (set_attr "mode" "SI")
1600    (set_attr "pent_pair" "np")
1601    (set_attr "athlon_decode" "vector")
1602    (set_attr "amdfam10_decode" "double")])
1603
1604 ;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL is disabled for AMDFAM10
1605 (define_insn "*swaphi_2"
1606   [(set (match_operand:HI 0 "register_operand" "+r")
1607         (match_operand:HI 1 "register_operand" "+r"))
1608    (set (match_dup 1)
1609         (match_dup 0))]
1610   "TARGET_PARTIAL_REG_STALL"
1611   "xchg{w}\t%1, %0"
1612   [(set_attr "type" "imov")
1613    (set_attr "mode" "HI")
1614    (set_attr "pent_pair" "np")
1615    (set_attr "athlon_decode" "vector")])
1616
1617 (define_expand "movstricthi"
1618   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" ""))
1619         (match_operand:HI 1 "general_operand" ""))]
1620   "! TARGET_PARTIAL_REG_STALL || optimize_size"
1621 {
1622   /* Don't generate memory->memory moves, go through a register */
1623   if (MEM_P (operands[0]) && MEM_P (operands[1]))
1624     operands[1] = force_reg (HImode, operands[1]);
1625 })
1626
1627 (define_insn "*movstricthi_1"
1628   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+rm,r"))
1629         (match_operand:HI 1 "general_operand" "rn,m"))]
1630   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1631    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1632   "mov{w}\t{%1, %0|%0, %1}"
1633   [(set_attr "type" "imov")
1634    (set_attr "mode" "HI")])
1635
1636 (define_insn "*movstricthi_xor"
1637   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
1638         (match_operand:HI 1 "const0_operand" "i"))
1639    (clobber (reg:CC FLAGS_REG))]
1640   "reload_completed
1641    && ((!TARGET_USE_MOV0 && !TARGET_PARTIAL_REG_STALL) || optimize_size)"
1642   "xor{w}\t%0, %0"
1643   [(set_attr "type" "alu1")
1644    (set_attr "mode" "HI")
1645    (set_attr "length_immediate" "0")])
1646
1647 (define_expand "movqi"
1648   [(set (match_operand:QI 0 "nonimmediate_operand" "")
1649         (match_operand:QI 1 "general_operand" ""))]
1650   ""
1651   "ix86_expand_move (QImode, operands); DONE;")
1652
1653 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1654 ;; "push a byte".  But actually we use pushl, which has the effect
1655 ;; of rounding the amount pushed up to a word.
1656
1657 (define_insn "*pushqi2"
1658   [(set (match_operand:QI 0 "push_operand" "=X")
1659         (match_operand:QI 1 "nonmemory_no_elim_operand" "rn"))]
1660   "!TARGET_64BIT"
1661   "push{l}\t%k1"
1662   [(set_attr "type" "push")
1663    (set_attr "mode" "SI")])
1664
1665 ;; For 64BIT abi we always round up to 8 bytes.
1666 (define_insn "*pushqi2_rex64"
1667   [(set (match_operand:QI 0 "push_operand" "=X")
1668         (match_operand:QI 1 "nonmemory_no_elim_operand" "qi"))]
1669   "TARGET_64BIT"
1670   "push{q}\t%q1"
1671   [(set_attr "type" "push")
1672    (set_attr "mode" "DI")])
1673
1674 ;; Situation is quite tricky about when to choose full sized (SImode) move
1675 ;; over QImode moves.  For Q_REG -> Q_REG move we use full size only for
1676 ;; partial register dependency machines (such as AMD Athlon), where QImode
1677 ;; moves issue extra dependency and for partial register stalls machines
1678 ;; that don't use QImode patterns (and QImode move cause stall on the next
1679 ;; instruction).
1680 ;;
1681 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
1682 ;; register stall machines with, where we use QImode instructions, since
1683 ;; partial register stall can be caused there.  Then we use movzx.
1684 (define_insn "*movqi_1"
1685   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
1686         (match_operand:QI 1 "general_operand"      " q,qn,qm,q,rn,qm,qn"))]
1687   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1688 {
1689   switch (get_attr_type (insn))
1690     {
1691     case TYPE_IMOVX:
1692       gcc_assert (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]));
1693       return "movz{bl|x}\t{%1, %k0|%k0, %1}";
1694     default:
1695       if (get_attr_mode (insn) == MODE_SI)
1696         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1697       else
1698         return "mov{b}\t{%1, %0|%0, %1}";
1699     }
1700 }
1701   [(set (attr "type")
1702      (cond [(and (eq_attr "alternative" "5")
1703                  (not (match_operand:QI 1 "aligned_operand" "")))
1704               (const_string "imovx")
1705             (ne (symbol_ref "optimize_size") (const_int 0))
1706               (const_string "imov")
1707             (and (eq_attr "alternative" "3")
1708                  (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1709                           (const_int 0))
1710                       (eq (symbol_ref "TARGET_QIMODE_MATH")
1711                           (const_int 0))))
1712               (const_string "imov")
1713             (eq_attr "alternative" "3,5")
1714               (const_string "imovx")
1715             (and (ne (symbol_ref "TARGET_MOVX")
1716                      (const_int 0))
1717                  (eq_attr "alternative" "2"))
1718               (const_string "imovx")
1719            ]
1720            (const_string "imov")))
1721    (set (attr "mode")
1722       (cond [(eq_attr "alternative" "3,4,5")
1723                (const_string "SI")
1724              (eq_attr "alternative" "6")
1725                (const_string "QI")
1726              (eq_attr "type" "imovx")
1727                (const_string "SI")
1728              (and (eq_attr "type" "imov")
1729                   (and (eq_attr "alternative" "0,1")
1730                        (and (ne (symbol_ref "TARGET_PARTIAL_REG_DEPENDENCY")
1731                                 (const_int 0))
1732                             (and (eq (symbol_ref "optimize_size")
1733                                      (const_int 0))
1734                                  (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1735                                      (const_int 0))))))
1736                (const_string "SI")
1737              ;; Avoid partial register stalls when not using QImode arithmetic
1738              (and (eq_attr "type" "imov")
1739                   (and (eq_attr "alternative" "0,1")
1740                        (and (ne (symbol_ref "TARGET_PARTIAL_REG_STALL")
1741                                 (const_int 0))
1742                             (eq (symbol_ref "TARGET_QIMODE_MATH")
1743                                 (const_int 0)))))
1744                (const_string "SI")
1745            ]
1746            (const_string "QI")))])
1747
1748 (define_expand "reload_outqi"
1749   [(parallel [(match_operand:QI 0 "" "=m")
1750               (match_operand:QI 1 "register_operand" "r")
1751               (match_operand:QI 2 "register_operand" "=&q")])]
1752   ""
1753 {
1754   rtx op0, op1, op2;
1755   op0 = operands[0]; op1 = operands[1]; op2 = operands[2];
1756
1757   gcc_assert (!reg_overlap_mentioned_p (op2, op0));
1758   if (! q_regs_operand (op1, QImode))
1759     {
1760       emit_insn (gen_movqi (op2, op1));
1761       op1 = op2;
1762     }
1763   emit_insn (gen_movqi (op0, op1));
1764   DONE;
1765 })
1766
1767 (define_insn "*swapqi_1"
1768   [(set (match_operand:QI 0 "register_operand" "+r")
1769         (match_operand:QI 1 "register_operand" "+r"))
1770    (set (match_dup 1)
1771         (match_dup 0))]
1772   "!TARGET_PARTIAL_REG_STALL || optimize_size"
1773   "xchg{l}\t%k1, %k0"
1774   [(set_attr "type" "imov")
1775    (set_attr "mode" "SI")
1776    (set_attr "pent_pair" "np")
1777    (set_attr "athlon_decode" "vector")
1778    (set_attr "amdfam10_decode" "vector")])
1779
1780 ;; Not added amdfam10_decode since TARGET_PARTIAL_REG_STALL is disabled for AMDFAM10
1781 (define_insn "*swapqi_2"
1782   [(set (match_operand:QI 0 "register_operand" "+q")
1783         (match_operand:QI 1 "register_operand" "+q"))
1784    (set (match_dup 1)
1785         (match_dup 0))]
1786   "TARGET_PARTIAL_REG_STALL"
1787   "xchg{b}\t%1, %0"
1788   [(set_attr "type" "imov")
1789    (set_attr "mode" "QI")
1790    (set_attr "pent_pair" "np")
1791    (set_attr "athlon_decode" "vector")])
1792
1793 (define_expand "movstrictqi"
1794   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
1795         (match_operand:QI 1 "general_operand" ""))]
1796   "! TARGET_PARTIAL_REG_STALL || optimize_size"
1797 {
1798   /* Don't generate memory->memory moves, go through a register.  */
1799   if (MEM_P (operands[0]) && MEM_P (operands[1]))
1800     operands[1] = force_reg (QImode, operands[1]);
1801 })
1802
1803 (define_insn "*movstrictqi_1"
1804   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
1805         (match_operand:QI 1 "general_operand" "*qn,m"))]
1806   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1807    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1808   "mov{b}\t{%1, %0|%0, %1}"
1809   [(set_attr "type" "imov")
1810    (set_attr "mode" "QI")])
1811
1812 (define_insn "*movstrictqi_xor"
1813   [(set (strict_low_part (match_operand:QI 0 "q_regs_operand" "+q"))
1814         (match_operand:QI 1 "const0_operand" "i"))
1815    (clobber (reg:CC FLAGS_REG))]
1816   "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1817   "xor{b}\t%0, %0"
1818   [(set_attr "type" "alu1")
1819    (set_attr "mode" "QI")
1820    (set_attr "length_immediate" "0")])
1821
1822 (define_insn "*movsi_extv_1"
1823   [(set (match_operand:SI 0 "register_operand" "=R")
1824         (sign_extract:SI (match_operand 1 "ext_register_operand" "Q")
1825                          (const_int 8)
1826                          (const_int 8)))]
1827   ""
1828   "movs{bl|x}\t{%h1, %0|%0, %h1}"
1829   [(set_attr "type" "imovx")
1830    (set_attr "mode" "SI")])
1831
1832 (define_insn "*movhi_extv_1"
1833   [(set (match_operand:HI 0 "register_operand" "=R")
1834         (sign_extract:HI (match_operand 1 "ext_register_operand" "Q")
1835                          (const_int 8)
1836                          (const_int 8)))]
1837   ""
1838   "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
1839   [(set_attr "type" "imovx")
1840    (set_attr "mode" "SI")])
1841
1842 (define_insn "*movqi_extv_1"
1843   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
1844         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1845                          (const_int 8)
1846                          (const_int 8)))]
1847   "!TARGET_64BIT"
1848 {
1849   switch (get_attr_type (insn))
1850     {
1851     case TYPE_IMOVX:
1852       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1853     default:
1854       return "mov{b}\t{%h1, %0|%0, %h1}";
1855     }
1856 }
1857   [(set (attr "type")
1858      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1859                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1860                              (ne (symbol_ref "TARGET_MOVX")
1861                                  (const_int 0))))
1862         (const_string "imovx")
1863         (const_string "imov")))
1864    (set (attr "mode")
1865      (if_then_else (eq_attr "type" "imovx")
1866         (const_string "SI")
1867         (const_string "QI")))])
1868
1869 (define_insn "*movqi_extv_1_rex64"
1870   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1871         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1872                          (const_int 8)
1873                          (const_int 8)))]
1874   "TARGET_64BIT"
1875 {
1876   switch (get_attr_type (insn))
1877     {
1878     case TYPE_IMOVX:
1879       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1880     default:
1881       return "mov{b}\t{%h1, %0|%0, %h1}";
1882     }
1883 }
1884   [(set (attr "type")
1885      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1886                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1887                              (ne (symbol_ref "TARGET_MOVX")
1888                                  (const_int 0))))
1889         (const_string "imovx")
1890         (const_string "imov")))
1891    (set (attr "mode")
1892      (if_then_else (eq_attr "type" "imovx")
1893         (const_string "SI")
1894         (const_string "QI")))])
1895
1896 ;; Stores and loads of ax to arbitrary constant address.
1897 ;; We fake an second form of instruction to force reload to load address
1898 ;; into register when rax is not available
1899 (define_insn "*movabsqi_1_rex64"
1900   [(set (mem:QI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1901         (match_operand:QI 1 "nonmemory_operand" "a,er"))]
1902   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1903   "@
1904    movabs{b}\t{%1, %P0|%P0, %1}
1905    mov{b}\t{%1, %a0|%a0, %1}"
1906   [(set_attr "type" "imov")
1907    (set_attr "modrm" "0,*")
1908    (set_attr "length_address" "8,0")
1909    (set_attr "length_immediate" "0,*")
1910    (set_attr "memory" "store")
1911    (set_attr "mode" "QI")])
1912
1913 (define_insn "*movabsqi_2_rex64"
1914   [(set (match_operand:QI 0 "register_operand" "=a,r")
1915         (mem:QI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1916   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1917   "@
1918    movabs{b}\t{%P1, %0|%0, %P1}
1919    mov{b}\t{%a1, %0|%0, %a1}"
1920   [(set_attr "type" "imov")
1921    (set_attr "modrm" "0,*")
1922    (set_attr "length_address" "8,0")
1923    (set_attr "length_immediate" "0")
1924    (set_attr "memory" "load")
1925    (set_attr "mode" "QI")])
1926
1927 (define_insn "*movdi_extzv_1"
1928   [(set (match_operand:DI 0 "register_operand" "=R")
1929         (zero_extract:DI (match_operand 1 "ext_register_operand" "Q")
1930                          (const_int 8)
1931                          (const_int 8)))]
1932   "TARGET_64BIT"
1933   "movz{bl|x}\t{%h1, %k0|%k0, %h1}"
1934   [(set_attr "type" "imovx")
1935    (set_attr "mode" "DI")])
1936
1937 (define_insn "*movsi_extzv_1"
1938   [(set (match_operand:SI 0 "register_operand" "=R")
1939         (zero_extract:SI (match_operand 1 "ext_register_operand" "Q")
1940                          (const_int 8)
1941                          (const_int 8)))]
1942   ""
1943   "movz{bl|x}\t{%h1, %0|%0, %h1}"
1944   [(set_attr "type" "imovx")
1945    (set_attr "mode" "SI")])
1946
1947 (define_insn "*movqi_extzv_2"
1948   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
1949         (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1950                                     (const_int 8)
1951                                     (const_int 8)) 0))]
1952   "!TARGET_64BIT"
1953 {
1954   switch (get_attr_type (insn))
1955     {
1956     case TYPE_IMOVX:
1957       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1958     default:
1959       return "mov{b}\t{%h1, %0|%0, %h1}";
1960     }
1961 }
1962   [(set (attr "type")
1963      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1964                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1965                              (ne (symbol_ref "TARGET_MOVX")
1966                                  (const_int 0))))
1967         (const_string "imovx")
1968         (const_string "imov")))
1969    (set (attr "mode")
1970      (if_then_else (eq_attr "type" "imovx")
1971         (const_string "SI")
1972         (const_string "QI")))])
1973
1974 (define_insn "*movqi_extzv_2_rex64"
1975   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1976         (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1977                                     (const_int 8)
1978                                     (const_int 8)) 0))]
1979   "TARGET_64BIT"
1980 {
1981   switch (get_attr_type (insn))
1982     {
1983     case TYPE_IMOVX:
1984       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1985     default:
1986       return "mov{b}\t{%h1, %0|%0, %h1}";
1987     }
1988 }
1989   [(set (attr "type")
1990      (if_then_else (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1991                         (ne (symbol_ref "TARGET_MOVX")
1992                             (const_int 0)))
1993         (const_string "imovx")
1994         (const_string "imov")))
1995    (set (attr "mode")
1996      (if_then_else (eq_attr "type" "imovx")
1997         (const_string "SI")
1998         (const_string "QI")))])
1999
2000 (define_insn "movsi_insv_1"
2001   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2002                          (const_int 8)
2003                          (const_int 8))
2004         (match_operand:SI 1 "general_operand" "Qmn"))]
2005   "!TARGET_64BIT"
2006   "mov{b}\t{%b1, %h0|%h0, %b1}"
2007   [(set_attr "type" "imov")
2008    (set_attr "mode" "QI")])
2009
2010 (define_insn "*movsi_insv_1_rex64"
2011   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2012                          (const_int 8)
2013                          (const_int 8))
2014         (match_operand:SI 1 "nonmemory_operand" "Qn"))]
2015   "TARGET_64BIT"
2016   "mov{b}\t{%b1, %h0|%h0, %b1}"
2017   [(set_attr "type" "imov")
2018    (set_attr "mode" "QI")])
2019
2020 (define_insn "movdi_insv_1_rex64"
2021   [(set (zero_extract:DI (match_operand 0 "ext_register_operand" "+Q")
2022                          (const_int 8)
2023                          (const_int 8))
2024         (match_operand:DI 1 "nonmemory_operand" "Qn"))]
2025   "TARGET_64BIT"
2026   "mov{b}\t{%b1, %h0|%h0, %b1}"
2027   [(set_attr "type" "imov")
2028    (set_attr "mode" "QI")])
2029
2030 (define_insn "*movqi_insv_2"
2031   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2032                          (const_int 8)
2033                          (const_int 8))
2034         (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
2035                      (const_int 8)))]
2036   ""
2037   "mov{b}\t{%h1, %h0|%h0, %h1}"
2038   [(set_attr "type" "imov")
2039    (set_attr "mode" "QI")])
2040
2041 (define_expand "movdi"
2042   [(set (match_operand:DI 0 "nonimmediate_operand" "")
2043         (match_operand:DI 1 "general_operand" ""))]
2044   ""
2045   "ix86_expand_move (DImode, operands); DONE;")
2046
2047 (define_insn "*pushdi"
2048   [(set (match_operand:DI 0 "push_operand" "=<")
2049         (match_operand:DI 1 "general_no_elim_operand" "riF*m"))]
2050   "!TARGET_64BIT"
2051   "#")
2052
2053 (define_insn "*pushdi2_rex64"
2054   [(set (match_operand:DI 0 "push_operand" "=<,!<")
2055         (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
2056   "TARGET_64BIT"
2057   "@
2058    push{q}\t%1
2059    #"
2060   [(set_attr "type" "push,multi")
2061    (set_attr "mode" "DI")])
2062
2063 ;; Convert impossible pushes of immediate to existing instructions.
2064 ;; First try to get scratch register and go through it.  In case this
2065 ;; fails, push sign extended lower part first and then overwrite
2066 ;; upper part by 32bit move.
2067 (define_peephole2
2068   [(match_scratch:DI 2 "r")
2069    (set (match_operand:DI 0 "push_operand" "")
2070         (match_operand:DI 1 "immediate_operand" ""))]
2071   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2072    && !x86_64_immediate_operand (operands[1], DImode)"
2073   [(set (match_dup 2) (match_dup 1))
2074    (set (match_dup 0) (match_dup 2))]
2075   "")
2076
2077 ;; We need to define this as both peepholer and splitter for case
2078 ;; peephole2 pass is not run.
2079 ;; "&& 1" is needed to keep it from matching the previous pattern.
2080 (define_peephole2
2081   [(set (match_operand:DI 0 "push_operand" "")
2082         (match_operand:DI 1 "immediate_operand" ""))]
2083   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2084    && !x86_64_immediate_operand (operands[1], DImode) && 1"
2085   [(set (match_dup 0) (match_dup 1))
2086    (set (match_dup 2) (match_dup 3))]
2087   "split_di (operands + 1, 1, operands + 2, operands + 3);
2088    operands[1] = gen_lowpart (DImode, operands[2]);
2089    operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
2090                                                     GEN_INT (4)));
2091   ")
2092
2093 (define_split
2094   [(set (match_operand:DI 0 "push_operand" "")
2095         (match_operand:DI 1 "immediate_operand" ""))]
2096   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2097                     ? epilogue_completed : reload_completed)
2098    && !symbolic_operand (operands[1], DImode)
2099    && !x86_64_immediate_operand (operands[1], DImode)"
2100   [(set (match_dup 0) (match_dup 1))
2101    (set (match_dup 2) (match_dup 3))]
2102   "split_di (operands + 1, 1, operands + 2, operands + 3);
2103    operands[1] = gen_lowpart (DImode, operands[2]);
2104    operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
2105                                                     GEN_INT (4)));
2106   ")
2107
2108 (define_insn "*pushdi2_prologue_rex64"
2109   [(set (match_operand:DI 0 "push_operand" "=<")
2110         (match_operand:DI 1 "general_no_elim_operand" "re*m"))
2111    (clobber (mem:BLK (scratch)))]
2112   "TARGET_64BIT"
2113   "push{q}\t%1"
2114   [(set_attr "type" "push")
2115    (set_attr "mode" "DI")])
2116
2117 (define_insn "*popdi1_epilogue_rex64"
2118   [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
2119         (mem:DI (reg:DI SP_REG)))
2120    (set (reg:DI SP_REG)
2121         (plus:DI (reg:DI SP_REG) (const_int 8)))
2122    (clobber (mem:BLK (scratch)))]
2123   "TARGET_64BIT"
2124   "pop{q}\t%0"
2125   [(set_attr "type" "pop")
2126    (set_attr "mode" "DI")])
2127
2128 (define_insn "popdi1"
2129   [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
2130         (mem:DI (reg:DI SP_REG)))
2131    (set (reg:DI SP_REG)
2132         (plus:DI (reg:DI SP_REG) (const_int 8)))]
2133   "TARGET_64BIT"
2134   "pop{q}\t%0"
2135   [(set_attr "type" "pop")
2136    (set_attr "mode" "DI")])
2137
2138 (define_insn "*movdi_xor_rex64"
2139   [(set (match_operand:DI 0 "register_operand" "=r")
2140         (match_operand:DI 1 "const0_operand" "i"))
2141    (clobber (reg:CC FLAGS_REG))]
2142   "TARGET_64BIT && (!TARGET_USE_MOV0 || optimize_size)
2143    && reload_completed"
2144   "xor{l}\t%k0, %k0";
2145   [(set_attr "type" "alu1")
2146    (set_attr "mode" "SI")
2147    (set_attr "length_immediate" "0")])
2148
2149 (define_insn "*movdi_or_rex64"
2150   [(set (match_operand:DI 0 "register_operand" "=r")
2151         (match_operand:DI 1 "const_int_operand" "i"))
2152    (clobber (reg:CC FLAGS_REG))]
2153   "TARGET_64BIT && (TARGET_MOVE_M1_VIA_OR || optimize_size)
2154    && reload_completed
2155    && operands[1] == constm1_rtx"
2156 {
2157   operands[1] = constm1_rtx;
2158   return "or{q}\t{%1, %0|%0, %1}";
2159 }
2160   [(set_attr "type" "alu1")
2161    (set_attr "mode" "DI")
2162    (set_attr "length_immediate" "1")])
2163
2164 (define_insn "*movdi_2"
2165   [(set (match_operand:DI 0 "nonimmediate_operand"
2166                         "=r  ,o  ,*y,m*y,*y,*Y2,m  ,*Y2,*Y2,*x,m ,*x,*x")
2167         (match_operand:DI 1 "general_operand"
2168                         "riFo,riF,C ,*y ,m ,C  ,*Y2,*Y2,m  ,C ,*x,*x,m "))]
2169   "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2170   "@
2171    #
2172    #
2173    pxor\t%0, %0
2174    movq\t{%1, %0|%0, %1}
2175    movq\t{%1, %0|%0, %1}
2176    pxor\t%0, %0
2177    movq\t{%1, %0|%0, %1}
2178    movdqa\t{%1, %0|%0, %1}
2179    movq\t{%1, %0|%0, %1}
2180    xorps\t%0, %0
2181    movlps\t{%1, %0|%0, %1}
2182    movaps\t{%1, %0|%0, %1}
2183    movlps\t{%1, %0|%0, %1}"
2184   [(set_attr "type" "*,*,mmx,mmxmov,mmxmov,sselog1,ssemov,ssemov,ssemov,sselog1,ssemov,ssemov,ssemov")
2185    (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF")])
2186
2187 (define_split
2188   [(set (match_operand:DI 0 "push_operand" "")
2189         (match_operand:DI 1 "general_operand" ""))]
2190   "!TARGET_64BIT && reload_completed
2191    && (! MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
2192   [(const_int 0)]
2193   "ix86_split_long_move (operands); DONE;")
2194
2195 ;; %%% This multiword shite has got to go.
2196 (define_split
2197   [(set (match_operand:DI 0 "nonimmediate_operand" "")
2198         (match_operand:DI 1 "general_operand" ""))]
2199   "!TARGET_64BIT && reload_completed
2200    && (!MMX_REG_P (operands[0]) && !SSE_REG_P (operands[0]))
2201    && (!MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
2202   [(const_int 0)]
2203   "ix86_split_long_move (operands); DONE;")
2204
2205 (define_insn "*movdi_1_rex64"
2206   [(set (match_operand:DI 0 "nonimmediate_operand"
2207           "=r,r  ,r,m ,!m,*y,*y,?r ,m ,?*Ym,?*y,*x,*x,?r ,m,?*Yi,*x,?*x,?*Ym")
2208         (match_operand:DI 1 "general_operand"
2209           "Z ,rem,i,re,n ,C ,*y,*Ym,*y,r   ,m  ,C ,*x,*Yi,*x,r  ,m ,*Ym,*x"))]
2210   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2211 {
2212   switch (get_attr_type (insn))
2213     {
2214     case TYPE_SSECVT:
2215       if (SSE_REG_P (operands[0]))
2216         return "movq2dq\t{%1, %0|%0, %1}";
2217       else
2218         return "movdq2q\t{%1, %0|%0, %1}";
2219
2220     case TYPE_SSEMOV:
2221       if (get_attr_mode (insn) == MODE_TI)
2222         return "movdqa\t{%1, %0|%0, %1}";
2223       /* FALLTHRU */
2224
2225     case TYPE_MMXMOV:
2226       /* Moves from and into integer register is done using movd
2227          opcode with REX prefix.  */
2228       if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
2229         return "movd\t{%1, %0|%0, %1}";
2230       return "movq\t{%1, %0|%0, %1}";
2231
2232     case TYPE_SSELOG1:
2233     case TYPE_MMXADD:
2234       return "pxor\t%0, %0";
2235
2236     case TYPE_MULTI:
2237       return "#";
2238
2239     case TYPE_LEA:
2240       return "lea{q}\t{%a1, %0|%0, %a1}";
2241
2242     default:
2243       gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
2244       if (get_attr_mode (insn) == MODE_SI)
2245         return "mov{l}\t{%k1, %k0|%k0, %k1}";
2246       else if (which_alternative == 2)
2247         return "movabs{q}\t{%1, %0|%0, %1}";
2248       else
2249         return "mov{q}\t{%1, %0|%0, %1}";
2250     }
2251 }
2252   [(set (attr "type")
2253      (cond [(eq_attr "alternative" "5")
2254               (const_string "mmxadd")
2255             (eq_attr "alternative" "6,7,8,9,10")
2256               (const_string "mmxmov")
2257             (eq_attr "alternative" "11")
2258               (const_string "sselog1")
2259             (eq_attr "alternative" "12,13,14,15,16")
2260               (const_string "ssemov")
2261             (eq_attr "alternative" "17,18")
2262               (const_string "ssecvt")
2263             (eq_attr "alternative" "4")
2264               (const_string "multi")
2265             (match_operand:DI 1 "pic_32bit_operand" "")
2266               (const_string "lea")
2267            ]
2268            (const_string "imov")))
2269    (set_attr "modrm" "*,0,0,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*")
2270    (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*,*")
2271    (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,DI,DI,TI,TI,DI,DI,DI,DI,DI,DI")])
2272
2273 ;; Stores and loads of ax to arbitrary constant address.
2274 ;; We fake an second form of instruction to force reload to load address
2275 ;; into register when rax is not available
2276 (define_insn "*movabsdi_1_rex64"
2277   [(set (mem:DI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2278         (match_operand:DI 1 "nonmemory_operand" "a,er"))]
2279   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
2280   "@
2281    movabs{q}\t{%1, %P0|%P0, %1}
2282    mov{q}\t{%1, %a0|%a0, %1}"
2283   [(set_attr "type" "imov")
2284    (set_attr "modrm" "0,*")
2285    (set_attr "length_address" "8,0")
2286    (set_attr "length_immediate" "0,*")
2287    (set_attr "memory" "store")
2288    (set_attr "mode" "DI")])
2289
2290 (define_insn "*movabsdi_2_rex64"
2291   [(set (match_operand:DI 0 "register_operand" "=a,r")
2292         (mem:DI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2293   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
2294   "@
2295    movabs{q}\t{%P1, %0|%0, %P1}
2296    mov{q}\t{%a1, %0|%0, %a1}"
2297   [(set_attr "type" "imov")
2298    (set_attr "modrm" "0,*")
2299    (set_attr "length_address" "8,0")
2300    (set_attr "length_immediate" "0")
2301    (set_attr "memory" "load")
2302    (set_attr "mode" "DI")])
2303
2304 ;; Convert impossible stores of immediate to existing instructions.
2305 ;; First try to get scratch register and go through it.  In case this
2306 ;; fails, move by 32bit parts.
2307 (define_peephole2
2308   [(match_scratch:DI 2 "r")
2309    (set (match_operand:DI 0 "memory_operand" "")
2310         (match_operand:DI 1 "immediate_operand" ""))]
2311   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2312    && !x86_64_immediate_operand (operands[1], DImode)"
2313   [(set (match_dup 2) (match_dup 1))
2314    (set (match_dup 0) (match_dup 2))]
2315   "")
2316
2317 ;; We need to define this as both peepholer and splitter for case
2318 ;; peephole2 pass is not run.
2319 ;; "&& 1" is needed to keep it from matching the previous pattern.
2320 (define_peephole2
2321   [(set (match_operand:DI 0 "memory_operand" "")
2322         (match_operand:DI 1 "immediate_operand" ""))]
2323   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2324    && !x86_64_immediate_operand (operands[1], DImode) && 1"
2325   [(set (match_dup 2) (match_dup 3))
2326    (set (match_dup 4) (match_dup 5))]
2327   "split_di (operands, 2, operands + 2, operands + 4);")
2328
2329 (define_split
2330   [(set (match_operand:DI 0 "memory_operand" "")
2331         (match_operand:DI 1 "immediate_operand" ""))]
2332   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2333                     ? epilogue_completed : reload_completed)
2334    && !symbolic_operand (operands[1], DImode)
2335    && !x86_64_immediate_operand (operands[1], DImode)"
2336   [(set (match_dup 2) (match_dup 3))
2337    (set (match_dup 4) (match_dup 5))]
2338   "split_di (operands, 2, operands + 2, operands + 4);")
2339
2340 (define_insn "*swapdi_rex64"
2341   [(set (match_operand:DI 0 "register_operand" "+r")
2342         (match_operand:DI 1 "register_operand" "+r"))
2343    (set (match_dup 1)
2344         (match_dup 0))]
2345   "TARGET_64BIT"
2346   "xchg{q}\t%1, %0"
2347   [(set_attr "type" "imov")
2348    (set_attr "mode" "DI")
2349    (set_attr "pent_pair" "np")
2350    (set_attr "athlon_decode" "vector")
2351    (set_attr "amdfam10_decode" "double")])
2352
2353 (define_expand "movti"
2354   [(set (match_operand:TI 0 "nonimmediate_operand" "")
2355         (match_operand:TI 1 "nonimmediate_operand" ""))]
2356   "TARGET_SSE || TARGET_64BIT"
2357 {
2358   if (TARGET_64BIT)
2359     ix86_expand_move (TImode, operands);
2360   else if (push_operand (operands[0], TImode))
2361     ix86_expand_push (TImode, operands[1]);
2362   else
2363     ix86_expand_vector_move (TImode, operands);
2364   DONE;
2365 })
2366
2367 (define_insn "*movti_internal"
2368   [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
2369         (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
2370   "TARGET_SSE && !TARGET_64BIT
2371    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2372 {
2373   switch (which_alternative)
2374     {
2375     case 0:
2376       if (get_attr_mode (insn) == MODE_V4SF)
2377         return "xorps\t%0, %0";
2378       else
2379         return "pxor\t%0, %0";
2380     case 1:
2381     case 2:
2382       if (get_attr_mode (insn) == MODE_V4SF)
2383         return "movaps\t{%1, %0|%0, %1}";
2384       else
2385         return "movdqa\t{%1, %0|%0, %1}";
2386     default:
2387       gcc_unreachable ();
2388     }
2389 }
2390   [(set_attr "type" "sselog1,ssemov,ssemov")
2391    (set (attr "mode")
2392         (cond [(ior (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2393                     (ne (symbol_ref "optimize_size") (const_int 0)))
2394                  (const_string "V4SF")
2395                (and (eq_attr "alternative" "2")
2396                     (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2397                         (const_int 0)))
2398                  (const_string "V4SF")]
2399               (const_string "TI")))])
2400
2401 (define_insn "*movti_rex64"
2402   [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o,x,x,xm")
2403         (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
2404   "TARGET_64BIT
2405    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
2406 {
2407   switch (which_alternative)
2408     {
2409     case 0:
2410     case 1:
2411       return "#";
2412     case 2:
2413       if (get_attr_mode (insn) == MODE_V4SF)
2414         return "xorps\t%0, %0";
2415       else
2416         return "pxor\t%0, %0";
2417     case 3:
2418     case 4:
2419       if (get_attr_mode (insn) == MODE_V4SF)
2420         return "movaps\t{%1, %0|%0, %1}";
2421       else
2422         return "movdqa\t{%1, %0|%0, %1}";
2423     default:
2424       gcc_unreachable ();
2425     }
2426 }
2427   [(set_attr "type" "*,*,sselog1,ssemov,ssemov")
2428    (set (attr "mode")
2429         (cond [(eq_attr "alternative" "2,3")
2430                  (if_then_else
2431                    (ne (symbol_ref "optimize_size")
2432                        (const_int 0))
2433                    (const_string "V4SF")
2434                    (const_string "TI"))
2435                (eq_attr "alternative" "4")
2436                  (if_then_else
2437                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2438                             (const_int 0))
2439                         (ne (symbol_ref "optimize_size")
2440                             (const_int 0)))
2441                    (const_string "V4SF")
2442                    (const_string "TI"))]
2443                (const_string "DI")))])
2444
2445 (define_split
2446   [(set (match_operand:TI 0 "nonimmediate_operand" "")
2447         (match_operand:TI 1 "general_operand" ""))]
2448   "reload_completed && !SSE_REG_P (operands[0])
2449    && !SSE_REG_P (operands[1])"
2450   [(const_int 0)]
2451   "ix86_split_long_move (operands); DONE;")
2452
2453 ;; This expands to what emit_move_complex would generate if we didn't
2454 ;; have a movti pattern.  Having this avoids problems with reload on
2455 ;; 32-bit targets when SSE is present, but doesn't seem to be harmful
2456 ;; to have around all the time.
2457 (define_expand "movcdi"
2458   [(set (match_operand:CDI 0 "nonimmediate_operand" "")
2459         (match_operand:CDI 1 "general_operand" ""))]
2460   ""
2461 {
2462   if (push_operand (operands[0], CDImode))
2463     emit_move_complex_push (CDImode, operands[0], operands[1]);
2464   else
2465     emit_move_complex_parts (operands[0], operands[1]);
2466   DONE;
2467 })
2468
2469 (define_expand "movsf"
2470   [(set (match_operand:SF 0 "nonimmediate_operand" "")
2471         (match_operand:SF 1 "general_operand" ""))]
2472   ""
2473   "ix86_expand_move (SFmode, operands); DONE;")
2474
2475 (define_insn "*pushsf"
2476   [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2477         (match_operand:SF 1 "general_no_elim_operand" "f,rFm,x"))]
2478   "!TARGET_64BIT"
2479 {
2480   /* Anything else should be already split before reg-stack.  */
2481   gcc_assert (which_alternative == 1);
2482   return "push{l}\t%1";
2483 }
2484   [(set_attr "type" "multi,push,multi")
2485    (set_attr "unit" "i387,*,*")
2486    (set_attr "mode" "SF,SI,SF")])
2487
2488 (define_insn "*pushsf_rex64"
2489   [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2490         (match_operand:SF 1 "nonmemory_no_elim_operand" "f,rF,x"))]
2491   "TARGET_64BIT"
2492 {
2493   /* Anything else should be already split before reg-stack.  */
2494   gcc_assert (which_alternative == 1);
2495   return "push{q}\t%q1";
2496 }
2497   [(set_attr "type" "multi,push,multi")
2498    (set_attr "unit" "i387,*,*")
2499    (set_attr "mode" "SF,DI,SF")])
2500
2501 (define_split
2502   [(set (match_operand:SF 0 "push_operand" "")
2503         (match_operand:SF 1 "memory_operand" ""))]
2504   "reload_completed
2505    && MEM_P (operands[1])
2506    && (operands[2] = find_constant_src (insn))"
2507   [(set (match_dup 0)
2508         (match_dup 2))])
2509
2510
2511 ;; %%% Kill this when call knows how to work this out.
2512 (define_split
2513   [(set (match_operand:SF 0 "push_operand" "")
2514         (match_operand:SF 1 "any_fp_register_operand" ""))]
2515   "!TARGET_64BIT"
2516   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
2517    (set (mem:SF (reg:SI SP_REG)) (match_dup 1))])
2518
2519 (define_split
2520   [(set (match_operand:SF 0 "push_operand" "")
2521         (match_operand:SF 1 "any_fp_register_operand" ""))]
2522   "TARGET_64BIT"
2523   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2524    (set (mem:SF (reg:DI SP_REG)) (match_dup 1))])
2525
2526 (define_insn "*movsf_1"
2527   [(set (match_operand:SF 0 "nonimmediate_operand"
2528           "=f,m,f,r  ,m ,x,x,x ,m,!*y,!m,!*y,?Yi,?r,!*Ym,!r")
2529         (match_operand:SF 1 "general_operand"
2530           "fm,f,G,rmF,Fr,C,x,xm,x,m  ,*y,*y ,r  ,Yi,r   ,*Ym"))]
2531   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2532    && (reload_in_progress || reload_completed
2533        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2534        || (!TARGET_SSE_MATH && optimize_size
2535            && standard_80387_constant_p (operands[1]))
2536        || GET_CODE (operands[1]) != CONST_DOUBLE
2537        || memory_operand (operands[0], SFmode))"
2538 {
2539   switch (which_alternative)
2540     {
2541     case 0:
2542     case 1:
2543       return output_387_reg_move (insn, operands);
2544
2545     case 2:
2546       return standard_80387_constant_opcode (operands[1]);
2547
2548     case 3:
2549     case 4:
2550       return "mov{l}\t{%1, %0|%0, %1}";
2551     case 5:
2552       if (get_attr_mode (insn) == MODE_TI)
2553         return "pxor\t%0, %0";
2554       else
2555         return "xorps\t%0, %0";
2556     case 6:
2557       if (get_attr_mode (insn) == MODE_V4SF)
2558         return "movaps\t{%1, %0|%0, %1}";
2559       else
2560         return "movss\t{%1, %0|%0, %1}";
2561     case 7: case 8:
2562       return "movss\t{%1, %0|%0, %1}";
2563
2564     case 9: case 10:
2565     case 12: case 13: case 14: case 15:
2566       return "movd\t{%1, %0|%0, %1}";
2567
2568     case 11:
2569       return "movq\t{%1, %0|%0, %1}";
2570
2571     default:
2572       gcc_unreachable ();
2573     }
2574 }
2575   [(set_attr "type" "fmov,fmov,fmov,imov,imov,sselog1,ssemov,ssemov,ssemov,mmxmov,mmxmov,mmxmov,ssemov,ssemov,mmxmov,mmxmov")
2576    (set (attr "mode")
2577         (cond [(eq_attr "alternative" "3,4,9,10")
2578                  (const_string "SI")
2579                (eq_attr "alternative" "5")
2580                  (if_then_else
2581                    (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2582                                  (const_int 0))
2583                              (ne (symbol_ref "TARGET_SSE2")
2584                                  (const_int 0)))
2585                         (eq (symbol_ref "optimize_size")
2586                             (const_int 0)))
2587                    (const_string "TI")
2588                    (const_string "V4SF"))
2589                /* For architectures resolving dependencies on
2590                   whole SSE registers use APS move to break dependency
2591                   chains, otherwise use short move to avoid extra work.
2592
2593                   Do the same for architectures resolving dependencies on
2594                   the parts.  While in DF mode it is better to always handle
2595                   just register parts, the SF mode is different due to lack
2596                   of instructions to load just part of the register.  It is
2597                   better to maintain the whole registers in single format
2598                   to avoid problems on using packed logical operations.  */
2599                (eq_attr "alternative" "6")
2600                  (if_then_else
2601                    (ior (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2602                             (const_int 0))
2603                         (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2604                             (const_int 0)))
2605                    (const_string "V4SF")
2606                    (const_string "SF"))
2607                (eq_attr "alternative" "11")
2608                  (const_string "DI")]
2609                (const_string "SF")))])
2610
2611 (define_insn "*swapsf"
2612   [(set (match_operand:SF 0 "fp_register_operand" "+f")
2613         (match_operand:SF 1 "fp_register_operand" "+f"))
2614    (set (match_dup 1)
2615         (match_dup 0))]
2616   "reload_completed || TARGET_80387"
2617 {
2618   if (STACK_TOP_P (operands[0]))
2619     return "fxch\t%1";
2620   else
2621     return "fxch\t%0";
2622 }
2623   [(set_attr "type" "fxch")
2624    (set_attr "mode" "SF")])
2625
2626 (define_expand "movdf"
2627   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2628         (match_operand:DF 1 "general_operand" ""))]
2629   ""
2630   "ix86_expand_move (DFmode, operands); DONE;")
2631
2632 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2633 ;; Size of pushdf using integer instructions is 2+2*memory operand size
2634 ;; On the average, pushdf using integers can be still shorter.  Allow this
2635 ;; pattern for optimize_size too.
2636
2637 (define_insn "*pushdf_nointeger"
2638   [(set (match_operand:DF 0 "push_operand" "=<,<,<,<")
2639         (match_operand:DF 1 "general_no_elim_operand" "f,Fo,*r,Y2"))]
2640   "!TARGET_64BIT && !TARGET_INTEGER_DFMODE_MOVES"
2641 {
2642   /* This insn should be already split before reg-stack.  */
2643   gcc_unreachable ();
2644 }
2645   [(set_attr "type" "multi")
2646    (set_attr "unit" "i387,*,*,*")
2647    (set_attr "mode" "DF,SI,SI,DF")])
2648
2649 (define_insn "*pushdf_integer"
2650   [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2651         (match_operand:DF 1 "general_no_elim_operand" "f,rFo,Y2"))]
2652   "TARGET_64BIT || TARGET_INTEGER_DFMODE_MOVES"
2653 {
2654   /* This insn should be already split before reg-stack.  */
2655   gcc_unreachable ();
2656 }
2657   [(set_attr "type" "multi")
2658    (set_attr "unit" "i387,*,*")
2659    (set_attr "mode" "DF,SI,DF")])
2660
2661 ;; %%% Kill this when call knows how to work this out.
2662 (define_split
2663   [(set (match_operand:DF 0 "push_operand" "")
2664         (match_operand:DF 1 "any_fp_register_operand" ""))]
2665   "!TARGET_64BIT && reload_completed"
2666   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
2667    (set (mem:DF (reg:SI SP_REG)) (match_dup 1))]
2668   "")
2669
2670 (define_split
2671   [(set (match_operand:DF 0 "push_operand" "")
2672         (match_operand:DF 1 "any_fp_register_operand" ""))]
2673   "TARGET_64BIT && reload_completed"
2674   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2675    (set (mem:DF (reg:DI SP_REG)) (match_dup 1))]
2676   "")
2677
2678 (define_split
2679   [(set (match_operand:DF 0 "push_operand" "")
2680         (match_operand:DF 1 "general_operand" ""))]
2681   "reload_completed"
2682   [(const_int 0)]
2683   "ix86_split_long_move (operands); DONE;")
2684
2685 ;; Moving is usually shorter when only FP registers are used. This separate
2686 ;; movdf pattern avoids the use of integer registers for FP operations
2687 ;; when optimizing for size.
2688
2689 (define_insn "*movdf_nointeger"
2690   [(set (match_operand:DF 0 "nonimmediate_operand"
2691                         "=f,m,f,*r  ,o  ,Y2*x,Y2*x,Y2*x ,m  ")
2692         (match_operand:DF 1 "general_operand"
2693                         "fm,f,G,*roF,*Fr,C   ,Y2*x,mY2*x,Y2*x"))]
2694   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2695    && ((optimize_size || !TARGET_INTEGER_DFMODE_MOVES) && !TARGET_64BIT)
2696    && (reload_in_progress || reload_completed
2697        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2698        || (!(TARGET_SSE2 && TARGET_SSE_MATH) && optimize_size
2699            && !memory_operand (operands[0], DFmode)
2700            && standard_80387_constant_p (operands[1]))
2701        || GET_CODE (operands[1]) != CONST_DOUBLE
2702        || ((optimize_size
2703             || !TARGET_MEMORY_MISMATCH_STALL
2704             || reload_in_progress || reload_completed)
2705            && memory_operand (operands[0], DFmode)))"
2706 {
2707   switch (which_alternative)
2708     {
2709     case 0:
2710     case 1:
2711       return output_387_reg_move (insn, operands);
2712
2713     case 2:
2714       return standard_80387_constant_opcode (operands[1]);
2715
2716     case 3:
2717     case 4:
2718       return "#";
2719     case 5:
2720       switch (get_attr_mode (insn))
2721         {
2722         case MODE_V4SF:
2723           return "xorps\t%0, %0";
2724         case MODE_V2DF:
2725           return "xorpd\t%0, %0";
2726         case MODE_TI:
2727           return "pxor\t%0, %0";
2728         default:
2729           gcc_unreachable ();
2730         }
2731     case 6:
2732     case 7:
2733     case 8:
2734       switch (get_attr_mode (insn))
2735         {
2736         case MODE_V4SF:
2737           return "movaps\t{%1, %0|%0, %1}";
2738         case MODE_V2DF:
2739           return "movapd\t{%1, %0|%0, %1}";
2740         case MODE_TI:
2741           return "movdqa\t{%1, %0|%0, %1}";
2742         case MODE_DI:
2743           return "movq\t{%1, %0|%0, %1}";
2744         case MODE_DF:
2745           return "movsd\t{%1, %0|%0, %1}";
2746         case MODE_V1DF:
2747           return "movlpd\t{%1, %0|%0, %1}";
2748         case MODE_V2SF:
2749           return "movlps\t{%1, %0|%0, %1}";
2750         default:
2751           gcc_unreachable ();
2752         }
2753
2754     default:
2755       gcc_unreachable ();
2756     }
2757 }
2758   [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov")
2759    (set (attr "mode")
2760         (cond [(eq_attr "alternative" "0,1,2")
2761                  (const_string "DF")
2762                (eq_attr "alternative" "3,4")
2763                  (const_string "SI")
2764
2765                /* For SSE1, we have many fewer alternatives.  */
2766                (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2767                  (cond [(eq_attr "alternative" "5,6")
2768                           (const_string "V4SF")
2769                        ]
2770                    (const_string "V2SF"))
2771
2772                /* xorps is one byte shorter.  */
2773                (eq_attr "alternative" "5")
2774                  (cond [(ne (symbol_ref "optimize_size")
2775                             (const_int 0))
2776                           (const_string "V4SF")
2777                         (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2778                             (const_int 0))
2779                           (const_string "TI")
2780                        ]
2781                        (const_string "V2DF"))
2782
2783                /* For architectures resolving dependencies on
2784                   whole SSE registers use APD move to break dependency
2785                   chains, otherwise use short move to avoid extra work.
2786
2787                   movaps encodes one byte shorter.  */
2788                (eq_attr "alternative" "6")
2789                  (cond
2790                    [(ne (symbol_ref "optimize_size")
2791                         (const_int 0))
2792                       (const_string "V4SF")
2793                     (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2794                         (const_int 0))
2795                       (const_string "V2DF")
2796                    ]
2797                    (const_string "DF"))
2798                /* For architectures resolving dependencies on register
2799                   parts we may avoid extra work to zero out upper part
2800                   of register.  */
2801                (eq_attr "alternative" "7")
2802                  (if_then_else
2803                    (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2804                        (const_int 0))
2805                    (const_string "V1DF")
2806                    (const_string "DF"))
2807               ]
2808               (const_string "DF")))])
2809
2810 (define_insn "*movdf_integer_rex64"
2811   [(set (match_operand:DF 0 "nonimmediate_operand"
2812                 "=f,m,f,r  ,m ,Y2*x,Y2*x,Y2*x,m   ,Yi,r ")
2813         (match_operand:DF 1 "general_operand"
2814                 "fm,f,G,rmF,Fr,C   ,Y2*x,m   ,Y2*x,r ,Yi"))]
2815   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))
2816    && (reload_in_progress || reload_completed
2817        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2818        || (!(TARGET_SSE2 && TARGET_SSE_MATH) && optimize_size
2819            && standard_80387_constant_p (operands[1]))
2820        || GET_CODE (operands[1]) != CONST_DOUBLE
2821        || memory_operand (operands[0], DFmode))"
2822 {
2823   switch (which_alternative)
2824     {
2825     case 0:
2826     case 1:
2827       return output_387_reg_move (insn, operands);
2828
2829     case 2:
2830       return standard_80387_constant_opcode (operands[1]);
2831
2832     case 3:
2833     case 4:
2834       return "#";
2835
2836     case 5:
2837       switch (get_attr_mode (insn))
2838         {
2839         case MODE_V4SF:
2840           return "xorps\t%0, %0";
2841         case MODE_V2DF:
2842           return "xorpd\t%0, %0";
2843         case MODE_TI:
2844           return "pxor\t%0, %0";
2845         default:
2846           gcc_unreachable ();
2847         }
2848     case 6:
2849     case 7:
2850     case 8:
2851       switch (get_attr_mode (insn))
2852         {
2853         case MODE_V4SF:
2854           return "movaps\t{%1, %0|%0, %1}";
2855         case MODE_V2DF:
2856           return "movapd\t{%1, %0|%0, %1}";
2857         case MODE_TI:
2858           return "movdqa\t{%1, %0|%0, %1}";
2859         case MODE_DI:
2860           return "movq\t{%1, %0|%0, %1}";
2861         case MODE_DF:
2862           return "movsd\t{%1, %0|%0, %1}";
2863         case MODE_V1DF:
2864           return "movlpd\t{%1, %0|%0, %1}";
2865         case MODE_V2SF:
2866           return "movlps\t{%1, %0|%0, %1}";
2867         default:
2868           gcc_unreachable ();
2869         }
2870
2871     case 9:
2872     case 10:
2873       return "movd\t{%1, %0|%0, %1}";
2874
2875     default:
2876       gcc_unreachable();
2877     }
2878 }
2879   [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov,ssemov,ssemov")
2880    (set (attr "mode")
2881         (cond [(eq_attr "alternative" "0,1,2")
2882                  (const_string "DF")
2883                (eq_attr "alternative" "3,4,9,10")
2884                  (const_string "DI")
2885
2886                /* For SSE1, we have many fewer alternatives.  */
2887                (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2888                  (cond [(eq_attr "alternative" "5,6")
2889                           (const_string "V4SF")
2890                        ]
2891                    (const_string "V2SF"))
2892
2893                /* xorps is one byte shorter.  */
2894                (eq_attr "alternative" "5")
2895                  (cond [(ne (symbol_ref "optimize_size")
2896                             (const_int 0))
2897                           (const_string "V4SF")
2898                         (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2899                             (const_int 0))
2900                           (const_string "TI")
2901                        ]
2902                        (const_string "V2DF"))
2903
2904                /* For architectures resolving dependencies on
2905                   whole SSE registers use APD move to break dependency
2906                   chains, otherwise use short move to avoid extra work.
2907
2908                   movaps encodes one byte shorter.  */
2909                (eq_attr "alternative" "6")
2910                  (cond
2911                    [(ne (symbol_ref "optimize_size")
2912                         (const_int 0))
2913                       (const_string "V4SF")
2914                     (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2915                         (const_int 0))
2916                       (const_string "V2DF")
2917                    ]
2918                    (const_string "DF"))
2919                /* For architectures resolving dependencies on register
2920                   parts we may avoid extra work to zero out upper part
2921                   of register.  */
2922                (eq_attr "alternative" "7")
2923                  (if_then_else
2924                    (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2925                        (const_int 0))
2926                    (const_string "V1DF")
2927                    (const_string "DF"))
2928               ]
2929               (const_string "DF")))])
2930
2931 (define_insn "*movdf_integer"
2932   [(set (match_operand:DF 0 "nonimmediate_operand"
2933                 "=f,m,f,r  ,o ,Y2*x,Y2*x,Y2*x,m   ")
2934         (match_operand:DF 1 "general_operand"
2935                 "fm,f,G,roF,Fr,C   ,Y2*x,m   ,Y2*x"))]
2936   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2937    && !optimize_size && TARGET_INTEGER_DFMODE_MOVES
2938    && (reload_in_progress || reload_completed
2939        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2940        || (!(TARGET_SSE2 && TARGET_SSE_MATH) && optimize_size
2941            && standard_80387_constant_p (operands[1]))
2942        || GET_CODE (operands[1]) != CONST_DOUBLE
2943        || memory_operand (operands[0], DFmode))"
2944 {
2945   switch (which_alternative)
2946     {
2947     case 0:
2948     case 1:
2949       return output_387_reg_move (insn, operands);
2950
2951     case 2:
2952       return standard_80387_constant_opcode (operands[1]);
2953
2954     case 3:
2955     case 4:
2956       return "#";
2957
2958     case 5:
2959       switch (get_attr_mode (insn))
2960         {
2961         case MODE_V4SF:
2962           return "xorps\t%0, %0";
2963         case MODE_V2DF:
2964           return "xorpd\t%0, %0";
2965         case MODE_TI:
2966           return "pxor\t%0, %0";
2967         default:
2968           gcc_unreachable ();
2969         }
2970     case 6:
2971     case 7:
2972     case 8:
2973       switch (get_attr_mode (insn))
2974         {
2975         case MODE_V4SF:
2976           return "movaps\t{%1, %0|%0, %1}";
2977         case MODE_V2DF:
2978           return "movapd\t{%1, %0|%0, %1}";
2979         case MODE_TI:
2980           return "movdqa\t{%1, %0|%0, %1}";
2981         case MODE_DI:
2982           return "movq\t{%1, %0|%0, %1}";
2983         case MODE_DF:
2984           return "movsd\t{%1, %0|%0, %1}";
2985         case MODE_V1DF:
2986           return "movlpd\t{%1, %0|%0, %1}";
2987         case MODE_V2SF:
2988           return "movlps\t{%1, %0|%0, %1}";
2989         default:
2990           gcc_unreachable ();
2991         }
2992
2993     default:
2994       gcc_unreachable();
2995     }
2996 }
2997   [(set_attr "type" "fmov,fmov,fmov,multi,multi,sselog1,ssemov,ssemov,ssemov")
2998    (set (attr "mode")
2999         (cond [(eq_attr "alternative" "0,1,2")
3000                  (const_string "DF")
3001                (eq_attr "alternative" "3,4")
3002                  (const_string "SI")
3003
3004                /* For SSE1, we have many fewer alternatives.  */
3005                (eq (symbol_ref "TARGET_SSE2") (const_int 0))
3006                  (cond [(eq_attr "alternative" "5,6")
3007                           (const_string "V4SF")
3008                        ]
3009                    (const_string "V2SF"))
3010
3011                /* xorps is one byte shorter.  */
3012                (eq_attr "alternative" "5")
3013                  (cond [(ne (symbol_ref "optimize_size")
3014                             (const_int 0))
3015                           (const_string "V4SF")
3016                         (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
3017                             (const_int 0))
3018                           (const_string "TI")
3019                        ]
3020                        (const_string "V2DF"))
3021
3022                /* For architectures resolving dependencies on
3023                   whole SSE registers use APD move to break dependency
3024                   chains, otherwise use short move to avoid extra work.
3025
3026                   movaps encodes one byte shorter.  */
3027                (eq_attr "alternative" "6")
3028                  (cond
3029                    [(ne (symbol_ref "optimize_size")
3030                         (const_int 0))
3031                       (const_string "V4SF")
3032                     (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
3033                         (const_int 0))
3034                       (const_string "V2DF")
3035                    ]
3036                    (const_string "DF"))
3037                /* For architectures resolving dependencies on register
3038                   parts we may avoid extra work to zero out upper part
3039                   of register.  */
3040                (eq_attr "alternative" "7")
3041                  (if_then_else
3042                    (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
3043                        (const_int 0))
3044                    (const_string "V1DF")
3045                    (const_string "DF"))
3046               ]
3047               (const_string "DF")))])
3048
3049 (define_split
3050   [(set (match_operand:DF 0 "nonimmediate_operand" "")
3051         (match_operand:DF 1 "general_operand" ""))]
3052   "reload_completed
3053    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3054    && ! (ANY_FP_REG_P (operands[0]) ||
3055          (GET_CODE (operands[0]) == SUBREG
3056           && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
3057    && ! (ANY_FP_REG_P (operands[1]) ||
3058          (GET_CODE (operands[1]) == SUBREG
3059           && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
3060   [(const_int 0)]
3061   "ix86_split_long_move (operands); DONE;")
3062
3063 (define_insn "*swapdf"
3064   [(set (match_operand:DF 0 "fp_register_operand" "+f")
3065         (match_operand:DF 1 "fp_register_operand" "+f"))
3066    (set (match_dup 1)
3067         (match_dup 0))]
3068   "reload_completed || TARGET_80387"
3069 {
3070   if (STACK_TOP_P (operands[0]))
3071     return "fxch\t%1";
3072   else
3073     return "fxch\t%0";
3074 }
3075   [(set_attr "type" "fxch")
3076    (set_attr "mode" "DF")])
3077
3078 (define_expand "movxf"
3079   [(set (match_operand:XF 0 "nonimmediate_operand" "")
3080         (match_operand:XF 1 "general_operand" ""))]
3081   ""
3082   "ix86_expand_move (XFmode, operands); DONE;")
3083
3084 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
3085 ;; Size of pushdf using integer instructions is 3+3*memory operand size
3086 ;; Pushing using integer instructions is longer except for constants
3087 ;; and direct memory references.
3088 ;; (assuming that any given constant is pushed only once, but this ought to be
3089 ;;  handled elsewhere).
3090
3091 (define_insn "*pushxf_nointeger"
3092   [(set (match_operand:XF 0 "push_operand" "=X,X,X")
3093         (match_operand:XF 1 "general_no_elim_operand" "f,Fo,*r"))]
3094   "optimize_size"
3095 {
3096   /* This insn should be already split before reg-stack.  */
3097   gcc_unreachable ();
3098 }
3099   [(set_attr "type" "multi")
3100    (set_attr "unit" "i387,*,*")
3101    (set_attr "mode" "XF,SI,SI")])
3102
3103 (define_insn "*pushxf_integer"
3104   [(set (match_operand:XF 0 "push_operand" "=<,<")
3105         (match_operand:XF 1 "general_no_elim_operand" "f,ro"))]
3106   "!optimize_size"
3107 {
3108   /* This insn should be already split before reg-stack.  */
3109   gcc_unreachable ();
3110 }
3111   [(set_attr "type" "multi")
3112    (set_attr "unit" "i387,*")
3113    (set_attr "mode" "XF,SI")])
3114
3115 (define_split
3116   [(set (match_operand 0 "push_operand" "")
3117         (match_operand 1 "general_operand" ""))]
3118   "reload_completed
3119    && (GET_MODE (operands[0]) == XFmode
3120        || GET_MODE (operands[0]) == DFmode)
3121    && !ANY_FP_REG_P (operands[1])"
3122   [(const_int 0)]
3123   "ix86_split_long_move (operands); DONE;")
3124
3125 (define_split
3126   [(set (match_operand:XF 0 "push_operand" "")
3127         (match_operand:XF 1 "any_fp_register_operand" ""))]
3128   "!TARGET_64BIT"
3129   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3130    (set (mem:XF (reg:SI SP_REG)) (match_dup 1))]
3131   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3132
3133 (define_split
3134   [(set (match_operand:XF 0 "push_operand" "")
3135         (match_operand:XF 1 "any_fp_register_operand" ""))]
3136   "TARGET_64BIT"
3137   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3138    (set (mem:XF (reg:DI SP_REG)) (match_dup 1))]
3139   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3140
3141 ;; Do not use integer registers when optimizing for size
3142 (define_insn "*movxf_nointeger"
3143   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,*r,o")
3144         (match_operand:XF 1 "general_operand" "fm,f,G,*roF,F*r"))]
3145   "optimize_size
3146    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3147    && (reload_in_progress || reload_completed
3148        || (optimize_size && standard_80387_constant_p (operands[1]))
3149        || GET_CODE (operands[1]) != CONST_DOUBLE
3150        || memory_operand (operands[0], XFmode))"
3151 {
3152   switch (which_alternative)
3153     {
3154     case 0:
3155     case 1:
3156       return output_387_reg_move (insn, operands);
3157
3158     case 2:
3159       return standard_80387_constant_opcode (operands[1]);
3160
3161     case 3: case 4:
3162       return "#";
3163     default:
3164       gcc_unreachable ();
3165     }
3166 }
3167   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
3168    (set_attr "mode" "XF,XF,XF,SI,SI")])
3169
3170 (define_insn "*movxf_integer"
3171   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,r,o")
3172         (match_operand:XF 1 "general_operand" "fm,f,G,roF,Fr"))]
3173   "!optimize_size
3174    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3175    && (reload_in_progress || reload_completed
3176        || (optimize_size && standard_80387_constant_p (operands[1]))
3177        || GET_CODE (operands[1]) != CONST_DOUBLE
3178        || memory_operand (operands[0], XFmode))"
3179 {
3180   switch (which_alternative)
3181     {
3182     case 0:
3183     case 1:
3184       return output_387_reg_move (insn, operands);
3185
3186     case 2:
3187       return standard_80387_constant_opcode (operands[1]);
3188
3189     case 3: case 4:
3190       return "#";
3191
3192     default:
3193       gcc_unreachable ();
3194     }
3195 }
3196   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
3197    (set_attr "mode" "XF,XF,XF,SI,SI")])
3198
3199 (define_expand "movtf"
3200   [(set (match_operand:TF 0 "nonimmediate_operand" "")
3201         (match_operand:TF 1 "nonimmediate_operand" ""))]
3202   "TARGET_64BIT"
3203 {
3204   ix86_expand_move (TFmode, operands);
3205   DONE;
3206 })
3207
3208 (define_insn "*movtf_internal"
3209   [(set (match_operand:TF 0 "nonimmediate_operand" "=x,m,x,?r,?o")
3210         (match_operand:TF 1 "general_operand" "xm,x,C,roF,Fr"))]
3211   "TARGET_64BIT
3212    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
3213 {
3214   switch (which_alternative)
3215     {
3216     case 0:
3217     case 1:
3218       if (get_attr_mode (insn) == MODE_V4SF)
3219         return "movaps\t{%1, %0|%0, %1}";
3220       else
3221         return "movdqa\t{%1, %0|%0, %1}";
3222     case 2:
3223       if (get_attr_mode (insn) == MODE_V4SF)
3224         return "xorps\t%0, %0";
3225       else
3226         return "pxor\t%0, %0";
3227     case 3:
3228     case 4:
3229         return "#";
3230     default:
3231       gcc_unreachable ();
3232     }
3233 }
3234   [(set_attr "type" "ssemov,ssemov,sselog1,*,*")
3235    (set (attr "mode")
3236         (cond [(eq_attr "alternative" "0,2")
3237                  (if_then_else
3238                    (ne (symbol_ref "optimize_size")
3239                        (const_int 0))
3240                    (const_string "V4SF")
3241                    (const_string "TI"))
3242                (eq_attr "alternative" "1")
3243                  (if_then_else
3244                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
3245                             (const_int 0))
3246                         (ne (symbol_ref "optimize_size")
3247                             (const_int 0)))
3248                    (const_string "V4SF")
3249                    (const_string "TI"))]
3250                (const_string "DI")))])
3251
3252 (define_split
3253   [(set (match_operand 0 "nonimmediate_operand" "")
3254         (match_operand 1 "general_operand" ""))]
3255   "reload_completed
3256    && !(MEM_P (operands[0]) && MEM_P (operands[1]))
3257    && GET_MODE (operands[0]) == XFmode
3258    && ! (ANY_FP_REG_P (operands[0]) ||
3259          (GET_CODE (operands[0]) == SUBREG
3260           && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
3261    && ! (ANY_FP_REG_P (operands[1]) ||
3262          (GET_CODE (operands[1]) == SUBREG
3263           && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
3264   [(const_int 0)]
3265   "ix86_split_long_move (operands); DONE;")
3266
3267 (define_split
3268   [(set (match_operand 0 "register_operand" "")
3269         (match_operand 1 "memory_operand" ""))]
3270   "reload_completed
3271    && MEM_P (operands[1])
3272    && (GET_MODE (operands[0]) == TFmode
3273        || GET_MODE (operands[0]) == XFmode
3274        || GET_MODE (operands[0]) == SFmode
3275        || GET_MODE (operands[0]) == DFmode)
3276    && (operands[2] = find_constant_src (insn))"
3277   [(set (match_dup 0) (match_dup 2))]
3278 {
3279   rtx c = operands[2];
3280   rtx r = operands[0];
3281
3282   if (GET_CODE (r) == SUBREG)
3283     r = SUBREG_REG (r);
3284
3285   if (SSE_REG_P (r))
3286     {
3287       if (!standard_sse_constant_p (c))
3288         FAIL;
3289     }
3290   else if (FP_REG_P (r))
3291     {
3292       if (!standard_80387_constant_p (c))
3293         FAIL;
3294     }
3295   else if (MMX_REG_P (r))
3296     FAIL;
3297 })
3298
3299 (define_split
3300   [(set (match_operand 0 "register_operand" "")
3301         (float_extend (match_operand 1 "memory_operand" "")))]
3302   "reload_completed
3303    && MEM_P (operands[1])
3304    && (GET_MODE (operands[0]) == TFmode
3305        || GET_MODE (operands[0]) == XFmode
3306        || GET_MODE (operands[0]) == SFmode
3307        || GET_MODE (operands[0]) == DFmode)
3308    && (operands[2] = find_constant_src (insn))"
3309   [(set (match_dup 0) (match_dup 2))]
3310 {
3311   rtx c = operands[2];
3312   rtx r = operands[0];
3313
3314   if (GET_CODE (r) == SUBREG)
3315     r = SUBREG_REG (r);
3316
3317   if (SSE_REG_P (r))
3318     {
3319       if (!standard_sse_constant_p (c))
3320         FAIL;
3321     }
3322   else if (FP_REG_P (r))
3323     {
3324       if (!standard_80387_constant_p (c))
3325         FAIL;
3326     }
3327   else if (MMX_REG_P (r))
3328     FAIL;
3329 })
3330
3331 (define_insn "swapxf"
3332   [(set (match_operand:XF 0 "register_operand" "+f")
3333         (match_operand:XF 1 "register_operand" "+f"))
3334    (set (match_dup 1)
3335         (match_dup 0))]
3336   "TARGET_80387"
3337 {
3338   if (STACK_TOP_P (operands[0]))
3339     return "fxch\t%1";
3340   else
3341     return "fxch\t%0";
3342 }
3343   [(set_attr "type" "fxch")
3344    (set_attr "mode" "XF")])
3345
3346 ;; Split the load of -0.0 or -1.0 into fldz;fchs or fld1;fchs sequence
3347 (define_split
3348   [(set (match_operand:X87MODEF 0 "register_operand" "")
3349         (match_operand:X87MODEF 1 "immediate_operand" ""))]
3350   "reload_completed && FP_REGNO_P (REGNO (operands[0]))
3351    && (standard_80387_constant_p (operands[1]) == 8
3352        || standard_80387_constant_p (operands[1]) == 9)"
3353   [(set (match_dup 0)(match_dup 1))
3354    (set (match_dup 0)
3355         (neg:X87MODEF (match_dup 0)))]
3356 {
3357   REAL_VALUE_TYPE r;
3358
3359   REAL_VALUE_FROM_CONST_DOUBLE (r, operands[1]);
3360   if (real_isnegzero (&r))
3361     operands[1] = CONST0_RTX (<MODE>mode);
3362   else
3363     operands[1] = CONST1_RTX (<MODE>mode);
3364 })
3365
3366 (define_split
3367   [(set (match_operand:TF 0 "nonimmediate_operand" "")
3368         (match_operand:TF 1 "general_operand" ""))]
3369   "reload_completed
3370    && !(SSE_REG_P (operands[0]) || SSE_REG_P (operands[1]))"
3371   [(const_int 0)]
3372   "ix86_split_long_move (operands); DONE;")
3373 \f
3374 ;; Zero extension instructions
3375
3376 (define_expand "zero_extendhisi2"
3377   [(set (match_operand:SI 0 "register_operand" "")
3378      (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
3379   ""
3380 {
3381   if (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3382     {
3383       operands[1] = force_reg (HImode, operands[1]);
3384       emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
3385       DONE;
3386     }
3387 })
3388
3389 (define_insn "zero_extendhisi2_and"
3390   [(set (match_operand:SI 0 "register_operand" "=r")
3391      (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
3392    (clobber (reg:CC FLAGS_REG))]
3393   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3394   "#"
3395   [(set_attr "type" "alu1")
3396    (set_attr "mode" "SI")])
3397
3398 (define_split
3399   [(set (match_operand:SI 0 "register_operand" "")
3400         (zero_extend:SI (match_operand:HI 1 "register_operand" "")))
3401    (clobber (reg:CC FLAGS_REG))]
3402   "reload_completed && TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3403   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
3404               (clobber (reg:CC FLAGS_REG))])]
3405   "")
3406
3407 (define_insn "*zero_extendhisi2_movzwl"
3408   [(set (match_operand:SI 0 "register_operand" "=r")
3409      (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3410   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3411   "movz{wl|x}\t{%1, %0|%0, %1}"
3412   [(set_attr "type" "imovx")
3413    (set_attr "mode" "SI")])
3414
3415 (define_expand "zero_extendqihi2"
3416   [(parallel
3417     [(set (match_operand:HI 0 "register_operand" "")
3418        (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3419      (clobber (reg:CC FLAGS_REG))])]
3420   ""
3421   "")
3422
3423 (define_insn "*zero_extendqihi2_and"
3424   [(set (match_operand:HI 0 "register_operand" "=r,?&q")
3425      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3426    (clobber (reg:CC FLAGS_REG))]
3427   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3428   "#"
3429   [(set_attr "type" "alu1")
3430    (set_attr "mode" "HI")])
3431
3432 (define_insn "*zero_extendqihi2_movzbw_and"
3433   [(set (match_operand:HI 0 "register_operand" "=r,r")
3434      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3435    (clobber (reg:CC FLAGS_REG))]
3436   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3437   "#"
3438   [(set_attr "type" "imovx,alu1")
3439    (set_attr "mode" "HI")])
3440
3441 ; zero extend to SImode here to avoid partial register stalls
3442 (define_insn "*zero_extendqihi2_movzbl"
3443   [(set (match_operand:HI 0 "register_operand" "=r")
3444      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3445   "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3446   "movz{bl|x}\t{%1, %k0|%k0, %1}"
3447   [(set_attr "type" "imovx")
3448    (set_attr "mode" "SI")])
3449
3450 ;; For the movzbw case strip only the clobber
3451 (define_split
3452   [(set (match_operand:HI 0 "register_operand" "")
3453         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3454    (clobber (reg:CC FLAGS_REG))]
3455   "reload_completed
3456    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3457    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3458   [(set (match_operand:HI 0 "register_operand" "")
3459         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))])
3460
3461 ;; When source and destination does not overlap, clear destination
3462 ;; first and then do the movb
3463 (define_split
3464   [(set (match_operand:HI 0 "register_operand" "")
3465         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3466    (clobber (reg:CC FLAGS_REG))]
3467   "reload_completed
3468    && ANY_QI_REG_P (operands[0])
3469    && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3470    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3471   [(set (match_dup 0) (const_int 0))
3472    (set (strict_low_part (match_dup 2)) (match_dup 1))]
3473   "operands[2] = gen_lowpart (QImode, operands[0]);")
3474
3475 ;; Rest is handled by single and.
3476 (define_split
3477   [(set (match_operand:HI 0 "register_operand" "")
3478         (zero_extend:HI (match_operand:QI 1 "register_operand" "")))
3479    (clobber (reg:CC FLAGS_REG))]
3480   "reload_completed
3481    && true_regnum (operands[0]) == true_regnum (operands[1])"
3482   [(parallel [(set (match_dup 0) (and:HI (match_dup 0) (const_int 255)))
3483               (clobber (reg:CC FLAGS_REG))])]
3484   "")
3485
3486 (define_expand "zero_extendqisi2"
3487   [(parallel
3488     [(set (match_operand:SI 0 "register_operand" "")
3489        (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3490      (clobber (reg:CC FLAGS_REG))])]
3491   ""
3492   "")
3493
3494 (define_insn "*zero_extendqisi2_and"
3495   [(set (match_operand:SI 0 "register_operand" "=r,?&q")
3496      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3497    (clobber (reg:CC FLAGS_REG))]
3498   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3499   "#"
3500   [(set_attr "type" "alu1")
3501    (set_attr "mode" "SI")])
3502
3503 (define_insn "*zero_extendqisi2_movzbw_and"
3504   [(set (match_operand:SI 0 "register_operand" "=r,r")
3505      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3506    (clobber (reg:CC FLAGS_REG))]
3507   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3508   "#"
3509   [(set_attr "type" "imovx,alu1")
3510    (set_attr "mode" "SI")])
3511
3512 (define_insn "*zero_extendqisi2_movzbw"
3513   [(set (match_operand:SI 0 "register_operand" "=r")
3514      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3515   "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3516   "movz{bl|x}\t{%1, %0|%0, %1}"
3517   [(set_attr "type" "imovx")
3518    (set_attr "mode" "SI")])
3519
3520 ;; For the movzbl case strip only the clobber
3521 (define_split
3522   [(set (match_operand:SI 0 "register_operand" "")
3523         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3524    (clobber (reg:CC FLAGS_REG))]
3525   "reload_completed
3526    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3527    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3528   [(set (match_dup 0)
3529         (zero_extend:SI (match_dup 1)))])
3530
3531 ;; When source and destination does not overlap, clear destination
3532 ;; first and then do the movb
3533 (define_split
3534   [(set (match_operand:SI 0 "register_operand" "")
3535         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3536    (clobber (reg:CC FLAGS_REG))]
3537   "reload_completed
3538    && ANY_QI_REG_P (operands[0])
3539    && (ANY_QI_REG_P (operands[1]) || MEM_P (operands[1]))
3540    && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3541    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3542   [(set (match_dup 0) (const_int 0))
3543    (set (strict_low_part (match_dup 2)) (match_dup 1))]
3544   "operands[2] = gen_lowpart (QImode, operands[0]);")
3545
3546 ;; Rest is handled by single and.
3547 (define_split
3548   [(set (match_operand:SI 0 "register_operand" "")
3549         (zero_extend:SI (match_operand:QI 1 "register_operand" "")))
3550    (clobber (reg:CC FLAGS_REG))]
3551   "reload_completed
3552    && true_regnum (operands[0]) == true_regnum (operands[1])"
3553   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 255)))
3554               (clobber (reg:CC FLAGS_REG))])]
3555   "")
3556
3557 ;; %%% Kill me once multi-word ops are sane.
3558 (define_expand "zero_extendsidi2"
3559   [(set (match_operand:DI 0 "register_operand" "")
3560      (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "")))]
3561   ""
3562 {
3563   if (!TARGET_64BIT)
3564     {
3565       emit_insn (gen_zero_extendsidi2_32 (operands[0], operands[1]));
3566       DONE;
3567     }
3568 })
3569
3570 (define_insn "zero_extendsidi2_32"
3571   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?o,?*Ym,?*y,?*Yi,*Y2")
3572         (zero_extend:DI
3573          (match_operand:SI 1 "nonimmediate_operand" "0,rm,r ,r   ,m  ,r   ,m")))
3574    (clobber (reg:CC FLAGS_REG))]
3575   "!TARGET_64BIT"
3576   "@
3577    #
3578    #
3579    #
3580    movd\t{%1, %0|%0, %1}
3581    movd\t{%1, %0|%0, %1}
3582    movd\t{%1, %0|%0, %1}
3583    movd\t{%1, %0|%0, %1}"
3584   [(set_attr "mode" "SI,SI,SI,DI,DI,TI,TI")
3585    (set_attr "type" "multi,multi,multi,mmxmov,mmxmov,ssemov,ssemov")])
3586
3587 (define_insn "zero_extendsidi2_rex64"
3588   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,?*Ym,?*y,?*Yi,*Y2")
3589      (zero_extend:DI
3590        (match_operand:SI 1 "nonimmediate_operand"  "rm,0,r   ,m  ,r   ,m")))]
3591   "TARGET_64BIT"
3592   "@
3593    mov\t{%k1, %k0|%k0, %k1}
3594    #
3595    movd\t{%1, %0|%0, %1}
3596    movd\t{%1, %0|%0, %1}
3597    movd\t{%1, %0|%0, %1}
3598    movd\t{%1, %0|%0, %1}"
3599   [(set_attr "type" "imovx,imov,mmxmov,mmxmov,ssemov,ssemov")
3600    (set_attr "mode" "SI,DI,DI,DI,TI,TI")])
3601
3602 (define_split
3603   [(set (match_operand:DI 0 "memory_operand" "")
3604      (zero_extend:DI (match_dup 0)))]
3605   "TARGET_64BIT"
3606   [(set (match_dup 4) (const_int 0))]
3607   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3608
3609 (define_split
3610   [(set (match_operand:DI 0 "register_operand" "")
3611         (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3612    (clobber (reg:CC FLAGS_REG))]
3613   "!TARGET_64BIT && reload_completed
3614    && true_regnum (operands[0]) == true_regnum (operands[1])"
3615   [(set (match_dup 4) (const_int 0))]
3616   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3617
3618 (define_split
3619   [(set (match_operand:DI 0 "nonimmediate_operand" "")
3620         (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3621    (clobber (reg:CC FLAGS_REG))]
3622   "!TARGET_64BIT && reload_completed
3623    && !SSE_REG_P (operands[0]) && !MMX_REG_P (operands[0])"
3624   [(set (match_dup 3) (match_dup 1))
3625    (set (match_dup 4) (const_int 0))]
3626   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3627
3628 (define_insn "zero_extendhidi2"
3629   [(set (match_operand:DI 0 "register_operand" "=r")
3630      (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3631   "TARGET_64BIT"
3632   "movz{wl|x}\t{%1, %k0|%k0, %1}"
3633   [(set_attr "type" "imovx")
3634    (set_attr "mode" "DI")])
3635
3636 (define_insn "zero_extendqidi2"
3637   [(set (match_operand:DI 0 "register_operand" "=r")
3638      (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "rm")))]
3639   "TARGET_64BIT"
3640   "movz{bl|x}\t{%1, %k0|%k0, %1}"
3641   [(set_attr "type" "imovx")
3642    (set_attr "mode" "DI")])
3643 \f
3644 ;; Sign extension instructions
3645
3646 (define_expand "extendsidi2"
3647   [(parallel [(set (match_operand:DI 0 "register_operand" "")
3648                    (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3649               (clobber (reg:CC FLAGS_REG))
3650               (clobber (match_scratch:SI 2 ""))])]
3651   ""
3652 {
3653   if (TARGET_64BIT)
3654     {
3655       emit_insn (gen_extendsidi2_rex64 (operands[0], operands[1]));
3656       DONE;
3657     }
3658 })
3659
3660 (define_insn "*extendsidi2_1"
3661   [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3662         (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3663    (clobber (reg:CC FLAGS_REG))
3664    (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3665   "!TARGET_64BIT"
3666   "#")
3667
3668 (define_insn "extendsidi2_rex64"
3669   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3670         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3671   "TARGET_64BIT"
3672   "@
3673    {cltq|cdqe}
3674    movs{lq|x}\t{%1,%0|%0, %1}"
3675   [(set_attr "type" "imovx")
3676    (set_attr "mode" "DI")
3677    (set_attr "prefix_0f" "0")
3678    (set_attr "modrm" "0,1")])
3679
3680 (define_insn "extendhidi2"
3681   [(set (match_operand:DI 0 "register_operand" "=r")
3682         (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3683   "TARGET_64BIT"
3684   "movs{wq|x}\t{%1,%0|%0, %1}"
3685   [(set_attr "type" "imovx")
3686    (set_attr "mode" "DI")])
3687
3688 (define_insn "extendqidi2"
3689   [(set (match_operand:DI 0 "register_operand" "=r")
3690         (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3691   "TARGET_64BIT"
3692   "movs{bq|x}\t{%1,%0|%0, %1}"
3693    [(set_attr "type" "imovx")
3694     (set_attr "mode" "DI")])
3695
3696 ;; Extend to memory case when source register does die.
3697 (define_split
3698   [(set (match_operand:DI 0 "memory_operand" "")
3699         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3700    (clobber (reg:CC FLAGS_REG))
3701    (clobber (match_operand:SI 2 "register_operand" ""))]
3702   "(reload_completed
3703     && dead_or_set_p (insn, operands[1])
3704     && !reg_mentioned_p (operands[1], operands[0]))"
3705   [(set (match_dup 3) (match_dup 1))
3706    (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3707               (clobber (reg:CC FLAGS_REG))])
3708    (set (match_dup 4) (match_dup 1))]
3709   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3710
3711 ;; Extend to memory case when source register does not die.
3712 (define_split
3713   [(set (match_operand:DI 0 "memory_operand" "")
3714         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3715    (clobber (reg:CC FLAGS_REG))
3716    (clobber (match_operand:SI 2 "register_operand" ""))]
3717   "reload_completed"
3718   [(const_int 0)]
3719 {
3720   split_di (&operands[0], 1, &operands[3], &operands[4]);
3721
3722   emit_move_insn (operands[3], operands[1]);
3723
3724   /* Generate a cltd if possible and doing so it profitable.  */
3725   if ((optimize_size || TARGET_USE_CLTD)
3726       && true_regnum (operands[1]) == AX_REG
3727       && true_regnum (operands[2]) == DX_REG)
3728     {
3729       emit_insn (gen_ashrsi3_31 (operands[2], operands[1], GEN_INT (31)));
3730     }
3731   else
3732     {
3733       emit_move_insn (operands[2], operands[1]);
3734       emit_insn (gen_ashrsi3_31 (operands[2], operands[2], GEN_INT (31)));
3735     }
3736   emit_move_insn (operands[4], operands[2]);
3737   DONE;
3738 })
3739
3740 ;; Extend to register case.  Optimize case where source and destination
3741 ;; registers match and cases where we can use cltd.
3742 (define_split
3743   [(set (match_operand:DI 0 "register_operand" "")
3744         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3745    (clobber (reg:CC FLAGS_REG))
3746    (clobber (match_scratch:SI 2 ""))]
3747   "reload_completed"
3748   [(const_int 0)]
3749 {
3750   split_di (&operands[0], 1, &operands[3], &operands[4]);
3751
3752   if (true_regnum (operands[3]) != true_regnum (operands[1]))
3753     emit_move_insn (operands[3], operands[1]);
3754
3755   /* Generate a cltd if possible and doing so it profitable.  */
3756   if ((optimize_size || TARGET_USE_CLTD)
3757       && true_regnum (operands[3]) == AX_REG)
3758     {
3759       emit_insn (gen_ashrsi3_31 (operands[4], operands[3], GEN_INT (31)));
3760       DONE;
3761     }
3762
3763   if (true_regnum (operands[4]) != true_regnum (operands[1]))
3764     emit_move_insn (operands[4], operands[1]);
3765
3766   emit_insn (gen_ashrsi3_31 (operands[4], operands[4], GEN_INT (31)));
3767   DONE;
3768 })
3769
3770 (define_insn "extendhisi2"
3771   [(set (match_operand:SI 0 "register_operand" "=*a,r")
3772         (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3773   ""
3774 {
3775   switch (get_attr_prefix_0f (insn))
3776     {
3777     case 0:
3778       return "{cwtl|cwde}";
3779     default:
3780       return "movs{wl|x}\t{%1,%0|%0, %1}";
3781     }
3782 }
3783   [(set_attr "type" "imovx")
3784    (set_attr "mode" "SI")
3785    (set (attr "prefix_0f")
3786      ;; movsx is short decodable while cwtl is vector decoded.
3787      (if_then_else (and (eq_attr "cpu" "!k6")
3788                         (eq_attr "alternative" "0"))
3789         (const_string "0")
3790         (const_string "1")))
3791    (set (attr "modrm")
3792      (if_then_else (eq_attr "prefix_0f" "0")
3793         (const_string "0")
3794         (const_string "1")))])
3795
3796 (define_insn "*extendhisi2_zext"
3797   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3798         (zero_extend:DI
3799           (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3800   "TARGET_64BIT"
3801 {
3802   switch (get_attr_prefix_0f (insn))
3803     {
3804     case 0:
3805       return "{cwtl|cwde}";
3806     default:
3807       return "movs{wl|x}\t{%1,%k0|%k0, %1}";
3808     }
3809 }
3810   [(set_attr "type" "imovx")
3811    (set_attr "mode" "SI")
3812    (set (attr "prefix_0f")
3813      ;; movsx is short decodable while cwtl is vector decoded.
3814      (if_then_else (and (eq_attr "cpu" "!k6")
3815                         (eq_attr "alternative" "0"))
3816         (const_string "0")
3817         (const_string "1")))
3818    (set (attr "modrm")
3819      (if_then_else (eq_attr "prefix_0f" "0")
3820         (const_string "0")
3821         (const_string "1")))])
3822
3823 (define_insn "extendqihi2"
3824   [(set (match_operand:HI 0 "register_operand" "=*a,r")
3825         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3826   ""
3827 {
3828   switch (get_attr_prefix_0f (insn))
3829     {
3830     case 0:
3831       return "{cbtw|cbw}";
3832     default:
3833       return "movs{bw|x}\t{%1,%0|%0, %1}";
3834     }
3835 }
3836   [(set_attr "type" "imovx")
3837    (set_attr "mode" "HI")
3838    (set (attr "prefix_0f")
3839      ;; movsx is short decodable while cwtl is vector decoded.
3840      (if_then_else (and (eq_attr "cpu" "!k6")
3841                         (eq_attr "alternative" "0"))
3842         (const_string "0")
3843         (const_string "1")))
3844    (set (attr "modrm")
3845      (if_then_else (eq_attr "prefix_0f" "0")
3846         (const_string "0")
3847         (const_string "1")))])
3848
3849 (define_insn "extendqisi2"
3850   [(set (match_operand:SI 0 "register_operand" "=r")
3851         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3852   ""
3853   "movs{bl|x}\t{%1,%0|%0, %1}"
3854    [(set_attr "type" "imovx")
3855     (set_attr "mode" "SI")])
3856
3857 (define_insn "*extendqisi2_zext"
3858   [(set (match_operand:DI 0 "register_operand" "=r")
3859         (zero_extend:DI
3860           (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3861   "TARGET_64BIT"
3862   "movs{bl|x}\t{%1,%k0|%k0, %1}"
3863    [(set_attr "type" "imovx")
3864     (set_attr "mode" "SI")])
3865 \f
3866 ;; Conversions between float and double.
3867
3868 ;; These are all no-ops in the model used for the 80387.  So just
3869 ;; emit moves.
3870
3871 ;; %%% Kill these when call knows how to work out a DFmode push earlier.
3872 (define_insn "*dummy_extendsfdf2"
3873   [(set (match_operand:DF 0 "push_operand" "=<")
3874         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fY2")))]
3875   "0"
3876   "#")
3877
3878 (define_split
3879   [(set (match_operand:DF 0 "push_operand" "")
3880         (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3881   "!TARGET_64BIT"
3882   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
3883    (set (mem:DF (reg:SI SP_REG)) (float_extend:DF (match_dup 1)))])
3884
3885 (define_split
3886   [(set (match_operand:DF 0 "push_operand" "")
3887         (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3888   "TARGET_64BIT"
3889   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
3890    (set (mem:DF (reg:DI SP_REG)) (float_extend:DF (match_dup 1)))])
3891
3892 (define_insn "*dummy_extendsfxf2"
3893   [(set (match_operand:XF 0 "push_operand" "=<")
3894         (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "f")))]
3895   "0"
3896   "#")
3897
3898 (define_split
3899   [(set (match_operand:XF 0 "push_operand" "")
3900         (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3901   ""
3902   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3903    (set (mem:XF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))]
3904   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3905
3906 (define_split
3907   [(set (match_operand:XF 0 "push_operand" "")
3908         (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3909   "TARGET_64BIT"
3910   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3911    (set (mem:DF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))]
3912   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3913
3914 (define_split
3915   [(set (match_operand:XF 0 "push_operand" "")
3916         (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3917   ""
3918   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3919    (set (mem:DF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))]
3920   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3921
3922 (define_split
3923   [(set (match_operand:XF 0 "push_operand" "")
3924         (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3925   "TARGET_64BIT"
3926   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3927    (set (mem:XF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))]
3928   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3929
3930 (define_expand "extendsfdf2"
3931   [(set (match_operand:DF 0 "nonimmediate_operand" "")
3932         (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
3933   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3934 {
3935   /* ??? Needed for compress_float_constant since all fp constants
3936      are LEGITIMATE_CONSTANT_P.  */
3937   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3938     {
3939       if ((!TARGET_SSE2 || TARGET_MIX_SSE_I387)
3940           && standard_80387_constant_p (operands[1]) > 0)
3941         {
3942           operands[1] = simplify_const_unary_operation
3943             (FLOAT_EXTEND, DFmode, operands[1], SFmode);
3944           emit_move_insn_1 (operands[0], operands[1]);
3945           DONE;
3946         }
3947       operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3948     }
3949 })
3950
3951 /* For converting SF(xmm2) to DF(xmm1), use the following code instead of
3952    cvtss2sd:
3953       unpcklps xmm2,xmm2   ; packed conversion might crash on signaling NaNs
3954       cvtps2pd xmm2,xmm1
3955    We do the conversion post reload to avoid producing of 128bit spills
3956    that might lead to ICE on 32bit target.  The sequence unlikely combine
3957    anyway.  */
3958 (define_split
3959   [(set (match_operand:DF 0 "register_operand" "")
3960         (float_extend:DF
3961           (match_operand:SF 1 "nonimmediate_operand" "")))]
3962   "(TARGET_USE_VECTOR_CONVERTS || TARGET_GENERIC) && !optimize_size
3963    && reload_completed && SSE_REG_P (operands[0])"
3964    [(set (match_dup 2)
3965          (float_extend:V2DF
3966            (vec_select:V2SF
3967              (match_dup 3)
3968              (parallel [(const_int 0) (const_int 1)]))))]
3969 {
3970   operands[2] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
3971   operands[3] = simplify_gen_subreg (V4SFmode, operands[0], DFmode, 0);
3972   /* Use movss for loading from memory, unpcklps reg, reg for registers.
3973      Try to avoid move when unpacking can be done in source.  */
3974   if (REG_P (operands[1]))
3975     {
3976       /* If it is unsafe to overwrite upper half of source, we need
3977          to move to destination and unpack there.  */
3978       if ((ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
3979            || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 4)
3980           && true_regnum (operands[0]) != true_regnum (operands[1]))
3981         {
3982           rtx tmp = gen_rtx_REG (SFmode, true_regnum (operands[0]));
3983           emit_move_insn (tmp, operands[1]);
3984         }
3985       else
3986         operands[3] = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
3987       emit_insn (gen_sse_unpcklps (operands[3], operands[3], operands[3]));
3988     }
3989   else
3990     emit_insn (gen_vec_setv4sf_0 (operands[3],
3991                                   CONST0_RTX (V4SFmode), operands[1]));
3992 })
3993
3994 (define_insn "*extendsfdf2_mixed"
3995   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m,x")
3996         (float_extend:DF
3997           (match_operand:SF 1 "nonimmediate_operand" "fm,f,xm")))]
3998   "TARGET_SSE2 && TARGET_MIX_SSE_I387"
3999 {
4000   switch (which_alternative)
4001     {
4002     case 0:
4003     case 1:
4004       return output_387_reg_move (insn, operands);
4005
4006     case 2:
4007       return "cvtss2sd\t{%1, %0|%0, %1}";
4008
4009     default:
4010       gcc_unreachable ();
4011     }
4012 }
4013   [(set_attr "type" "fmov,fmov,ssecvt")
4014    (set_attr "mode" "SF,XF,DF")])
4015
4016 (define_insn "*extendsfdf2_sse"
4017   [(set (match_operand:DF 0 "nonimmediate_operand" "=x")
4018         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
4019   "TARGET_SSE2 && TARGET_SSE_MATH"
4020   "cvtss2sd\t{%1, %0|%0, %1}"
4021   [(set_attr "type" "ssecvt")
4022    (set_attr "mode" "DF")])
4023
4024 (define_insn "*extendsfdf2_i387"
4025   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
4026         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
4027   "TARGET_80387"
4028   "* return output_387_reg_move (insn, operands);"
4029   [(set_attr "type" "fmov")
4030    (set_attr "mode" "SF,XF")])
4031
4032 (define_expand "extend<mode>xf2"
4033   [(set (match_operand:XF 0 "nonimmediate_operand" "")
4034         (float_extend:XF (match_operand:MODEF 1 "general_operand" "")))]
4035   "TARGET_80387"
4036 {
4037   /* ??? Needed for compress_float_constant since all fp constants
4038      are LEGITIMATE_CONSTANT_P.  */
4039   if (GET_CODE (operands[1]) == CONST_DOUBLE)
4040     {
4041       if (standard_80387_constant_p (operands[1]) > 0)
4042         {
4043           operands[1] = simplify_const_unary_operation
4044             (FLOAT_EXTEND, XFmode, operands[1], <MODE>mode);
4045           emit_move_insn_1 (operands[0], operands[1]);
4046           DONE;
4047         }
4048       operands[1] = validize_mem (force_const_mem (<MODE>mode, operands[1]));
4049     }
4050 })
4051
4052 (define_insn "*extend<mode>xf2_i387"
4053   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
4054         (float_extend:XF
4055           (match_operand:MODEF 1 "nonimmediate_operand" "fm,f")))]
4056   "TARGET_80387"
4057   "* return output_387_reg_move (insn, operands);"
4058   [(set_attr "type" "fmov")
4059    (set_attr "mode" "<MODE>,XF")])
4060
4061 ;; %%% This seems bad bad news.
4062 ;; This cannot output into an f-reg because there is no way to be sure
4063 ;; of truncating in that case.  Otherwise this is just like a simple move
4064 ;; insn.  So we pretend we can output to a reg in order to get better
4065 ;; register preferencing, but we really use a stack slot.
4066
4067 ;; Conversion from DFmode to SFmode.
4068
4069 (define_expand "truncdfsf2"
4070   [(set (match_operand:SF 0 "nonimmediate_operand" "")
4071         (float_truncate:SF
4072           (match_operand:DF 1 "nonimmediate_operand" "")))]
4073   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4074 {
4075   if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387)
4076     ;
4077   else if (flag_unsafe_math_optimizations)
4078     ;
4079   else
4080     {
4081       int slot = virtuals_instantiated ? SLOT_TEMP : SLOT_VIRTUAL;
4082       rtx temp = assign_386_stack_local (SFmode, slot);
4083       emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp));
4084       DONE;
4085     }
4086 })
4087
4088 /* For converting DF(xmm2) to SF(xmm1), use the following code instead of
4089    cvtsd2ss:
4090       unpcklpd xmm2,xmm2   ; packed conversion might crash on signaling NaNs
4091       cvtpd2ps xmm2,xmm1
4092    We do the conversion post reload to avoid producing of 128bit spills
4093    that might lead to ICE on 32bit target.  The sequence unlikely combine
4094    anyway.  */
4095 (define_split
4096   [(set (match_operand:SF 0 "register_operand" "")
4097         (float_truncate:SF
4098           (match_operand:DF 1 "nonimmediate_operand" "")))]
4099   "(TARGET_USE_VECTOR_CONVERTS || TARGET_GENERIC) && !optimize_size
4100    && reload_completed && SSE_REG_P (operands[0])"
4101    [(set (match_dup 2)
4102          (vec_concat:V4SF
4103            (float_truncate:V2SF
4104              (match_dup 4))
4105            (match_dup 3)))]
4106 {
4107   operands[2] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
4108   operands[3] = CONST0_RTX (V2SFmode);
4109   operands[4] = simplify_gen_subreg (V2DFmode, operands[0], SFmode, 0);
4110   /* Use movsd for loading from memory, unpcklpd for registers.
4111      Try to avoid move when unpacking can be done in source, or SSE3
4112      movddup is available.  */
4113   if (REG_P (operands[1]))
4114     {
4115       if (!TARGET_SSE3
4116           && true_regnum (operands[0]) != true_regnum (operands[1])
4117           && (ORIGINAL_REGNO (operands[1]) < FIRST_PSEUDO_REGISTER
4118               || PSEUDO_REGNO_BYTES (ORIGINAL_REGNO (operands[1])) > 8))
4119         {
4120           rtx tmp = simplify_gen_subreg (DFmode, operands[0], SFmode, 0);
4121           emit_move_insn (tmp, operands[1]);
4122           operands[1] = tmp;
4123         }
4124       else if (!TARGET_SSE3)
4125         operands[4] = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
4126       emit_insn (gen_vec_dupv2df (operands[4], operands[1]));
4127     }
4128   else
4129     emit_insn (gen_sse2_loadlpd (operands[4],
4130                                  CONST0_RTX (V2DFmode), operands[1]));
4131 })
4132
4133 (define_expand "truncdfsf2_with_temp"
4134   [(parallel [(set (match_operand:SF 0 "" "")
4135                    (float_truncate:SF (match_operand:DF 1 "" "")))
4136               (clobber (match_operand:SF 2 "" ""))])]
4137   "")
4138
4139 (define_insn "*truncdfsf_fast_mixed"
4140   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,f,x")
4141         (float_truncate:SF
4142           (match_operand:DF 1 "nonimmediate_operand" "f ,f,xm")))]
4143   "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations"
4144 {
4145   switch (which_alternative)
4146     {
4147     case 0:
4148     case 1:
4149       return output_387_reg_move (insn, operands);
4150     case 2:
4151       return "cvtsd2ss\t{%1, %0|%0, %1}";
4152     default:
4153       gcc_unreachable ();
4154     }
4155 }
4156   [(set_attr "type" "fmov,fmov,ssecvt")
4157    (set_attr "mode" "SF")])
4158
4159 ;; Yes, this one doesn't depend on flag_unsafe_math_optimizations,
4160 ;; because nothing we do here is unsafe.
4161 (define_insn "*truncdfsf_fast_sse"
4162   [(set (match_operand:SF 0 "nonimmediate_operand"   "=x")
4163         (float_truncate:SF
4164           (match_operand:DF 1 "nonimmediate_operand" "xm")))]
4165   "TARGET_SSE2 && TARGET_SSE_MATH"
4166   "cvtsd2ss\t{%1, %0|%0, %1}"
4167   [(set_attr "type" "ssecvt")
4168    (set_attr "mode" "SF")])
4169
4170 (define_insn "*truncdfsf_fast_i387"
4171   [(set (match_operand:SF 0 "nonimmediate_operand"   "=fm")
4172         (float_truncate:SF
4173           (match_operand:DF 1 "nonimmediate_operand" "f")))]
4174   "TARGET_80387 && flag_unsafe_math_optimizations"
4175   "* return output_387_reg_move (insn, operands);"
4176   [(set_attr "type" "fmov")
4177    (set_attr "mode" "SF")])
4178
4179 (define_insn "*truncdfsf_mixed"
4180   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,?fx*r,Y2")
4181         (float_truncate:SF
4182           (match_operand:DF 1 "nonimmediate_operand" "f ,f    ,Y2m")))
4183    (clobber (match_operand:SF 2 "memory_operand"     "=X,m    ,X"))]
4184   "TARGET_MIX_SSE_I387"
4185 {
4186   switch (which_alternative)
4187     {
4188     case 0:
4189       return output_387_reg_move (insn, operands);
4190
4191     case 1:
4192       return "#";
4193     case 2:
4194       return "cvtsd2ss\t{%1, %0|%0, %1}";
4195     default:
4196       gcc_unreachable ();
4197     }
4198 }
4199   [(set_attr "type" "fmov,multi,ssecvt")
4200    (set_attr "unit" "*,i387,*")
4201    (set_attr "mode" "SF")])
4202
4203 (define_insn "*truncdfsf_i387"
4204   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r")
4205         (float_truncate:SF
4206           (match_operand:DF 1 "nonimmediate_operand" "f,f")))
4207    (clobber (match_operand:SF 2 "memory_operand" "=X,m"))]
4208   "TARGET_80387"
4209 {
4210   switch (which_alternative)
4211     {
4212     case 0:
4213       return output_387_reg_move (insn, operands);
4214
4215     case 1:
4216       return "#";
4217     default:
4218       gcc_unreachable ();
4219     }
4220 }
4221   [(set_attr "type" "fmov,multi")
4222    (set_attr "unit" "*,i387")
4223    (set_attr "mode" "SF")])
4224
4225 (define_insn "*truncdfsf2_i387_1"
4226   [(set (match_operand:SF 0 "memory_operand" "=m")
4227         (float_truncate:SF
4228           (match_operand:DF 1 "register_operand" "f")))]
4229   "TARGET_80387
4230    && !(TARGET_SSE2 && TARGET_SSE_MATH)
4231    && !TARGET_MIX_SSE_I387"
4232   "* return output_387_reg_move (insn, operands);"
4233   [(set_attr "type" "fmov")
4234    (set_attr "mode" "SF")])
4235
4236 (define_split
4237   [(set (match_operand:SF 0 "register_operand" "")
4238         (float_truncate:SF
4239          (match_operand:DF 1 "fp_register_operand" "")))
4240    (clobber (match_operand 2 "" ""))]
4241   "reload_completed"
4242   [(set (match_dup 2) (match_dup 1))
4243    (set (match_dup 0) (match_dup 2))]
4244 {
4245   operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1]));
4246 })
4247
4248 ;; Conversion from XFmode to {SF,DF}mode
4249
4250 (define_expand "truncxf<mode>2"
4251   [(parallel [(set (match_operand:MODEF 0 "nonimmediate_operand" "")
4252                    (float_truncate:MODEF
4253                      (match_operand:XF 1 "register_operand" "")))
4254               (clobber (match_dup 2))])]
4255   "TARGET_80387"
4256 {
4257   if (flag_unsafe_math_optimizations)
4258     {
4259       rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (<MODE>mode);
4260       emit_insn (gen_truncxf<mode>2_i387_noop (reg, operands[1]));
4261       if (reg != operands[0])
4262         emit_move_insn (operands[0], reg);
4263       DONE;
4264     }
4265   else
4266     {
4267       int slot = virtuals_instantiated ? SLOT_TEMP : SLOT_VIRTUAL;
4268       operands[2] = assign_386_stack_local (<MODE>mode, slot);
4269     }
4270 })
4271
4272 (define_insn "*truncxfsf2_mixed"
4273   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r")
4274         (float_truncate:SF
4275           (match_operand:XF 1 "register_operand" "f,f")))
4276    (clobber (match_operand:SF 2 "memory_operand" "=X,m"))]
4277   "TARGET_80387"
4278 {
4279   gcc_assert (!which_alternative);
4280   return output_387_reg_move (insn, operands);
4281 }
4282   [(set_attr "type" "fmov,multi")
4283    (set_attr "unit" "*,i387")
4284    (set_attr "mode" "SF")])
4285
4286 (define_insn "*truncxfdf2_mixed"
4287   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?fY2*r")
4288         (float_truncate:DF
4289           (match_operand:XF 1 "register_operand" "f,f")))
4290    (clobber (match_operand:DF 2 "memory_operand" "=X,m"))]
4291   "TARGET_80387"
4292 {
4293   gcc_assert (!which_alternative);
4294   return output_387_reg_move (insn, operands);
4295 }
4296   [(set_attr "type" "fmov,multi")
4297    (set_attr "unit" "*,i387")
4298    (set_attr "mode" "DF")])
4299
4300 (define_insn "truncxf<mode>2_i387_noop"
4301   [(set (match_operand:MODEF 0 "register_operand" "=f")
4302         (float_truncate:MODEF
4303           (match_operand:XF 1 "register_operand" "f")))]
4304   "TARGET_80387 && flag_unsafe_math_optimizations"
4305   "* return output_387_reg_move (insn, operands);"
4306   [(set_attr "type" "fmov")
4307    (set_attr "mode" "<MODE>")])
4308
4309 (define_insn "*truncxf<mode>2_i387"
4310   [(set (match_operand:MODEF 0 "memory_operand" "=m")
4311         (float_truncate:MODEF
4312           (match_operand:XF 1 "register_operand" "f")))]
4313   "TARGET_80387"
4314   "* return output_387_reg_move (insn, operands);"
4315   [(set_attr "type" "fmov")
4316    (set_attr "mode" "<MODE>")])
4317
4318 (define_split
4319   [(set (match_operand:MODEF 0 "register_operand" "")
4320         (float_truncate:MODEF
4321           (match_operand:XF 1 "register_operand" "")))
4322    (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4323   "TARGET_80387 && reload_completed"
4324   [(set (match_dup 2) (float_truncate:MODEF (match_dup 1)))
4325    (set (match_dup 0) (match_dup 2))]
4326   "")
4327
4328 (define_split
4329   [(set (match_operand:MODEF 0 "memory_operand" "")
4330         (float_truncate:MODEF
4331           (match_operand:XF 1 "register_operand" "")))
4332    (clobber (match_operand:MODEF 2 "memory_operand" ""))]
4333   "TARGET_80387"
4334   [(set (match_dup 0) (float_truncate:MODEF (match_dup 1)))]
4335   "")
4336 \f
4337 ;; Signed conversion to DImode.
4338
4339 (define_expand "fix_truncxfdi2"
4340   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4341                    (fix:DI (match_operand:XF 1 "register_operand" "")))
4342               (clobber (reg:CC FLAGS_REG))])]
4343   "TARGET_80387"
4344 {
4345   if (TARGET_FISTTP)
4346    {
4347      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4348      DONE;
4349    }
4350 })
4351
4352 (define_expand "fix_trunc<mode>di2"
4353   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4354                    (fix:DI (match_operand:MODEF 1 "register_operand" "")))
4355               (clobber (reg:CC FLAGS_REG))])]
4356   "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))"
4357 {
4358   if (TARGET_FISTTP
4359       && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4360    {
4361      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4362      DONE;
4363    }
4364   if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))
4365    {
4366      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4367      emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1]));
4368      if (out != operands[0])
4369         emit_move_insn (operands[0], out);
4370      DONE;
4371    }
4372 })
4373
4374 ;; Signed conversion to SImode.
4375
4376 (define_expand "fix_truncxfsi2"
4377   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4378                    (fix:SI (match_operand:XF 1 "register_operand" "")))
4379               (clobber (reg:CC FLAGS_REG))])]
4380   "TARGET_80387"
4381 {
4382   if (TARGET_FISTTP)
4383    {
4384      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4385      DONE;
4386    }
4387 })
4388
4389 (define_expand "fix_trunc<mode>si2"
4390   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4391                    (fix:SI (match_operand:MODEF 1 "register_operand" "")))
4392               (clobber (reg:CC FLAGS_REG))])]
4393   "TARGET_80387 || SSE_FLOAT_MODE_P (<MODE>mode)"
4394 {
4395   if (TARGET_FISTTP
4396       && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4397    {
4398      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4399      DONE;
4400    }
4401   if (SSE_FLOAT_MODE_P (<MODE>mode))
4402    {
4403      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4404      emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1]));
4405      if (out != operands[0])
4406         emit_move_insn (operands[0], out);
4407      DONE;
4408    }
4409 })
4410
4411 ;; Signed conversion to HImode.
4412
4413 (define_expand "fix_trunc<mode>hi2"
4414   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4415                    (fix:HI (match_operand:X87MODEF 1 "register_operand" "")))
4416               (clobber (reg:CC FLAGS_REG))])]
4417   "TARGET_80387
4418    && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))"
4419 {
4420   if (TARGET_FISTTP)
4421    {
4422      emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1]));
4423      DONE;
4424    }
4425 })
4426
4427 ;; Unsigned conversion to SImode.
4428
4429 (define_expand "fixuns_trunc<mode>si2"
4430   [(parallel
4431     [(set (match_operand:SI 0 "register_operand" "")
4432           (unsigned_fix:SI
4433             (match_operand:MODEF 1 "nonimmediate_operand" "")))
4434      (use (match_dup 2))
4435      (clobber (match_scratch:<ssevecmode> 3 ""))
4436      (clobber (match_scratch:<ssevecmode> 4 ""))])]
4437   "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH && !optimize_size"
4438 {
4439   enum machine_mode mode = <MODE>mode;
4440   enum machine_mode vecmode = <ssevecmode>mode;
4441   REAL_VALUE_TYPE TWO31r;
4442   rtx two31;
4443
4444   real_ldexp (&TWO31r, &dconst1, 31);
4445   two31 = const_double_from_real_value (TWO31r, mode);
4446   two31 = ix86_build_const_vector (mode, true, two31);
4447   operands[2] = force_reg (vecmode, two31);
4448 })
4449
4450 (define_insn_and_split "*fixuns_trunc<mode>_1"
4451   [(set (match_operand:SI 0 "register_operand" "=&x,&x")
4452         (unsigned_fix:SI
4453           (match_operand:MODEF 3 "nonimmediate_operand" "xm,xm")))
4454    (use (match_operand:<ssevecmode> 4  "nonimmediate_operand" "m,x"))
4455    (clobber (match_scratch:<ssevecmode> 1 "=x,&x"))
4456    (clobber (match_scratch:<ssevecmode> 2 "=x,x"))]
4457   "!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH && !optimize_size"
4458   "#"
4459   "&& reload_completed"
4460   [(const_int 0)]
4461 {
4462   ix86_split_convert_uns_si_sse (operands);
4463   DONE;
4464 })
4465
4466 ;; Unsigned conversion to HImode.
4467 ;; Without these patterns, we'll try the unsigned SI conversion which
4468 ;; is complex for SSE, rather than the signed SI conversion, which isn't.
4469
4470 (define_expand "fixuns_trunc<mode>hi2"
4471   [(set (match_dup 2)
4472         (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "")))
4473    (set (match_operand:HI 0 "nonimmediate_operand" "")
4474         (subreg:HI (match_dup 2) 0))]
4475   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
4476   "operands[2] = gen_reg_rtx (SImode);")
4477
4478 ;; When SSE is available, it is always faster to use it!
4479 (define_insn "fix_trunc<mode>di_sse"
4480   [(set (match_operand:DI 0 "register_operand" "=r,r")
4481         (fix:DI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4482   "TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode)
4483    && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4484   "cvtts<ssemodefsuffix>2si{q}\t{%1, %0|%0, %1}"
4485   [(set_attr "type" "sseicvt")
4486    (set_attr "mode" "<MODE>")
4487    (set_attr "athlon_decode" "double,vector")
4488    (set_attr "amdfam10_decode" "double,double")])
4489
4490 (define_insn "fix_trunc<mode>si_sse"
4491   [(set (match_operand:SI 0 "register_operand" "=r,r")
4492         (fix:SI (match_operand:MODEF 1 "nonimmediate_operand" "x,m")))]
4493   "SSE_FLOAT_MODE_P (<MODE>mode)
4494    && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4495   "cvtts<ssemodefsuffix>2si\t{%1, %0|%0, %1}"
4496   [(set_attr "type" "sseicvt")
4497    (set_attr "mode" "<MODE>")
4498    (set_attr "athlon_decode" "double,vector")
4499    (set_attr "amdfam10_decode" "double,double")])
4500
4501 ;; Shorten x87->SSE reload sequences of fix_trunc?f?i_sse patterns.
4502 (define_peephole2
4503   [(set (match_operand:MODEF 0 "register_operand" "")
4504         (match_operand:MODEF 1 "memory_operand" ""))
4505    (set (match_operand:SSEMODEI24 2 "register_operand" "")
4506         (fix:SSEMODEI24 (match_dup 0)))]
4507   "TARGET_SHORTEN_X87_SSE
4508    && peep2_reg_dead_p (2, operands[0])"
4509   [(set (match_dup 2) (fix:SSEMODEI24 (match_dup 1)))]
4510   "")
4511
4512 ;; Avoid vector decoded forms of the instruction.
4513 (define_peephole2
4514   [(match_scratch:DF 2 "Y2")
4515    (set (match_operand:SSEMODEI24 0 "register_operand" "")
4516         (fix:SSEMODEI24 (match_operand:DF 1 "memory_operand" "")))]
4517   "TARGET_AVOID_VECTOR_DECODE && !optimize_size"
4518   [(set (match_dup 2) (match_dup 1))
4519    (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4520   "")
4521
4522 (define_peephole2
4523   [(match_scratch:SF 2 "x")
4524    (set (match_operand:SSEMODEI24 0 "register_operand" "")
4525         (fix:SSEMODEI24 (match_operand:SF 1 "memory_operand" "")))]
4526   "TARGET_AVOID_VECTOR_DECODE && !optimize_size"
4527   [(set (match_dup 2) (match_dup 1))
4528    (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4529   "")
4530
4531 (define_insn_and_split "fix_trunc<mode>_fisttp_i387_1"
4532   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
4533         (fix:X87MODEI (match_operand 1 "register_operand" "")))]
4534   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4535    && TARGET_FISTTP
4536    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4537          && (TARGET_64BIT || <MODE>mode != DImode))
4538         && TARGET_SSE_MATH)
4539    && !(reload_completed || reload_in_progress)"
4540   "#"
4541   "&& 1"
4542   [(const_int 0)]
4543 {
4544   if (memory_operand (operands[0], VOIDmode))
4545     emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1]));
4546   else
4547     {
4548       operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4549       emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0],
4550                                                             operands[1],
4551                                                             operands[2]));
4552     }
4553   DONE;
4554 }
4555   [(set_attr "type" "fisttp")
4556    (set_attr "mode" "<MODE>")])
4557
4558 (define_insn "fix_trunc<mode>_i387_fisttp"
4559   [(set (match_operand:X87MODEI 0 "memory_operand" "=m")
4560         (fix:X87MODEI (match_operand 1 "register_operand" "f")))
4561    (clobber (match_scratch:XF 2 "=&1f"))]
4562   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4563    && TARGET_FISTTP
4564    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4565          && (TARGET_64BIT || <MODE>mode != DImode))
4566         && TARGET_SSE_MATH)"
4567   "* return output_fix_trunc (insn, operands, 1);"
4568   [(set_attr "type" "fisttp")
4569    (set_attr "mode" "<MODE>")])
4570
4571 (define_insn "fix_trunc<mode>_i387_fisttp_with_temp"
4572   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4573         (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
4574    (clobber (match_operand:X87MODEI 2 "memory_operand" "=m,m"))
4575    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
4576   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4577    && TARGET_FISTTP
4578    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4579         && (TARGET_64BIT || <MODE>mode != DImode))
4580         && TARGET_SSE_MATH)"
4581   "#"
4582   [(set_attr "type" "fisttp")
4583    (set_attr "mode" "<MODE>")])
4584
4585 (define_split
4586   [(set (match_operand:X87MODEI 0 "register_operand" "")
4587         (fix:X87MODEI (match_operand 1 "register_operand" "")))
4588    (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4589    (clobber (match_scratch 3 ""))]
4590   "reload_completed"
4591   [(parallel [(set (match_dup 2) (fix:X87MODEI (match_dup 1)))
4592               (clobber (match_dup 3))])
4593    (set (match_dup 0) (match_dup 2))]
4594   "")
4595
4596 (define_split
4597   [(set (match_operand:X87MODEI 0 "memory_operand" "")
4598         (fix:X87MODEI (match_operand 1 "register_operand" "")))
4599    (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4600    (clobber (match_scratch 3 ""))]
4601   "reload_completed"
4602   [(parallel [(set (match_dup 0) (fix:X87MODEI (match_dup 1)))
4603               (clobber (match_dup 3))])]
4604   "")
4605
4606 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4607 ;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control
4608 ;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG
4609 ;; clobbering insns can be used. Look at emit_i387_cw_initialization ()
4610 ;; function in i386.c.
4611 (define_insn_and_split "*fix_trunc<mode>_i387_1"
4612   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
4613         (fix:X87MODEI (match_operand 1 "register_operand" "")))
4614    (clobber (reg:CC FLAGS_REG))]
4615   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4616    && !TARGET_FISTTP
4617    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4618          && (TARGET_64BIT || <MODE>mode != DImode))
4619    && !(reload_completed || reload_in_progress)"
4620   "#"
4621   "&& 1"
4622   [(const_int 0)]
4623 {
4624   ix86_optimize_mode_switching[I387_TRUNC] = 1;
4625
4626   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
4627   operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
4628   if (memory_operand (operands[0], VOIDmode))
4629     emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1],
4630                                          operands[2], operands[3]));
4631   else
4632     {
4633       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4634       emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1],
4635                                                      operands[2], operands[3],
4636                                                      operands[4]));
4637     }
4638   DONE;
4639 }
4640   [(set_attr "type" "fistp")
4641    (set_attr "i387_cw" "trunc")
4642    (set_attr "mode" "<MODE>")])
4643
4644 (define_insn "fix_truncdi_i387"
4645   [(set (match_operand:DI 0 "memory_operand" "=m")
4646         (fix:DI (match_operand 1 "register_operand" "f")))
4647    (use (match_operand:HI 2 "memory_operand" "m"))
4648    (use (match_operand:HI 3 "memory_operand" "m"))
4649    (clobber (match_scratch:XF 4 "=&1f"))]
4650   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4651    && !TARGET_FISTTP
4652    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4653   "* return output_fix_trunc (insn, operands, 0);"
4654   [(set_attr "type" "fistp")
4655    (set_attr "i387_cw" "trunc")
4656    (set_attr "mode" "DI")])
4657
4658 (define_insn "fix_truncdi_i387_with_temp"
4659   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4660         (fix:DI (match_operand 1 "register_operand" "f,f")))
4661    (use (match_operand:HI 2 "memory_operand" "m,m"))
4662    (use (match_operand:HI 3 "memory_operand" "m,m"))
4663    (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
4664    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
4665   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4666    && !TARGET_FISTTP
4667    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4668   "#"
4669   [(set_attr "type" "fistp")
4670    (set_attr "i387_cw" "trunc")
4671    (set_attr "mode" "DI")])
4672
4673 (define_split
4674   [(set (match_operand:DI 0 "register_operand" "")
4675         (fix:DI (match_operand 1 "register_operand" "")))
4676    (use (match_operand:HI 2 "memory_operand" ""))
4677    (use (match_operand:HI 3 "memory_operand" ""))
4678    (clobber (match_operand:DI 4 "memory_operand" ""))
4679    (clobber (match_scratch 5 ""))]
4680   "reload_completed"
4681   [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
4682               (use (match_dup 2))
4683               (use (match_dup 3))
4684               (clobber (match_dup 5))])
4685    (set (match_dup 0) (match_dup 4))]
4686   "")
4687
4688 (define_split
4689   [(set (match_operand:DI 0 "memory_operand" "")
4690         (fix:DI (match_operand 1 "register_operand" "")))
4691    (use (match_operand:HI 2 "memory_operand" ""))
4692    (use (match_operand:HI 3 "memory_operand" ""))
4693    (clobber (match_operand:DI 4 "memory_operand" ""))
4694    (clobber (match_scratch 5 ""))]
4695   "reload_completed"
4696   [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
4697               (use (match_dup 2))
4698               (use (match_dup 3))
4699               (clobber (match_dup 5))])]
4700   "")
4701
4702 (define_insn "fix_trunc<mode>_i387"
4703   [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
4704         (fix:X87MODEI12 (match_operand 1 "register_operand" "f")))
4705    (use (match_operand:HI 2 "memory_operand" "m"))
4706    (use (match_operand:HI 3 "memory_operand" "m"))]
4707   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4708    && !TARGET_FISTTP
4709    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4710   "* return output_fix_trunc (insn, operands, 0);"
4711   [(set_attr "type" "fistp")
4712    (set_attr "i387_cw" "trunc")
4713    (set_attr "mode" "<MODE>")])
4714
4715 (define_insn "fix_trunc<mode>_i387_with_temp"
4716   [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
4717         (fix:X87MODEI12 (match_operand 1 "register_operand" "f,f")))
4718    (use (match_operand:HI 2 "memory_operand" "m,m"))
4719    (use (match_operand:HI 3 "memory_operand" "m,m"))
4720    (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
4721   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
4722    && !TARGET_FISTTP
4723    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4724   "#"
4725   [(set_attr "type" "fistp")
4726    (set_attr "i387_cw" "trunc")
4727    (set_attr "mode" "<MODE>")])
4728
4729 (define_split
4730   [(set (match_operand:X87MODEI12 0 "register_operand" "")
4731         (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4732    (use (match_operand:HI 2 "memory_operand" ""))
4733    (use (match_operand:HI 3 "memory_operand" ""))
4734    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4735   "reload_completed"
4736   [(parallel [(set (match_dup 4) (fix:X87MODEI12 (match_dup 1)))
4737               (use (match_dup 2))
4738               (use (match_dup 3))])
4739    (set (match_dup 0) (match_dup 4))]
4740   "")
4741
4742 (define_split
4743   [(set (match_operand:X87MODEI12 0 "memory_operand" "")
4744         (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4745    (use (match_operand:HI 2 "memory_operand" ""))
4746    (use (match_operand:HI 3 "memory_operand" ""))
4747    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4748   "reload_completed"
4749   [(parallel [(set (match_dup 0) (fix:X87MODEI12 (match_dup 1)))
4750               (use (match_dup 2))
4751               (use (match_dup 3))])]
4752   "")
4753
4754 (define_insn "x86_fnstcw_1"
4755   [(set (match_operand:HI 0 "memory_operand" "=m")
4756         (unspec:HI [(reg:HI FPCR_REG)] UNSPEC_FSTCW))]
4757   "TARGET_80387"
4758   "fnstcw\t%0"
4759   [(set_attr "length" "2")
4760    (set_attr "mode" "HI")
4761    (set_attr "unit" "i387")])
4762
4763 (define_insn "x86_fldcw_1"
4764   [(set (reg:HI FPCR_REG)
4765         (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
4766   "TARGET_80387"
4767   "fldcw\t%0"
4768   [(set_attr "length" "2")
4769    (set_attr "mode" "HI")
4770    (set_attr "unit" "i387")
4771    (set_attr "athlon_decode" "vector")
4772    (set_attr "amdfam10_decode" "vector")])
4773 \f
4774 ;; Conversion between fixed point and floating point.
4775
4776 ;; Even though we only accept memory inputs, the backend _really_
4777 ;; wants to be able to do this between registers.
4778
4779 (define_expand "floathi<mode>2"
4780   [(set (match_operand:MODEF 0 "register_operand" "")
4781         (float:MODEF (match_operand:HI 1 "nonimmediate_operand" "")))]
4782   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
4783 {
4784   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4785     {
4786       emit_insn
4787         (gen_floatsi<mode>2 (operands[0],
4788                              convert_to_mode (SImode, operands[1], 0)));
4789       DONE;
4790     }
4791 })
4792
4793 (define_insn "*floathi<mode>2_i387"
4794   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
4795         (float:MODEF
4796           (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4797   "TARGET_80387
4798    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
4799        || TARGET_MIX_SSE_I387)"
4800   "@
4801    fild%z1\t%1
4802    #"
4803   [(set_attr "type" "fmov,multi")
4804    (set_attr "mode" "<MODE>")
4805    (set_attr "unit" "*,i387")
4806    (set_attr "fp_int_src" "true")])
4807
4808 (define_expand "floatsi<mode>2"
4809   [(set (match_operand:MODEF 0 "register_operand" "")
4810         (float:MODEF (match_operand:SI 1 "nonimmediate_operand" "")))]
4811   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
4812   "
4813    /* When we use vector converts, we can't have input in memory.  */
4814    if (GET_MODE (operands[0]) == DFmode
4815        && TARGET_USE_VECTOR_CONVERTS && !optimize_size && TARGET_SSE_MATH
4816        && SSE_FLOAT_MODE_P (DFmode))
4817      operands[1] = force_reg (SImode, operands[1]);
4818    else if (GET_MODE (operands[0]) == SFmode
4819             && !optimize_size && TARGET_USE_VECTOR_CONVERTS && TARGET_SSE_MATH
4820             && SSE_FLOAT_MODE_P (SFmode))
4821      {
4822        /* When !flag_trapping_math, we handle SImode->SFmode vector
4823           conversions same way as SImode->DFmode.
4824
4825           For flat_trapping_math we can't safely use vector conversion without
4826           clearing upper half, otherwise precision exception might occur.
4827           However we can still generate the common sequence converting value
4828           from general register to XMM register as:
4829
4830             mov         reg32, mem32
4831             movd        mem32, xmm
4832             cvtdq2pd xmm,xmm
4833
4834           because we know that movd clears the upper half.
4835
4836           Sadly in this case we can't rely on reload moving the value to XMM
4837           register, since we need to know if upper half is OK, so we need
4838           to do reloading by hand.  We force operand to memory unless target
4839           supports inter unit moves.  */
4840        if (!flag_trapping_math)
4841          operands[1] = force_reg (SImode, operands[1]);
4842        else if (!MEM_P (operands[1]))
4843          {
4844            int slot = virtuals_instantiated ? SLOT_TEMP : SLOT_VIRTUAL;
4845            rtx tmp = assign_386_stack_local (SImode, slot);
4846            emit_move_insn (tmp, operands[1]);
4847            operands[1] = tmp;
4848          }
4849      }
4850    /* Offload operand of cvtsi2ss and cvtsi2sd into memory for
4851       !TARGET_INTER_UNIT_CONVERSIONS
4852       It is necessary for the patterns to not accept nonmemory operands
4853       as we would optimize out later.  */
4854    else if (!TARGET_INTER_UNIT_CONVERSIONS
4855             && TARGET_SSE_MATH && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
4856             && !optimize_size
4857             && !MEM_P (operands[1]))
4858      {
4859        int slot = virtuals_instantiated ? SLOT_TEMP : SLOT_VIRTUAL;
4860        rtx tmp = assign_386_stack_local (GET_MODE (operands[1]), slot);
4861        emit_move_insn (tmp, operands[1]);
4862        operands[1] = tmp;
4863      }
4864   ")
4865
4866 (define_insn "*floatsisf2_mixed_vector"
4867   [(set (match_operand:SF 0 "register_operand" "=x,f,?f")
4868         (float:SF (match_operand:SI 1 "nonimmediate_operand" "x,m,r")))]
4869   "TARGET_MIX_SSE_I387 && !flag_trapping_math
4870    && TARGET_USE_VECTOR_CONVERTS && !optimize_size"
4871   "@
4872    cvtdq2ps\t{%1, %0|%0, %1}
4873    fild%z1\t%1
4874    #"
4875   [(set_attr "type" "sseicvt,fmov,multi")
4876    (set_attr "mode" "SF")
4877    (set_attr "unit" "*,i387,*")
4878    (set_attr "athlon_decode" "double,*,*")
4879    (set_attr "amdfam10_decode" "double,*,*")
4880    (set_attr "fp_int_src" "false,true,true")])
4881
4882 (define_insn "*floatsisf2_mixed"
4883   [(set (match_operand:SF 0 "register_operand" "=f,?f,x,x")
4884         (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,m")))]
4885   "TARGET_MIX_SSE_I387
4886    && ((!TARGET_USE_VECTOR_CONVERTS && TARGET_INTER_UNIT_CONVERSIONS)
4887        || optimize_size)"
4888   "@
4889    fild%z1\t%1
4890    #
4891    cvtsi2ss\t{%1, %0|%0, %1}
4892    cvtsi2ss\t{%1, %0|%0, %1}"
4893   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4894    (set_attr "mode" "SF")
4895    (set_attr "unit" "*,i387,*,*")
4896    (set_attr "athlon_decode" "*,*,vector,double")
4897    (set_attr "amdfam10_decode" "*,*,vector,double")
4898    (set_attr "fp_int_src" "true")])
4899
4900 (define_insn "*floatsisf2_mixed_memory"
4901   [(set (match_operand:SF 0 "register_operand" "=f,x")
4902         (float:SF (match_operand:SI 1 "memory_operand" "m,m")))]
4903   "TARGET_MIX_SSE_I387
4904    && !TARGET_INTER_UNIT_CONVERSIONS && !optimize_size"
4905   "@
4906    fild%z1\t%1
4907    cvtsi2ss\t{%1, %0|%0, %1}"
4908   [(set_attr "type" "fmov,sseicvt")
4909    (set_attr "mode" "SF")
4910    (set_attr "athlon_decode" "*,double")
4911    (set_attr "amdfam10_decode" "*,double")
4912    (set_attr "fp_int_src" "true")])
4913
4914 (define_insn "*floatsisf2_sse_vector_nointernunit"
4915   [(set (match_operand:SF 0 "register_operand" "=x")
4916         (float:SF (match_operand:SI 1 "memory_operand" "m")))]
4917   "TARGET_SSE_MATH && flag_trapping_math
4918    && TARGET_USE_VECTOR_CONVERTS && !optimize_size
4919    && !TARGET_INTER_UNIT_MOVES"
4920   "#"
4921   [(set_attr "type" "multi")])
4922
4923 (define_insn "*floatsisf2_sse_vector_internunit"
4924   [(set (match_operand:SF 0 "register_operand" "=x,x")
4925         (float:SF (match_operand:SI 1 "nonimmediate_operand" "rm,x")))]
4926   "TARGET_SSE_MATH && flag_trapping_math
4927    && TARGET_USE_VECTOR_CONVERTS && !optimize_size
4928    && TARGET_INTER_UNIT_MOVES"
4929   "#"
4930   [(set_attr "type" "multi")])
4931
4932 (define_split
4933   [(set (match_operand:SF 0 "register_operand" "")
4934         (float:SF (match_operand:SI 1 "nonimmediate_operand" "")))]
4935   "flag_trapping_math
4936    && TARGET_USE_VECTOR_CONVERTS && reload_completed
4937    && (TARGET_INTER_UNIT_MOVES || MEM_P (operands[1]))
4938    && !SSE_REG_P (operands[1]) && SSE_REG_P (operands[0])"
4939   [(set (match_dup 0)
4940         (float:V4SF (match_dup 2)))]
4941 {
4942   operands[2] = simplify_gen_subreg (V4SImode, operands[0], SFmode, 0);
4943   operands[0] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
4944   emit_insn (gen_sse2_loadld (operands[2], CONST0_RTX (V4SImode), operands[1]));
4945 })
4946
4947 (define_split
4948   [(set (match_operand:SF 0 "register_operand" "")
4949         (float:SF (match_operand:SI 1 "register_operand" "")))]
4950   "flag_trapping_math
4951    && TARGET_USE_VECTOR_CONVERTS && reload_completed
4952    && SSE_REG_P (operands[1]) && SSE_REG_P (operands[0])"
4953   [(set (match_dup 2) (vec_duplicate:V4SI (match_dup 1)))
4954    (set (match_dup 0)
4955         (float:V4SF (match_dup 2)))]
4956 {
4957   operands[2] = simplify_gen_subreg (V4SImode, operands[0], SFmode, 0);
4958   operands[0] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
4959 })
4960
4961 (define_insn "*floatsisf2_sse_vector"
4962   [(set (match_operand:SF 0 "register_operand" "=x")
4963         (float:SF (match_operand:SI 1 "register_operand" "x")))]
4964   "TARGET_SSE_MATH && !flag_trapping_math
4965    && TARGET_USE_VECTOR_CONVERTS && !optimize_size
4966    && !TARGET_INTER_UNIT_MOVES"
4967   "cvtdq2ps\t{%1, %0|%0, %1}"
4968   [(set_attr "type" "sseicvt")
4969    (set_attr "mode" "SF")
4970    (set_attr "athlon_decode" "double")
4971    (set_attr "amdfam10_decode" "double")
4972    (set_attr "fp_int_src" "true")])
4973
4974 (define_insn "*floatsisf2_sse"
4975   [(set (match_operand:SF 0 "register_operand" "=x,x")
4976         (float:SF (match_operand:SI 1 "nonimmediate_operand" "r,m")))]
4977   "TARGET_SSE_MATH
4978    && ((!TARGET_USE_VECTOR_CONVERTS && TARGET_INTER_UNIT_CONVERSIONS)
4979        || optimize_size)"
4980   "cvtsi2ss\t{%1, %0|%0, %1}"
4981   [(set_attr "type" "sseicvt")
4982    (set_attr "mode" "SF")
4983    (set_attr "athlon_decode" "vector,double")
4984    (set_attr "amdfam10_decode" "vector,double")
4985    (set_attr "fp_int_src" "true")])
4986
4987 (define_insn "*floatsisf2_sse_memory"
4988   [(set (match_operand:SF 0 "register_operand" "=x")
4989         (float:SF (match_operand:SI 1 "memory_operand" "m")))]
4990   "TARGET_SSE_MATH
4991    && !TARGET_INTER_UNIT_CONVERSIONS && !optimize_size"
4992   "cvtsi2ss\t{%1, %0|%0, %1}"
4993   [(set_attr "type" "sseicvt")
4994    (set_attr "mode" "SF")
4995    (set_attr "athlon_decode" "double")
4996    (set_attr "amdfam10_decode" "double")
4997    (set_attr "fp_int_src" "true")])
4998
4999 (define_insn "*floatsidf2_mixed_vector"
5000   [(set (match_operand:DF 0 "register_operand" "=x,f,f")
5001         (float:DF (match_operand:SI 1 "nonimmediate_operand" "x,m,r")))]
5002   "TARGET_SSE2 && TARGET_MIX_SSE_I387
5003    && TARGET_USE_VECTOR_CONVERTS && !optimize_size"
5004   "@
5005    cvtdq2pd\t{%1, %0|%0, %1}
5006    fild%z1\t%1
5007    #"
5008   [(set_attr "type" "sseicvt,fmov,multi")
5009    (set_attr "mode" "V2DF,DF,DF")
5010    (set_attr "unit" "*,*,i387")
5011    (set_attr "athlon_decode" "double,*,*")
5012    (set_attr "amdfam10_decode" "double,*,*")
5013    (set_attr "fp_int_src" "false,true,true")])
5014
5015 (define_insn "*floatsidf2_mixed"
5016   [(set (match_operand:DF 0 "register_operand" "=f,?f,x,x,!x")
5017         (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,m,x")))]
5018   "TARGET_SSE2 && TARGET_MIX_SSE_I387
5019    && ((!TARGET_USE_VECTOR_CONVERTS && TARGET_INTER_UNIT_CONVERSIONS)
5020        || optimize_size)"
5021   "@
5022    fild%z1\t%1
5023    #
5024    cvtsi2sd\t{%1, %0|%0, %1}
5025    cvtsi2sd\t{%1, %0|%0, %1}
5026    cvtdq2pd\t{%1, %0|%0, %1}"
5027   [(set_attr "type" "fmov,multi,sseicvt,sseicvt,sseicvt")
5028    (set_attr "mode" "DF,DF,DF,DF,V2DF")
5029    (set_attr "unit" "*,i387,*,*,*")
5030    (set_attr "athlon_decode" "*,*,double,direct,double")
5031    (set_attr "amdfam10_decode" "*,*,vector,double,double")
5032    (set_attr "fp_int_src" "true,true,true,true,false")])
5033
5034 (define_insn "*floatsidf2_mixed_memory"
5035   [(set (match_operand:DF 0 "register_operand" "=f,x")
5036         (float:DF (match_operand:SI 1 "memory_operand" "m,m")))]
5037   "TARGET_SSE2 && TARGET_MIX_SSE_I387
5038    && !TARGET_INTER_UNIT_CONVERSIONS && !optimize_size"
5039   "@
5040    fild%z1\t%1
5041    cvtsi2sd\t{%1, %0|%0, %1}"
5042   [(set_attr "type" "fmov,sseicvt")
5043    (set_attr "mode" "DF")
5044    (set_attr "athlon_decode" "*,direct")
5045    (set_attr "amdfam10_decode" "*,double")
5046    (set_attr "fp_int_src" "true")])
5047
5048 (define_insn "*floatsidf2_sse_vector"
5049   [(set (match_operand:DF 0 "register_operand" "=x")
5050         (float:DF (match_operand:SI 1 "register_operand" "x")))]
5051   "TARGET_SSE2 && TARGET_SSE_MATH
5052    && TARGET_USE_VECTOR_CONVERTS && !optimize_size"
5053   "cvtdq2pd\t{%1, %0|%0, %1}"
5054   [(set_attr "type" "sseicvt")
5055    (set_attr "mode" "V2DF")
5056    (set_attr "athlon_decode" "double")
5057    (set_attr "amdfam10_decode" "double")
5058    (set_attr "fp_int_src" "true")])
5059
5060 (define_split
5061   [(set (match_operand:DF 0 "register_operand" "")
5062         (float:DF (match_operand:SI 1 "memory_operand" "")))]
5063   "TARGET_USE_VECTOR_CONVERTS && reload_completed
5064    && SSE_REG_P (operands[0])"
5065   [(set (match_dup 0)
5066         (float:V2DF
5067           (vec_select:V2SI
5068             (match_dup 2)
5069             (parallel [(const_int 0) (const_int 1)]))))]
5070 {
5071   operands[2] = simplify_gen_subreg (V4SImode, operands[0], DFmode, 0);
5072   operands[0] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
5073   emit_insn (gen_sse2_loadld (operands[2], CONST0_RTX (V4SImode), operands[1]));
5074 })
5075
5076 (define_insn "*floatsidf2_sse"
5077   [(set (match_operand:DF 0 "register_operand" "=x,x,!x")
5078         (float:DF (match_operand:SI 1 "nonimmediate_operand" "r,m,x")))]
5079   "TARGET_SSE2 && TARGET_SSE_MATH
5080    && ((!TARGET_USE_VECTOR_CONVERTS && TARGET_INTER_UNIT_CONVERSIONS)
5081        || optimize_size)"
5082   "@
5083    cvtsi2sd\t{%1, %0|%0, %1}
5084    cvtsi2sd\t{%1, %0|%0, %1}
5085    cvtdq2pd\t{%1, %0|%0, %1}"
5086   [(set_attr "type" "sseicvt")
5087    (set_attr "mode" "DF,DF,V2DF")
5088    (set_attr "athlon_decode" "double,direct,double")
5089    (set_attr "amdfam10_decode" "vector,double,double")
5090    (set_attr "fp_int_src" "true")])
5091
5092 (define_insn "*floatsidf2_memory"
5093   [(set (match_operand:DF 0 "register_operand" "=x")
5094         (float:DF (match_operand:SI 1 "memory_operand" "x")))]
5095   "TARGET_SSE2 && TARGET_SSE_MATH
5096    && ((!TARGET_USE_VECTOR_CONVERTS && TARGET_INTER_UNIT_CONVERSIONS)
5097        || optimize_size)"
5098   "cvtsi2sd\t{%1, %0|%0, %1}"
5099   [(set_attr "type" "sseicvt")
5100    (set_attr "mode" "DF")
5101    (set_attr "athlon_decode" "direct")
5102    (set_attr "amdfam10_decode" "double")
5103    (set_attr "fp_int_src" "true")])
5104
5105 (define_insn "*floatsi<mode>2_i387"
5106   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
5107         (float:MODEF
5108           (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
5109   "TARGET_80387
5110    && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0])))"
5111   "@
5112    fild%z1\t%1
5113    #"
5114   [(set_attr "type" "fmov,multi")
5115    (set_attr "mode" "<MODE>")
5116    (set_attr "unit" "*,i387")
5117    (set_attr "fp_int_src" "true")])
5118
5119 (define_expand "floatdisf2"
5120   [(set (match_operand:SF 0 "register_operand" "")
5121         (float:SF (match_operand:DI 1 "nonimmediate_operand" "")))]
5122   "TARGET_80387 || (TARGET_64BIT && TARGET_SSE_MATH)"
5123 {
5124   if (!TARGET_INTER_UNIT_CONVERSIONS && TARGET_64BIT
5125       && TARGET_SSE_MATH && SSE_FLOAT_MODE_P (SFmode)
5126       && !optimize_size
5127       && !MEM_P (operands[1]))
5128     {
5129       int slot = virtuals_instantiated ? SLOT_TEMP : SLOT_VIRTUAL;
5130       rtx tmp = assign_386_stack_local (GET_MODE (operands[1]), slot);
5131       emit_move_insn (tmp, operands[1]);
5132       operands[1] = tmp;
5133     }
5134 })
5135
5136 (define_insn "*floatdisf2_mixed"
5137   [(set (match_operand:SF 0 "register_operand" "=f,?f,x,x")
5138         (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,m")))]
5139   "TARGET_64BIT && TARGET_MIX_SSE_I387
5140    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_size)"
5141   "@
5142    fild%z1\t%1
5143    #
5144    cvtsi2ss{q}\t{%1, %0|%0, %1}
5145    cvtsi2ss{q}\t{%1, %0|%0, %1}"
5146   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
5147    (set_attr "mode" "SF")
5148    (set_attr "unit" "*,i387,*,*")
5149    (set_attr "athlon_decode" "*,*,vector,double")
5150    (set_attr "amdfam10_decode" "*,*,vector,double")
5151    (set_attr "fp_int_src" "true")])
5152
5153 (define_insn "*floatdisf2_mixed"
5154   [(set (match_operand:SF 0 "register_operand" "=f,x")
5155         (float:SF (match_operand:DI 1 "memory_operand" "m,m")))]
5156   "TARGET_64BIT && TARGET_MIX_SSE_I387
5157    && !TARGET_INTER_UNIT_CONVERSIONS && !optimize_size"
5158   "@
5159    fild%z1\t%1
5160    cvtsi2ss{q}\t{%1, %0|%0, %1}"
5161   [(set_attr "type" "fmov,sseicvt")
5162    (set_attr "mode" "SF")
5163    (set_attr "athlon_decode" "*,double")
5164    (set_attr "amdfam10_decode" "*,double")
5165    (set_attr "fp_int_src" "true")])
5166
5167 (define_insn "*floatdisf2_sse"
5168   [(set (match_operand:SF 0 "register_operand" "=x,x")
5169         (float:SF (match_operand:DI 1 "nonimmediate_operand" "r,m")))]
5170   "TARGET_64BIT && TARGET_SSE_MATH
5171    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_size)"
5172   "cvtsi2ss{q}\t{%1, %0|%0, %1}"
5173   [(set_attr "type" "sseicvt")
5174    (set_attr "mode" "SF")
5175    (set_attr "athlon_decode" "vector,double")
5176    (set_attr "amdfam10_decode" "vector,double")
5177    (set_attr "fp_int_src" "true")])
5178
5179 (define_insn "*floatdisf2_memory"
5180   [(set (match_operand:SF 0 "register_operand" "=x")
5181         (float:SF (match_operand:DI 1 "memory_operand" "m")))]
5182   "TARGET_64BIT && TARGET_SSE_MATH
5183    && !TARGET_INTER_UNIT_CONVERSIONS && !optimize_size"
5184   "cvtsi2ss{q}\t{%1, %0|%0, %1}"
5185   [(set_attr "type" "sseicvt")
5186    (set_attr "mode" "SF")
5187    (set_attr "athlon_decode" "double")
5188    (set_attr "amdfam10_decode" "double")
5189    (set_attr "fp_int_src" "true")])
5190
5191 (define_expand "floatdidf2"
5192   [(set (match_operand:DF 0 "register_operand" "")
5193         (float:DF (match_operand:DI 1 "nonimmediate_operand" "")))]
5194   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
5195 {
5196   if (!TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH)
5197     {
5198       ix86_expand_convert_sign_didf_sse (operands[0], operands[1]);
5199       DONE;
5200     }
5201   if (!TARGET_INTER_UNIT_CONVERSIONS && TARGET_64BIT
5202       && TARGET_SSE_MATH && SSE_FLOAT_MODE_P (DFmode)
5203       && !optimize_size
5204       && !MEM_P (operands[1]))
5205     {
5206       int slot = virtuals_instantiated ? SLOT_TEMP : SLOT_VIRTUAL;
5207       rtx tmp = assign_386_stack_local (GET_MODE (operands[1]), slot);
5208       emit_move_insn (tmp, operands[1]);
5209       operands[1] = tmp;
5210     }
5211 })
5212
5213 (define_insn "*floatdidf2_mixed"
5214   [(set (match_operand:DF 0 "register_operand" "=f,?f,x,x")
5215         (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,m")))]
5216   "TARGET_64BIT && TARGET_SSE2 && TARGET_MIX_SSE_I387
5217    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_size)"
5218   "@
5219    fild%z1\t%1
5220    #
5221    cvtsi2sd{q}\t{%1, %0|%0, %1}
5222    cvtsi2sd{q}\t{%1, %0|%0, %1}"
5223   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
5224    (set_attr "mode" "DF")
5225    (set_attr "unit" "*,i387,*,*")
5226    (set_attr "athlon_decode" "*,*,double,direct")
5227    (set_attr "amdfam10_decode" "*,*,vector,double")
5228    (set_attr "fp_int_src" "true")])
5229
5230 (define_insn "*floatdidf2_mixed_memory"
5231   [(set (match_operand:DF 0 "register_operand" "=f,x")
5232         (float:DF (match_operand:DI 1 "memory_operand" "m,m")))]
5233   "TARGET_64BIT && TARGET_SSE2 && TARGET_MIX_SSE_I387
5234    && !TARGET_INTER_UNIT_CONVERSIONS && !optimize_size"
5235   "@
5236    fild%z1\t%1
5237    cvtsi2sd{q}\t{%1, %0|%0, %1}"
5238   [(set_attr "type" "fmov,sseicvt")
5239    (set_attr "mode" "DF")
5240    (set_attr "athlon_decode" "*,direct")
5241    (set_attr "amdfam10_decode" "*,double")
5242    (set_attr "fp_int_src" "true")])
5243
5244 (define_insn "*floatdidf2_sse"
5245   [(set (match_operand:DF 0 "register_operand" "=x,x")
5246         (float:DF (match_operand:DI 1 "nonimmediate_operand" "r,m")))]
5247   "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH
5248    && (TARGET_INTER_UNIT_CONVERSIONS || optimize_size)"
5249   "cvtsi2sd{q}\t{%1, %0|%0, %1}"
5250   [(set_attr "type" "sseicvt")
5251    (set_attr "mode" "DF")
5252    (set_attr "athlon_decode" "double,direct")
5253    (set_attr "amdfam10_decode" "vector,double")
5254    (set_attr "fp_int_src" "true")])
5255
5256 (define_insn "*floatdidf2_sse_memory"
5257   [(set (match_operand:DF 0 "register_operand" "=x")
5258         (float:DF (match_operand:DI 1 "memory_operand" "m")))]
5259   "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH
5260    && !TARGET_INTER_UNIT_CONVERSIONS && !optimize_size"
5261   "cvtsi2sd{q}\t{%1, %0|%0, %1}"
5262   [(set_attr "type" "sseicvt")
5263    (set_attr "mode" "DF")
5264    (set_attr "athlon_decode" "direct")
5265    (set_attr "amdfam10_decode" "double")
5266    (set_attr "fp_int_src" "true")])
5267
5268 (define_insn "*floatdi<mode>2_i387"
5269   [(set (match_operand:MODEF 0 "register_operand" "=f,f")
5270         (float:MODEF
5271           (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
5272   "TARGET_80387
5273    && (!TARGET_SSE_MATH || !TARGET_64BIT
5274        || !SSE_FLOAT_MODE_P (GET_MODE (operands[0])))"
5275   "@
5276    fild%z1\t%1
5277    #"
5278   [(set_attr "type" "fmov,multi")
5279    (set_attr "mode" "<MODE>")
5280    (set_attr "unit" "*,i387")
5281    (set_attr "fp_int_src" "true")])
5282
5283 (define_insn "float<mode>xf2"
5284   [(set (match_operand:XF 0 "register_operand" "=f,f")
5285         (float:XF (match_operand:X87MODEI 1 "nonimmediate_operand" "m,?r")))]
5286   "TARGET_80387"
5287   "@
5288    fild%z1\t%1
5289    #"
5290   [(set_attr "type" "fmov,multi")
5291    (set_attr "mode" "XF")
5292    (set_attr "unit" "*,i387")
5293    (set_attr "fp_int_src" "true")])
5294
5295 ;; %%% Kill these when reload knows how to do it.
5296 (define_split
5297   [(set (match_operand 0 "fp_register_operand" "")
5298         (float (match_operand 1 "register_operand" "")))]
5299   "reload_completed
5300    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))"
5301   [(const_int 0)]
5302 {
5303   operands[2] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
5304   operands[2] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[2]);
5305   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[2]));
5306   ix86_free_from_memory (GET_MODE (operands[1]));
5307   DONE;
5308 })
5309
5310 (define_expand "floatunssi<mode>2"
5311   [(use (match_operand:MODEF 0 "register_operand" ""))
5312    (use (match_operand:SI 1 "nonimmediate_operand" ""))]
5313   "!TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
5314 {
5315   ix86_expand_convert_uns_si<mode>_sse (operands[0], operands[1]);
5316   DONE;
5317 })
5318
5319 (define_expand "floatunsdisf2"
5320   [(use (match_operand:SF 0 "register_operand" ""))
5321    (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5322   "TARGET_64BIT && TARGET_SSE_MATH"
5323   "x86_emit_floatuns (operands); DONE;")
5324
5325 (define_expand "floatunsdidf2"
5326   [(use (match_operand:DF 0 "register_operand" ""))
5327    (use (match_operand:DI 1 "nonimmediate_operand" ""))]
5328   "(TARGET_64BIT || TARGET_KEEPS_VECTOR_ALIGNED_STACK)
5329    && TARGET_SSE2 && TARGET_SSE_MATH"
5330 {
5331   if (TARGET_64BIT)
5332     x86_emit_floatuns (operands);
5333   else
5334     ix86_expand_convert_uns_didf_sse (operands[0], operands[1]);
5335   DONE;
5336 })
5337 \f
5338 ;; Add instructions
5339
5340 ;; %%% splits for addditi3
5341
5342 (define_expand "addti3"
5343   [(set (match_operand:TI 0 "nonimmediate_operand" "")
5344         (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
5345                  (match_operand:TI 2 "x86_64_general_operand" "")))
5346    (clobber (reg:CC FLAGS_REG))]
5347   "TARGET_64BIT"
5348   "ix86_expand_binary_operator (PLUS, TImode, operands); DONE;")
5349
5350 (define_insn "*addti3_1"
5351   [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o")
5352         (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0,0")
5353                  (match_operand:TI 2 "x86_64_general_operand" "roe,re")))
5354    (clobber (reg:CC FLAGS_REG))]
5355   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, TImode, operands)"
5356   "#")
5357
5358 (define_split
5359   [(set (match_operand:TI 0 "nonimmediate_operand" "")
5360         (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
5361                  (match_operand:TI 2 "x86_64_general_operand" "")))
5362    (clobber (reg:CC FLAGS_REG))]
5363   "TARGET_64BIT && reload_completed"
5364   [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
5365                                           UNSPEC_ADD_CARRY))
5366               (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))])
5367    (parallel [(set (match_dup 3)
5368                    (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
5369                                      (match_dup 4))
5370                             (match_dup 5)))
5371               (clobber (reg:CC FLAGS_REG))])]
5372   "split_ti (operands+0, 1, operands+0, operands+3);
5373    split_ti (operands+1, 1, operands+1, operands+4);
5374    split_ti (operands+2, 1, operands+2, operands+5);")
5375
5376 ;; %%% splits for addsidi3
5377 ;  [(set (match_operand:DI 0 "nonimmediate_operand" "")
5378 ;       (plus:DI (match_operand:DI 1 "general_operand" "")
5379 ;                (zero_extend:DI (match_operand:SI 2 "general_operand" ""))))]
5380
5381 (define_expand "adddi3"
5382   [(set (match_operand:DI 0 "nonimmediate_operand" "")
5383         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5384                  (match_operand:DI 2 "x86_64_general_operand" "")))
5385    (clobber (reg:CC FLAGS_REG))]
5386   ""
5387   "ix86_expand_binary_operator (PLUS, DImode, operands); DONE;")
5388
5389 (define_insn "*adddi3_1"
5390   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
5391         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5392                  (match_operand:DI 2 "general_operand" "roiF,riF")))
5393    (clobber (reg:CC FLAGS_REG))]
5394   "!TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5395   "#")
5396
5397 (define_split
5398   [(set (match_operand:DI 0 "nonimmediate_operand" "")
5399         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5400                  (match_operand:DI 2 "general_operand" "")))
5401    (clobber (reg:CC FLAGS_REG))]
5402   "!TARGET_64BIT && reload_completed"
5403   [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
5404                                           UNSPEC_ADD_CARRY))
5405               (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))])
5406    (parallel [(set (match_dup 3)
5407                    (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
5408                                      (match_dup 4))
5409                             (match_dup 5)))
5410               (clobber (reg:CC FLAGS_REG))])]
5411   "split_di (operands+0, 1, operands+0, operands+3);
5412    split_di (operands+1, 1, operands+1, operands+4);
5413    split_di (operands+2, 1, operands+2, operands+5);")
5414
5415 (define_insn "adddi3_carry_rex64"
5416   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
5417           (plus:DI (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
5418                             (match_operand:DI 1 "nonimmediate_operand" "%0,0"))
5419                    (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
5420    (clobber (reg:CC FLAGS_REG))]
5421   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5422   "adc{q}\t{%2, %0|%0, %2}"
5423   [(set_attr "type" "alu")
5424    (set_attr "pent_pair" "pu")
5425    (set_attr "mode" "DI")])
5426
5427 (define_insn "*adddi3_cc_rex64"
5428   [(set (reg:CC FLAGS_REG)
5429         (unspec:CC [(match_operand:DI 1 "nonimmediate_operand" "%0,0")
5430                     (match_operand:DI 2 "x86_64_general_operand" "re,rm")]
5431                    UNSPEC_ADD_CARRY))
5432    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
5433         (plus:DI (match_dup 1) (match_dup 2)))]
5434   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5435   "add{q}\t{%2, %0|%0, %2}"
5436   [(set_attr "type" "alu")
5437    (set_attr "mode" "DI")])
5438
5439 (define_insn "*<addsub><mode>3_cc_overflow"
5440   [(set (reg:CCC FLAGS_REG)
5441         (compare:CCC
5442             (plusminus:SWI
5443                 (match_operand:SWI 1 "nonimmediate_operand" "<comm>0,0")
5444                 (match_operand:SWI 2 "<general_operand>" "<r><i>,<r>m"))
5445             (match_dup 1)))
5446    (set (match_operand:SWI 0 "nonimmediate_operand" "=<r>m,<r>")
5447         (plusminus:SWI (match_dup 1) (match_dup 2)))]
5448   "ix86_binary_operator_ok (<CODE>, <MODE>mode, operands)"
5449   "<addsub>{<imodesuffix>}\t{%2, %0|%0, %2}"
5450   [(set_attr "type" "alu")
5451    (set_attr "mode" "<MODE>")])
5452
5453 (define_insn "*add<mode>3_cconly_overflow"
5454   [(set (reg:CCC FLAGS_REG)
5455         (compare:CCC
5456                 (plus:SWI (match_operand:SWI 1 "nonimmediate_operand" "%0")
5457                           (match_operand:SWI 2 "<general_operand>" "<r><i>m"))
5458                 (match_dup 1)))
5459    (clobber (match_scratch:SWI 0 "=<r>"))]
5460   "ix86_binary_operator_ok (PLUS, <MODE>mode, operands)"
5461   "add{<imodesuffix>}\t{%2, %0|%0, %2}"
5462   [(set_attr "type" "alu")
5463    (set_attr "mode" "<MODE>")])
5464
5465 (define_insn "*sub<mode>3_cconly_overflow"
5466   [(set (reg:CCC FLAGS_REG)
5467         (compare:CCC
5468              (minus:SWI (match_operand:SWI 0 "nonimmediate_operand" "<r>m,<r>")
5469                         (match_operand:SWI 1 "<general_operand>" "<r><i>,<r>m"))
5470              (match_dup 0)))]
5471   ""
5472   "cmp{<imodesuffix>}\t{%1, %0|%0, %1}"
5473   [(set_attr "type" "icmp")
5474    (set_attr "mode" "<MODE>")])
5475
5476 (define_insn "*<addsub>si3_zext_cc_overflow"
5477   [(set (reg:CCC FLAGS_REG)
5478         (compare:CCC
5479             (plusminus:SI (match_operand:SI 1 "nonimmediate_operand" "<comm>0")
5480                           (match_operand:SI 2 "general_operand" "g"))
5481             (match_dup 1)))
5482    (set (match_operand:DI 0 "register_operand" "=r")
5483         (zero_extend:DI (plusminus:SI (match_dup 1) (match_dup 2))))]
5484   "TARGET_64BIT && ix86_binary_operator_ok (<CODE>, SImode, operands)"
5485   "<addsub>{l}\t{%2, %k0|%k0, %2}"
5486   [(set_attr "type" "alu")
5487    (set_attr "mode" "SI")])
5488
5489 (define_insn "addqi3_carry"
5490   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
5491           (plus:QI (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
5492                             (match_operand:QI 1 "nonimmediate_operand" "%0,0"))
5493                    (match_operand:QI 2 "general_operand" "qi,qm")))
5494    (clobber (reg:CC FLAGS_REG))]
5495   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5496   "adc{b}\t{%2, %0|%0, %2}"
5497   [(set_attr "type" "alu")
5498    (set_attr "pent_pair" "pu")
5499    (set_attr "mode" "QI")])
5500
5501 (define_insn "addhi3_carry"
5502   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
5503           (plus:HI (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
5504                             (match_operand:HI 1 "nonimmediate_operand" "%0,0"))
5505                    (match_operand:HI 2 "general_operand" "ri,rm")))
5506    (clobber (reg:CC FLAGS_REG))]
5507   "ix86_binary_operator_ok (PLUS, HImode, operands)"
5508   "adc{w}\t{%2, %0|%0, %2}"
5509   [(set_attr "type" "alu")
5510    (set_attr "pent_pair" "pu")
5511    (set_attr "mode" "HI")])
5512
5513 (define_insn "addsi3_carry"
5514   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
5515           (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
5516                             (match_operand:SI 1 "nonimmediate_operand" "%0,0"))
5517                    (match_operand:SI 2 "general_operand" "ri,rm")))
5518    (clobber (reg:CC FLAGS_REG))]
5519   "ix86_binary_operator_ok (PLUS, SImode, operands)"
5520   "adc{l}\t{%2, %0|%0, %2}"
5521   [(set_attr "type" "alu")
5522    (set_attr "pent_pair" "pu")
5523    (set_attr "mode" "SI")])
5524
5525 (define_insn "*addsi3_carry_zext"
5526   [(set (match_operand:DI 0 "register_operand" "=r")
5527           (zero_extend:DI
5528             (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
5529                               (match_operand:SI 1 "nonimmediate_operand" "%0"))
5530                      (match_operand:SI 2 "general_operand" "g"))))
5531    (clobber (reg:CC FLAGS_REG))]
5532   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5533   "adc{l}\t{%2, %k0|%k0, %2}"
5534   [(set_attr "type" "alu")
5535    (set_attr "pent_pair" "pu")
5536    (set_attr "mode" "SI")])
5537
5538 (define_insn "*addsi3_cc"
5539   [(set (reg:CC FLAGS_REG)
5540         (unspec:CC [(match_operand:SI 1 "nonimmediate_operand" "%0,0")
5541                     (match_operand:SI 2 "general_operand" "ri,rm")]
5542                    UNSPEC_ADD_CARRY))
5543    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
5544         (plus:SI (match_dup 1) (match_dup 2)))]
5545   "ix86_binary_operator_ok (PLUS, SImode, operands)"
5546   "add{l}\t{%2, %0|%0, %2}"
5547   [(set_attr "type" "alu")
5548    (set_attr "mode" "SI")])
5549
5550 (define_insn "addqi3_cc"
5551   [(set (reg:CC FLAGS_REG)
5552         (unspec:CC [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
5553                     (match_operand:QI 2 "general_operand" "qi,qm")]
5554                    UNSPEC_ADD_CARRY))
5555    (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
5556         (plus:QI (match_dup 1) (match_dup 2)))]
5557   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5558   "add{b}\t{%2, %0|%0, %2}"
5559   [(set_attr "type" "alu")
5560    (set_attr "mode" "QI")])
5561
5562 (define_expand "addsi3"
5563   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
5564                    (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
5565                             (match_operand:SI 2 "general_operand" "")))
5566               (clobber (reg:CC FLAGS_REG))])]
5567   ""
5568   "ix86_expand_binary_operator (PLUS, SImode, operands); DONE;")
5569
5570 (define_insn "*lea_1"
5571   [(set (match_operand:SI 0 "register_operand" "=r")
5572         (match_operand:SI 1 "no_seg_address_operand" "p"))]
5573   "!TARGET_64BIT"
5574   "lea{l}\t{%a1, %0|%0, %a1}"
5575   [(set_attr "type" "lea")
5576    (set_attr "mode" "SI")])
5577
5578 (define_insn "*lea_1_rex64"
5579   [(set (match_operand:SI 0 "register_operand" "=r")
5580         (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0))]
5581   "TARGET_64BIT"
5582   "lea{l}\t{%a1, %0|%0, %a1}"
5583   [(set_attr "type" "lea")
5584    (set_attr "mode" "SI")])
5585
5586 (define_insn "*lea_1_zext"
5587   [(set (match_operand:DI 0 "register_operand" "=r")
5588         (zero_extend:DI
5589          (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0)))]
5590   "TARGET_64BIT"
5591   "lea{l}\t{%a1, %k0|%k0, %a1}"
5592   [(set_attr "type" "lea")
5593    (set_attr "mode" "SI")])
5594
5595 (define_insn "*lea_2_rex64"
5596   [(set (match_operand:DI 0 "register_operand" "=r")
5597         (match_operand:DI 1 "no_seg_address_operand" "p"))]
5598   "TARGET_64BIT"
5599   "lea{q}\t{%a1, %0|%0, %a1}"
5600   [(set_attr "type" "lea")
5601    (set_attr "mode" "DI")])
5602
5603 ;; The lea patterns for non-Pmodes needs to be matched by several
5604 ;; insns converted to real lea by splitters.
5605
5606 (define_insn_and_split "*lea_general_1"
5607   [(set (match_operand 0 "register_operand" "=r")
5608         (plus (plus (match_operand 1 "index_register_operand" "l")
5609                     (match_operand 2 "register_operand" "r"))
5610               (match_operand 3 "immediate_operand" "i")))]
5611   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5612     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5613    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5614    && GET_MODE (operands[0]) == GET_MODE (operands[1])
5615    && GET_MODE (operands[0]) == GET_MODE (operands[2])
5616    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
5617        || GET_MODE (operands[3]) == VOIDmode)"
5618   "#"
5619   "&& reload_completed"
5620   [(const_int 0)]
5621 {
5622   rtx pat;
5623   operands[0] = gen_lowpart (SImode, operands[0]);
5624   operands[1] = gen_lowpart (Pmode, operands[1]);
5625   operands[2] = gen_lowpart (Pmode, operands[2]);
5626   operands[3] = gen_lowpart (Pmode, operands[3]);
5627   pat = gen_rtx_PLUS (Pmode, gen_rtx_PLUS (Pmode, operands[1], operands[2]),
5628                       operands[3]);
5629   if (Pmode != SImode)
5630     pat = gen_rtx_SUBREG (SImode, pat, 0);
5631   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5632   DONE;
5633 }
5634   [(set_attr "type" "lea")
5635    (set_attr "mode" "SI")])
5636
5637 (define_insn_and_split "*lea_general_1_zext"
5638   [(set (match_operand:DI 0 "register_operand" "=r")
5639         (zero_extend:DI
5640           (plus:SI (plus:SI (match_operand:SI 1 "index_register_operand" "l")
5641                             (match_operand:SI 2 "register_operand" "r"))
5642                    (match_operand:SI 3 "immediate_operand" "i"))))]
5643   "TARGET_64BIT"
5644   "#"
5645   "&& reload_completed"
5646   [(set (match_dup 0)
5647         (zero_extend:DI (subreg:SI (plus:DI (plus:DI (match_dup 1)
5648                                                      (match_dup 2))
5649                                             (match_dup 3)) 0)))]
5650 {
5651   operands[1] = gen_lowpart (Pmode, operands[1]);
5652   operands[2] = gen_lowpart (Pmode, operands[2]);
5653   operands[3] = gen_lowpart (Pmode, operands[3]);
5654 }
5655   [(set_attr "type" "lea")
5656    (set_attr "mode" "SI")])
5657
5658 (define_insn_and_split "*lea_general_2"
5659   [(set (match_operand 0 "register_operand" "=r")
5660         (plus (mult (match_operand 1 "index_register_operand" "l")
5661                     (match_operand 2 "const248_operand" "i"))
5662               (match_operand 3 "nonmemory_operand" "ri")))]
5663   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5664     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5665    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5666    && GET_MODE (operands[0]) == GET_MODE (operands[1])
5667    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
5668        || GET_MODE (operands[3]) == VOIDmode)"
5669   "#"
5670   "&& reload_completed"
5671   [(const_int 0)]
5672 {
5673   rtx pat;
5674   operands[0] = gen_lowpart (SImode, operands[0]);
5675   operands[1] = gen_lowpart (Pmode, operands[1]);
5676   operands[3] = gen_lowpart (Pmode, operands[3]);
5677   pat = gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], operands[2]),
5678                       operands[3]);
5679   if (Pmode != SImode)
5680     pat = gen_rtx_SUBREG (SImode, pat, 0);
5681   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5682   DONE;
5683 }
5684   [(set_attr "type" "lea")
5685    (set_attr "mode" "SI")])
5686
5687 (define_insn_and_split "*lea_general_2_zext"
5688   [(set (match_operand:DI 0 "register_operand" "=r")
5689         (zero_extend:DI
5690           (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "l")
5691                             (match_operand:SI 2 "const248_operand" "n"))
5692                    (match_operand:SI 3 "nonmemory_operand" "ri"))))]
5693   "TARGET_64BIT"
5694   "#"
5695   "&& reload_completed"
5696   [(set (match_dup 0)
5697         (zero_extend:DI (subreg:SI (plus:DI (mult:DI (match_dup 1)
5698                                                      (match_dup 2))
5699                                             (match_dup 3)) 0)))]
5700 {
5701   operands[1] = gen_lowpart (Pmode, operands[1]);
5702   operands[3] = gen_lowpart (Pmode, operands[3]);
5703 }
5704   [(set_attr "type" "lea")
5705    (set_attr "mode" "SI")])
5706
5707 (define_insn_and_split "*lea_general_3"
5708   [(set (match_operand 0 "register_operand" "=r")
5709         (plus (plus (mult (match_operand 1 "index_register_operand" "l")
5710                           (match_operand 2 "const248_operand" "i"))
5711                     (match_operand 3 "register_operand" "r"))
5712               (match_operand 4 "immediate_operand" "i")))]
5713   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5714     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5715    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5716    && GET_MODE (operands[0]) == GET_MODE (operands[1])
5717    && GET_MODE (operands[0]) == GET_MODE (operands[3])"
5718   "#"
5719   "&& reload_completed"
5720   [(const_int 0)]
5721 {
5722   rtx pat;
5723   operands[0] = gen_lowpart (SImode, operands[0]);
5724   operands[1] = gen_lowpart (Pmode, operands[1]);
5725   operands[3] = gen_lowpart (Pmode, operands[3]);
5726   operands[4] = gen_lowpart (Pmode, operands[4]);
5727   pat = gen_rtx_PLUS (Pmode,
5728                       gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1],
5729                                                          operands[2]),
5730                                     operands[3]),
5731                       operands[4]);
5732   if (Pmode != SImode)
5733     pat = gen_rtx_SUBREG (SImode, pat, 0);
5734   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5735   DONE;
5736 }
5737   [(set_attr "type" "lea")
5738    (set_attr "mode" "SI")])
5739
5740 (define_insn_and_split "*lea_general_3_zext"
5741   [(set (match_operand:DI 0 "register_operand" "=r")
5742         (zero_extend:DI
5743           (plus:SI (plus:SI (mult:SI
5744                               (match_operand:SI 1 "index_register_operand" "l")
5745                               (match_operand:SI 2 "const248_operand" "n"))
5746                             (match_operand:SI 3 "register_operand" "r"))
5747                    (match_operand:SI 4 "immediate_operand" "i"))))]
5748   "TARGET_64BIT"
5749   "#"
5750   "&& reload_completed"
5751   [(set (match_dup 0)
5752         (zero_extend:DI (subreg:SI (plus:DI (plus:DI (mult:DI (match_dup 1)
5753                                                               (match_dup 2))
5754                                                      (match_dup 3))
5755                                             (match_dup 4)) 0)))]
5756 {
5757   operands[1] = gen_lowpart (Pmode, operands[1]);
5758   operands[3] = gen_lowpart (Pmode, operands[3]);
5759   operands[4] = gen_lowpart (Pmode, operands[4]);
5760 }
5761   [(set_attr "type" "lea")
5762    (set_attr "mode" "SI")])
5763
5764 (define_insn "*adddi_1_rex64"
5765   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r")
5766         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,r")
5767                  (match_operand:DI 2 "x86_64_general_operand" "rme,re,le")))
5768    (clobber (reg:CC FLAGS_REG))]
5769   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5770 {
5771   switch (get_attr_type (insn))
5772     {
5773     case TYPE_LEA:
5774       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5775       return "lea{q}\t{%a2, %0|%0, %a2}";
5776
5777     case TYPE_INCDEC:
5778       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5779       if (operands[2] == const1_rtx)
5780         return "inc{q}\t%0";
5781       else
5782         {
5783           gcc_assert (operands[2] == constm1_rtx);
5784           return "dec{q}\t%0";
5785         }
5786
5787     default:
5788       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5789
5790       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5791          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5792       if (CONST_INT_P (operands[2])
5793           /* Avoid overflows.  */
5794           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5795           && (INTVAL (operands[2]) == 128
5796               || (INTVAL (operands[2]) < 0
5797                   && INTVAL (operands[2]) != -128)))
5798         {
5799           operands[2] = GEN_INT (-INTVAL (operands[2]));
5800           return "sub{q}\t{%2, %0|%0, %2}";
5801         }
5802       return "add{q}\t{%2, %0|%0, %2}";
5803     }
5804 }
5805   [(set (attr "type")
5806      (cond [(eq_attr "alternative" "2")
5807               (const_string "lea")
5808             ; Current assemblers are broken and do not allow @GOTOFF in
5809             ; ought but a memory context.
5810             (match_operand:DI 2 "pic_symbolic_operand" "")
5811               (const_string "lea")
5812             (match_operand:DI 2 "incdec_operand" "")
5813               (const_string "incdec")
5814            ]
5815            (const_string "alu")))
5816    (set_attr "mode" "DI")])
5817
5818 ;; Convert lea to the lea pattern to avoid flags dependency.
5819 (define_split
5820   [(set (match_operand:DI 0 "register_operand" "")
5821         (plus:DI (match_operand:DI 1 "register_operand" "")
5822                  (match_operand:DI 2 "x86_64_nonmemory_operand" "")))
5823    (clobber (reg:CC FLAGS_REG))]
5824   "TARGET_64BIT && reload_completed
5825    && true_regnum (operands[0]) != true_regnum (operands[1])"
5826   [(set (match_dup 0)
5827         (plus:DI (match_dup 1)
5828                  (match_dup 2)))]
5829   "")
5830
5831 (define_insn "*adddi_2_rex64"
5832   [(set (reg FLAGS_REG)
5833         (compare
5834           (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5835                    (match_operand:DI 2 "x86_64_general_operand" "rme,re"))
5836           (const_int 0)))
5837    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
5838         (plus:DI (match_dup 1) (match_dup 2)))]
5839   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5840    && ix86_binary_operator_ok (PLUS, DImode, operands)
5841    /* Current assemblers are broken and do not allow @GOTOFF in
5842       ought but a memory context.  */
5843    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5844 {
5845   switch (get_attr_type (insn))
5846     {
5847     case TYPE_INCDEC:
5848       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5849       if (operands[2] == const1_rtx)
5850         return "inc{q}\t%0";
5851       else
5852         {
5853           gcc_assert (operands[2] == constm1_rtx);
5854           return "dec{q}\t%0";
5855         }
5856
5857     default:
5858       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5859       /* ???? We ought to handle there the 32bit case too
5860          - do we need new constraint?  */
5861       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5862          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5863       if (CONST_INT_P (operands[2])
5864           /* Avoid overflows.  */
5865           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5866           && (INTVAL (operands[2]) == 128
5867               || (INTVAL (operands[2]) < 0
5868                   && INTVAL (operands[2]) != -128)))
5869         {
5870           operands[2] = GEN_INT (-INTVAL (operands[2]));
5871           return "sub{q}\t{%2, %0|%0, %2}";
5872         }
5873       return "add{q}\t{%2, %0|%0, %2}";
5874     }
5875 }
5876   [(set (attr "type")
5877      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5878         (const_string "incdec")
5879         (const_string "alu")))
5880    (set_attr "mode" "DI")])
5881
5882 (define_insn "*adddi_3_rex64"
5883   [(set (reg FLAGS_REG)
5884         (compare (neg:DI (match_operand:DI 2 "x86_64_general_operand" "rme"))
5885                  (match_operand:DI 1 "x86_64_general_operand" "%0")))
5886    (clobber (match_scratch:DI 0 "=r"))]
5887   "TARGET_64BIT
5888    && ix86_match_ccmode (insn, CCZmode)
5889    && !(MEM_P (operands[1]) && MEM_P (operands[2]))
5890    /* Current assemblers are broken and do not allow @GOTOFF in
5891       ought but a memory context.  */
5892    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5893 {
5894   switch (get_attr_type (insn))
5895     {
5896     case TYPE_INCDEC:
5897       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5898       if (operands[2] == const1_rtx)
5899         return "inc{q}\t%0";
5900       else
5901         {
5902           gcc_assert (operands[2] == constm1_rtx);
5903           return "dec{q}\t%0";
5904         }
5905
5906     default:
5907       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5908       /* ???? We ought to handle there the 32bit case too
5909          - do we need new constraint?  */
5910       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5911          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5912       if (CONST_INT_P (operands[2])
5913           /* Avoid overflows.  */
5914           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5915           && (INTVAL (operands[2]) == 128
5916               || (INTVAL (operands[2]) < 0
5917                   && INTVAL (operands[2]) != -128)))
5918         {
5919           operands[2] = GEN_INT (-INTVAL (operands[2]));
5920           return "sub{q}\t{%2, %0|%0, %2}";
5921         }
5922       return "add{q}\t{%2, %0|%0, %2}";
5923     }
5924 }
5925   [(set (attr "type")
5926      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5927         (const_string "incdec")
5928         (const_string "alu")))
5929    (set_attr "mode" "DI")])
5930
5931 ; For comparisons against 1, -1 and 128, we may generate better code
5932 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
5933 ; is matched then.  We can't accept general immediate, because for
5934 ; case of overflows,  the result is messed up.
5935 ; This pattern also don't hold of 0x8000000000000000, since the value overflows
5936 ; when negated.
5937 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5938 ; only for comparisons not depending on it.
5939 (define_insn "*adddi_4_rex64"
5940   [(set (reg FLAGS_REG)
5941         (compare (match_operand:DI 1 "nonimmediate_operand" "0")
5942                  (match_operand:DI 2 "x86_64_immediate_operand" "e")))
5943    (clobber (match_scratch:DI 0 "=rm"))]
5944   "TARGET_64BIT
5945    &&  ix86_match_ccmode (insn, CCGCmode)"
5946 {
5947   switch (get_attr_type (insn))
5948     {
5949     case TYPE_INCDEC:
5950       if (operands[2] == constm1_rtx)
5951         return "inc{q}\t%0";
5952       else
5953         {
5954           gcc_assert (operands[2] == const1_rtx);
5955           return "dec{q}\t%0";
5956         }
5957
5958     default:
5959       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5960       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5961          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5962       if ((INTVAL (operands[2]) == -128
5963            || (INTVAL (operands[2]) > 0
5964                && INTVAL (operands[2]) != 128))
5965           /* Avoid overflows.  */
5966           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))))
5967         return "sub{q}\t{%2, %0|%0, %2}";
5968       operands[2] = GEN_INT (-INTVAL (operands[2]));
5969       return "add{q}\t{%2, %0|%0, %2}";
5970     }
5971 }
5972   [(set (attr "type")
5973      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5974         (const_string "incdec")
5975         (const_string "alu")))
5976    (set_attr "mode" "DI")])
5977
5978 (define_insn "*adddi_5_rex64"
5979   [(set (reg FLAGS_REG)
5980         (compare
5981           (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5982                    (match_operand:DI 2 "x86_64_general_operand" "rme"))
5983           (const_int 0)))
5984    (clobber (match_scratch:DI 0 "=r"))]
5985   "TARGET_64BIT
5986    && ix86_match_ccmode (insn, CCGOCmode)
5987    && !(MEM_P (operands[1]) && MEM_P (operands[2]))
5988    /* Current assemblers are broken and do not allow @GOTOFF in
5989       ought but a memory context.  */
5990    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5991 {
5992   switch (get_attr_type (insn))
5993     {
5994     case TYPE_INCDEC:
5995       gcc_assert (rtx_equal_p (operands[0], operands[1]));
5996       if (operands[2] == const1_rtx)
5997         return "inc{q}\t%0";
5998       else
5999         {
6000           gcc_assert (operands[2] == constm1_rtx);
6001           return "dec{q}\t%0";
6002         }
6003
6004     default:
6005       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6006       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6007          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6008       if (CONST_INT_P (operands[2])
6009           /* Avoid overflows.  */
6010           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
6011           && (INTVAL (operands[2]) == 128
6012               || (INTVAL (operands[2]) < 0
6013                   && INTVAL (operands[2]) != -128)))
6014         {
6015           operands[2] = GEN_INT (-INTVAL (operands[2]));
6016           return "sub{q}\t{%2, %0|%0, %2}";
6017         }
6018       return "add{q}\t{%2, %0|%0, %2}";
6019     }
6020 }
6021   [(set (attr "type")
6022      (if_then_else (match_operand:DI 2 "incdec_operand" "")
6023         (const_string "incdec")
6024         (const_string "alu")))
6025    (set_attr "mode" "DI")])
6026
6027
6028 (define_insn "*addsi_1"
6029   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,rm,r")
6030         (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,r")
6031                  (match_operand:SI 2 "general_operand" "rmni,rni,lni")))
6032    (clobber (reg:CC FLAGS_REG))]
6033   "ix86_binary_operator_ok (PLUS, SImode, operands)"
6034 {
6035   switch (get_attr_type (insn))
6036     {
6037     case TYPE_LEA:
6038       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
6039       return "lea{l}\t{%a2, %0|%0, %a2}";
6040
6041     case TYPE_INCDEC:
6042       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6043       if (operands[2] == const1_rtx)
6044         return "inc{l}\t%0";
6045       else
6046         {
6047           gcc_assert (operands[2] == constm1_rtx);
6048           return "dec{l}\t%0";
6049         }
6050
6051     default:
6052       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6053
6054       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6055          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6056       if (CONST_INT_P (operands[2])
6057           && (INTVAL (operands[2]) == 128
6058               || (INTVAL (operands[2]) < 0
6059                   && INTVAL (operands[2]) != -128)))
6060         {
6061           operands[2] = GEN_INT (-INTVAL (operands[2]));
6062           return "sub{l}\t{%2, %0|%0, %2}";
6063         }
6064       return "add{l}\t{%2, %0|%0, %2}";
6065     }
6066 }
6067   [(set (attr "type")
6068      (cond [(eq_attr "alternative" "2")
6069               (const_string "lea")
6070             ; Current assemblers are broken and do not allow @GOTOFF in
6071             ; ought but a memory context.
6072             (match_operand:SI 2 "pic_symbolic_operand" "")
6073               (const_string "lea")
6074             (match_operand:SI 2 "incdec_operand" "")
6075               (const_string "incdec")
6076            ]
6077            (const_string "alu")))
6078    (set_attr "mode" "SI")])
6079
6080 ;; Convert lea to the lea pattern to avoid flags dependency.
6081 (define_split
6082   [(set (match_operand 0 "register_operand" "")
6083         (plus (match_operand 1 "register_operand" "")
6084               (match_operand 2 "nonmemory_operand" "")))
6085    (clobber (reg:CC FLAGS_REG))]
6086   "reload_completed
6087    && true_regnum (operands[0]) != true_regnum (operands[1])"
6088   [(const_int 0)]
6089 {
6090   rtx pat;
6091   /* In -fPIC mode the constructs like (const (unspec [symbol_ref]))
6092      may confuse gen_lowpart.  */
6093   if (GET_MODE (operands[0]) != Pmode)
6094     {
6095       operands[1] = gen_lowpart (Pmode, operands[1]);
6096       operands[2] = gen_lowpart (Pmode, operands[2]);
6097     }
6098   operands[0] = gen_lowpart (SImode, operands[0]);
6099   pat = gen_rtx_PLUS (Pmode, operands[1], operands[2]);
6100   if (Pmode != SImode)
6101     pat = gen_rtx_SUBREG (SImode, pat, 0);
6102   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
6103   DONE;
6104 })
6105
6106 ;; It may seem that nonimmediate operand is proper one for operand 1.
6107 ;; The addsi_1 pattern allows nonimmediate operand at that place and
6108 ;; we take care in ix86_binary_operator_ok to not allow two memory
6109 ;; operands so proper swapping will be done in reload.  This allow
6110 ;; patterns constructed from addsi_1 to match.
6111 (define_insn "addsi_1_zext"
6112   [(set (match_operand:DI 0 "register_operand" "=r,r")
6113         (zero_extend:DI
6114           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r")
6115                    (match_operand:SI 2 "general_operand" "rmni,lni"))))
6116    (clobber (reg:CC FLAGS_REG))]
6117   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
6118 {
6119   switch (get_attr_type (insn))
6120     {
6121     case TYPE_LEA:
6122       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
6123       return "lea{l}\t{%a2, %k0|%k0, %a2}";
6124
6125     case TYPE_INCDEC:
6126       if (operands[2] == const1_rtx)
6127         return "inc{l}\t%k0";
6128       else
6129         {
6130           gcc_assert (operands[2] == constm1_rtx);
6131           return "dec{l}\t%k0";
6132         }
6133
6134     default:
6135       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6136          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6137       if (CONST_INT_P (operands[2])
6138           && (INTVAL (operands[2]) == 128
6139               || (INTVAL (operands[2]) < 0
6140                   && INTVAL (operands[2]) != -128)))
6141         {
6142           operands[2] = GEN_INT (-INTVAL (operands[2]));
6143           return "sub{l}\t{%2, %k0|%k0, %2}";
6144         }
6145       return "add{l}\t{%2, %k0|%k0, %2}";
6146     }
6147 }
6148   [(set (attr "type")
6149      (cond [(eq_attr "alternative" "1")
6150               (const_string "lea")
6151             ; Current assemblers are broken and do not allow @GOTOFF in
6152             ; ought but a memory context.
6153             (match_operand:SI 2 "pic_symbolic_operand" "")
6154               (const_string "lea")
6155             (match_operand:SI 2 "incdec_operand" "")
6156               (const_string "incdec")
6157            ]
6158            (const_string "alu")))
6159    (set_attr "mode" "SI")])
6160
6161 ;; Convert lea to the lea pattern to avoid flags dependency.
6162 (define_split
6163   [(set (match_operand:DI 0 "register_operand" "")
6164         (zero_extend:DI
6165           (plus:SI (match_operand:SI 1 "register_operand" "")
6166                    (match_operand:SI 2 "nonmemory_operand" ""))))
6167    (clobber (reg:CC FLAGS_REG))]
6168   "TARGET_64BIT && reload_completed
6169    && true_regnum (operands[0]) != true_regnum (operands[1])"
6170   [(set (match_dup 0)
6171         (zero_extend:DI (subreg:SI (plus:DI (match_dup 1) (match_dup 2)) 0)))]
6172 {
6173   operands[1] = gen_lowpart (Pmode, operands[1]);
6174   operands[2] = gen_lowpart (Pmode, operands[2]);
6175 })
6176
6177 (define_insn "*addsi_2"
6178   [(set (reg FLAGS_REG)
6179         (compare
6180           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
6181                    (match_operand:SI 2 "general_operand" "rmni,rni"))
6182           (const_int 0)))
6183    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
6184         (plus:SI (match_dup 1) (match_dup 2)))]
6185   "ix86_match_ccmode (insn, CCGOCmode)
6186    && ix86_binary_operator_ok (PLUS, SImode, operands)
6187    /* Current assemblers are broken and do not allow @GOTOFF in
6188       ought but a memory context.  */
6189    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6190 {
6191   switch (get_attr_type (insn))
6192     {
6193     case TYPE_INCDEC:
6194       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6195       if (operands[2] == const1_rtx)
6196         return "inc{l}\t%0";
6197       else
6198         {
6199           gcc_assert (operands[2] == constm1_rtx);
6200           return "dec{l}\t%0";
6201         }
6202
6203     default:
6204       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6205       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6206          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6207       if (CONST_INT_P (operands[2])
6208           && (INTVAL (operands[2]) == 128
6209               || (INTVAL (operands[2]) < 0
6210                   && INTVAL (operands[2]) != -128)))
6211         {
6212           operands[2] = GEN_INT (-INTVAL (operands[2]));
6213           return "sub{l}\t{%2, %0|%0, %2}";
6214         }
6215       return "add{l}\t{%2, %0|%0, %2}";
6216     }
6217 }
6218   [(set (attr "type")
6219      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6220         (const_string "incdec")
6221         (const_string "alu")))
6222    (set_attr "mode" "SI")])
6223
6224 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
6225 (define_insn "*addsi_2_zext"
6226   [(set (reg FLAGS_REG)
6227         (compare
6228           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
6229                    (match_operand:SI 2 "general_operand" "rmni"))
6230           (const_int 0)))
6231    (set (match_operand:DI 0 "register_operand" "=r")
6232         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
6233   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6234    && ix86_binary_operator_ok (PLUS, SImode, operands)
6235    /* Current assemblers are broken and do not allow @GOTOFF in
6236       ought but a memory context.  */
6237    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6238 {
6239   switch (get_attr_type (insn))
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      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6266         (const_string "incdec")
6267         (const_string "alu")))
6268    (set_attr "mode" "SI")])
6269
6270 (define_insn "*addsi_3"
6271   [(set (reg FLAGS_REG)
6272         (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
6273                  (match_operand:SI 1 "nonimmediate_operand" "%0")))
6274    (clobber (match_scratch:SI 0 "=r"))]
6275   "ix86_match_ccmode (insn, CCZmode)
6276    && !(MEM_P (operands[1]) && MEM_P (operands[2]))
6277    /* Current assemblers are broken and do not allow @GOTOFF in
6278       ought but a memory context.  */
6279    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6280 {
6281   switch (get_attr_type (insn))
6282     {
6283     case TYPE_INCDEC:
6284       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6285       if (operands[2] == const1_rtx)
6286         return "inc{l}\t%0";
6287       else
6288         {
6289           gcc_assert (operands[2] == constm1_rtx);
6290           return "dec{l}\t%0";
6291         }
6292
6293     default:
6294       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6295       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6296          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6297       if (CONST_INT_P (operands[2])
6298           && (INTVAL (operands[2]) == 128
6299               || (INTVAL (operands[2]) < 0
6300                   && INTVAL (operands[2]) != -128)))
6301         {
6302           operands[2] = GEN_INT (-INTVAL (operands[2]));
6303           return "sub{l}\t{%2, %0|%0, %2}";
6304         }
6305       return "add{l}\t{%2, %0|%0, %2}";
6306     }
6307 }
6308   [(set (attr "type")
6309      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6310         (const_string "incdec")
6311         (const_string "alu")))
6312    (set_attr "mode" "SI")])
6313
6314 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
6315 (define_insn "*addsi_3_zext"
6316   [(set (reg FLAGS_REG)
6317         (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
6318                  (match_operand:SI 1 "nonimmediate_operand" "%0")))
6319    (set (match_operand:DI 0 "register_operand" "=r")
6320         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
6321   "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
6322    && ix86_binary_operator_ok (PLUS, SImode, operands)
6323    /* Current assemblers are broken and do not allow @GOTOFF in
6324       ought but a memory context.  */
6325    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6326 {
6327   switch (get_attr_type (insn))
6328     {
6329     case TYPE_INCDEC:
6330       if (operands[2] == const1_rtx)
6331         return "inc{l}\t%k0";
6332       else
6333         {
6334           gcc_assert (operands[2] == constm1_rtx);
6335           return "dec{l}\t%k0";
6336         }
6337
6338     default:
6339       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6340          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6341       if (CONST_INT_P (operands[2])
6342           && (INTVAL (operands[2]) == 128
6343               || (INTVAL (operands[2]) < 0
6344                   && INTVAL (operands[2]) != -128)))
6345         {
6346           operands[2] = GEN_INT (-INTVAL (operands[2]));
6347           return "sub{l}\t{%2, %k0|%k0, %2}";
6348         }
6349       return "add{l}\t{%2, %k0|%k0, %2}";
6350     }
6351 }
6352   [(set (attr "type")
6353      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6354         (const_string "incdec")
6355         (const_string "alu")))
6356    (set_attr "mode" "SI")])
6357
6358 ; For comparisons against 1, -1 and 128, we may generate better code
6359 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
6360 ; is matched then.  We can't accept general immediate, because for
6361 ; case of overflows,  the result is messed up.
6362 ; This pattern also don't hold of 0x80000000, since the value overflows
6363 ; when negated.
6364 ; Also carry flag is reversed compared to cmp, so this conversion is valid
6365 ; only for comparisons not depending on it.
6366 (define_insn "*addsi_4"
6367   [(set (reg FLAGS_REG)
6368         (compare (match_operand:SI 1 "nonimmediate_operand" "0")
6369                  (match_operand:SI 2 "const_int_operand" "n")))
6370    (clobber (match_scratch:SI 0 "=rm"))]
6371   "ix86_match_ccmode (insn, CCGCmode)
6372    && (INTVAL (operands[2]) & 0xffffffff) != 0x80000000"
6373 {
6374   switch (get_attr_type (insn))
6375     {
6376     case TYPE_INCDEC:
6377       if (operands[2] == constm1_rtx)
6378         return "inc{l}\t%0";
6379       else
6380         {
6381           gcc_assert (operands[2] == const1_rtx);
6382           return "dec{l}\t%0";
6383         }
6384
6385     default:
6386       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6387       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6388          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6389       if ((INTVAL (operands[2]) == -128
6390            || (INTVAL (operands[2]) > 0
6391                && INTVAL (operands[2]) != 128)))
6392         return "sub{l}\t{%2, %0|%0, %2}";
6393       operands[2] = GEN_INT (-INTVAL (operands[2]));
6394       return "add{l}\t{%2, %0|%0, %2}";
6395     }
6396 }
6397   [(set (attr "type")
6398      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6399         (const_string "incdec")
6400         (const_string "alu")))
6401    (set_attr "mode" "SI")])
6402
6403 (define_insn "*addsi_5"
6404   [(set (reg FLAGS_REG)
6405         (compare
6406           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
6407                    (match_operand:SI 2 "general_operand" "rmni"))
6408           (const_int 0)))
6409    (clobber (match_scratch:SI 0 "=r"))]
6410   "ix86_match_ccmode (insn, CCGOCmode)
6411    && !(MEM_P (operands[1]) && MEM_P (operands[2]))
6412    /* Current assemblers are broken and do not allow @GOTOFF in
6413       ought but a memory context.  */
6414    && ! pic_symbolic_operand (operands[2], VOIDmode)"
6415 {
6416   switch (get_attr_type (insn))
6417     {
6418     case TYPE_INCDEC:
6419       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6420       if (operands[2] == const1_rtx)
6421         return "inc{l}\t%0";
6422       else
6423         {
6424           gcc_assert (operands[2] == constm1_rtx);
6425           return "dec{l}\t%0";
6426         }
6427
6428     default:
6429       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6430       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6431          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6432       if (CONST_INT_P (operands[2])
6433           && (INTVAL (operands[2]) == 128
6434               || (INTVAL (operands[2]) < 0
6435                   && INTVAL (operands[2]) != -128)))
6436         {
6437           operands[2] = GEN_INT (-INTVAL (operands[2]));
6438           return "sub{l}\t{%2, %0|%0, %2}";
6439         }
6440       return "add{l}\t{%2, %0|%0, %2}";
6441     }
6442 }
6443   [(set (attr "type")
6444      (if_then_else (match_operand:SI 2 "incdec_operand" "")
6445         (const_string "incdec")
6446         (const_string "alu")))
6447    (set_attr "mode" "SI")])
6448
6449 (define_expand "addhi3"
6450   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
6451                    (plus:HI (match_operand:HI 1 "nonimmediate_operand" "")
6452                             (match_operand:HI 2 "general_operand" "")))
6453               (clobber (reg:CC FLAGS_REG))])]
6454   "TARGET_HIMODE_MATH"
6455   "ix86_expand_binary_operator (PLUS, HImode, operands); DONE;")
6456
6457 ;; %%% After Dave's SUBREG_BYTE stuff goes in, re-enable incb %ah
6458 ;; type optimizations enabled by define-splits.  This is not important
6459 ;; for PII, and in fact harmful because of partial register stalls.
6460
6461 (define_insn "*addhi_1_lea"
6462   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
6463         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r")
6464                  (match_operand:HI 2 "general_operand" "ri,rm,lni")))
6465    (clobber (reg:CC FLAGS_REG))]
6466   "!TARGET_PARTIAL_REG_STALL
6467    && ix86_binary_operator_ok (PLUS, HImode, operands)"
6468 {
6469   switch (get_attr_type (insn))
6470     {
6471     case TYPE_LEA:
6472       return "#";
6473     case TYPE_INCDEC:
6474       if (operands[2] == const1_rtx)
6475         return "inc{w}\t%0";
6476       else
6477         {
6478           gcc_assert (operands[2] == constm1_rtx);
6479           return "dec{w}\t%0";
6480         }
6481
6482     default:
6483       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6484          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6485       if (CONST_INT_P (operands[2])
6486           && (INTVAL (operands[2]) == 128
6487               || (INTVAL (operands[2]) < 0
6488                   && INTVAL (operands[2]) != -128)))
6489         {
6490           operands[2] = GEN_INT (-INTVAL (operands[2]));
6491           return "sub{w}\t{%2, %0|%0, %2}";
6492         }
6493       return "add{w}\t{%2, %0|%0, %2}";
6494     }
6495 }
6496   [(set (attr "type")
6497      (if_then_else (eq_attr "alternative" "2")
6498         (const_string "lea")
6499         (if_then_else (match_operand:HI 2 "incdec_operand" "")
6500            (const_string "incdec")
6501            (const_string "alu"))))
6502    (set_attr "mode" "HI,HI,SI")])
6503
6504 (define_insn "*addhi_1"
6505   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6506         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
6507                  (match_operand:HI 2 "general_operand" "ri,rm")))
6508    (clobber (reg:CC FLAGS_REG))]
6509   "TARGET_PARTIAL_REG_STALL
6510    && ix86_binary_operator_ok (PLUS, HImode, operands)"
6511 {
6512   switch (get_attr_type (insn))
6513     {
6514     case TYPE_INCDEC:
6515       if (operands[2] == const1_rtx)
6516         return "inc{w}\t%0";
6517       else
6518         {
6519           gcc_assert (operands[2] == constm1_rtx);
6520           return "dec{w}\t%0";
6521         }
6522
6523     default:
6524       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6525          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6526       if (CONST_INT_P (operands[2])
6527           && (INTVAL (operands[2]) == 128
6528               || (INTVAL (operands[2]) < 0
6529                   && INTVAL (operands[2]) != -128)))
6530         {
6531           operands[2] = GEN_INT (-INTVAL (operands[2]));
6532           return "sub{w}\t{%2, %0|%0, %2}";
6533         }
6534       return "add{w}\t{%2, %0|%0, %2}";
6535     }
6536 }
6537   [(set (attr "type")
6538      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6539         (const_string "incdec")
6540         (const_string "alu")))
6541    (set_attr "mode" "HI")])
6542
6543 (define_insn "*addhi_2"
6544   [(set (reg FLAGS_REG)
6545         (compare
6546           (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
6547                    (match_operand:HI 2 "general_operand" "rmni,rni"))
6548           (const_int 0)))
6549    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
6550         (plus:HI (match_dup 1) (match_dup 2)))]
6551   "ix86_match_ccmode (insn, CCGOCmode)
6552    && ix86_binary_operator_ok (PLUS, HImode, operands)"
6553 {
6554   switch (get_attr_type (insn))
6555     {
6556     case TYPE_INCDEC:
6557       if (operands[2] == const1_rtx)
6558         return "inc{w}\t%0";
6559       else
6560         {
6561           gcc_assert (operands[2] == constm1_rtx);
6562           return "dec{w}\t%0";
6563         }
6564
6565     default:
6566       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6567          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6568       if (CONST_INT_P (operands[2])
6569           && (INTVAL (operands[2]) == 128
6570               || (INTVAL (operands[2]) < 0
6571                   && INTVAL (operands[2]) != -128)))
6572         {
6573           operands[2] = GEN_INT (-INTVAL (operands[2]));
6574           return "sub{w}\t{%2, %0|%0, %2}";
6575         }
6576       return "add{w}\t{%2, %0|%0, %2}";
6577     }
6578 }
6579   [(set (attr "type")
6580      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6581         (const_string "incdec")
6582         (const_string "alu")))
6583    (set_attr "mode" "HI")])
6584
6585 (define_insn "*addhi_3"
6586   [(set (reg FLAGS_REG)
6587         (compare (neg:HI (match_operand:HI 2 "general_operand" "rmni"))
6588                  (match_operand:HI 1 "nonimmediate_operand" "%0")))
6589    (clobber (match_scratch:HI 0 "=r"))]
6590   "ix86_match_ccmode (insn, CCZmode)
6591    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6592 {
6593   switch (get_attr_type (insn))
6594     {
6595     case TYPE_INCDEC:
6596       if (operands[2] == const1_rtx)
6597         return "inc{w}\t%0";
6598       else
6599         {
6600           gcc_assert (operands[2] == constm1_rtx);
6601           return "dec{w}\t%0";
6602         }
6603
6604     default:
6605       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6606          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6607       if (CONST_INT_P (operands[2])
6608           && (INTVAL (operands[2]) == 128
6609               || (INTVAL (operands[2]) < 0
6610                   && INTVAL (operands[2]) != -128)))
6611         {
6612           operands[2] = GEN_INT (-INTVAL (operands[2]));
6613           return "sub{w}\t{%2, %0|%0, %2}";
6614         }
6615       return "add{w}\t{%2, %0|%0, %2}";
6616     }
6617 }
6618   [(set (attr "type")
6619      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6620         (const_string "incdec")
6621         (const_string "alu")))
6622    (set_attr "mode" "HI")])
6623
6624 ; See comments above addsi_4 for details.
6625 (define_insn "*addhi_4"
6626   [(set (reg FLAGS_REG)
6627         (compare (match_operand:HI 1 "nonimmediate_operand" "0")
6628                  (match_operand:HI 2 "const_int_operand" "n")))
6629    (clobber (match_scratch:HI 0 "=rm"))]
6630   "ix86_match_ccmode (insn, CCGCmode)
6631    && (INTVAL (operands[2]) & 0xffff) != 0x8000"
6632 {
6633   switch (get_attr_type (insn))
6634     {
6635     case TYPE_INCDEC:
6636       if (operands[2] == constm1_rtx)
6637         return "inc{w}\t%0";
6638       else
6639         {
6640           gcc_assert (operands[2] == const1_rtx);
6641           return "dec{w}\t%0";
6642         }
6643
6644     default:
6645       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6646       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6647          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6648       if ((INTVAL (operands[2]) == -128
6649            || (INTVAL (operands[2]) > 0
6650                && INTVAL (operands[2]) != 128)))
6651         return "sub{w}\t{%2, %0|%0, %2}";
6652       operands[2] = GEN_INT (-INTVAL (operands[2]));
6653       return "add{w}\t{%2, %0|%0, %2}";
6654     }
6655 }
6656   [(set (attr "type")
6657      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6658         (const_string "incdec")
6659         (const_string "alu")))
6660    (set_attr "mode" "SI")])
6661
6662
6663 (define_insn "*addhi_5"
6664   [(set (reg FLAGS_REG)
6665         (compare
6666           (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
6667                    (match_operand:HI 2 "general_operand" "rmni"))
6668           (const_int 0)))
6669    (clobber (match_scratch:HI 0 "=r"))]
6670   "ix86_match_ccmode (insn, CCGOCmode)
6671    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6672 {
6673   switch (get_attr_type (insn))
6674     {
6675     case TYPE_INCDEC:
6676       if (operands[2] == const1_rtx)
6677         return "inc{w}\t%0";
6678       else
6679         {
6680           gcc_assert (operands[2] == constm1_rtx);
6681           return "dec{w}\t%0";
6682         }
6683
6684     default:
6685       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6686          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6687       if (CONST_INT_P (operands[2])
6688           && (INTVAL (operands[2]) == 128
6689               || (INTVAL (operands[2]) < 0
6690                   && INTVAL (operands[2]) != -128)))
6691         {
6692           operands[2] = GEN_INT (-INTVAL (operands[2]));
6693           return "sub{w}\t{%2, %0|%0, %2}";
6694         }
6695       return "add{w}\t{%2, %0|%0, %2}";
6696     }
6697 }
6698   [(set (attr "type")
6699      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6700         (const_string "incdec")
6701         (const_string "alu")))
6702    (set_attr "mode" "HI")])
6703
6704 (define_expand "addqi3"
6705   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6706                    (plus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6707                             (match_operand:QI 2 "general_operand" "")))
6708               (clobber (reg:CC FLAGS_REG))])]
6709   "TARGET_QIMODE_MATH"
6710   "ix86_expand_binary_operator (PLUS, QImode, operands); DONE;")
6711
6712 ;; %%% Potential partial reg stall on alternative 2.  What to do?
6713 (define_insn "*addqi_1_lea"
6714   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r,r")
6715         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,r")
6716                  (match_operand:QI 2 "general_operand" "qn,qmn,rn,ln")))
6717    (clobber (reg:CC FLAGS_REG))]
6718   "!TARGET_PARTIAL_REG_STALL
6719    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6720 {
6721   int widen = (which_alternative == 2);
6722   switch (get_attr_type (insn))
6723     {
6724     case TYPE_LEA:
6725       return "#";
6726     case TYPE_INCDEC:
6727       if (operands[2] == const1_rtx)
6728         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6729       else
6730         {
6731           gcc_assert (operands[2] == constm1_rtx);
6732           return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6733         }
6734
6735     default:
6736       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6737          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6738       if (CONST_INT_P (operands[2])
6739           && (INTVAL (operands[2]) == 128
6740               || (INTVAL (operands[2]) < 0
6741                   && INTVAL (operands[2]) != -128)))
6742         {
6743           operands[2] = GEN_INT (-INTVAL (operands[2]));
6744           if (widen)
6745             return "sub{l}\t{%2, %k0|%k0, %2}";
6746           else
6747             return "sub{b}\t{%2, %0|%0, %2}";
6748         }
6749       if (widen)
6750         return "add{l}\t{%k2, %k0|%k0, %k2}";
6751       else
6752         return "add{b}\t{%2, %0|%0, %2}";
6753     }
6754 }
6755   [(set (attr "type")
6756      (if_then_else (eq_attr "alternative" "3")
6757         (const_string "lea")
6758         (if_then_else (match_operand:QI 2 "incdec_operand" "")
6759            (const_string "incdec")
6760            (const_string "alu"))))
6761    (set_attr "mode" "QI,QI,SI,SI")])
6762
6763 (define_insn "*addqi_1"
6764   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
6765         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
6766                  (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
6767    (clobber (reg:CC FLAGS_REG))]
6768   "TARGET_PARTIAL_REG_STALL
6769    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6770 {
6771   int widen = (which_alternative == 2);
6772   switch (get_attr_type (insn))
6773     {
6774     case TYPE_INCDEC:
6775       if (operands[2] == const1_rtx)
6776         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6777       else
6778         {
6779           gcc_assert (operands[2] == constm1_rtx);
6780           return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6781         }
6782
6783     default:
6784       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6785          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6786       if (CONST_INT_P (operands[2])
6787           && (INTVAL (operands[2]) == 128
6788               || (INTVAL (operands[2]) < 0
6789                   && INTVAL (operands[2]) != -128)))
6790         {
6791           operands[2] = GEN_INT (-INTVAL (operands[2]));
6792           if (widen)
6793             return "sub{l}\t{%2, %k0|%k0, %2}";
6794           else
6795             return "sub{b}\t{%2, %0|%0, %2}";
6796         }
6797       if (widen)
6798         return "add{l}\t{%k2, %k0|%k0, %k2}";
6799       else
6800         return "add{b}\t{%2, %0|%0, %2}";
6801     }
6802 }
6803   [(set (attr "type")
6804      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6805         (const_string "incdec")
6806         (const_string "alu")))
6807    (set_attr "mode" "QI,QI,SI")])
6808
6809 (define_insn "*addqi_1_slp"
6810   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6811         (plus:QI (match_dup 0)
6812                  (match_operand:QI 1 "general_operand" "qn,qnm")))
6813    (clobber (reg:CC FLAGS_REG))]
6814   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6815    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
6816 {
6817   switch (get_attr_type (insn))
6818     {
6819     case TYPE_INCDEC:
6820       if (operands[1] == const1_rtx)
6821         return "inc{b}\t%0";
6822       else
6823         {
6824           gcc_assert (operands[1] == constm1_rtx);
6825           return "dec{b}\t%0";
6826         }
6827
6828     default:
6829       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.  */
6830       if (CONST_INT_P (operands[1])
6831           && INTVAL (operands[1]) < 0)
6832         {
6833           operands[1] = GEN_INT (-INTVAL (operands[1]));
6834           return "sub{b}\t{%1, %0|%0, %1}";
6835         }
6836       return "add{b}\t{%1, %0|%0, %1}";
6837     }
6838 }
6839   [(set (attr "type")
6840      (if_then_else (match_operand:QI 1 "incdec_operand" "")
6841         (const_string "incdec")
6842         (const_string "alu1")))
6843    (set (attr "memory")
6844      (if_then_else (match_operand 1 "memory_operand" "")
6845         (const_string "load")
6846         (const_string "none")))
6847    (set_attr "mode" "QI")])
6848
6849 (define_insn "*addqi_2"
6850   [(set (reg FLAGS_REG)
6851         (compare
6852           (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
6853                    (match_operand:QI 2 "general_operand" "qmni,qni"))
6854           (const_int 0)))
6855    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
6856         (plus:QI (match_dup 1) (match_dup 2)))]
6857   "ix86_match_ccmode (insn, CCGOCmode)
6858    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6859 {
6860   switch (get_attr_type (insn))
6861     {
6862     case TYPE_INCDEC:
6863       if (operands[2] == const1_rtx)
6864         return "inc{b}\t%0";
6865       else
6866         {
6867           gcc_assert (operands[2] == constm1_rtx
6868                       || (CONST_INT_P (operands[2])
6869                           && INTVAL (operands[2]) == 255));
6870           return "dec{b}\t%0";
6871         }
6872
6873     default:
6874       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
6875       if (CONST_INT_P (operands[2])
6876           && INTVAL (operands[2]) < 0)
6877         {
6878           operands[2] = GEN_INT (-INTVAL (operands[2]));
6879           return "sub{b}\t{%2, %0|%0, %2}";
6880         }
6881       return "add{b}\t{%2, %0|%0, %2}";
6882     }
6883 }
6884   [(set (attr "type")
6885      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6886         (const_string "incdec")
6887         (const_string "alu")))
6888    (set_attr "mode" "QI")])
6889
6890 (define_insn "*addqi_3"
6891   [(set (reg FLAGS_REG)
6892         (compare (neg:QI (match_operand:QI 2 "general_operand" "qmni"))
6893                  (match_operand:QI 1 "nonimmediate_operand" "%0")))
6894    (clobber (match_scratch:QI 0 "=q"))]
6895   "ix86_match_ccmode (insn, CCZmode)
6896    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6897 {
6898   switch (get_attr_type (insn))
6899     {
6900     case TYPE_INCDEC:
6901       if (operands[2] == const1_rtx)
6902         return "inc{b}\t%0";
6903       else
6904         {
6905           gcc_assert (operands[2] == constm1_rtx
6906                       || (CONST_INT_P (operands[2])
6907                           && INTVAL (operands[2]) == 255));
6908           return "dec{b}\t%0";
6909         }
6910
6911     default:
6912       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
6913       if (CONST_INT_P (operands[2])
6914           && INTVAL (operands[2]) < 0)
6915         {
6916           operands[2] = GEN_INT (-INTVAL (operands[2]));
6917           return "sub{b}\t{%2, %0|%0, %2}";
6918         }
6919       return "add{b}\t{%2, %0|%0, %2}";
6920     }
6921 }
6922   [(set (attr "type")
6923      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6924         (const_string "incdec")
6925         (const_string "alu")))
6926    (set_attr "mode" "QI")])
6927
6928 ; See comments above addsi_4 for details.
6929 (define_insn "*addqi_4"
6930   [(set (reg FLAGS_REG)
6931         (compare (match_operand:QI 1 "nonimmediate_operand" "0")
6932                  (match_operand:QI 2 "const_int_operand" "n")))
6933    (clobber (match_scratch:QI 0 "=qm"))]
6934   "ix86_match_ccmode (insn, CCGCmode)
6935    && (INTVAL (operands[2]) & 0xff) != 0x80"
6936 {
6937   switch (get_attr_type (insn))
6938     {
6939     case TYPE_INCDEC:
6940       if (operands[2] == constm1_rtx
6941           || (CONST_INT_P (operands[2])
6942               && INTVAL (operands[2]) == 255))
6943         return "inc{b}\t%0";
6944       else
6945         {
6946           gcc_assert (operands[2] == const1_rtx);
6947           return "dec{b}\t%0";
6948         }
6949
6950     default:
6951       gcc_assert (rtx_equal_p (operands[0], operands[1]));
6952       if (INTVAL (operands[2]) < 0)
6953         {
6954           operands[2] = GEN_INT (-INTVAL (operands[2]));
6955           return "add{b}\t{%2, %0|%0, %2}";
6956         }
6957       return "sub{b}\t{%2, %0|%0, %2}";
6958     }
6959 }
6960   [(set (attr "type")
6961      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6962         (const_string "incdec")
6963         (const_string "alu")))
6964    (set_attr "mode" "QI")])
6965
6966
6967 (define_insn "*addqi_5"
6968   [(set (reg FLAGS_REG)
6969         (compare
6970           (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6971                    (match_operand:QI 2 "general_operand" "qmni"))
6972           (const_int 0)))
6973    (clobber (match_scratch:QI 0 "=q"))]
6974   "ix86_match_ccmode (insn, CCGOCmode)
6975    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
6976 {
6977   switch (get_attr_type (insn))
6978     {
6979     case TYPE_INCDEC:
6980       if (operands[2] == const1_rtx)
6981         return "inc{b}\t%0";
6982       else
6983         {
6984           gcc_assert (operands[2] == constm1_rtx
6985                       || (CONST_INT_P (operands[2])
6986                           && INTVAL (operands[2]) == 255));
6987           return "dec{b}\t%0";
6988         }
6989
6990     default:
6991       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
6992       if (CONST_INT_P (operands[2])
6993           && INTVAL (operands[2]) < 0)
6994         {
6995           operands[2] = GEN_INT (-INTVAL (operands[2]));
6996           return "sub{b}\t{%2, %0|%0, %2}";
6997         }
6998       return "add{b}\t{%2, %0|%0, %2}";
6999     }
7000 }
7001   [(set (attr "type")
7002      (if_then_else (match_operand:QI 2 "incdec_operand" "")
7003         (const_string "incdec")
7004         (const_string "alu")))
7005    (set_attr "mode" "QI")])
7006
7007
7008 (define_insn "addqi_ext_1"
7009   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7010                          (const_int 8)
7011                          (const_int 8))
7012         (plus:SI
7013           (zero_extract:SI
7014             (match_operand 1 "ext_register_operand" "0")
7015             (const_int 8)
7016             (const_int 8))
7017           (match_operand:QI 2 "general_operand" "Qmn")))
7018    (clobber (reg:CC FLAGS_REG))]
7019   "!TARGET_64BIT"
7020 {
7021   switch (get_attr_type (insn))
7022     {
7023     case TYPE_INCDEC:
7024       if (operands[2] == const1_rtx)
7025         return "inc{b}\t%h0";
7026       else
7027         {
7028           gcc_assert (operands[2] == constm1_rtx
7029                       || (CONST_INT_P (operands[2])
7030                           && INTVAL (operands[2]) == 255));
7031           return "dec{b}\t%h0";
7032         }
7033
7034     default:
7035       return "add{b}\t{%2, %h0|%h0, %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 (define_insn "*addqi_ext_1_rex64"
7045   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7046                          (const_int 8)
7047                          (const_int 8))
7048         (plus:SI
7049           (zero_extract:SI
7050             (match_operand 1 "ext_register_operand" "0")
7051             (const_int 8)
7052             (const_int 8))
7053           (match_operand:QI 2 "nonmemory_operand" "Qn")))
7054    (clobber (reg:CC FLAGS_REG))]
7055   "TARGET_64BIT"
7056 {
7057   switch (get_attr_type (insn))
7058     {
7059     case TYPE_INCDEC:
7060       if (operands[2] == const1_rtx)
7061         return "inc{b}\t%h0";
7062       else
7063         {
7064           gcc_assert (operands[2] == constm1_rtx
7065                       || (CONST_INT_P (operands[2])
7066                           && INTVAL (operands[2]) == 255));
7067           return "dec{b}\t%h0";
7068         }
7069
7070     default:
7071       return "add{b}\t{%2, %h0|%h0, %2}";
7072     }
7073 }
7074   [(set (attr "type")
7075      (if_then_else (match_operand:QI 2 "incdec_operand" "")
7076         (const_string "incdec")
7077         (const_string "alu")))
7078    (set_attr "mode" "QI")])
7079
7080 (define_insn "*addqi_ext_2"
7081   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7082                          (const_int 8)
7083                          (const_int 8))
7084         (plus:SI
7085           (zero_extract:SI
7086             (match_operand 1 "ext_register_operand" "%0")
7087             (const_int 8)
7088             (const_int 8))
7089           (zero_extract:SI
7090             (match_operand 2 "ext_register_operand" "Q")
7091             (const_int 8)
7092             (const_int 8))))
7093    (clobber (reg:CC FLAGS_REG))]
7094   ""
7095   "add{b}\t{%h2, %h0|%h0, %h2}"
7096   [(set_attr "type" "alu")
7097    (set_attr "mode" "QI")])
7098
7099 ;; The patterns that match these are at the end of this file.
7100
7101 (define_expand "addxf3"
7102   [(set (match_operand:XF 0 "register_operand" "")
7103         (plus:XF (match_operand:XF 1 "register_operand" "")
7104                  (match_operand:XF 2 "register_operand" "")))]
7105   "TARGET_80387"
7106   "")
7107
7108 (define_expand "add<mode>3"
7109   [(set (match_operand:MODEF 0 "register_operand" "")
7110         (plus:MODEF (match_operand:MODEF 1 "register_operand" "")
7111                     (match_operand:MODEF 2 "nonimmediate_operand" "")))]
7112   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
7113   "")
7114 \f
7115 ;; Subtract instructions
7116
7117 ;; %%% splits for subditi3
7118
7119 (define_expand "subti3"
7120   [(parallel [(set (match_operand:TI 0 "nonimmediate_operand" "")
7121                    (minus:TI (match_operand:TI 1 "nonimmediate_operand" "")
7122                              (match_operand:TI 2 "x86_64_general_operand" "")))
7123               (clobber (reg:CC FLAGS_REG))])]
7124   "TARGET_64BIT"
7125   "ix86_expand_binary_operator (MINUS, TImode, operands); DONE;")
7126
7127 (define_insn "*subti3_1"
7128   [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o")
7129         (minus:TI (match_operand:TI 1 "nonimmediate_operand" "0,0")
7130                   (match_operand:TI 2 "x86_64_general_operand" "roe,re")))
7131    (clobber (reg:CC FLAGS_REG))]
7132   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, TImode, operands)"
7133   "#")
7134
7135 (define_split
7136   [(set (match_operand:TI 0 "nonimmediate_operand" "")
7137         (minus:TI (match_operand:TI 1 "nonimmediate_operand" "")
7138                   (match_operand:TI 2 "x86_64_general_operand" "")))
7139    (clobber (reg:CC FLAGS_REG))]
7140   "TARGET_64BIT && reload_completed"
7141   [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
7142               (set (match_dup 0) (minus:DI (match_dup 1) (match_dup 2)))])
7143    (parallel [(set (match_dup 3)
7144                    (minus:DI (match_dup 4)
7145                              (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
7146                                       (match_dup 5))))
7147               (clobber (reg:CC FLAGS_REG))])]
7148   "split_ti (operands+0, 1, operands+0, operands+3);
7149    split_ti (operands+1, 1, operands+1, operands+4);
7150    split_ti (operands+2, 1, operands+2, operands+5);")
7151
7152 ;; %%% splits for subsidi3
7153
7154 (define_expand "subdi3"
7155   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
7156                    (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
7157                              (match_operand:DI 2 "x86_64_general_operand" "")))
7158               (clobber (reg:CC FLAGS_REG))])]
7159   ""
7160   "ix86_expand_binary_operator (MINUS, DImode, operands); DONE;")
7161
7162 (define_insn "*subdi3_1"
7163   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
7164         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7165                   (match_operand:DI 2 "general_operand" "roiF,riF")))
7166    (clobber (reg:CC FLAGS_REG))]
7167   "!TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
7168   "#")
7169
7170 (define_split
7171   [(set (match_operand:DI 0 "nonimmediate_operand" "")
7172         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
7173                   (match_operand:DI 2 "general_operand" "")))
7174    (clobber (reg:CC FLAGS_REG))]
7175   "!TARGET_64BIT && reload_completed"
7176   [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
7177               (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 2)))])
7178    (parallel [(set (match_dup 3)
7179                    (minus:SI (match_dup 4)
7180                              (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
7181                                       (match_dup 5))))
7182               (clobber (reg:CC FLAGS_REG))])]
7183   "split_di (operands+0, 1, operands+0, operands+3);
7184    split_di (operands+1, 1, operands+1, operands+4);
7185    split_di (operands+2, 1, operands+2, operands+5);")
7186
7187 (define_insn "subdi3_carry_rex64"
7188   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7189           (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7190             (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
7191                (match_operand:DI 2 "x86_64_general_operand" "re,rm"))))
7192    (clobber (reg:CC FLAGS_REG))]
7193   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
7194   "sbb{q}\t{%2, %0|%0, %2}"
7195   [(set_attr "type" "alu")
7196    (set_attr "pent_pair" "pu")
7197    (set_attr "mode" "DI")])
7198
7199 (define_insn "*subdi_1_rex64"
7200   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7201         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7202                   (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
7203    (clobber (reg:CC FLAGS_REG))]
7204   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
7205   "sub{q}\t{%2, %0|%0, %2}"
7206   [(set_attr "type" "alu")
7207    (set_attr "mode" "DI")])
7208
7209 (define_insn "*subdi_2_rex64"
7210   [(set (reg FLAGS_REG)
7211         (compare
7212           (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
7213                     (match_operand:DI 2 "x86_64_general_operand" "re,rm"))
7214           (const_int 0)))
7215    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7216         (minus:DI (match_dup 1) (match_dup 2)))]
7217   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
7218    && ix86_binary_operator_ok (MINUS, DImode, operands)"
7219   "sub{q}\t{%2, %0|%0, %2}"
7220   [(set_attr "type" "alu")
7221    (set_attr "mode" "DI")])
7222
7223 (define_insn "*subdi_3_rex63"
7224   [(set (reg FLAGS_REG)
7225         (compare (match_operand:DI 1 "nonimmediate_operand" "0,0")
7226                  (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
7227    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
7228         (minus:DI (match_dup 1) (match_dup 2)))]
7229   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
7230    && ix86_binary_operator_ok (MINUS, SImode, operands)"
7231   "sub{q}\t{%2, %0|%0, %2}"
7232   [(set_attr "type" "alu")
7233    (set_attr "mode" "DI")])
7234
7235 (define_insn "subqi3_carry"
7236   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
7237           (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
7238             (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
7239                (match_operand:QI 2 "general_operand" "qi,qm"))))
7240    (clobber (reg:CC FLAGS_REG))]
7241   "ix86_binary_operator_ok (MINUS, QImode, operands)"
7242   "sbb{b}\t{%2, %0|%0, %2}"
7243   [(set_attr "type" "alu")
7244    (set_attr "pent_pair" "pu")
7245    (set_attr "mode" "QI")])
7246
7247 (define_insn "subhi3_carry"
7248   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7249           (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
7250             (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
7251                (match_operand:HI 2 "general_operand" "ri,rm"))))
7252    (clobber (reg:CC FLAGS_REG))]
7253   "ix86_binary_operator_ok (MINUS, HImode, operands)"
7254   "sbb{w}\t{%2, %0|%0, %2}"
7255   [(set_attr "type" "alu")
7256    (set_attr "pent_pair" "pu")
7257    (set_attr "mode" "HI")])
7258
7259 (define_insn "subsi3_carry"
7260   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7261           (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
7262             (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
7263                (match_operand:SI 2 "general_operand" "ri,rm"))))
7264    (clobber (reg:CC FLAGS_REG))]
7265   "ix86_binary_operator_ok (MINUS, SImode, operands)"
7266   "sbb{l}\t{%2, %0|%0, %2}"
7267   [(set_attr "type" "alu")
7268    (set_attr "pent_pair" "pu")
7269    (set_attr "mode" "SI")])
7270
7271 (define_insn "subsi3_carry_zext"
7272   [(set (match_operand:DI 0 "register_operand" "=r")
7273           (zero_extend:DI
7274             (minus:SI (match_operand:SI 1 "register_operand" "0")
7275               (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
7276                  (match_operand:SI 2 "general_operand" "g")))))
7277    (clobber (reg:CC FLAGS_REG))]
7278   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
7279   "sbb{l}\t{%2, %k0|%k0, %2}"
7280   [(set_attr "type" "alu")
7281    (set_attr "pent_pair" "pu")
7282    (set_attr "mode" "SI")])
7283
7284 (define_expand "subsi3"
7285   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
7286                    (minus:SI (match_operand:SI 1 "nonimmediate_operand" "")
7287                              (match_operand:SI 2 "general_operand" "")))
7288               (clobber (reg:CC FLAGS_REG))])]
7289   ""
7290   "ix86_expand_binary_operator (MINUS, SImode, operands); DONE;")
7291
7292 (define_insn "*subsi_1"
7293   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7294         (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
7295                   (match_operand:SI 2 "general_operand" "ri,rm")))
7296    (clobber (reg:CC FLAGS_REG))]
7297   "ix86_binary_operator_ok (MINUS, SImode, operands)"
7298   "sub{l}\t{%2, %0|%0, %2}"
7299   [(set_attr "type" "alu")
7300    (set_attr "mode" "SI")])
7301
7302 (define_insn "*subsi_1_zext"
7303   [(set (match_operand:DI 0 "register_operand" "=r")
7304         (zero_extend:DI
7305           (minus:SI (match_operand:SI 1 "register_operand" "0")
7306                     (match_operand:SI 2 "general_operand" "g"))))
7307    (clobber (reg:CC FLAGS_REG))]
7308   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
7309   "sub{l}\t{%2, %k0|%k0, %2}"
7310   [(set_attr "type" "alu")
7311    (set_attr "mode" "SI")])
7312
7313 (define_insn "*subsi_2"
7314   [(set (reg FLAGS_REG)
7315         (compare
7316           (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
7317                     (match_operand:SI 2 "general_operand" "ri,rm"))
7318           (const_int 0)))
7319    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7320         (minus:SI (match_dup 1) (match_dup 2)))]
7321   "ix86_match_ccmode (insn, CCGOCmode)
7322    && ix86_binary_operator_ok (MINUS, SImode, operands)"
7323   "sub{l}\t{%2, %0|%0, %2}"
7324   [(set_attr "type" "alu")
7325    (set_attr "mode" "SI")])
7326
7327 (define_insn "*subsi_2_zext"
7328   [(set (reg FLAGS_REG)
7329         (compare
7330           (minus:SI (match_operand:SI 1 "register_operand" "0")
7331                     (match_operand:SI 2 "general_operand" "g"))
7332           (const_int 0)))
7333    (set (match_operand:DI 0 "register_operand" "=r")
7334         (zero_extend:DI
7335           (minus:SI (match_dup 1)
7336                     (match_dup 2))))]
7337   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
7338    && ix86_binary_operator_ok (MINUS, SImode, operands)"
7339   "sub{l}\t{%2, %k0|%k0, %2}"
7340   [(set_attr "type" "alu")
7341    (set_attr "mode" "SI")])
7342
7343 (define_insn "*subsi_3"
7344   [(set (reg FLAGS_REG)
7345         (compare (match_operand:SI 1 "nonimmediate_operand" "0,0")
7346                  (match_operand:SI 2 "general_operand" "ri,rm")))
7347    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7348         (minus:SI (match_dup 1) (match_dup 2)))]
7349   "ix86_match_ccmode (insn, CCmode)
7350    && ix86_binary_operator_ok (MINUS, SImode, operands)"
7351   "sub{l}\t{%2, %0|%0, %2}"
7352   [(set_attr "type" "alu")
7353    (set_attr "mode" "SI")])
7354
7355 (define_insn "*subsi_3_zext"
7356   [(set (reg FLAGS_REG)
7357         (compare (match_operand:SI 1 "register_operand" "0")
7358                  (match_operand:SI 2 "general_operand" "g")))
7359    (set (match_operand:DI 0 "register_operand" "=r")
7360         (zero_extend:DI
7361           (minus:SI (match_dup 1)
7362                     (match_dup 2))))]
7363   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
7364    && ix86_binary_operator_ok (MINUS, SImode, operands)"
7365   "sub{l}\t{%2, %1|%1, %2}"
7366   [(set_attr "type" "alu")
7367    (set_attr "mode" "DI")])
7368
7369 (define_expand "subhi3"
7370   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
7371                    (minus:HI (match_operand:HI 1 "nonimmediate_operand" "")
7372                              (match_operand:HI 2 "general_operand" "")))
7373               (clobber (reg:CC FLAGS_REG))])]
7374   "TARGET_HIMODE_MATH"
7375   "ix86_expand_binary_operator (MINUS, HImode, operands); DONE;")
7376
7377 (define_insn "*subhi_1"
7378   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7379         (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
7380                   (match_operand:HI 2 "general_operand" "ri,rm")))
7381    (clobber (reg:CC FLAGS_REG))]
7382   "ix86_binary_operator_ok (MINUS, HImode, operands)"
7383   "sub{w}\t{%2, %0|%0, %2}"
7384   [(set_attr "type" "alu")
7385    (set_attr "mode" "HI")])
7386
7387 (define_insn "*subhi_2"
7388   [(set (reg FLAGS_REG)
7389         (compare
7390           (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
7391                     (match_operand:HI 2 "general_operand" "ri,rm"))
7392           (const_int 0)))
7393    (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7394         (minus:HI (match_dup 1) (match_dup 2)))]
7395   "ix86_match_ccmode (insn, CCGOCmode)
7396    && ix86_binary_operator_ok (MINUS, HImode, operands)"
7397   "sub{w}\t{%2, %0|%0, %2}"
7398   [(set_attr "type" "alu")
7399    (set_attr "mode" "HI")])
7400
7401 (define_insn "*subhi_3"
7402   [(set (reg FLAGS_REG)
7403         (compare (match_operand:HI 1 "nonimmediate_operand" "0,0")
7404                  (match_operand:HI 2 "general_operand" "ri,rm")))
7405    (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
7406         (minus:HI (match_dup 1) (match_dup 2)))]
7407   "ix86_match_ccmode (insn, CCmode)
7408    && ix86_binary_operator_ok (MINUS, HImode, operands)"
7409   "sub{w}\t{%2, %0|%0, %2}"
7410   [(set_attr "type" "alu")
7411    (set_attr "mode" "HI")])
7412
7413 (define_expand "subqi3"
7414   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
7415                    (minus:QI (match_operand:QI 1 "nonimmediate_operand" "")
7416                              (match_operand:QI 2 "general_operand" "")))
7417               (clobber (reg:CC FLAGS_REG))])]
7418   "TARGET_QIMODE_MATH"
7419   "ix86_expand_binary_operator (MINUS, QImode, operands); DONE;")
7420
7421 (define_insn "*subqi_1"
7422   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
7423         (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
7424                   (match_operand:QI 2 "general_operand" "qn,qmn")))
7425    (clobber (reg:CC FLAGS_REG))]
7426   "ix86_binary_operator_ok (MINUS, QImode, operands)"
7427   "sub{b}\t{%2, %0|%0, %2}"
7428   [(set_attr "type" "alu")
7429    (set_attr "mode" "QI")])
7430
7431 (define_insn "*subqi_1_slp"
7432   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
7433         (minus:QI (match_dup 0)
7434                   (match_operand:QI 1 "general_operand" "qn,qmn")))
7435    (clobber (reg:CC FLAGS_REG))]
7436   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
7437    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
7438   "sub{b}\t{%1, %0|%0, %1}"
7439   [(set_attr "type" "alu1")
7440    (set_attr "mode" "QI")])
7441
7442 (define_insn "*subqi_2"
7443   [(set (reg FLAGS_REG)
7444         (compare
7445           (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
7446                     (match_operand:QI 2 "general_operand" "qi,qm"))
7447           (const_int 0)))
7448    (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
7449         (minus:HI (match_dup 1) (match_dup 2)))]
7450   "ix86_match_ccmode (insn, CCGOCmode)
7451    && ix86_binary_operator_ok (MINUS, QImode, operands)"
7452   "sub{b}\t{%2, %0|%0, %2}"
7453   [(set_attr "type" "alu")
7454    (set_attr "mode" "QI")])
7455
7456 (define_insn "*subqi_3"
7457   [(set (reg FLAGS_REG)
7458         (compare (match_operand:QI 1 "nonimmediate_operand" "0,0")
7459                  (match_operand:QI 2 "general_operand" "qi,qm")))
7460    (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
7461         (minus:HI (match_dup 1) (match_dup 2)))]
7462   "ix86_match_ccmode (insn, CCmode)
7463    && ix86_binary_operator_ok (MINUS, QImode, operands)"
7464   "sub{b}\t{%2, %0|%0, %2}"
7465   [(set_attr "type" "alu")
7466    (set_attr "mode" "QI")])
7467
7468 ;; The patterns that match these are at the end of this file.
7469
7470 (define_expand "subxf3"
7471   [(set (match_operand:XF 0 "register_operand" "")
7472         (minus:XF (match_operand:XF 1 "register_operand" "")
7473                   (match_operand:XF 2 "register_operand" "")))]
7474   "TARGET_80387"
7475   "")
7476
7477 (define_expand "sub<mode>3"
7478   [(set (match_operand:MODEF 0 "register_operand" "")
7479         (minus:MODEF (match_operand:MODEF 1 "register_operand" "")
7480                      (match_operand:MODEF 2 "nonimmediate_operand" "")))]
7481   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
7482   "")
7483 \f
7484 ;; Multiply instructions
7485
7486 (define_expand "muldi3"
7487   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7488                    (mult:DI (match_operand:DI 1 "register_operand" "")
7489                             (match_operand:DI 2 "x86_64_general_operand" "")))
7490               (clobber (reg:CC FLAGS_REG))])]
7491   "TARGET_64BIT"
7492   "")
7493
7494 ;; On AMDFAM10
7495 ;; IMUL reg64, reg64, imm8      Direct
7496 ;; IMUL reg64, mem64, imm8      VectorPath
7497 ;; IMUL reg64, reg64, imm32     Direct
7498 ;; IMUL reg64, mem64, imm32     VectorPath
7499 ;; IMUL reg64, reg64            Direct
7500 ;; IMUL reg64, mem64            Direct
7501
7502 (define_insn "*muldi3_1_rex64"
7503   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
7504         (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%rm,rm,0")
7505                  (match_operand:DI 2 "x86_64_general_operand" "K,e,mr")))
7506    (clobber (reg:CC FLAGS_REG))]
7507   "TARGET_64BIT
7508    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7509   "@
7510    imul{q}\t{%2, %1, %0|%0, %1, %2}
7511    imul{q}\t{%2, %1, %0|%0, %1, %2}
7512    imul{q}\t{%2, %0|%0, %2}"
7513   [(set_attr "type" "imul")
7514    (set_attr "prefix_0f" "0,0,1")
7515    (set (attr "athlon_decode")
7516         (cond [(eq_attr "cpu" "athlon")
7517                   (const_string "vector")
7518                (eq_attr "alternative" "1")
7519                   (const_string "vector")
7520                (and (eq_attr "alternative" "2")
7521                     (match_operand 1 "memory_operand" ""))
7522                   (const_string "vector")]
7523               (const_string "direct")))
7524    (set (attr "amdfam10_decode")
7525         (cond [(and (eq_attr "alternative" "0,1")
7526                     (match_operand 1 "memory_operand" ""))
7527                   (const_string "vector")]
7528               (const_string "direct")))
7529    (set_attr "mode" "DI")])
7530
7531 (define_expand "mulsi3"
7532   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7533                    (mult:SI (match_operand:SI 1 "register_operand" "")
7534                             (match_operand:SI 2 "general_operand" "")))
7535               (clobber (reg:CC FLAGS_REG))])]
7536   ""
7537   "")
7538
7539 ;; On AMDFAM10
7540 ;; IMUL reg32, reg32, imm8      Direct
7541 ;; IMUL reg32, mem32, imm8      VectorPath
7542 ;; IMUL reg32, reg32, imm32     Direct
7543 ;; IMUL reg32, mem32, imm32     VectorPath
7544 ;; IMUL reg32, reg32            Direct
7545 ;; IMUL reg32, mem32            Direct
7546
7547 (define_insn "*mulsi3_1"
7548   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
7549         (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
7550                  (match_operand:SI 2 "general_operand" "K,i,mr")))
7551    (clobber (reg:CC FLAGS_REG))]
7552   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
7553   "@
7554    imul{l}\t{%2, %1, %0|%0, %1, %2}
7555    imul{l}\t{%2, %1, %0|%0, %1, %2}
7556    imul{l}\t{%2, %0|%0, %2}"
7557   [(set_attr "type" "imul")
7558    (set_attr "prefix_0f" "0,0,1")
7559    (set (attr "athlon_decode")
7560         (cond [(eq_attr "cpu" "athlon")
7561                   (const_string "vector")
7562                (eq_attr "alternative" "1")
7563                   (const_string "vector")
7564                (and (eq_attr "alternative" "2")
7565                     (match_operand 1 "memory_operand" ""))
7566                   (const_string "vector")]
7567               (const_string "direct")))
7568    (set (attr "amdfam10_decode")
7569         (cond [(and (eq_attr "alternative" "0,1")
7570                     (match_operand 1 "memory_operand" ""))
7571                   (const_string "vector")]
7572               (const_string "direct")))
7573    (set_attr "mode" "SI")])
7574
7575 (define_insn "*mulsi3_1_zext"
7576   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
7577         (zero_extend:DI
7578           (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
7579                    (match_operand:SI 2 "general_operand" "K,i,mr"))))
7580    (clobber (reg:CC FLAGS_REG))]
7581   "TARGET_64BIT
7582    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7583   "@
7584    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
7585    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
7586    imul{l}\t{%2, %k0|%k0, %2}"
7587   [(set_attr "type" "imul")
7588    (set_attr "prefix_0f" "0,0,1")
7589    (set (attr "athlon_decode")
7590         (cond [(eq_attr "cpu" "athlon")
7591                   (const_string "vector")
7592                (eq_attr "alternative" "1")
7593                   (const_string "vector")
7594                (and (eq_attr "alternative" "2")
7595                     (match_operand 1 "memory_operand" ""))
7596                   (const_string "vector")]
7597               (const_string "direct")))
7598    (set (attr "amdfam10_decode")
7599         (cond [(and (eq_attr "alternative" "0,1")
7600                     (match_operand 1 "memory_operand" ""))
7601                   (const_string "vector")]
7602               (const_string "direct")))
7603    (set_attr "mode" "SI")])
7604
7605 (define_expand "mulhi3"
7606   [(parallel [(set (match_operand:HI 0 "register_operand" "")
7607                    (mult:HI (match_operand:HI 1 "register_operand" "")
7608                             (match_operand:HI 2 "general_operand" "")))
7609               (clobber (reg:CC FLAGS_REG))])]
7610   "TARGET_HIMODE_MATH"
7611   "")
7612
7613 ;; On AMDFAM10
7614 ;; IMUL reg16, reg16, imm8      VectorPath
7615 ;; IMUL reg16, mem16, imm8      VectorPath
7616 ;; IMUL reg16, reg16, imm16     VectorPath
7617 ;; IMUL reg16, mem16, imm16     VectorPath
7618 ;; IMUL reg16, reg16            Direct
7619 ;; IMUL reg16, mem16            Direct
7620 (define_insn "*mulhi3_1"
7621   [(set (match_operand:HI 0 "register_operand" "=r,r,r")
7622         (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
7623                  (match_operand:HI 2 "general_operand" "K,i,mr")))
7624    (clobber (reg:CC FLAGS_REG))]
7625   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
7626   "@
7627    imul{w}\t{%2, %1, %0|%0, %1, %2}
7628    imul{w}\t{%2, %1, %0|%0, %1, %2}
7629    imul{w}\t{%2, %0|%0, %2}"
7630   [(set_attr "type" "imul")
7631    (set_attr "prefix_0f" "0,0,1")
7632    (set (attr "athlon_decode")
7633         (cond [(eq_attr "cpu" "athlon")
7634                   (const_string "vector")
7635                (eq_attr "alternative" "1,2")
7636                   (const_string "vector")]
7637               (const_string "direct")))
7638    (set (attr "amdfam10_decode")
7639         (cond [(eq_attr "alternative" "0,1")
7640                   (const_string "vector")]
7641               (const_string "direct")))
7642    (set_attr "mode" "HI")])
7643
7644 (define_expand "mulqi3"
7645   [(parallel [(set (match_operand:QI 0 "register_operand" "")
7646                    (mult:QI (match_operand:QI 1 "nonimmediate_operand" "")
7647                             (match_operand:QI 2 "register_operand" "")))
7648               (clobber (reg:CC FLAGS_REG))])]
7649   "TARGET_QIMODE_MATH"
7650   "")
7651
7652 ;;On AMDFAM10
7653 ;; MUL reg8     Direct
7654 ;; MUL mem8     Direct
7655
7656 (define_insn "*mulqi3_1"
7657   [(set (match_operand:QI 0 "register_operand" "=a")
7658         (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
7659                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
7660    (clobber (reg:CC FLAGS_REG))]
7661   "TARGET_QIMODE_MATH
7662    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7663   "mul{b}\t%2"
7664   [(set_attr "type" "imul")
7665    (set_attr "length_immediate" "0")
7666    (set (attr "athlon_decode")
7667      (if_then_else (eq_attr "cpu" "athlon")
7668         (const_string "vector")
7669         (const_string "direct")))
7670    (set_attr "amdfam10_decode" "direct")
7671    (set_attr "mode" "QI")])
7672
7673 (define_expand "umulqihi3"
7674   [(parallel [(set (match_operand:HI 0 "register_operand" "")
7675                    (mult:HI (zero_extend:HI
7676                               (match_operand:QI 1 "nonimmediate_operand" ""))
7677                             (zero_extend:HI
7678                               (match_operand:QI 2 "register_operand" ""))))
7679               (clobber (reg:CC FLAGS_REG))])]
7680   "TARGET_QIMODE_MATH"
7681   "")
7682
7683 (define_insn "*umulqihi3_1"
7684   [(set (match_operand:HI 0 "register_operand" "=a")
7685         (mult:HI (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
7686                  (zero_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
7687    (clobber (reg:CC FLAGS_REG))]
7688   "TARGET_QIMODE_MATH
7689    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7690   "mul{b}\t%2"
7691   [(set_attr "type" "imul")
7692    (set_attr "length_immediate" "0")
7693    (set (attr "athlon_decode")
7694      (if_then_else (eq_attr "cpu" "athlon")
7695         (const_string "vector")
7696         (const_string "direct")))
7697    (set_attr "amdfam10_decode" "direct")
7698    (set_attr "mode" "QI")])
7699
7700 (define_expand "mulqihi3"
7701   [(parallel [(set (match_operand:HI 0 "register_operand" "")
7702                    (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))
7703                             (sign_extend:HI (match_operand:QI 2 "register_operand" ""))))
7704               (clobber (reg:CC FLAGS_REG))])]
7705   "TARGET_QIMODE_MATH"
7706   "")
7707
7708 (define_insn "*mulqihi3_insn"
7709   [(set (match_operand:HI 0 "register_operand" "=a")
7710         (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
7711                  (sign_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
7712    (clobber (reg:CC FLAGS_REG))]
7713   "TARGET_QIMODE_MATH
7714    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7715   "imul{b}\t%2"
7716   [(set_attr "type" "imul")
7717    (set_attr "length_immediate" "0")
7718    (set (attr "athlon_decode")
7719      (if_then_else (eq_attr "cpu" "athlon")
7720         (const_string "vector")
7721         (const_string "direct")))
7722    (set_attr "amdfam10_decode" "direct")
7723    (set_attr "mode" "QI")])
7724
7725 (define_expand "umulditi3"
7726   [(parallel [(set (match_operand:TI 0 "register_operand" "")
7727                    (mult:TI (zero_extend:TI
7728                               (match_operand:DI 1 "nonimmediate_operand" ""))
7729                             (zero_extend:TI
7730                               (match_operand:DI 2 "register_operand" ""))))
7731               (clobber (reg:CC FLAGS_REG))])]
7732   "TARGET_64BIT"
7733   "")
7734
7735 (define_insn "*umulditi3_insn"
7736   [(set (match_operand:TI 0 "register_operand" "=A")
7737         (mult:TI (zero_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
7738                  (zero_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
7739    (clobber (reg:CC FLAGS_REG))]
7740   "TARGET_64BIT
7741    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7742   "mul{q}\t%2"
7743   [(set_attr "type" "imul")
7744    (set_attr "length_immediate" "0")
7745    (set (attr "athlon_decode")
7746      (if_then_else (eq_attr "cpu" "athlon")
7747         (const_string "vector")
7748         (const_string "double")))
7749    (set_attr "amdfam10_decode" "double")
7750    (set_attr "mode" "DI")])
7751
7752 ;; We can't use this pattern in 64bit mode, since it results in two separate 32bit registers
7753 (define_expand "umulsidi3"
7754   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7755                    (mult:DI (zero_extend:DI
7756                               (match_operand:SI 1 "nonimmediate_operand" ""))
7757                             (zero_extend:DI
7758                               (match_operand:SI 2 "register_operand" ""))))
7759               (clobber (reg:CC FLAGS_REG))])]
7760   "!TARGET_64BIT"
7761   "")
7762
7763 (define_insn "*umulsidi3_insn"
7764   [(set (match_operand:DI 0 "register_operand" "=A")
7765         (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7766                  (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7767    (clobber (reg:CC FLAGS_REG))]
7768   "!TARGET_64BIT
7769    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7770   "mul{l}\t%2"
7771   [(set_attr "type" "imul")
7772    (set_attr "length_immediate" "0")
7773    (set (attr "athlon_decode")
7774      (if_then_else (eq_attr "cpu" "athlon")
7775         (const_string "vector")
7776         (const_string "double")))
7777    (set_attr "amdfam10_decode" "double")
7778    (set_attr "mode" "SI")])
7779
7780 (define_expand "mulditi3"
7781   [(parallel [(set (match_operand:TI 0 "register_operand" "")
7782                    (mult:TI (sign_extend:TI
7783                               (match_operand:DI 1 "nonimmediate_operand" ""))
7784                             (sign_extend:TI
7785                               (match_operand:DI 2 "register_operand" ""))))
7786               (clobber (reg:CC FLAGS_REG))])]
7787   "TARGET_64BIT"
7788   "")
7789
7790 (define_insn "*mulditi3_insn"
7791   [(set (match_operand:TI 0 "register_operand" "=A")
7792         (mult:TI (sign_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
7793                  (sign_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
7794    (clobber (reg:CC FLAGS_REG))]
7795   "TARGET_64BIT
7796    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7797   "imul{q}\t%2"
7798   [(set_attr "type" "imul")
7799    (set_attr "length_immediate" "0")
7800    (set (attr "athlon_decode")
7801      (if_then_else (eq_attr "cpu" "athlon")
7802         (const_string "vector")
7803         (const_string "double")))
7804    (set_attr "amdfam10_decode" "double")
7805    (set_attr "mode" "DI")])
7806
7807 (define_expand "mulsidi3"
7808   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7809                    (mult:DI (sign_extend:DI
7810                               (match_operand:SI 1 "nonimmediate_operand" ""))
7811                             (sign_extend:DI
7812                               (match_operand:SI 2 "register_operand" ""))))
7813               (clobber (reg:CC FLAGS_REG))])]
7814   "!TARGET_64BIT"
7815   "")
7816
7817 (define_insn "*mulsidi3_insn"
7818   [(set (match_operand:DI 0 "register_operand" "=A")
7819         (mult:DI (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7820                  (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7821    (clobber (reg:CC FLAGS_REG))]
7822   "!TARGET_64BIT
7823    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7824   "imul{l}\t%2"
7825   [(set_attr "type" "imul")
7826    (set_attr "length_immediate" "0")
7827    (set (attr "athlon_decode")
7828      (if_then_else (eq_attr "cpu" "athlon")
7829         (const_string "vector")
7830         (const_string "double")))
7831    (set_attr "amdfam10_decode" "double")
7832    (set_attr "mode" "SI")])
7833
7834 (define_expand "umuldi3_highpart"
7835   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7836                    (truncate:DI
7837                      (lshiftrt:TI
7838                        (mult:TI (zero_extend:TI
7839                                   (match_operand:DI 1 "nonimmediate_operand" ""))
7840                                 (zero_extend:TI
7841                                   (match_operand:DI 2 "register_operand" "")))
7842                        (const_int 64))))
7843               (clobber (match_scratch:DI 3 ""))
7844               (clobber (reg:CC FLAGS_REG))])]
7845   "TARGET_64BIT"
7846   "")
7847
7848 (define_insn "*umuldi3_highpart_rex64"
7849   [(set (match_operand:DI 0 "register_operand" "=d")
7850         (truncate:DI
7851           (lshiftrt:TI
7852             (mult:TI (zero_extend:TI
7853                        (match_operand:DI 1 "nonimmediate_operand" "%a"))
7854                      (zero_extend:TI
7855                        (match_operand:DI 2 "nonimmediate_operand" "rm")))
7856             (const_int 64))))
7857    (clobber (match_scratch:DI 3 "=1"))
7858    (clobber (reg:CC FLAGS_REG))]
7859   "TARGET_64BIT
7860    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7861   "mul{q}\t%2"
7862   [(set_attr "type" "imul")
7863    (set_attr "length_immediate" "0")
7864    (set (attr "athlon_decode")
7865      (if_then_else (eq_attr "cpu" "athlon")
7866         (const_string "vector")
7867         (const_string "double")))
7868    (set_attr "amdfam10_decode" "double")
7869    (set_attr "mode" "DI")])
7870
7871 (define_expand "umulsi3_highpart"
7872   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7873                    (truncate:SI
7874                      (lshiftrt:DI
7875                        (mult:DI (zero_extend:DI
7876                                   (match_operand:SI 1 "nonimmediate_operand" ""))
7877                                 (zero_extend:DI
7878                                   (match_operand:SI 2 "register_operand" "")))
7879                        (const_int 32))))
7880               (clobber (match_scratch:SI 3 ""))
7881               (clobber (reg:CC FLAGS_REG))])]
7882   ""
7883   "")
7884
7885 (define_insn "*umulsi3_highpart_insn"
7886   [(set (match_operand:SI 0 "register_operand" "=d")
7887         (truncate:SI
7888           (lshiftrt:DI
7889             (mult:DI (zero_extend:DI
7890                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7891                      (zero_extend:DI
7892                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7893             (const_int 32))))
7894    (clobber (match_scratch:SI 3 "=1"))
7895    (clobber (reg:CC FLAGS_REG))]
7896   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
7897   "mul{l}\t%2"
7898   [(set_attr "type" "imul")
7899    (set_attr "length_immediate" "0")
7900    (set (attr "athlon_decode")
7901      (if_then_else (eq_attr "cpu" "athlon")
7902         (const_string "vector")
7903         (const_string "double")))
7904    (set_attr "amdfam10_decode" "double")
7905    (set_attr "mode" "SI")])
7906
7907 (define_insn "*umulsi3_highpart_zext"
7908   [(set (match_operand:DI 0 "register_operand" "=d")
7909         (zero_extend:DI (truncate:SI
7910           (lshiftrt:DI
7911             (mult:DI (zero_extend:DI
7912                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7913                      (zero_extend:DI
7914                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7915             (const_int 32)))))
7916    (clobber (match_scratch:SI 3 "=1"))
7917    (clobber (reg:CC FLAGS_REG))]
7918   "TARGET_64BIT
7919    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7920   "mul{l}\t%2"
7921   [(set_attr "type" "imul")
7922    (set_attr "length_immediate" "0")
7923    (set (attr "athlon_decode")
7924      (if_then_else (eq_attr "cpu" "athlon")
7925         (const_string "vector")
7926         (const_string "double")))
7927    (set_attr "amdfam10_decode" "double")
7928    (set_attr "mode" "SI")])
7929
7930 (define_expand "smuldi3_highpart"
7931   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7932                    (truncate:DI
7933                      (lshiftrt:TI
7934                        (mult:TI (sign_extend:TI
7935                                   (match_operand:DI 1 "nonimmediate_operand" ""))
7936                                 (sign_extend:TI
7937                                   (match_operand:DI 2 "register_operand" "")))
7938                        (const_int 64))))
7939               (clobber (match_scratch:DI 3 ""))
7940               (clobber (reg:CC FLAGS_REG))])]
7941   "TARGET_64BIT"
7942   "")
7943
7944 (define_insn "*smuldi3_highpart_rex64"
7945   [(set (match_operand:DI 0 "register_operand" "=d")
7946         (truncate:DI
7947           (lshiftrt:TI
7948             (mult:TI (sign_extend:TI
7949                        (match_operand:DI 1 "nonimmediate_operand" "%a"))
7950                      (sign_extend:TI
7951                        (match_operand:DI 2 "nonimmediate_operand" "rm")))
7952             (const_int 64))))
7953    (clobber (match_scratch:DI 3 "=1"))
7954    (clobber (reg:CC FLAGS_REG))]
7955   "TARGET_64BIT
7956    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
7957   "imul{q}\t%2"
7958   [(set_attr "type" "imul")
7959    (set (attr "athlon_decode")
7960      (if_then_else (eq_attr "cpu" "athlon")
7961         (const_string "vector")
7962         (const_string "double")))
7963    (set_attr "amdfam10_decode" "double")
7964    (set_attr "mode" "DI")])
7965
7966 (define_expand "smulsi3_highpart"
7967   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7968                    (truncate:SI
7969                      (lshiftrt:DI
7970                        (mult:DI (sign_extend:DI
7971                                   (match_operand:SI 1 "nonimmediate_operand" ""))
7972                                 (sign_extend:DI
7973                                   (match_operand:SI 2 "register_operand" "")))
7974                        (const_int 32))))
7975               (clobber (match_scratch:SI 3 ""))
7976               (clobber (reg:CC FLAGS_REG))])]
7977   ""
7978   "")
7979
7980 (define_insn "*smulsi3_highpart_insn"
7981   [(set (match_operand:SI 0 "register_operand" "=d")
7982         (truncate:SI
7983           (lshiftrt:DI
7984             (mult:DI (sign_extend:DI
7985                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7986                      (sign_extend:DI
7987                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7988             (const_int 32))))
7989    (clobber (match_scratch:SI 3 "=1"))
7990    (clobber (reg:CC FLAGS_REG))]
7991   "!(MEM_P (operands[1]) && MEM_P (operands[2]))"
7992   "imul{l}\t%2"
7993   [(set_attr "type" "imul")
7994    (set (attr "athlon_decode")
7995      (if_then_else (eq_attr "cpu" "athlon")
7996         (const_string "vector")
7997         (const_string "double")))
7998    (set_attr "amdfam10_decode" "double")
7999    (set_attr "mode" "SI")])
8000
8001 (define_insn "*smulsi3_highpart_zext"
8002   [(set (match_operand:DI 0 "register_operand" "=d")
8003         (zero_extend:DI (truncate:SI
8004           (lshiftrt:DI
8005             (mult:DI (sign_extend:DI
8006                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
8007                      (sign_extend:DI
8008                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
8009             (const_int 32)))))
8010    (clobber (match_scratch:SI 3 "=1"))
8011    (clobber (reg:CC FLAGS_REG))]
8012   "TARGET_64BIT
8013    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
8014   "imul{l}\t%2"
8015   [(set_attr "type" "imul")
8016    (set (attr "athlon_decode")
8017      (if_then_else (eq_attr "cpu" "athlon")
8018         (const_string "vector")
8019         (const_string "double")))
8020    (set_attr "amdfam10_decode" "double")
8021    (set_attr "mode" "SI")])
8022
8023 ;; The patterns that match these are at the end of this file.
8024
8025 (define_expand "mulxf3"
8026   [(set (match_operand:XF 0 "register_operand" "")
8027         (mult:XF (match_operand:XF 1 "register_operand" "")
8028                  (match_operand:XF 2 "register_operand" "")))]
8029   "TARGET_80387"
8030   "")
8031
8032 (define_expand "mul<mode>3"
8033   [(set (match_operand:MODEF 0 "register_operand" "")
8034         (mult:MODEF (match_operand:MODEF 1 "register_operand" "")
8035                     (match_operand:MODEF 2 "nonimmediate_operand" "")))]
8036   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
8037   "")
8038
8039 ;; SSE5 scalar multiply/add instructions are defined in sse.md.
8040
8041 \f
8042 ;; Divide instructions
8043
8044 (define_insn "divqi3"
8045   [(set (match_operand:QI 0 "register_operand" "=a")
8046         (div:QI (match_operand:HI 1 "register_operand" "0")
8047                 (match_operand:QI 2 "nonimmediate_operand" "qm")))
8048    (clobber (reg:CC FLAGS_REG))]
8049   "TARGET_QIMODE_MATH"
8050   "idiv{b}\t%2"
8051   [(set_attr "type" "idiv")
8052    (set_attr "mode" "QI")])
8053
8054 (define_insn "udivqi3"
8055   [(set (match_operand:QI 0 "register_operand" "=a")
8056         (udiv:QI (match_operand:HI 1 "register_operand" "0")
8057                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
8058    (clobber (reg:CC FLAGS_REG))]
8059   "TARGET_QIMODE_MATH"
8060   "div{b}\t%2"
8061   [(set_attr "type" "idiv")
8062    (set_attr "mode" "QI")])
8063
8064 ;; The patterns that match these are at the end of this file.
8065
8066 (define_expand "divxf3"
8067   [(set (match_operand:XF 0 "register_operand" "")
8068         (div:XF (match_operand:XF 1 "register_operand" "")
8069                 (match_operand:XF 2 "register_operand" "")))]
8070   "TARGET_80387"
8071   "")
8072
8073 (define_expand "divdf3"
8074   [(set (match_operand:DF 0 "register_operand" "")
8075         (div:DF (match_operand:DF 1 "register_operand" "")
8076                 (match_operand:DF 2 "nonimmediate_operand" "")))]
8077    "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
8078    "")
8079
8080 (define_expand "divsf3"
8081   [(set (match_operand:SF 0 "register_operand" "")
8082         (div:SF (match_operand:SF 1 "register_operand" "")
8083                 (match_operand:SF 2 "nonimmediate_operand" "")))]
8084   "TARGET_80387 || TARGET_SSE_MATH"
8085 {
8086   if (TARGET_SSE_MATH && TARGET_RECIP && !optimize_size
8087       && flag_finite_math_only && !flag_trapping_math
8088       && flag_unsafe_math_optimizations)
8089     {
8090       ix86_emit_swdivsf (operands[0], operands[1],
8091                          operands[2], SFmode);
8092       DONE;
8093     }
8094 })
8095 \f
8096 ;; Remainder instructions.
8097
8098 (define_expand "divmoddi4"
8099   [(parallel [(set (match_operand:DI 0 "register_operand" "")
8100                    (div:DI (match_operand:DI 1 "register_operand" "")
8101                            (match_operand:DI 2 "nonimmediate_operand" "")))
8102               (set (match_operand:DI 3 "register_operand" "")
8103                    (mod:DI (match_dup 1) (match_dup 2)))
8104               (clobber (reg:CC FLAGS_REG))])]
8105   "TARGET_64BIT"
8106   "")
8107
8108 ;; Allow to come the parameter in eax or edx to avoid extra moves.
8109 ;; Penalize eax case slightly because it results in worse scheduling
8110 ;; of code.
8111 (define_insn "*divmoddi4_nocltd_rex64"
8112   [(set (match_operand:DI 0 "register_operand" "=&a,?a")
8113         (div:DI (match_operand:DI 2 "register_operand" "1,0")
8114                 (match_operand:DI 3 "nonimmediate_operand" "rm,rm")))
8115    (set (match_operand:DI 1 "register_operand" "=&d,&d")
8116         (mod:DI (match_dup 2) (match_dup 3)))
8117    (clobber (reg:CC FLAGS_REG))]
8118   "TARGET_64BIT && !optimize_size && !TARGET_USE_CLTD"
8119   "#"
8120   [(set_attr "type" "multi")])
8121
8122 (define_insn "*divmoddi4_cltd_rex64"
8123   [(set (match_operand:DI 0 "register_operand" "=a")
8124         (div:DI (match_operand:DI 2 "register_operand" "a")
8125                 (match_operand:DI 3 "nonimmediate_operand" "rm")))
8126    (set (match_operand:DI 1 "register_operand" "=&d")
8127         (mod:DI (match_dup 2) (match_dup 3)))
8128    (clobber (reg:CC FLAGS_REG))]
8129   "TARGET_64BIT && (optimize_size || TARGET_USE_CLTD)"
8130   "#"
8131   [(set_attr "type" "multi")])
8132
8133 (define_insn "*divmoddi_noext_rex64"
8134   [(set (match_operand:DI 0 "register_operand" "=a")
8135         (div:DI (match_operand:DI 1 "register_operand" "0")
8136                 (match_operand:DI 2 "nonimmediate_operand" "rm")))
8137    (set (match_operand:DI 3 "register_operand" "=d")
8138         (mod:DI (match_dup 1) (match_dup 2)))
8139    (use (match_operand:DI 4 "register_operand" "3"))
8140    (clobber (reg:CC FLAGS_REG))]
8141   "TARGET_64BIT"
8142   "idiv{q}\t%2"
8143   [(set_attr "type" "idiv")
8144    (set_attr "mode" "DI")])
8145
8146 (define_split
8147   [(set (match_operand:DI 0 "register_operand" "")
8148         (div:DI (match_operand:DI 1 "register_operand" "")
8149                 (match_operand:DI 2 "nonimmediate_operand" "")))
8150    (set (match_operand:DI 3 "register_operand" "")
8151         (mod:DI (match_dup 1) (match_dup 2)))
8152    (clobber (reg:CC FLAGS_REG))]
8153   "TARGET_64BIT && reload_completed"
8154   [(parallel [(set (match_dup 3)
8155                    (ashiftrt:DI (match_dup 4) (const_int 63)))
8156               (clobber (reg:CC FLAGS_REG))])
8157    (parallel [(set (match_dup 0)
8158                    (div:DI (reg:DI 0) (match_dup 2)))
8159               (set (match_dup 3)
8160                    (mod:DI (reg:DI 0) (match_dup 2)))
8161               (use (match_dup 3))
8162               (clobber (reg:CC FLAGS_REG))])]
8163 {
8164   /* Avoid use of cltd in favor of a mov+shift.  */
8165   if (!TARGET_USE_CLTD && !optimize_size)
8166     {
8167       if (true_regnum (operands[1]))
8168         emit_move_insn (operands[0], operands[1]);
8169       else
8170         emit_move_insn (operands[3], operands[1]);
8171       operands[4] = operands[3];
8172     }
8173   else
8174     {
8175       gcc_assert (!true_regnum (operands[1]));
8176       operands[4] = operands[1];
8177     }
8178 })
8179
8180
8181 (define_expand "divmodsi4"
8182   [(parallel [(set (match_operand:SI 0 "register_operand" "")
8183                    (div:SI (match_operand:SI 1 "register_operand" "")
8184                            (match_operand:SI 2 "nonimmediate_operand" "")))
8185               (set (match_operand:SI 3 "register_operand" "")
8186                    (mod:SI (match_dup 1) (match_dup 2)))
8187               (clobber (reg:CC FLAGS_REG))])]
8188   ""
8189   "")
8190
8191 ;; Allow to come the parameter in eax or edx to avoid extra moves.
8192 ;; Penalize eax case slightly because it results in worse scheduling
8193 ;; of code.
8194 (define_insn "*divmodsi4_nocltd"
8195   [(set (match_operand:SI 0 "register_operand" "=&a,?a")
8196         (div:SI (match_operand:SI 2 "register_operand" "1,0")
8197                 (match_operand:SI 3 "nonimmediate_operand" "rm,rm")))
8198    (set (match_operand:SI 1 "register_operand" "=&d,&d")
8199         (mod:SI (match_dup 2) (match_dup 3)))
8200    (clobber (reg:CC FLAGS_REG))]
8201   "!optimize_size && !TARGET_USE_CLTD"
8202   "#"
8203   [(set_attr "type" "multi")])
8204
8205 (define_insn "*divmodsi4_cltd"
8206   [(set (match_operand:SI 0 "register_operand" "=a")
8207         (div:SI (match_operand:SI 2 "register_operand" "a")
8208                 (match_operand:SI 3 "nonimmediate_operand" "rm")))
8209    (set (match_operand:SI 1 "register_operand" "=&d")
8210         (mod:SI (match_dup 2) (match_dup 3)))
8211    (clobber (reg:CC FLAGS_REG))]
8212   "optimize_size || TARGET_USE_CLTD"
8213   "#"
8214   [(set_attr "type" "multi")])
8215
8216 (define_insn "*divmodsi_noext"
8217   [(set (match_operand:SI 0 "register_operand" "=a")
8218         (div:SI (match_operand:SI 1 "register_operand" "0")
8219                 (match_operand:SI 2 "nonimmediate_operand" "rm")))
8220    (set (match_operand:SI 3 "register_operand" "=d")
8221         (mod:SI (match_dup 1) (match_dup 2)))
8222    (use (match_operand:SI 4 "register_operand" "3"))
8223    (clobber (reg:CC FLAGS_REG))]
8224   ""
8225   "idiv{l}\t%2"
8226   [(set_attr "type" "idiv")
8227    (set_attr "mode" "SI")])
8228
8229 (define_split
8230   [(set (match_operand:SI 0 "register_operand" "")
8231         (div:SI (match_operand:SI 1 "register_operand" "")
8232                 (match_operand:SI 2 "nonimmediate_operand" "")))
8233    (set (match_operand:SI 3 "register_operand" "")
8234         (mod:SI (match_dup 1) (match_dup 2)))
8235    (clobber (reg:CC FLAGS_REG))]
8236   "reload_completed"
8237   [(parallel [(set (match_dup 3)
8238                    (ashiftrt:SI (match_dup 4) (const_int 31)))
8239               (clobber (reg:CC FLAGS_REG))])
8240    (parallel [(set (match_dup 0)
8241                    (div:SI (reg:SI 0) (match_dup 2)))
8242               (set (match_dup 3)
8243                    (mod:SI (reg:SI 0) (match_dup 2)))
8244               (use (match_dup 3))
8245               (clobber (reg:CC FLAGS_REG))])]
8246 {
8247   /* Avoid use of cltd in favor of a mov+shift.  */
8248   if (!TARGET_USE_CLTD && !optimize_size)
8249     {
8250       if (true_regnum (operands[1]))
8251         emit_move_insn (operands[0], operands[1]);
8252       else
8253         emit_move_insn (operands[3], operands[1]);
8254       operands[4] = operands[3];
8255     }
8256   else
8257     {
8258       gcc_assert (!true_regnum (operands[1]));
8259       operands[4] = operands[1];
8260     }
8261 })
8262 ;; %%% Split me.
8263 (define_insn "divmodhi4"
8264   [(set (match_operand:HI 0 "register_operand" "=a")
8265         (div:HI (match_operand:HI 1 "register_operand" "0")
8266                 (match_operand:HI 2 "nonimmediate_operand" "rm")))
8267    (set (match_operand:HI 3 "register_operand" "=&d")
8268         (mod:HI (match_dup 1) (match_dup 2)))
8269    (clobber (reg:CC FLAGS_REG))]
8270   "TARGET_HIMODE_MATH"
8271   "cwtd\;idiv{w}\t%2"
8272   [(set_attr "type" "multi")
8273    (set_attr "length_immediate" "0")
8274    (set_attr "mode" "SI")])
8275
8276 (define_insn "udivmoddi4"
8277   [(set (match_operand:DI 0 "register_operand" "=a")
8278         (udiv:DI (match_operand:DI 1 "register_operand" "0")
8279                  (match_operand:DI 2 "nonimmediate_operand" "rm")))
8280    (set (match_operand:DI 3 "register_operand" "=&d")
8281         (umod:DI (match_dup 1) (match_dup 2)))
8282    (clobber (reg:CC FLAGS_REG))]
8283   "TARGET_64BIT"
8284   "xor{q}\t%3, %3\;div{q}\t%2"
8285   [(set_attr "type" "multi")
8286    (set_attr "length_immediate" "0")
8287    (set_attr "mode" "DI")])
8288
8289 (define_insn "*udivmoddi4_noext"
8290   [(set (match_operand:DI 0 "register_operand" "=a")
8291         (udiv:DI (match_operand:DI 1 "register_operand" "0")
8292                  (match_operand:DI 2 "nonimmediate_operand" "rm")))
8293    (set (match_operand:DI 3 "register_operand" "=d")
8294         (umod:DI (match_dup 1) (match_dup 2)))
8295    (use (match_dup 3))
8296    (clobber (reg:CC FLAGS_REG))]
8297   "TARGET_64BIT"
8298   "div{q}\t%2"
8299   [(set_attr "type" "idiv")
8300    (set_attr "mode" "DI")])
8301
8302 (define_split
8303   [(set (match_operand:DI 0 "register_operand" "")
8304         (udiv:DI (match_operand:DI 1 "register_operand" "")
8305                  (match_operand:DI 2 "nonimmediate_operand" "")))
8306    (set (match_operand:DI 3 "register_operand" "")
8307         (umod:DI (match_dup 1) (match_dup 2)))
8308    (clobber (reg:CC FLAGS_REG))]
8309   "TARGET_64BIT && reload_completed"
8310   [(set (match_dup 3) (const_int 0))
8311    (parallel [(set (match_dup 0)
8312                    (udiv:DI (match_dup 1) (match_dup 2)))
8313               (set (match_dup 3)
8314                    (umod:DI (match_dup 1) (match_dup 2)))
8315               (use (match_dup 3))
8316               (clobber (reg:CC FLAGS_REG))])]
8317   "")
8318
8319 (define_insn "udivmodsi4"
8320   [(set (match_operand:SI 0 "register_operand" "=a")
8321         (udiv:SI (match_operand:SI 1 "register_operand" "0")
8322                  (match_operand:SI 2 "nonimmediate_operand" "rm")))
8323    (set (match_operand:SI 3 "register_operand" "=&d")
8324         (umod:SI (match_dup 1) (match_dup 2)))
8325    (clobber (reg:CC FLAGS_REG))]
8326   ""
8327   "xor{l}\t%3, %3\;div{l}\t%2"
8328   [(set_attr "type" "multi")
8329    (set_attr "length_immediate" "0")
8330    (set_attr "mode" "SI")])
8331
8332 (define_insn "*udivmodsi4_noext"
8333   [(set (match_operand:SI 0 "register_operand" "=a")
8334         (udiv:SI (match_operand:SI 1 "register_operand" "0")
8335                  (match_operand:SI 2 "nonimmediate_operand" "rm")))
8336    (set (match_operand:SI 3 "register_operand" "=d")
8337         (umod:SI (match_dup 1) (match_dup 2)))
8338    (use (match_dup 3))
8339    (clobber (reg:CC FLAGS_REG))]
8340   ""
8341   "div{l}\t%2"
8342   [(set_attr "type" "idiv")
8343    (set_attr "mode" "SI")])
8344
8345 (define_split
8346   [(set (match_operand:SI 0 "register_operand" "")
8347         (udiv:SI (match_operand:SI 1 "register_operand" "")
8348                  (match_operand:SI 2 "nonimmediate_operand" "")))
8349    (set (match_operand:SI 3 "register_operand" "")
8350         (umod:SI (match_dup 1) (match_dup 2)))
8351    (clobber (reg:CC FLAGS_REG))]
8352   "reload_completed"
8353   [(set (match_dup 3) (const_int 0))
8354    (parallel [(set (match_dup 0)
8355                    (udiv:SI (match_dup 1) (match_dup 2)))
8356               (set (match_dup 3)
8357                    (umod:SI (match_dup 1) (match_dup 2)))
8358               (use (match_dup 3))
8359               (clobber (reg:CC FLAGS_REG))])]
8360   "")
8361
8362 (define_expand "udivmodhi4"
8363   [(set (match_dup 4) (const_int 0))
8364    (parallel [(set (match_operand:HI 0 "register_operand" "")
8365                    (udiv:HI (match_operand:HI 1 "register_operand" "")
8366                             (match_operand:HI 2 "nonimmediate_operand" "")))
8367               (set (match_operand:HI 3 "register_operand" "")
8368                    (umod:HI (match_dup 1) (match_dup 2)))
8369               (use (match_dup 4))
8370               (clobber (reg:CC FLAGS_REG))])]
8371   "TARGET_HIMODE_MATH"
8372   "operands[4] = gen_reg_rtx (HImode);")
8373
8374 (define_insn "*udivmodhi_noext"
8375   [(set (match_operand:HI 0 "register_operand" "=a")
8376         (udiv:HI (match_operand:HI 1 "register_operand" "0")
8377                  (match_operand:HI 2 "nonimmediate_operand" "rm")))
8378    (set (match_operand:HI 3 "register_operand" "=d")
8379         (umod:HI (match_dup 1) (match_dup 2)))
8380    (use (match_operand:HI 4 "register_operand" "3"))
8381    (clobber (reg:CC FLAGS_REG))]
8382   ""
8383   "div{w}\t%2"
8384   [(set_attr "type" "idiv")
8385    (set_attr "mode" "HI")])
8386
8387 ;; We cannot use div/idiv for double division, because it causes
8388 ;; "division by zero" on the overflow and that's not what we expect
8389 ;; from truncate.  Because true (non truncating) double division is
8390 ;; never generated, we can't create this insn anyway.
8391 ;
8392 ;(define_insn ""
8393 ;  [(set (match_operand:SI 0 "register_operand" "=a")
8394 ;       (truncate:SI
8395 ;         (udiv:DI (match_operand:DI 1 "register_operand" "A")
8396 ;                  (zero_extend:DI
8397 ;                    (match_operand:SI 2 "nonimmediate_operand" "rm")))))
8398 ;   (set (match_operand:SI 3 "register_operand" "=d")
8399 ;       (truncate:SI
8400 ;         (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
8401 ;   (clobber (reg:CC FLAGS_REG))]
8402 ;  ""
8403 ;  "div{l}\t{%2, %0|%0, %2}"
8404 ;  [(set_attr "type" "idiv")])
8405 \f
8406 ;;- Logical AND instructions
8407
8408 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
8409 ;; Note that this excludes ah.
8410
8411 (define_insn "*testdi_1_rex64"
8412   [(set (reg FLAGS_REG)
8413         (compare
8414           (and:DI (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
8415                   (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
8416           (const_int 0)))]
8417   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8418    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8419   "@
8420    test{l}\t{%k1, %k0|%k0, %k1}
8421    test{l}\t{%k1, %k0|%k0, %k1}
8422    test{q}\t{%1, %0|%0, %1}
8423    test{q}\t{%1, %0|%0, %1}
8424    test{q}\t{%1, %0|%0, %1}"
8425   [(set_attr "type" "test")
8426    (set_attr "modrm" "0,1,0,1,1")
8427    (set_attr "mode" "SI,SI,DI,DI,DI")
8428    (set_attr "pent_pair" "uv,np,uv,np,uv")])
8429
8430 (define_insn "testsi_1"
8431   [(set (reg FLAGS_REG)
8432         (compare
8433           (and:SI (match_operand:SI 0 "nonimmediate_operand" "%!*a,r,rm")
8434                   (match_operand:SI 1 "general_operand" "in,in,rin"))
8435           (const_int 0)))]
8436   "ix86_match_ccmode (insn, CCNOmode)
8437    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8438   "test{l}\t{%1, %0|%0, %1}"
8439   [(set_attr "type" "test")
8440    (set_attr "modrm" "0,1,1")
8441    (set_attr "mode" "SI")
8442    (set_attr "pent_pair" "uv,np,uv")])
8443
8444 (define_expand "testsi_ccno_1"
8445   [(set (reg:CCNO FLAGS_REG)
8446         (compare:CCNO
8447           (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
8448                   (match_operand:SI 1 "nonmemory_operand" ""))
8449           (const_int 0)))]
8450   ""
8451   "")
8452
8453 (define_insn "*testhi_1"
8454   [(set (reg FLAGS_REG)
8455         (compare (and:HI (match_operand:HI 0 "nonimmediate_operand" "%!*a,r,rm")
8456                          (match_operand:HI 1 "general_operand" "n,n,rn"))
8457                  (const_int 0)))]
8458   "ix86_match_ccmode (insn, CCNOmode)
8459    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8460   "test{w}\t{%1, %0|%0, %1}"
8461   [(set_attr "type" "test")
8462    (set_attr "modrm" "0,1,1")
8463    (set_attr "mode" "HI")
8464    (set_attr "pent_pair" "uv,np,uv")])
8465
8466 (define_expand "testqi_ccz_1"
8467   [(set (reg:CCZ FLAGS_REG)
8468         (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
8469                              (match_operand:QI 1 "nonmemory_operand" ""))
8470                  (const_int 0)))]
8471   ""
8472   "")
8473
8474 (define_insn "*testqi_1_maybe_si"
8475   [(set (reg FLAGS_REG)
8476         (compare
8477           (and:QI
8478             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
8479             (match_operand:QI 1 "general_operand" "n,n,qn,n"))
8480           (const_int 0)))]
8481    "!(MEM_P (operands[0]) && MEM_P (operands[1]))
8482     && ix86_match_ccmode (insn,
8483                          CONST_INT_P (operands[1])
8484                          && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
8485 {
8486   if (which_alternative == 3)
8487     {
8488       if (CONST_INT_P (operands[1]) && INTVAL (operands[1]) < 0)
8489         operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
8490       return "test{l}\t{%1, %k0|%k0, %1}";
8491     }
8492   return "test{b}\t{%1, %0|%0, %1}";
8493 }
8494   [(set_attr "type" "test")
8495    (set_attr "modrm" "0,1,1,1")
8496    (set_attr "mode" "QI,QI,QI,SI")
8497    (set_attr "pent_pair" "uv,np,uv,np")])
8498
8499 (define_insn "*testqi_1"
8500   [(set (reg FLAGS_REG)
8501         (compare
8502           (and:QI
8503             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm")
8504             (match_operand:QI 1 "general_operand" "n,n,qn"))
8505           (const_int 0)))]
8506   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
8507    && ix86_match_ccmode (insn, CCNOmode)"
8508   "test{b}\t{%1, %0|%0, %1}"
8509   [(set_attr "type" "test")
8510    (set_attr "modrm" "0,1,1")
8511    (set_attr "mode" "QI")
8512    (set_attr "pent_pair" "uv,np,uv")])
8513
8514 (define_expand "testqi_ext_ccno_0"
8515   [(set (reg:CCNO FLAGS_REG)
8516         (compare:CCNO
8517           (and:SI
8518             (zero_extract:SI
8519               (match_operand 0 "ext_register_operand" "")
8520               (const_int 8)
8521               (const_int 8))
8522             (match_operand 1 "const_int_operand" ""))
8523           (const_int 0)))]
8524   ""
8525   "")
8526
8527 (define_insn "*testqi_ext_0"
8528   [(set (reg FLAGS_REG)
8529         (compare
8530           (and:SI
8531             (zero_extract:SI
8532               (match_operand 0 "ext_register_operand" "Q")
8533               (const_int 8)
8534               (const_int 8))
8535             (match_operand 1 "const_int_operand" "n"))
8536           (const_int 0)))]
8537   "ix86_match_ccmode (insn, CCNOmode)"
8538   "test{b}\t{%1, %h0|%h0, %1}"
8539   [(set_attr "type" "test")
8540    (set_attr "mode" "QI")
8541    (set_attr "length_immediate" "1")
8542    (set_attr "pent_pair" "np")])
8543
8544 (define_insn "*testqi_ext_1"
8545   [(set (reg FLAGS_REG)
8546         (compare
8547           (and:SI
8548             (zero_extract:SI
8549               (match_operand 0 "ext_register_operand" "Q")
8550               (const_int 8)
8551               (const_int 8))
8552             (zero_extend:SI
8553               (match_operand:QI 1 "general_operand" "Qm")))
8554           (const_int 0)))]
8555   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8556    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8557   "test{b}\t{%1, %h0|%h0, %1}"
8558   [(set_attr "type" "test")
8559    (set_attr "mode" "QI")])
8560
8561 (define_insn "*testqi_ext_1_rex64"
8562   [(set (reg FLAGS_REG)
8563         (compare
8564           (and:SI
8565             (zero_extract:SI
8566               (match_operand 0 "ext_register_operand" "Q")
8567               (const_int 8)
8568               (const_int 8))
8569             (zero_extend:SI
8570               (match_operand:QI 1 "register_operand" "Q")))
8571           (const_int 0)))]
8572   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
8573   "test{b}\t{%1, %h0|%h0, %1}"
8574   [(set_attr "type" "test")
8575    (set_attr "mode" "QI")])
8576
8577 (define_insn "*testqi_ext_2"
8578   [(set (reg FLAGS_REG)
8579         (compare
8580           (and:SI
8581             (zero_extract:SI
8582               (match_operand 0 "ext_register_operand" "Q")
8583               (const_int 8)
8584               (const_int 8))
8585             (zero_extract:SI
8586               (match_operand 1 "ext_register_operand" "Q")
8587               (const_int 8)
8588               (const_int 8)))
8589           (const_int 0)))]
8590   "ix86_match_ccmode (insn, CCNOmode)"
8591   "test{b}\t{%h1, %h0|%h0, %h1}"
8592   [(set_attr "type" "test")
8593    (set_attr "mode" "QI")])
8594
8595 ;; Combine likes to form bit extractions for some tests.  Humor it.
8596 (define_insn "*testqi_ext_3"
8597   [(set (reg FLAGS_REG)
8598         (compare (zero_extract:SI
8599                    (match_operand 0 "nonimmediate_operand" "rm")
8600                    (match_operand:SI 1 "const_int_operand" "")
8601                    (match_operand:SI 2 "const_int_operand" ""))
8602                  (const_int 0)))]
8603   "ix86_match_ccmode (insn, CCNOmode)
8604    && INTVAL (operands[1]) > 0
8605    && INTVAL (operands[2]) >= 0
8606    && INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
8607    && (GET_MODE (operands[0]) == SImode
8608        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
8609        || GET_MODE (operands[0]) == HImode
8610        || GET_MODE (operands[0]) == QImode)"
8611   "#")
8612
8613 (define_insn "*testqi_ext_3_rex64"
8614   [(set (reg FLAGS_REG)
8615         (compare (zero_extract:DI
8616                    (match_operand 0 "nonimmediate_operand" "rm")
8617                    (match_operand:DI 1 "const_int_operand" "")
8618                    (match_operand:DI 2 "const_int_operand" ""))
8619                  (const_int 0)))]
8620   "TARGET_64BIT
8621    && ix86_match_ccmode (insn, CCNOmode)
8622    && INTVAL (operands[1]) > 0
8623    && INTVAL (operands[2]) >= 0
8624    /* Ensure that resulting mask is zero or sign extended operand.  */
8625    && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
8626        || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
8627            && INTVAL (operands[1]) > 32))
8628    && (GET_MODE (operands[0]) == SImode
8629        || GET_MODE (operands[0]) == DImode
8630        || GET_MODE (operands[0]) == HImode
8631        || GET_MODE (operands[0]) == QImode)"
8632   "#")
8633
8634 (define_split
8635   [(set (match_operand 0 "flags_reg_operand" "")
8636         (match_operator 1 "compare_operator"
8637           [(zero_extract
8638              (match_operand 2 "nonimmediate_operand" "")
8639              (match_operand 3 "const_int_operand" "")
8640              (match_operand 4 "const_int_operand" ""))
8641            (const_int 0)]))]
8642   "ix86_match_ccmode (insn, CCNOmode)"
8643   [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
8644 {
8645   rtx val = operands[2];
8646   HOST_WIDE_INT len = INTVAL (operands[3]);
8647   HOST_WIDE_INT pos = INTVAL (operands[4]);
8648   HOST_WIDE_INT mask;
8649   enum machine_mode mode, submode;
8650
8651   mode = GET_MODE (val);
8652   if (MEM_P (val))
8653     {
8654       /* ??? Combine likes to put non-volatile mem extractions in QImode
8655          no matter the size of the test.  So find a mode that works.  */
8656       if (! MEM_VOLATILE_P (val))
8657         {
8658           mode = smallest_mode_for_size (pos + len, MODE_INT);
8659           val = adjust_address (val, mode, 0);
8660         }
8661     }
8662   else if (GET_CODE (val) == SUBREG
8663            && (submode = GET_MODE (SUBREG_REG (val)),
8664                GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
8665            && pos + len <= GET_MODE_BITSIZE (submode))
8666     {
8667       /* Narrow a paradoxical subreg to prevent partial register stalls.  */
8668       mode = submode;
8669       val = SUBREG_REG (val);
8670     }
8671   else if (mode == HImode && pos + len <= 8)
8672     {
8673       /* Small HImode tests can be converted to QImode.  */
8674       mode = QImode;
8675       val = gen_lowpart (QImode, val);
8676     }
8677
8678   if (len == HOST_BITS_PER_WIDE_INT)
8679     mask = -1;
8680   else
8681     mask = ((HOST_WIDE_INT)1 << len) - 1;
8682   mask <<= pos;
8683
8684   operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
8685 })
8686
8687 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
8688 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
8689 ;; this is relatively important trick.
8690 ;; Do the conversion only post-reload to avoid limiting of the register class
8691 ;; to QI regs.
8692 (define_split
8693   [(set (match_operand 0 "flags_reg_operand" "")
8694         (match_operator 1 "compare_operator"
8695           [(and (match_operand 2 "register_operand" "")
8696                 (match_operand 3 "const_int_operand" ""))
8697            (const_int 0)]))]
8698    "reload_completed
8699     && QI_REG_P (operands[2])
8700     && GET_MODE (operands[2]) != QImode
8701     && ((ix86_match_ccmode (insn, CCZmode)
8702          && !(INTVAL (operands[3]) & ~(255 << 8)))
8703         || (ix86_match_ccmode (insn, CCNOmode)
8704             && !(INTVAL (operands[3]) & ~(127 << 8))))"
8705   [(set (match_dup 0)
8706         (match_op_dup 1
8707           [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
8708                    (match_dup 3))
8709            (const_int 0)]))]
8710   "operands[2] = gen_lowpart (SImode, operands[2]);
8711    operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);")
8712
8713 (define_split
8714   [(set (match_operand 0 "flags_reg_operand" "")
8715         (match_operator 1 "compare_operator"
8716           [(and (match_operand 2 "nonimmediate_operand" "")
8717                 (match_operand 3 "const_int_operand" ""))
8718            (const_int 0)]))]
8719    "reload_completed
8720     && GET_MODE (operands[2]) != QImode
8721     && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
8722     && ((ix86_match_ccmode (insn, CCZmode)
8723          && !(INTVAL (operands[3]) & ~255))
8724         || (ix86_match_ccmode (insn, CCNOmode)
8725             && !(INTVAL (operands[3]) & ~127)))"
8726   [(set (match_dup 0)
8727         (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
8728                          (const_int 0)]))]
8729   "operands[2] = gen_lowpart (QImode, operands[2]);
8730    operands[3] = gen_lowpart (QImode, operands[3]);")
8731
8732
8733 ;; %%% This used to optimize known byte-wide and operations to memory,
8734 ;; and sometimes to QImode registers.  If this is considered useful,
8735 ;; it should be done with splitters.
8736
8737 (define_expand "anddi3"
8738   [(set (match_operand:DI 0 "nonimmediate_operand" "")
8739         (and:DI (match_operand:DI 1 "nonimmediate_operand" "")
8740                 (match_operand:DI 2 "x86_64_szext_general_operand" "")))
8741    (clobber (reg:CC FLAGS_REG))]
8742   "TARGET_64BIT"
8743   "ix86_expand_binary_operator (AND, DImode, operands); DONE;")
8744
8745 (define_insn "*anddi_1_rex64"
8746   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
8747         (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
8748                 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
8749    (clobber (reg:CC FLAGS_REG))]
8750   "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
8751 {
8752   switch (get_attr_type (insn))
8753     {
8754     case TYPE_IMOVX:
8755       {
8756         enum machine_mode mode;
8757
8758         gcc_assert (CONST_INT_P (operands[2]));
8759         if (INTVAL (operands[2]) == 0xff)
8760           mode = QImode;
8761         else
8762           {
8763             gcc_assert (INTVAL (operands[2]) == 0xffff);
8764             mode = HImode;
8765           }
8766
8767         operands[1] = gen_lowpart (mode, operands[1]);
8768         if (mode == QImode)
8769           return "movz{bq|x}\t{%1,%0|%0, %1}";
8770         else
8771           return "movz{wq|x}\t{%1,%0|%0, %1}";
8772       }
8773
8774     default:
8775       gcc_assert (rtx_equal_p (operands[0], operands[1]));
8776       if (get_attr_mode (insn) == MODE_SI)
8777         return "and{l}\t{%k2, %k0|%k0, %k2}";
8778       else
8779         return "and{q}\t{%2, %0|%0, %2}";
8780     }
8781 }
8782   [(set_attr "type" "alu,alu,alu,imovx")
8783    (set_attr "length_immediate" "*,*,*,0")
8784    (set_attr "mode" "SI,DI,DI,DI")])
8785
8786 (define_insn "*anddi_2"
8787   [(set (reg FLAGS_REG)
8788         (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
8789                          (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
8790                  (const_int 0)))
8791    (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
8792         (and:DI (match_dup 1) (match_dup 2)))]
8793   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8794    && ix86_binary_operator_ok (AND, DImode, operands)"
8795   "@
8796    and{l}\t{%k2, %k0|%k0, %k2}
8797    and{q}\t{%2, %0|%0, %2}
8798    and{q}\t{%2, %0|%0, %2}"
8799   [(set_attr "type" "alu")
8800    (set_attr "mode" "SI,DI,DI")])
8801
8802 (define_expand "andsi3"
8803   [(set (match_operand:SI 0 "nonimmediate_operand" "")
8804         (and:SI (match_operand:SI 1 "nonimmediate_operand" "")
8805                 (match_operand:SI 2 "general_operand" "")))
8806    (clobber (reg:CC FLAGS_REG))]
8807   ""
8808   "ix86_expand_binary_operator (AND, SImode, operands); DONE;")
8809
8810 (define_insn "*andsi_1"
8811   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
8812         (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
8813                 (match_operand:SI 2 "general_operand" "ri,rm,L")))
8814    (clobber (reg:CC FLAGS_REG))]
8815   "ix86_binary_operator_ok (AND, SImode, operands)"
8816 {
8817   switch (get_attr_type (insn))
8818     {
8819     case TYPE_IMOVX:
8820       {
8821         enum machine_mode mode;
8822
8823         gcc_assert (CONST_INT_P (operands[2]));
8824         if (INTVAL (operands[2]) == 0xff)
8825           mode = QImode;
8826         else
8827           {
8828             gcc_assert (INTVAL (operands[2]) == 0xffff);
8829             mode = HImode;
8830           }
8831
8832         operands[1] = gen_lowpart (mode, operands[1]);
8833         if (mode == QImode)
8834           return "movz{bl|x}\t{%1,%0|%0, %1}";
8835         else
8836           return "movz{wl|x}\t{%1,%0|%0, %1}";
8837       }
8838
8839     default:
8840       gcc_assert (rtx_equal_p (operands[0], operands[1]));
8841       return "and{l}\t{%2, %0|%0, %2}";
8842     }
8843 }
8844   [(set_attr "type" "alu,alu,imovx")
8845    (set_attr "length_immediate" "*,*,0")
8846    (set_attr "mode" "SI")])
8847
8848 (define_split
8849   [(set (match_operand 0 "register_operand" "")
8850         (and (match_dup 0)
8851              (const_int -65536)))
8852    (clobber (reg:CC FLAGS_REG))]
8853   "optimize_size || (TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)"
8854   [(set (strict_low_part (match_dup 1)) (const_int 0))]
8855   "operands[1] = gen_lowpart (HImode, operands[0]);")
8856
8857 (define_split
8858   [(set (match_operand 0 "ext_register_operand" "")
8859         (and (match_dup 0)
8860              (const_int -256)))
8861    (clobber (reg:CC FLAGS_REG))]
8862   "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8863   [(set (strict_low_part (match_dup 1)) (const_int 0))]
8864   "operands[1] = gen_lowpart (QImode, operands[0]);")
8865
8866 (define_split
8867   [(set (match_operand 0 "ext_register_operand" "")
8868         (and (match_dup 0)
8869              (const_int -65281)))
8870    (clobber (reg:CC FLAGS_REG))]
8871   "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8872   [(parallel [(set (zero_extract:SI (match_dup 0)
8873                                     (const_int 8)
8874                                     (const_int 8))
8875                    (xor:SI
8876                      (zero_extract:SI (match_dup 0)
8877                                       (const_int 8)
8878                                       (const_int 8))
8879                      (zero_extract:SI (match_dup 0)
8880                                       (const_int 8)
8881                                       (const_int 8))))
8882               (clobber (reg:CC FLAGS_REG))])]
8883   "operands[0] = gen_lowpart (SImode, operands[0]);")
8884
8885 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8886 (define_insn "*andsi_1_zext"
8887   [(set (match_operand:DI 0 "register_operand" "=r")
8888         (zero_extend:DI
8889           (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8890                   (match_operand:SI 2 "general_operand" "g"))))
8891    (clobber (reg:CC FLAGS_REG))]
8892   "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
8893   "and{l}\t{%2, %k0|%k0, %2}"
8894   [(set_attr "type" "alu")
8895    (set_attr "mode" "SI")])
8896
8897 (define_insn "*andsi_2"
8898   [(set (reg FLAGS_REG)
8899         (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8900                          (match_operand:SI 2 "general_operand" "g,ri"))
8901                  (const_int 0)))
8902    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8903         (and:SI (match_dup 1) (match_dup 2)))]
8904   "ix86_match_ccmode (insn, CCNOmode)
8905    && ix86_binary_operator_ok (AND, SImode, operands)"
8906   "and{l}\t{%2, %0|%0, %2}"
8907   [(set_attr "type" "alu")
8908    (set_attr "mode" "SI")])
8909
8910 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8911 (define_insn "*andsi_2_zext"
8912   [(set (reg FLAGS_REG)
8913         (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8914                          (match_operand:SI 2 "general_operand" "g"))
8915                  (const_int 0)))
8916    (set (match_operand:DI 0 "register_operand" "=r")
8917         (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
8918   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8919    && ix86_binary_operator_ok (AND, SImode, operands)"
8920   "and{l}\t{%2, %k0|%k0, %2}"
8921   [(set_attr "type" "alu")
8922    (set_attr "mode" "SI")])
8923
8924 (define_expand "andhi3"
8925   [(set (match_operand:HI 0 "nonimmediate_operand" "")
8926         (and:HI (match_operand:HI 1 "nonimmediate_operand" "")
8927                 (match_operand:HI 2 "general_operand" "")))
8928    (clobber (reg:CC FLAGS_REG))]
8929   "TARGET_HIMODE_MATH"
8930   "ix86_expand_binary_operator (AND, HImode, operands); DONE;")
8931
8932 (define_insn "*andhi_1"
8933   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
8934         (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
8935                 (match_operand:HI 2 "general_operand" "ri,rm,L")))
8936    (clobber (reg:CC FLAGS_REG))]
8937   "ix86_binary_operator_ok (AND, HImode, operands)"
8938 {
8939   switch (get_attr_type (insn))
8940     {
8941     case TYPE_IMOVX:
8942       gcc_assert (CONST_INT_P (operands[2]));
8943       gcc_assert (INTVAL (operands[2]) == 0xff);
8944       return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
8945
8946     default:
8947       gcc_assert (rtx_equal_p (operands[0], operands[1]));
8948
8949       return "and{w}\t{%2, %0|%0, %2}";
8950     }
8951 }
8952   [(set_attr "type" "alu,alu,imovx")
8953    (set_attr "length_immediate" "*,*,0")
8954    (set_attr "mode" "HI,HI,SI")])
8955
8956 (define_insn "*andhi_2"
8957   [(set (reg FLAGS_REG)
8958         (compare (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8959                          (match_operand:HI 2 "general_operand" "g,ri"))
8960                  (const_int 0)))
8961    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8962         (and:HI (match_dup 1) (match_dup 2)))]
8963   "ix86_match_ccmode (insn, CCNOmode)
8964    && ix86_binary_operator_ok (AND, HImode, operands)"
8965   "and{w}\t{%2, %0|%0, %2}"
8966   [(set_attr "type" "alu")
8967    (set_attr "mode" "HI")])
8968
8969 (define_expand "andqi3"
8970   [(set (match_operand:QI 0 "nonimmediate_operand" "")
8971         (and:QI (match_operand:QI 1 "nonimmediate_operand" "")
8972                 (match_operand:QI 2 "general_operand" "")))
8973    (clobber (reg:CC FLAGS_REG))]
8974   "TARGET_QIMODE_MATH"
8975   "ix86_expand_binary_operator (AND, QImode, operands); DONE;")
8976
8977 ;; %%% Potential partial reg stall on alternative 2.  What to do?
8978 (define_insn "*andqi_1"
8979   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
8980         (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8981                 (match_operand:QI 2 "general_operand" "qi,qmi,ri")))
8982    (clobber (reg:CC FLAGS_REG))]
8983   "ix86_binary_operator_ok (AND, QImode, operands)"
8984   "@
8985    and{b}\t{%2, %0|%0, %2}
8986    and{b}\t{%2, %0|%0, %2}
8987    and{l}\t{%k2, %k0|%k0, %k2}"
8988   [(set_attr "type" "alu")
8989    (set_attr "mode" "QI,QI,SI")])
8990
8991 (define_insn "*andqi_1_slp"
8992   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
8993         (and:QI (match_dup 0)
8994                 (match_operand:QI 1 "general_operand" "qi,qmi")))
8995    (clobber (reg:CC FLAGS_REG))]
8996   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8997    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
8998   "and{b}\t{%1, %0|%0, %1}"
8999   [(set_attr "type" "alu1")
9000    (set_attr "mode" "QI")])
9001
9002 (define_insn "*andqi_2_maybe_si"
9003   [(set (reg FLAGS_REG)
9004         (compare (and:QI
9005                       (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9006                       (match_operand:QI 2 "general_operand" "qim,qi,i"))
9007                  (const_int 0)))
9008    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
9009         (and:QI (match_dup 1) (match_dup 2)))]
9010   "ix86_binary_operator_ok (AND, QImode, operands)
9011    && ix86_match_ccmode (insn,
9012                          CONST_INT_P (operands[2])
9013                          && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
9014 {
9015   if (which_alternative == 2)
9016     {
9017       if (CONST_INT_P (operands[2]) && INTVAL (operands[2]) < 0)
9018         operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
9019       return "and{l}\t{%2, %k0|%k0, %2}";
9020     }
9021   return "and{b}\t{%2, %0|%0, %2}";
9022 }
9023   [(set_attr "type" "alu")
9024    (set_attr "mode" "QI,QI,SI")])
9025
9026 (define_insn "*andqi_2"
9027   [(set (reg FLAGS_REG)
9028         (compare (and:QI
9029                    (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9030                    (match_operand:QI 2 "general_operand" "qim,qi"))
9031                  (const_int 0)))
9032    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9033         (and:QI (match_dup 1) (match_dup 2)))]
9034   "ix86_match_ccmode (insn, CCNOmode)
9035    && ix86_binary_operator_ok (AND, QImode, operands)"
9036   "and{b}\t{%2, %0|%0, %2}"
9037   [(set_attr "type" "alu")
9038    (set_attr "mode" "QI")])
9039
9040 (define_insn "*andqi_2_slp"
9041   [(set (reg FLAGS_REG)
9042         (compare (and:QI
9043                    (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9044                    (match_operand:QI 1 "nonimmediate_operand" "qmi,qi"))
9045                  (const_int 0)))
9046    (set (strict_low_part (match_dup 0))
9047         (and:QI (match_dup 0) (match_dup 1)))]
9048   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9049    && ix86_match_ccmode (insn, CCNOmode)
9050    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9051   "and{b}\t{%1, %0|%0, %1}"
9052   [(set_attr "type" "alu1")
9053    (set_attr "mode" "QI")])
9054
9055 ;; ??? A bug in recog prevents it from recognizing a const_int as an
9056 ;; operand to zero_extend in andqi_ext_1.  It was checking explicitly
9057 ;; for a QImode operand, which of course failed.
9058
9059 (define_insn "andqi_ext_0"
9060   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9061                          (const_int 8)
9062                          (const_int 8))
9063         (and:SI
9064           (zero_extract:SI
9065             (match_operand 1 "ext_register_operand" "0")
9066             (const_int 8)
9067             (const_int 8))
9068           (match_operand 2 "const_int_operand" "n")))
9069    (clobber (reg:CC FLAGS_REG))]
9070   ""
9071   "and{b}\t{%2, %h0|%h0, %2}"
9072   [(set_attr "type" "alu")
9073    (set_attr "length_immediate" "1")
9074    (set_attr "mode" "QI")])
9075
9076 ;; Generated by peephole translating test to and.  This shows up
9077 ;; often in fp comparisons.
9078
9079 (define_insn "*andqi_ext_0_cc"
9080   [(set (reg FLAGS_REG)
9081         (compare
9082           (and:SI
9083             (zero_extract:SI
9084               (match_operand 1 "ext_register_operand" "0")
9085               (const_int 8)
9086               (const_int 8))
9087             (match_operand 2 "const_int_operand" "n"))
9088           (const_int 0)))
9089    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9090                          (const_int 8)
9091                          (const_int 8))
9092         (and:SI
9093           (zero_extract:SI
9094             (match_dup 1)
9095             (const_int 8)
9096             (const_int 8))
9097           (match_dup 2)))]
9098   "ix86_match_ccmode (insn, CCNOmode)"
9099   "and{b}\t{%2, %h0|%h0, %2}"
9100   [(set_attr "type" "alu")
9101    (set_attr "length_immediate" "1")
9102    (set_attr "mode" "QI")])
9103
9104 (define_insn "*andqi_ext_1"
9105   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9106                          (const_int 8)
9107                          (const_int 8))
9108         (and:SI
9109           (zero_extract:SI
9110             (match_operand 1 "ext_register_operand" "0")
9111             (const_int 8)
9112             (const_int 8))
9113           (zero_extend:SI
9114             (match_operand:QI 2 "general_operand" "Qm"))))
9115    (clobber (reg:CC FLAGS_REG))]
9116   "!TARGET_64BIT"
9117   "and{b}\t{%2, %h0|%h0, %2}"
9118   [(set_attr "type" "alu")
9119    (set_attr "length_immediate" "0")
9120    (set_attr "mode" "QI")])
9121
9122 (define_insn "*andqi_ext_1_rex64"
9123   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9124                          (const_int 8)
9125                          (const_int 8))
9126         (and:SI
9127           (zero_extract:SI
9128             (match_operand 1 "ext_register_operand" "0")
9129             (const_int 8)
9130             (const_int 8))
9131           (zero_extend:SI
9132             (match_operand 2 "ext_register_operand" "Q"))))
9133    (clobber (reg:CC FLAGS_REG))]
9134   "TARGET_64BIT"
9135   "and{b}\t{%2, %h0|%h0, %2}"
9136   [(set_attr "type" "alu")
9137    (set_attr "length_immediate" "0")
9138    (set_attr "mode" "QI")])
9139
9140 (define_insn "*andqi_ext_2"
9141   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9142                          (const_int 8)
9143                          (const_int 8))
9144         (and:SI
9145           (zero_extract:SI
9146             (match_operand 1 "ext_register_operand" "%0")
9147             (const_int 8)
9148             (const_int 8))
9149           (zero_extract:SI
9150             (match_operand 2 "ext_register_operand" "Q")
9151             (const_int 8)
9152             (const_int 8))))
9153    (clobber (reg:CC FLAGS_REG))]
9154   ""
9155   "and{b}\t{%h2, %h0|%h0, %h2}"
9156   [(set_attr "type" "alu")
9157    (set_attr "length_immediate" "0")
9158    (set_attr "mode" "QI")])
9159
9160 ;; Convert wide AND instructions with immediate operand to shorter QImode
9161 ;; equivalents when possible.
9162 ;; Don't do the splitting with memory operands, since it introduces risk
9163 ;; of memory mismatch stalls.  We may want to do the splitting for optimizing
9164 ;; for size, but that can (should?) be handled by generic code instead.
9165 (define_split
9166   [(set (match_operand 0 "register_operand" "")
9167         (and (match_operand 1 "register_operand" "")
9168              (match_operand 2 "const_int_operand" "")))
9169    (clobber (reg:CC FLAGS_REG))]
9170    "reload_completed
9171     && QI_REG_P (operands[0])
9172     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9173     && !(~INTVAL (operands[2]) & ~(255 << 8))
9174     && GET_MODE (operands[0]) != QImode"
9175   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9176                    (and:SI (zero_extract:SI (match_dup 1)
9177                                             (const_int 8) (const_int 8))
9178                            (match_dup 2)))
9179               (clobber (reg:CC FLAGS_REG))])]
9180   "operands[0] = gen_lowpart (SImode, operands[0]);
9181    operands[1] = gen_lowpart (SImode, operands[1]);
9182    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9183
9184 ;; Since AND can be encoded with sign extended immediate, this is only
9185 ;; profitable when 7th bit is not set.
9186 (define_split
9187   [(set (match_operand 0 "register_operand" "")
9188         (and (match_operand 1 "general_operand" "")
9189              (match_operand 2 "const_int_operand" "")))
9190    (clobber (reg:CC FLAGS_REG))]
9191    "reload_completed
9192     && ANY_QI_REG_P (operands[0])
9193     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9194     && !(~INTVAL (operands[2]) & ~255)
9195     && !(INTVAL (operands[2]) & 128)
9196     && GET_MODE (operands[0]) != QImode"
9197   [(parallel [(set (strict_low_part (match_dup 0))
9198                    (and:QI (match_dup 1)
9199                            (match_dup 2)))
9200               (clobber (reg:CC FLAGS_REG))])]
9201   "operands[0] = gen_lowpart (QImode, operands[0]);
9202    operands[1] = gen_lowpart (QImode, operands[1]);
9203    operands[2] = gen_lowpart (QImode, operands[2]);")
9204 \f
9205 ;; Logical inclusive OR instructions
9206
9207 ;; %%% This used to optimize known byte-wide and operations to memory.
9208 ;; If this is considered useful, it should be done with splitters.
9209
9210 (define_expand "iordi3"
9211   [(set (match_operand:DI 0 "nonimmediate_operand" "")
9212         (ior:DI (match_operand:DI 1 "nonimmediate_operand" "")
9213                 (match_operand:DI 2 "x86_64_general_operand" "")))
9214    (clobber (reg:CC FLAGS_REG))]
9215   "TARGET_64BIT"
9216   "ix86_expand_binary_operator (IOR, DImode, operands); DONE;")
9217
9218 (define_insn "*iordi_1_rex64"
9219   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
9220         (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9221                 (match_operand:DI 2 "x86_64_general_operand" "re,rme")))
9222    (clobber (reg:CC FLAGS_REG))]
9223   "TARGET_64BIT
9224    && ix86_binary_operator_ok (IOR, DImode, operands)"
9225   "or{q}\t{%2, %0|%0, %2}"
9226   [(set_attr "type" "alu")
9227    (set_attr "mode" "DI")])
9228
9229 (define_insn "*iordi_2_rex64"
9230   [(set (reg FLAGS_REG)
9231         (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9232                          (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
9233                  (const_int 0)))
9234    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
9235         (ior:DI (match_dup 1) (match_dup 2)))]
9236   "TARGET_64BIT
9237    && ix86_match_ccmode (insn, CCNOmode)
9238    && ix86_binary_operator_ok (IOR, DImode, operands)"
9239   "or{q}\t{%2, %0|%0, %2}"
9240   [(set_attr "type" "alu")
9241    (set_attr "mode" "DI")])
9242
9243 (define_insn "*iordi_3_rex64"
9244   [(set (reg FLAGS_REG)
9245         (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
9246                          (match_operand:DI 2 "x86_64_general_operand" "rem"))
9247                  (const_int 0)))
9248    (clobber (match_scratch:DI 0 "=r"))]
9249   "TARGET_64BIT
9250    && ix86_match_ccmode (insn, CCNOmode)
9251    && ix86_binary_operator_ok (IOR, DImode, operands)"
9252   "or{q}\t{%2, %0|%0, %2}"
9253   [(set_attr "type" "alu")
9254    (set_attr "mode" "DI")])
9255
9256
9257 (define_expand "iorsi3"
9258   [(set (match_operand:SI 0 "nonimmediate_operand" "")
9259         (ior:SI (match_operand:SI 1 "nonimmediate_operand" "")
9260                 (match_operand:SI 2 "general_operand" "")))
9261    (clobber (reg:CC FLAGS_REG))]
9262   ""
9263   "ix86_expand_binary_operator (IOR, SImode, operands); DONE;")
9264
9265 (define_insn "*iorsi_1"
9266   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
9267         (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9268                 (match_operand:SI 2 "general_operand" "ri,g")))
9269    (clobber (reg:CC FLAGS_REG))]
9270   "ix86_binary_operator_ok (IOR, SImode, operands)"
9271   "or{l}\t{%2, %0|%0, %2}"
9272   [(set_attr "type" "alu")
9273    (set_attr "mode" "SI")])
9274
9275 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9276 (define_insn "*iorsi_1_zext"
9277   [(set (match_operand:DI 0 "register_operand" "=r")
9278         (zero_extend:DI
9279           (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9280                   (match_operand:SI 2 "general_operand" "g"))))
9281    (clobber (reg:CC FLAGS_REG))]
9282   "TARGET_64BIT && ix86_binary_operator_ok (IOR, SImode, operands)"
9283   "or{l}\t{%2, %k0|%k0, %2}"
9284   [(set_attr "type" "alu")
9285    (set_attr "mode" "SI")])
9286
9287 (define_insn "*iorsi_1_zext_imm"
9288   [(set (match_operand:DI 0 "register_operand" "=r")
9289         (ior:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
9290                 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
9291    (clobber (reg:CC FLAGS_REG))]
9292   "TARGET_64BIT"
9293   "or{l}\t{%2, %k0|%k0, %2}"
9294   [(set_attr "type" "alu")
9295    (set_attr "mode" "SI")])
9296
9297 (define_insn "*iorsi_2"
9298   [(set (reg FLAGS_REG)
9299         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9300                          (match_operand:SI 2 "general_operand" "g,ri"))
9301                  (const_int 0)))
9302    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
9303         (ior:SI (match_dup 1) (match_dup 2)))]
9304   "ix86_match_ccmode (insn, CCNOmode)
9305    && ix86_binary_operator_ok (IOR, SImode, operands)"
9306   "or{l}\t{%2, %0|%0, %2}"
9307   [(set_attr "type" "alu")
9308    (set_attr "mode" "SI")])
9309
9310 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9311 ;; ??? Special case for immediate operand is missing - it is tricky.
9312 (define_insn "*iorsi_2_zext"
9313   [(set (reg FLAGS_REG)
9314         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9315                          (match_operand:SI 2 "general_operand" "g"))
9316                  (const_int 0)))
9317    (set (match_operand:DI 0 "register_operand" "=r")
9318         (zero_extend:DI (ior:SI (match_dup 1) (match_dup 2))))]
9319   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9320    && ix86_binary_operator_ok (IOR, SImode, operands)"
9321   "or{l}\t{%2, %k0|%k0, %2}"
9322   [(set_attr "type" "alu")
9323    (set_attr "mode" "SI")])
9324
9325 (define_insn "*iorsi_2_zext_imm"
9326   [(set (reg FLAGS_REG)
9327         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9328                          (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
9329                  (const_int 0)))
9330    (set (match_operand:DI 0 "register_operand" "=r")
9331         (ior:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
9332   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9333    && ix86_binary_operator_ok (IOR, SImode, operands)"
9334   "or{l}\t{%2, %k0|%k0, %2}"
9335   [(set_attr "type" "alu")
9336    (set_attr "mode" "SI")])
9337
9338 (define_insn "*iorsi_3"
9339   [(set (reg FLAGS_REG)
9340         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9341                          (match_operand:SI 2 "general_operand" "g"))
9342                  (const_int 0)))
9343    (clobber (match_scratch:SI 0 "=r"))]
9344   "ix86_match_ccmode (insn, CCNOmode)
9345    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9346   "or{l}\t{%2, %0|%0, %2}"
9347   [(set_attr "type" "alu")
9348    (set_attr "mode" "SI")])
9349
9350 (define_expand "iorhi3"
9351   [(set (match_operand:HI 0 "nonimmediate_operand" "")
9352         (ior:HI (match_operand:HI 1 "nonimmediate_operand" "")
9353                 (match_operand:HI 2 "general_operand" "")))
9354    (clobber (reg:CC FLAGS_REG))]
9355   "TARGET_HIMODE_MATH"
9356   "ix86_expand_binary_operator (IOR, HImode, operands); DONE;")
9357
9358 (define_insn "*iorhi_1"
9359   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
9360         (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9361                 (match_operand:HI 2 "general_operand" "g,ri")))
9362    (clobber (reg:CC FLAGS_REG))]
9363   "ix86_binary_operator_ok (IOR, HImode, operands)"
9364   "or{w}\t{%2, %0|%0, %2}"
9365   [(set_attr "type" "alu")
9366    (set_attr "mode" "HI")])
9367
9368 (define_insn "*iorhi_2"
9369   [(set (reg FLAGS_REG)
9370         (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9371                          (match_operand:HI 2 "general_operand" "g,ri"))
9372                  (const_int 0)))
9373    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
9374         (ior:HI (match_dup 1) (match_dup 2)))]
9375   "ix86_match_ccmode (insn, CCNOmode)
9376    && ix86_binary_operator_ok (IOR, HImode, operands)"
9377   "or{w}\t{%2, %0|%0, %2}"
9378   [(set_attr "type" "alu")
9379    (set_attr "mode" "HI")])
9380
9381 (define_insn "*iorhi_3"
9382   [(set (reg FLAGS_REG)
9383         (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
9384                          (match_operand:HI 2 "general_operand" "g"))
9385                  (const_int 0)))
9386    (clobber (match_scratch:HI 0 "=r"))]
9387   "ix86_match_ccmode (insn, CCNOmode)
9388    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9389   "or{w}\t{%2, %0|%0, %2}"
9390   [(set_attr "type" "alu")
9391    (set_attr "mode" "HI")])
9392
9393 (define_expand "iorqi3"
9394   [(set (match_operand:QI 0 "nonimmediate_operand" "")
9395         (ior:QI (match_operand:QI 1 "nonimmediate_operand" "")
9396                 (match_operand:QI 2 "general_operand" "")))
9397    (clobber (reg:CC FLAGS_REG))]
9398   "TARGET_QIMODE_MATH"
9399   "ix86_expand_binary_operator (IOR, QImode, operands); DONE;")
9400
9401 ;; %%% Potential partial reg stall on alternative 2.  What to do?
9402 (define_insn "*iorqi_1"
9403   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
9404         (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9405                 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
9406    (clobber (reg:CC FLAGS_REG))]
9407   "ix86_binary_operator_ok (IOR, QImode, operands)"
9408   "@
9409    or{b}\t{%2, %0|%0, %2}
9410    or{b}\t{%2, %0|%0, %2}
9411    or{l}\t{%k2, %k0|%k0, %k2}"
9412   [(set_attr "type" "alu")
9413    (set_attr "mode" "QI,QI,SI")])
9414
9415 (define_insn "*iorqi_1_slp"
9416   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
9417         (ior:QI (match_dup 0)
9418                 (match_operand:QI 1 "general_operand" "qmi,qi")))
9419    (clobber (reg:CC FLAGS_REG))]
9420   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9421    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9422   "or{b}\t{%1, %0|%0, %1}"
9423   [(set_attr "type" "alu1")
9424    (set_attr "mode" "QI")])
9425
9426 (define_insn "*iorqi_2"
9427   [(set (reg FLAGS_REG)
9428         (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9429                          (match_operand:QI 2 "general_operand" "qim,qi"))
9430                  (const_int 0)))
9431    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9432         (ior:QI (match_dup 1) (match_dup 2)))]
9433   "ix86_match_ccmode (insn, CCNOmode)
9434    && ix86_binary_operator_ok (IOR, QImode, operands)"
9435   "or{b}\t{%2, %0|%0, %2}"
9436   [(set_attr "type" "alu")
9437    (set_attr "mode" "QI")])
9438
9439 (define_insn "*iorqi_2_slp"
9440   [(set (reg FLAGS_REG)
9441         (compare (ior:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9442                          (match_operand:QI 1 "general_operand" "qim,qi"))
9443                  (const_int 0)))
9444    (set (strict_low_part (match_dup 0))
9445         (ior:QI (match_dup 0) (match_dup 1)))]
9446   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9447    && ix86_match_ccmode (insn, CCNOmode)
9448    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9449   "or{b}\t{%1, %0|%0, %1}"
9450   [(set_attr "type" "alu1")
9451    (set_attr "mode" "QI")])
9452
9453 (define_insn "*iorqi_3"
9454   [(set (reg FLAGS_REG)
9455         (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
9456                          (match_operand:QI 2 "general_operand" "qim"))
9457                  (const_int 0)))
9458    (clobber (match_scratch:QI 0 "=q"))]
9459   "ix86_match_ccmode (insn, CCNOmode)
9460    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9461   "or{b}\t{%2, %0|%0, %2}"
9462   [(set_attr "type" "alu")
9463    (set_attr "mode" "QI")])
9464
9465 (define_insn "iorqi_ext_0"
9466   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9467                          (const_int 8)
9468                          (const_int 8))
9469         (ior:SI
9470           (zero_extract:SI
9471             (match_operand 1 "ext_register_operand" "0")
9472             (const_int 8)
9473             (const_int 8))
9474           (match_operand 2 "const_int_operand" "n")))
9475    (clobber (reg:CC FLAGS_REG))]
9476   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9477   "or{b}\t{%2, %h0|%h0, %2}"
9478   [(set_attr "type" "alu")
9479    (set_attr "length_immediate" "1")
9480    (set_attr "mode" "QI")])
9481
9482 (define_insn "*iorqi_ext_1"
9483   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9484                          (const_int 8)
9485                          (const_int 8))
9486         (ior:SI
9487           (zero_extract:SI
9488             (match_operand 1 "ext_register_operand" "0")
9489             (const_int 8)
9490             (const_int 8))
9491           (zero_extend:SI
9492             (match_operand:QI 2 "general_operand" "Qm"))))
9493    (clobber (reg:CC FLAGS_REG))]
9494   "!TARGET_64BIT
9495    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9496   "or{b}\t{%2, %h0|%h0, %2}"
9497   [(set_attr "type" "alu")
9498    (set_attr "length_immediate" "0")
9499    (set_attr "mode" "QI")])
9500
9501 (define_insn "*iorqi_ext_1_rex64"
9502   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9503                          (const_int 8)
9504                          (const_int 8))
9505         (ior:SI
9506           (zero_extract:SI
9507             (match_operand 1 "ext_register_operand" "0")
9508             (const_int 8)
9509             (const_int 8))
9510           (zero_extend:SI
9511             (match_operand 2 "ext_register_operand" "Q"))))
9512    (clobber (reg:CC FLAGS_REG))]
9513   "TARGET_64BIT
9514    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9515   "or{b}\t{%2, %h0|%h0, %2}"
9516   [(set_attr "type" "alu")
9517    (set_attr "length_immediate" "0")
9518    (set_attr "mode" "QI")])
9519
9520 (define_insn "*iorqi_ext_2"
9521   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9522                          (const_int 8)
9523                          (const_int 8))
9524         (ior:SI
9525           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
9526                            (const_int 8)
9527                            (const_int 8))
9528           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
9529                            (const_int 8)
9530                            (const_int 8))))
9531    (clobber (reg:CC FLAGS_REG))]
9532   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9533   "ior{b}\t{%h2, %h0|%h0, %h2}"
9534   [(set_attr "type" "alu")
9535    (set_attr "length_immediate" "0")
9536    (set_attr "mode" "QI")])
9537
9538 (define_split
9539   [(set (match_operand 0 "register_operand" "")
9540         (ior (match_operand 1 "register_operand" "")
9541              (match_operand 2 "const_int_operand" "")))
9542    (clobber (reg:CC FLAGS_REG))]
9543    "reload_completed
9544     && QI_REG_P (operands[0])
9545     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9546     && !(INTVAL (operands[2]) & ~(255 << 8))
9547     && GET_MODE (operands[0]) != QImode"
9548   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9549                    (ior:SI (zero_extract:SI (match_dup 1)
9550                                             (const_int 8) (const_int 8))
9551                            (match_dup 2)))
9552               (clobber (reg:CC FLAGS_REG))])]
9553   "operands[0] = gen_lowpart (SImode, operands[0]);
9554    operands[1] = gen_lowpart (SImode, operands[1]);
9555    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9556
9557 ;; Since OR can be encoded with sign extended immediate, this is only
9558 ;; profitable when 7th bit is set.
9559 (define_split
9560   [(set (match_operand 0 "register_operand" "")
9561         (ior (match_operand 1 "general_operand" "")
9562              (match_operand 2 "const_int_operand" "")))
9563    (clobber (reg:CC FLAGS_REG))]
9564    "reload_completed
9565     && ANY_QI_REG_P (operands[0])
9566     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9567     && !(INTVAL (operands[2]) & ~255)
9568     && (INTVAL (operands[2]) & 128)
9569     && GET_MODE (operands[0]) != QImode"
9570   [(parallel [(set (strict_low_part (match_dup 0))
9571                    (ior:QI (match_dup 1)
9572                            (match_dup 2)))
9573               (clobber (reg:CC FLAGS_REG))])]
9574   "operands[0] = gen_lowpart (QImode, operands[0]);
9575    operands[1] = gen_lowpart (QImode, operands[1]);
9576    operands[2] = gen_lowpart (QImode, operands[2]);")
9577 \f
9578 ;; Logical XOR instructions
9579
9580 ;; %%% This used to optimize known byte-wide and operations to memory.
9581 ;; If this is considered useful, it should be done with splitters.
9582
9583 (define_expand "xordi3"
9584   [(set (match_operand:DI 0 "nonimmediate_operand" "")
9585         (xor:DI (match_operand:DI 1 "nonimmediate_operand" "")
9586                 (match_operand:DI 2 "x86_64_general_operand" "")))
9587    (clobber (reg:CC FLAGS_REG))]
9588   "TARGET_64BIT"
9589   "ix86_expand_binary_operator (XOR, DImode, operands); DONE;")
9590
9591 (define_insn "*xordi_1_rex64"
9592   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
9593         (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9594                 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
9595    (clobber (reg:CC FLAGS_REG))]
9596   "TARGET_64BIT
9597    && ix86_binary_operator_ok (XOR, DImode, operands)"
9598   "@
9599    xor{q}\t{%2, %0|%0, %2}
9600    xor{q}\t{%2, %0|%0, %2}"
9601   [(set_attr "type" "alu")
9602    (set_attr "mode" "DI,DI")])
9603
9604 (define_insn "*xordi_2_rex64"
9605   [(set (reg FLAGS_REG)
9606         (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9607                          (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
9608                  (const_int 0)))
9609    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
9610         (xor:DI (match_dup 1) (match_dup 2)))]
9611   "TARGET_64BIT
9612    && ix86_match_ccmode (insn, CCNOmode)
9613    && ix86_binary_operator_ok (XOR, DImode, operands)"
9614   "@
9615    xor{q}\t{%2, %0|%0, %2}
9616    xor{q}\t{%2, %0|%0, %2}"
9617   [(set_attr "type" "alu")
9618    (set_attr "mode" "DI,DI")])
9619
9620 (define_insn "*xordi_3_rex64"
9621   [(set (reg FLAGS_REG)
9622         (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
9623                          (match_operand:DI 2 "x86_64_general_operand" "rem"))
9624                  (const_int 0)))
9625    (clobber (match_scratch:DI 0 "=r"))]
9626   "TARGET_64BIT
9627    && ix86_match_ccmode (insn, CCNOmode)
9628    && ix86_binary_operator_ok (XOR, DImode, operands)"
9629   "xor{q}\t{%2, %0|%0, %2}"
9630   [(set_attr "type" "alu")
9631    (set_attr "mode" "DI")])
9632
9633 (define_expand "xorsi3"
9634   [(set (match_operand:SI 0 "nonimmediate_operand" "")
9635         (xor:SI (match_operand:SI 1 "nonimmediate_operand" "")
9636                 (match_operand:SI 2 "general_operand" "")))
9637    (clobber (reg:CC FLAGS_REG))]
9638   ""
9639   "ix86_expand_binary_operator (XOR, SImode, operands); DONE;")
9640
9641 (define_insn "*xorsi_1"
9642   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
9643         (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9644                 (match_operand:SI 2 "general_operand" "ri,rm")))
9645    (clobber (reg:CC FLAGS_REG))]
9646   "ix86_binary_operator_ok (XOR, SImode, operands)"
9647   "xor{l}\t{%2, %0|%0, %2}"
9648   [(set_attr "type" "alu")
9649    (set_attr "mode" "SI")])
9650
9651 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9652 ;; Add speccase for immediates
9653 (define_insn "*xorsi_1_zext"
9654   [(set (match_operand:DI 0 "register_operand" "=r")
9655         (zero_extend:DI
9656           (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9657                   (match_operand:SI 2 "general_operand" "g"))))
9658    (clobber (reg:CC FLAGS_REG))]
9659   "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
9660   "xor{l}\t{%2, %k0|%k0, %2}"
9661   [(set_attr "type" "alu")
9662    (set_attr "mode" "SI")])
9663
9664 (define_insn "*xorsi_1_zext_imm"
9665   [(set (match_operand:DI 0 "register_operand" "=r")
9666         (xor:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
9667                 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
9668    (clobber (reg:CC FLAGS_REG))]
9669   "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
9670   "xor{l}\t{%2, %k0|%k0, %2}"
9671   [(set_attr "type" "alu")
9672    (set_attr "mode" "SI")])
9673
9674 (define_insn "*xorsi_2"
9675   [(set (reg FLAGS_REG)
9676         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9677                          (match_operand:SI 2 "general_operand" "g,ri"))
9678                  (const_int 0)))
9679    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
9680         (xor:SI (match_dup 1) (match_dup 2)))]
9681   "ix86_match_ccmode (insn, CCNOmode)
9682    && ix86_binary_operator_ok (XOR, SImode, operands)"
9683   "xor{l}\t{%2, %0|%0, %2}"
9684   [(set_attr "type" "alu")
9685    (set_attr "mode" "SI")])
9686
9687 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9688 ;; ??? Special case for immediate operand is missing - it is tricky.
9689 (define_insn "*xorsi_2_zext"
9690   [(set (reg FLAGS_REG)
9691         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9692                          (match_operand:SI 2 "general_operand" "g"))
9693                  (const_int 0)))
9694    (set (match_operand:DI 0 "register_operand" "=r")
9695         (zero_extend:DI (xor:SI (match_dup 1) (match_dup 2))))]
9696   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9697    && ix86_binary_operator_ok (XOR, SImode, operands)"
9698   "xor{l}\t{%2, %k0|%k0, %2}"
9699   [(set_attr "type" "alu")
9700    (set_attr "mode" "SI")])
9701
9702 (define_insn "*xorsi_2_zext_imm"
9703   [(set (reg FLAGS_REG)
9704         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9705                          (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
9706                  (const_int 0)))
9707    (set (match_operand:DI 0 "register_operand" "=r")
9708         (xor:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
9709   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9710    && ix86_binary_operator_ok (XOR, SImode, operands)"
9711   "xor{l}\t{%2, %k0|%k0, %2}"
9712   [(set_attr "type" "alu")
9713    (set_attr "mode" "SI")])
9714
9715 (define_insn "*xorsi_3"
9716   [(set (reg FLAGS_REG)
9717         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9718                          (match_operand:SI 2 "general_operand" "g"))
9719                  (const_int 0)))
9720    (clobber (match_scratch:SI 0 "=r"))]
9721   "ix86_match_ccmode (insn, CCNOmode)
9722    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9723   "xor{l}\t{%2, %0|%0, %2}"
9724   [(set_attr "type" "alu")
9725    (set_attr "mode" "SI")])
9726
9727 (define_expand "xorhi3"
9728   [(set (match_operand:HI 0 "nonimmediate_operand" "")
9729         (xor:HI (match_operand:HI 1 "nonimmediate_operand" "")
9730                 (match_operand:HI 2 "general_operand" "")))
9731    (clobber (reg:CC FLAGS_REG))]
9732   "TARGET_HIMODE_MATH"
9733   "ix86_expand_binary_operator (XOR, HImode, operands); DONE;")
9734
9735 (define_insn "*xorhi_1"
9736   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
9737         (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9738                 (match_operand:HI 2 "general_operand" "g,ri")))
9739    (clobber (reg:CC FLAGS_REG))]
9740   "ix86_binary_operator_ok (XOR, HImode, operands)"
9741   "xor{w}\t{%2, %0|%0, %2}"
9742   [(set_attr "type" "alu")
9743    (set_attr "mode" "HI")])
9744
9745 (define_insn "*xorhi_2"
9746   [(set (reg FLAGS_REG)
9747         (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9748                          (match_operand:HI 2 "general_operand" "g,ri"))
9749                  (const_int 0)))
9750    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
9751         (xor:HI (match_dup 1) (match_dup 2)))]
9752   "ix86_match_ccmode (insn, CCNOmode)
9753    && ix86_binary_operator_ok (XOR, HImode, operands)"
9754   "xor{w}\t{%2, %0|%0, %2}"
9755   [(set_attr "type" "alu")
9756    (set_attr "mode" "HI")])
9757
9758 (define_insn "*xorhi_3"
9759   [(set (reg FLAGS_REG)
9760         (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
9761                          (match_operand:HI 2 "general_operand" "g"))
9762                  (const_int 0)))
9763    (clobber (match_scratch:HI 0 "=r"))]
9764   "ix86_match_ccmode (insn, CCNOmode)
9765    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9766   "xor{w}\t{%2, %0|%0, %2}"
9767   [(set_attr "type" "alu")
9768    (set_attr "mode" "HI")])
9769
9770 (define_expand "xorqi3"
9771   [(set (match_operand:QI 0 "nonimmediate_operand" "")
9772         (xor:QI (match_operand:QI 1 "nonimmediate_operand" "")
9773                 (match_operand:QI 2 "general_operand" "")))
9774    (clobber (reg:CC FLAGS_REG))]
9775   "TARGET_QIMODE_MATH"
9776   "ix86_expand_binary_operator (XOR, QImode, operands); DONE;")
9777
9778 ;; %%% Potential partial reg stall on alternative 2.  What to do?
9779 (define_insn "*xorqi_1"
9780   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
9781         (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9782                 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
9783    (clobber (reg:CC FLAGS_REG))]
9784   "ix86_binary_operator_ok (XOR, QImode, operands)"
9785   "@
9786    xor{b}\t{%2, %0|%0, %2}
9787    xor{b}\t{%2, %0|%0, %2}
9788    xor{l}\t{%k2, %k0|%k0, %k2}"
9789   [(set_attr "type" "alu")
9790    (set_attr "mode" "QI,QI,SI")])
9791
9792 (define_insn "*xorqi_1_slp"
9793   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
9794         (xor:QI (match_dup 0)
9795                 (match_operand:QI 1 "general_operand" "qi,qmi")))
9796    (clobber (reg:CC FLAGS_REG))]
9797   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9798    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9799   "xor{b}\t{%1, %0|%0, %1}"
9800   [(set_attr "type" "alu1")
9801    (set_attr "mode" "QI")])
9802
9803 (define_insn "xorqi_ext_0"
9804   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9805                          (const_int 8)
9806                          (const_int 8))
9807         (xor:SI
9808           (zero_extract:SI
9809             (match_operand 1 "ext_register_operand" "0")
9810             (const_int 8)
9811             (const_int 8))
9812           (match_operand 2 "const_int_operand" "n")))
9813    (clobber (reg:CC FLAGS_REG))]
9814   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9815   "xor{b}\t{%2, %h0|%h0, %2}"
9816   [(set_attr "type" "alu")
9817    (set_attr "length_immediate" "1")
9818    (set_attr "mode" "QI")])
9819
9820 (define_insn "*xorqi_ext_1"
9821   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9822                          (const_int 8)
9823                          (const_int 8))
9824         (xor:SI
9825           (zero_extract:SI
9826             (match_operand 1 "ext_register_operand" "0")
9827             (const_int 8)
9828             (const_int 8))
9829           (zero_extend:SI
9830             (match_operand:QI 2 "general_operand" "Qm"))))
9831    (clobber (reg:CC FLAGS_REG))]
9832   "!TARGET_64BIT
9833    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9834   "xor{b}\t{%2, %h0|%h0, %2}"
9835   [(set_attr "type" "alu")
9836    (set_attr "length_immediate" "0")
9837    (set_attr "mode" "QI")])
9838
9839 (define_insn "*xorqi_ext_1_rex64"
9840   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9841                          (const_int 8)
9842                          (const_int 8))
9843         (xor:SI
9844           (zero_extract:SI
9845             (match_operand 1 "ext_register_operand" "0")
9846             (const_int 8)
9847             (const_int 8))
9848           (zero_extend:SI
9849             (match_operand 2 "ext_register_operand" "Q"))))
9850    (clobber (reg:CC FLAGS_REG))]
9851   "TARGET_64BIT
9852    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9853   "xor{b}\t{%2, %h0|%h0, %2}"
9854   [(set_attr "type" "alu")
9855    (set_attr "length_immediate" "0")
9856    (set_attr "mode" "QI")])
9857
9858 (define_insn "*xorqi_ext_2"
9859   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9860                          (const_int 8)
9861                          (const_int 8))
9862         (xor:SI
9863           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
9864                            (const_int 8)
9865                            (const_int 8))
9866           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
9867                            (const_int 8)
9868                            (const_int 8))))
9869    (clobber (reg:CC FLAGS_REG))]
9870   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9871   "xor{b}\t{%h2, %h0|%h0, %h2}"
9872   [(set_attr "type" "alu")
9873    (set_attr "length_immediate" "0")
9874    (set_attr "mode" "QI")])
9875
9876 (define_insn "*xorqi_cc_1"
9877   [(set (reg FLAGS_REG)
9878         (compare
9879           (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9880                   (match_operand:QI 2 "general_operand" "qim,qi"))
9881           (const_int 0)))
9882    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9883         (xor:QI (match_dup 1) (match_dup 2)))]
9884   "ix86_match_ccmode (insn, CCNOmode)
9885    && ix86_binary_operator_ok (XOR, QImode, operands)"
9886   "xor{b}\t{%2, %0|%0, %2}"
9887   [(set_attr "type" "alu")
9888    (set_attr "mode" "QI")])
9889
9890 (define_insn "*xorqi_2_slp"
9891   [(set (reg FLAGS_REG)
9892         (compare (xor:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9893                          (match_operand:QI 1 "general_operand" "qim,qi"))
9894                  (const_int 0)))
9895    (set (strict_low_part (match_dup 0))
9896         (xor:QI (match_dup 0) (match_dup 1)))]
9897   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9898    && ix86_match_ccmode (insn, CCNOmode)
9899    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
9900   "xor{b}\t{%1, %0|%0, %1}"
9901   [(set_attr "type" "alu1")
9902    (set_attr "mode" "QI")])
9903
9904 (define_insn "*xorqi_cc_2"
9905   [(set (reg FLAGS_REG)
9906         (compare
9907           (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
9908                   (match_operand:QI 2 "general_operand" "qim"))
9909           (const_int 0)))
9910    (clobber (match_scratch:QI 0 "=q"))]
9911   "ix86_match_ccmode (insn, CCNOmode)
9912    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
9913   "xor{b}\t{%2, %0|%0, %2}"
9914   [(set_attr "type" "alu")
9915    (set_attr "mode" "QI")])
9916
9917 (define_insn "*xorqi_cc_ext_1"
9918   [(set (reg FLAGS_REG)
9919         (compare
9920           (xor:SI
9921             (zero_extract:SI
9922               (match_operand 1 "ext_register_operand" "0")
9923               (const_int 8)
9924               (const_int 8))
9925             (match_operand:QI 2 "general_operand" "qmn"))
9926           (const_int 0)))
9927    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
9928                          (const_int 8)
9929                          (const_int 8))
9930         (xor:SI
9931           (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9932           (match_dup 2)))]
9933   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9934   "xor{b}\t{%2, %h0|%h0, %2}"
9935   [(set_attr "type" "alu")
9936    (set_attr "mode" "QI")])
9937
9938 (define_insn "*xorqi_cc_ext_1_rex64"
9939   [(set (reg FLAGS_REG)
9940         (compare
9941           (xor:SI
9942             (zero_extract:SI
9943               (match_operand 1 "ext_register_operand" "0")
9944               (const_int 8)
9945               (const_int 8))
9946             (match_operand:QI 2 "nonmemory_operand" "Qn"))
9947           (const_int 0)))
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 (match_dup 1) (const_int 8) (const_int 8))
9953           (match_dup 2)))]
9954   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9955   "xor{b}\t{%2, %h0|%h0, %2}"
9956   [(set_attr "type" "alu")
9957    (set_attr "mode" "QI")])
9958
9959 (define_expand "xorqi_cc_ext_1"
9960   [(parallel [
9961      (set (reg:CCNO FLAGS_REG)
9962           (compare:CCNO
9963             (xor:SI
9964               (zero_extract:SI
9965                 (match_operand 1 "ext_register_operand" "")
9966                 (const_int 8)
9967                 (const_int 8))
9968               (match_operand:QI 2 "general_operand" ""))
9969             (const_int 0)))
9970      (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
9971                            (const_int 8)
9972                            (const_int 8))
9973           (xor:SI
9974             (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9975             (match_dup 2)))])]
9976   ""
9977   "")
9978
9979 (define_split
9980   [(set (match_operand 0 "register_operand" "")
9981         (xor (match_operand 1 "register_operand" "")
9982              (match_operand 2 "const_int_operand" "")))
9983    (clobber (reg:CC FLAGS_REG))]
9984    "reload_completed
9985     && QI_REG_P (operands[0])
9986     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9987     && !(INTVAL (operands[2]) & ~(255 << 8))
9988     && GET_MODE (operands[0]) != QImode"
9989   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9990                    (xor:SI (zero_extract:SI (match_dup 1)
9991                                             (const_int 8) (const_int 8))
9992                            (match_dup 2)))
9993               (clobber (reg:CC FLAGS_REG))])]
9994   "operands[0] = gen_lowpart (SImode, operands[0]);
9995    operands[1] = gen_lowpart (SImode, operands[1]);
9996    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9997
9998 ;; Since XOR can be encoded with sign extended immediate, this is only
9999 ;; profitable when 7th bit is set.
10000 (define_split
10001   [(set (match_operand 0 "register_operand" "")
10002         (xor (match_operand 1 "general_operand" "")
10003              (match_operand 2 "const_int_operand" "")))
10004    (clobber (reg:CC FLAGS_REG))]
10005    "reload_completed
10006     && ANY_QI_REG_P (operands[0])
10007     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
10008     && !(INTVAL (operands[2]) & ~255)
10009     && (INTVAL (operands[2]) & 128)
10010     && GET_MODE (operands[0]) != QImode"
10011   [(parallel [(set (strict_low_part (match_dup 0))
10012                    (xor:QI (match_dup 1)
10013                            (match_dup 2)))
10014               (clobber (reg:CC FLAGS_REG))])]
10015   "operands[0] = gen_lowpart (QImode, operands[0]);
10016    operands[1] = gen_lowpart (QImode, operands[1]);
10017    operands[2] = gen_lowpart (QImode, operands[2]);")
10018 \f
10019 ;; Negation instructions
10020
10021 (define_expand "negti2"
10022   [(parallel [(set (match_operand:TI 0 "nonimmediate_operand" "")
10023                    (neg:TI (match_operand:TI 1 "nonimmediate_operand" "")))
10024               (clobber (reg:CC FLAGS_REG))])]
10025   "TARGET_64BIT"
10026   "ix86_expand_unary_operator (NEG, TImode, operands); DONE;")
10027
10028 (define_insn "*negti2_1"
10029   [(set (match_operand:TI 0 "nonimmediate_operand" "=ro")
10030         (neg:TI (match_operand:TI 1 "nonimmediate_operand" "0")))
10031    (clobber (reg:CC FLAGS_REG))]
10032   "TARGET_64BIT
10033    && ix86_unary_operator_ok (NEG, TImode, operands)"
10034   "#")
10035
10036 (define_split
10037   [(set (match_operand:TI 0 "nonimmediate_operand" "")
10038         (neg:TI (match_operand:TI 1 "nonimmediate_operand" "")))
10039    (clobber (reg:CC FLAGS_REG))]
10040   "TARGET_64BIT && reload_completed"
10041   [(parallel
10042     [(set (reg:CCZ FLAGS_REG)
10043           (compare:CCZ (neg:DI (match_dup 2)) (const_int 0)))
10044      (set (match_dup 0) (neg:DI (match_dup 2)))])
10045    (parallel
10046     [(set (match_dup 1)
10047           (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
10048                             (match_dup 3))
10049                    (const_int 0)))
10050      (clobber (reg:CC FLAGS_REG))])
10051    (parallel
10052     [(set (match_dup 1)
10053           (neg:DI (match_dup 1)))
10054      (clobber (reg:CC FLAGS_REG))])]
10055   "split_ti (operands+1, 1, operands+2, operands+3);
10056    split_ti (operands+0, 1, operands+0, operands+1);")
10057
10058 (define_expand "negdi2"
10059   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
10060                    (neg:DI (match_operand:DI 1 "nonimmediate_operand" "")))
10061               (clobber (reg:CC FLAGS_REG))])]
10062   ""
10063   "ix86_expand_unary_operator (NEG, DImode, operands); DONE;")
10064
10065 (define_insn "*negdi2_1"
10066   [(set (match_operand:DI 0 "nonimmediate_operand" "=ro")
10067         (neg:DI (match_operand:DI 1 "general_operand" "0")))
10068    (clobber (reg:CC FLAGS_REG))]
10069   "!TARGET_64BIT
10070    && ix86_unary_operator_ok (NEG, DImode, operands)"
10071   "#")
10072
10073 (define_split
10074   [(set (match_operand:DI 0 "nonimmediate_operand" "")
10075         (neg:DI (match_operand:DI 1 "general_operand" "")))
10076    (clobber (reg:CC FLAGS_REG))]
10077   "!TARGET_64BIT && reload_completed"
10078   [(parallel
10079     [(set (reg:CCZ FLAGS_REG)
10080           (compare:CCZ (neg:SI (match_dup 2)) (const_int 0)))
10081      (set (match_dup 0) (neg:SI (match_dup 2)))])
10082    (parallel
10083     [(set (match_dup 1)
10084           (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
10085                             (match_dup 3))
10086                    (const_int 0)))
10087      (clobber (reg:CC FLAGS_REG))])
10088    (parallel
10089     [(set (match_dup 1)
10090           (neg:SI (match_dup 1)))
10091      (clobber (reg:CC FLAGS_REG))])]
10092   "split_di (operands+1, 1, operands+2, operands+3);
10093    split_di (operands+0, 1, operands+0, operands+1);")
10094
10095 (define_insn "*negdi2_1_rex64"
10096   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10097         (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0")))
10098    (clobber (reg:CC FLAGS_REG))]
10099   "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
10100   "neg{q}\t%0"
10101   [(set_attr "type" "negnot")
10102    (set_attr "mode" "DI")])
10103
10104 ;; The problem with neg is that it does not perform (compare x 0),
10105 ;; it really performs (compare 0 x), which leaves us with the zero
10106 ;; flag being the only useful item.
10107
10108 (define_insn "*negdi2_cmpz_rex64"
10109   [(set (reg:CCZ FLAGS_REG)
10110         (compare:CCZ (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
10111                      (const_int 0)))
10112    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10113         (neg:DI (match_dup 1)))]
10114   "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
10115   "neg{q}\t%0"
10116   [(set_attr "type" "negnot")
10117    (set_attr "mode" "DI")])
10118
10119
10120 (define_expand "negsi2"
10121   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
10122                    (neg:SI (match_operand:SI 1 "nonimmediate_operand" "")))
10123               (clobber (reg:CC FLAGS_REG))])]
10124   ""
10125   "ix86_expand_unary_operator (NEG, SImode, operands); DONE;")
10126
10127 (define_insn "*negsi2_1"
10128   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10129         (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0")))
10130    (clobber (reg:CC FLAGS_REG))]
10131   "ix86_unary_operator_ok (NEG, SImode, operands)"
10132   "neg{l}\t%0"
10133   [(set_attr "type" "negnot")
10134    (set_attr "mode" "SI")])
10135
10136 ;; Combine is quite creative about this pattern.
10137 (define_insn "*negsi2_1_zext"
10138   [(set (match_operand:DI 0 "register_operand" "=r")
10139         (lshiftrt:DI (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
10140                                         (const_int 32)))
10141                      (const_int 32)))
10142    (clobber (reg:CC FLAGS_REG))]
10143   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
10144   "neg{l}\t%k0"
10145   [(set_attr "type" "negnot")
10146    (set_attr "mode" "SI")])
10147
10148 ;; The problem with neg is that it does not perform (compare x 0),
10149 ;; it really performs (compare 0 x), which leaves us with the zero
10150 ;; flag being the only useful item.
10151
10152 (define_insn "*negsi2_cmpz"
10153   [(set (reg:CCZ FLAGS_REG)
10154         (compare:CCZ (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
10155                      (const_int 0)))
10156    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10157         (neg:SI (match_dup 1)))]
10158   "ix86_unary_operator_ok (NEG, SImode, operands)"
10159   "neg{l}\t%0"
10160   [(set_attr "type" "negnot")
10161    (set_attr "mode" "SI")])
10162
10163 (define_insn "*negsi2_cmpz_zext"
10164   [(set (reg:CCZ FLAGS_REG)
10165         (compare:CCZ (lshiftrt:DI
10166                        (neg:DI (ashift:DI
10167                                  (match_operand:DI 1 "register_operand" "0")
10168                                  (const_int 32)))
10169                        (const_int 32))
10170                      (const_int 0)))
10171    (set (match_operand:DI 0 "register_operand" "=r")
10172         (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
10173                                         (const_int 32)))
10174                      (const_int 32)))]
10175   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
10176   "neg{l}\t%k0"
10177   [(set_attr "type" "negnot")
10178    (set_attr "mode" "SI")])
10179
10180 (define_expand "neghi2"
10181   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
10182                    (neg:HI (match_operand:HI 1 "nonimmediate_operand" "")))
10183               (clobber (reg:CC FLAGS_REG))])]
10184   "TARGET_HIMODE_MATH"
10185   "ix86_expand_unary_operator (NEG, HImode, operands); DONE;")
10186
10187 (define_insn "*neghi2_1"
10188   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10189         (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0")))
10190    (clobber (reg:CC FLAGS_REG))]
10191   "ix86_unary_operator_ok (NEG, HImode, operands)"
10192   "neg{w}\t%0"
10193   [(set_attr "type" "negnot")
10194    (set_attr "mode" "HI")])
10195
10196 (define_insn "*neghi2_cmpz"
10197   [(set (reg:CCZ FLAGS_REG)
10198         (compare:CCZ (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
10199                      (const_int 0)))
10200    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10201         (neg:HI (match_dup 1)))]
10202   "ix86_unary_operator_ok (NEG, HImode, operands)"
10203   "neg{w}\t%0"
10204   [(set_attr "type" "negnot")
10205    (set_attr "mode" "HI")])
10206
10207 (define_expand "negqi2"
10208   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
10209                    (neg:QI (match_operand:QI 1 "nonimmediate_operand" "")))
10210               (clobber (reg:CC FLAGS_REG))])]
10211   "TARGET_QIMODE_MATH"
10212   "ix86_expand_unary_operator (NEG, QImode, operands); DONE;")
10213
10214 (define_insn "*negqi2_1"
10215   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10216         (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0")))
10217    (clobber (reg:CC FLAGS_REG))]
10218   "ix86_unary_operator_ok (NEG, QImode, operands)"
10219   "neg{b}\t%0"
10220   [(set_attr "type" "negnot")
10221    (set_attr "mode" "QI")])
10222
10223 (define_insn "*negqi2_cmpz"
10224   [(set (reg:CCZ FLAGS_REG)
10225         (compare:CCZ (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
10226                      (const_int 0)))
10227    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10228         (neg:QI (match_dup 1)))]
10229   "ix86_unary_operator_ok (NEG, QImode, operands)"
10230   "neg{b}\t%0"
10231   [(set_attr "type" "negnot")
10232    (set_attr "mode" "QI")])
10233
10234 ;; Changing of sign for FP values is doable using integer unit too.
10235
10236 (define_expand "neg<mode>2"
10237   [(set (match_operand:X87MODEF 0 "register_operand" "")
10238         (neg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "")))]
10239   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
10240   "ix86_expand_fp_absneg_operator (NEG, <MODE>mode, operands); DONE;")
10241
10242 (define_expand "abs<mode>2"
10243   [(set (match_operand:X87MODEF 0 "register_operand" "")
10244         (abs:X87MODEF (match_operand:X87MODEF 1 "register_operand" "")))]
10245   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
10246   "ix86_expand_fp_absneg_operator (ABS, <MODE>mode, operands); DONE;")
10247
10248 (define_insn "*absneg<mode>2_mixed"
10249   [(set (match_operand:MODEF 0 "register_operand" "=x,x,f,!r")
10250         (match_operator:MODEF 3 "absneg_operator"
10251           [(match_operand:MODEF 1 "register_operand" "0,x,0,0")]))
10252    (use (match_operand:<ssevecmode> 2 "nonimmediate_operand" "xm,0,X,X"))
10253    (clobber (reg:CC FLAGS_REG))]
10254   "TARGET_MIX_SSE_I387 && SSE_FLOAT_MODE_P (<MODE>mode)"
10255   "#")
10256
10257 (define_insn "*absneg<mode>2_sse"
10258   [(set (match_operand:MODEF 0 "register_operand" "=x,x,!r")
10259         (match_operator:MODEF 3 "absneg_operator"
10260           [(match_operand:MODEF 1 "register_operand" "0 ,x,0")]))
10261    (use (match_operand:<ssevecmode> 2 "register_operand" "xm,0,X"))
10262    (clobber (reg:CC FLAGS_REG))]
10263   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
10264   "#")
10265
10266 (define_insn "*absneg<mode>2_i387"
10267   [(set (match_operand:X87MODEF 0 "register_operand" "=f,!r")
10268         (match_operator:X87MODEF 3 "absneg_operator"
10269           [(match_operand:X87MODEF 1 "register_operand" "0,0")]))
10270    (use (match_operand 2 "" ""))
10271    (clobber (reg:CC FLAGS_REG))]
10272   "TARGET_80387 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
10273   "#")
10274
10275 (define_expand "negtf2"
10276   [(set (match_operand:TF 0 "register_operand" "")
10277         (neg:TF (match_operand:TF 1 "register_operand" "")))]
10278   "TARGET_64BIT"
10279   "ix86_expand_fp_absneg_operator (NEG, TFmode, operands); DONE;")
10280
10281 (define_expand "abstf2"
10282   [(set (match_operand:TF 0 "register_operand" "")
10283         (abs:TF (match_operand:TF 1 "register_operand" "")))]
10284   "TARGET_64BIT"
10285   "ix86_expand_fp_absneg_operator (ABS, TFmode, operands); DONE;")
10286
10287 (define_insn "*absnegtf2_sse"
10288   [(set (match_operand:TF 0 "register_operand" "=x,x")
10289         (match_operator:TF 3 "absneg_operator"
10290           [(match_operand:TF 1 "register_operand" "0,x")]))
10291    (use (match_operand:TF 2 "nonimmediate_operand" "xm,0"))
10292    (clobber (reg:CC FLAGS_REG))]
10293   "TARGET_64BIT"
10294   "#")
10295
10296 ;; Splitters for fp abs and neg.
10297
10298 (define_split
10299   [(set (match_operand 0 "fp_register_operand" "")
10300         (match_operator 1 "absneg_operator" [(match_dup 0)]))
10301    (use (match_operand 2 "" ""))
10302    (clobber (reg:CC FLAGS_REG))]
10303   "reload_completed"
10304   [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))])
10305
10306 (define_split
10307   [(set (match_operand 0 "register_operand" "")
10308         (match_operator 3 "absneg_operator"
10309           [(match_operand 1 "register_operand" "")]))
10310    (use (match_operand 2 "nonimmediate_operand" ""))
10311    (clobber (reg:CC FLAGS_REG))]
10312   "reload_completed && SSE_REG_P (operands[0])"
10313   [(set (match_dup 0) (match_dup 3))]
10314 {
10315   enum machine_mode mode = GET_MODE (operands[0]);
10316   enum machine_mode vmode = GET_MODE (operands[2]);
10317   rtx tmp;
10318
10319   operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0);
10320   operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0);
10321   if (operands_match_p (operands[0], operands[2]))
10322     {
10323       tmp = operands[1];
10324       operands[1] = operands[2];
10325       operands[2] = tmp;
10326     }
10327   if (GET_CODE (operands[3]) == ABS)
10328     tmp = gen_rtx_AND (vmode, operands[1], operands[2]);
10329   else
10330     tmp = gen_rtx_XOR (vmode, operands[1], operands[2]);
10331   operands[3] = tmp;
10332 })
10333
10334 (define_split
10335   [(set (match_operand:SF 0 "register_operand" "")
10336         (match_operator:SF 1 "absneg_operator" [(match_dup 0)]))
10337    (use (match_operand:V4SF 2 "" ""))
10338    (clobber (reg:CC FLAGS_REG))]
10339   "reload_completed"
10340   [(parallel [(set (match_dup 0) (match_dup 1))
10341               (clobber (reg:CC FLAGS_REG))])]
10342 {
10343   rtx tmp;
10344   operands[0] = gen_lowpart (SImode, operands[0]);
10345   if (GET_CODE (operands[1]) == ABS)
10346     {
10347       tmp = gen_int_mode (0x7fffffff, SImode);
10348       tmp = gen_rtx_AND (SImode, operands[0], tmp);
10349     }
10350   else
10351     {
10352       tmp = gen_int_mode (0x80000000, SImode);
10353       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
10354     }
10355   operands[1] = tmp;
10356 })
10357
10358 (define_split
10359   [(set (match_operand:DF 0 "register_operand" "")
10360         (match_operator:DF 1 "absneg_operator" [(match_dup 0)]))
10361    (use (match_operand 2 "" ""))
10362    (clobber (reg:CC FLAGS_REG))]
10363   "reload_completed"
10364   [(parallel [(set (match_dup 0) (match_dup 1))
10365               (clobber (reg:CC FLAGS_REG))])]
10366 {
10367   rtx tmp;
10368   if (TARGET_64BIT)
10369     {
10370       tmp = gen_lowpart (DImode, operands[0]);
10371       tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63));
10372       operands[0] = tmp;
10373
10374       if (GET_CODE (operands[1]) == ABS)
10375         tmp = const0_rtx;
10376       else
10377         tmp = gen_rtx_NOT (DImode, tmp);
10378     }
10379   else
10380     {
10381       operands[0] = gen_highpart (SImode, operands[0]);
10382       if (GET_CODE (operands[1]) == ABS)
10383         {
10384           tmp = gen_int_mode (0x7fffffff, SImode);
10385           tmp = gen_rtx_AND (SImode, operands[0], tmp);
10386         }
10387       else
10388         {
10389           tmp = gen_int_mode (0x80000000, SImode);
10390           tmp = gen_rtx_XOR (SImode, operands[0], tmp);
10391         }
10392     }
10393   operands[1] = tmp;
10394 })
10395
10396 (define_split
10397   [(set (match_operand:XF 0 "register_operand" "")
10398         (match_operator:XF 1 "absneg_operator" [(match_dup 0)]))
10399    (use (match_operand 2 "" ""))
10400    (clobber (reg:CC FLAGS_REG))]
10401   "reload_completed"
10402   [(parallel [(set (match_dup 0) (match_dup 1))
10403               (clobber (reg:CC FLAGS_REG))])]
10404 {
10405   rtx tmp;
10406   operands[0] = gen_rtx_REG (SImode,
10407                              true_regnum (operands[0])
10408                              + (TARGET_64BIT ? 1 : 2));
10409   if (GET_CODE (operands[1]) == ABS)
10410     {
10411       tmp = GEN_INT (0x7fff);
10412       tmp = gen_rtx_AND (SImode, operands[0], tmp);
10413     }
10414   else
10415     {
10416       tmp = GEN_INT (0x8000);
10417       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
10418     }
10419   operands[1] = tmp;
10420 })
10421
10422 ;; Conditionalize these after reload. If they match before reload, we
10423 ;; lose the clobber and ability to use integer instructions.
10424
10425 (define_insn "*neg<mode>2_1"
10426   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
10427         (neg:X87MODEF (match_operand:X87MODEF 1 "register_operand" "0")))]
10428   "TARGET_80387
10429    && (reload_completed || !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
10430   "fchs"
10431   [(set_attr "type" "fsgn")
10432    (set_attr "mode" "<MODE>")])
10433
10434 (define_insn "*abs<mode>2_1"
10435   [(set (match_operand:X87MODEF 0 "register_operand" "=f")
10436         (abs:X87MODEF (match_operand:X87MODEF 1 "register_operand" "0")))]
10437   "TARGET_80387
10438    && (reload_completed || !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))"
10439   "fabs"
10440   [(set_attr "type" "fsgn")
10441    (set_attr "mode" "<MODE>")])
10442
10443 (define_insn "*negextendsfdf2"
10444   [(set (match_operand:DF 0 "register_operand" "=f")
10445         (neg:DF (float_extend:DF
10446                   (match_operand:SF 1 "register_operand" "0"))))]
10447   "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
10448   "fchs"
10449   [(set_attr "type" "fsgn")
10450    (set_attr "mode" "DF")])
10451
10452 (define_insn "*negextenddfxf2"
10453   [(set (match_operand:XF 0 "register_operand" "=f")
10454         (neg:XF (float_extend:XF
10455                   (match_operand:DF 1 "register_operand" "0"))))]
10456   "TARGET_80387"
10457   "fchs"
10458   [(set_attr "type" "fsgn")
10459    (set_attr "mode" "XF")])
10460
10461 (define_insn "*negextendsfxf2"
10462   [(set (match_operand:XF 0 "register_operand" "=f")
10463         (neg:XF (float_extend:XF
10464                   (match_operand:SF 1 "register_operand" "0"))))]
10465   "TARGET_80387"
10466   "fchs"
10467   [(set_attr "type" "fsgn")
10468    (set_attr "mode" "XF")])
10469
10470 (define_insn "*absextendsfdf2"
10471   [(set (match_operand:DF 0 "register_operand" "=f")
10472         (abs:DF (float_extend:DF
10473                   (match_operand:SF 1 "register_operand" "0"))))]
10474   "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
10475   "fabs"
10476   [(set_attr "type" "fsgn")
10477    (set_attr "mode" "DF")])
10478
10479 (define_insn "*absextenddfxf2"
10480   [(set (match_operand:XF 0 "register_operand" "=f")
10481         (abs:XF (float_extend:XF
10482           (match_operand:DF 1 "register_operand" "0"))))]
10483   "TARGET_80387"
10484   "fabs"
10485   [(set_attr "type" "fsgn")
10486    (set_attr "mode" "XF")])
10487
10488 (define_insn "*absextendsfxf2"
10489   [(set (match_operand:XF 0 "register_operand" "=f")
10490         (abs:XF (float_extend:XF
10491           (match_operand:SF 1 "register_operand" "0"))))]
10492   "TARGET_80387"
10493   "fabs"
10494   [(set_attr "type" "fsgn")
10495    (set_attr "mode" "XF")])
10496
10497 ;; Copysign instructions
10498
10499 (define_mode_iterator CSGNMODE [SF DF TF])
10500 (define_mode_attr CSGNVMODE [(SF "V4SF") (DF "V2DF") (TF "TF")])
10501
10502 (define_expand "copysign<mode>3"
10503   [(match_operand:CSGNMODE 0 "register_operand" "")
10504    (match_operand:CSGNMODE 1 "nonmemory_operand" "")
10505    (match_operand:CSGNMODE 2 "register_operand" "")]
10506   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
10507    || (TARGET_64BIT && (<MODE>mode == TFmode))"
10508 {
10509   ix86_expand_copysign (operands);
10510   DONE;
10511 })
10512
10513 (define_insn_and_split "copysign<mode>3_const"
10514   [(set (match_operand:CSGNMODE 0 "register_operand" "=x")
10515         (unspec:CSGNMODE
10516           [(match_operand:<CSGNVMODE> 1 "vector_move_operand" "xmC")
10517            (match_operand:CSGNMODE 2 "register_operand" "0")
10518            (match_operand:<CSGNVMODE> 3 "nonimmediate_operand" "xm")]
10519           UNSPEC_COPYSIGN))]
10520   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
10521    || (TARGET_64BIT && (<MODE>mode == TFmode))"
10522   "#"
10523   "&& reload_completed"
10524   [(const_int 0)]
10525 {
10526   ix86_split_copysign_const (operands);
10527   DONE;
10528 })
10529
10530 (define_insn "copysign<mode>3_var"
10531   [(set (match_operand:CSGNMODE 0 "register_operand" "=x,x,x,x,x")
10532         (unspec:CSGNMODE
10533           [(match_operand:CSGNMODE 2 "register_operand" "x,0,0,x,x")
10534            (match_operand:CSGNMODE 3 "register_operand" "1,1,x,1,x")
10535            (match_operand:<CSGNVMODE> 4 "nonimmediate_operand" "X,xm,xm,0,0")
10536            (match_operand:<CSGNVMODE> 5 "nonimmediate_operand" "0,xm,1,xm,1")]
10537           UNSPEC_COPYSIGN))
10538    (clobber (match_scratch:<CSGNVMODE> 1 "=x,x,x,x,x"))]
10539   "(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
10540    || (TARGET_64BIT && (<MODE>mode == TFmode))"
10541   "#")
10542
10543 (define_split
10544   [(set (match_operand:CSGNMODE 0 "register_operand" "")
10545         (unspec:CSGNMODE
10546           [(match_operand:CSGNMODE 2 "register_operand" "")
10547            (match_operand:CSGNMODE 3 "register_operand" "")
10548            (match_operand:<CSGNVMODE> 4 "" "")
10549            (match_operand:<CSGNVMODE> 5 "" "")]
10550           UNSPEC_COPYSIGN))
10551    (clobber (match_scratch:<CSGNVMODE> 1 ""))]
10552   "((SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
10553     || (TARGET_64BIT && (<MODE>mode == TFmode)))
10554    && reload_completed"
10555   [(const_int 0)]
10556 {
10557   ix86_split_copysign_var (operands);
10558   DONE;
10559 })
10560 \f
10561 ;; One complement instructions
10562
10563 (define_expand "one_cmpldi2"
10564   [(set (match_operand:DI 0 "nonimmediate_operand" "")
10565         (not:DI (match_operand:DI 1 "nonimmediate_operand" "")))]
10566   "TARGET_64BIT"
10567   "ix86_expand_unary_operator (NOT, DImode, operands); DONE;")
10568
10569 (define_insn "*one_cmpldi2_1_rex64"
10570   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10571         (not:DI (match_operand:DI 1 "nonimmediate_operand" "0")))]
10572   "TARGET_64BIT && ix86_unary_operator_ok (NOT, DImode, operands)"
10573   "not{q}\t%0"
10574   [(set_attr "type" "negnot")
10575    (set_attr "mode" "DI")])
10576
10577 (define_insn "*one_cmpldi2_2_rex64"
10578   [(set (reg FLAGS_REG)
10579         (compare (not:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
10580                  (const_int 0)))
10581    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10582         (not:DI (match_dup 1)))]
10583   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10584    && ix86_unary_operator_ok (NOT, DImode, operands)"
10585   "#"
10586   [(set_attr "type" "alu1")
10587    (set_attr "mode" "DI")])
10588
10589 (define_split
10590   [(set (match_operand 0 "flags_reg_operand" "")
10591         (match_operator 2 "compare_operator"
10592           [(not:DI (match_operand:DI 3 "nonimmediate_operand" ""))
10593            (const_int 0)]))
10594    (set (match_operand:DI 1 "nonimmediate_operand" "")
10595         (not:DI (match_dup 3)))]
10596   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
10597   [(parallel [(set (match_dup 0)
10598                    (match_op_dup 2
10599                      [(xor:DI (match_dup 3) (const_int -1))
10600                       (const_int 0)]))
10601               (set (match_dup 1)
10602                    (xor:DI (match_dup 3) (const_int -1)))])]
10603   "")
10604
10605 (define_expand "one_cmplsi2"
10606   [(set (match_operand:SI 0 "nonimmediate_operand" "")
10607         (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
10608   ""
10609   "ix86_expand_unary_operator (NOT, SImode, operands); DONE;")
10610
10611 (define_insn "*one_cmplsi2_1"
10612   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10613         (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))]
10614   "ix86_unary_operator_ok (NOT, SImode, operands)"
10615   "not{l}\t%0"
10616   [(set_attr "type" "negnot")
10617    (set_attr "mode" "SI")])
10618
10619 ;; ??? Currently never generated - xor is used instead.
10620 (define_insn "*one_cmplsi2_1_zext"
10621   [(set (match_operand:DI 0 "register_operand" "=r")
10622         (zero_extend:DI (not:SI (match_operand:SI 1 "register_operand" "0"))))]
10623   "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
10624   "not{l}\t%k0"
10625   [(set_attr "type" "negnot")
10626    (set_attr "mode" "SI")])
10627
10628 (define_insn "*one_cmplsi2_2"
10629   [(set (reg FLAGS_REG)
10630         (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
10631                  (const_int 0)))
10632    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10633         (not:SI (match_dup 1)))]
10634   "ix86_match_ccmode (insn, CCNOmode)
10635    && ix86_unary_operator_ok (NOT, SImode, operands)"
10636   "#"
10637   [(set_attr "type" "alu1")
10638    (set_attr "mode" "SI")])
10639
10640 (define_split
10641   [(set (match_operand 0 "flags_reg_operand" "")
10642         (match_operator 2 "compare_operator"
10643           [(not:SI (match_operand:SI 3 "nonimmediate_operand" ""))
10644            (const_int 0)]))
10645    (set (match_operand:SI 1 "nonimmediate_operand" "")
10646         (not:SI (match_dup 3)))]
10647   "ix86_match_ccmode (insn, CCNOmode)"
10648   [(parallel [(set (match_dup 0)
10649                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
10650                                     (const_int 0)]))
10651               (set (match_dup 1)
10652                    (xor:SI (match_dup 3) (const_int -1)))])]
10653   "")
10654
10655 ;; ??? Currently never generated - xor is used instead.
10656 (define_insn "*one_cmplsi2_2_zext"
10657   [(set (reg FLAGS_REG)
10658         (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
10659                  (const_int 0)))
10660    (set (match_operand:DI 0 "register_operand" "=r")
10661         (zero_extend:DI (not:SI (match_dup 1))))]
10662   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10663    && ix86_unary_operator_ok (NOT, SImode, operands)"
10664   "#"
10665   [(set_attr "type" "alu1")
10666    (set_attr "mode" "SI")])
10667
10668 (define_split
10669   [(set (match_operand 0 "flags_reg_operand" "")
10670         (match_operator 2 "compare_operator"
10671           [(not:SI (match_operand:SI 3 "register_operand" ""))
10672            (const_int 0)]))
10673    (set (match_operand:DI 1 "register_operand" "")
10674         (zero_extend:DI (not:SI (match_dup 3))))]
10675   "ix86_match_ccmode (insn, CCNOmode)"
10676   [(parallel [(set (match_dup 0)
10677                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
10678                                     (const_int 0)]))
10679               (set (match_dup 1)
10680                    (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])]
10681   "")
10682
10683 (define_expand "one_cmplhi2"
10684   [(set (match_operand:HI 0 "nonimmediate_operand" "")
10685         (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
10686   "TARGET_HIMODE_MATH"
10687   "ix86_expand_unary_operator (NOT, HImode, operands); DONE;")
10688
10689 (define_insn "*one_cmplhi2_1"
10690   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10691         (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))]
10692   "ix86_unary_operator_ok (NOT, HImode, operands)"
10693   "not{w}\t%0"
10694   [(set_attr "type" "negnot")
10695    (set_attr "mode" "HI")])
10696
10697 (define_insn "*one_cmplhi2_2"
10698   [(set (reg FLAGS_REG)
10699         (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
10700                  (const_int 0)))
10701    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10702         (not:HI (match_dup 1)))]
10703   "ix86_match_ccmode (insn, CCNOmode)
10704    && ix86_unary_operator_ok (NEG, HImode, operands)"
10705   "#"
10706   [(set_attr "type" "alu1")
10707    (set_attr "mode" "HI")])
10708
10709 (define_split
10710   [(set (match_operand 0 "flags_reg_operand" "")
10711         (match_operator 2 "compare_operator"
10712           [(not:HI (match_operand:HI 3 "nonimmediate_operand" ""))
10713            (const_int 0)]))
10714    (set (match_operand:HI 1 "nonimmediate_operand" "")
10715         (not:HI (match_dup 3)))]
10716   "ix86_match_ccmode (insn, CCNOmode)"
10717   [(parallel [(set (match_dup 0)
10718                    (match_op_dup 2 [(xor:HI (match_dup 3) (const_int -1))
10719                                     (const_int 0)]))
10720               (set (match_dup 1)
10721                    (xor:HI (match_dup 3) (const_int -1)))])]
10722   "")
10723
10724 ;; %%% Potential partial reg stall on alternative 1.  What to do?
10725 (define_expand "one_cmplqi2"
10726   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10727         (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
10728   "TARGET_QIMODE_MATH"
10729   "ix86_expand_unary_operator (NOT, QImode, operands); DONE;")
10730
10731 (define_insn "*one_cmplqi2_1"
10732   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10733         (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
10734   "ix86_unary_operator_ok (NOT, QImode, operands)"
10735   "@
10736    not{b}\t%0
10737    not{l}\t%k0"
10738   [(set_attr "type" "negnot")
10739    (set_attr "mode" "QI,SI")])
10740
10741 (define_insn "*one_cmplqi2_2"
10742   [(set (reg FLAGS_REG)
10743         (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
10744                  (const_int 0)))
10745    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10746         (not:QI (match_dup 1)))]
10747   "ix86_match_ccmode (insn, CCNOmode)
10748    && ix86_unary_operator_ok (NOT, QImode, operands)"
10749   "#"
10750   [(set_attr "type" "alu1")
10751    (set_attr "mode" "QI")])
10752
10753 (define_split
10754   [(set (match_operand 0 "flags_reg_operand" "")
10755         (match_operator 2 "compare_operator"
10756           [(not:QI (match_operand:QI 3 "nonimmediate_operand" ""))
10757            (const_int 0)]))
10758    (set (match_operand:QI 1 "nonimmediate_operand" "")
10759         (not:QI (match_dup 3)))]
10760   "ix86_match_ccmode (insn, CCNOmode)"
10761   [(parallel [(set (match_dup 0)
10762                    (match_op_dup 2 [(xor:QI (match_dup 3) (const_int -1))
10763                                     (const_int 0)]))
10764               (set (match_dup 1)
10765                    (xor:QI (match_dup 3) (const_int -1)))])]
10766   "")
10767 \f
10768 ;; Arithmetic shift instructions
10769
10770 ;; DImode shifts are implemented using the i386 "shift double" opcode,
10771 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem".  If the shift count
10772 ;; is variable, then the count is in %cl and the "imm" operand is dropped
10773 ;; from the assembler input.
10774 ;;
10775 ;; This instruction shifts the target reg/mem as usual, but instead of
10776 ;; shifting in zeros, bits are shifted in from reg operand.  If the insn
10777 ;; is a left shift double, bits are taken from the high order bits of
10778 ;; reg, else if the insn is a shift right double, bits are taken from the
10779 ;; low order bits of reg.  So if %eax is "1234" and %edx is "5678",
10780 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
10781 ;;
10782 ;; Since sh[lr]d does not change the `reg' operand, that is done
10783 ;; separately, making all shifts emit pairs of shift double and normal
10784 ;; shift.  Since sh[lr]d does not shift more than 31 bits, and we wish to
10785 ;; support a 63 bit shift, each shift where the count is in a reg expands
10786 ;; to a pair of shifts, a branch, a shift by 32 and a label.
10787 ;;
10788 ;; If the shift count is a constant, we need never emit more than one
10789 ;; shift pair, instead using moves and sign extension for counts greater
10790 ;; than 31.
10791
10792 (define_expand "ashlti3"
10793   [(parallel [(set (match_operand:TI 0 "register_operand" "")
10794                    (ashift:TI (match_operand:TI 1 "register_operand" "")
10795                               (match_operand:QI 2 "nonmemory_operand" "")))
10796               (clobber (reg:CC FLAGS_REG))])]
10797   "TARGET_64BIT"
10798 {
10799   if (! immediate_operand (operands[2], QImode))
10800     {
10801       emit_insn (gen_ashlti3_1 (operands[0], operands[1], operands[2]));
10802       DONE;
10803     }
10804   ix86_expand_binary_operator (ASHIFT, TImode, operands);
10805   DONE;
10806 })
10807
10808 (define_insn "ashlti3_1"
10809   [(set (match_operand:TI 0 "register_operand" "=r")
10810         (ashift:TI (match_operand:TI 1 "register_operand" "0")
10811                    (match_operand:QI 2 "register_operand" "c")))
10812    (clobber (match_scratch:DI 3 "=&r"))
10813    (clobber (reg:CC FLAGS_REG))]
10814   "TARGET_64BIT"
10815   "#"
10816   [(set_attr "type" "multi")])
10817
10818 ;; This pattern must be defined before *ashlti3_2 to prevent
10819 ;; combine pass from converting sse2_ashlti3 to *ashlti3_2.
10820
10821 (define_insn "sse2_ashlti3"
10822   [(set (match_operand:TI 0 "register_operand" "=x")
10823         (ashift:TI (match_operand:TI 1 "register_operand" "0")
10824                    (match_operand:SI 2 "const_0_to_255_mul_8_operand" "n")))]
10825   "TARGET_SSE2"
10826 {
10827   operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
10828   return "pslldq\t{%2, %0|%0, %2}";
10829 }
10830   [(set_attr "type" "sseishft")
10831    (set_attr "prefix_data16" "1")
10832    (set_attr "mode" "TI")])
10833
10834 (define_insn "*ashlti3_2"
10835   [(set (match_operand:TI 0 "register_operand" "=r")
10836         (ashift:TI (match_operand:TI 1 "register_operand" "0")
10837                    (match_operand:QI 2 "immediate_operand" "O")))
10838    (clobber (reg:CC FLAGS_REG))]
10839   "TARGET_64BIT"
10840   "#"
10841   [(set_attr "type" "multi")])
10842
10843 (define_split
10844   [(set (match_operand:TI 0 "register_operand" "")
10845         (ashift:TI (match_operand:TI 1 "nonmemory_operand" "")
10846                    (match_operand:QI 2 "register_operand" "")))
10847    (clobber (match_scratch:DI 3 ""))
10848    (clobber (reg:CC FLAGS_REG))]
10849   "TARGET_64BIT && reload_completed"
10850   [(const_int 0)]
10851   "ix86_split_ashl (operands, operands[3], TImode); DONE;")
10852
10853 (define_split
10854   [(set (match_operand:TI 0 "register_operand" "")
10855         (ashift:TI (match_operand:TI 1 "register_operand" "")
10856                    (match_operand:QI 2 "immediate_operand" "")))
10857    (clobber (reg:CC FLAGS_REG))]
10858   "TARGET_64BIT && reload_completed"
10859   [(const_int 0)]
10860   "ix86_split_ashl (operands, NULL_RTX, TImode); DONE;")
10861
10862 (define_insn "x86_64_shld"
10863   [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m,r*m")
10864         (ior:DI (ashift:DI (match_dup 0)
10865                   (match_operand:QI 2 "nonmemory_operand" "J,c"))
10866                 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r,r")
10867                   (minus:QI (const_int 64) (match_dup 2)))))
10868    (clobber (reg:CC FLAGS_REG))]
10869   "TARGET_64BIT"
10870   "@
10871    shld{q}\t{%2, %1, %0|%0, %1, %2}
10872    shld{q}\t{%s2%1, %0|%0, %1, %2}"
10873   [(set_attr "type" "ishift")
10874    (set_attr "prefix_0f" "1")
10875    (set_attr "mode" "DI")
10876    (set_attr "athlon_decode" "vector")
10877    (set_attr "amdfam10_decode" "vector")])
10878
10879 (define_expand "x86_64_shift_adj"
10880   [(set (reg:CCZ FLAGS_REG)
10881         (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
10882                              (const_int 64))
10883                      (const_int 0)))
10884    (set (match_operand:DI 0 "register_operand" "")
10885         (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10886                          (match_operand:DI 1 "register_operand" "")
10887                          (match_dup 0)))
10888    (set (match_dup 1)
10889         (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10890                          (match_operand:DI 3 "register_operand" "r")
10891                          (match_dup 1)))]
10892   "TARGET_64BIT"
10893   "")
10894
10895 (define_expand "ashldi3"
10896   [(set (match_operand:DI 0 "shiftdi_operand" "")
10897         (ashift:DI (match_operand:DI 1 "ashldi_input_operand" "")
10898                    (match_operand:QI 2 "nonmemory_operand" "")))]
10899   ""
10900   "ix86_expand_binary_operator (ASHIFT, DImode, operands); DONE;")
10901
10902 (define_insn "*ashldi3_1_rex64"
10903   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
10904         (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0,l")
10905                    (match_operand:QI 2 "nonmemory_operand" "cJ,M")))
10906    (clobber (reg:CC FLAGS_REG))]
10907   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10908 {
10909   switch (get_attr_type (insn))
10910     {
10911     case TYPE_ALU:
10912       gcc_assert (operands[2] == const1_rtx);
10913       gcc_assert (rtx_equal_p (operands[0], operands[1]));
10914       return "add{q}\t%0, %0";
10915
10916     case TYPE_LEA:
10917       gcc_assert (CONST_INT_P (operands[2]));
10918       gcc_assert ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) <= 3);
10919       operands[1] = gen_rtx_MULT (DImode, operands[1],
10920                                   GEN_INT (1 << INTVAL (operands[2])));
10921       return "lea{q}\t{%a1, %0|%0, %a1}";
10922
10923     default:
10924       if (REG_P (operands[2]))
10925         return "sal{q}\t{%b2, %0|%0, %b2}";
10926       else if (operands[2] == const1_rtx
10927                && (TARGET_SHIFT1 || optimize_size))
10928         return "sal{q}\t%0";
10929       else
10930         return "sal{q}\t{%2, %0|%0, %2}";
10931     }
10932 }
10933   [(set (attr "type")
10934      (cond [(eq_attr "alternative" "1")
10935               (const_string "lea")
10936             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10937                           (const_int 0))
10938                       (match_operand 0 "register_operand" ""))
10939                  (match_operand 2 "const1_operand" ""))
10940               (const_string "alu")
10941            ]
10942            (const_string "ishift")))
10943    (set_attr "mode" "DI")])
10944
10945 ;; Convert lea to the lea pattern to avoid flags dependency.
10946 (define_split
10947   [(set (match_operand:DI 0 "register_operand" "")
10948         (ashift:DI (match_operand:DI 1 "index_register_operand" "")
10949                    (match_operand:QI 2 "immediate_operand" "")))
10950    (clobber (reg:CC FLAGS_REG))]
10951   "TARGET_64BIT && reload_completed
10952    && true_regnum (operands[0]) != true_regnum (operands[1])"
10953   [(set (match_dup 0)
10954         (mult:DI (match_dup 1)
10955                  (match_dup 2)))]
10956   "operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);")
10957
10958 ;; This pattern can't accept a variable shift count, since shifts by
10959 ;; zero don't affect the flags.  We assume that shifts by constant
10960 ;; zero are optimized away.
10961 (define_insn "*ashldi3_cmp_rex64"
10962   [(set (reg FLAGS_REG)
10963         (compare
10964           (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10965                      (match_operand:QI 2 "immediate_operand" "e"))
10966           (const_int 0)))
10967    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10968         (ashift:DI (match_dup 1) (match_dup 2)))]
10969   "TARGET_64BIT
10970    && (optimize_size
10971        || !TARGET_PARTIAL_FLAG_REG_STALL
10972        || (operands[2] == const1_rtx
10973            && (TARGET_SHIFT1
10974                || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
10975    && ix86_match_ccmode (insn, CCGOCmode)
10976    && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10977 {
10978   switch (get_attr_type (insn))
10979     {
10980     case TYPE_ALU:
10981       gcc_assert (operands[2] == const1_rtx);
10982       return "add{q}\t%0, %0";
10983
10984     default:
10985       if (REG_P (operands[2]))
10986         return "sal{q}\t{%b2, %0|%0, %b2}";
10987       else if (operands[2] == const1_rtx
10988                && (TARGET_SHIFT1 || optimize_size))
10989         return "sal{q}\t%0";
10990       else
10991         return "sal{q}\t{%2, %0|%0, %2}";
10992     }
10993 }
10994   [(set (attr "type")
10995      (cond [(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 (define_insn "*ashldi3_cconly_rex64"
11005   [(set (reg FLAGS_REG)
11006         (compare
11007           (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11008                      (match_operand:QI 2 "immediate_operand" "e"))
11009           (const_int 0)))
11010    (clobber (match_scratch:DI 0 "=r"))]
11011   "TARGET_64BIT
11012    && (optimize_size
11013        || !TARGET_PARTIAL_FLAG_REG_STALL
11014        || (operands[2] == const1_rtx
11015            && (TARGET_SHIFT1
11016                || TARGET_DOUBLE_WITH_ADD)))
11017    && ix86_match_ccmode (insn, CCGOCmode)
11018    && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
11019 {
11020   switch (get_attr_type (insn))
11021     {
11022     case TYPE_ALU:
11023       gcc_assert (operands[2] == const1_rtx);
11024       return "add{q}\t%0, %0";
11025
11026     default:
11027       if (REG_P (operands[2]))
11028         return "sal{q}\t{%b2, %0|%0, %b2}";
11029       else if (operands[2] == const1_rtx
11030                && (TARGET_SHIFT1 || optimize_size))
11031         return "sal{q}\t%0";
11032       else
11033         return "sal{q}\t{%2, %0|%0, %2}";
11034     }
11035 }
11036   [(set (attr "type")
11037      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11038                           (const_int 0))
11039                       (match_operand 0 "register_operand" ""))
11040                  (match_operand 2 "const1_operand" ""))
11041               (const_string "alu")
11042            ]
11043            (const_string "ishift")))
11044    (set_attr "mode" "DI")])
11045
11046 (define_insn "*ashldi3_1"
11047   [(set (match_operand:DI 0 "register_operand" "=&r,r")
11048         (ashift:DI (match_operand:DI 1 "reg_or_pm1_operand" "n,0")
11049                    (match_operand:QI 2 "nonmemory_operand" "Jc,Jc")))
11050    (clobber (reg:CC FLAGS_REG))]
11051   "!TARGET_64BIT"
11052   "#"
11053   [(set_attr "type" "multi")])
11054
11055 ;; By default we don't ask for a scratch register, because when DImode
11056 ;; values are manipulated, registers are already at a premium.  But if
11057 ;; we have one handy, we won't turn it away.
11058 (define_peephole2
11059   [(match_scratch:SI 3 "r")
11060    (parallel [(set (match_operand:DI 0 "register_operand" "")
11061                    (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
11062                               (match_operand:QI 2 "nonmemory_operand" "")))
11063               (clobber (reg:CC FLAGS_REG))])
11064    (match_dup 3)]
11065   "!TARGET_64BIT && TARGET_CMOVE"
11066   [(const_int 0)]
11067   "ix86_split_ashl (operands, operands[3], DImode); DONE;")
11068
11069 (define_split
11070   [(set (match_operand:DI 0 "register_operand" "")
11071         (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
11072                    (match_operand:QI 2 "nonmemory_operand" "")))
11073    (clobber (reg:CC FLAGS_REG))]
11074   "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
11075                      ? epilogue_completed : reload_completed)"
11076   [(const_int 0)]
11077   "ix86_split_ashl (operands, NULL_RTX, DImode); DONE;")
11078
11079 (define_insn "x86_shld_1"
11080   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
11081         (ior:SI (ashift:SI (match_dup 0)
11082                   (match_operand:QI 2 "nonmemory_operand" "I,c"))
11083                 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
11084                   (minus:QI (const_int 32) (match_dup 2)))))
11085    (clobber (reg:CC FLAGS_REG))]
11086   ""
11087   "@
11088    shld{l}\t{%2, %1, %0|%0, %1, %2}
11089    shld{l}\t{%s2%1, %0|%0, %1, %2}"
11090   [(set_attr "type" "ishift")
11091    (set_attr "prefix_0f" "1")
11092    (set_attr "mode" "SI")
11093    (set_attr "pent_pair" "np")
11094    (set_attr "athlon_decode" "vector")
11095    (set_attr "amdfam10_decode" "vector")])
11096
11097 (define_expand "x86_shift_adj_1"
11098   [(set (reg:CCZ FLAGS_REG)
11099         (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
11100                              (const_int 32))
11101                      (const_int 0)))
11102    (set (match_operand:SI 0 "register_operand" "")
11103         (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
11104                          (match_operand:SI 1 "register_operand" "")
11105                          (match_dup 0)))
11106    (set (match_dup 1)
11107         (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
11108                          (match_operand:SI 3 "register_operand" "r")
11109                          (match_dup 1)))]
11110   "TARGET_CMOVE"
11111   "")
11112
11113 (define_expand "x86_shift_adj_2"
11114   [(use (match_operand:SI 0 "register_operand" ""))
11115    (use (match_operand:SI 1 "register_operand" ""))
11116    (use (match_operand:QI 2 "register_operand" ""))]
11117   ""
11118 {
11119   rtx label = gen_label_rtx ();
11120   rtx tmp;
11121
11122   emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
11123
11124   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
11125   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
11126   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
11127                               gen_rtx_LABEL_REF (VOIDmode, label),
11128                               pc_rtx);
11129   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
11130   JUMP_LABEL (tmp) = label;
11131
11132   emit_move_insn (operands[0], operands[1]);
11133   ix86_expand_clear (operands[1]);
11134
11135   emit_label (label);
11136   LABEL_NUSES (label) = 1;
11137
11138   DONE;
11139 })
11140
11141 (define_expand "ashlsi3"
11142   [(set (match_operand:SI 0 "nonimmediate_operand" "")
11143         (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
11144                    (match_operand:QI 2 "nonmemory_operand" "")))
11145    (clobber (reg:CC FLAGS_REG))]
11146   ""
11147   "ix86_expand_binary_operator (ASHIFT, SImode, operands); DONE;")
11148
11149 (define_insn "*ashlsi3_1"
11150   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
11151         (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l")
11152                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
11153    (clobber (reg:CC FLAGS_REG))]
11154   "ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11155 {
11156   switch (get_attr_type (insn))
11157     {
11158     case TYPE_ALU:
11159       gcc_assert (operands[2] == const1_rtx);
11160       gcc_assert (rtx_equal_p (operands[0], operands[1]));
11161       return "add{l}\t%0, %0";
11162
11163     case TYPE_LEA:
11164       return "#";
11165
11166     default:
11167       if (REG_P (operands[2]))
11168         return "sal{l}\t{%b2, %0|%0, %b2}";
11169       else if (operands[2] == const1_rtx
11170                && (TARGET_SHIFT1 || optimize_size))
11171         return "sal{l}\t%0";
11172       else
11173         return "sal{l}\t{%2, %0|%0, %2}";
11174     }
11175 }
11176   [(set (attr "type")
11177      (cond [(eq_attr "alternative" "1")
11178               (const_string "lea")
11179             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11180                           (const_int 0))
11181                       (match_operand 0 "register_operand" ""))
11182                  (match_operand 2 "const1_operand" ""))
11183               (const_string "alu")
11184            ]
11185            (const_string "ishift")))
11186    (set_attr "mode" "SI")])
11187
11188 ;; Convert lea to the lea pattern to avoid flags dependency.
11189 (define_split
11190   [(set (match_operand 0 "register_operand" "")
11191         (ashift (match_operand 1 "index_register_operand" "")
11192                 (match_operand:QI 2 "const_int_operand" "")))
11193    (clobber (reg:CC FLAGS_REG))]
11194   "reload_completed
11195    && true_regnum (operands[0]) != true_regnum (operands[1])
11196    && GET_MODE_SIZE (GET_MODE (operands[0])) <= 4"
11197   [(const_int 0)]
11198 {
11199   rtx pat;
11200   enum machine_mode mode = GET_MODE (operands[0]);
11201
11202   if (GET_MODE_SIZE (mode) < 4)
11203     operands[0] = gen_lowpart (SImode, operands[0]);
11204   if (mode != Pmode)
11205     operands[1] = gen_lowpart (Pmode, operands[1]);
11206   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
11207
11208   pat = gen_rtx_MULT (Pmode, operands[1], operands[2]);
11209   if (Pmode != SImode)
11210     pat = gen_rtx_SUBREG (SImode, pat, 0);
11211   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
11212   DONE;
11213 })
11214
11215 ;; Rare case of shifting RSP is handled by generating move and shift
11216 (define_split
11217   [(set (match_operand 0 "register_operand" "")
11218         (ashift (match_operand 1 "register_operand" "")
11219                 (match_operand:QI 2 "const_int_operand" "")))
11220    (clobber (reg:CC FLAGS_REG))]
11221   "reload_completed
11222    && true_regnum (operands[0]) != true_regnum (operands[1])"
11223   [(const_int 0)]
11224 {
11225   rtx pat, clob;
11226   emit_move_insn (operands[0], operands[1]);
11227   pat = gen_rtx_SET (VOIDmode, operands[0],
11228                      gen_rtx_ASHIFT (GET_MODE (operands[0]),
11229                                      operands[0], operands[2]));
11230   clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
11231   emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, pat, clob)));
11232   DONE;
11233 })
11234
11235 (define_insn "*ashlsi3_1_zext"
11236   [(set (match_operand:DI 0 "register_operand" "=r,r")
11237         (zero_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "0,l")
11238                         (match_operand:QI 2 "nonmemory_operand" "cI,M"))))
11239    (clobber (reg:CC FLAGS_REG))]
11240   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11241 {
11242   switch (get_attr_type (insn))
11243     {
11244     case TYPE_ALU:
11245       gcc_assert (operands[2] == const1_rtx);
11246       return "add{l}\t%k0, %k0";
11247
11248     case TYPE_LEA:
11249       return "#";
11250
11251     default:
11252       if (REG_P (operands[2]))
11253         return "sal{l}\t{%b2, %k0|%k0, %b2}";
11254       else if (operands[2] == const1_rtx
11255                && (TARGET_SHIFT1 || optimize_size))
11256         return "sal{l}\t%k0";
11257       else
11258         return "sal{l}\t{%2, %k0|%k0, %2}";
11259     }
11260 }
11261   [(set (attr "type")
11262      (cond [(eq_attr "alternative" "1")
11263               (const_string "lea")
11264             (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11265                      (const_int 0))
11266                  (match_operand 2 "const1_operand" ""))
11267               (const_string "alu")
11268            ]
11269            (const_string "ishift")))
11270    (set_attr "mode" "SI")])
11271
11272 ;; Convert lea to the lea pattern to avoid flags dependency.
11273 (define_split
11274   [(set (match_operand:DI 0 "register_operand" "")
11275         (zero_extend:DI (ashift (match_operand 1 "register_operand" "")
11276                                 (match_operand:QI 2 "const_int_operand" ""))))
11277    (clobber (reg:CC FLAGS_REG))]
11278   "TARGET_64BIT && reload_completed
11279    && true_regnum (operands[0]) != true_regnum (operands[1])"
11280   [(set (match_dup 0) (zero_extend:DI
11281                         (subreg:SI (mult:SI (match_dup 1)
11282                                             (match_dup 2)) 0)))]
11283 {
11284   operands[1] = gen_lowpart (Pmode, operands[1]);
11285   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
11286 })
11287
11288 ;; This pattern can't accept a variable shift count, since shifts by
11289 ;; zero don't affect the flags.  We assume that shifts by constant
11290 ;; zero are optimized away.
11291 (define_insn "*ashlsi3_cmp"
11292   [(set (reg FLAGS_REG)
11293         (compare
11294           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11295                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11296           (const_int 0)))
11297    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11298         (ashift:SI (match_dup 1) (match_dup 2)))]
11299    "(optimize_size
11300      || !TARGET_PARTIAL_FLAG_REG_STALL
11301      || (operands[2] == const1_rtx
11302          && (TARGET_SHIFT1
11303              || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
11304    && ix86_match_ccmode (insn, CCGOCmode)
11305    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11306 {
11307   switch (get_attr_type (insn))
11308     {
11309     case TYPE_ALU:
11310       gcc_assert (operands[2] == const1_rtx);
11311       return "add{l}\t%0, %0";
11312
11313     default:
11314       if (REG_P (operands[2]))
11315         return "sal{l}\t{%b2, %0|%0, %b2}";
11316       else if (operands[2] == const1_rtx
11317                && (TARGET_SHIFT1 || optimize_size))
11318         return "sal{l}\t%0";
11319       else
11320         return "sal{l}\t{%2, %0|%0, %2}";
11321     }
11322 }
11323   [(set (attr "type")
11324      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11325                           (const_int 0))
11326                       (match_operand 0 "register_operand" ""))
11327                  (match_operand 2 "const1_operand" ""))
11328               (const_string "alu")
11329            ]
11330            (const_string "ishift")))
11331    (set_attr "mode" "SI")])
11332
11333 (define_insn "*ashlsi3_cconly"
11334   [(set (reg FLAGS_REG)
11335         (compare
11336           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11337                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11338           (const_int 0)))
11339    (clobber (match_scratch:SI 0 "=r"))]
11340   "(optimize_size
11341     || !TARGET_PARTIAL_FLAG_REG_STALL
11342     || (operands[2] == const1_rtx
11343         && (TARGET_SHIFT1
11344             || TARGET_DOUBLE_WITH_ADD)))
11345    && ix86_match_ccmode (insn, CCGOCmode)
11346    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11347 {
11348   switch (get_attr_type (insn))
11349     {
11350     case TYPE_ALU:
11351       gcc_assert (operands[2] == const1_rtx);
11352       return "add{l}\t%0, %0";
11353
11354     default:
11355       if (REG_P (operands[2]))
11356         return "sal{l}\t{%b2, %0|%0, %b2}";
11357       else if (operands[2] == const1_rtx
11358                && (TARGET_SHIFT1 || optimize_size))
11359         return "sal{l}\t%0";
11360       else
11361         return "sal{l}\t{%2, %0|%0, %2}";
11362     }
11363 }
11364   [(set (attr "type")
11365      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11366                           (const_int 0))
11367                       (match_operand 0 "register_operand" ""))
11368                  (match_operand 2 "const1_operand" ""))
11369               (const_string "alu")
11370            ]
11371            (const_string "ishift")))
11372    (set_attr "mode" "SI")])
11373
11374 (define_insn "*ashlsi3_cmp_zext"
11375   [(set (reg FLAGS_REG)
11376         (compare
11377           (ashift:SI (match_operand:SI 1 "register_operand" "0")
11378                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11379           (const_int 0)))
11380    (set (match_operand:DI 0 "register_operand" "=r")
11381         (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
11382   "TARGET_64BIT
11383    && (optimize_size
11384        || !TARGET_PARTIAL_FLAG_REG_STALL
11385        || (operands[2] == const1_rtx
11386            && (TARGET_SHIFT1
11387                || TARGET_DOUBLE_WITH_ADD)))
11388    && ix86_match_ccmode (insn, CCGOCmode)
11389    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11390 {
11391   switch (get_attr_type (insn))
11392     {
11393     case TYPE_ALU:
11394       gcc_assert (operands[2] == const1_rtx);
11395       return "add{l}\t%k0, %k0";
11396
11397     default:
11398       if (REG_P (operands[2]))
11399         return "sal{l}\t{%b2, %k0|%k0, %b2}";
11400       else if (operands[2] == const1_rtx
11401                && (TARGET_SHIFT1 || optimize_size))
11402         return "sal{l}\t%k0";
11403       else
11404         return "sal{l}\t{%2, %k0|%k0, %2}";
11405     }
11406 }
11407   [(set (attr "type")
11408      (cond [(and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11409                      (const_int 0))
11410                  (match_operand 2 "const1_operand" ""))
11411               (const_string "alu")
11412            ]
11413            (const_string "ishift")))
11414    (set_attr "mode" "SI")])
11415
11416 (define_expand "ashlhi3"
11417   [(set (match_operand:HI 0 "nonimmediate_operand" "")
11418         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "")
11419                    (match_operand:QI 2 "nonmemory_operand" "")))
11420    (clobber (reg:CC FLAGS_REG))]
11421   "TARGET_HIMODE_MATH"
11422   "ix86_expand_binary_operator (ASHIFT, HImode, operands); DONE;")
11423
11424 (define_insn "*ashlhi3_1_lea"
11425   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
11426         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
11427                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
11428    (clobber (reg:CC FLAGS_REG))]
11429   "!TARGET_PARTIAL_REG_STALL
11430    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11431 {
11432   switch (get_attr_type (insn))
11433     {
11434     case TYPE_LEA:
11435       return "#";
11436     case TYPE_ALU:
11437       gcc_assert (operands[2] == const1_rtx);
11438       return "add{w}\t%0, %0";
11439
11440     default:
11441       if (REG_P (operands[2]))
11442         return "sal{w}\t{%b2, %0|%0, %b2}";
11443       else if (operands[2] == const1_rtx
11444                && (TARGET_SHIFT1 || optimize_size))
11445         return "sal{w}\t%0";
11446       else
11447         return "sal{w}\t{%2, %0|%0, %2}";
11448     }
11449 }
11450   [(set (attr "type")
11451      (cond [(eq_attr "alternative" "1")
11452               (const_string "lea")
11453             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11454                           (const_int 0))
11455                       (match_operand 0 "register_operand" ""))
11456                  (match_operand 2 "const1_operand" ""))
11457               (const_string "alu")
11458            ]
11459            (const_string "ishift")))
11460    (set_attr "mode" "HI,SI")])
11461
11462 (define_insn "*ashlhi3_1"
11463   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11464         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11465                    (match_operand:QI 2 "nonmemory_operand" "cI")))
11466    (clobber (reg:CC FLAGS_REG))]
11467   "TARGET_PARTIAL_REG_STALL
11468    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11469 {
11470   switch (get_attr_type (insn))
11471     {
11472     case TYPE_ALU:
11473       gcc_assert (operands[2] == const1_rtx);
11474       return "add{w}\t%0, %0";
11475
11476     default:
11477       if (REG_P (operands[2]))
11478         return "sal{w}\t{%b2, %0|%0, %b2}";
11479       else if (operands[2] == const1_rtx
11480                && (TARGET_SHIFT1 || optimize_size))
11481         return "sal{w}\t%0";
11482       else
11483         return "sal{w}\t{%2, %0|%0, %2}";
11484     }
11485 }
11486   [(set (attr "type")
11487      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11488                           (const_int 0))
11489                       (match_operand 0 "register_operand" ""))
11490                  (match_operand 2 "const1_operand" ""))
11491               (const_string "alu")
11492            ]
11493            (const_string "ishift")))
11494    (set_attr "mode" "HI")])
11495
11496 ;; This pattern can't accept a variable shift count, since shifts by
11497 ;; zero don't affect the flags.  We assume that shifts by constant
11498 ;; zero are optimized away.
11499 (define_insn "*ashlhi3_cmp"
11500   [(set (reg FLAGS_REG)
11501         (compare
11502           (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11503                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11504           (const_int 0)))
11505    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11506         (ashift:HI (match_dup 1) (match_dup 2)))]
11507   "(optimize_size
11508     || !TARGET_PARTIAL_FLAG_REG_STALL
11509     || (operands[2] == const1_rtx
11510         && (TARGET_SHIFT1
11511             || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
11512    && ix86_match_ccmode (insn, CCGOCmode)
11513    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11514 {
11515   switch (get_attr_type (insn))
11516     {
11517     case TYPE_ALU:
11518       gcc_assert (operands[2] == const1_rtx);
11519       return "add{w}\t%0, %0";
11520
11521     default:
11522       if (REG_P (operands[2]))
11523         return "sal{w}\t{%b2, %0|%0, %b2}";
11524       else if (operands[2] == const1_rtx
11525                && (TARGET_SHIFT1 || optimize_size))
11526         return "sal{w}\t%0";
11527       else
11528         return "sal{w}\t{%2, %0|%0, %2}";
11529     }
11530 }
11531   [(set (attr "type")
11532      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11533                           (const_int 0))
11534                       (match_operand 0 "register_operand" ""))
11535                  (match_operand 2 "const1_operand" ""))
11536               (const_string "alu")
11537            ]
11538            (const_string "ishift")))
11539    (set_attr "mode" "HI")])
11540
11541 (define_insn "*ashlhi3_cconly"
11542   [(set (reg FLAGS_REG)
11543         (compare
11544           (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11545                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11546           (const_int 0)))
11547    (clobber (match_scratch:HI 0 "=r"))]
11548   "(optimize_size
11549     || !TARGET_PARTIAL_FLAG_REG_STALL
11550     || (operands[2] == const1_rtx
11551         && (TARGET_SHIFT1
11552             || TARGET_DOUBLE_WITH_ADD)))
11553    && ix86_match_ccmode (insn, CCGOCmode)
11554    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11555 {
11556   switch (get_attr_type (insn))
11557     {
11558     case TYPE_ALU:
11559       gcc_assert (operands[2] == const1_rtx);
11560       return "add{w}\t%0, %0";
11561
11562     default:
11563       if (REG_P (operands[2]))
11564         return "sal{w}\t{%b2, %0|%0, %b2}";
11565       else if (operands[2] == const1_rtx
11566                && (TARGET_SHIFT1 || optimize_size))
11567         return "sal{w}\t%0";
11568       else
11569         return "sal{w}\t{%2, %0|%0, %2}";
11570     }
11571 }
11572   [(set (attr "type")
11573      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11574                           (const_int 0))
11575                       (match_operand 0 "register_operand" ""))
11576                  (match_operand 2 "const1_operand" ""))
11577               (const_string "alu")
11578            ]
11579            (const_string "ishift")))
11580    (set_attr "mode" "HI")])
11581
11582 (define_expand "ashlqi3"
11583   [(set (match_operand:QI 0 "nonimmediate_operand" "")
11584         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "")
11585                    (match_operand:QI 2 "nonmemory_operand" "")))
11586    (clobber (reg:CC FLAGS_REG))]
11587   "TARGET_QIMODE_MATH"
11588   "ix86_expand_binary_operator (ASHIFT, QImode, operands); DONE;")
11589
11590 ;; %%% Potential partial reg stall on alternative 2.  What to do?
11591
11592 (define_insn "*ashlqi3_1_lea"
11593   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r")
11594         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
11595                    (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
11596    (clobber (reg:CC FLAGS_REG))]
11597   "!TARGET_PARTIAL_REG_STALL
11598    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11599 {
11600   switch (get_attr_type (insn))
11601     {
11602     case TYPE_LEA:
11603       return "#";
11604     case TYPE_ALU:
11605       gcc_assert (operands[2] == const1_rtx);
11606       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
11607         return "add{l}\t%k0, %k0";
11608       else
11609         return "add{b}\t%0, %0";
11610
11611     default:
11612       if (REG_P (operands[2]))
11613         {
11614           if (get_attr_mode (insn) == MODE_SI)
11615             return "sal{l}\t{%b2, %k0|%k0, %b2}";
11616           else
11617             return "sal{b}\t{%b2, %0|%0, %b2}";
11618         }
11619       else if (operands[2] == const1_rtx
11620                && (TARGET_SHIFT1 || optimize_size))
11621         {
11622           if (get_attr_mode (insn) == MODE_SI)
11623             return "sal{l}\t%0";
11624           else
11625             return "sal{b}\t%0";
11626         }
11627       else
11628         {
11629           if (get_attr_mode (insn) == MODE_SI)
11630             return "sal{l}\t{%2, %k0|%k0, %2}";
11631           else
11632             return "sal{b}\t{%2, %0|%0, %2}";
11633         }
11634     }
11635 }
11636   [(set (attr "type")
11637      (cond [(eq_attr "alternative" "2")
11638               (const_string "lea")
11639             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11640                           (const_int 0))
11641                       (match_operand 0 "register_operand" ""))
11642                  (match_operand 2 "const1_operand" ""))
11643               (const_string "alu")
11644            ]
11645            (const_string "ishift")))
11646    (set_attr "mode" "QI,SI,SI")])
11647
11648 (define_insn "*ashlqi3_1"
11649   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
11650         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11651                    (match_operand:QI 2 "nonmemory_operand" "cI,cI")))
11652    (clobber (reg:CC FLAGS_REG))]
11653   "TARGET_PARTIAL_REG_STALL
11654    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11655 {
11656   switch (get_attr_type (insn))
11657     {
11658     case TYPE_ALU:
11659       gcc_assert (operands[2] == const1_rtx);
11660       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
11661         return "add{l}\t%k0, %k0";
11662       else
11663         return "add{b}\t%0, %0";
11664
11665     default:
11666       if (REG_P (operands[2]))
11667         {
11668           if (get_attr_mode (insn) == MODE_SI)
11669             return "sal{l}\t{%b2, %k0|%k0, %b2}";
11670           else
11671             return "sal{b}\t{%b2, %0|%0, %b2}";
11672         }
11673       else if (operands[2] == const1_rtx
11674                && (TARGET_SHIFT1 || optimize_size))
11675         {
11676           if (get_attr_mode (insn) == MODE_SI)
11677             return "sal{l}\t%0";
11678           else
11679             return "sal{b}\t%0";
11680         }
11681       else
11682         {
11683           if (get_attr_mode (insn) == MODE_SI)
11684             return "sal{l}\t{%2, %k0|%k0, %2}";
11685           else
11686             return "sal{b}\t{%2, %0|%0, %2}";
11687         }
11688     }
11689 }
11690   [(set (attr "type")
11691      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11692                           (const_int 0))
11693                       (match_operand 0 "register_operand" ""))
11694                  (match_operand 2 "const1_operand" ""))
11695               (const_string "alu")
11696            ]
11697            (const_string "ishift")))
11698    (set_attr "mode" "QI,SI")])
11699
11700 ;; This pattern can't accept a variable shift count, since shifts by
11701 ;; zero don't affect the flags.  We assume that shifts by constant
11702 ;; zero are optimized away.
11703 (define_insn "*ashlqi3_cmp"
11704   [(set (reg FLAGS_REG)
11705         (compare
11706           (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11707                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11708           (const_int 0)))
11709    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11710         (ashift:QI (match_dup 1) (match_dup 2)))]
11711   "(optimize_size
11712     || !TARGET_PARTIAL_FLAG_REG_STALL
11713     || (operands[2] == const1_rtx
11714         && (TARGET_SHIFT1
11715             || (TARGET_DOUBLE_WITH_ADD && REG_P (operands[0])))))
11716    && ix86_match_ccmode (insn, CCGOCmode)
11717    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11718 {
11719   switch (get_attr_type (insn))
11720     {
11721     case TYPE_ALU:
11722       gcc_assert (operands[2] == const1_rtx);
11723       return "add{b}\t%0, %0";
11724
11725     default:
11726       if (REG_P (operands[2]))
11727         return "sal{b}\t{%b2, %0|%0, %b2}";
11728       else if (operands[2] == const1_rtx
11729                && (TARGET_SHIFT1 || optimize_size))
11730         return "sal{b}\t%0";
11731       else
11732         return "sal{b}\t{%2, %0|%0, %2}";
11733     }
11734 }
11735   [(set (attr "type")
11736      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11737                           (const_int 0))
11738                       (match_operand 0 "register_operand" ""))
11739                  (match_operand 2 "const1_operand" ""))
11740               (const_string "alu")
11741            ]
11742            (const_string "ishift")))
11743    (set_attr "mode" "QI")])
11744
11745 (define_insn "*ashlqi3_cconly"
11746   [(set (reg FLAGS_REG)
11747         (compare
11748           (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11749                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
11750           (const_int 0)))
11751    (clobber (match_scratch:QI 0 "=q"))]
11752   "(optimize_size
11753     || !TARGET_PARTIAL_FLAG_REG_STALL
11754     || (operands[2] == const1_rtx
11755         && (TARGET_SHIFT1
11756             || TARGET_DOUBLE_WITH_ADD)))
11757    && ix86_match_ccmode (insn, CCGOCmode)
11758    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11759 {
11760   switch (get_attr_type (insn))
11761     {
11762     case TYPE_ALU:
11763       gcc_assert (operands[2] == const1_rtx);
11764       return "add{b}\t%0, %0";
11765
11766     default:
11767       if (REG_P (operands[2]))
11768         return "sal{b}\t{%b2, %0|%0, %b2}";
11769       else if (operands[2] == const1_rtx
11770                && (TARGET_SHIFT1 || optimize_size))
11771         return "sal{b}\t%0";
11772       else
11773         return "sal{b}\t{%2, %0|%0, %2}";
11774     }
11775 }
11776   [(set (attr "type")
11777      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11778                           (const_int 0))
11779                       (match_operand 0 "register_operand" ""))
11780                  (match_operand 2 "const1_operand" ""))
11781               (const_string "alu")
11782            ]
11783            (const_string "ishift")))
11784    (set_attr "mode" "QI")])
11785
11786 ;; See comment above `ashldi3' about how this works.
11787
11788 (define_expand "ashrti3"
11789   [(parallel [(set (match_operand:TI 0 "register_operand" "")
11790                    (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
11791                                 (match_operand:QI 2 "nonmemory_operand" "")))
11792               (clobber (reg:CC FLAGS_REG))])]
11793   "TARGET_64BIT"
11794 {
11795   if (! immediate_operand (operands[2], QImode))
11796     {
11797       emit_insn (gen_ashrti3_1 (operands[0], operands[1], operands[2]));
11798       DONE;
11799     }
11800   ix86_expand_binary_operator (ASHIFTRT, TImode, operands);
11801   DONE;
11802 })
11803
11804 (define_insn "ashrti3_1"
11805   [(set (match_operand:TI 0 "register_operand" "=r")
11806         (ashiftrt:TI (match_operand:TI 1 "register_operand" "0")
11807                      (match_operand:QI 2 "register_operand" "c")))
11808    (clobber (match_scratch:DI 3 "=&r"))
11809    (clobber (reg:CC FLAGS_REG))]
11810   "TARGET_64BIT"
11811   "#"
11812   [(set_attr "type" "multi")])
11813
11814 (define_insn "*ashrti3_2"
11815   [(set (match_operand:TI 0 "register_operand" "=r")
11816         (ashiftrt:TI (match_operand:TI 1 "register_operand" "0")
11817                      (match_operand:QI 2 "immediate_operand" "O")))
11818    (clobber (reg:CC FLAGS_REG))]
11819   "TARGET_64BIT"
11820   "#"
11821   [(set_attr "type" "multi")])
11822
11823 (define_split
11824   [(set (match_operand:TI 0 "register_operand" "")
11825         (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
11826                      (match_operand:QI 2 "register_operand" "")))
11827    (clobber (match_scratch:DI 3 ""))
11828    (clobber (reg:CC FLAGS_REG))]
11829   "TARGET_64BIT && reload_completed"
11830   [(const_int 0)]
11831   "ix86_split_ashr (operands, operands[3], TImode); DONE;")
11832
11833 (define_split
11834   [(set (match_operand:TI 0 "register_operand" "")
11835         (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
11836                      (match_operand:QI 2 "immediate_operand" "")))
11837    (clobber (reg:CC FLAGS_REG))]
11838   "TARGET_64BIT && reload_completed"
11839   [(const_int 0)]
11840   "ix86_split_ashr (operands, NULL_RTX, TImode); DONE;")
11841
11842 (define_insn "x86_64_shrd"
11843   [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m,r*m")
11844         (ior:DI (ashiftrt:DI (match_dup 0)
11845                   (match_operand:QI 2 "nonmemory_operand" "J,c"))
11846                 (ashift:DI (match_operand:DI 1 "register_operand" "r,r")
11847                   (minus:QI (const_int 64) (match_dup 2)))))
11848    (clobber (reg:CC FLAGS_REG))]
11849   "TARGET_64BIT"
11850   "@
11851    shrd{q}\t{%2, %1, %0|%0, %1, %2}
11852    shrd{q}\t{%s2%1, %0|%0, %1, %2}"
11853   [(set_attr "type" "ishift")
11854    (set_attr "prefix_0f" "1")
11855    (set_attr "mode" "DI")
11856    (set_attr "athlon_decode" "vector")
11857    (set_attr "amdfam10_decode" "vector")])
11858
11859 (define_expand "ashrdi3"
11860   [(set (match_operand:DI 0 "shiftdi_operand" "")
11861         (ashiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
11862                      (match_operand:QI 2 "nonmemory_operand" "")))]
11863   ""
11864   "ix86_expand_binary_operator (ASHIFTRT, DImode, operands); DONE;")
11865
11866 (define_insn "*ashrdi3_63_rex64"
11867   [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
11868         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
11869                      (match_operand:DI 2 "const_int_operand" "i,i")))
11870    (clobber (reg:CC FLAGS_REG))]
11871   "TARGET_64BIT && INTVAL (operands[2]) == 63
11872    && (TARGET_USE_CLTD || optimize_size)
11873    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11874   "@
11875    {cqto|cqo}
11876    sar{q}\t{%2, %0|%0, %2}"
11877   [(set_attr "type" "imovx,ishift")
11878    (set_attr "prefix_0f" "0,*")
11879    (set_attr "length_immediate" "0,*")
11880    (set_attr "modrm" "0,1")
11881    (set_attr "mode" "DI")])
11882
11883 (define_insn "*ashrdi3_1_one_bit_rex64"
11884   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11885         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11886                      (match_operand:QI 2 "const1_operand" "")))
11887    (clobber (reg:CC FLAGS_REG))]
11888   "TARGET_64BIT
11889    && (TARGET_SHIFT1 || optimize_size)
11890    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11891   "sar{q}\t%0"
11892   [(set_attr "type" "ishift")
11893    (set (attr "length")
11894      (if_then_else (match_operand:DI 0 "register_operand" "")
11895         (const_string "2")
11896         (const_string "*")))])
11897
11898 (define_insn "*ashrdi3_1_rex64"
11899   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11900         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11901                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
11902    (clobber (reg:CC FLAGS_REG))]
11903   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11904   "@
11905    sar{q}\t{%2, %0|%0, %2}
11906    sar{q}\t{%b2, %0|%0, %b2}"
11907   [(set_attr "type" "ishift")
11908    (set_attr "mode" "DI")])
11909
11910 ;; This pattern can't accept a variable shift count, since shifts by
11911 ;; zero don't affect the flags.  We assume that shifts by constant
11912 ;; zero are optimized away.
11913 (define_insn "*ashrdi3_one_bit_cmp_rex64"
11914   [(set (reg FLAGS_REG)
11915         (compare
11916           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11917                        (match_operand:QI 2 "const1_operand" ""))
11918           (const_int 0)))
11919    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11920         (ashiftrt:DI (match_dup 1) (match_dup 2)))]
11921   "TARGET_64BIT
11922    && (TARGET_SHIFT1 || optimize_size)
11923    && ix86_match_ccmode (insn, CCGOCmode)
11924    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11925   "sar{q}\t%0"
11926   [(set_attr "type" "ishift")
11927    (set (attr "length")
11928      (if_then_else (match_operand:DI 0 "register_operand" "")
11929         (const_string "2")
11930         (const_string "*")))])
11931
11932 (define_insn "*ashrdi3_one_bit_cconly_rex64"
11933   [(set (reg FLAGS_REG)
11934         (compare
11935           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11936                        (match_operand:QI 2 "const1_operand" ""))
11937           (const_int 0)))
11938    (clobber (match_scratch:DI 0 "=r"))]
11939   "TARGET_64BIT
11940    && (TARGET_SHIFT1 || optimize_size)
11941    && ix86_match_ccmode (insn, CCGOCmode)
11942    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11943   "sar{q}\t%0"
11944   [(set_attr "type" "ishift")
11945    (set_attr "length" "2")])
11946
11947 ;; This pattern can't accept a variable shift count, since shifts by
11948 ;; zero don't affect the flags.  We assume that shifts by constant
11949 ;; zero are optimized away.
11950 (define_insn "*ashrdi3_cmp_rex64"
11951   [(set (reg FLAGS_REG)
11952         (compare
11953           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11954                        (match_operand:QI 2 "const_int_operand" "n"))
11955           (const_int 0)))
11956    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11957         (ashiftrt:DI (match_dup 1) (match_dup 2)))]
11958   "TARGET_64BIT
11959    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
11960    && ix86_match_ccmode (insn, CCGOCmode)
11961    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11962   "sar{q}\t{%2, %0|%0, %2}"
11963   [(set_attr "type" "ishift")
11964    (set_attr "mode" "DI")])
11965
11966 (define_insn "*ashrdi3_cconly_rex64"
11967   [(set (reg FLAGS_REG)
11968         (compare
11969           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11970                        (match_operand:QI 2 "const_int_operand" "n"))
11971           (const_int 0)))
11972    (clobber (match_scratch:DI 0 "=r"))]
11973   "TARGET_64BIT
11974    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
11975    && ix86_match_ccmode (insn, CCGOCmode)
11976    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11977   "sar{q}\t{%2, %0|%0, %2}"
11978   [(set_attr "type" "ishift")
11979    (set_attr "mode" "DI")])
11980
11981 (define_insn "*ashrdi3_1"
11982   [(set (match_operand:DI 0 "register_operand" "=r")
11983         (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
11984                      (match_operand:QI 2 "nonmemory_operand" "Jc")))
11985    (clobber (reg:CC FLAGS_REG))]
11986   "!TARGET_64BIT"
11987   "#"
11988   [(set_attr "type" "multi")])
11989
11990 ;; By default we don't ask for a scratch register, because when DImode
11991 ;; values are manipulated, registers are already at a premium.  But if
11992 ;; we have one handy, we won't turn it away.
11993 (define_peephole2
11994   [(match_scratch:SI 3 "r")
11995    (parallel [(set (match_operand:DI 0 "register_operand" "")
11996                    (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
11997                                 (match_operand:QI 2 "nonmemory_operand" "")))
11998               (clobber (reg:CC FLAGS_REG))])
11999    (match_dup 3)]
12000   "!TARGET_64BIT && TARGET_CMOVE"
12001   [(const_int 0)]
12002   "ix86_split_ashr (operands, operands[3], DImode); DONE;")
12003
12004 (define_split
12005   [(set (match_operand:DI 0 "register_operand" "")
12006         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
12007                      (match_operand:QI 2 "nonmemory_operand" "")))
12008    (clobber (reg:CC FLAGS_REG))]
12009   "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
12010                      ? epilogue_completed : reload_completed)"
12011   [(const_int 0)]
12012   "ix86_split_ashr (operands, NULL_RTX, DImode); DONE;")
12013
12014 (define_insn "x86_shrd_1"
12015   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
12016         (ior:SI (ashiftrt:SI (match_dup 0)
12017                   (match_operand:QI 2 "nonmemory_operand" "I,c"))
12018                 (ashift:SI (match_operand:SI 1 "register_operand" "r,r")
12019                   (minus:QI (const_int 32) (match_dup 2)))))
12020    (clobber (reg:CC FLAGS_REG))]
12021   ""
12022   "@
12023    shrd{l}\t{%2, %1, %0|%0, %1, %2}
12024    shrd{l}\t{%s2%1, %0|%0, %1, %2}"
12025   [(set_attr "type" "ishift")
12026    (set_attr "prefix_0f" "1")
12027    (set_attr "pent_pair" "np")
12028    (set_attr "mode" "SI")])
12029
12030 (define_expand "x86_shift_adj_3"
12031   [(use (match_operand:SI 0 "register_operand" ""))
12032    (use (match_operand:SI 1 "register_operand" ""))
12033    (use (match_operand:QI 2 "register_operand" ""))]
12034   ""
12035 {
12036   rtx label = gen_label_rtx ();
12037   rtx tmp;
12038
12039   emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
12040
12041   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
12042   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
12043   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
12044                               gen_rtx_LABEL_REF (VOIDmode, label),
12045                               pc_rtx);
12046   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
12047   JUMP_LABEL (tmp) = label;
12048
12049   emit_move_insn (operands[0], operands[1]);
12050   emit_insn (gen_ashrsi3_31 (operands[1], operands[1], GEN_INT (31)));
12051
12052   emit_label (label);
12053   LABEL_NUSES (label) = 1;
12054
12055   DONE;
12056 })
12057
12058 (define_insn "ashrsi3_31"
12059   [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
12060         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
12061                      (match_operand:SI 2 "const_int_operand" "i,i")))
12062    (clobber (reg:CC FLAGS_REG))]
12063   "INTVAL (operands[2]) == 31 && (TARGET_USE_CLTD || optimize_size)
12064    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12065   "@
12066    {cltd|cdq}
12067    sar{l}\t{%2, %0|%0, %2}"
12068   [(set_attr "type" "imovx,ishift")
12069    (set_attr "prefix_0f" "0,*")
12070    (set_attr "length_immediate" "0,*")
12071    (set_attr "modrm" "0,1")
12072    (set_attr "mode" "SI")])
12073
12074 (define_insn "*ashrsi3_31_zext"
12075   [(set (match_operand:DI 0 "register_operand" "=*d,r")
12076         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
12077                                      (match_operand:SI 2 "const_int_operand" "i,i"))))
12078    (clobber (reg:CC FLAGS_REG))]
12079   "TARGET_64BIT && (TARGET_USE_CLTD || optimize_size)
12080    && INTVAL (operands[2]) == 31
12081    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12082   "@
12083    {cltd|cdq}
12084    sar{l}\t{%2, %k0|%k0, %2}"
12085   [(set_attr "type" "imovx,ishift")
12086    (set_attr "prefix_0f" "0,*")
12087    (set_attr "length_immediate" "0,*")
12088    (set_attr "modrm" "0,1")
12089    (set_attr "mode" "SI")])
12090
12091 (define_expand "ashrsi3"
12092   [(set (match_operand:SI 0 "nonimmediate_operand" "")
12093         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
12094                      (match_operand:QI 2 "nonmemory_operand" "")))
12095    (clobber (reg:CC FLAGS_REG))]
12096   ""
12097   "ix86_expand_binary_operator (ASHIFTRT, SImode, operands); DONE;")
12098
12099 (define_insn "*ashrsi3_1_one_bit"
12100   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12101         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12102                      (match_operand:QI 2 "const1_operand" "")))
12103    (clobber (reg:CC FLAGS_REG))]
12104   "(TARGET_SHIFT1 || optimize_size)
12105    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12106   "sar{l}\t%0"
12107   [(set_attr "type" "ishift")
12108    (set (attr "length")
12109      (if_then_else (match_operand:SI 0 "register_operand" "")
12110         (const_string "2")
12111         (const_string "*")))])
12112
12113 (define_insn "*ashrsi3_1_one_bit_zext"
12114   [(set (match_operand:DI 0 "register_operand" "=r")
12115         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
12116                                      (match_operand:QI 2 "const1_operand" ""))))
12117    (clobber (reg:CC FLAGS_REG))]
12118   "TARGET_64BIT
12119    && (TARGET_SHIFT1 || optimize_size)
12120    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12121   "sar{l}\t%k0"
12122   [(set_attr "type" "ishift")
12123    (set_attr "length" "2")])
12124
12125 (define_insn "*ashrsi3_1"
12126   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12127         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12128                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12129    (clobber (reg:CC FLAGS_REG))]
12130   "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12131   "@
12132    sar{l}\t{%2, %0|%0, %2}
12133    sar{l}\t{%b2, %0|%0, %b2}"
12134   [(set_attr "type" "ishift")
12135    (set_attr "mode" "SI")])
12136
12137 (define_insn "*ashrsi3_1_zext"
12138   [(set (match_operand:DI 0 "register_operand" "=r,r")
12139         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0")
12140                                      (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12141    (clobber (reg:CC FLAGS_REG))]
12142   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12143   "@
12144    sar{l}\t{%2, %k0|%k0, %2}
12145    sar{l}\t{%b2, %k0|%k0, %b2}"
12146   [(set_attr "type" "ishift")
12147    (set_attr "mode" "SI")])
12148
12149 ;; This pattern can't accept a variable shift count, since shifts by
12150 ;; zero don't affect the flags.  We assume that shifts by constant
12151 ;; zero are optimized away.
12152 (define_insn "*ashrsi3_one_bit_cmp"
12153   [(set (reg FLAGS_REG)
12154         (compare
12155           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12156                        (match_operand:QI 2 "const1_operand" ""))
12157           (const_int 0)))
12158    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12159         (ashiftrt:SI (match_dup 1) (match_dup 2)))]
12160   "(TARGET_SHIFT1 || optimize_size)
12161    && ix86_match_ccmode (insn, CCGOCmode)
12162    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12163   "sar{l}\t%0"
12164   [(set_attr "type" "ishift")
12165    (set (attr "length")
12166      (if_then_else (match_operand:SI 0 "register_operand" "")
12167         (const_string "2")
12168         (const_string "*")))])
12169
12170 (define_insn "*ashrsi3_one_bit_cconly"
12171   [(set (reg FLAGS_REG)
12172         (compare
12173           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12174                        (match_operand:QI 2 "const1_operand" ""))
12175           (const_int 0)))
12176    (clobber (match_scratch:SI 0 "=r"))]
12177   "(TARGET_SHIFT1 || optimize_size)
12178    && ix86_match_ccmode (insn, CCGOCmode)
12179    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12180   "sar{l}\t%0"
12181   [(set_attr "type" "ishift")
12182    (set_attr "length" "2")])
12183
12184 (define_insn "*ashrsi3_one_bit_cmp_zext"
12185   [(set (reg FLAGS_REG)
12186         (compare
12187           (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
12188                        (match_operand:QI 2 "const1_operand" ""))
12189           (const_int 0)))
12190    (set (match_operand:DI 0 "register_operand" "=r")
12191         (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
12192   "TARGET_64BIT
12193    && (TARGET_SHIFT1 || optimize_size)
12194    && ix86_match_ccmode (insn, CCmode)
12195    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12196   "sar{l}\t%k0"
12197   [(set_attr "type" "ishift")
12198    (set_attr "length" "2")])
12199
12200 ;; This pattern can't accept a variable shift count, since shifts by
12201 ;; zero don't affect the flags.  We assume that shifts by constant
12202 ;; zero are optimized away.
12203 (define_insn "*ashrsi3_cmp"
12204   [(set (reg FLAGS_REG)
12205         (compare
12206           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12207                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12208           (const_int 0)))
12209    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12210         (ashiftrt:SI (match_dup 1) (match_dup 2)))]
12211   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12212    && ix86_match_ccmode (insn, CCGOCmode)
12213    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12214   "sar{l}\t{%2, %0|%0, %2}"
12215   [(set_attr "type" "ishift")
12216    (set_attr "mode" "SI")])
12217
12218 (define_insn "*ashrsi3_cconly"
12219   [(set (reg FLAGS_REG)
12220         (compare
12221           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12222                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12223           (const_int 0)))
12224    (clobber (match_scratch:SI 0 "=r"))]
12225   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12226    && ix86_match_ccmode (insn, CCGOCmode)
12227    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12228   "sar{l}\t{%2, %0|%0, %2}"
12229   [(set_attr "type" "ishift")
12230    (set_attr "mode" "SI")])
12231
12232 (define_insn "*ashrsi3_cmp_zext"
12233   [(set (reg FLAGS_REG)
12234         (compare
12235           (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
12236                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12237           (const_int 0)))
12238    (set (match_operand:DI 0 "register_operand" "=r")
12239         (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
12240   "TARGET_64BIT
12241    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12242    && ix86_match_ccmode (insn, CCGOCmode)
12243    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
12244   "sar{l}\t{%2, %k0|%k0, %2}"
12245   [(set_attr "type" "ishift")
12246    (set_attr "mode" "SI")])
12247
12248 (define_expand "ashrhi3"
12249   [(set (match_operand:HI 0 "nonimmediate_operand" "")
12250         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
12251                      (match_operand:QI 2 "nonmemory_operand" "")))
12252    (clobber (reg:CC FLAGS_REG))]
12253   "TARGET_HIMODE_MATH"
12254   "ix86_expand_binary_operator (ASHIFTRT, HImode, operands); DONE;")
12255
12256 (define_insn "*ashrhi3_1_one_bit"
12257   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12258         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12259                      (match_operand:QI 2 "const1_operand" "")))
12260    (clobber (reg:CC FLAGS_REG))]
12261   "(TARGET_SHIFT1 || optimize_size)
12262    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12263   "sar{w}\t%0"
12264   [(set_attr "type" "ishift")
12265    (set (attr "length")
12266      (if_then_else (match_operand 0 "register_operand" "")
12267         (const_string "2")
12268         (const_string "*")))])
12269
12270 (define_insn "*ashrhi3_1"
12271   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12272         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12273                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12274    (clobber (reg:CC FLAGS_REG))]
12275   "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12276   "@
12277    sar{w}\t{%2, %0|%0, %2}
12278    sar{w}\t{%b2, %0|%0, %b2}"
12279   [(set_attr "type" "ishift")
12280    (set_attr "mode" "HI")])
12281
12282 ;; This pattern can't accept a variable shift count, since shifts by
12283 ;; zero don't affect the flags.  We assume that shifts by constant
12284 ;; zero are optimized away.
12285 (define_insn "*ashrhi3_one_bit_cmp"
12286   [(set (reg FLAGS_REG)
12287         (compare
12288           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12289                        (match_operand:QI 2 "const1_operand" ""))
12290           (const_int 0)))
12291    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12292         (ashiftrt:HI (match_dup 1) (match_dup 2)))]
12293   "(TARGET_SHIFT1 || optimize_size)
12294    && ix86_match_ccmode (insn, CCGOCmode)
12295    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12296   "sar{w}\t%0"
12297   [(set_attr "type" "ishift")
12298    (set (attr "length")
12299      (if_then_else (match_operand 0 "register_operand" "")
12300         (const_string "2")
12301         (const_string "*")))])
12302
12303 (define_insn "*ashrhi3_one_bit_cconly"
12304   [(set (reg FLAGS_REG)
12305         (compare
12306           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12307                        (match_operand:QI 2 "const1_operand" ""))
12308           (const_int 0)))
12309    (clobber (match_scratch:HI 0 "=r"))]
12310   "(TARGET_SHIFT1 || optimize_size)
12311    && ix86_match_ccmode (insn, CCGOCmode)
12312    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12313   "sar{w}\t%0"
12314   [(set_attr "type" "ishift")
12315    (set_attr "length" "2")])
12316
12317 ;; This pattern can't accept a variable shift count, since shifts by
12318 ;; zero don't affect the flags.  We assume that shifts by constant
12319 ;; zero are optimized away.
12320 (define_insn "*ashrhi3_cmp"
12321   [(set (reg FLAGS_REG)
12322         (compare
12323           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12324                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12325           (const_int 0)))
12326    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12327         (ashiftrt:HI (match_dup 1) (match_dup 2)))]
12328   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12329    && ix86_match_ccmode (insn, CCGOCmode)
12330    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12331   "sar{w}\t{%2, %0|%0, %2}"
12332   [(set_attr "type" "ishift")
12333    (set_attr "mode" "HI")])
12334
12335 (define_insn "*ashrhi3_cconly"
12336   [(set (reg FLAGS_REG)
12337         (compare
12338           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12339                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12340           (const_int 0)))
12341    (clobber (match_scratch:HI 0 "=r"))]
12342   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12343    && ix86_match_ccmode (insn, CCGOCmode)
12344    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
12345   "sar{w}\t{%2, %0|%0, %2}"
12346   [(set_attr "type" "ishift")
12347    (set_attr "mode" "HI")])
12348
12349 (define_expand "ashrqi3"
12350   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12351         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
12352                      (match_operand:QI 2 "nonmemory_operand" "")))
12353    (clobber (reg:CC FLAGS_REG))]
12354   "TARGET_QIMODE_MATH"
12355   "ix86_expand_binary_operator (ASHIFTRT, QImode, operands); DONE;")
12356
12357 (define_insn "*ashrqi3_1_one_bit"
12358   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12359         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12360                      (match_operand:QI 2 "const1_operand" "")))
12361    (clobber (reg:CC FLAGS_REG))]
12362   "(TARGET_SHIFT1 || optimize_size)
12363    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12364   "sar{b}\t%0"
12365   [(set_attr "type" "ishift")
12366    (set (attr "length")
12367      (if_then_else (match_operand 0 "register_operand" "")
12368         (const_string "2")
12369         (const_string "*")))])
12370
12371 (define_insn "*ashrqi3_1_one_bit_slp"
12372   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12373         (ashiftrt:QI (match_dup 0)
12374                      (match_operand:QI 1 "const1_operand" "")))
12375    (clobber (reg:CC FLAGS_REG))]
12376   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12377    && (TARGET_SHIFT1 || optimize_size)
12378    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12379   "sar{b}\t%0"
12380   [(set_attr "type" "ishift1")
12381    (set (attr "length")
12382      (if_then_else (match_operand 0 "register_operand" "")
12383         (const_string "2")
12384         (const_string "*")))])
12385
12386 (define_insn "*ashrqi3_1"
12387   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12388         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12389                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12390    (clobber (reg:CC FLAGS_REG))]
12391   "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12392   "@
12393    sar{b}\t{%2, %0|%0, %2}
12394    sar{b}\t{%b2, %0|%0, %b2}"
12395   [(set_attr "type" "ishift")
12396    (set_attr "mode" "QI")])
12397
12398 (define_insn "*ashrqi3_1_slp"
12399   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12400         (ashiftrt:QI (match_dup 0)
12401                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
12402    (clobber (reg:CC FLAGS_REG))]
12403   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12404    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
12405   "@
12406    sar{b}\t{%1, %0|%0, %1}
12407    sar{b}\t{%b1, %0|%0, %b1}"
12408   [(set_attr "type" "ishift1")
12409    (set_attr "mode" "QI")])
12410
12411 ;; This pattern can't accept a variable shift count, since shifts by
12412 ;; zero don't affect the flags.  We assume that shifts by constant
12413 ;; zero are optimized away.
12414 (define_insn "*ashrqi3_one_bit_cmp"
12415   [(set (reg FLAGS_REG)
12416         (compare
12417           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12418                        (match_operand:QI 2 "const1_operand" "I"))
12419           (const_int 0)))
12420    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12421         (ashiftrt:QI (match_dup 1) (match_dup 2)))]
12422   "(TARGET_SHIFT1 || optimize_size)
12423    && ix86_match_ccmode (insn, CCGOCmode)
12424    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12425   "sar{b}\t%0"
12426   [(set_attr "type" "ishift")
12427    (set (attr "length")
12428      (if_then_else (match_operand 0 "register_operand" "")
12429         (const_string "2")
12430         (const_string "*")))])
12431
12432 (define_insn "*ashrqi3_one_bit_cconly"
12433   [(set (reg FLAGS_REG)
12434         (compare
12435           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12436                        (match_operand:QI 2 "const1_operand" "I"))
12437           (const_int 0)))
12438    (clobber (match_scratch:QI 0 "=q"))]
12439   "(TARGET_SHIFT1 || optimize_size)
12440    && ix86_match_ccmode (insn, CCGOCmode)
12441    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12442   "sar{b}\t%0"
12443   [(set_attr "type" "ishift")
12444    (set_attr "length" "2")])
12445
12446 ;; This pattern can't accept a variable shift count, since shifts by
12447 ;; zero don't affect the flags.  We assume that shifts by constant
12448 ;; zero are optimized away.
12449 (define_insn "*ashrqi3_cmp"
12450   [(set (reg FLAGS_REG)
12451         (compare
12452           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12453                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12454           (const_int 0)))
12455    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12456         (ashiftrt:QI (match_dup 1) (match_dup 2)))]
12457   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12458    && ix86_match_ccmode (insn, CCGOCmode)
12459    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12460   "sar{b}\t{%2, %0|%0, %2}"
12461   [(set_attr "type" "ishift")
12462    (set_attr "mode" "QI")])
12463
12464 (define_insn "*ashrqi3_cconly"
12465   [(set (reg FLAGS_REG)
12466         (compare
12467           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12468                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12469           (const_int 0)))
12470    (clobber (match_scratch:QI 0 "=q"))]
12471   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12472    && ix86_match_ccmode (insn, CCGOCmode)
12473    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
12474   "sar{b}\t{%2, %0|%0, %2}"
12475   [(set_attr "type" "ishift")
12476    (set_attr "mode" "QI")])
12477
12478 \f
12479 ;; Logical shift instructions
12480
12481 ;; See comment above `ashldi3' about how this works.
12482
12483 (define_expand "lshrti3"
12484   [(parallel [(set (match_operand:TI 0 "register_operand" "")
12485                    (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
12486                                 (match_operand:QI 2 "nonmemory_operand" "")))
12487               (clobber (reg:CC FLAGS_REG))])]
12488   "TARGET_64BIT"
12489 {
12490   if (! immediate_operand (operands[2], QImode))
12491     {
12492       emit_insn (gen_lshrti3_1 (operands[0], operands[1], operands[2]));
12493       DONE;
12494     }
12495   ix86_expand_binary_operator (LSHIFTRT, TImode, operands);
12496   DONE;
12497 })
12498
12499 (define_insn "lshrti3_1"
12500   [(set (match_operand:TI 0 "register_operand" "=r")
12501         (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
12502                      (match_operand:QI 2 "register_operand" "c")))
12503    (clobber (match_scratch:DI 3 "=&r"))
12504    (clobber (reg:CC FLAGS_REG))]
12505   "TARGET_64BIT"
12506   "#"
12507   [(set_attr "type" "multi")])
12508
12509 ;; This pattern must be defined before *lshrti3_2 to prevent
12510 ;; combine pass from converting sse2_lshrti3 to *lshrti3_2.
12511
12512 (define_insn "sse2_lshrti3"
12513   [(set (match_operand:TI 0 "register_operand" "=x")
12514         (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
12515                      (match_operand:SI 2 "const_0_to_255_mul_8_operand" "n")))]
12516   "TARGET_SSE2"
12517 {
12518   operands[2] = GEN_INT (INTVAL (operands[2]) / 8);
12519   return "psrldq\t{%2, %0|%0, %2}";
12520 }
12521   [(set_attr "type" "sseishft")
12522    (set_attr "prefix_data16" "1")
12523    (set_attr "mode" "TI")])
12524
12525 (define_insn "*lshrti3_2"
12526   [(set (match_operand:TI 0 "register_operand" "=r")
12527         (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
12528                      (match_operand:QI 2 "immediate_operand" "O")))
12529    (clobber (reg:CC FLAGS_REG))]
12530   "TARGET_64BIT"
12531   "#"
12532   [(set_attr "type" "multi")])
12533
12534 (define_split
12535   [(set (match_operand:TI 0 "register_operand" "")
12536         (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
12537                      (match_operand:QI 2 "register_operand" "")))
12538    (clobber (match_scratch:DI 3 ""))
12539    (clobber (reg:CC FLAGS_REG))]
12540   "TARGET_64BIT && reload_completed"
12541   [(const_int 0)]
12542   "ix86_split_lshr (operands, operands[3], TImode); DONE;")
12543
12544 (define_split
12545   [(set (match_operand:TI 0 "register_operand" "")
12546         (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
12547                      (match_operand:QI 2 "immediate_operand" "")))
12548    (clobber (reg:CC FLAGS_REG))]
12549   "TARGET_64BIT && reload_completed"
12550   [(const_int 0)]
12551   "ix86_split_lshr (operands, NULL_RTX, TImode); DONE;")
12552
12553 (define_expand "lshrdi3"
12554   [(set (match_operand:DI 0 "shiftdi_operand" "")
12555         (lshiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
12556                      (match_operand:QI 2 "nonmemory_operand" "")))]
12557   ""
12558   "ix86_expand_binary_operator (LSHIFTRT, DImode, operands); DONE;")
12559
12560 (define_insn "*lshrdi3_1_one_bit_rex64"
12561   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12562         (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12563                      (match_operand:QI 2 "const1_operand" "")))
12564    (clobber (reg:CC FLAGS_REG))]
12565   "TARGET_64BIT
12566    && (TARGET_SHIFT1 || optimize_size)
12567    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12568   "shr{q}\t%0"
12569   [(set_attr "type" "ishift")
12570    (set (attr "length")
12571      (if_then_else (match_operand:DI 0 "register_operand" "")
12572         (const_string "2")
12573         (const_string "*")))])
12574
12575 (define_insn "*lshrdi3_1_rex64"
12576   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
12577         (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
12578                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
12579    (clobber (reg:CC FLAGS_REG))]
12580   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12581   "@
12582    shr{q}\t{%2, %0|%0, %2}
12583    shr{q}\t{%b2, %0|%0, %b2}"
12584   [(set_attr "type" "ishift")
12585    (set_attr "mode" "DI")])
12586
12587 ;; This pattern can't accept a variable shift count, since shifts by
12588 ;; zero don't affect the flags.  We assume that shifts by constant
12589 ;; zero are optimized away.
12590 (define_insn "*lshrdi3_cmp_one_bit_rex64"
12591   [(set (reg FLAGS_REG)
12592         (compare
12593           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12594                        (match_operand:QI 2 "const1_operand" ""))
12595           (const_int 0)))
12596    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12597         (lshiftrt:DI (match_dup 1) (match_dup 2)))]
12598   "TARGET_64BIT
12599    && (TARGET_SHIFT1 || optimize_size)
12600    && ix86_match_ccmode (insn, CCGOCmode)
12601    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12602   "shr{q}\t%0"
12603   [(set_attr "type" "ishift")
12604    (set (attr "length")
12605      (if_then_else (match_operand:DI 0 "register_operand" "")
12606         (const_string "2")
12607         (const_string "*")))])
12608
12609 (define_insn "*lshrdi3_cconly_one_bit_rex64"
12610   [(set (reg FLAGS_REG)
12611         (compare
12612           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12613                        (match_operand:QI 2 "const1_operand" ""))
12614           (const_int 0)))
12615    (clobber (match_scratch:DI 0 "=r"))]
12616   "TARGET_64BIT
12617    && (TARGET_SHIFT1 || optimize_size)
12618    && ix86_match_ccmode (insn, CCGOCmode)
12619    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12620   "shr{q}\t%0"
12621   [(set_attr "type" "ishift")
12622    (set_attr "length" "2")])
12623
12624 ;; This pattern can't accept a variable shift count, since shifts by
12625 ;; zero don't affect the flags.  We assume that shifts by constant
12626 ;; zero are optimized away.
12627 (define_insn "*lshrdi3_cmp_rex64"
12628   [(set (reg FLAGS_REG)
12629         (compare
12630           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12631                        (match_operand:QI 2 "const_int_operand" "e"))
12632           (const_int 0)))
12633    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12634         (lshiftrt:DI (match_dup 1) (match_dup 2)))]
12635   "TARGET_64BIT
12636    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12637    && ix86_match_ccmode (insn, CCGOCmode)
12638    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12639   "shr{q}\t{%2, %0|%0, %2}"
12640   [(set_attr "type" "ishift")
12641    (set_attr "mode" "DI")])
12642
12643 (define_insn "*lshrdi3_cconly_rex64"
12644   [(set (reg FLAGS_REG)
12645         (compare
12646           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12647                        (match_operand:QI 2 "const_int_operand" "e"))
12648           (const_int 0)))
12649    (clobber (match_scratch:DI 0 "=r"))]
12650   "TARGET_64BIT
12651    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12652    && ix86_match_ccmode (insn, CCGOCmode)
12653    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12654   "shr{q}\t{%2, %0|%0, %2}"
12655   [(set_attr "type" "ishift")
12656    (set_attr "mode" "DI")])
12657
12658 (define_insn "*lshrdi3_1"
12659   [(set (match_operand:DI 0 "register_operand" "=r")
12660         (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
12661                      (match_operand:QI 2 "nonmemory_operand" "Jc")))
12662    (clobber (reg:CC FLAGS_REG))]
12663   "!TARGET_64BIT"
12664   "#"
12665   [(set_attr "type" "multi")])
12666
12667 ;; By default we don't ask for a scratch register, because when DImode
12668 ;; values are manipulated, registers are already at a premium.  But if
12669 ;; we have one handy, we won't turn it away.
12670 (define_peephole2
12671   [(match_scratch:SI 3 "r")
12672    (parallel [(set (match_operand:DI 0 "register_operand" "")
12673                    (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
12674                                 (match_operand:QI 2 "nonmemory_operand" "")))
12675               (clobber (reg:CC FLAGS_REG))])
12676    (match_dup 3)]
12677   "!TARGET_64BIT && TARGET_CMOVE"
12678   [(const_int 0)]
12679   "ix86_split_lshr (operands, operands[3], DImode); DONE;")
12680
12681 (define_split
12682   [(set (match_operand:DI 0 "register_operand" "")
12683         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
12684                      (match_operand:QI 2 "nonmemory_operand" "")))
12685    (clobber (reg:CC FLAGS_REG))]
12686   "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
12687                      ? epilogue_completed : reload_completed)"
12688   [(const_int 0)]
12689   "ix86_split_lshr (operands, NULL_RTX, DImode); DONE;")
12690
12691 (define_expand "lshrsi3"
12692   [(set (match_operand:SI 0 "nonimmediate_operand" "")
12693         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
12694                      (match_operand:QI 2 "nonmemory_operand" "")))
12695    (clobber (reg:CC FLAGS_REG))]
12696   ""
12697   "ix86_expand_binary_operator (LSHIFTRT, SImode, operands); DONE;")
12698
12699 (define_insn "*lshrsi3_1_one_bit"
12700   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12701         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12702                      (match_operand:QI 2 "const1_operand" "")))
12703    (clobber (reg:CC FLAGS_REG))]
12704   "(TARGET_SHIFT1 || optimize_size)
12705    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12706   "shr{l}\t%0"
12707   [(set_attr "type" "ishift")
12708    (set (attr "length")
12709      (if_then_else (match_operand:SI 0 "register_operand" "")
12710         (const_string "2")
12711         (const_string "*")))])
12712
12713 (define_insn "*lshrsi3_1_one_bit_zext"
12714   [(set (match_operand:DI 0 "register_operand" "=r")
12715         (lshiftrt:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "0"))
12716                      (match_operand:QI 2 "const1_operand" "")))
12717    (clobber (reg:CC FLAGS_REG))]
12718   "TARGET_64BIT
12719    && (TARGET_SHIFT1 || optimize_size)
12720    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12721   "shr{l}\t%k0"
12722   [(set_attr "type" "ishift")
12723    (set_attr "length" "2")])
12724
12725 (define_insn "*lshrsi3_1"
12726   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12727         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12728                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12729    (clobber (reg:CC FLAGS_REG))]
12730   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12731   "@
12732    shr{l}\t{%2, %0|%0, %2}
12733    shr{l}\t{%b2, %0|%0, %b2}"
12734   [(set_attr "type" "ishift")
12735    (set_attr "mode" "SI")])
12736
12737 (define_insn "*lshrsi3_1_zext"
12738   [(set (match_operand:DI 0 "register_operand" "=r,r")
12739         (zero_extend:DI
12740           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12741                        (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12742    (clobber (reg:CC FLAGS_REG))]
12743   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12744   "@
12745    shr{l}\t{%2, %k0|%k0, %2}
12746    shr{l}\t{%b2, %k0|%k0, %b2}"
12747   [(set_attr "type" "ishift")
12748    (set_attr "mode" "SI")])
12749
12750 ;; This pattern can't accept a variable shift count, since shifts by
12751 ;; zero don't affect the flags.  We assume that shifts by constant
12752 ;; zero are optimized away.
12753 (define_insn "*lshrsi3_one_bit_cmp"
12754   [(set (reg FLAGS_REG)
12755         (compare
12756           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12757                        (match_operand:QI 2 "const1_operand" ""))
12758           (const_int 0)))
12759    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12760         (lshiftrt:SI (match_dup 1) (match_dup 2)))]
12761   "(TARGET_SHIFT1 || optimize_size)
12762    && ix86_match_ccmode (insn, CCGOCmode)
12763    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12764   "shr{l}\t%0"
12765   [(set_attr "type" "ishift")
12766    (set (attr "length")
12767      (if_then_else (match_operand:SI 0 "register_operand" "")
12768         (const_string "2")
12769         (const_string "*")))])
12770
12771 (define_insn "*lshrsi3_one_bit_cconly"
12772   [(set (reg FLAGS_REG)
12773         (compare
12774           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12775                        (match_operand:QI 2 "const1_operand" ""))
12776           (const_int 0)))
12777    (clobber (match_scratch:SI 0 "=r"))]
12778   "(TARGET_SHIFT1 || optimize_size)
12779    && ix86_match_ccmode (insn, CCGOCmode)
12780    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12781   "shr{l}\t%0"
12782   [(set_attr "type" "ishift")
12783    (set_attr "length" "2")])
12784
12785 (define_insn "*lshrsi3_cmp_one_bit_zext"
12786   [(set (reg FLAGS_REG)
12787         (compare
12788           (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
12789                        (match_operand:QI 2 "const1_operand" ""))
12790           (const_int 0)))
12791    (set (match_operand:DI 0 "register_operand" "=r")
12792         (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
12793   "TARGET_64BIT
12794    && (TARGET_SHIFT1 || optimize_size)
12795    && ix86_match_ccmode (insn, CCGOCmode)
12796    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12797   "shr{l}\t%k0"
12798   [(set_attr "type" "ishift")
12799    (set_attr "length" "2")])
12800
12801 ;; This pattern can't accept a variable shift count, since shifts by
12802 ;; zero don't affect the flags.  We assume that shifts by constant
12803 ;; zero are optimized away.
12804 (define_insn "*lshrsi3_cmp"
12805   [(set (reg FLAGS_REG)
12806         (compare
12807           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12808                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12809           (const_int 0)))
12810    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12811         (lshiftrt:SI (match_dup 1) (match_dup 2)))]
12812   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12813    && ix86_match_ccmode (insn, CCGOCmode)
12814    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12815   "shr{l}\t{%2, %0|%0, %2}"
12816   [(set_attr "type" "ishift")
12817    (set_attr "mode" "SI")])
12818
12819 (define_insn "*lshrsi3_cconly"
12820   [(set (reg FLAGS_REG)
12821       (compare
12822         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12823                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
12824         (const_int 0)))
12825    (clobber (match_scratch:SI 0 "=r"))]
12826   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12827    && ix86_match_ccmode (insn, CCGOCmode)
12828    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12829   "shr{l}\t{%2, %0|%0, %2}"
12830   [(set_attr "type" "ishift")
12831    (set_attr "mode" "SI")])
12832
12833 (define_insn "*lshrsi3_cmp_zext"
12834   [(set (reg FLAGS_REG)
12835         (compare
12836           (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
12837                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12838           (const_int 0)))
12839    (set (match_operand:DI 0 "register_operand" "=r")
12840         (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
12841   "TARGET_64BIT
12842    && (optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12843    && ix86_match_ccmode (insn, CCGOCmode)
12844    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12845   "shr{l}\t{%2, %k0|%k0, %2}"
12846   [(set_attr "type" "ishift")
12847    (set_attr "mode" "SI")])
12848
12849 (define_expand "lshrhi3"
12850   [(set (match_operand:HI 0 "nonimmediate_operand" "")
12851         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
12852                      (match_operand:QI 2 "nonmemory_operand" "")))
12853    (clobber (reg:CC FLAGS_REG))]
12854   "TARGET_HIMODE_MATH"
12855   "ix86_expand_binary_operator (LSHIFTRT, HImode, operands); DONE;")
12856
12857 (define_insn "*lshrhi3_1_one_bit"
12858   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12859         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12860                      (match_operand:QI 2 "const1_operand" "")))
12861    (clobber (reg:CC FLAGS_REG))]
12862   "(TARGET_SHIFT1 || optimize_size)
12863    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12864   "shr{w}\t%0"
12865   [(set_attr "type" "ishift")
12866    (set (attr "length")
12867      (if_then_else (match_operand 0 "register_operand" "")
12868         (const_string "2")
12869         (const_string "*")))])
12870
12871 (define_insn "*lshrhi3_1"
12872   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12873         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12874                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12875    (clobber (reg:CC FLAGS_REG))]
12876   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12877   "@
12878    shr{w}\t{%2, %0|%0, %2}
12879    shr{w}\t{%b2, %0|%0, %b2}"
12880   [(set_attr "type" "ishift")
12881    (set_attr "mode" "HI")])
12882
12883 ;; This pattern can't accept a variable shift count, since shifts by
12884 ;; zero don't affect the flags.  We assume that shifts by constant
12885 ;; zero are optimized away.
12886 (define_insn "*lshrhi3_one_bit_cmp"
12887   [(set (reg FLAGS_REG)
12888         (compare
12889           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12890                        (match_operand:QI 2 "const1_operand" ""))
12891           (const_int 0)))
12892    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12893         (lshiftrt:HI (match_dup 1) (match_dup 2)))]
12894   "(TARGET_SHIFT1 || optimize_size)
12895    && ix86_match_ccmode (insn, CCGOCmode)
12896    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12897   "shr{w}\t%0"
12898   [(set_attr "type" "ishift")
12899    (set (attr "length")
12900      (if_then_else (match_operand:SI 0 "register_operand" "")
12901         (const_string "2")
12902         (const_string "*")))])
12903
12904 (define_insn "*lshrhi3_one_bit_cconly"
12905   [(set (reg FLAGS_REG)
12906         (compare
12907           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12908                        (match_operand:QI 2 "const1_operand" ""))
12909           (const_int 0)))
12910    (clobber (match_scratch:HI 0 "=r"))]
12911   "(TARGET_SHIFT1 || optimize_size)
12912    && ix86_match_ccmode (insn, CCGOCmode)
12913    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12914   "shr{w}\t%0"
12915   [(set_attr "type" "ishift")
12916    (set_attr "length" "2")])
12917
12918 ;; This pattern can't accept a variable shift count, since shifts by
12919 ;; zero don't affect the flags.  We assume that shifts by constant
12920 ;; zero are optimized away.
12921 (define_insn "*lshrhi3_cmp"
12922   [(set (reg FLAGS_REG)
12923         (compare
12924           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12925                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12926           (const_int 0)))
12927    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12928         (lshiftrt:HI (match_dup 1) (match_dup 2)))]
12929   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12930    && ix86_match_ccmode (insn, CCGOCmode)
12931    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12932   "shr{w}\t{%2, %0|%0, %2}"
12933   [(set_attr "type" "ishift")
12934    (set_attr "mode" "HI")])
12935
12936 (define_insn "*lshrhi3_cconly"
12937   [(set (reg FLAGS_REG)
12938         (compare
12939           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12940                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
12941           (const_int 0)))
12942    (clobber (match_scratch:HI 0 "=r"))]
12943   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
12944    && ix86_match_ccmode (insn, CCGOCmode)
12945    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12946   "shr{w}\t{%2, %0|%0, %2}"
12947   [(set_attr "type" "ishift")
12948    (set_attr "mode" "HI")])
12949
12950 (define_expand "lshrqi3"
12951   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12952         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
12953                      (match_operand:QI 2 "nonmemory_operand" "")))
12954    (clobber (reg:CC FLAGS_REG))]
12955   "TARGET_QIMODE_MATH"
12956   "ix86_expand_binary_operator (LSHIFTRT, QImode, operands); DONE;")
12957
12958 (define_insn "*lshrqi3_1_one_bit"
12959   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12960         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12961                      (match_operand:QI 2 "const1_operand" "")))
12962    (clobber (reg:CC FLAGS_REG))]
12963   "(TARGET_SHIFT1 || optimize_size)
12964    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
12965   "shr{b}\t%0"
12966   [(set_attr "type" "ishift")
12967    (set (attr "length")
12968      (if_then_else (match_operand 0 "register_operand" "")
12969         (const_string "2")
12970         (const_string "*")))])
12971
12972 (define_insn "*lshrqi3_1_one_bit_slp"
12973   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12974         (lshiftrt:QI (match_dup 0)
12975                      (match_operand:QI 1 "const1_operand" "")))
12976    (clobber (reg:CC FLAGS_REG))]
12977   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12978    && (TARGET_SHIFT1 || optimize_size)"
12979   "shr{b}\t%0"
12980   [(set_attr "type" "ishift1")
12981    (set (attr "length")
12982      (if_then_else (match_operand 0 "register_operand" "")
12983         (const_string "2")
12984         (const_string "*")))])
12985
12986 (define_insn "*lshrqi3_1"
12987   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12988         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12989                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12990    (clobber (reg:CC FLAGS_REG))]
12991   "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
12992   "@
12993    shr{b}\t{%2, %0|%0, %2}
12994    shr{b}\t{%b2, %0|%0, %b2}"
12995   [(set_attr "type" "ishift")
12996    (set_attr "mode" "QI")])
12997
12998 (define_insn "*lshrqi3_1_slp"
12999   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
13000         (lshiftrt:QI (match_dup 0)
13001                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
13002    (clobber (reg:CC FLAGS_REG))]
13003   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13004    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
13005   "@
13006    shr{b}\t{%1, %0|%0, %1}
13007    shr{b}\t{%b1, %0|%0, %b1}"
13008   [(set_attr "type" "ishift1")
13009    (set_attr "mode" "QI")])
13010
13011 ;; This pattern can't accept a variable shift count, since shifts by
13012 ;; zero don't affect the flags.  We assume that shifts by constant
13013 ;; zero are optimized away.
13014 (define_insn "*lshrqi2_one_bit_cmp"
13015   [(set (reg FLAGS_REG)
13016         (compare
13017           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13018                        (match_operand:QI 2 "const1_operand" ""))
13019           (const_int 0)))
13020    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13021         (lshiftrt:QI (match_dup 1) (match_dup 2)))]
13022   "(TARGET_SHIFT1 || optimize_size)
13023    && ix86_match_ccmode (insn, CCGOCmode)
13024    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13025   "shr{b}\t%0"
13026   [(set_attr "type" "ishift")
13027    (set (attr "length")
13028      (if_then_else (match_operand:SI 0 "register_operand" "")
13029         (const_string "2")
13030         (const_string "*")))])
13031
13032 (define_insn "*lshrqi2_one_bit_cconly"
13033   [(set (reg FLAGS_REG)
13034         (compare
13035           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13036                        (match_operand:QI 2 "const1_operand" ""))
13037           (const_int 0)))
13038    (clobber (match_scratch:QI 0 "=q"))]
13039   "(TARGET_SHIFT1 || optimize_size)
13040    && ix86_match_ccmode (insn, CCGOCmode)
13041    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13042   "shr{b}\t%0"
13043   [(set_attr "type" "ishift")
13044    (set_attr "length" "2")])
13045
13046 ;; This pattern can't accept a variable shift count, since shifts by
13047 ;; zero don't affect the flags.  We assume that shifts by constant
13048 ;; zero are optimized away.
13049 (define_insn "*lshrqi2_cmp"
13050   [(set (reg FLAGS_REG)
13051         (compare
13052           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13053                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
13054           (const_int 0)))
13055    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13056         (lshiftrt:QI (match_dup 1) (match_dup 2)))]
13057   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
13058    && ix86_match_ccmode (insn, CCGOCmode)
13059    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13060   "shr{b}\t{%2, %0|%0, %2}"
13061   [(set_attr "type" "ishift")
13062    (set_attr "mode" "QI")])
13063
13064 (define_insn "*lshrqi2_cconly"
13065   [(set (reg FLAGS_REG)
13066         (compare
13067           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13068                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
13069           (const_int 0)))
13070    (clobber (match_scratch:QI 0 "=q"))]
13071   "(optimize_size || !TARGET_PARTIAL_FLAG_REG_STALL)
13072    && ix86_match_ccmode (insn, CCGOCmode)
13073    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
13074   "shr{b}\t{%2, %0|%0, %2}"
13075   [(set_attr "type" "ishift")
13076    (set_attr "mode" "QI")])
13077 \f
13078 ;; Rotate instructions
13079
13080 (define_expand "rotldi3"
13081   [(set (match_operand:DI 0 "shiftdi_operand" "")
13082         (rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
13083                    (match_operand:QI 2 "nonmemory_operand" "")))
13084    (clobber (reg:CC FLAGS_REG))]
13085  ""
13086 {
13087   if (TARGET_64BIT)
13088     {
13089       ix86_expand_binary_operator (ROTATE, DImode, operands);
13090       DONE;
13091     }
13092   if (!const_1_to_31_operand (operands[2], VOIDmode))
13093     FAIL;
13094   emit_insn (gen_ix86_rotldi3 (operands[0], operands[1], operands[2]));
13095   DONE;
13096 })
13097
13098 ;; Implement rotation using two double-precision shift instructions
13099 ;; and a scratch register.
13100 (define_insn_and_split "ix86_rotldi3"
13101  [(set (match_operand:DI 0 "register_operand" "=r")
13102        (rotate:DI (match_operand:DI 1 "register_operand" "0")
13103                   (match_operand:QI 2 "const_1_to_31_operand" "I")))
13104   (clobber (reg:CC FLAGS_REG))
13105   (clobber (match_scratch:SI 3 "=&r"))]
13106  "!TARGET_64BIT"
13107  ""
13108  "&& reload_completed"
13109  [(set (match_dup 3) (match_dup 4))
13110   (parallel
13111    [(set (match_dup 4)
13112          (ior:SI (ashift:SI (match_dup 4) (match_dup 2))
13113                  (lshiftrt:SI (match_dup 5)
13114                               (minus:QI (const_int 32) (match_dup 2)))))
13115     (clobber (reg:CC FLAGS_REG))])
13116   (parallel
13117    [(set (match_dup 5)
13118          (ior:SI (ashift:SI (match_dup 5) (match_dup 2))
13119                  (lshiftrt:SI (match_dup 3)
13120                               (minus:QI (const_int 32) (match_dup 2)))))
13121     (clobber (reg:CC FLAGS_REG))])]
13122  "split_di (operands, 1, operands + 4, operands + 5);")
13123
13124 (define_insn "*rotlsi3_1_one_bit_rex64"
13125   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
13126         (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13127                    (match_operand:QI 2 "const1_operand" "")))
13128    (clobber (reg:CC FLAGS_REG))]
13129   "TARGET_64BIT
13130    && (TARGET_SHIFT1 || optimize_size)
13131    && ix86_binary_operator_ok (ROTATE, DImode, operands)"
13132   "rol{q}\t%0"
13133   [(set_attr "type" "rotate")
13134    (set (attr "length")
13135      (if_then_else (match_operand:DI 0 "register_operand" "")
13136         (const_string "2")
13137         (const_string "*")))])
13138
13139 (define_insn "*rotldi3_1_rex64"
13140   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
13141         (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
13142                    (match_operand:QI 2 "nonmemory_operand" "e,c")))
13143    (clobber (reg:CC FLAGS_REG))]
13144   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)"
13145   "@
13146    rol{q}\t{%2, %0|%0, %2}
13147    rol{q}\t{%b2, %0|%0, %b2}"
13148   [(set_attr "type" "rotate")
13149    (set_attr "mode" "DI")])
13150
13151 (define_expand "rotlsi3"
13152   [(set (match_operand:SI 0 "nonimmediate_operand" "")
13153         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
13154                    (match_operand:QI 2 "nonmemory_operand" "")))
13155    (clobber (reg:CC FLAGS_REG))]
13156   ""
13157   "ix86_expand_binary_operator (ROTATE, SImode, operands); DONE;")
13158
13159 (define_insn "*rotlsi3_1_one_bit"
13160   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
13161         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13162                    (match_operand:QI 2 "const1_operand" "")))
13163    (clobber (reg:CC FLAGS_REG))]
13164   "(TARGET_SHIFT1 || optimize_size)
13165    && ix86_binary_operator_ok (ROTATE, SImode, operands)"
13166   "rol{l}\t%0"
13167   [(set_attr "type" "rotate")
13168    (set (attr "length")
13169      (if_then_else (match_operand:SI 0 "register_operand" "")
13170         (const_string "2")
13171         (const_string "*")))])
13172
13173 (define_insn "*rotlsi3_1_one_bit_zext"
13174   [(set (match_operand:DI 0 "register_operand" "=r")
13175         (zero_extend:DI
13176           (rotate:SI (match_operand:SI 1 "register_operand" "0")
13177                      (match_operand:QI 2 "const1_operand" ""))))
13178    (clobber (reg:CC FLAGS_REG))]
13179   "TARGET_64BIT
13180    && (TARGET_SHIFT1 || optimize_size)
13181    && ix86_binary_operator_ok (ROTATE, SImode, operands)"
13182   "rol{l}\t%k0"
13183   [(set_attr "type" "rotate")
13184    (set_attr "length" "2")])
13185
13186 (define_insn "*rotlsi3_1"
13187   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
13188         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
13189                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
13190    (clobber (reg:CC FLAGS_REG))]
13191   "ix86_binary_operator_ok (ROTATE, SImode, operands)"
13192   "@
13193    rol{l}\t{%2, %0|%0, %2}
13194    rol{l}\t{%b2, %0|%0, %b2}"
13195   [(set_attr "type" "rotate")
13196    (set_attr "mode" "SI")])
13197
13198 (define_insn "*rotlsi3_1_zext"
13199   [(set (match_operand:DI 0 "register_operand" "=r,r")
13200         (zero_extend:DI
13201           (rotate:SI (match_operand:SI 1 "register_operand" "0,0")
13202                      (match_operand:QI 2 "nonmemory_operand" "I,c"))))
13203    (clobber (reg:CC FLAGS_REG))]
13204   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)"
13205   "@
13206    rol{l}\t{%2, %k0|%k0, %2}
13207    rol{l}\t{%b2, %k0|%k0, %b2}"
13208   [(set_attr "type" "rotate")
13209    (set_attr "mode" "SI")])
13210
13211 (define_expand "rotlhi3"
13212   [(set (match_operand:HI 0 "nonimmediate_operand" "")
13213         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "")
13214                    (match_operand:QI 2 "nonmemory_operand" "")))
13215    (clobber (reg:CC FLAGS_REG))]
13216   "TARGET_HIMODE_MATH"
13217   "ix86_expand_binary_operator (ROTATE, HImode, operands); DONE;")
13218
13219 (define_insn "*rotlhi3_1_one_bit"
13220   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
13221         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0")
13222                    (match_operand:QI 2 "const1_operand" "")))
13223    (clobber (reg:CC FLAGS_REG))]
13224   "(TARGET_SHIFT1 || optimize_size)
13225    && ix86_binary_operator_ok (ROTATE, HImode, operands)"
13226   "rol{w}\t%0"
13227   [(set_attr "type" "rotate")
13228    (set (attr "length")
13229      (if_then_else (match_operand 0 "register_operand" "")
13230         (const_string "2")
13231         (const_string "*")))])
13232
13233 (define_insn "*rotlhi3_1"
13234   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
13235         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
13236                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
13237    (clobber (reg:CC FLAGS_REG))]
13238   "ix86_binary_operator_ok (ROTATE, HImode, operands)"
13239   "@
13240    rol{w}\t{%2, %0|%0, %2}
13241    rol{w}\t{%b2, %0|%0, %b2}"
13242   [(set_attr "type" "rotate")
13243    (set_attr "mode" "HI")])
13244
13245 (define_split
13246  [(set (match_operand:HI 0 "register_operand" "")
13247        (rotate:HI (match_dup 0) (const_int 8)))
13248   (clobber (reg:CC FLAGS_REG))]
13249  "reload_completed"
13250  [(parallel [(set (strict_low_part (match_dup 0))
13251                   (bswap:HI (match_dup 0)))
13252              (clobber (reg:CC FLAGS_REG))])]
13253  "")
13254
13255 (define_expand "rotlqi3"
13256   [(set (match_operand:QI 0 "nonimmediate_operand" "")
13257         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "")
13258                    (match_operand:QI 2 "nonmemory_operand" "")))
13259    (clobber (reg:CC FLAGS_REG))]
13260   "TARGET_QIMODE_MATH"
13261   "ix86_expand_binary_operator (ROTATE, QImode, operands); DONE;")
13262
13263 (define_insn "*rotlqi3_1_one_bit_slp"
13264   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
13265         (rotate:QI (match_dup 0)
13266                    (match_operand:QI 1 "const1_operand" "")))
13267    (clobber (reg:CC FLAGS_REG))]
13268   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13269    && (TARGET_SHIFT1 || optimize_size)"
13270   "rol{b}\t%0"
13271   [(set_attr "type" "rotate1")
13272    (set (attr "length")
13273      (if_then_else (match_operand 0 "register_operand" "")
13274         (const_string "2")
13275         (const_string "*")))])
13276
13277 (define_insn "*rotlqi3_1_one_bit"
13278   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13279         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13280                    (match_operand:QI 2 "const1_operand" "")))
13281    (clobber (reg:CC FLAGS_REG))]
13282   "(TARGET_SHIFT1 || optimize_size)
13283    && ix86_binary_operator_ok (ROTATE, QImode, operands)"
13284   "rol{b}\t%0"
13285   [(set_attr "type" "rotate")
13286    (set (attr "length")
13287      (if_then_else (match_operand 0 "register_operand" "")
13288         (const_string "2")
13289         (const_string "*")))])
13290
13291 (define_insn "*rotlqi3_1_slp"
13292   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
13293         (rotate:QI (match_dup 0)
13294                    (match_operand:QI 1 "nonmemory_operand" "I,c")))
13295    (clobber (reg:CC FLAGS_REG))]
13296   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13297    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
13298   "@
13299    rol{b}\t{%1, %0|%0, %1}
13300    rol{b}\t{%b1, %0|%0, %b1}"
13301   [(set_attr "type" "rotate1")
13302    (set_attr "mode" "QI")])
13303
13304 (define_insn "*rotlqi3_1"
13305   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
13306         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
13307                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
13308    (clobber (reg:CC FLAGS_REG))]
13309   "ix86_binary_operator_ok (ROTATE, QImode, operands)"
13310   "@
13311    rol{b}\t{%2, %0|%0, %2}
13312    rol{b}\t{%b2, %0|%0, %b2}"
13313   [(set_attr "type" "rotate")
13314    (set_attr "mode" "QI")])
13315
13316 (define_expand "rotrdi3"
13317   [(set (match_operand:DI 0 "shiftdi_operand" "")
13318         (rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
13319                    (match_operand:QI 2 "nonmemory_operand" "")))
13320    (clobber (reg:CC FLAGS_REG))]
13321  ""
13322 {
13323   if (TARGET_64BIT)
13324     {
13325       ix86_expand_binary_operator (ROTATERT, DImode, operands);
13326       DONE;
13327     }
13328   if (!const_1_to_31_operand (operands[2], VOIDmode))
13329     FAIL;
13330   emit_insn (gen_ix86_rotrdi3 (operands[0], operands[1], operands[2]));
13331   DONE;
13332 })
13333
13334 ;; Implement rotation using two double-precision shift instructions
13335 ;; and a scratch register.
13336 (define_insn_and_split "ix86_rotrdi3"
13337  [(set (match_operand:DI 0 "register_operand" "=r")
13338        (rotatert:DI (match_operand:DI 1 "register_operand" "0")
13339                     (match_operand:QI 2 "const_1_to_31_operand" "I")))
13340   (clobber (reg:CC FLAGS_REG))
13341   (clobber (match_scratch:SI 3 "=&r"))]
13342  "!TARGET_64BIT"
13343  ""
13344  "&& reload_completed"
13345  [(set (match_dup 3) (match_dup 4))
13346   (parallel
13347    [(set (match_dup 4)
13348          (ior:SI (ashiftrt:SI (match_dup 4) (match_dup 2))
13349                  (ashift:SI (match_dup 5)
13350                             (minus:QI (const_int 32) (match_dup 2)))))
13351     (clobber (reg:CC FLAGS_REG))])
13352   (parallel
13353    [(set (match_dup 5)
13354          (ior:SI (ashiftrt:SI (match_dup 5) (match_dup 2))
13355                  (ashift:SI (match_dup 3)
13356                             (minus:QI (const_int 32) (match_dup 2)))))
13357     (clobber (reg:CC FLAGS_REG))])]
13358  "split_di (operands, 1, operands + 4, operands + 5);")
13359
13360 (define_insn "*rotrdi3_1_one_bit_rex64"
13361   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
13362         (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0")
13363                      (match_operand:QI 2 "const1_operand" "")))
13364    (clobber (reg:CC FLAGS_REG))]
13365   "TARGET_64BIT
13366    && (TARGET_SHIFT1 || optimize_size)
13367    && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
13368   "ror{q}\t%0"
13369   [(set_attr "type" "rotate")
13370    (set (attr "length")
13371      (if_then_else (match_operand:DI 0 "register_operand" "")
13372         (const_string "2")
13373         (const_string "*")))])
13374
13375 (define_insn "*rotrdi3_1_rex64"
13376   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
13377         (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
13378                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
13379    (clobber (reg:CC FLAGS_REG))]
13380   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
13381   "@
13382    ror{q}\t{%2, %0|%0, %2}
13383    ror{q}\t{%b2, %0|%0, %b2}"
13384   [(set_attr "type" "rotate")
13385    (set_attr "mode" "DI")])
13386
13387 (define_expand "rotrsi3"
13388   [(set (match_operand:SI 0 "nonimmediate_operand" "")
13389         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
13390                      (match_operand:QI 2 "nonmemory_operand" "")))
13391    (clobber (reg:CC FLAGS_REG))]
13392   ""
13393   "ix86_expand_binary_operator (ROTATERT, SImode, operands); DONE;")
13394
13395 (define_insn "*rotrsi3_1_one_bit"
13396   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
13397         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0")
13398                      (match_operand:QI 2 "const1_operand" "")))
13399    (clobber (reg:CC FLAGS_REG))]
13400   "(TARGET_SHIFT1 || optimize_size)
13401    && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13402   "ror{l}\t%0"
13403   [(set_attr "type" "rotate")
13404    (set (attr "length")
13405      (if_then_else (match_operand:SI 0 "register_operand" "")
13406         (const_string "2")
13407         (const_string "*")))])
13408
13409 (define_insn "*rotrsi3_1_one_bit_zext"
13410   [(set (match_operand:DI 0 "register_operand" "=r")
13411         (zero_extend:DI
13412           (rotatert:SI (match_operand:SI 1 "register_operand" "0")
13413                        (match_operand:QI 2 "const1_operand" ""))))
13414    (clobber (reg:CC FLAGS_REG))]
13415   "TARGET_64BIT
13416    && (TARGET_SHIFT1 || optimize_size)
13417    && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13418   "ror{l}\t%k0"
13419   [(set_attr "type" "rotate")
13420    (set (attr "length")
13421      (if_then_else (match_operand:SI 0 "register_operand" "")
13422         (const_string "2")
13423         (const_string "*")))])
13424
13425 (define_insn "*rotrsi3_1"
13426   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
13427         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
13428                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
13429    (clobber (reg:CC FLAGS_REG))]
13430   "ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13431   "@
13432    ror{l}\t{%2, %0|%0, %2}
13433    ror{l}\t{%b2, %0|%0, %b2}"
13434   [(set_attr "type" "rotate")
13435    (set_attr "mode" "SI")])
13436
13437 (define_insn "*rotrsi3_1_zext"
13438   [(set (match_operand:DI 0 "register_operand" "=r,r")
13439         (zero_extend:DI
13440           (rotatert:SI (match_operand:SI 1 "register_operand" "0,0")
13441                        (match_operand:QI 2 "nonmemory_operand" "I,c"))))
13442    (clobber (reg:CC FLAGS_REG))]
13443   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
13444   "@
13445    ror{l}\t{%2, %k0|%k0, %2}
13446    ror{l}\t{%b2, %k0|%k0, %b2}"
13447   [(set_attr "type" "rotate")
13448    (set_attr "mode" "SI")])
13449
13450 (define_expand "rotrhi3"
13451   [(set (match_operand:HI 0 "nonimmediate_operand" "")
13452         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "")
13453                      (match_operand:QI 2 "nonmemory_operand" "")))
13454    (clobber (reg:CC FLAGS_REG))]
13455   "TARGET_HIMODE_MATH"
13456   "ix86_expand_binary_operator (ROTATERT, HImode, operands); DONE;")
13457
13458 (define_insn "*rotrhi3_one_bit"
13459   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
13460         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0")
13461                      (match_operand:QI 2 "const1_operand" "")))
13462    (clobber (reg:CC FLAGS_REG))]
13463   "(TARGET_SHIFT1 || optimize_size)
13464    && ix86_binary_operator_ok (ROTATERT, HImode, operands)"
13465   "ror{w}\t%0"
13466   [(set_attr "type" "rotate")
13467    (set (attr "length")
13468      (if_then_else (match_operand 0 "register_operand" "")
13469         (const_string "2")
13470         (const_string "*")))])
13471
13472 (define_insn "*rotrhi3_1"
13473   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
13474         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
13475                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
13476    (clobber (reg:CC FLAGS_REG))]
13477   "ix86_binary_operator_ok (ROTATERT, HImode, operands)"
13478   "@
13479    ror{w}\t{%2, %0|%0, %2}
13480    ror{w}\t{%b2, %0|%0, %b2}"
13481   [(set_attr "type" "rotate")
13482    (set_attr "mode" "HI")])
13483
13484 (define_split
13485  [(set (match_operand:HI 0 "register_operand" "")
13486        (rotatert:HI (match_dup 0) (const_int 8)))
13487   (clobber (reg:CC FLAGS_REG))]
13488  "reload_completed"
13489  [(parallel [(set (strict_low_part (match_dup 0))
13490                   (bswap:HI (match_dup 0)))
13491              (clobber (reg:CC FLAGS_REG))])]
13492  "")
13493
13494 (define_expand "rotrqi3"
13495   [(set (match_operand:QI 0 "nonimmediate_operand" "")
13496         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "")
13497                      (match_operand:QI 2 "nonmemory_operand" "")))
13498    (clobber (reg:CC FLAGS_REG))]
13499   "TARGET_QIMODE_MATH"
13500   "ix86_expand_binary_operator (ROTATERT, QImode, operands); DONE;")
13501
13502 (define_insn "*rotrqi3_1_one_bit"
13503   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13504         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0")
13505                      (match_operand:QI 2 "const1_operand" "")))
13506    (clobber (reg:CC FLAGS_REG))]
13507   "(TARGET_SHIFT1 || optimize_size)
13508    && ix86_binary_operator_ok (ROTATERT, QImode, operands)"
13509   "ror{b}\t%0"
13510   [(set_attr "type" "rotate")
13511    (set (attr "length")
13512      (if_then_else (match_operand 0 "register_operand" "")
13513         (const_string "2")
13514         (const_string "*")))])
13515
13516 (define_insn "*rotrqi3_1_one_bit_slp"
13517   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
13518         (rotatert:QI (match_dup 0)
13519                      (match_operand:QI 1 "const1_operand" "")))
13520    (clobber (reg:CC FLAGS_REG))]
13521   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13522    && (TARGET_SHIFT1 || optimize_size)"
13523   "ror{b}\t%0"
13524   [(set_attr "type" "rotate1")
13525    (set (attr "length")
13526      (if_then_else (match_operand 0 "register_operand" "")
13527         (const_string "2")
13528         (const_string "*")))])
13529
13530 (define_insn "*rotrqi3_1"
13531   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
13532         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
13533                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
13534    (clobber (reg:CC FLAGS_REG))]
13535   "ix86_binary_operator_ok (ROTATERT, QImode, operands)"
13536   "@
13537    ror{b}\t{%2, %0|%0, %2}
13538    ror{b}\t{%b2, %0|%0, %b2}"
13539   [(set_attr "type" "rotate")
13540    (set_attr "mode" "QI")])
13541
13542 (define_insn "*rotrqi3_1_slp"
13543   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
13544         (rotatert:QI (match_dup 0)
13545                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
13546    (clobber (reg:CC FLAGS_REG))]
13547   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
13548    && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
13549   "@
13550    ror{b}\t{%1, %0|%0, %1}
13551    ror{b}\t{%b1, %0|%0, %b1}"
13552   [(set_attr "type" "rotate1")
13553    (set_attr "mode" "QI")])
13554 \f
13555 ;; Bit set / bit test instructions
13556
13557 (define_expand "extv"
13558   [(set (match_operand:SI 0 "register_operand" "")
13559         (sign_extract:SI (match_operand:SI 1 "register_operand" "")
13560                          (match_operand:SI 2 "const8_operand" "")
13561                          (match_operand:SI 3 "const8_operand" "")))]
13562   ""
13563 {
13564   /* Handle extractions from %ah et al.  */
13565   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
13566     FAIL;
13567
13568   /* From mips.md: extract_bit_field doesn't verify that our source
13569      matches the predicate, so check it again here.  */
13570   if (! ext_register_operand (operands[1], VOIDmode))
13571     FAIL;
13572 })
13573
13574 (define_expand "extzv"
13575   [(set (match_operand:SI 0 "register_operand" "")
13576         (zero_extract:SI (match_operand 1 "ext_register_operand" "")
13577                          (match_operand:SI 2 "const8_operand" "")
13578                          (match_operand:SI 3 "const8_operand" "")))]
13579   ""
13580 {
13581   /* Handle extractions from %ah et al.  */
13582   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
13583     FAIL;
13584
13585   /* From mips.md: extract_bit_field doesn't verify that our source
13586      matches the predicate, so check it again here.  */
13587   if (! ext_register_operand (operands[1], VOIDmode))
13588     FAIL;
13589 })
13590
13591 (define_expand "insv"
13592   [(set (zero_extract (match_operand 0 "ext_register_operand" "")
13593                       (match_operand 1 "const8_operand" "")
13594                       (match_operand 2 "const8_operand" ""))
13595         (match_operand 3 "register_operand" ""))]
13596   ""
13597 {
13598   /* Handle insertions to %ah et al.  */
13599   if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
13600     FAIL;
13601
13602   /* From mips.md: insert_bit_field doesn't verify that our source
13603      matches the predicate, so check it again here.  */
13604   if (! ext_register_operand (operands[0], VOIDmode))
13605     FAIL;
13606
13607   if (TARGET_64BIT)
13608     emit_insn (gen_movdi_insv_1_rex64 (operands[0], operands[3]));
13609   else
13610     emit_insn (gen_movsi_insv_1 (operands[0], operands[3]));
13611
13612   DONE;
13613 })
13614
13615 ;; %%% bts, btr, btc, bt.
13616 ;; In general these instructions are *slow* when applied to memory,
13617 ;; since they enforce atomic operation.  When applied to registers,
13618 ;; it depends on the cpu implementation.  They're never faster than
13619 ;; the corresponding and/ior/xor operations, so with 32-bit there's
13620 ;; no point.  But in 64-bit, we can't hold the relevant immediates
13621 ;; within the instruction itself, so operating on bits in the high
13622 ;; 32-bits of a register becomes easier.
13623 ;;
13624 ;; These are slow on Nocona, but fast on Athlon64.  We do require the use
13625 ;; of btrq and btcq for corner cases of post-reload expansion of absdf and
13626 ;; negdf respectively, so they can never be disabled entirely.
13627
13628 (define_insn "*btsq"
13629   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
13630                          (const_int 1)
13631                          (match_operand:DI 1 "const_0_to_63_operand" ""))
13632         (const_int 1))
13633    (clobber (reg:CC FLAGS_REG))]
13634   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
13635   "bts{q} %1,%0"
13636   [(set_attr "type" "alu1")])
13637
13638 (define_insn "*btrq"
13639   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
13640                          (const_int 1)
13641                          (match_operand:DI 1 "const_0_to_63_operand" ""))
13642         (const_int 0))
13643    (clobber (reg:CC FLAGS_REG))]
13644   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
13645   "btr{q} %1,%0"
13646   [(set_attr "type" "alu1")])
13647
13648 (define_insn "*btcq"
13649   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
13650                          (const_int 1)
13651                          (match_operand:DI 1 "const_0_to_63_operand" ""))
13652         (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
13653    (clobber (reg:CC FLAGS_REG))]
13654   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
13655   "btc{q} %1,%0"
13656   [(set_attr "type" "alu1")])
13657
13658 ;; Allow Nocona to avoid these instructions if a register is available.
13659
13660 (define_peephole2
13661   [(match_scratch:DI 2 "r")
13662    (parallel [(set (zero_extract:DI
13663                      (match_operand:DI 0 "register_operand" "")
13664                      (const_int 1)
13665                      (match_operand:DI 1 "const_0_to_63_operand" ""))
13666                    (const_int 1))
13667               (clobber (reg:CC FLAGS_REG))])]
13668   "TARGET_64BIT && !TARGET_USE_BT"
13669   [(const_int 0)]
13670 {
13671   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
13672   rtx op1;
13673
13674   if (HOST_BITS_PER_WIDE_INT >= 64)
13675     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13676   else if (i < HOST_BITS_PER_WIDE_INT)
13677     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13678   else
13679     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
13680
13681   op1 = immed_double_const (lo, hi, DImode);
13682   if (i >= 31)
13683     {
13684       emit_move_insn (operands[2], op1);
13685       op1 = operands[2];
13686     }
13687
13688   emit_insn (gen_iordi3 (operands[0], operands[0], op1));
13689   DONE;
13690 })
13691
13692 (define_peephole2
13693   [(match_scratch:DI 2 "r")
13694    (parallel [(set (zero_extract:DI
13695                      (match_operand:DI 0 "register_operand" "")
13696                      (const_int 1)
13697                      (match_operand:DI 1 "const_0_to_63_operand" ""))
13698                    (const_int 0))
13699               (clobber (reg:CC FLAGS_REG))])]
13700   "TARGET_64BIT && !TARGET_USE_BT"
13701   [(const_int 0)]
13702 {
13703   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
13704   rtx op1;
13705
13706   if (HOST_BITS_PER_WIDE_INT >= 64)
13707     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13708   else if (i < HOST_BITS_PER_WIDE_INT)
13709     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13710   else
13711     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
13712
13713   op1 = immed_double_const (~lo, ~hi, DImode);
13714   if (i >= 32)
13715     {
13716       emit_move_insn (operands[2], op1);
13717       op1 = operands[2];
13718     }
13719
13720   emit_insn (gen_anddi3 (operands[0], operands[0], op1));
13721   DONE;
13722 })
13723
13724 (define_peephole2
13725   [(match_scratch:DI 2 "r")
13726    (parallel [(set (zero_extract:DI
13727                      (match_operand:DI 0 "register_operand" "")
13728                      (const_int 1)
13729                      (match_operand:DI 1 "const_0_to_63_operand" ""))
13730               (not:DI (zero_extract:DI
13731                         (match_dup 0) (const_int 1) (match_dup 1))))
13732               (clobber (reg:CC FLAGS_REG))])]
13733   "TARGET_64BIT && !TARGET_USE_BT"
13734   [(const_int 0)]
13735 {
13736   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
13737   rtx op1;
13738
13739   if (HOST_BITS_PER_WIDE_INT >= 64)
13740     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13741   else if (i < HOST_BITS_PER_WIDE_INT)
13742     lo = (HOST_WIDE_INT)1 << i, hi = 0;
13743   else
13744     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
13745
13746   op1 = immed_double_const (lo, hi, DImode);
13747   if (i >= 31)
13748     {
13749       emit_move_insn (operands[2], op1);
13750       op1 = operands[2];
13751     }
13752
13753   emit_insn (gen_xordi3 (operands[0], operands[0], op1));
13754   DONE;
13755 })
13756 \f
13757 ;; Store-flag instructions.
13758
13759 ;; For all sCOND expanders, also expand the compare or test insn that
13760 ;; generates cc0.  Generate an equality comparison if `seq' or `sne'.
13761
13762 ;; %%% Do the expansion to SImode.  If PII, do things the xor+setcc way
13763 ;; to avoid partial register stalls.  Otherwise do things the setcc+movzx
13764 ;; way, which can later delete the movzx if only QImode is needed.
13765
13766 (define_expand "seq"
13767   [(set (match_operand:QI 0 "register_operand" "")
13768         (eq:QI (reg:CC FLAGS_REG) (const_int 0)))]
13769   ""
13770   "if (ix86_expand_setcc (EQ, operands[0])) DONE; else FAIL;")
13771
13772 (define_expand "sne"
13773   [(set (match_operand:QI 0 "register_operand" "")
13774         (ne:QI (reg:CC FLAGS_REG) (const_int 0)))]
13775   ""
13776   "if (ix86_expand_setcc (NE, operands[0])) DONE; else FAIL;")
13777
13778 (define_expand "sgt"
13779   [(set (match_operand:QI 0 "register_operand" "")
13780         (gt:QI (reg:CC FLAGS_REG) (const_int 0)))]
13781   ""
13782   "if (ix86_expand_setcc (GT, operands[0])) DONE; else FAIL;")
13783
13784 (define_expand "sgtu"
13785   [(set (match_operand:QI 0 "register_operand" "")
13786         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))]
13787   ""
13788   "if (ix86_expand_setcc (GTU, operands[0])) DONE; else FAIL;")
13789
13790 (define_expand "slt"
13791   [(set (match_operand:QI 0 "register_operand" "")
13792         (lt:QI (reg:CC FLAGS_REG) (const_int 0)))]
13793   ""
13794   "if (ix86_expand_setcc (LT, operands[0])) DONE; else FAIL;")
13795
13796 (define_expand "sltu"
13797   [(set (match_operand:QI 0 "register_operand" "")
13798         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))]
13799   ""
13800   "if (ix86_expand_setcc (LTU, operands[0])) DONE; else FAIL;")
13801
13802 (define_expand "sge"
13803   [(set (match_operand:QI 0 "register_operand" "")
13804         (ge:QI (reg:CC FLAGS_REG) (const_int 0)))]
13805   ""
13806   "if (ix86_expand_setcc (GE, operands[0])) DONE; else FAIL;")
13807
13808 (define_expand "sgeu"
13809   [(set (match_operand:QI 0 "register_operand" "")
13810         (geu:QI (reg:CC FLAGS_REG) (const_int 0)))]
13811   ""
13812   "if (ix86_expand_setcc (GEU, operands[0])) DONE; else FAIL;")
13813
13814 (define_expand "sle"
13815   [(set (match_operand:QI 0 "register_operand" "")
13816         (le:QI (reg:CC FLAGS_REG) (const_int 0)))]
13817   ""
13818   "if (ix86_expand_setcc (LE, operands[0])) DONE; else FAIL;")
13819
13820 (define_expand "sleu"
13821   [(set (match_operand:QI 0 "register_operand" "")
13822         (leu:QI (reg:CC FLAGS_REG) (const_int 0)))]
13823   ""
13824   "if (ix86_expand_setcc (LEU, operands[0])) DONE; else FAIL;")
13825
13826 (define_expand "sunordered"
13827   [(set (match_operand:QI 0 "register_operand" "")
13828         (unordered:QI (reg:CC FLAGS_REG) (const_int 0)))]
13829   "TARGET_80387 || TARGET_SSE"
13830   "if (ix86_expand_setcc (UNORDERED, operands[0])) DONE; else FAIL;")
13831
13832 (define_expand "sordered"
13833   [(set (match_operand:QI 0 "register_operand" "")
13834         (ordered:QI (reg:CC FLAGS_REG) (const_int 0)))]
13835   "TARGET_80387"
13836   "if (ix86_expand_setcc (ORDERED, operands[0])) DONE; else FAIL;")
13837
13838 (define_expand "suneq"
13839   [(set (match_operand:QI 0 "register_operand" "")
13840         (uneq:QI (reg:CC FLAGS_REG) (const_int 0)))]
13841   "TARGET_80387 || TARGET_SSE"
13842   "if (ix86_expand_setcc (UNEQ, operands[0])) DONE; else FAIL;")
13843
13844 (define_expand "sunge"
13845   [(set (match_operand:QI 0 "register_operand" "")
13846         (unge:QI (reg:CC FLAGS_REG) (const_int 0)))]
13847   "TARGET_80387 || TARGET_SSE"
13848   "if (ix86_expand_setcc (UNGE, operands[0])) DONE; else FAIL;")
13849
13850 (define_expand "sungt"
13851   [(set (match_operand:QI 0 "register_operand" "")
13852         (ungt:QI (reg:CC FLAGS_REG) (const_int 0)))]
13853   "TARGET_80387 || TARGET_SSE"
13854   "if (ix86_expand_setcc (UNGT, operands[0])) DONE; else FAIL;")
13855
13856 (define_expand "sunle"
13857   [(set (match_operand:QI 0 "register_operand" "")
13858         (unle:QI (reg:CC FLAGS_REG) (const_int 0)))]
13859   "TARGET_80387 || TARGET_SSE"
13860   "if (ix86_expand_setcc (UNLE, operands[0])) DONE; else FAIL;")
13861
13862 (define_expand "sunlt"
13863   [(set (match_operand:QI 0 "register_operand" "")
13864         (unlt:QI (reg:CC FLAGS_REG) (const_int 0)))]
13865   "TARGET_80387 || TARGET_SSE"
13866   "if (ix86_expand_setcc (UNLT, operands[0])) DONE; else FAIL;")
13867
13868 (define_expand "sltgt"
13869   [(set (match_operand:QI 0 "register_operand" "")
13870         (ltgt:QI (reg:CC FLAGS_REG) (const_int 0)))]
13871   "TARGET_80387 || TARGET_SSE"
13872   "if (ix86_expand_setcc (LTGT, operands[0])) DONE; else FAIL;")
13873
13874 (define_insn "*setcc_1"
13875   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
13876         (match_operator:QI 1 "ix86_comparison_operator"
13877           [(reg FLAGS_REG) (const_int 0)]))]
13878   ""
13879   "set%C1\t%0"
13880   [(set_attr "type" "setcc")
13881    (set_attr "mode" "QI")])
13882
13883 (define_insn "*setcc_2"
13884   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
13885         (match_operator:QI 1 "ix86_comparison_operator"
13886           [(reg FLAGS_REG) (const_int 0)]))]
13887   ""
13888   "set%C1\t%0"
13889   [(set_attr "type" "setcc")
13890    (set_attr "mode" "QI")])
13891
13892 ;; In general it is not safe to assume too much about CCmode registers,
13893 ;; so simplify-rtx stops when it sees a second one.  Under certain
13894 ;; conditions this is safe on x86, so help combine not create
13895 ;;
13896 ;;      seta    %al
13897 ;;      testb   %al, %al
13898 ;;      sete    %al
13899
13900 (define_split
13901   [(set (match_operand:QI 0 "nonimmediate_operand" "")
13902         (ne:QI (match_operator 1 "ix86_comparison_operator"
13903                  [(reg FLAGS_REG) (const_int 0)])
13904             (const_int 0)))]
13905   ""
13906   [(set (match_dup 0) (match_dup 1))]
13907 {
13908   PUT_MODE (operands[1], QImode);
13909 })
13910
13911 (define_split
13912   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
13913         (ne:QI (match_operator 1 "ix86_comparison_operator"
13914                  [(reg FLAGS_REG) (const_int 0)])
13915             (const_int 0)))]
13916   ""
13917   [(set (match_dup 0) (match_dup 1))]
13918 {
13919   PUT_MODE (operands[1], QImode);
13920 })
13921
13922 (define_split
13923   [(set (match_operand:QI 0 "nonimmediate_operand" "")
13924         (eq:QI (match_operator 1 "ix86_comparison_operator"
13925                  [(reg FLAGS_REG) (const_int 0)])
13926             (const_int 0)))]
13927   ""
13928   [(set (match_dup 0) (match_dup 1))]
13929 {
13930   rtx new_op1 = copy_rtx (operands[1]);
13931   operands[1] = new_op1;
13932   PUT_MODE (new_op1, QImode);
13933   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
13934                                              GET_MODE (XEXP (new_op1, 0))));
13935
13936   /* Make sure that (a) the CCmode we have for the flags is strong
13937      enough for the reversed compare or (b) we have a valid FP compare.  */
13938   if (! ix86_comparison_operator (new_op1, VOIDmode))
13939     FAIL;
13940 })
13941
13942 (define_split
13943   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
13944         (eq:QI (match_operator 1 "ix86_comparison_operator"
13945                  [(reg FLAGS_REG) (const_int 0)])
13946             (const_int 0)))]
13947   ""
13948   [(set (match_dup 0) (match_dup 1))]
13949 {
13950   rtx new_op1 = copy_rtx (operands[1]);
13951   operands[1] = new_op1;
13952   PUT_MODE (new_op1, QImode);
13953   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
13954                                              GET_MODE (XEXP (new_op1, 0))));
13955
13956   /* Make sure that (a) the CCmode we have for the flags is strong
13957      enough for the reversed compare or (b) we have a valid FP compare.  */
13958   if (! ix86_comparison_operator (new_op1, VOIDmode))
13959     FAIL;
13960 })
13961
13962 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
13963 ;; subsequent logical operations are used to imitate conditional moves.
13964 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
13965 ;; it directly.
13966
13967 (define_insn "*sse_setcc<mode>"
13968   [(set (match_operand:MODEF 0 "register_operand" "=x")
13969         (match_operator:MODEF 1 "sse_comparison_operator"
13970           [(match_operand:MODEF 2 "register_operand" "0")
13971            (match_operand:MODEF 3 "nonimmediate_operand" "xm")]))]
13972   "SSE_FLOAT_MODE_P (<MODE>mode) && !TARGET_SSE5"
13973   "cmp%D1s<ssemodefsuffix>\t{%3, %0|%0, %3}"
13974   [(set_attr "type" "ssecmp")
13975    (set_attr "mode" "<MODE>")])
13976
13977 (define_insn "*sse5_setcc<mode>"
13978   [(set (match_operand:MODEF 0 "register_operand" "=x")
13979         (match_operator:MODEF 1 "sse5_comparison_float_operator"
13980           [(match_operand:MODEF 2 "register_operand" "x")
13981            (match_operand:MODEF 3 "nonimmediate_operand" "xm")]))]
13982   "TARGET_SSE5"
13983   "com%Y1s<ssemodefsuffix>\t{%3, %2, %0|%0, %2, %3}"
13984   [(set_attr "type" "sse4arg")
13985    (set_attr "mode" "<MODE>")])
13986
13987 \f
13988 ;; Basic conditional jump instructions.
13989 ;; We ignore the overflow flag for signed branch instructions.
13990
13991 ;; For all bCOND expanders, also expand the compare or test insn that
13992 ;; generates reg FLAGS_REG.  Generate an equality comparison if `beq' or `bne'.
13993
13994 (define_expand "beq"
13995   [(set (pc)
13996         (if_then_else (match_dup 1)
13997                       (label_ref (match_operand 0 "" ""))
13998                       (pc)))]
13999   ""
14000   "ix86_expand_branch (EQ, operands[0]); DONE;")
14001
14002 (define_expand "bne"
14003   [(set (pc)
14004         (if_then_else (match_dup 1)
14005                       (label_ref (match_operand 0 "" ""))
14006                       (pc)))]
14007   ""
14008   "ix86_expand_branch (NE, operands[0]); DONE;")
14009
14010 (define_expand "bgt"
14011   [(set (pc)
14012         (if_then_else (match_dup 1)
14013                       (label_ref (match_operand 0 "" ""))
14014                       (pc)))]
14015   ""
14016   "ix86_expand_branch (GT, operands[0]); DONE;")
14017
14018 (define_expand "bgtu"
14019   [(set (pc)
14020         (if_then_else (match_dup 1)
14021                       (label_ref (match_operand 0 "" ""))
14022                       (pc)))]
14023   ""
14024   "ix86_expand_branch (GTU, operands[0]); DONE;")
14025
14026 (define_expand "blt"
14027   [(set (pc)
14028         (if_then_else (match_dup 1)
14029                       (label_ref (match_operand 0 "" ""))
14030                       (pc)))]
14031   ""
14032   "ix86_expand_branch (LT, operands[0]); DONE;")
14033
14034 (define_expand "bltu"
14035   [(set (pc)
14036         (if_then_else (match_dup 1)
14037                       (label_ref (match_operand 0 "" ""))
14038                       (pc)))]
14039   ""
14040   "ix86_expand_branch (LTU, operands[0]); DONE;")
14041
14042 (define_expand "bge"
14043   [(set (pc)
14044         (if_then_else (match_dup 1)
14045                       (label_ref (match_operand 0 "" ""))
14046                       (pc)))]
14047   ""
14048   "ix86_expand_branch (GE, operands[0]); DONE;")
14049
14050 (define_expand "bgeu"
14051   [(set (pc)
14052         (if_then_else (match_dup 1)
14053                       (label_ref (match_operand 0 "" ""))
14054                       (pc)))]
14055   ""
14056   "ix86_expand_branch (GEU, operands[0]); DONE;")
14057
14058 (define_expand "ble"
14059   [(set (pc)
14060         (if_then_else (match_dup 1)
14061                       (label_ref (match_operand 0 "" ""))
14062                       (pc)))]
14063   ""
14064   "ix86_expand_branch (LE, operands[0]); DONE;")
14065
14066 (define_expand "bleu"
14067   [(set (pc)
14068         (if_then_else (match_dup 1)
14069                       (label_ref (match_operand 0 "" ""))
14070                       (pc)))]
14071   ""
14072   "ix86_expand_branch (LEU, operands[0]); DONE;")
14073
14074 (define_expand "bunordered"
14075   [(set (pc)
14076         (if_then_else (match_dup 1)
14077                       (label_ref (match_operand 0 "" ""))
14078                       (pc)))]
14079   "TARGET_80387 || TARGET_SSE_MATH"
14080   "ix86_expand_branch (UNORDERED, operands[0]); DONE;")
14081
14082 (define_expand "bordered"
14083   [(set (pc)
14084         (if_then_else (match_dup 1)
14085                       (label_ref (match_operand 0 "" ""))
14086                       (pc)))]
14087   "TARGET_80387 || TARGET_SSE_MATH"
14088   "ix86_expand_branch (ORDERED, operands[0]); DONE;")
14089
14090 (define_expand "buneq"
14091   [(set (pc)
14092         (if_then_else (match_dup 1)
14093                       (label_ref (match_operand 0 "" ""))
14094                       (pc)))]
14095   "TARGET_80387 || TARGET_SSE_MATH"
14096   "ix86_expand_branch (UNEQ, operands[0]); DONE;")
14097
14098 (define_expand "bunge"
14099   [(set (pc)
14100         (if_then_else (match_dup 1)
14101                       (label_ref (match_operand 0 "" ""))
14102                       (pc)))]
14103   "TARGET_80387 || TARGET_SSE_MATH"
14104   "ix86_expand_branch (UNGE, operands[0]); DONE;")
14105
14106 (define_expand "bungt"
14107   [(set (pc)
14108         (if_then_else (match_dup 1)
14109                       (label_ref (match_operand 0 "" ""))
14110                       (pc)))]
14111   "TARGET_80387 || TARGET_SSE_MATH"
14112   "ix86_expand_branch (UNGT, operands[0]); DONE;")
14113
14114 (define_expand "bunle"
14115   [(set (pc)
14116         (if_then_else (match_dup 1)
14117                       (label_ref (match_operand 0 "" ""))
14118                       (pc)))]
14119   "TARGET_80387 || TARGET_SSE_MATH"
14120   "ix86_expand_branch (UNLE, operands[0]); DONE;")
14121
14122 (define_expand "bunlt"
14123   [(set (pc)
14124         (if_then_else (match_dup 1)
14125                       (label_ref (match_operand 0 "" ""))
14126                       (pc)))]
14127   "TARGET_80387 || TARGET_SSE_MATH"
14128   "ix86_expand_branch (UNLT, operands[0]); DONE;")
14129
14130 (define_expand "bltgt"
14131   [(set (pc)
14132         (if_then_else (match_dup 1)
14133                       (label_ref (match_operand 0 "" ""))
14134                       (pc)))]
14135   "TARGET_80387 || TARGET_SSE_MATH"
14136   "ix86_expand_branch (LTGT, operands[0]); DONE;")
14137
14138 (define_insn "*jcc_1"
14139   [(set (pc)
14140         (if_then_else (match_operator 1 "ix86_comparison_operator"
14141                                       [(reg FLAGS_REG) (const_int 0)])
14142                       (label_ref (match_operand 0 "" ""))
14143                       (pc)))]
14144   ""
14145   "%+j%C1\t%l0"
14146   [(set_attr "type" "ibr")
14147    (set_attr "modrm" "0")
14148    (set (attr "length")
14149            (if_then_else (and (ge (minus (match_dup 0) (pc))
14150                                   (const_int -126))
14151                               (lt (minus (match_dup 0) (pc))
14152                                   (const_int 128)))
14153              (const_int 2)
14154              (const_int 6)))])
14155
14156 (define_insn "*jcc_2"
14157   [(set (pc)
14158         (if_then_else (match_operator 1 "ix86_comparison_operator"
14159                                       [(reg FLAGS_REG) (const_int 0)])
14160                       (pc)
14161                       (label_ref (match_operand 0 "" ""))))]
14162   ""
14163   "%+j%c1\t%l0"
14164   [(set_attr "type" "ibr")
14165    (set_attr "modrm" "0")
14166    (set (attr "length")
14167            (if_then_else (and (ge (minus (match_dup 0) (pc))
14168                                   (const_int -126))
14169                               (lt (minus (match_dup 0) (pc))
14170                                   (const_int 128)))
14171              (const_int 2)
14172              (const_int 6)))])
14173
14174 ;; In general it is not safe to assume too much about CCmode registers,
14175 ;; so simplify-rtx stops when it sees a second one.  Under certain
14176 ;; conditions this is safe on x86, so help combine not create
14177 ;;
14178 ;;      seta    %al
14179 ;;      testb   %al, %al
14180 ;;      je      Lfoo
14181
14182 (define_split
14183   [(set (pc)
14184         (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
14185                                       [(reg FLAGS_REG) (const_int 0)])
14186                           (const_int 0))
14187                       (label_ref (match_operand 1 "" ""))
14188                       (pc)))]
14189   ""
14190   [(set (pc)
14191         (if_then_else (match_dup 0)
14192                       (label_ref (match_dup 1))
14193                       (pc)))]
14194 {
14195   PUT_MODE (operands[0], VOIDmode);
14196 })
14197
14198 (define_split
14199   [(set (pc)
14200         (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
14201                                       [(reg FLAGS_REG) (const_int 0)])
14202                           (const_int 0))
14203                       (label_ref (match_operand 1 "" ""))
14204                       (pc)))]
14205   ""
14206   [(set (pc)
14207         (if_then_else (match_dup 0)
14208                       (label_ref (match_dup 1))
14209                       (pc)))]
14210 {
14211   rtx new_op0 = copy_rtx (operands[0]);
14212   operands[0] = new_op0;
14213   PUT_MODE (new_op0, VOIDmode);
14214   PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0),
14215                                              GET_MODE (XEXP (new_op0, 0))));
14216
14217   /* Make sure that (a) the CCmode we have for the flags is strong
14218      enough for the reversed compare or (b) we have a valid FP compare.  */
14219   if (! ix86_comparison_operator (new_op0, VOIDmode))
14220     FAIL;
14221 })
14222
14223 ;; Define combination compare-and-branch fp compare instructions to use
14224 ;; during early optimization.  Splitting the operation apart early makes
14225 ;; for bad code when we want to reverse the operation.
14226
14227 (define_insn "*fp_jcc_1_mixed"
14228   [(set (pc)
14229         (if_then_else (match_operator 0 "comparison_operator"
14230                         [(match_operand 1 "register_operand" "f,x")
14231                          (match_operand 2 "nonimmediate_operand" "f,xm")])
14232           (label_ref (match_operand 3 "" ""))
14233           (pc)))
14234    (clobber (reg:CCFP FPSR_REG))
14235    (clobber (reg:CCFP FLAGS_REG))]
14236   "TARGET_MIX_SSE_I387
14237    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14238    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14239    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14240   "#")
14241
14242 (define_insn "*fp_jcc_1_sse"
14243   [(set (pc)
14244         (if_then_else (match_operator 0 "comparison_operator"
14245                         [(match_operand 1 "register_operand" "x")
14246                          (match_operand 2 "nonimmediate_operand" "xm")])
14247           (label_ref (match_operand 3 "" ""))
14248           (pc)))
14249    (clobber (reg:CCFP FPSR_REG))
14250    (clobber (reg:CCFP FLAGS_REG))]
14251   "TARGET_SSE_MATH
14252    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14253    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14254    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14255   "#")
14256
14257 (define_insn "*fp_jcc_1_387"
14258   [(set (pc)
14259         (if_then_else (match_operator 0 "comparison_operator"
14260                         [(match_operand 1 "register_operand" "f")
14261                          (match_operand 2 "register_operand" "f")])
14262           (label_ref (match_operand 3 "" ""))
14263           (pc)))
14264    (clobber (reg:CCFP FPSR_REG))
14265    (clobber (reg:CCFP FLAGS_REG))]
14266   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14267    && TARGET_CMOVE
14268    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14269    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14270   "#")
14271
14272 (define_insn "*fp_jcc_2_mixed"
14273   [(set (pc)
14274         (if_then_else (match_operator 0 "comparison_operator"
14275                         [(match_operand 1 "register_operand" "f,x")
14276                          (match_operand 2 "nonimmediate_operand" "f,xm")])
14277           (pc)
14278           (label_ref (match_operand 3 "" ""))))
14279    (clobber (reg:CCFP FPSR_REG))
14280    (clobber (reg:CCFP FLAGS_REG))]
14281   "TARGET_MIX_SSE_I387
14282    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14283    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14284    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14285   "#")
14286
14287 (define_insn "*fp_jcc_2_sse"
14288   [(set (pc)
14289         (if_then_else (match_operator 0 "comparison_operator"
14290                         [(match_operand 1 "register_operand" "x")
14291                          (match_operand 2 "nonimmediate_operand" "xm")])
14292           (pc)
14293           (label_ref (match_operand 3 "" ""))))
14294    (clobber (reg:CCFP FPSR_REG))
14295    (clobber (reg:CCFP FLAGS_REG))]
14296   "TARGET_SSE_MATH
14297    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
14298    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14299    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14300   "#")
14301
14302 (define_insn "*fp_jcc_2_387"
14303   [(set (pc)
14304         (if_then_else (match_operator 0 "comparison_operator"
14305                         [(match_operand 1 "register_operand" "f")
14306                          (match_operand 2 "register_operand" "f")])
14307           (pc)
14308           (label_ref (match_operand 3 "" ""))))
14309    (clobber (reg:CCFP FPSR_REG))
14310    (clobber (reg:CCFP FLAGS_REG))]
14311   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14312    && TARGET_CMOVE
14313    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14314    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14315   "#")
14316
14317 (define_insn "*fp_jcc_3_387"
14318   [(set (pc)
14319         (if_then_else (match_operator 0 "comparison_operator"
14320                         [(match_operand 1 "register_operand" "f")
14321                          (match_operand 2 "nonimmediate_operand" "fm")])
14322           (label_ref (match_operand 3 "" ""))
14323           (pc)))
14324    (clobber (reg:CCFP FPSR_REG))
14325    (clobber (reg:CCFP FLAGS_REG))
14326    (clobber (match_scratch:HI 4 "=a"))]
14327   "TARGET_80387
14328    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
14329    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14330    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
14331    && SELECT_CC_MODE (GET_CODE (operands[0]),
14332                       operands[1], operands[2]) == CCFPmode
14333    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14334   "#")
14335
14336 (define_insn "*fp_jcc_4_387"
14337   [(set (pc)
14338         (if_then_else (match_operator 0 "comparison_operator"
14339                         [(match_operand 1 "register_operand" "f")
14340                          (match_operand 2 "nonimmediate_operand" "fm")])
14341           (pc)
14342           (label_ref (match_operand 3 "" ""))))
14343    (clobber (reg:CCFP FPSR_REG))
14344    (clobber (reg:CCFP FLAGS_REG))
14345    (clobber (match_scratch:HI 4 "=a"))]
14346   "TARGET_80387
14347    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
14348    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14349    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
14350    && SELECT_CC_MODE (GET_CODE (operands[0]),
14351                       operands[1], operands[2]) == CCFPmode
14352    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14353   "#")
14354
14355 (define_insn "*fp_jcc_5_387"
14356   [(set (pc)
14357         (if_then_else (match_operator 0 "comparison_operator"
14358                         [(match_operand 1 "register_operand" "f")
14359                          (match_operand 2 "register_operand" "f")])
14360           (label_ref (match_operand 3 "" ""))
14361           (pc)))
14362    (clobber (reg:CCFP FPSR_REG))
14363    (clobber (reg:CCFP FLAGS_REG))
14364    (clobber (match_scratch:HI 4 "=a"))]
14365   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14366    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14367    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14368   "#")
14369
14370 (define_insn "*fp_jcc_6_387"
14371   [(set (pc)
14372         (if_then_else (match_operator 0 "comparison_operator"
14373                         [(match_operand 1 "register_operand" "f")
14374                          (match_operand 2 "register_operand" "f")])
14375           (pc)
14376           (label_ref (match_operand 3 "" ""))))
14377    (clobber (reg:CCFP FPSR_REG))
14378    (clobber (reg:CCFP FLAGS_REG))
14379    (clobber (match_scratch:HI 4 "=a"))]
14380   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14381    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14382    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14383   "#")
14384
14385 (define_insn "*fp_jcc_7_387"
14386   [(set (pc)
14387         (if_then_else (match_operator 0 "comparison_operator"
14388                         [(match_operand 1 "register_operand" "f")
14389                          (match_operand 2 "const0_operand" "X")])
14390           (label_ref (match_operand 3 "" ""))
14391           (pc)))
14392    (clobber (reg:CCFP FPSR_REG))
14393    (clobber (reg:CCFP FLAGS_REG))
14394    (clobber (match_scratch:HI 4 "=a"))]
14395   "X87_FLOAT_MODE_P (GET_MODE (operands[1]))
14396    && GET_MODE (operands[1]) == GET_MODE (operands[2])
14397    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
14398    && SELECT_CC_MODE (GET_CODE (operands[0]),
14399                       operands[1], operands[2]) == CCFPmode
14400    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
14401   "#")
14402
14403 ;; The order of operands in *fp_jcc_8_387 is forced by combine in
14404 ;; simplify_comparison () function. Float operator is treated as RTX_OBJ
14405 ;; with a precedence over other operators and is always put in the first
14406 ;; place. Swap condition and operands to match ficom instruction.
14407
14408 (define_insn "*fp_jcc_8<mode>_387"
14409   [(set (pc)
14410         (if_then_else (match_operator 0 "comparison_operator"
14411                         [(match_operator 1 "float_operator"
14412                            [(match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r")])
14413                            (match_operand 3 "register_operand" "f,f")])
14414           (label_ref (match_operand 4 "" ""))
14415           (pc)))
14416    (clobber (reg:CCFP FPSR_REG))
14417    (clobber (reg:CCFP FLAGS_REG))
14418    (clobber (match_scratch:HI 5 "=a,a"))]
14419   "X87_FLOAT_MODE_P (GET_MODE (operands[3]))
14420    && TARGET_USE_<MODE>MODE_FIOP
14421    && GET_MODE (operands[1]) == GET_MODE (operands[3])
14422    && !ix86_use_fcomi_compare (swap_condition (GET_CODE (operands[0])))
14423    && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode
14424    && ix86_fp_jump_nontrivial_p (swap_condition (GET_CODE (operands[0])))"
14425   "#")
14426
14427 (define_split
14428   [(set (pc)
14429         (if_then_else (match_operator 0 "comparison_operator"
14430                         [(match_operand 1 "register_operand" "")
14431                          (match_operand 2 "nonimmediate_operand" "")])
14432           (match_operand 3 "" "")
14433           (match_operand 4 "" "")))
14434    (clobber (reg:CCFP FPSR_REG))
14435    (clobber (reg:CCFP FLAGS_REG))]
14436   "reload_completed"
14437   [(const_int 0)]
14438 {
14439   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
14440                         operands[3], operands[4], NULL_RTX, NULL_RTX);
14441   DONE;
14442 })
14443
14444 (define_split
14445   [(set (pc)
14446         (if_then_else (match_operator 0 "comparison_operator"
14447                         [(match_operand 1 "register_operand" "")
14448                          (match_operand 2 "general_operand" "")])
14449           (match_operand 3 "" "")
14450           (match_operand 4 "" "")))
14451    (clobber (reg:CCFP FPSR_REG))
14452    (clobber (reg:CCFP FLAGS_REG))
14453    (clobber (match_scratch:HI 5 "=a"))]
14454   "reload_completed"
14455   [(const_int 0)]
14456 {
14457   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
14458                         operands[3], operands[4], operands[5], NULL_RTX);
14459   DONE;
14460 })
14461
14462 (define_split
14463   [(set (pc)
14464         (if_then_else (match_operator 0 "comparison_operator"
14465                         [(match_operator 1 "float_operator"
14466                            [(match_operand:X87MODEI12 2 "memory_operand" "")])
14467                            (match_operand 3 "register_operand" "")])
14468           (match_operand 4 "" "")
14469           (match_operand 5 "" "")))
14470    (clobber (reg:CCFP FPSR_REG))
14471    (clobber (reg:CCFP FLAGS_REG))
14472    (clobber (match_scratch:HI 6 "=a"))]
14473   "reload_completed"
14474   [(const_int 0)]
14475 {
14476   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]);
14477   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
14478                         operands[3], operands[7],
14479                         operands[4], operands[5], operands[6], NULL_RTX);
14480   DONE;
14481 })
14482
14483 ;; %%% Kill this when reload knows how to do it.
14484 (define_split
14485   [(set (pc)
14486         (if_then_else (match_operator 0 "comparison_operator"
14487                         [(match_operator 1 "float_operator"
14488                            [(match_operand:X87MODEI12 2 "register_operand" "")])
14489                            (match_operand 3 "register_operand" "")])
14490           (match_operand 4 "" "")
14491           (match_operand 5 "" "")))
14492    (clobber (reg:CCFP FPSR_REG))
14493    (clobber (reg:CCFP FLAGS_REG))
14494    (clobber (match_scratch:HI 6 "=a"))]
14495   "reload_completed"
14496   [(const_int 0)]
14497 {
14498   operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
14499   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]);
14500   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
14501                         operands[3], operands[7],
14502                         operands[4], operands[5], operands[6], operands[2]);
14503   DONE;
14504 })
14505 \f
14506 ;; Unconditional and other jump instructions
14507
14508 (define_insn "jump"
14509   [(set (pc)
14510         (label_ref (match_operand 0 "" "")))]
14511   ""
14512   "jmp\t%l0"
14513   [(set_attr "type" "ibr")
14514    (set (attr "length")
14515            (if_then_else (and (ge (minus (match_dup 0) (pc))
14516                                   (const_int -126))
14517                               (lt (minus (match_dup 0) (pc))
14518                                   (const_int 128)))
14519              (const_int 2)
14520              (const_int 5)))
14521    (set_attr "modrm" "0")])
14522
14523 (define_expand "indirect_jump"
14524   [(set (pc) (match_operand 0 "nonimmediate_operand" ""))]
14525   ""
14526   "")
14527
14528 (define_insn "*indirect_jump"
14529   [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))]
14530   "!TARGET_64BIT"
14531   "jmp\t%A0"
14532   [(set_attr "type" "ibr")
14533    (set_attr "length_immediate" "0")])
14534
14535 (define_insn "*indirect_jump_rtx64"
14536   [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))]
14537   "TARGET_64BIT"
14538   "jmp\t%A0"
14539   [(set_attr "type" "ibr")
14540    (set_attr "length_immediate" "0")])
14541
14542 (define_expand "tablejump"
14543   [(parallel [(set (pc) (match_operand 0 "nonimmediate_operand" ""))
14544               (use (label_ref (match_operand 1 "" "")))])]
14545   ""
14546 {
14547   /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
14548      relative.  Convert the relative address to an absolute address.  */
14549   if (flag_pic)
14550     {
14551       rtx op0, op1;
14552       enum rtx_code code;
14553
14554       /* We can't use @GOTOFF for text labels on VxWorks;
14555          see gotoff_operand.  */
14556       if (TARGET_64BIT || TARGET_VXWORKS_RTP)
14557         {
14558           code = PLUS;
14559           op0 = operands[0];
14560           op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
14561         }
14562       else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
14563         {
14564           code = PLUS;
14565           op0 = operands[0];
14566           op1 = pic_offset_table_rtx;
14567         }
14568       else
14569         {
14570           code = MINUS;
14571           op0 = pic_offset_table_rtx;
14572           op1 = operands[0];
14573         }
14574
14575       operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
14576                                          OPTAB_DIRECT);
14577     }
14578 })
14579
14580 (define_insn "*tablejump_1"
14581   [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))
14582    (use (label_ref (match_operand 1 "" "")))]
14583   "!TARGET_64BIT"
14584   "jmp\t%A0"
14585   [(set_attr "type" "ibr")
14586    (set_attr "length_immediate" "0")])
14587
14588 (define_insn "*tablejump_1_rtx64"
14589   [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))
14590    (use (label_ref (match_operand 1 "" "")))]
14591   "TARGET_64BIT"
14592   "jmp\t%A0"
14593   [(set_attr "type" "ibr")
14594    (set_attr "length_immediate" "0")])
14595 \f
14596 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
14597
14598 (define_peephole2
14599   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
14600    (set (match_operand:QI 1 "register_operand" "")
14601         (match_operator:QI 2 "ix86_comparison_operator"
14602           [(reg FLAGS_REG) (const_int 0)]))
14603    (set (match_operand 3 "q_regs_operand" "")
14604         (zero_extend (match_dup 1)))]
14605   "(peep2_reg_dead_p (3, operands[1])
14606     || operands_match_p (operands[1], operands[3]))
14607    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
14608   [(set (match_dup 4) (match_dup 0))
14609    (set (strict_low_part (match_dup 5))
14610         (match_dup 2))]
14611 {
14612   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
14613   operands[5] = gen_lowpart (QImode, operands[3]);
14614   ix86_expand_clear (operands[3]);
14615 })
14616
14617 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
14618
14619 (define_peephole2
14620   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
14621    (set (match_operand:QI 1 "register_operand" "")
14622         (match_operator:QI 2 "ix86_comparison_operator"
14623           [(reg FLAGS_REG) (const_int 0)]))
14624    (parallel [(set (match_operand 3 "q_regs_operand" "")
14625                    (zero_extend (match_dup 1)))
14626               (clobber (reg:CC FLAGS_REG))])]
14627   "(peep2_reg_dead_p (3, operands[1])
14628     || operands_match_p (operands[1], operands[3]))
14629    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
14630   [(set (match_dup 4) (match_dup 0))
14631    (set (strict_low_part (match_dup 5))
14632         (match_dup 2))]
14633 {
14634   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
14635   operands[5] = gen_lowpart (QImode, operands[3]);
14636   ix86_expand_clear (operands[3]);
14637 })
14638 \f
14639 ;; Call instructions.
14640
14641 ;; The predicates normally associated with named expanders are not properly
14642 ;; checked for calls.  This is a bug in the generic code, but it isn't that
14643 ;; easy to fix.  Ignore it for now and be prepared to fix things up.
14644
14645 ;; Call subroutine returning no value.
14646
14647 (define_expand "call_pop"
14648   [(parallel [(call (match_operand:QI 0 "" "")
14649                     (match_operand:SI 1 "" ""))
14650               (set (reg:SI SP_REG)
14651                    (plus:SI (reg:SI SP_REG)
14652                             (match_operand:SI 3 "" "")))])]
14653   "!TARGET_64BIT"
14654 {
14655   ix86_expand_call (NULL, operands[0], operands[1], operands[2], operands[3], 0);
14656   DONE;
14657 })
14658
14659 (define_insn "*call_pop_0"
14660   [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" ""))
14661          (match_operand:SI 1 "" ""))
14662    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
14663                             (match_operand:SI 2 "immediate_operand" "")))]
14664   "!TARGET_64BIT"
14665 {
14666   if (SIBLING_CALL_P (insn))
14667     return "jmp\t%P0";
14668   else
14669     return "call\t%P0";
14670 }
14671   [(set_attr "type" "call")])
14672
14673 (define_insn "*call_pop_1"
14674   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
14675          (match_operand:SI 1 "" ""))
14676    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
14677                             (match_operand:SI 2 "immediate_operand" "i")))]
14678   "!TARGET_64BIT"
14679 {
14680   if (constant_call_address_operand (operands[0], Pmode))
14681     {
14682       if (SIBLING_CALL_P (insn))
14683         return "jmp\t%P0";
14684       else
14685         return "call\t%P0";
14686     }
14687   if (SIBLING_CALL_P (insn))
14688     return "jmp\t%A0";
14689   else
14690     return "call\t%A0";
14691 }
14692   [(set_attr "type" "call")])
14693
14694 (define_expand "call"
14695   [(call (match_operand:QI 0 "" "")
14696          (match_operand 1 "" ""))
14697    (use (match_operand 2 "" ""))]
14698   ""
14699 {
14700   ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 0);
14701   DONE;
14702 })
14703
14704 (define_expand "sibcall"
14705   [(call (match_operand:QI 0 "" "")
14706          (match_operand 1 "" ""))
14707    (use (match_operand 2 "" ""))]
14708   ""
14709 {
14710   ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 1);
14711   DONE;
14712 })
14713
14714 (define_insn "*call_0"
14715   [(call (mem:QI (match_operand 0 "constant_call_address_operand" ""))
14716          (match_operand 1 "" ""))]
14717   ""
14718 {
14719   if (SIBLING_CALL_P (insn))
14720     return "jmp\t%P0";
14721   else
14722     return "call\t%P0";
14723 }
14724   [(set_attr "type" "call")])
14725
14726 (define_insn "*call_1"
14727   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
14728          (match_operand 1 "" ""))]
14729   "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
14730 {
14731   if (constant_call_address_operand (operands[0], Pmode))
14732     return "call\t%P0";
14733   return "call\t%A0";
14734 }
14735   [(set_attr "type" "call")])
14736
14737 (define_insn "*sibcall_1"
14738   [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "s,c,d,a"))
14739          (match_operand 1 "" ""))]
14740   "SIBLING_CALL_P (insn) && !TARGET_64BIT"
14741 {
14742   if (constant_call_address_operand (operands[0], Pmode))
14743     return "jmp\t%P0";
14744   return "jmp\t%A0";
14745 }
14746   [(set_attr "type" "call")])
14747
14748 (define_insn "*call_1_rex64"
14749   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rsm"))
14750          (match_operand 1 "" ""))]
14751   "!SIBLING_CALL_P (insn) && TARGET_64BIT
14752    && ix86_cmodel != CM_LARGE && ix86_cmodel != CM_LARGE_PIC"
14753 {
14754   if (constant_call_address_operand (operands[0], Pmode))
14755     return "call\t%P0";
14756   return "call\t%A0";
14757 }
14758   [(set_attr "type" "call")])
14759
14760 (define_insn "*call_1_rex64_large"
14761   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rm"))
14762          (match_operand 1 "" ""))]
14763   "!SIBLING_CALL_P (insn) && TARGET_64BIT"
14764   "call\t%A0"
14765   [(set_attr "type" "call")])
14766
14767 (define_insn "*sibcall_1_rex64"
14768   [(call (mem:QI (match_operand:DI 0 "constant_call_address_operand" ""))
14769          (match_operand 1 "" ""))]
14770   "SIBLING_CALL_P (insn) && TARGET_64BIT"
14771   "jmp\t%P0"
14772   [(set_attr "type" "call")])
14773
14774 (define_insn "*sibcall_1_rex64_v"
14775   [(call (mem:QI (reg:DI R11_REG))
14776          (match_operand 0 "" ""))]
14777   "SIBLING_CALL_P (insn) && TARGET_64BIT"
14778   "jmp\t{*%%}r11"
14779   [(set_attr "type" "call")])
14780
14781
14782 ;; Call subroutine, returning value in operand 0
14783
14784 (define_expand "call_value_pop"
14785   [(parallel [(set (match_operand 0 "" "")
14786                    (call (match_operand:QI 1 "" "")
14787                          (match_operand:SI 2 "" "")))
14788               (set (reg:SI SP_REG)
14789                    (plus:SI (reg:SI SP_REG)
14790                             (match_operand:SI 4 "" "")))])]
14791   "!TARGET_64BIT"
14792 {
14793   ix86_expand_call (operands[0], operands[1], operands[2],
14794                     operands[3], operands[4], 0);
14795   DONE;
14796 })
14797
14798 (define_expand "call_value"
14799   [(set (match_operand 0 "" "")
14800         (call (match_operand:QI 1 "" "")
14801               (match_operand:SI 2 "" "")))
14802    (use (match_operand:SI 3 "" ""))]
14803   ;; Operand 2 not used on the i386.
14804   ""
14805 {
14806   ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 0);
14807   DONE;
14808 })
14809
14810 (define_expand "sibcall_value"
14811   [(set (match_operand 0 "" "")
14812         (call (match_operand:QI 1 "" "")
14813               (match_operand:SI 2 "" "")))
14814    (use (match_operand:SI 3 "" ""))]
14815   ;; Operand 2 not used on the i386.
14816   ""
14817 {
14818   ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 1);
14819   DONE;
14820 })
14821
14822 ;; Call subroutine returning any type.
14823
14824 (define_expand "untyped_call"
14825   [(parallel [(call (match_operand 0 "" "")
14826                     (const_int 0))
14827               (match_operand 1 "" "")
14828               (match_operand 2 "" "")])]
14829   ""
14830 {
14831   int i;
14832
14833   /* In order to give reg-stack an easier job in validating two
14834      coprocessor registers as containing a possible return value,
14835      simply pretend the untyped call returns a complex long double
14836      value.  */
14837
14838   ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
14839                      ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
14840                     operands[0], const0_rtx, GEN_INT (SSE_REGPARM_MAX - 1),
14841                     NULL, 0);
14842
14843   for (i = 0; i < XVECLEN (operands[2], 0); i++)
14844     {
14845       rtx set = XVECEXP (operands[2], 0, i);
14846       emit_move_insn (SET_DEST (set), SET_SRC (set));
14847     }
14848
14849   /* The optimizer does not know that the call sets the function value
14850      registers we stored in the result block.  We avoid problems by
14851      claiming that all hard registers are used and clobbered at this
14852      point.  */
14853   emit_insn (gen_blockage ());
14854
14855   DONE;
14856 })
14857 \f
14858 ;; Prologue and epilogue instructions
14859
14860 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
14861 ;; all of memory.  This blocks insns from being moved across this point.
14862
14863 (define_insn "blockage"
14864   [(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)]
14865   ""
14866   ""
14867   [(set_attr "length" "0")])
14868
14869 ;; As USE insns aren't meaningful after reload, this is used instead
14870 ;; to prevent deleting instructions setting registers for PIC code
14871 (define_insn "prologue_use"
14872   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_PROLOGUE_USE)]
14873   ""
14874   ""
14875   [(set_attr "length" "0")])
14876
14877 ;; Insn emitted into the body of a function to return from a function.
14878 ;; This is only done if the function's epilogue is known to be simple.
14879 ;; See comments for ix86_can_use_return_insn_p in i386.c.
14880
14881 (define_expand "return"
14882   [(return)]
14883   "ix86_can_use_return_insn_p ()"
14884 {
14885   if (current_function_pops_args)
14886     {
14887       rtx popc = GEN_INT (current_function_pops_args);
14888       emit_jump_insn (gen_return_pop_internal (popc));
14889       DONE;
14890     }
14891 })
14892
14893 (define_insn "return_internal"
14894   [(return)]
14895   "reload_completed"
14896   "ret"
14897   [(set_attr "length" "1")
14898    (set_attr "length_immediate" "0")
14899    (set_attr "modrm" "0")])
14900
14901 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
14902 ;; instruction Athlon and K8 have.
14903
14904 (define_insn "return_internal_long"
14905   [(return)
14906    (unspec [(const_int 0)] UNSPEC_REP)]
14907   "reload_completed"
14908   "rep\;ret"
14909   [(set_attr "length" "1")
14910    (set_attr "length_immediate" "0")
14911    (set_attr "prefix_rep" "1")
14912    (set_attr "modrm" "0")])
14913
14914 (define_insn "return_pop_internal"
14915   [(return)
14916    (use (match_operand:SI 0 "const_int_operand" ""))]
14917   "reload_completed"
14918   "ret\t%0"
14919   [(set_attr "length" "3")
14920    (set_attr "length_immediate" "2")
14921    (set_attr "modrm" "0")])
14922
14923 (define_insn "return_indirect_internal"
14924   [(return)
14925    (use (match_operand:SI 0 "register_operand" "r"))]
14926   "reload_completed"
14927   "jmp\t%A0"
14928   [(set_attr "type" "ibr")
14929    (set_attr "length_immediate" "0")])
14930
14931 (define_insn "nop"
14932   [(const_int 0)]
14933   ""
14934   "nop"
14935   [(set_attr "length" "1")
14936    (set_attr "length_immediate" "0")
14937    (set_attr "modrm" "0")])
14938
14939 ;; Align to 16-byte boundary, max skip in op0.  Used to avoid
14940 ;; branch prediction penalty for the third jump in a 16-byte
14941 ;; block on K8.
14942
14943 (define_insn "align"
14944   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
14945   ""
14946 {
14947 #ifdef ASM_OUTPUT_MAX_SKIP_ALIGN
14948   ASM_OUTPUT_MAX_SKIP_ALIGN (asm_out_file, 4, (int)INTVAL (operands[0]));
14949 #else
14950   /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
14951      The align insn is used to avoid 3 jump instructions in the row to improve
14952      branch prediction and the benefits hardly outweigh the cost of extra 8
14953      nops on the average inserted by full alignment pseudo operation.  */
14954 #endif
14955   return "";
14956 }
14957   [(set_attr "length" "16")])
14958
14959 (define_expand "prologue"
14960   [(const_int 0)]
14961   ""
14962   "ix86_expand_prologue (); DONE;")
14963
14964 (define_insn "set_got"
14965   [(set (match_operand:SI 0 "register_operand" "=r")
14966         (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
14967    (clobber (reg:CC FLAGS_REG))]
14968   "!TARGET_64BIT"
14969   { return output_set_got (operands[0], NULL_RTX); }
14970   [(set_attr "type" "multi")
14971    (set_attr "length" "12")])
14972
14973 (define_insn "set_got_labelled"
14974   [(set (match_operand:SI 0 "register_operand" "=r")
14975         (unspec:SI [(label_ref (match_operand 1 "" ""))]
14976          UNSPEC_SET_GOT))
14977    (clobber (reg:CC FLAGS_REG))]
14978   "!TARGET_64BIT"
14979   { return output_set_got (operands[0], operands[1]); }
14980   [(set_attr "type" "multi")
14981    (set_attr "length" "12")])
14982
14983 (define_insn "set_got_rex64"
14984   [(set (match_operand:DI 0 "register_operand" "=r")
14985         (unspec:DI [(const_int 0)] UNSPEC_SET_GOT))]
14986   "TARGET_64BIT"
14987   "lea{q}\t{_GLOBAL_OFFSET_TABLE_(%%rip), %0|%0, _GLOBAL_OFFSET_TABLE_[rip]}"
14988   [(set_attr "type" "lea")
14989    (set_attr "length" "6")])
14990
14991 (define_insn "set_rip_rex64"
14992   [(set (match_operand:DI 0 "register_operand" "=r")
14993         (unspec:DI [(match_operand:DI 1 "" "")] UNSPEC_SET_RIP))]
14994   "TARGET_64BIT"
14995   "lea{q}\t{%l1(%%rip), %0|%0, %l1[rip]}"
14996   [(set_attr "type" "lea")
14997    (set_attr "length" "6")])
14998
14999 (define_insn "set_got_offset_rex64"
15000   [(set (match_operand:DI 0 "register_operand" "=r")
15001         (unspec:DI [(match_operand:DI 1 "" "")] UNSPEC_SET_GOT_OFFSET))]
15002   "TARGET_64BIT"
15003   "movabs{q}\t{$_GLOBAL_OFFSET_TABLE_-%l1, %0|%0, OFFSET FLAT:_GLOBAL_OFFSET_TABLE_-%l1}"
15004   [(set_attr "type" "imov")
15005    (set_attr "length" "11")])
15006
15007 (define_expand "epilogue"
15008   [(const_int 0)]
15009   ""
15010   "ix86_expand_epilogue (1); DONE;")
15011
15012 (define_expand "sibcall_epilogue"
15013   [(const_int 0)]
15014   ""
15015   "ix86_expand_epilogue (0); DONE;")
15016
15017 (define_expand "eh_return"
15018   [(use (match_operand 0 "register_operand" ""))]
15019   ""
15020 {
15021   rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
15022
15023   /* Tricky bit: we write the address of the handler to which we will
15024      be returning into someone else's stack frame, one word below the
15025      stack address we wish to restore.  */
15026   tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
15027   tmp = plus_constant (tmp, -UNITS_PER_WORD);
15028   tmp = gen_rtx_MEM (Pmode, tmp);
15029   emit_move_insn (tmp, ra);
15030
15031   if (Pmode == SImode)
15032     emit_jump_insn (gen_eh_return_si (sa));
15033   else
15034     emit_jump_insn (gen_eh_return_di (sa));
15035   emit_barrier ();
15036   DONE;
15037 })
15038
15039 (define_insn_and_split "eh_return_si"
15040   [(set (pc)
15041         (unspec [(match_operand:SI 0 "register_operand" "c")]
15042                  UNSPEC_EH_RETURN))]
15043   "!TARGET_64BIT"
15044   "#"
15045   "reload_completed"
15046   [(const_int 0)]
15047   "ix86_expand_epilogue (2); DONE;")
15048
15049 (define_insn_and_split "eh_return_di"
15050   [(set (pc)
15051         (unspec [(match_operand:DI 0 "register_operand" "c")]
15052                  UNSPEC_EH_RETURN))]
15053   "TARGET_64BIT"
15054   "#"
15055   "reload_completed"
15056   [(const_int 0)]
15057   "ix86_expand_epilogue (2); DONE;")
15058
15059 (define_insn "leave"
15060   [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4)))
15061    (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG)))
15062    (clobber (mem:BLK (scratch)))]
15063   "!TARGET_64BIT"
15064   "leave"
15065   [(set_attr "type" "leave")])
15066
15067 (define_insn "leave_rex64"
15068   [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8)))
15069    (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG)))
15070    (clobber (mem:BLK (scratch)))]
15071   "TARGET_64BIT"
15072   "leave"
15073   [(set_attr "type" "leave")])
15074 \f
15075 (define_expand "ffssi2"
15076   [(parallel
15077      [(set (match_operand:SI 0 "register_operand" "")
15078            (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "")))
15079       (clobber (match_scratch:SI 2 ""))
15080       (clobber (reg:CC FLAGS_REG))])]
15081   ""
15082 {
15083   if (TARGET_CMOVE)
15084     {
15085       emit_insn (gen_ffs_cmove (operands[0], operands[1]));
15086       DONE;
15087     }
15088 })
15089
15090 (define_expand "ffs_cmove"
15091   [(set (match_dup 2) (const_int -1))
15092    (parallel [(set (reg:CCZ FLAGS_REG)
15093                    (compare:CCZ (match_operand:SI 1 "register_operand" "")
15094                                 (const_int 0)))
15095               (set (match_operand:SI 0 "nonimmediate_operand" "")
15096                    (ctz:SI (match_dup 1)))])
15097    (set (match_dup 0) (if_then_else:SI
15098                         (eq (reg:CCZ FLAGS_REG) (const_int 0))
15099                         (match_dup 2)
15100                         (match_dup 0)))
15101    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
15102               (clobber (reg:CC FLAGS_REG))])]
15103   "TARGET_CMOVE"
15104   "operands[2] = gen_reg_rtx (SImode);")
15105
15106 (define_insn_and_split "*ffs_no_cmove"
15107   [(set (match_operand:SI 0 "nonimmediate_operand" "=r")
15108         (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
15109    (clobber (match_scratch:SI 2 "=&q"))
15110    (clobber (reg:CC FLAGS_REG))]
15111   "!TARGET_CMOVE"
15112   "#"
15113   "&& reload_completed"
15114   [(parallel [(set (reg:CCZ FLAGS_REG)
15115                    (compare:CCZ (match_dup 1) (const_int 0)))
15116               (set (match_dup 0) (ctz:SI (match_dup 1)))])
15117    (set (strict_low_part (match_dup 3))
15118         (eq:QI (reg:CCZ FLAGS_REG) (const_int 0)))
15119    (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
15120               (clobber (reg:CC FLAGS_REG))])
15121    (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
15122               (clobber (reg:CC FLAGS_REG))])
15123    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
15124               (clobber (reg:CC FLAGS_REG))])]
15125 {
15126   operands[3] = gen_lowpart (QImode, operands[2]);
15127   ix86_expand_clear (operands[2]);
15128 })
15129
15130 (define_insn "*ffssi_1"
15131   [(set (reg:CCZ FLAGS_REG)
15132         (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "rm")
15133                      (const_int 0)))
15134    (set (match_operand:SI 0 "register_operand" "=r")
15135         (ctz:SI (match_dup 1)))]
15136   ""
15137   "bsf{l}\t{%1, %0|%0, %1}"
15138   [(set_attr "prefix_0f" "1")])
15139
15140 (define_expand "ffsdi2"
15141   [(set (match_dup 2) (const_int -1))
15142    (parallel [(set (reg:CCZ FLAGS_REG)
15143                    (compare:CCZ (match_operand:DI 1 "register_operand" "")
15144                                 (const_int 0)))
15145               (set (match_operand:DI 0 "nonimmediate_operand" "")
15146                    (ctz:DI (match_dup 1)))])
15147    (set (match_dup 0) (if_then_else:DI
15148                         (eq (reg:CCZ FLAGS_REG) (const_int 0))
15149                         (match_dup 2)
15150                         (match_dup 0)))
15151    (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (const_int 1)))
15152               (clobber (reg:CC FLAGS_REG))])]
15153   "TARGET_64BIT"
15154   "operands[2] = gen_reg_rtx (DImode);")
15155
15156 (define_insn "*ffsdi_1"
15157   [(set (reg:CCZ FLAGS_REG)
15158         (compare:CCZ (match_operand:DI 1 "nonimmediate_operand" "rm")
15159                      (const_int 0)))
15160    (set (match_operand:DI 0 "register_operand" "=r")
15161         (ctz:DI (match_dup 1)))]
15162   "TARGET_64BIT"
15163   "bsf{q}\t{%1, %0|%0, %1}"
15164   [(set_attr "prefix_0f" "1")])
15165
15166 (define_insn "ctzsi2"
15167   [(set (match_operand:SI 0 "register_operand" "=r")
15168         (ctz:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
15169    (clobber (reg:CC FLAGS_REG))]
15170   ""
15171   "bsf{l}\t{%1, %0|%0, %1}"
15172   [(set_attr "prefix_0f" "1")])
15173
15174 (define_insn "ctzdi2"
15175   [(set (match_operand:DI 0 "register_operand" "=r")
15176         (ctz:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
15177    (clobber (reg:CC FLAGS_REG))]
15178   "TARGET_64BIT"
15179   "bsf{q}\t{%1, %0|%0, %1}"
15180   [(set_attr "prefix_0f" "1")])
15181
15182 (define_expand "clzsi2"
15183   [(parallel
15184      [(set (match_operand:SI 0 "register_operand" "")
15185            (minus:SI (const_int 31)
15186                      (clz:SI (match_operand:SI 1 "nonimmediate_operand" ""))))
15187       (clobber (reg:CC FLAGS_REG))])
15188    (parallel
15189      [(set (match_dup 0) (xor:SI (match_dup 0) (const_int 31)))
15190       (clobber (reg:CC FLAGS_REG))])]
15191   ""
15192 {
15193   if (TARGET_ABM)
15194     {
15195       emit_insn (gen_clzsi2_abm (operands[0], operands[1]));
15196       DONE;
15197     }
15198 })
15199
15200 (define_insn "clzsi2_abm"
15201   [(set (match_operand:SI 0 "register_operand" "=r")
15202         (clz:SI (match_operand:SI 1 "nonimmediate_operand" "")))
15203    (clobber (reg:CC FLAGS_REG))]
15204   "TARGET_ABM"
15205   "lzcnt{l}\t{%1, %0|%0, %1}"
15206   [(set_attr "prefix_rep" "1")
15207    (set_attr "type" "bitmanip")
15208    (set_attr "mode" "SI")])
15209
15210 (define_insn "*bsr"
15211   [(set (match_operand:SI 0 "register_operand" "=r")
15212         (minus:SI (const_int 31)
15213                   (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
15214    (clobber (reg:CC FLAGS_REG))]
15215   ""
15216   "bsr{l}\t{%1, %0|%0, %1}"
15217   [(set_attr "prefix_0f" "1")
15218    (set_attr "mode" "SI")])
15219
15220 (define_insn "popcountsi2"
15221   [(set (match_operand:SI 0 "register_operand" "=r")
15222         (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "")))
15223    (clobber (reg:CC FLAGS_REG))]
15224   "TARGET_POPCNT"
15225   "popcnt{l}\t{%1, %0|%0, %1}"
15226   [(set_attr "prefix_rep" "1")
15227    (set_attr "type" "bitmanip")
15228    (set_attr "mode" "SI")])
15229
15230 (define_insn "*popcountsi2_cmp"
15231   [(set (reg FLAGS_REG)
15232         (compare
15233           (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))
15234           (const_int 0)))
15235    (set (match_operand:SI 0 "register_operand" "=r")
15236         (popcount:SI (match_dup 1)))]
15237   "TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
15238   "popcnt{l}\t{%1, %0|%0, %1}"
15239   [(set_attr "prefix_rep" "1")
15240    (set_attr "type" "bitmanip")
15241    (set_attr "mode" "SI")])
15242
15243 (define_insn "*popcountsi2_cmp_zext"
15244   [(set (reg FLAGS_REG)
15245         (compare
15246           (popcount:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))
15247           (const_int 0)))
15248    (set (match_operand:DI 0 "register_operand" "=r")
15249         (zero_extend:DI(popcount:SI (match_dup 1))))]
15250   "TARGET_64BIT && TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
15251   "popcnt{l}\t{%1, %0|%0, %1}"
15252   [(set_attr "prefix_rep" "1")
15253    (set_attr "type" "bitmanip")
15254    (set_attr "mode" "SI")])
15255
15256 (define_expand "bswapsi2"
15257   [(set (match_operand:SI 0 "register_operand" "")
15258         (bswap:SI (match_operand:SI 1 "register_operand" "")))]
15259   ""
15260 {
15261   if (!TARGET_BSWAP)
15262     {
15263       rtx x = operands[0];
15264
15265       emit_move_insn (x, operands[1]);
15266       emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
15267       emit_insn (gen_rotlsi3 (x, x, GEN_INT (16)));
15268       emit_insn (gen_bswaphi_lowpart (gen_lowpart (HImode, x)));
15269       DONE;
15270     }
15271 })
15272
15273 (define_insn "*bswapsi_1"
15274   [(set (match_operand:SI 0 "register_operand" "=r")
15275         (bswap:SI (match_operand:SI 1 "register_operand" "0")))]
15276   "TARGET_BSWAP"
15277   "bswap\t%0"
15278   [(set_attr "prefix_0f" "1")
15279    (set_attr "length" "2")])
15280
15281 (define_insn "*bswaphi_lowpart_1"
15282   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+Q,r"))
15283         (bswap:HI (match_dup 0)))
15284    (clobber (reg:CC FLAGS_REG))]
15285   "TARGET_USE_XCHGB || optimize_size"
15286   "@
15287     xchg{b}\t{%h0, %b0|%b0, %h0}
15288     rol{w}\t{$8, %0|%0, 8}"
15289   [(set_attr "length" "2,4")
15290    (set_attr "mode" "QI,HI")])
15291
15292 (define_insn "bswaphi_lowpart"
15293   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
15294         (bswap:HI (match_dup 0)))
15295    (clobber (reg:CC FLAGS_REG))]
15296   ""
15297   "rol{w}\t{$8, %0|%0, 8}"
15298   [(set_attr "length" "4")
15299    (set_attr "mode" "HI")])
15300
15301 (define_insn "bswapdi2"
15302   [(set (match_operand:DI 0 "register_operand" "=r")
15303         (bswap:DI (match_operand:DI 1 "register_operand" "0")))]
15304   "TARGET_64BIT"
15305   "bswap\t%0"
15306   [(set_attr "prefix_0f" "1")
15307    (set_attr "length" "3")])
15308
15309 (define_expand "clzdi2"
15310   [(parallel
15311      [(set (match_operand:DI 0 "register_operand" "")
15312            (minus:DI (const_int 63)
15313                      (clz:DI (match_operand:DI 1 "nonimmediate_operand" ""))))
15314       (clobber (reg:CC FLAGS_REG))])
15315    (parallel
15316      [(set (match_dup 0) (xor:DI (match_dup 0) (const_int 63)))
15317       (clobber (reg:CC FLAGS_REG))])]
15318   "TARGET_64BIT"
15319 {
15320   if (TARGET_ABM)
15321     {
15322       emit_insn (gen_clzdi2_abm (operands[0], operands[1]));
15323       DONE;
15324     }
15325 })
15326
15327 (define_insn "clzdi2_abm"
15328   [(set (match_operand:DI 0 "register_operand" "=r")
15329         (clz:DI (match_operand:DI 1 "nonimmediate_operand" "")))
15330    (clobber (reg:CC FLAGS_REG))]
15331   "TARGET_64BIT && TARGET_ABM"
15332   "lzcnt{q}\t{%1, %0|%0, %1}"
15333   [(set_attr "prefix_rep" "1")
15334    (set_attr "type" "bitmanip")
15335    (set_attr "mode" "DI")])
15336
15337 (define_insn "*bsr_rex64"
15338   [(set (match_operand:DI 0 "register_operand" "=r")
15339         (minus:DI (const_int 63)
15340                   (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))))
15341    (clobber (reg:CC FLAGS_REG))]
15342   "TARGET_64BIT"
15343   "bsr{q}\t{%1, %0|%0, %1}"
15344   [(set_attr "prefix_0f" "1")
15345    (set_attr "mode" "DI")])
15346
15347 (define_insn "popcountdi2"
15348   [(set (match_operand:DI 0 "register_operand" "=r")
15349         (popcount:DI (match_operand:DI 1 "nonimmediate_operand" "")))
15350    (clobber (reg:CC FLAGS_REG))]
15351   "TARGET_64BIT && TARGET_POPCNT"
15352   "popcnt{q}\t{%1, %0|%0, %1}"
15353   [(set_attr "prefix_rep" "1")
15354    (set_attr "type" "bitmanip")
15355    (set_attr "mode" "DI")])
15356
15357 (define_insn "*popcountdi2_cmp"
15358   [(set (reg FLAGS_REG)
15359         (compare
15360           (popcount:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))
15361           (const_int 0)))
15362    (set (match_operand:DI 0 "register_operand" "=r")
15363         (popcount:DI (match_dup 1)))]
15364   "TARGET_64BIT && TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
15365   "popcnt{q}\t{%1, %0|%0, %1}"
15366   [(set_attr "prefix_rep" "1")
15367    (set_attr "type" "bitmanip")
15368    (set_attr "mode" "DI")])
15369
15370 (define_expand "clzhi2"
15371   [(parallel
15372      [(set (match_operand:HI 0 "register_operand" "")
15373            (minus:HI (const_int 15)
15374                      (clz:HI (match_operand:HI 1 "nonimmediate_operand" ""))))
15375       (clobber (reg:CC FLAGS_REG))])
15376    (parallel
15377      [(set (match_dup 0) (xor:HI (match_dup 0) (const_int 15)))
15378       (clobber (reg:CC FLAGS_REG))])]
15379   ""
15380 {
15381   if (TARGET_ABM)
15382     {
15383       emit_insn (gen_clzhi2_abm (operands[0], operands[1]));
15384       DONE;
15385     }
15386 })
15387
15388 (define_insn "clzhi2_abm"
15389   [(set (match_operand:HI 0 "register_operand" "=r")
15390         (clz:HI (match_operand:HI 1 "nonimmediate_operand" "")))
15391    (clobber (reg:CC FLAGS_REG))]
15392   "TARGET_ABM"
15393   "lzcnt{w}\t{%1, %0|%0, %1}"
15394   [(set_attr "prefix_rep" "1")
15395    (set_attr "type" "bitmanip")
15396    (set_attr "mode" "HI")])
15397
15398 (define_insn "*bsrhi"
15399   [(set (match_operand:HI 0 "register_operand" "=r")
15400         (minus:HI (const_int 15)
15401                   (clz:HI (match_operand:HI 1 "nonimmediate_operand" "rm"))))
15402    (clobber (reg:CC FLAGS_REG))]
15403   ""
15404   "bsr{w}\t{%1, %0|%0, %1}"
15405   [(set_attr "prefix_0f" "1")
15406    (set_attr "mode" "HI")])
15407
15408 (define_insn "popcounthi2"
15409   [(set (match_operand:HI 0 "register_operand" "=r")
15410         (popcount:HI (match_operand:HI 1 "nonimmediate_operand" "")))
15411    (clobber (reg:CC FLAGS_REG))]
15412   "TARGET_POPCNT"
15413   "popcnt{w}\t{%1, %0|%0, %1}"
15414   [(set_attr "prefix_rep" "1")
15415    (set_attr "type" "bitmanip")
15416    (set_attr "mode" "HI")])
15417
15418 (define_insn "*popcounthi2_cmp"
15419   [(set (reg FLAGS_REG)
15420         (compare
15421           (popcount:HI (match_operand:HI 1 "nonimmediate_operand" "rm"))
15422           (const_int 0)))
15423    (set (match_operand:HI 0 "register_operand" "=r")
15424         (popcount:HI (match_dup 1)))]
15425   "TARGET_POPCNT && ix86_match_ccmode (insn, CCZmode)"
15426   "popcnt{w}\t{%1, %0|%0, %1}"
15427   [(set_attr "prefix_rep" "1")
15428    (set_attr "type" "bitmanip")
15429    (set_attr "mode" "HI")])
15430
15431 (define_expand "paritydi2"
15432   [(set (match_operand:DI 0 "register_operand" "")
15433         (parity:DI (match_operand:DI 1 "nonimmediate_operand" "")))]
15434   "! TARGET_POPCNT"
15435 {
15436   rtx scratch = gen_reg_rtx (QImode);
15437   rtx cond;
15438
15439   emit_insn (gen_paritydi2_cmp (NULL_RTX, NULL_RTX,
15440                                 NULL_RTX, operands[1]));
15441
15442   cond = gen_rtx_fmt_ee (ORDERED, QImode,
15443                          gen_rtx_REG (CCmode, FLAGS_REG),
15444                          const0_rtx);
15445   emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
15446
15447   if (TARGET_64BIT)
15448     emit_insn (gen_zero_extendqidi2 (operands[0], scratch));
15449   else
15450     {
15451       rtx tmp = gen_reg_rtx (SImode);
15452
15453       emit_insn (gen_zero_extendqisi2 (tmp, scratch));
15454       emit_insn (gen_zero_extendsidi2 (operands[0], tmp));
15455     }
15456   DONE;
15457 })
15458
15459 (define_insn_and_split "paritydi2_cmp"
15460   [(set (reg:CC FLAGS_REG)
15461         (parity:CC (match_operand:DI 3 "nonimmediate_operand" "0,m")))
15462    (clobber (match_scratch:DI 0 "=r,X"))
15463    (clobber (match_scratch:SI 1 "=r,r"))
15464    (clobber (match_scratch:HI 2 "=Q,Q"))]
15465   "! TARGET_POPCNT"
15466   "#"
15467   "&& reload_completed"
15468   [(parallel
15469      [(set (match_dup 1)
15470            (xor:SI (match_dup 1) (match_dup 4)))
15471       (clobber (reg:CC FLAGS_REG))])
15472    (parallel
15473      [(set (reg:CC FLAGS_REG)
15474            (parity:CC (match_dup 1)))
15475       (clobber (match_dup 1))
15476       (clobber (match_dup 2))])]
15477 {
15478   operands[4] = gen_lowpart (SImode, operands[3]);
15479
15480   if (MEM_P (operands[3]))
15481     emit_move_insn (operands[1], gen_highpart (SImode, operands[3]));
15482   else if (! TARGET_64BIT)
15483     operands[1] = gen_highpart (SImode, operands[3]);
15484   else
15485     {
15486       emit_move_insn (operands[1], gen_lowpart (SImode, operands[3]));
15487       emit_insn (gen_lshrdi3 (operands[3], operands[3], GEN_INT (32)));
15488     }
15489 })
15490
15491 (define_expand "paritysi2"
15492   [(set (match_operand:SI 0 "register_operand" "")
15493         (parity:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
15494   "! TARGET_POPCNT"
15495 {
15496   rtx scratch = gen_reg_rtx (QImode);
15497   rtx cond;
15498
15499   emit_insn (gen_paritysi2_cmp (NULL_RTX, NULL_RTX, operands[1]));
15500
15501   cond = gen_rtx_fmt_ee (ORDERED, QImode,
15502                          gen_rtx_REG (CCmode, FLAGS_REG),
15503                          const0_rtx);
15504   emit_insn (gen_rtx_SET (VOIDmode, scratch, cond));
15505
15506   emit_insn (gen_zero_extendqisi2 (operands[0], scratch));
15507   DONE;
15508 })
15509
15510 (define_insn_and_split "paritysi2_cmp"
15511   [(set (reg:CC FLAGS_REG)
15512         (parity:CC (match_operand:SI 2 "nonimmediate_operand" "0,m")))
15513    (clobber (match_scratch:SI 0 "=r,X"))
15514    (clobber (match_scratch:HI 1 "=Q,Q"))]
15515   "! TARGET_POPCNT"
15516   "#"
15517   "&& reload_completed"
15518   [(parallel
15519      [(set (match_dup 1)
15520            (xor:HI (match_dup 1) (match_dup 3)))
15521       (clobber (reg:CC FLAGS_REG))])
15522    (parallel
15523      [(set (reg:CC FLAGS_REG)
15524            (parity:CC (match_dup 1)))
15525       (clobber (match_dup 1))])]
15526 {
15527   operands[3] = gen_lowpart (HImode, operands[2]);
15528
15529   if (MEM_P (operands[2]))
15530     emit_move_insn (operands[1], gen_highpart (HImode, operands[2]));
15531   else
15532     {
15533       emit_move_insn (operands[1], gen_lowpart (HImode, operands[2]));
15534       emit_insn (gen_lshrsi3 (operands[2], operands[2], GEN_INT (16)));
15535     }
15536 })
15537
15538 (define_insn "*parityhi2_cmp"
15539   [(set (reg:CC FLAGS_REG)
15540         (parity:CC (match_operand:HI 1 "register_operand" "0")))
15541    (clobber (match_scratch:HI 0 "=Q"))]
15542   "! TARGET_POPCNT"
15543   "xor{b}\t{%h0, %b0|%b0, %h0}"
15544   [(set_attr "length" "2")
15545    (set_attr "mode" "HI")])
15546
15547 (define_insn "*parityqi2_cmp"
15548   [(set (reg:CC FLAGS_REG)
15549         (parity:CC (match_operand:QI 0 "register_operand" "q")))]
15550   "! TARGET_POPCNT"
15551   "test{b}\t%0, %0"
15552   [(set_attr "length" "2")
15553    (set_attr "mode" "QI")])
15554 \f
15555 ;; Thread-local storage patterns for ELF.
15556 ;;
15557 ;; Note that these code sequences must appear exactly as shown
15558 ;; in order to allow linker relaxation.
15559
15560 (define_insn "*tls_global_dynamic_32_gnu"
15561   [(set (match_operand:SI 0 "register_operand" "=a")
15562         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
15563                     (match_operand:SI 2 "tls_symbolic_operand" "")
15564                     (match_operand:SI 3 "call_insn_operand" "")]
15565                     UNSPEC_TLS_GD))
15566    (clobber (match_scratch:SI 4 "=d"))
15567    (clobber (match_scratch:SI 5 "=c"))
15568    (clobber (reg:CC FLAGS_REG))]
15569   "!TARGET_64BIT && TARGET_GNU_TLS"
15570   "lea{l}\t{%a2@TLSGD(,%1,1), %0|%0, %a2@TLSGD[%1*1]}\;call\t%P3"
15571   [(set_attr "type" "multi")
15572    (set_attr "length" "12")])
15573
15574 (define_insn "*tls_global_dynamic_32_sun"
15575   [(set (match_operand:SI 0 "register_operand" "=a")
15576         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
15577                     (match_operand:SI 2 "tls_symbolic_operand" "")
15578                     (match_operand:SI 3 "call_insn_operand" "")]
15579                     UNSPEC_TLS_GD))
15580    (clobber (match_scratch:SI 4 "=d"))
15581    (clobber (match_scratch:SI 5 "=c"))
15582    (clobber (reg:CC FLAGS_REG))]
15583   "!TARGET_64BIT && TARGET_SUN_TLS"
15584   "lea{l}\t{%a2@DTLNDX(%1), %4|%4, %a2@DTLNDX[%1]}
15585         push{l}\t%4\;call\t%a2@TLSPLT\;pop{l}\t%4\;nop"
15586   [(set_attr "type" "multi")
15587    (set_attr "length" "14")])
15588
15589 (define_expand "tls_global_dynamic_32"
15590   [(parallel [(set (match_operand:SI 0 "register_operand" "")
15591                    (unspec:SI
15592                     [(match_dup 2)
15593                      (match_operand:SI 1 "tls_symbolic_operand" "")
15594                      (match_dup 3)]
15595                     UNSPEC_TLS_GD))
15596               (clobber (match_scratch:SI 4 ""))
15597               (clobber (match_scratch:SI 5 ""))
15598               (clobber (reg:CC FLAGS_REG))])]
15599   ""
15600 {
15601   if (flag_pic)
15602     operands[2] = pic_offset_table_rtx;
15603   else
15604     {
15605       operands[2] = gen_reg_rtx (Pmode);
15606       emit_insn (gen_set_got (operands[2]));
15607     }
15608   if (TARGET_GNU2_TLS)
15609     {
15610        emit_insn (gen_tls_dynamic_gnu2_32
15611                   (operands[0], operands[1], operands[2]));
15612        DONE;
15613     }
15614   operands[3] = ix86_tls_get_addr ();
15615 })
15616
15617 (define_insn "*tls_global_dynamic_64"
15618   [(set (match_operand:DI 0 "register_operand" "=a")
15619         (call:DI (mem:QI (match_operand:DI 2 "call_insn_operand" ""))
15620                  (match_operand:DI 3 "" "")))
15621    (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
15622               UNSPEC_TLS_GD)]
15623   "TARGET_64BIT"
15624   ".byte\t0x66\;lea{q}\t{%a1@TLSGD(%%rip), %%rdi|rdi, %a1@TLSGD[rip]}\;.word\t0x6666\;rex64\;call\t%P2"
15625   [(set_attr "type" "multi")
15626    (set_attr "length" "16")])
15627
15628 (define_expand "tls_global_dynamic_64"
15629   [(parallel [(set (match_operand:DI 0 "register_operand" "")
15630                    (call:DI (mem:QI (match_dup 2)) (const_int 0)))
15631               (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
15632                          UNSPEC_TLS_GD)])]
15633   ""
15634 {
15635   if (TARGET_GNU2_TLS)
15636     {
15637        emit_insn (gen_tls_dynamic_gnu2_64
15638                   (operands[0], operands[1]));
15639        DONE;
15640     }
15641   operands[2] = ix86_tls_get_addr ();
15642 })
15643
15644 (define_insn "*tls_local_dynamic_base_32_gnu"
15645   [(set (match_operand:SI 0 "register_operand" "=a")
15646         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
15647                     (match_operand:SI 2 "call_insn_operand" "")]
15648                    UNSPEC_TLS_LD_BASE))
15649    (clobber (match_scratch:SI 3 "=d"))
15650    (clobber (match_scratch:SI 4 "=c"))
15651    (clobber (reg:CC FLAGS_REG))]
15652   "!TARGET_64BIT && TARGET_GNU_TLS"
15653   "lea{l}\t{%&@TLSLDM(%1), %0|%0, %&@TLSLDM[%1]}\;call\t%P2"
15654   [(set_attr "type" "multi")
15655    (set_attr "length" "11")])
15656
15657 (define_insn "*tls_local_dynamic_base_32_sun"
15658   [(set (match_operand:SI 0 "register_operand" "=a")
15659         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
15660                     (match_operand:SI 2 "call_insn_operand" "")]
15661                    UNSPEC_TLS_LD_BASE))
15662    (clobber (match_scratch:SI 3 "=d"))
15663    (clobber (match_scratch:SI 4 "=c"))
15664    (clobber (reg:CC FLAGS_REG))]
15665   "!TARGET_64BIT && TARGET_SUN_TLS"
15666   "lea{l}\t{%&@TMDNX(%1), %3|%3, %&@TMDNX[%1]}
15667         push{l}\t%3\;call\t%&@TLSPLT\;pop{l}\t%3"
15668   [(set_attr "type" "multi")
15669    (set_attr "length" "13")])
15670
15671 (define_expand "tls_local_dynamic_base_32"
15672   [(parallel [(set (match_operand:SI 0 "register_operand" "")
15673                    (unspec:SI [(match_dup 1) (match_dup 2)]
15674                               UNSPEC_TLS_LD_BASE))
15675               (clobber (match_scratch:SI 3 ""))
15676               (clobber (match_scratch:SI 4 ""))
15677               (clobber (reg:CC FLAGS_REG))])]
15678   ""
15679 {
15680   if (flag_pic)
15681     operands[1] = pic_offset_table_rtx;
15682   else
15683     {
15684       operands[1] = gen_reg_rtx (Pmode);
15685       emit_insn (gen_set_got (operands[1]));
15686     }
15687   if (TARGET_GNU2_TLS)
15688     {
15689        emit_insn (gen_tls_dynamic_gnu2_32
15690                   (operands[0], ix86_tls_module_base (), operands[1]));
15691        DONE;
15692     }
15693   operands[2] = ix86_tls_get_addr ();
15694 })
15695
15696 (define_insn "*tls_local_dynamic_base_64"
15697   [(set (match_operand:DI 0 "register_operand" "=a")
15698         (call:DI (mem:QI (match_operand:DI 1 "call_insn_operand" ""))
15699                  (match_operand:DI 2 "" "")))
15700    (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
15701   "TARGET_64BIT"
15702   "lea{q}\t{%&@TLSLD(%%rip), %%rdi|rdi, %&@TLSLD[rip]}\;call\t%P1"
15703   [(set_attr "type" "multi")
15704    (set_attr "length" "12")])
15705
15706 (define_expand "tls_local_dynamic_base_64"
15707   [(parallel [(set (match_operand:DI 0 "register_operand" "")
15708                    (call:DI (mem:QI (match_dup 1)) (const_int 0)))
15709               (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])]
15710   ""
15711 {
15712   if (TARGET_GNU2_TLS)
15713     {
15714        emit_insn (gen_tls_dynamic_gnu2_64
15715                   (operands[0], ix86_tls_module_base ()));
15716        DONE;
15717     }
15718   operands[1] = ix86_tls_get_addr ();
15719 })
15720
15721 ;; Local dynamic of a single variable is a lose.  Show combine how
15722 ;; to convert that back to global dynamic.
15723
15724 (define_insn_and_split "*tls_local_dynamic_32_once"
15725   [(set (match_operand:SI 0 "register_operand" "=a")
15726         (plus:SI (unspec:SI [(match_operand:SI 1 "register_operand" "b")
15727                              (match_operand:SI 2 "call_insn_operand" "")]
15728                             UNSPEC_TLS_LD_BASE)
15729                  (const:SI (unspec:SI
15730                             [(match_operand:SI 3 "tls_symbolic_operand" "")]
15731                             UNSPEC_DTPOFF))))
15732    (clobber (match_scratch:SI 4 "=d"))
15733    (clobber (match_scratch:SI 5 "=c"))
15734    (clobber (reg:CC FLAGS_REG))]
15735   ""
15736   "#"
15737   ""
15738   [(parallel [(set (match_dup 0)
15739                    (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
15740                               UNSPEC_TLS_GD))
15741               (clobber (match_dup 4))
15742               (clobber (match_dup 5))
15743               (clobber (reg:CC FLAGS_REG))])]
15744   "")
15745
15746 ;; Load and add the thread base pointer from %gs:0.
15747
15748 (define_insn "*load_tp_si"
15749   [(set (match_operand:SI 0 "register_operand" "=r")
15750         (unspec:SI [(const_int 0)] UNSPEC_TP))]
15751   "!TARGET_64BIT"
15752   "mov{l}\t{%%gs:0, %0|%0, DWORD PTR gs:0}"
15753   [(set_attr "type" "imov")
15754    (set_attr "modrm" "0")
15755    (set_attr "length" "7")
15756    (set_attr "memory" "load")
15757    (set_attr "imm_disp" "false")])
15758
15759 (define_insn "*add_tp_si"
15760   [(set (match_operand:SI 0 "register_operand" "=r")
15761         (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
15762                  (match_operand:SI 1 "register_operand" "0")))
15763    (clobber (reg:CC FLAGS_REG))]
15764   "!TARGET_64BIT"
15765   "add{l}\t{%%gs:0, %0|%0, DWORD PTR gs:0}"
15766   [(set_attr "type" "alu")
15767    (set_attr "modrm" "0")
15768    (set_attr "length" "7")
15769    (set_attr "memory" "load")
15770    (set_attr "imm_disp" "false")])
15771
15772 (define_insn "*load_tp_di"
15773   [(set (match_operand:DI 0 "register_operand" "=r")
15774         (unspec:DI [(const_int 0)] UNSPEC_TP))]
15775   "TARGET_64BIT"
15776   "mov{q}\t{%%fs:0, %0|%0, QWORD PTR fs:0}"
15777   [(set_attr "type" "imov")
15778    (set_attr "modrm" "0")
15779    (set_attr "length" "7")
15780    (set_attr "memory" "load")
15781    (set_attr "imm_disp" "false")])
15782
15783 (define_insn "*add_tp_di"
15784   [(set (match_operand:DI 0 "register_operand" "=r")
15785         (plus:DI (unspec:DI [(const_int 0)] UNSPEC_TP)
15786                  (match_operand:DI 1 "register_operand" "0")))
15787    (clobber (reg:CC FLAGS_REG))]
15788   "TARGET_64BIT"
15789   "add{q}\t{%%fs:0, %0|%0, QWORD PTR fs:0}"
15790   [(set_attr "type" "alu")
15791    (set_attr "modrm" "0")
15792    (set_attr "length" "7")
15793    (set_attr "memory" "load")
15794    (set_attr "imm_disp" "false")])
15795
15796 ;; GNU2 TLS patterns can be split.
15797
15798 (define_expand "tls_dynamic_gnu2_32"
15799   [(set (match_dup 3)
15800         (plus:SI (match_operand:SI 2 "register_operand" "")
15801                  (const:SI
15802                   (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")]
15803                              UNSPEC_TLSDESC))))
15804    (parallel
15805     [(set (match_operand:SI 0 "register_operand" "")
15806           (unspec:SI [(match_dup 1) (match_dup 3)
15807                       (match_dup 2) (reg:SI SP_REG)]
15808                       UNSPEC_TLSDESC))
15809      (clobber (reg:CC FLAGS_REG))])]
15810   "!TARGET_64BIT && TARGET_GNU2_TLS"
15811 {
15812   operands[3] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
15813   ix86_tls_descriptor_calls_expanded_in_cfun = true;
15814 })
15815
15816 (define_insn "*tls_dynamic_lea_32"
15817   [(set (match_operand:SI 0 "register_operand" "=r")
15818         (plus:SI (match_operand:SI 1 "register_operand" "b")
15819                  (const:SI
15820                   (unspec:SI [(match_operand:SI 2 "tls_symbolic_operand" "")]
15821                               UNSPEC_TLSDESC))))]
15822   "!TARGET_64BIT && TARGET_GNU2_TLS"
15823   "lea{l}\t{%a2@TLSDESC(%1), %0|%0, %a2@TLSDESC[%1]}"
15824   [(set_attr "type" "lea")
15825    (set_attr "mode" "SI")
15826    (set_attr "length" "6")
15827    (set_attr "length_address" "4")])
15828
15829 (define_insn "*tls_dynamic_call_32"
15830   [(set (match_operand:SI 0 "register_operand" "=a")
15831         (unspec:SI [(match_operand:SI 1 "tls_symbolic_operand" "")
15832                     (match_operand:SI 2 "register_operand" "0")
15833                     ;; we have to make sure %ebx still points to the GOT
15834                     (match_operand:SI 3 "register_operand" "b")
15835                     (reg:SI SP_REG)]
15836                    UNSPEC_TLSDESC))
15837    (clobber (reg:CC FLAGS_REG))]
15838   "!TARGET_64BIT && TARGET_GNU2_TLS"
15839   "call\t{*%a1@TLSCALL(%2)|[DWORD PTR [%2+%a1@TLSCALL]]}"
15840   [(set_attr "type" "call")
15841    (set_attr "length" "2")
15842    (set_attr "length_address" "0")])
15843
15844 (define_insn_and_split "*tls_dynamic_gnu2_combine_32"
15845   [(set (match_operand:SI 0 "register_operand" "=&a")
15846         (plus:SI
15847          (unspec:SI [(match_operand:SI 3 "tls_modbase_operand" "")
15848                      (match_operand:SI 4 "" "")
15849                      (match_operand:SI 2 "register_operand" "b")
15850                      (reg:SI SP_REG)]
15851                     UNSPEC_TLSDESC)
15852          (const:SI (unspec:SI
15853                     [(match_operand:SI 1 "tls_symbolic_operand" "")]
15854                     UNSPEC_DTPOFF))))
15855    (clobber (reg:CC FLAGS_REG))]
15856   "!TARGET_64BIT && TARGET_GNU2_TLS"
15857   "#"
15858   ""
15859   [(set (match_dup 0) (match_dup 5))]
15860 {
15861   operands[5] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
15862   emit_insn (gen_tls_dynamic_gnu2_32 (operands[5], operands[1], operands[2]));
15863 })
15864
15865 (define_expand "tls_dynamic_gnu2_64"
15866   [(set (match_dup 2)
15867         (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
15868                    UNSPEC_TLSDESC))
15869    (parallel
15870     [(set (match_operand:DI 0 "register_operand" "")
15871           (unspec:DI [(match_dup 1) (match_dup 2) (reg:DI SP_REG)]
15872                      UNSPEC_TLSDESC))
15873      (clobber (reg:CC FLAGS_REG))])]
15874   "TARGET_64BIT && TARGET_GNU2_TLS"
15875 {
15876   operands[2] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
15877   ix86_tls_descriptor_calls_expanded_in_cfun = true;
15878 })
15879
15880 (define_insn "*tls_dynamic_lea_64"
15881   [(set (match_operand:DI 0 "register_operand" "=r")
15882         (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
15883                    UNSPEC_TLSDESC))]
15884   "TARGET_64BIT && TARGET_GNU2_TLS"
15885   "lea{q}\t{%a1@TLSDESC(%%rip), %0|%0, %a1@TLSDESC[rip]}"
15886   [(set_attr "type" "lea")
15887    (set_attr "mode" "DI")
15888    (set_attr "length" "7")
15889    (set_attr "length_address" "4")])
15890
15891 (define_insn "*tls_dynamic_call_64"
15892   [(set (match_operand:DI 0 "register_operand" "=a")
15893         (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")
15894                     (match_operand:DI 2 "register_operand" "0")
15895                     (reg:DI SP_REG)]
15896                    UNSPEC_TLSDESC))
15897    (clobber (reg:CC FLAGS_REG))]
15898   "TARGET_64BIT && TARGET_GNU2_TLS"
15899   "call\t{*%a1@TLSCALL(%2)|[QWORD PTR [%2+%a1@TLSCALL]]}"
15900   [(set_attr "type" "call")
15901    (set_attr "length" "2")
15902    (set_attr "length_address" "0")])
15903
15904 (define_insn_and_split "*tls_dynamic_gnu2_combine_64"
15905   [(set (match_operand:DI 0 "register_operand" "=&a")
15906         (plus:DI
15907          (unspec:DI [(match_operand:DI 2 "tls_modbase_operand" "")
15908                      (match_operand:DI 3 "" "")
15909                      (reg:DI SP_REG)]
15910                     UNSPEC_TLSDESC)
15911          (const:DI (unspec:DI
15912                     [(match_operand:DI 1 "tls_symbolic_operand" "")]
15913                     UNSPEC_DTPOFF))))
15914    (clobber (reg:CC FLAGS_REG))]
15915   "TARGET_64BIT && TARGET_GNU2_TLS"
15916   "#"
15917   ""
15918   [(set (match_dup 0) (match_dup 4))]
15919 {
15920   operands[4] = !can_create_pseudo_p () ? operands[0] : gen_reg_rtx (Pmode);
15921   emit_insn (gen_tls_dynamic_gnu2_64 (operands[4], operands[1]));
15922 })
15923
15924 ;;
15925 \f
15926 ;; These patterns match the binary 387 instructions for addM3, subM3,
15927 ;; mulM3 and divM3.  There are three patterns for each of DFmode and
15928 ;; SFmode.  The first is the normal insn, the second the same insn but
15929 ;; with one operand a conversion, and the third the same insn but with
15930 ;; the other operand a conversion.  The conversion may be SFmode or
15931 ;; SImode if the target mode DFmode, but only SImode if the target mode
15932 ;; is SFmode.
15933
15934 ;; Gcc is slightly more smart about handling normal two address instructions
15935 ;; so use special patterns for add and mull.
15936
15937 (define_insn "*fop_sf_comm_mixed"
15938   [(set (match_operand:SF 0 "register_operand" "=f,x")
15939         (match_operator:SF 3 "binary_fp_operator"
15940                         [(match_operand:SF 1 "nonimmediate_operand" "%0,0")
15941                          (match_operand:SF 2 "nonimmediate_operand" "fm,xm")]))]
15942   "TARGET_MIX_SSE_I387
15943    && COMMUTATIVE_ARITH_P (operands[3])
15944    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
15945   "* return output_387_binary_op (insn, operands);"
15946   [(set (attr "type")
15947         (if_then_else (eq_attr "alternative" "1")
15948            (if_then_else (match_operand:SF 3 "mult_operator" "")
15949               (const_string "ssemul")
15950               (const_string "sseadd"))
15951            (if_then_else (match_operand:SF 3 "mult_operator" "")
15952               (const_string "fmul")
15953               (const_string "fop"))))
15954    (set_attr "mode" "SF")])
15955
15956 (define_insn "*fop_sf_comm_sse"
15957   [(set (match_operand:SF 0 "register_operand" "=x")
15958         (match_operator:SF 3 "binary_fp_operator"
15959                         [(match_operand:SF 1 "nonimmediate_operand" "%0")
15960                          (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
15961   "TARGET_SSE_MATH
15962    && COMMUTATIVE_ARITH_P (operands[3])
15963    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
15964   "* return output_387_binary_op (insn, operands);"
15965   [(set (attr "type")
15966         (if_then_else (match_operand:SF 3 "mult_operator" "")
15967            (const_string "ssemul")
15968            (const_string "sseadd")))
15969    (set_attr "mode" "SF")])
15970
15971 (define_insn "*fop_sf_comm_i387"
15972   [(set (match_operand:SF 0 "register_operand" "=f")
15973         (match_operator:SF 3 "binary_fp_operator"
15974                         [(match_operand:SF 1 "nonimmediate_operand" "%0")
15975                          (match_operand:SF 2 "nonimmediate_operand" "fm")]))]
15976   "TARGET_80387
15977    && COMMUTATIVE_ARITH_P (operands[3])
15978    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
15979   "* return output_387_binary_op (insn, operands);"
15980   [(set (attr "type")
15981         (if_then_else (match_operand:SF 3 "mult_operator" "")
15982            (const_string "fmul")
15983            (const_string "fop")))
15984    (set_attr "mode" "SF")])
15985
15986 (define_insn "*fop_sf_1_mixed"
15987   [(set (match_operand:SF 0 "register_operand" "=f,f,x")
15988         (match_operator:SF 3 "binary_fp_operator"
15989                         [(match_operand:SF 1 "nonimmediate_operand" "0,fm,0")
15990                          (match_operand:SF 2 "nonimmediate_operand" "fm,0,xm")]))]
15991   "TARGET_MIX_SSE_I387
15992    && !COMMUTATIVE_ARITH_P (operands[3])
15993    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
15994   "* return output_387_binary_op (insn, operands);"
15995   [(set (attr "type")
15996         (cond [(and (eq_attr "alternative" "2")
15997                     (match_operand:SF 3 "mult_operator" ""))
15998                  (const_string "ssemul")
15999                (and (eq_attr "alternative" "2")
16000                     (match_operand:SF 3 "div_operator" ""))
16001                  (const_string "ssediv")
16002                (eq_attr "alternative" "2")
16003                  (const_string "sseadd")
16004                (match_operand:SF 3 "mult_operator" "")
16005                  (const_string "fmul")
16006                (match_operand:SF 3 "div_operator" "")
16007                  (const_string "fdiv")
16008               ]
16009               (const_string "fop")))
16010    (set_attr "mode" "SF")])
16011
16012 (define_insn "*rcpsf2_sse"
16013   [(set (match_operand:SF 0 "register_operand" "=x")
16014         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
16015                    UNSPEC_RCP))]
16016   "TARGET_SSE_MATH"
16017   "rcpss\t{%1, %0|%0, %1}"
16018   [(set_attr "type" "sse")
16019    (set_attr "mode" "SF")])
16020
16021 (define_insn "*fop_sf_1_sse"
16022   [(set (match_operand:SF 0 "register_operand" "=x")
16023         (match_operator:SF 3 "binary_fp_operator"
16024                         [(match_operand:SF 1 "register_operand" "0")
16025                          (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
16026   "TARGET_SSE_MATH
16027    && !COMMUTATIVE_ARITH_P (operands[3])"
16028   "* return output_387_binary_op (insn, operands);"
16029   [(set (attr "type")
16030         (cond [(match_operand:SF 3 "mult_operator" "")
16031                  (const_string "ssemul")
16032                (match_operand:SF 3 "div_operator" "")
16033                  (const_string "ssediv")
16034               ]
16035               (const_string "sseadd")))
16036    (set_attr "mode" "SF")])
16037
16038 ;; This pattern is not fully shadowed by the pattern above.
16039 (define_insn "*fop_sf_1_i387"
16040   [(set (match_operand:SF 0 "register_operand" "=f,f")
16041         (match_operator:SF 3 "binary_fp_operator"
16042                         [(match_operand:SF 1 "nonimmediate_operand" "0,fm")
16043                          (match_operand:SF 2 "nonimmediate_operand" "fm,0")]))]
16044   "TARGET_80387 && !TARGET_SSE_MATH
16045    && !COMMUTATIVE_ARITH_P (operands[3])
16046    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16047   "* return output_387_binary_op (insn, operands);"
16048   [(set (attr "type")
16049         (cond [(match_operand:SF 3 "mult_operator" "")
16050                  (const_string "fmul")
16051                (match_operand:SF 3 "div_operator" "")
16052                  (const_string "fdiv")
16053               ]
16054               (const_string "fop")))
16055    (set_attr "mode" "SF")])
16056
16057 ;; ??? Add SSE splitters for these!
16058 (define_insn "*fop_sf_2<mode>_i387"
16059   [(set (match_operand:SF 0 "register_operand" "=f,f")
16060         (match_operator:SF 3 "binary_fp_operator"
16061           [(float:SF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
16062            (match_operand:SF 2 "register_operand" "0,0")]))]
16063   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH"
16064   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16065   [(set (attr "type")
16066         (cond [(match_operand:SF 3 "mult_operator" "")
16067                  (const_string "fmul")
16068                (match_operand:SF 3 "div_operator" "")
16069                  (const_string "fdiv")
16070               ]
16071               (const_string "fop")))
16072    (set_attr "fp_int_src" "true")
16073    (set_attr "mode" "<MODE>")])
16074
16075 (define_insn "*fop_sf_3<mode>_i387"
16076   [(set (match_operand:SF 0 "register_operand" "=f,f")
16077         (match_operator:SF 3 "binary_fp_operator"
16078           [(match_operand:SF 1 "register_operand" "0,0")
16079            (float:SF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
16080   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH"
16081   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16082   [(set (attr "type")
16083         (cond [(match_operand:SF 3 "mult_operator" "")
16084                  (const_string "fmul")
16085                (match_operand:SF 3 "div_operator" "")
16086                  (const_string "fdiv")
16087               ]
16088               (const_string "fop")))
16089    (set_attr "fp_int_src" "true")
16090    (set_attr "mode" "<MODE>")])
16091
16092 (define_insn "*fop_df_comm_mixed"
16093   [(set (match_operand:DF 0 "register_operand" "=f,x")
16094         (match_operator:DF 3 "binary_fp_operator"
16095           [(match_operand:DF 1 "nonimmediate_operand" "%0,0")
16096            (match_operand:DF 2 "nonimmediate_operand" "fm,xm")]))]
16097   "TARGET_SSE2 && TARGET_MIX_SSE_I387
16098    && COMMUTATIVE_ARITH_P (operands[3])
16099    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16100   "* return output_387_binary_op (insn, operands);"
16101   [(set (attr "type")
16102         (if_then_else (eq_attr "alternative" "1")
16103            (if_then_else (match_operand:DF 3 "mult_operator" "")
16104               (const_string "ssemul")
16105               (const_string "sseadd"))
16106            (if_then_else (match_operand:DF 3 "mult_operator" "")
16107               (const_string "fmul")
16108               (const_string "fop"))))
16109    (set_attr "mode" "DF")])
16110
16111 (define_insn "*fop_df_comm_sse"
16112   [(set (match_operand:DF 0 "register_operand" "=x")
16113         (match_operator:DF 3 "binary_fp_operator"
16114           [(match_operand:DF 1 "nonimmediate_operand" "%0")
16115            (match_operand:DF 2 "nonimmediate_operand" "xm")]))]
16116   "TARGET_SSE2 && TARGET_SSE_MATH
16117    && COMMUTATIVE_ARITH_P (operands[3])
16118    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16119   "* return output_387_binary_op (insn, operands);"
16120   [(set (attr "type")
16121         (if_then_else (match_operand:DF 3 "mult_operator" "")
16122            (const_string "ssemul")
16123            (const_string "sseadd")))
16124    (set_attr "mode" "DF")])
16125
16126 (define_insn "*fop_df_comm_i387"
16127   [(set (match_operand:DF 0 "register_operand" "=f")
16128         (match_operator:DF 3 "binary_fp_operator"
16129                         [(match_operand:DF 1 "nonimmediate_operand" "%0")
16130                          (match_operand:DF 2 "nonimmediate_operand" "fm")]))]
16131   "TARGET_80387
16132    && COMMUTATIVE_ARITH_P (operands[3])
16133    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16134   "* return output_387_binary_op (insn, operands);"
16135   [(set (attr "type")
16136         (if_then_else (match_operand:DF 3 "mult_operator" "")
16137            (const_string "fmul")
16138            (const_string "fop")))
16139    (set_attr "mode" "DF")])
16140
16141 (define_insn "*fop_df_1_mixed"
16142   [(set (match_operand:DF 0 "register_operand" "=f,f,x")
16143         (match_operator:DF 3 "binary_fp_operator"
16144           [(match_operand:DF 1 "nonimmediate_operand" "0,fm,0")
16145            (match_operand:DF 2 "nonimmediate_operand" "fm,0,xm")]))]
16146   "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
16147    && !COMMUTATIVE_ARITH_P (operands[3])
16148    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16149   "* return output_387_binary_op (insn, operands);"
16150   [(set (attr "type")
16151         (cond [(and (eq_attr "alternative" "2")
16152                     (match_operand:DF 3 "mult_operator" ""))
16153                  (const_string "ssemul")
16154                (and (eq_attr "alternative" "2")
16155                     (match_operand:DF 3 "div_operator" ""))
16156                  (const_string "ssediv")
16157                (eq_attr "alternative" "2")
16158                  (const_string "sseadd")
16159                (match_operand:DF 3 "mult_operator" "")
16160                  (const_string "fmul")
16161                (match_operand:DF 3 "div_operator" "")
16162                  (const_string "fdiv")
16163               ]
16164               (const_string "fop")))
16165    (set_attr "mode" "DF")])
16166
16167 (define_insn "*fop_df_1_sse"
16168   [(set (match_operand:DF 0 "register_operand" "=x")
16169         (match_operator:DF 3 "binary_fp_operator"
16170           [(match_operand:DF 1 "register_operand" "0")
16171            (match_operand:DF 2 "nonimmediate_operand" "xm")]))]
16172   "TARGET_SSE2 && TARGET_SSE_MATH
16173    && !COMMUTATIVE_ARITH_P (operands[3])"
16174   "* return output_387_binary_op (insn, operands);"
16175   [(set_attr "mode" "DF")
16176    (set (attr "type")
16177         (cond [(match_operand:DF 3 "mult_operator" "")
16178                  (const_string "ssemul")
16179                (match_operand:DF 3 "div_operator" "")
16180                  (const_string "ssediv")
16181               ]
16182               (const_string "sseadd")))])
16183
16184 ;; This pattern is not fully shadowed by the pattern above.
16185 (define_insn "*fop_df_1_i387"
16186   [(set (match_operand:DF 0 "register_operand" "=f,f")
16187         (match_operator:DF 3 "binary_fp_operator"
16188                         [(match_operand:DF 1 "nonimmediate_operand" "0,fm")
16189                          (match_operand:DF 2 "nonimmediate_operand" "fm,0")]))]
16190   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
16191    && !COMMUTATIVE_ARITH_P (operands[3])
16192    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16193   "* return output_387_binary_op (insn, operands);"
16194   [(set (attr "type")
16195         (cond [(match_operand:DF 3 "mult_operator" "")
16196                  (const_string "fmul")
16197                (match_operand:DF 3 "div_operator" "")
16198                  (const_string "fdiv")
16199               ]
16200               (const_string "fop")))
16201    (set_attr "mode" "DF")])
16202
16203 ;; ??? Add SSE splitters for these!
16204 (define_insn "*fop_df_2<mode>_i387"
16205   [(set (match_operand:DF 0 "register_operand" "=f,f")
16206         (match_operator:DF 3 "binary_fp_operator"
16207            [(float:DF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
16208             (match_operand:DF 2 "register_operand" "0,0")]))]
16209   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
16210    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
16211   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16212   [(set (attr "type")
16213         (cond [(match_operand:DF 3 "mult_operator" "")
16214                  (const_string "fmul")
16215                (match_operand:DF 3 "div_operator" "")
16216                  (const_string "fdiv")
16217               ]
16218               (const_string "fop")))
16219    (set_attr "fp_int_src" "true")
16220    (set_attr "mode" "<MODE>")])
16221
16222 (define_insn "*fop_df_3<mode>_i387"
16223   [(set (match_operand:DF 0 "register_operand" "=f,f")
16224         (match_operator:DF 3 "binary_fp_operator"
16225            [(match_operand:DF 1 "register_operand" "0,0")
16226             (float:DF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
16227   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
16228    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
16229   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16230   [(set (attr "type")
16231         (cond [(match_operand:DF 3 "mult_operator" "")
16232                  (const_string "fmul")
16233                (match_operand:DF 3 "div_operator" "")
16234                  (const_string "fdiv")
16235               ]
16236               (const_string "fop")))
16237    (set_attr "fp_int_src" "true")
16238    (set_attr "mode" "<MODE>")])
16239
16240 (define_insn "*fop_df_4_i387"
16241   [(set (match_operand:DF 0 "register_operand" "=f,f")
16242         (match_operator:DF 3 "binary_fp_operator"
16243            [(float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
16244             (match_operand:DF 2 "register_operand" "0,f")]))]
16245   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
16246    && !(MEM_P (operands[1]) && MEM_P (operands[2]))"
16247   "* return output_387_binary_op (insn, operands);"
16248   [(set (attr "type")
16249         (cond [(match_operand:DF 3 "mult_operator" "")
16250                  (const_string "fmul")
16251                (match_operand:DF 3 "div_operator" "")
16252                  (const_string "fdiv")
16253               ]
16254               (const_string "fop")))
16255    (set_attr "mode" "SF")])
16256
16257 (define_insn "*fop_df_5_i387"
16258   [(set (match_operand:DF 0 "register_operand" "=f,f")
16259         (match_operator:DF 3 "binary_fp_operator"
16260           [(match_operand:DF 1 "register_operand" "0,f")
16261            (float_extend:DF
16262             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
16263   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
16264   "* return output_387_binary_op (insn, operands);"
16265   [(set (attr "type")
16266         (cond [(match_operand:DF 3 "mult_operator" "")
16267                  (const_string "fmul")
16268                (match_operand:DF 3 "div_operator" "")
16269                  (const_string "fdiv")
16270               ]
16271               (const_string "fop")))
16272    (set_attr "mode" "SF")])
16273
16274 (define_insn "*fop_df_6_i387"
16275   [(set (match_operand:DF 0 "register_operand" "=f,f")
16276         (match_operator:DF 3 "binary_fp_operator"
16277           [(float_extend:DF
16278             (match_operand:SF 1 "register_operand" "0,f"))
16279            (float_extend:DF
16280             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
16281   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
16282   "* return output_387_binary_op (insn, operands);"
16283   [(set (attr "type")
16284         (cond [(match_operand:DF 3 "mult_operator" "")
16285                  (const_string "fmul")
16286                (match_operand:DF 3 "div_operator" "")
16287                  (const_string "fdiv")
16288               ]
16289               (const_string "fop")))
16290    (set_attr "mode" "SF")])
16291
16292 (define_insn "*fop_xf_comm_i387"
16293   [(set (match_operand:XF 0 "register_operand" "=f")
16294         (match_operator:XF 3 "binary_fp_operator"
16295                         [(match_operand:XF 1 "register_operand" "%0")
16296                          (match_operand:XF 2 "register_operand" "f")]))]
16297   "TARGET_80387
16298    && COMMUTATIVE_ARITH_P (operands[3])"
16299   "* return output_387_binary_op (insn, operands);"
16300   [(set (attr "type")
16301         (if_then_else (match_operand:XF 3 "mult_operator" "")
16302            (const_string "fmul")
16303            (const_string "fop")))
16304    (set_attr "mode" "XF")])
16305
16306 (define_insn "*fop_xf_1_i387"
16307   [(set (match_operand:XF 0 "register_operand" "=f,f")
16308         (match_operator:XF 3 "binary_fp_operator"
16309                         [(match_operand:XF 1 "register_operand" "0,f")
16310                          (match_operand:XF 2 "register_operand" "f,0")]))]
16311   "TARGET_80387
16312    && !COMMUTATIVE_ARITH_P (operands[3])"
16313   "* return output_387_binary_op (insn, operands);"
16314   [(set (attr "type")
16315         (cond [(match_operand:XF 3 "mult_operator" "")
16316                  (const_string "fmul")
16317                (match_operand:XF 3 "div_operator" "")
16318                  (const_string "fdiv")
16319               ]
16320               (const_string "fop")))
16321    (set_attr "mode" "XF")])
16322
16323 (define_insn "*fop_xf_2<mode>_i387"
16324   [(set (match_operand:XF 0 "register_operand" "=f,f")
16325         (match_operator:XF 3 "binary_fp_operator"
16326            [(float:XF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
16327             (match_operand:XF 2 "register_operand" "0,0")]))]
16328   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP"
16329   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16330   [(set (attr "type")
16331         (cond [(match_operand:XF 3 "mult_operator" "")
16332                  (const_string "fmul")
16333                (match_operand:XF 3 "div_operator" "")
16334                  (const_string "fdiv")
16335               ]
16336               (const_string "fop")))
16337    (set_attr "fp_int_src" "true")
16338    (set_attr "mode" "<MODE>")])
16339
16340 (define_insn "*fop_xf_3<mode>_i387"
16341   [(set (match_operand:XF 0 "register_operand" "=f,f")
16342         (match_operator:XF 3 "binary_fp_operator"
16343           [(match_operand:XF 1 "register_operand" "0,0")
16344            (float:XF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
16345   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP"
16346   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
16347   [(set (attr "type")
16348         (cond [(match_operand:XF 3 "mult_operator" "")
16349                  (const_string "fmul")
16350                (match_operand:XF 3 "div_operator" "")
16351                  (const_string "fdiv")
16352               ]
16353               (const_string "fop")))
16354    (set_attr "fp_int_src" "true")
16355    (set_attr "mode" "<MODE>")])
16356
16357 (define_insn "*fop_xf_4_i387"
16358   [(set (match_operand:XF 0 "register_operand" "=f,f")
16359         (match_operator:XF 3 "binary_fp_operator"
16360            [(float_extend:XF
16361               (match_operand:MODEF 1 "nonimmediate_operand" "fm,0"))
16362             (match_operand:XF 2 "register_operand" "0,f")]))]
16363   "TARGET_80387"
16364   "* return output_387_binary_op (insn, operands);"
16365   [(set (attr "type")
16366         (cond [(match_operand:XF 3 "mult_operator" "")
16367                  (const_string "fmul")
16368                (match_operand:XF 3 "div_operator" "")
16369                  (const_string "fdiv")
16370               ]
16371               (const_string "fop")))
16372    (set_attr "mode" "SF")])
16373
16374 (define_insn "*fop_xf_5_i387"
16375   [(set (match_operand:XF 0 "register_operand" "=f,f")
16376         (match_operator:XF 3 "binary_fp_operator"
16377           [(match_operand:XF 1 "register_operand" "0,f")
16378            (float_extend:XF
16379              (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
16380   "TARGET_80387"
16381   "* return output_387_binary_op (insn, operands);"
16382   [(set (attr "type")
16383         (cond [(match_operand:XF 3 "mult_operator" "")
16384                  (const_string "fmul")
16385                (match_operand:XF 3 "div_operator" "")
16386                  (const_string "fdiv")
16387               ]
16388               (const_string "fop")))
16389    (set_attr "mode" "SF")])
16390
16391 (define_insn "*fop_xf_6_i387"
16392   [(set (match_operand:XF 0 "register_operand" "=f,f")
16393         (match_operator:XF 3 "binary_fp_operator"
16394           [(float_extend:XF
16395              (match_operand:MODEF 1 "register_operand" "0,f"))
16396            (float_extend:XF
16397              (match_operand:MODEF 2 "nonimmediate_operand" "fm,0"))]))]
16398   "TARGET_80387"
16399   "* return output_387_binary_op (insn, operands);"
16400   [(set (attr "type")
16401         (cond [(match_operand:XF 3 "mult_operator" "")
16402                  (const_string "fmul")
16403                (match_operand:XF 3 "div_operator" "")
16404                  (const_string "fdiv")
16405               ]
16406               (const_string "fop")))
16407    (set_attr "mode" "SF")])
16408
16409 (define_split
16410   [(set (match_operand 0 "register_operand" "")
16411         (match_operator 3 "binary_fp_operator"
16412            [(float (match_operand:X87MODEI12 1 "register_operand" ""))
16413             (match_operand 2 "register_operand" "")]))]
16414   "reload_completed
16415    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))"
16416   [(const_int 0)]
16417 {
16418   operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
16419   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
16420   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
16421                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
16422                                           GET_MODE (operands[3]),
16423                                           operands[4],
16424                                           operands[2])));
16425   ix86_free_from_memory (GET_MODE (operands[1]));
16426   DONE;
16427 })
16428
16429 (define_split
16430   [(set (match_operand 0 "register_operand" "")
16431         (match_operator 3 "binary_fp_operator"
16432            [(match_operand 1 "register_operand" "")
16433             (float (match_operand:X87MODEI12 2 "register_operand" ""))]))]
16434   "reload_completed
16435    && X87_FLOAT_MODE_P (GET_MODE (operands[0]))"
16436   [(const_int 0)]
16437 {
16438   operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
16439   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
16440   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
16441                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
16442                                           GET_MODE (operands[3]),
16443                                           operands[1],
16444                                           operands[4])));
16445   ix86_free_from_memory (GET_MODE (operands[2]));
16446   DONE;
16447 })
16448 \f
16449 ;; FPU special functions.
16450
16451 ;; This pattern implements a no-op XFmode truncation for
16452 ;; all fancy i386 XFmode math functions.
16453
16454 (define_insn "truncxf<mode>2_i387_noop_unspec"
16455   [(set (match_operand:MODEF 0 "register_operand" "=f")
16456         (unspec:MODEF [(match_operand:XF 1 "register_operand" "f")]
16457         UNSPEC_TRUNC_NOOP))]
16458   "TARGET_USE_FANCY_MATH_387"
16459   "* return output_387_reg_move (insn, operands);"
16460   [(set_attr "type" "fmov")
16461    (set_attr "mode" "<MODE>")])
16462
16463 (define_insn "sqrtxf2"
16464   [(set (match_operand:XF 0 "register_operand" "=f")
16465         (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
16466   "TARGET_USE_FANCY_MATH_387"
16467   "fsqrt"
16468   [(set_attr "type" "fpspc")
16469    (set_attr "mode" "XF")
16470    (set_attr "athlon_decode" "direct")
16471    (set_attr "amdfam10_decode" "direct")])
16472
16473 (define_insn "sqrt_extend<mode>xf2_i387"
16474   [(set (match_operand:XF 0 "register_operand" "=f")
16475         (sqrt:XF
16476           (float_extend:XF
16477             (match_operand:MODEF 1 "register_operand" "0"))))]
16478   "TARGET_USE_FANCY_MATH_387"
16479   "fsqrt"
16480   [(set_attr "type" "fpspc")
16481    (set_attr "mode" "XF")
16482    (set_attr "athlon_decode" "direct")
16483    (set_attr "amdfam10_decode" "direct")])
16484
16485 (define_insn "*rsqrtsf2_sse"
16486   [(set (match_operand:SF 0 "register_operand" "=x")
16487         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "xm")]
16488                    UNSPEC_RSQRT))]
16489   "TARGET_SSE_MATH"
16490   "rsqrtss\t{%1, %0|%0, %1}"
16491   [(set_attr "type" "sse")
16492    (set_attr "mode" "SF")])
16493
16494 (define_expand "rsqrtsf2"
16495   [(set (match_operand:SF 0 "register_operand" "")
16496         (unspec:SF [(match_operand:SF 1 "nonimmediate_operand" "")]
16497                    UNSPEC_RSQRT))]
16498   "TARGET_SSE_MATH"
16499 {
16500   ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 1);
16501   DONE;
16502 })
16503
16504 (define_insn "*sqrt<mode>2_sse"
16505   [(set (match_operand:MODEF 0 "register_operand" "=x")
16506         (sqrt:MODEF
16507           (match_operand:MODEF 1 "nonimmediate_operand" "xm")))]
16508   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
16509   "sqrts<ssemodefsuffix>\t{%1, %0|%0, %1}"
16510   [(set_attr "type" "sse")
16511    (set_attr "mode" "<MODE>")
16512    (set_attr "athlon_decode" "*")
16513    (set_attr "amdfam10_decode" "*")])
16514
16515 (define_expand "sqrt<mode>2"
16516   [(set (match_operand:MODEF 0 "register_operand" "")
16517         (sqrt:MODEF
16518           (match_operand:MODEF 1 "nonimmediate_operand" "")))]
16519   "TARGET_USE_FANCY_MATH_387
16520    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
16521 {
16522   if (<MODE>mode == SFmode
16523       && TARGET_SSE_MATH && TARGET_RECIP && !optimize_size
16524       && flag_finite_math_only && !flag_trapping_math
16525       && flag_unsafe_math_optimizations)
16526     {
16527       ix86_emit_swsqrtsf (operands[0], operands[1], SFmode, 0);
16528       DONE;
16529     }
16530
16531   if (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
16532     {
16533       rtx op0 = gen_reg_rtx (XFmode);
16534       rtx op1 = force_reg (<MODE>mode, operands[1]);
16535
16536       emit_insn (gen_sqrt_extend<mode>xf2_i387 (op0, op1));
16537       emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op0));
16538       DONE;
16539    }
16540 })
16541
16542 (define_insn "fpremxf4_i387"
16543   [(set (match_operand:XF 0 "register_operand" "=f")
16544         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
16545                     (match_operand:XF 3 "register_operand" "1")]
16546                    UNSPEC_FPREM_F))
16547    (set (match_operand:XF 1 "register_operand" "=u")
16548         (unspec:XF [(match_dup 2) (match_dup 3)]
16549                    UNSPEC_FPREM_U))
16550    (set (reg:CCFP FPSR_REG)
16551         (unspec:CCFP [(match_dup 2) (match_dup 3)]
16552                      UNSPEC_C2_FLAG))]
16553   "TARGET_USE_FANCY_MATH_387"
16554   "fprem"
16555   [(set_attr "type" "fpspc")
16556    (set_attr "mode" "XF")])
16557
16558 (define_expand "fmodxf3"
16559   [(use (match_operand:XF 0 "register_operand" ""))
16560    (use (match_operand:XF 1 "register_operand" ""))
16561    (use (match_operand:XF 2 "register_operand" ""))]
16562   "TARGET_USE_FANCY_MATH_387"
16563 {
16564   rtx label = gen_label_rtx ();
16565
16566   rtx op2;
16567
16568   if (rtx_equal_p (operands[1], operands[2]))
16569     {
16570       op2 = gen_reg_rtx (XFmode);
16571       emit_move_insn (op2, operands[2]);
16572     }
16573   else
16574     op2 = operands[2];
16575
16576   emit_label (label);
16577   emit_insn (gen_fpremxf4_i387 (operands[1], op2, operands[1], op2));
16578   ix86_emit_fp_unordered_jump (label);
16579   LABEL_NUSES (label) = 1;
16580
16581   emit_move_insn (operands[0], operands[1]);
16582   DONE;
16583 })
16584
16585 (define_expand "fmod<mode>3"
16586   [(use (match_operand:MODEF 0 "register_operand" ""))
16587    (use (match_operand:MODEF 1 "general_operand" ""))
16588    (use (match_operand:MODEF 2 "general_operand" ""))]
16589   "TARGET_USE_FANCY_MATH_387"
16590 {
16591   rtx label = gen_label_rtx ();
16592
16593   rtx op1 = gen_reg_rtx (XFmode);
16594   rtx op2 = gen_reg_rtx (XFmode);
16595
16596   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
16597   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
16598
16599   emit_label (label);
16600   emit_insn (gen_fpremxf4_i387 (op1, op2, op1, op2));
16601   ix86_emit_fp_unordered_jump (label);
16602   LABEL_NUSES (label) = 1;
16603
16604   /* Truncate the result properly for strict SSE math.  */
16605   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
16606       && !TARGET_MIX_SSE_I387)
16607     emit_insn (gen_truncxf<mode>2 (operands[0], op1));
16608   else
16609     emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op1));
16610
16611   DONE;
16612 })
16613
16614 (define_insn "fprem1xf4_i387"
16615   [(set (match_operand:XF 0 "register_operand" "=f")
16616         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
16617                     (match_operand:XF 3 "register_operand" "1")]
16618                    UNSPEC_FPREM1_F))
16619    (set (match_operand:XF 1 "register_operand" "=u")
16620         (unspec:XF [(match_dup 2) (match_dup 3)]
16621                    UNSPEC_FPREM1_U))
16622    (set (reg:CCFP FPSR_REG)
16623         (unspec:CCFP [(match_dup 2) (match_dup 3)]
16624                      UNSPEC_C2_FLAG))]
16625   "TARGET_USE_FANCY_MATH_387"
16626   "fprem1"
16627   [(set_attr "type" "fpspc")
16628    (set_attr "mode" "XF")])
16629
16630 (define_expand "remainderxf3"
16631   [(use (match_operand:XF 0 "register_operand" ""))
16632    (use (match_operand:XF 1 "register_operand" ""))
16633    (use (match_operand:XF 2 "register_operand" ""))]
16634   "TARGET_USE_FANCY_MATH_387"
16635 {
16636   rtx label = gen_label_rtx ();
16637
16638   rtx op2;
16639
16640   if (rtx_equal_p (operands[1], operands[2]))
16641     {
16642       op2 = gen_reg_rtx (XFmode);
16643       emit_move_insn (op2, operands[2]);
16644     }
16645   else
16646     op2 = operands[2];
16647
16648   emit_label (label);
16649   emit_insn (gen_fprem1xf4_i387 (operands[1], op2, operands[1], op2));
16650   ix86_emit_fp_unordered_jump (label);
16651   LABEL_NUSES (label) = 1;
16652
16653   emit_move_insn (operands[0], operands[1]);
16654   DONE;
16655 })
16656
16657 (define_expand "remainder<mode>3"
16658   [(use (match_operand:MODEF 0 "register_operand" ""))
16659    (use (match_operand:MODEF 1 "general_operand" ""))
16660    (use (match_operand:MODEF 2 "general_operand" ""))]
16661   "TARGET_USE_FANCY_MATH_387"
16662 {
16663   rtx label = gen_label_rtx ();
16664
16665   rtx op1 = gen_reg_rtx (XFmode);
16666   rtx op2 = gen_reg_rtx (XFmode);
16667
16668   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
16669   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
16670
16671   emit_label (label);
16672
16673   emit_insn (gen_fprem1xf4_i387 (op1, op2, op1, op2));
16674   ix86_emit_fp_unordered_jump (label);
16675   LABEL_NUSES (label) = 1;
16676
16677   /* Truncate the result properly for strict SSE math.  */
16678   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
16679       && !TARGET_MIX_SSE_I387)
16680     emit_insn (gen_truncxf<mode>2 (operands[0], op1));
16681   else
16682     emit_insn (gen_truncxf<mode>2_i387_noop_unspec (operands[0], op1));
16683
16684   DONE;
16685 })
16686
16687 (define_insn "*sinxf2_i387"
16688   [(set (match_operand:XF 0 "register_operand" "=f")
16689         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
16690   "TARGET_USE_FANCY_MATH_387
16691    && flag_unsafe_math_optimizations"
16692   "fsin"
16693   [(set_attr "type" "fpspc")
16694    (set_attr "mode" "XF")])
16695
16696 (define_insn "*sin_extend<mode>xf2_i387"
16697   [(set (match_operand:XF 0 "register_operand" "=f")
16698         (unspec:XF [(float_extend:XF
16699                       (match_operand:MODEF 1 "register_operand" "0"))]
16700                    UNSPEC_SIN))]
16701   "TARGET_USE_FANCY_MATH_387
16702    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16703        || TARGET_MIX_SSE_I387)
16704    && flag_unsafe_math_optimizations"
16705   "fsin"
16706   [(set_attr "type" "fpspc")
16707    (set_attr "mode" "XF")])
16708
16709 (define_insn "*cosxf2_i387"
16710   [(set (match_operand:XF 0 "register_operand" "=f")
16711         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
16712   "TARGET_USE_FANCY_MATH_387
16713    && flag_unsafe_math_optimizations"
16714   "fcos"
16715   [(set_attr "type" "fpspc")
16716    (set_attr "mode" "XF")])
16717
16718 (define_insn "*cos_extend<mode>xf2_i387"
16719   [(set (match_operand:XF 0 "register_operand" "=f")
16720         (unspec:XF [(float_extend:XF
16721                       (match_operand:MODEF 1 "register_operand" "0"))]
16722                    UNSPEC_COS))]
16723   "TARGET_USE_FANCY_MATH_387
16724    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16725        || TARGET_MIX_SSE_I387)
16726    && flag_unsafe_math_optimizations"
16727   "fcos"
16728   [(set_attr "type" "fpspc")
16729    (set_attr "mode" "XF")])
16730
16731 ;; When sincos pattern is defined, sin and cos builtin functions will be
16732 ;; expanded to sincos pattern with one of its outputs left unused.
16733 ;; CSE pass will figure out if two sincos patterns can be combined,
16734 ;; otherwise sincos pattern will be split back to sin or cos pattern,
16735 ;; depending on the unused output.
16736
16737 (define_insn "sincosxf3"
16738   [(set (match_operand:XF 0 "register_operand" "=f")
16739         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
16740                    UNSPEC_SINCOS_COS))
16741    (set (match_operand:XF 1 "register_operand" "=u")
16742         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
16743   "TARGET_USE_FANCY_MATH_387
16744    && flag_unsafe_math_optimizations"
16745   "fsincos"
16746   [(set_attr "type" "fpspc")
16747    (set_attr "mode" "XF")])
16748
16749 (define_split
16750   [(set (match_operand:XF 0 "register_operand" "")
16751         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
16752                    UNSPEC_SINCOS_COS))
16753    (set (match_operand:XF 1 "register_operand" "")
16754         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
16755   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
16756    && !(reload_completed || reload_in_progress)"
16757   [(set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_SIN))]
16758   "")
16759
16760 (define_split
16761   [(set (match_operand:XF 0 "register_operand" "")
16762         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
16763                    UNSPEC_SINCOS_COS))
16764    (set (match_operand:XF 1 "register_operand" "")
16765         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
16766   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
16767    && !(reload_completed || reload_in_progress)"
16768   [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))]
16769   "")
16770
16771 (define_insn "sincos_extend<mode>xf3_i387"
16772   [(set (match_operand:XF 0 "register_operand" "=f")
16773         (unspec:XF [(float_extend:XF
16774                       (match_operand:MODEF 2 "register_operand" "0"))]
16775                    UNSPEC_SINCOS_COS))
16776    (set (match_operand:XF 1 "register_operand" "=u")
16777         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
16778   "TARGET_USE_FANCY_MATH_387
16779    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16780        || TARGET_MIX_SSE_I387)
16781    && flag_unsafe_math_optimizations"
16782   "fsincos"
16783   [(set_attr "type" "fpspc")
16784    (set_attr "mode" "XF")])
16785
16786 (define_split
16787   [(set (match_operand:XF 0 "register_operand" "")
16788         (unspec:XF [(float_extend:XF
16789                       (match_operand:MODEF 2 "register_operand" ""))]
16790                    UNSPEC_SINCOS_COS))
16791    (set (match_operand:XF 1 "register_operand" "")
16792         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
16793   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
16794    && !(reload_completed || reload_in_progress)"
16795   [(set (match_dup 1) (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SIN))]
16796   "")
16797
16798 (define_split
16799   [(set (match_operand:XF 0 "register_operand" "")
16800         (unspec:XF [(float_extend:XF
16801                       (match_operand:MODEF 2 "register_operand" ""))]
16802                    UNSPEC_SINCOS_COS))
16803    (set (match_operand:XF 1 "register_operand" "")
16804         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_SINCOS_SIN))]
16805   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
16806    && !(reload_completed || reload_in_progress)"
16807   [(set (match_dup 0) (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_COS))]
16808   "")
16809
16810 (define_expand "sincos<mode>3"
16811   [(use (match_operand:MODEF 0 "register_operand" ""))
16812    (use (match_operand:MODEF 1 "register_operand" ""))
16813    (use (match_operand:MODEF 2 "register_operand" ""))]
16814   "TARGET_USE_FANCY_MATH_387
16815    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16816        || TARGET_MIX_SSE_I387)
16817    && flag_unsafe_math_optimizations"
16818 {
16819   rtx op0 = gen_reg_rtx (XFmode);
16820   rtx op1 = gen_reg_rtx (XFmode);
16821
16822   emit_insn (gen_sincos_extend<mode>xf3_i387 (op0, op1, operands[2]));
16823   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16824   emit_insn (gen_truncxf<mode>2_i387_noop (operands[1], op1));
16825   DONE;
16826 })
16827
16828 (define_insn "fptanxf4_i387"
16829   [(set (match_operand:XF 0 "register_operand" "=f")
16830         (match_operand:XF 3 "const_double_operand" "F"))
16831    (set (match_operand:XF 1 "register_operand" "=u")
16832         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
16833                    UNSPEC_TAN))]
16834   "TARGET_USE_FANCY_MATH_387
16835    && flag_unsafe_math_optimizations
16836    && standard_80387_constant_p (operands[3]) == 2"
16837   "fptan"
16838   [(set_attr "type" "fpspc")
16839    (set_attr "mode" "XF")])
16840
16841 (define_insn "fptan_extend<mode>xf4_i387"
16842   [(set (match_operand:MODEF 0 "register_operand" "=f")
16843         (match_operand:MODEF 3 "const_double_operand" "F"))
16844    (set (match_operand:XF 1 "register_operand" "=u")
16845         (unspec:XF [(float_extend:XF
16846                       (match_operand:MODEF 2 "register_operand" "0"))]
16847                    UNSPEC_TAN))]
16848   "TARGET_USE_FANCY_MATH_387
16849    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16850        || TARGET_MIX_SSE_I387)
16851    && flag_unsafe_math_optimizations
16852    && standard_80387_constant_p (operands[3]) == 2"
16853   "fptan"
16854   [(set_attr "type" "fpspc")
16855    (set_attr "mode" "XF")])
16856
16857 (define_expand "tanxf2"
16858   [(use (match_operand:XF 0 "register_operand" ""))
16859    (use (match_operand:XF 1 "register_operand" ""))]
16860   "TARGET_USE_FANCY_MATH_387
16861    && flag_unsafe_math_optimizations"
16862 {
16863   rtx one = gen_reg_rtx (XFmode);
16864   rtx op2 = CONST1_RTX (XFmode); /* fld1 */
16865
16866   emit_insn (gen_fptanxf4_i387 (one, operands[0], operands[1], op2));
16867   DONE;
16868 })
16869
16870 (define_expand "tan<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 one = gen_reg_rtx (<MODE>mode);
16881   rtx op2 = CONST1_RTX (<MODE>mode); /* fld1 */
16882
16883   emit_insn (gen_fptan_extend<mode>xf4_i387 (one, op0,
16884                                              operands[1], op2));
16885   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16886   DONE;
16887 })
16888
16889 (define_insn "*fpatanxf3_i387"
16890   [(set (match_operand:XF 0 "register_operand" "=f")
16891         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
16892                     (match_operand:XF 2 "register_operand" "u")]
16893                    UNSPEC_FPATAN))
16894    (clobber (match_scratch:XF 3 "=2"))]
16895   "TARGET_USE_FANCY_MATH_387
16896    && flag_unsafe_math_optimizations"
16897   "fpatan"
16898   [(set_attr "type" "fpspc")
16899    (set_attr "mode" "XF")])
16900
16901 (define_insn "fpatan_extend<mode>xf3_i387"
16902   [(set (match_operand:XF 0 "register_operand" "=f")
16903         (unspec:XF [(float_extend:XF
16904                       (match_operand:MODEF 1 "register_operand" "0"))
16905                     (float_extend:XF
16906                       (match_operand:MODEF 2 "register_operand" "u"))]
16907                    UNSPEC_FPATAN))
16908    (clobber (match_scratch:XF 3 "=2"))]
16909   "TARGET_USE_FANCY_MATH_387
16910    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16911        || TARGET_MIX_SSE_I387)
16912    && flag_unsafe_math_optimizations"
16913   "fpatan"
16914   [(set_attr "type" "fpspc")
16915    (set_attr "mode" "XF")])
16916
16917 (define_expand "atan2xf3"
16918   [(parallel [(set (match_operand:XF 0 "register_operand" "")
16919                    (unspec:XF [(match_operand:XF 2 "register_operand" "")
16920                                (match_operand:XF 1 "register_operand" "")]
16921                               UNSPEC_FPATAN))
16922               (clobber (match_scratch:XF 3 ""))])]
16923   "TARGET_USE_FANCY_MATH_387
16924    && flag_unsafe_math_optimizations"
16925   "")
16926
16927 (define_expand "atan2<mode>3"
16928   [(use (match_operand:MODEF 0 "register_operand" ""))
16929    (use (match_operand:MODEF 1 "register_operand" ""))
16930    (use (match_operand:MODEF 2 "register_operand" ""))]
16931   "TARGET_USE_FANCY_MATH_387
16932    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16933        || TARGET_MIX_SSE_I387)
16934    && flag_unsafe_math_optimizations"
16935 {
16936   rtx op0 = gen_reg_rtx (XFmode);
16937
16938   emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, operands[2], operands[1]));
16939   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16940   DONE;
16941 })
16942
16943 (define_expand "atanxf2"
16944   [(parallel [(set (match_operand:XF 0 "register_operand" "")
16945                    (unspec:XF [(match_dup 2)
16946                                (match_operand:XF 1 "register_operand" "")]
16947                               UNSPEC_FPATAN))
16948               (clobber (match_scratch:XF 3 ""))])]
16949   "TARGET_USE_FANCY_MATH_387
16950    && flag_unsafe_math_optimizations"
16951 {
16952   operands[2] = gen_reg_rtx (XFmode);
16953   emit_move_insn (operands[2], CONST1_RTX (XFmode));  /* fld1 */
16954 })
16955
16956 (define_expand "atan<mode>2"
16957   [(use (match_operand:MODEF 0 "register_operand" ""))
16958    (use (match_operand:MODEF 1 "register_operand" ""))]
16959   "TARGET_USE_FANCY_MATH_387
16960    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
16961        || TARGET_MIX_SSE_I387)
16962    && flag_unsafe_math_optimizations"
16963 {
16964   rtx op0 = gen_reg_rtx (XFmode);
16965
16966   rtx op2 = gen_reg_rtx (<MODE>mode);
16967   emit_move_insn (op2, CONST1_RTX (<MODE>mode));  /* fld1 */
16968
16969   emit_insn (gen_fpatan_extend<mode>xf3_i387 (op0, op2, operands[1]));
16970   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
16971   DONE;
16972 })
16973
16974 (define_expand "asinxf2"
16975   [(set (match_dup 2)
16976         (mult:XF (match_operand:XF 1 "register_operand" "")
16977                  (match_dup 1)))
16978    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
16979    (set (match_dup 5) (sqrt:XF (match_dup 4)))
16980    (parallel [(set (match_operand:XF 0 "register_operand" "")
16981                    (unspec:XF [(match_dup 5) (match_dup 1)]
16982                               UNSPEC_FPATAN))
16983               (clobber (match_scratch:XF 6 ""))])]
16984   "TARGET_USE_FANCY_MATH_387
16985    && flag_unsafe_math_optimizations && !optimize_size"
16986 {
16987   int i;
16988
16989   for (i = 2; i < 6; i++)
16990     operands[i] = gen_reg_rtx (XFmode);
16991
16992   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
16993 })
16994
16995 (define_expand "asin<mode>2"
16996   [(use (match_operand:MODEF 0 "register_operand" ""))
16997    (use (match_operand:MODEF 1 "general_operand" ""))]
16998  "TARGET_USE_FANCY_MATH_387
16999    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17000        || TARGET_MIX_SSE_I387)
17001    && flag_unsafe_math_optimizations && !optimize_size"
17002 {
17003   rtx op0 = gen_reg_rtx (XFmode);
17004   rtx op1 = gen_reg_rtx (XFmode);
17005
17006   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17007   emit_insn (gen_asinxf2 (op0, op1));
17008   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17009   DONE;
17010 })
17011
17012 (define_expand "acosxf2"
17013   [(set (match_dup 2)
17014         (mult:XF (match_operand:XF 1 "register_operand" "")
17015                  (match_dup 1)))
17016    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
17017    (set (match_dup 5) (sqrt:XF (match_dup 4)))
17018    (parallel [(set (match_operand:XF 0 "register_operand" "")
17019                    (unspec:XF [(match_dup 1) (match_dup 5)]
17020                               UNSPEC_FPATAN))
17021               (clobber (match_scratch:XF 6 ""))])]
17022   "TARGET_USE_FANCY_MATH_387
17023    && flag_unsafe_math_optimizations && !optimize_size"
17024 {
17025   int i;
17026
17027   for (i = 2; i < 6; i++)
17028     operands[i] = gen_reg_rtx (XFmode);
17029
17030   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
17031 })
17032
17033 (define_expand "acos<mode>2"
17034   [(use (match_operand:MODEF 0 "register_operand" ""))
17035    (use (match_operand:MODEF 1 "general_operand" ""))]
17036  "TARGET_USE_FANCY_MATH_387
17037    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17038        || TARGET_MIX_SSE_I387)
17039    && flag_unsafe_math_optimizations && !optimize_size"
17040 {
17041   rtx op0 = gen_reg_rtx (XFmode);
17042   rtx op1 = gen_reg_rtx (XFmode);
17043
17044   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17045   emit_insn (gen_acosxf2 (op0, op1));
17046   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17047   DONE;
17048 })
17049
17050 (define_insn "fyl2xxf3_i387"
17051   [(set (match_operand:XF 0 "register_operand" "=f")
17052         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
17053                     (match_operand:XF 2 "register_operand" "u")]
17054                    UNSPEC_FYL2X))
17055    (clobber (match_scratch:XF 3 "=2"))]
17056   "TARGET_USE_FANCY_MATH_387
17057    && flag_unsafe_math_optimizations"
17058   "fyl2x"
17059   [(set_attr "type" "fpspc")
17060    (set_attr "mode" "XF")])
17061
17062 (define_insn "fyl2x_extend<mode>xf3_i387"
17063   [(set (match_operand:XF 0 "register_operand" "=f")
17064         (unspec:XF [(float_extend:XF
17065                       (match_operand:MODEF 1 "register_operand" "0"))
17066                     (match_operand:XF 2 "register_operand" "u")]
17067                    UNSPEC_FYL2X))
17068    (clobber (match_scratch:XF 3 "=2"))]
17069   "TARGET_USE_FANCY_MATH_387
17070    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17071        || TARGET_MIX_SSE_I387)
17072    && flag_unsafe_math_optimizations"
17073   "fyl2x"
17074   [(set_attr "type" "fpspc")
17075    (set_attr "mode" "XF")])
17076
17077 (define_expand "logxf2"
17078   [(parallel [(set (match_operand:XF 0 "register_operand" "")
17079                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
17080                                (match_dup 2)] UNSPEC_FYL2X))
17081               (clobber (match_scratch:XF 3 ""))])]
17082   "TARGET_USE_FANCY_MATH_387
17083    && flag_unsafe_math_optimizations"
17084 {
17085   operands[2] = gen_reg_rtx (XFmode);
17086   emit_move_insn (operands[2], standard_80387_constant_rtx (4)); /* fldln2 */
17087 })
17088
17089 (define_expand "log<mode>2"
17090   [(use (match_operand:MODEF 0 "register_operand" ""))
17091    (use (match_operand:MODEF 1 "register_operand" ""))]
17092   "TARGET_USE_FANCY_MATH_387
17093    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17094        || TARGET_MIX_SSE_I387)
17095    && flag_unsafe_math_optimizations"
17096 {
17097   rtx op0 = gen_reg_rtx (XFmode);
17098
17099   rtx op2 = gen_reg_rtx (XFmode);
17100   emit_move_insn (op2, standard_80387_constant_rtx (4)); /* fldln2 */
17101
17102   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
17103   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17104   DONE;
17105 })
17106
17107 (define_expand "log10xf2"
17108   [(parallel [(set (match_operand:XF 0 "register_operand" "")
17109                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
17110                                (match_dup 2)] UNSPEC_FYL2X))
17111               (clobber (match_scratch:XF 3 ""))])]
17112   "TARGET_USE_FANCY_MATH_387
17113    && flag_unsafe_math_optimizations"
17114 {
17115   operands[2] = gen_reg_rtx (XFmode);
17116   emit_move_insn (operands[2], standard_80387_constant_rtx (3)); /* fldlg2 */
17117 })
17118
17119 (define_expand "log10<mode>2"
17120   [(use (match_operand:MODEF 0 "register_operand" ""))
17121    (use (match_operand:MODEF 1 "register_operand" ""))]
17122   "TARGET_USE_FANCY_MATH_387
17123    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17124        || TARGET_MIX_SSE_I387)
17125    && flag_unsafe_math_optimizations"
17126 {
17127   rtx op0 = gen_reg_rtx (XFmode);
17128
17129   rtx op2 = gen_reg_rtx (XFmode);
17130   emit_move_insn (op2, standard_80387_constant_rtx (3)); /* fldlg2 */
17131
17132   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
17133   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17134   DONE;
17135 })
17136
17137 (define_expand "log2xf2"
17138   [(parallel [(set (match_operand:XF 0 "register_operand" "")
17139                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
17140                                (match_dup 2)] UNSPEC_FYL2X))
17141               (clobber (match_scratch:XF 3 ""))])]
17142   "TARGET_USE_FANCY_MATH_387
17143    && flag_unsafe_math_optimizations"
17144 {
17145   operands[2] = gen_reg_rtx (XFmode);
17146   emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
17147 })
17148
17149 (define_expand "log2<mode>2"
17150   [(use (match_operand:MODEF 0 "register_operand" ""))
17151    (use (match_operand:MODEF 1 "register_operand" ""))]
17152   "TARGET_USE_FANCY_MATH_387
17153    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17154        || TARGET_MIX_SSE_I387)
17155    && flag_unsafe_math_optimizations"
17156 {
17157   rtx op0 = gen_reg_rtx (XFmode);
17158
17159   rtx op2 = gen_reg_rtx (XFmode);
17160   emit_move_insn (op2, CONST1_RTX (XFmode)); /* fld1 */
17161
17162   emit_insn (gen_fyl2x_extend<mode>xf3_i387 (op0, operands[1], op2));
17163   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17164   DONE;
17165 })
17166
17167 (define_insn "fyl2xp1xf3_i387"
17168   [(set (match_operand:XF 0 "register_operand" "=f")
17169         (unspec:XF [(match_operand:XF 1 "register_operand" "0")
17170                     (match_operand:XF 2 "register_operand" "u")]
17171                    UNSPEC_FYL2XP1))
17172    (clobber (match_scratch:XF 3 "=2"))]
17173   "TARGET_USE_FANCY_MATH_387
17174    && flag_unsafe_math_optimizations"
17175   "fyl2xp1"
17176   [(set_attr "type" "fpspc")
17177    (set_attr "mode" "XF")])
17178
17179 (define_insn "fyl2xp1_extend<mode>xf3_i387"
17180   [(set (match_operand:XF 0 "register_operand" "=f")
17181         (unspec:XF [(float_extend:XF
17182                       (match_operand:MODEF 1 "register_operand" "0"))
17183                     (match_operand:XF 2 "register_operand" "u")]
17184                    UNSPEC_FYL2XP1))
17185    (clobber (match_scratch:XF 3 "=2"))]
17186   "TARGET_USE_FANCY_MATH_387
17187    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17188        || TARGET_MIX_SSE_I387)
17189    && flag_unsafe_math_optimizations"
17190   "fyl2xp1"
17191   [(set_attr "type" "fpspc")
17192    (set_attr "mode" "XF")])
17193
17194 (define_expand "log1pxf2"
17195   [(use (match_operand:XF 0 "register_operand" ""))
17196    (use (match_operand:XF 1 "register_operand" ""))]
17197   "TARGET_USE_FANCY_MATH_387
17198    && flag_unsafe_math_optimizations && !optimize_size"
17199 {
17200   ix86_emit_i387_log1p (operands[0], operands[1]);
17201   DONE;
17202 })
17203
17204 (define_expand "log1p<mode>2"
17205   [(use (match_operand:MODEF 0 "register_operand" ""))
17206    (use (match_operand:MODEF 1 "register_operand" ""))]
17207   "TARGET_USE_FANCY_MATH_387
17208    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17209        || TARGET_MIX_SSE_I387)
17210    && flag_unsafe_math_optimizations && !optimize_size"
17211 {
17212   rtx op0 = gen_reg_rtx (XFmode);
17213
17214   operands[1] = gen_rtx_FLOAT_EXTEND (XFmode, operands[1]);
17215
17216   ix86_emit_i387_log1p (op0, operands[1]);
17217   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17218   DONE;
17219 })
17220
17221 (define_insn "fxtractxf3_i387"
17222   [(set (match_operand:XF 0 "register_operand" "=f")
17223         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
17224                    UNSPEC_XTRACT_FRACT))
17225    (set (match_operand:XF 1 "register_operand" "=u")
17226         (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]
17227   "TARGET_USE_FANCY_MATH_387
17228    && flag_unsafe_math_optimizations"
17229   "fxtract"
17230   [(set_attr "type" "fpspc")
17231    (set_attr "mode" "XF")])
17232
17233 (define_insn "fxtract_extend<mode>xf3_i387"
17234   [(set (match_operand:XF 0 "register_operand" "=f")
17235         (unspec:XF [(float_extend:XF
17236                       (match_operand:MODEF 2 "register_operand" "0"))]
17237                    UNSPEC_XTRACT_FRACT))
17238    (set (match_operand:XF 1 "register_operand" "=u")
17239         (unspec:XF [(float_extend:XF (match_dup 2))] UNSPEC_XTRACT_EXP))]
17240   "TARGET_USE_FANCY_MATH_387
17241    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17242        || TARGET_MIX_SSE_I387)
17243    && flag_unsafe_math_optimizations"
17244   "fxtract"
17245   [(set_attr "type" "fpspc")
17246    (set_attr "mode" "XF")])
17247
17248 (define_expand "logbxf2"
17249   [(parallel [(set (match_dup 2)
17250                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
17251                               UNSPEC_XTRACT_FRACT))
17252               (set (match_operand:XF 0 "register_operand" "")
17253                    (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
17254   "TARGET_USE_FANCY_MATH_387
17255    && flag_unsafe_math_optimizations"
17256 {
17257   operands[2] = gen_reg_rtx (XFmode);
17258 })
17259
17260 (define_expand "logb<mode>2"
17261   [(use (match_operand:MODEF 0 "register_operand" ""))
17262    (use (match_operand:MODEF 1 "register_operand" ""))]
17263   "TARGET_USE_FANCY_MATH_387
17264    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17265        || TARGET_MIX_SSE_I387)
17266    && flag_unsafe_math_optimizations"
17267 {
17268   rtx op0 = gen_reg_rtx (XFmode);
17269   rtx op1 = gen_reg_rtx (XFmode);
17270
17271   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
17272   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op1));
17273   DONE;
17274 })
17275
17276 (define_expand "ilogbxf2"
17277   [(use (match_operand:SI 0 "register_operand" ""))
17278    (use (match_operand:XF 1 "register_operand" ""))]
17279   "TARGET_USE_FANCY_MATH_387
17280    && flag_unsafe_math_optimizations && !optimize_size"
17281 {
17282   rtx op0 = gen_reg_rtx (XFmode);
17283   rtx op1 = gen_reg_rtx (XFmode);
17284
17285   emit_insn (gen_fxtractxf3_i387 (op0, op1, operands[1]));
17286   emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
17287   DONE;
17288 })
17289
17290 (define_expand "ilogb<mode>2"
17291   [(use (match_operand:SI 0 "register_operand" ""))
17292    (use (match_operand:MODEF 1 "register_operand" ""))]
17293   "TARGET_USE_FANCY_MATH_387
17294    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17295        || TARGET_MIX_SSE_I387)
17296    && flag_unsafe_math_optimizations && !optimize_size"
17297 {
17298   rtx op0 = gen_reg_rtx (XFmode);
17299   rtx op1 = gen_reg_rtx (XFmode);
17300
17301   emit_insn (gen_fxtract_extend<mode>xf3_i387 (op0, op1, operands[1]));
17302   emit_insn (gen_fix_truncxfsi2 (operands[0], op1));
17303   DONE;
17304 })
17305
17306 (define_insn "*f2xm1xf2_i387"
17307   [(set (match_operand:XF 0 "register_operand" "=f")
17308         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17309                    UNSPEC_F2XM1))]
17310   "TARGET_USE_FANCY_MATH_387
17311    && flag_unsafe_math_optimizations"
17312   "f2xm1"
17313   [(set_attr "type" "fpspc")
17314    (set_attr "mode" "XF")])
17315
17316 (define_insn "*fscalexf4_i387"
17317   [(set (match_operand:XF 0 "register_operand" "=f")
17318         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
17319                     (match_operand:XF 3 "register_operand" "1")]
17320                    UNSPEC_FSCALE_FRACT))
17321    (set (match_operand:XF 1 "register_operand" "=u")
17322         (unspec:XF [(match_dup 2) (match_dup 3)]
17323                    UNSPEC_FSCALE_EXP))]
17324   "TARGET_USE_FANCY_MATH_387
17325    && flag_unsafe_math_optimizations"
17326   "fscale"
17327   [(set_attr "type" "fpspc")
17328    (set_attr "mode" "XF")])
17329
17330 (define_expand "expNcorexf3"
17331   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
17332                                (match_operand:XF 2 "register_operand" "")))
17333    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
17334    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
17335    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
17336    (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
17337    (parallel [(set (match_operand:XF 0 "register_operand" "")
17338                    (unspec:XF [(match_dup 8) (match_dup 4)]
17339                               UNSPEC_FSCALE_FRACT))
17340               (set (match_dup 9)
17341                    (unspec:XF [(match_dup 8) (match_dup 4)]
17342                               UNSPEC_FSCALE_EXP))])]
17343   "TARGET_USE_FANCY_MATH_387
17344    && flag_unsafe_math_optimizations && !optimize_size"
17345 {
17346   int i;
17347
17348   for (i = 3; i < 10; i++)
17349     operands[i] = gen_reg_rtx (XFmode);
17350
17351   emit_move_insn (operands[7], CONST1_RTX (XFmode));  /* fld1 */
17352 })
17353
17354 (define_expand "expxf2"
17355   [(use (match_operand:XF 0 "register_operand" ""))
17356    (use (match_operand:XF 1 "register_operand" ""))]
17357   "TARGET_USE_FANCY_MATH_387
17358    && flag_unsafe_math_optimizations && !optimize_size"
17359 {
17360   rtx op2 = gen_reg_rtx (XFmode);
17361   emit_move_insn (op2, standard_80387_constant_rtx (5)); /* fldl2e */
17362
17363   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
17364   DONE;
17365 })
17366
17367 (define_expand "exp<mode>2"
17368   [(use (match_operand:MODEF 0 "register_operand" ""))
17369    (use (match_operand:MODEF 1 "general_operand" ""))]
17370  "TARGET_USE_FANCY_MATH_387
17371    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17372        || TARGET_MIX_SSE_I387)
17373    && flag_unsafe_math_optimizations && !optimize_size"
17374 {
17375   rtx op0 = gen_reg_rtx (XFmode);
17376   rtx op1 = gen_reg_rtx (XFmode);
17377
17378   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17379   emit_insn (gen_expxf2 (op0, op1));
17380   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17381   DONE;
17382 })
17383
17384 (define_expand "exp10xf2"
17385   [(use (match_operand:XF 0 "register_operand" ""))
17386    (use (match_operand:XF 1 "register_operand" ""))]
17387   "TARGET_USE_FANCY_MATH_387
17388    && flag_unsafe_math_optimizations && !optimize_size"
17389 {
17390   rtx op2 = gen_reg_rtx (XFmode);
17391   emit_move_insn (op2, standard_80387_constant_rtx (6)); /* fldl2t */
17392
17393   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
17394   DONE;
17395 })
17396
17397 (define_expand "exp10<mode>2"
17398   [(use (match_operand:MODEF 0 "register_operand" ""))
17399    (use (match_operand:MODEF 1 "general_operand" ""))]
17400  "TARGET_USE_FANCY_MATH_387
17401    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17402        || TARGET_MIX_SSE_I387)
17403    && flag_unsafe_math_optimizations && !optimize_size"
17404 {
17405   rtx op0 = gen_reg_rtx (XFmode);
17406   rtx op1 = gen_reg_rtx (XFmode);
17407
17408   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17409   emit_insn (gen_exp10xf2 (op0, op1));
17410   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17411   DONE;
17412 })
17413
17414 (define_expand "exp2xf2"
17415   [(use (match_operand:XF 0 "register_operand" ""))
17416    (use (match_operand:XF 1 "register_operand" ""))]
17417   "TARGET_USE_FANCY_MATH_387
17418    && flag_unsafe_math_optimizations && !optimize_size"
17419 {
17420   rtx op2 = gen_reg_rtx (XFmode);
17421   emit_move_insn (op2, CONST1_RTX (XFmode));  /* fld1 */
17422
17423   emit_insn (gen_expNcorexf3 (operands[0], operands[1], op2));
17424   DONE;
17425 })
17426
17427 (define_expand "exp2<mode>2"
17428   [(use (match_operand:MODEF 0 "register_operand" ""))
17429    (use (match_operand:MODEF 1 "general_operand" ""))]
17430  "TARGET_USE_FANCY_MATH_387
17431    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17432        || TARGET_MIX_SSE_I387)
17433    && flag_unsafe_math_optimizations && !optimize_size"
17434 {
17435   rtx op0 = gen_reg_rtx (XFmode);
17436   rtx op1 = gen_reg_rtx (XFmode);
17437
17438   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17439   emit_insn (gen_exp2xf2 (op0, op1));
17440   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17441   DONE;
17442 })
17443
17444 (define_expand "expm1xf2"
17445   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
17446                                (match_dup 2)))
17447    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
17448    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
17449    (set (match_dup 9) (float_extend:XF (match_dup 13)))
17450    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
17451    (parallel [(set (match_dup 7)
17452                    (unspec:XF [(match_dup 6) (match_dup 4)]
17453                               UNSPEC_FSCALE_FRACT))
17454               (set (match_dup 8)
17455                    (unspec:XF [(match_dup 6) (match_dup 4)]
17456                               UNSPEC_FSCALE_EXP))])
17457    (parallel [(set (match_dup 10)
17458                    (unspec:XF [(match_dup 9) (match_dup 8)]
17459                               UNSPEC_FSCALE_FRACT))
17460               (set (match_dup 11)
17461                    (unspec:XF [(match_dup 9) (match_dup 8)]
17462                               UNSPEC_FSCALE_EXP))])
17463    (set (match_dup 12) (minus:XF (match_dup 10)
17464                                  (float_extend:XF (match_dup 13))))
17465    (set (match_operand:XF 0 "register_operand" "")
17466         (plus:XF (match_dup 12) (match_dup 7)))]
17467   "TARGET_USE_FANCY_MATH_387
17468    && flag_unsafe_math_optimizations && !optimize_size"
17469 {
17470   int i;
17471
17472   for (i = 2; i < 13; i++)
17473     operands[i] = gen_reg_rtx (XFmode);
17474
17475   operands[13]
17476     = validize_mem (force_const_mem (SFmode, CONST1_RTX (SFmode))); /* fld1 */
17477
17478   emit_move_insn (operands[2], standard_80387_constant_rtx (5)); /* fldl2e */
17479 })
17480
17481 (define_expand "expm1<mode>2"
17482   [(use (match_operand:MODEF 0 "register_operand" ""))
17483    (use (match_operand:MODEF 1 "general_operand" ""))]
17484  "TARGET_USE_FANCY_MATH_387
17485    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17486        || TARGET_MIX_SSE_I387)
17487    && flag_unsafe_math_optimizations && !optimize_size"
17488 {
17489   rtx op0 = gen_reg_rtx (XFmode);
17490   rtx op1 = gen_reg_rtx (XFmode);
17491
17492   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17493   emit_insn (gen_expm1xf2 (op0, op1));
17494   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17495   DONE;
17496 })
17497
17498 (define_expand "ldexpxf3"
17499   [(set (match_dup 3)
17500         (float:XF (match_operand:SI 2 "register_operand" "")))
17501    (parallel [(set (match_operand:XF 0 " register_operand" "")
17502                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
17503                                (match_dup 3)]
17504                               UNSPEC_FSCALE_FRACT))
17505               (set (match_dup 4)
17506                    (unspec:XF [(match_dup 1) (match_dup 3)]
17507                               UNSPEC_FSCALE_EXP))])]
17508   "TARGET_USE_FANCY_MATH_387
17509    && flag_unsafe_math_optimizations && !optimize_size"
17510 {
17511   operands[3] = gen_reg_rtx (XFmode);
17512   operands[4] = gen_reg_rtx (XFmode);
17513 })
17514
17515 (define_expand "ldexp<mode>3"
17516   [(use (match_operand:MODEF 0 "register_operand" ""))
17517    (use (match_operand:MODEF 1 "general_operand" ""))
17518    (use (match_operand:SI 2 "register_operand" ""))]
17519  "TARGET_USE_FANCY_MATH_387
17520    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17521        || TARGET_MIX_SSE_I387)
17522    && flag_unsafe_math_optimizations && !optimize_size"
17523 {
17524   rtx op0 = gen_reg_rtx (XFmode);
17525   rtx op1 = gen_reg_rtx (XFmode);
17526
17527   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17528   emit_insn (gen_ldexpxf3 (op0, op1, operands[2]));
17529   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17530   DONE;
17531 })
17532
17533 (define_expand "scalbxf3"
17534   [(parallel [(set (match_operand:XF 0 " register_operand" "")
17535                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
17536                                (match_operand:XF 2 "register_operand" "")]
17537                               UNSPEC_FSCALE_FRACT))
17538               (set (match_dup 3)
17539                    (unspec:XF [(match_dup 1) (match_dup 2)]
17540                               UNSPEC_FSCALE_EXP))])]
17541   "TARGET_USE_FANCY_MATH_387
17542    && flag_unsafe_math_optimizations && !optimize_size"
17543 {
17544   operands[3] = gen_reg_rtx (XFmode);
17545 })
17546
17547 (define_expand "scalb<mode>3"
17548   [(use (match_operand:MODEF 0 "register_operand" ""))
17549    (use (match_operand:MODEF 1 "general_operand" ""))
17550    (use (match_operand:MODEF 2 "register_operand" ""))]
17551  "TARGET_USE_FANCY_MATH_387
17552    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17553        || TARGET_MIX_SSE_I387)
17554    && flag_unsafe_math_optimizations && !optimize_size"
17555 {
17556   rtx op0 = gen_reg_rtx (XFmode);
17557   rtx op1 = gen_reg_rtx (XFmode);
17558   rtx op2 = gen_reg_rtx (XFmode);
17559
17560   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17561   emit_insn (gen_extend<mode>xf2 (op2, operands[2]));
17562   emit_insn (gen_scalbxf3 (op0, op1, op2));
17563   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17564   DONE;
17565 })
17566 \f
17567
17568 (define_insn "sse4_1_round<mode>2"
17569   [(set (match_operand:MODEF 0 "register_operand" "=x")
17570         (unspec:MODEF [(match_operand:MODEF 1 "register_operand" "x")
17571                        (match_operand:SI 2 "const_0_to_15_operand" "n")]
17572                       UNSPEC_ROUND))]
17573   "TARGET_ROUND"
17574   "rounds<ssemodefsuffix>\t{%2, %1, %0|%0, %1, %2}"
17575   [(set_attr "type" "ssecvt")
17576    (set_attr "prefix_extra" "1")
17577    (set_attr "mode" "<MODE>")])
17578
17579 (define_insn "rintxf2"
17580   [(set (match_operand:XF 0 "register_operand" "=f")
17581         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17582                    UNSPEC_FRNDINT))]
17583   "TARGET_USE_FANCY_MATH_387
17584    && flag_unsafe_math_optimizations"
17585   "frndint"
17586   [(set_attr "type" "fpspc")
17587    (set_attr "mode" "XF")])
17588
17589 (define_expand "rint<mode>2"
17590   [(use (match_operand:MODEF 0 "register_operand" ""))
17591    (use (match_operand:MODEF 1 "register_operand" ""))]
17592   "(TARGET_USE_FANCY_MATH_387
17593     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17594         || TARGET_MIX_SSE_I387)
17595     && flag_unsafe_math_optimizations)
17596    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17597        && !flag_trapping_math
17598        && (TARGET_ROUND || !optimize_size))"
17599 {
17600   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17601       && !flag_trapping_math
17602       && (TARGET_ROUND || !optimize_size))
17603     {
17604       if (TARGET_ROUND)
17605         emit_insn (gen_sse4_1_round<mode>2
17606                    (operands[0], operands[1], GEN_INT (0x04)));
17607       else
17608         ix86_expand_rint (operand0, operand1);
17609     }
17610   else
17611     {
17612       rtx op0 = gen_reg_rtx (XFmode);
17613       rtx op1 = gen_reg_rtx (XFmode);
17614
17615       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17616       emit_insn (gen_rintxf2 (op0, op1));
17617
17618       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17619     }
17620   DONE;
17621 })
17622
17623 (define_expand "round<mode>2"
17624   [(match_operand:MODEF 0 "register_operand" "")
17625    (match_operand:MODEF 1 "nonimmediate_operand" "")]
17626   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17627    && !flag_trapping_math && !flag_rounding_math
17628    && !optimize_size"
17629 {
17630   if (TARGET_64BIT || (<MODE>mode != DFmode))
17631     ix86_expand_round (operand0, operand1);
17632   else
17633     ix86_expand_rounddf_32 (operand0, operand1);
17634   DONE;
17635 })
17636
17637 (define_insn_and_split "*fistdi2_1"
17638   [(set (match_operand:DI 0 "nonimmediate_operand" "")
17639         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17640                    UNSPEC_FIST))]
17641   "TARGET_USE_FANCY_MATH_387
17642    && !(reload_completed || reload_in_progress)"
17643   "#"
17644   "&& 1"
17645   [(const_int 0)]
17646 {
17647   if (memory_operand (operands[0], VOIDmode))
17648     emit_insn (gen_fistdi2 (operands[0], operands[1]));
17649   else
17650     {
17651       operands[2] = assign_386_stack_local (DImode, SLOT_TEMP);
17652       emit_insn (gen_fistdi2_with_temp (operands[0], operands[1],
17653                                          operands[2]));
17654     }
17655   DONE;
17656 }
17657   [(set_attr "type" "fpspc")
17658    (set_attr "mode" "DI")])
17659
17660 (define_insn "fistdi2"
17661   [(set (match_operand:DI 0 "memory_operand" "=m")
17662         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
17663                    UNSPEC_FIST))
17664    (clobber (match_scratch:XF 2 "=&1f"))]
17665   "TARGET_USE_FANCY_MATH_387"
17666   "* return output_fix_trunc (insn, operands, 0);"
17667   [(set_attr "type" "fpspc")
17668    (set_attr "mode" "DI")])
17669
17670 (define_insn "fistdi2_with_temp"
17671   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
17672         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
17673                    UNSPEC_FIST))
17674    (clobber (match_operand:DI 2 "memory_operand" "=m,m"))
17675    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
17676   "TARGET_USE_FANCY_MATH_387"
17677   "#"
17678   [(set_attr "type" "fpspc")
17679    (set_attr "mode" "DI")])
17680
17681 (define_split
17682   [(set (match_operand:DI 0 "register_operand" "")
17683         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17684                    UNSPEC_FIST))
17685    (clobber (match_operand:DI 2 "memory_operand" ""))
17686    (clobber (match_scratch 3 ""))]
17687   "reload_completed"
17688   [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
17689               (clobber (match_dup 3))])
17690    (set (match_dup 0) (match_dup 2))]
17691   "")
17692
17693 (define_split
17694   [(set (match_operand:DI 0 "memory_operand" "")
17695         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17696                    UNSPEC_FIST))
17697    (clobber (match_operand:DI 2 "memory_operand" ""))
17698    (clobber (match_scratch 3 ""))]
17699   "reload_completed"
17700   [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
17701               (clobber (match_dup 3))])]
17702   "")
17703
17704 (define_insn_and_split "*fist<mode>2_1"
17705   [(set (match_operand:X87MODEI12 0 "register_operand" "")
17706         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17707                            UNSPEC_FIST))]
17708   "TARGET_USE_FANCY_MATH_387
17709    && !(reload_completed || reload_in_progress)"
17710   "#"
17711   "&& 1"
17712   [(const_int 0)]
17713 {
17714   operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
17715   emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1],
17716                                         operands[2]));
17717   DONE;
17718 }
17719   [(set_attr "type" "fpspc")
17720    (set_attr "mode" "<MODE>")])
17721
17722 (define_insn "fist<mode>2"
17723   [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
17724         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
17725                            UNSPEC_FIST))]
17726   "TARGET_USE_FANCY_MATH_387"
17727   "* return output_fix_trunc (insn, operands, 0);"
17728   [(set_attr "type" "fpspc")
17729    (set_attr "mode" "<MODE>")])
17730
17731 (define_insn "fist<mode>2_with_temp"
17732   [(set (match_operand:X87MODEI12 0 "register_operand" "=r")
17733         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
17734                            UNSPEC_FIST))
17735    (clobber (match_operand:X87MODEI12 2 "memory_operand" "=m"))]
17736   "TARGET_USE_FANCY_MATH_387"
17737   "#"
17738   [(set_attr "type" "fpspc")
17739    (set_attr "mode" "<MODE>")])
17740
17741 (define_split
17742   [(set (match_operand:X87MODEI12 0 "register_operand" "")
17743         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17744                            UNSPEC_FIST))
17745    (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
17746   "reload_completed"
17747   [(set (match_dup 2) (unspec:X87MODEI12 [(match_dup 1)] UNSPEC_FIST))
17748    (set (match_dup 0) (match_dup 2))]
17749   "")
17750
17751 (define_split
17752   [(set (match_operand:X87MODEI12 0 "memory_operand" "")
17753         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17754                            UNSPEC_FIST))
17755    (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
17756   "reload_completed"
17757   [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)] UNSPEC_FIST))]
17758   "")
17759
17760 (define_expand "lrintxf<mode>2"
17761   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
17762      (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
17763                       UNSPEC_FIST))]
17764   "TARGET_USE_FANCY_MATH_387"
17765   "")
17766
17767 (define_expand "lrint<MODEF:mode><SSEMODEI24:mode>2"
17768   [(set (match_operand:SSEMODEI24 0 "nonimmediate_operand" "")
17769      (unspec:SSEMODEI24 [(match_operand:MODEF 1 "register_operand" "")]
17770                         UNSPEC_FIX_NOTRUNC))]
17771   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
17772    && ((<SSEMODEI24:MODE>mode != DImode) || TARGET_64BIT)"
17773   "")
17774
17775 (define_expand "lround<MODEF:mode><SSEMODEI24:mode>2"
17776   [(match_operand:SSEMODEI24 0 "nonimmediate_operand" "")
17777    (match_operand:MODEF 1 "register_operand" "")]
17778   "SSE_FLOAT_MODE_P (<MODEF:MODE>mode) && TARGET_SSE_MATH
17779    && ((<SSEMODEI24:MODE>mode != DImode) || TARGET_64BIT)
17780    && !flag_trapping_math && !flag_rounding_math
17781    && !optimize_size"
17782 {
17783   ix86_expand_lround (operand0, operand1);
17784   DONE;
17785 })
17786
17787 ;; Rounding mode control word calculation could clobber FLAGS_REG.
17788 (define_insn_and_split "frndintxf2_floor"
17789   [(set (match_operand:XF 0 "register_operand" "")
17790         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
17791          UNSPEC_FRNDINT_FLOOR))
17792    (clobber (reg:CC FLAGS_REG))]
17793   "TARGET_USE_FANCY_MATH_387
17794    && flag_unsafe_math_optimizations
17795    && !(reload_completed || reload_in_progress)"
17796   "#"
17797   "&& 1"
17798   [(const_int 0)]
17799 {
17800   ix86_optimize_mode_switching[I387_FLOOR] = 1;
17801
17802   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17803   operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
17804
17805   emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1],
17806                                         operands[2], operands[3]));
17807   DONE;
17808 }
17809   [(set_attr "type" "frndint")
17810    (set_attr "i387_cw" "floor")
17811    (set_attr "mode" "XF")])
17812
17813 (define_insn "frndintxf2_floor_i387"
17814   [(set (match_operand:XF 0 "register_operand" "=f")
17815         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17816          UNSPEC_FRNDINT_FLOOR))
17817    (use (match_operand:HI 2 "memory_operand" "m"))
17818    (use (match_operand:HI 3 "memory_operand" "m"))]
17819   "TARGET_USE_FANCY_MATH_387
17820    && flag_unsafe_math_optimizations"
17821   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
17822   [(set_attr "type" "frndint")
17823    (set_attr "i387_cw" "floor")
17824    (set_attr "mode" "XF")])
17825
17826 (define_expand "floorxf2"
17827   [(use (match_operand:XF 0 "register_operand" ""))
17828    (use (match_operand:XF 1 "register_operand" ""))]
17829   "TARGET_USE_FANCY_MATH_387
17830    && flag_unsafe_math_optimizations && !optimize_size"
17831 {
17832   emit_insn (gen_frndintxf2_floor (operands[0], operands[1]));
17833   DONE;
17834 })
17835
17836 (define_expand "floor<mode>2"
17837   [(use (match_operand:MODEF 0 "register_operand" ""))
17838    (use (match_operand:MODEF 1 "register_operand" ""))]
17839   "(TARGET_USE_FANCY_MATH_387
17840     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
17841         || TARGET_MIX_SSE_I387)
17842     && flag_unsafe_math_optimizations && !optimize_size)
17843    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17844        && !flag_trapping_math
17845        && (TARGET_ROUND || !optimize_size))"
17846 {
17847   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
17848       && !flag_trapping_math
17849       && (TARGET_ROUND || !optimize_size))
17850     {
17851       if (TARGET_ROUND)
17852         emit_insn (gen_sse4_1_round<mode>2
17853                    (operands[0], operands[1], GEN_INT (0x01)));
17854       else if (TARGET_64BIT || (<MODE>mode != DFmode))
17855         ix86_expand_floorceil (operand0, operand1, true);
17856       else
17857         ix86_expand_floorceildf_32 (operand0, operand1, true);
17858     }
17859   else
17860     {
17861       rtx op0 = gen_reg_rtx (XFmode);
17862       rtx op1 = gen_reg_rtx (XFmode);
17863
17864       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
17865       emit_insn (gen_frndintxf2_floor (op0, op1));
17866
17867       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
17868     }
17869   DONE;
17870 })
17871
17872 (define_insn_and_split "*fist<mode>2_floor_1"
17873   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
17874         (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
17875          UNSPEC_FIST_FLOOR))
17876    (clobber (reg:CC FLAGS_REG))]
17877   "TARGET_USE_FANCY_MATH_387
17878    && flag_unsafe_math_optimizations
17879    && !(reload_completed || reload_in_progress)"
17880   "#"
17881   "&& 1"
17882   [(const_int 0)]
17883 {
17884   ix86_optimize_mode_switching[I387_FLOOR] = 1;
17885
17886   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17887   operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
17888   if (memory_operand (operands[0], VOIDmode))
17889     emit_insn (gen_fist<mode>2_floor (operands[0], operands[1],
17890                                       operands[2], operands[3]));
17891   else
17892     {
17893       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
17894       emit_insn (gen_fist<mode>2_floor_with_temp (operands[0], operands[1],
17895                                                   operands[2], operands[3],
17896                                                   operands[4]));
17897     }
17898   DONE;
17899 }
17900   [(set_attr "type" "fistp")
17901    (set_attr "i387_cw" "floor")
17902    (set_attr "mode" "<MODE>")])
17903
17904 (define_insn "fistdi2_floor"
17905   [(set (match_operand:DI 0 "memory_operand" "=m")
17906         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
17907          UNSPEC_FIST_FLOOR))
17908    (use (match_operand:HI 2 "memory_operand" "m"))
17909    (use (match_operand:HI 3 "memory_operand" "m"))
17910    (clobber (match_scratch:XF 4 "=&1f"))]
17911   "TARGET_USE_FANCY_MATH_387
17912    && flag_unsafe_math_optimizations"
17913   "* return output_fix_trunc (insn, operands, 0);"
17914   [(set_attr "type" "fistp")
17915    (set_attr "i387_cw" "floor")
17916    (set_attr "mode" "DI")])
17917
17918 (define_insn "fistdi2_floor_with_temp"
17919   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
17920         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
17921          UNSPEC_FIST_FLOOR))
17922    (use (match_operand:HI 2 "memory_operand" "m,m"))
17923    (use (match_operand:HI 3 "memory_operand" "m,m"))
17924    (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
17925    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
17926   "TARGET_USE_FANCY_MATH_387
17927    && flag_unsafe_math_optimizations"
17928   "#"
17929   [(set_attr "type" "fistp")
17930    (set_attr "i387_cw" "floor")
17931    (set_attr "mode" "DI")])
17932
17933 (define_split
17934   [(set (match_operand:DI 0 "register_operand" "")
17935         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17936          UNSPEC_FIST_FLOOR))
17937    (use (match_operand:HI 2 "memory_operand" ""))
17938    (use (match_operand:HI 3 "memory_operand" ""))
17939    (clobber (match_operand:DI 4 "memory_operand" ""))
17940    (clobber (match_scratch 5 ""))]
17941   "reload_completed"
17942   [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
17943               (use (match_dup 2))
17944               (use (match_dup 3))
17945               (clobber (match_dup 5))])
17946    (set (match_dup 0) (match_dup 4))]
17947   "")
17948
17949 (define_split
17950   [(set (match_operand:DI 0 "memory_operand" "")
17951         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17952          UNSPEC_FIST_FLOOR))
17953    (use (match_operand:HI 2 "memory_operand" ""))
17954    (use (match_operand:HI 3 "memory_operand" ""))
17955    (clobber (match_operand:DI 4 "memory_operand" ""))
17956    (clobber (match_scratch 5 ""))]
17957   "reload_completed"
17958   [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
17959               (use (match_dup 2))
17960               (use (match_dup 3))
17961               (clobber (match_dup 5))])]
17962   "")
17963
17964 (define_insn "fist<mode>2_floor"
17965   [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
17966         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
17967          UNSPEC_FIST_FLOOR))
17968    (use (match_operand:HI 2 "memory_operand" "m"))
17969    (use (match_operand:HI 3 "memory_operand" "m"))]
17970   "TARGET_USE_FANCY_MATH_387
17971    && flag_unsafe_math_optimizations"
17972   "* return output_fix_trunc (insn, operands, 0);"
17973   [(set_attr "type" "fistp")
17974    (set_attr "i387_cw" "floor")
17975    (set_attr "mode" "<MODE>")])
17976
17977 (define_insn "fist<mode>2_floor_with_temp"
17978   [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
17979         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
17980          UNSPEC_FIST_FLOOR))
17981    (use (match_operand:HI 2 "memory_operand" "m,m"))
17982    (use (match_operand:HI 3 "memory_operand" "m,m"))
17983    (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
17984   "TARGET_USE_FANCY_MATH_387
17985    && flag_unsafe_math_optimizations"
17986   "#"
17987   [(set_attr "type" "fistp")
17988    (set_attr "i387_cw" "floor")
17989    (set_attr "mode" "<MODE>")])
17990
17991 (define_split
17992   [(set (match_operand:X87MODEI12 0 "register_operand" "")
17993         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17994          UNSPEC_FIST_FLOOR))
17995    (use (match_operand:HI 2 "memory_operand" ""))
17996    (use (match_operand:HI 3 "memory_operand" ""))
17997    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
17998   "reload_completed"
17999   [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
18000                                   UNSPEC_FIST_FLOOR))
18001               (use (match_dup 2))
18002               (use (match_dup 3))])
18003    (set (match_dup 0) (match_dup 4))]
18004   "")
18005
18006 (define_split
18007   [(set (match_operand:X87MODEI12 0 "memory_operand" "")
18008         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18009          UNSPEC_FIST_FLOOR))
18010    (use (match_operand:HI 2 "memory_operand" ""))
18011    (use (match_operand:HI 3 "memory_operand" ""))
18012    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
18013   "reload_completed"
18014   [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
18015                                   UNSPEC_FIST_FLOOR))
18016               (use (match_dup 2))
18017               (use (match_dup 3))])]
18018   "")
18019
18020 (define_expand "lfloorxf<mode>2"
18021   [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
18022                    (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
18023                     UNSPEC_FIST_FLOOR))
18024               (clobber (reg:CC FLAGS_REG))])]
18025   "TARGET_USE_FANCY_MATH_387
18026    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
18027    && flag_unsafe_math_optimizations"
18028   "")
18029
18030 (define_expand "lfloor<mode>di2"
18031   [(match_operand:DI 0 "nonimmediate_operand" "")
18032    (match_operand:MODEF 1 "register_operand" "")]
18033   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH && TARGET_64BIT
18034    && !flag_trapping_math
18035    && !optimize_size"
18036 {
18037   ix86_expand_lfloorceil (operand0, operand1, true);
18038   DONE;
18039 })
18040
18041 (define_expand "lfloor<mode>si2"
18042   [(match_operand:SI 0 "nonimmediate_operand" "")
18043    (match_operand:MODEF 1 "register_operand" "")]
18044   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18045    && !flag_trapping_math
18046    && (!optimize_size || !TARGET_64BIT)"
18047 {
18048   ix86_expand_lfloorceil (operand0, operand1, true);
18049   DONE;
18050 })
18051
18052 ;; Rounding mode control word calculation could clobber FLAGS_REG.
18053 (define_insn_and_split "frndintxf2_ceil"
18054   [(set (match_operand:XF 0 "register_operand" "")
18055         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
18056          UNSPEC_FRNDINT_CEIL))
18057    (clobber (reg:CC FLAGS_REG))]
18058   "TARGET_USE_FANCY_MATH_387
18059    && flag_unsafe_math_optimizations
18060    && !(reload_completed || reload_in_progress)"
18061   "#"
18062   "&& 1"
18063   [(const_int 0)]
18064 {
18065   ix86_optimize_mode_switching[I387_CEIL] = 1;
18066
18067   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18068   operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
18069
18070   emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1],
18071                                        operands[2], operands[3]));
18072   DONE;
18073 }
18074   [(set_attr "type" "frndint")
18075    (set_attr "i387_cw" "ceil")
18076    (set_attr "mode" "XF")])
18077
18078 (define_insn "frndintxf2_ceil_i387"
18079   [(set (match_operand:XF 0 "register_operand" "=f")
18080         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
18081          UNSPEC_FRNDINT_CEIL))
18082    (use (match_operand:HI 2 "memory_operand" "m"))
18083    (use (match_operand:HI 3 "memory_operand" "m"))]
18084   "TARGET_USE_FANCY_MATH_387
18085    && flag_unsafe_math_optimizations"
18086   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
18087   [(set_attr "type" "frndint")
18088    (set_attr "i387_cw" "ceil")
18089    (set_attr "mode" "XF")])
18090
18091 (define_expand "ceilxf2"
18092   [(use (match_operand:XF 0 "register_operand" ""))
18093    (use (match_operand:XF 1 "register_operand" ""))]
18094   "TARGET_USE_FANCY_MATH_387
18095    && flag_unsafe_math_optimizations && !optimize_size"
18096 {
18097   emit_insn (gen_frndintxf2_ceil (operands[0], operands[1]));
18098   DONE;
18099 })
18100
18101 (define_expand "ceil<mode>2"
18102   [(use (match_operand:MODEF 0 "register_operand" ""))
18103    (use (match_operand:MODEF 1 "register_operand" ""))]
18104   "(TARGET_USE_FANCY_MATH_387
18105     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18106         || TARGET_MIX_SSE_I387)
18107     && flag_unsafe_math_optimizations && !optimize_size)
18108    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18109        && !flag_trapping_math
18110        && (TARGET_ROUND || !optimize_size))"
18111 {
18112   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18113       && !flag_trapping_math
18114       && (TARGET_ROUND || !optimize_size))
18115     {
18116       if (TARGET_ROUND)
18117         emit_insn (gen_sse4_1_round<mode>2
18118                    (operands[0], operands[1], GEN_INT (0x02)));
18119       else if (TARGET_64BIT || (<MODE>mode != DFmode))
18120         ix86_expand_floorceil (operand0, operand1, false);
18121       else
18122         ix86_expand_floorceildf_32 (operand0, operand1, false);
18123     }
18124   else
18125     {
18126       rtx op0 = gen_reg_rtx (XFmode);
18127       rtx op1 = gen_reg_rtx (XFmode);
18128
18129       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18130       emit_insn (gen_frndintxf2_ceil (op0, op1));
18131
18132       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18133     }
18134   DONE;
18135 })
18136
18137 (define_insn_and_split "*fist<mode>2_ceil_1"
18138   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
18139         (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
18140          UNSPEC_FIST_CEIL))
18141    (clobber (reg:CC FLAGS_REG))]
18142   "TARGET_USE_FANCY_MATH_387
18143    && flag_unsafe_math_optimizations
18144    && !(reload_completed || reload_in_progress)"
18145   "#"
18146   "&& 1"
18147   [(const_int 0)]
18148 {
18149   ix86_optimize_mode_switching[I387_CEIL] = 1;
18150
18151   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18152   operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
18153   if (memory_operand (operands[0], VOIDmode))
18154     emit_insn (gen_fist<mode>2_ceil (operands[0], operands[1],
18155                                      operands[2], operands[3]));
18156   else
18157     {
18158       operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
18159       emit_insn (gen_fist<mode>2_ceil_with_temp (operands[0], operands[1],
18160                                                  operands[2], operands[3],
18161                                                  operands[4]));
18162     }
18163   DONE;
18164 }
18165   [(set_attr "type" "fistp")
18166    (set_attr "i387_cw" "ceil")
18167    (set_attr "mode" "<MODE>")])
18168
18169 (define_insn "fistdi2_ceil"
18170   [(set (match_operand:DI 0 "memory_operand" "=m")
18171         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
18172          UNSPEC_FIST_CEIL))
18173    (use (match_operand:HI 2 "memory_operand" "m"))
18174    (use (match_operand:HI 3 "memory_operand" "m"))
18175    (clobber (match_scratch:XF 4 "=&1f"))]
18176   "TARGET_USE_FANCY_MATH_387
18177    && flag_unsafe_math_optimizations"
18178   "* return output_fix_trunc (insn, operands, 0);"
18179   [(set_attr "type" "fistp")
18180    (set_attr "i387_cw" "ceil")
18181    (set_attr "mode" "DI")])
18182
18183 (define_insn "fistdi2_ceil_with_temp"
18184   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
18185         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
18186          UNSPEC_FIST_CEIL))
18187    (use (match_operand:HI 2 "memory_operand" "m,m"))
18188    (use (match_operand:HI 3 "memory_operand" "m,m"))
18189    (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
18190    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
18191   "TARGET_USE_FANCY_MATH_387
18192    && flag_unsafe_math_optimizations"
18193   "#"
18194   [(set_attr "type" "fistp")
18195    (set_attr "i387_cw" "ceil")
18196    (set_attr "mode" "DI")])
18197
18198 (define_split
18199   [(set (match_operand:DI 0 "register_operand" "")
18200         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
18201          UNSPEC_FIST_CEIL))
18202    (use (match_operand:HI 2 "memory_operand" ""))
18203    (use (match_operand:HI 3 "memory_operand" ""))
18204    (clobber (match_operand:DI 4 "memory_operand" ""))
18205    (clobber (match_scratch 5 ""))]
18206   "reload_completed"
18207   [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
18208               (use (match_dup 2))
18209               (use (match_dup 3))
18210               (clobber (match_dup 5))])
18211    (set (match_dup 0) (match_dup 4))]
18212   "")
18213
18214 (define_split
18215   [(set (match_operand:DI 0 "memory_operand" "")
18216         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
18217          UNSPEC_FIST_CEIL))
18218    (use (match_operand:HI 2 "memory_operand" ""))
18219    (use (match_operand:HI 3 "memory_operand" ""))
18220    (clobber (match_operand:DI 4 "memory_operand" ""))
18221    (clobber (match_scratch 5 ""))]
18222   "reload_completed"
18223   [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
18224               (use (match_dup 2))
18225               (use (match_dup 3))
18226               (clobber (match_dup 5))])]
18227   "")
18228
18229 (define_insn "fist<mode>2_ceil"
18230   [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
18231         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
18232          UNSPEC_FIST_CEIL))
18233    (use (match_operand:HI 2 "memory_operand" "m"))
18234    (use (match_operand:HI 3 "memory_operand" "m"))]
18235   "TARGET_USE_FANCY_MATH_387
18236    && flag_unsafe_math_optimizations"
18237   "* return output_fix_trunc (insn, operands, 0);"
18238   [(set_attr "type" "fistp")
18239    (set_attr "i387_cw" "ceil")
18240    (set_attr "mode" "<MODE>")])
18241
18242 (define_insn "fist<mode>2_ceil_with_temp"
18243   [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
18244         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
18245          UNSPEC_FIST_CEIL))
18246    (use (match_operand:HI 2 "memory_operand" "m,m"))
18247    (use (match_operand:HI 3 "memory_operand" "m,m"))
18248    (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
18249   "TARGET_USE_FANCY_MATH_387
18250    && flag_unsafe_math_optimizations"
18251   "#"
18252   [(set_attr "type" "fistp")
18253    (set_attr "i387_cw" "ceil")
18254    (set_attr "mode" "<MODE>")])
18255
18256 (define_split
18257   [(set (match_operand:X87MODEI12 0 "register_operand" "")
18258         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18259          UNSPEC_FIST_CEIL))
18260    (use (match_operand:HI 2 "memory_operand" ""))
18261    (use (match_operand:HI 3 "memory_operand" ""))
18262    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
18263   "reload_completed"
18264   [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
18265                                   UNSPEC_FIST_CEIL))
18266               (use (match_dup 2))
18267               (use (match_dup 3))])
18268    (set (match_dup 0) (match_dup 4))]
18269   "")
18270
18271 (define_split
18272   [(set (match_operand:X87MODEI12 0 "memory_operand" "")
18273         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
18274          UNSPEC_FIST_CEIL))
18275    (use (match_operand:HI 2 "memory_operand" ""))
18276    (use (match_operand:HI 3 "memory_operand" ""))
18277    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
18278   "reload_completed"
18279   [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
18280                                   UNSPEC_FIST_CEIL))
18281               (use (match_dup 2))
18282               (use (match_dup 3))])]
18283   "")
18284
18285 (define_expand "lceilxf<mode>2"
18286   [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
18287                    (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
18288                     UNSPEC_FIST_CEIL))
18289               (clobber (reg:CC FLAGS_REG))])]
18290   "TARGET_USE_FANCY_MATH_387
18291    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
18292    && flag_unsafe_math_optimizations"
18293   "")
18294
18295 (define_expand "lceil<mode>di2"
18296   [(match_operand:DI 0 "nonimmediate_operand" "")
18297    (match_operand:MODEF 1 "register_operand" "")]
18298   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH && TARGET_64BIT
18299    && !flag_trapping_math"
18300 {
18301   ix86_expand_lfloorceil (operand0, operand1, false);
18302   DONE;
18303 })
18304
18305 (define_expand "lceil<mode>si2"
18306   [(match_operand:SI 0 "nonimmediate_operand" "")
18307    (match_operand:MODEF 1 "register_operand" "")]
18308   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18309    && !flag_trapping_math"
18310 {
18311   ix86_expand_lfloorceil (operand0, operand1, false);
18312   DONE;
18313 })
18314
18315 ;; Rounding mode control word calculation could clobber FLAGS_REG.
18316 (define_insn_and_split "frndintxf2_trunc"
18317   [(set (match_operand:XF 0 "register_operand" "")
18318         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
18319          UNSPEC_FRNDINT_TRUNC))
18320    (clobber (reg:CC FLAGS_REG))]
18321   "TARGET_USE_FANCY_MATH_387
18322    && flag_unsafe_math_optimizations
18323    && !(reload_completed || reload_in_progress)"
18324   "#"
18325   "&& 1"
18326   [(const_int 0)]
18327 {
18328   ix86_optimize_mode_switching[I387_TRUNC] = 1;
18329
18330   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18331   operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
18332
18333   emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1],
18334                                         operands[2], operands[3]));
18335   DONE;
18336 }
18337   [(set_attr "type" "frndint")
18338    (set_attr "i387_cw" "trunc")
18339    (set_attr "mode" "XF")])
18340
18341 (define_insn "frndintxf2_trunc_i387"
18342   [(set (match_operand:XF 0 "register_operand" "=f")
18343         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
18344          UNSPEC_FRNDINT_TRUNC))
18345    (use (match_operand:HI 2 "memory_operand" "m"))
18346    (use (match_operand:HI 3 "memory_operand" "m"))]
18347   "TARGET_USE_FANCY_MATH_387
18348    && flag_unsafe_math_optimizations"
18349   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
18350   [(set_attr "type" "frndint")
18351    (set_attr "i387_cw" "trunc")
18352    (set_attr "mode" "XF")])
18353
18354 (define_expand "btruncxf2"
18355   [(use (match_operand:XF 0 "register_operand" ""))
18356    (use (match_operand:XF 1 "register_operand" ""))]
18357   "TARGET_USE_FANCY_MATH_387
18358    && flag_unsafe_math_optimizations && !optimize_size"
18359 {
18360   emit_insn (gen_frndintxf2_trunc (operands[0], operands[1]));
18361   DONE;
18362 })
18363
18364 (define_expand "btrunc<mode>2"
18365   [(use (match_operand:MODEF 0 "register_operand" ""))
18366    (use (match_operand:MODEF 1 "register_operand" ""))]
18367   "(TARGET_USE_FANCY_MATH_387
18368     && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18369         || TARGET_MIX_SSE_I387)
18370     && flag_unsafe_math_optimizations && !optimize_size)
18371    || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18372        && !flag_trapping_math
18373        && (TARGET_ROUND || !optimize_size))"
18374 {
18375   if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH
18376       && !flag_trapping_math
18377       && (TARGET_ROUND || !optimize_size))
18378     {
18379       if (TARGET_ROUND)
18380         emit_insn (gen_sse4_1_round<mode>2
18381                    (operands[0], operands[1], GEN_INT (0x03)));
18382       else if (TARGET_64BIT || (<MODE>mode != DFmode))
18383         ix86_expand_trunc (operand0, operand1);
18384       else
18385         ix86_expand_truncdf_32 (operand0, operand1);
18386     }
18387   else
18388     {
18389       rtx op0 = gen_reg_rtx (XFmode);
18390       rtx op1 = gen_reg_rtx (XFmode);
18391
18392       emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18393       emit_insn (gen_frndintxf2_trunc (op0, op1));
18394
18395       emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18396     }
18397   DONE;
18398 })
18399
18400 ;; Rounding mode control word calculation could clobber FLAGS_REG.
18401 (define_insn_and_split "frndintxf2_mask_pm"
18402   [(set (match_operand:XF 0 "register_operand" "")
18403         (unspec:XF [(match_operand:XF 1 "register_operand" "")]
18404          UNSPEC_FRNDINT_MASK_PM))
18405    (clobber (reg:CC FLAGS_REG))]
18406   "TARGET_USE_FANCY_MATH_387
18407    && flag_unsafe_math_optimizations
18408    && !(reload_completed || reload_in_progress)"
18409   "#"
18410   "&& 1"
18411   [(const_int 0)]
18412 {
18413   ix86_optimize_mode_switching[I387_MASK_PM] = 1;
18414
18415   operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
18416   operands[3] = assign_386_stack_local (HImode, SLOT_CW_MASK_PM);
18417
18418   emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1],
18419                                           operands[2], operands[3]));
18420   DONE;
18421 }
18422   [(set_attr "type" "frndint")
18423    (set_attr "i387_cw" "mask_pm")
18424    (set_attr "mode" "XF")])
18425
18426 (define_insn "frndintxf2_mask_pm_i387"
18427   [(set (match_operand:XF 0 "register_operand" "=f")
18428         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
18429          UNSPEC_FRNDINT_MASK_PM))
18430    (use (match_operand:HI 2 "memory_operand" "m"))
18431    (use (match_operand:HI 3 "memory_operand" "m"))]
18432   "TARGET_USE_FANCY_MATH_387
18433    && flag_unsafe_math_optimizations"
18434   "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2"
18435   [(set_attr "type" "frndint")
18436    (set_attr "i387_cw" "mask_pm")
18437    (set_attr "mode" "XF")])
18438
18439 (define_expand "nearbyintxf2"
18440   [(use (match_operand:XF 0 "register_operand" ""))
18441    (use (match_operand:XF 1 "register_operand" ""))]
18442   "TARGET_USE_FANCY_MATH_387
18443    && flag_unsafe_math_optimizations"
18444 {
18445   emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1]));
18446
18447   DONE;
18448 })
18449
18450 (define_expand "nearbyint<mode>2"
18451   [(use (match_operand:MODEF 0 "register_operand" ""))
18452    (use (match_operand:MODEF 1 "register_operand" ""))]
18453   "TARGET_USE_FANCY_MATH_387
18454    && (!(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)
18455        || TARGET_MIX_SSE_I387)
18456    && flag_unsafe_math_optimizations"
18457 {
18458   rtx op0 = gen_reg_rtx (XFmode);
18459   rtx op1 = gen_reg_rtx (XFmode);
18460
18461   emit_insn (gen_extend<mode>xf2 (op1, operands[1]));
18462   emit_insn (gen_frndintxf2_mask_pm (op0, op1));
18463
18464   emit_insn (gen_truncxf<mode>2_i387_noop (operands[0], op0));
18465   DONE;
18466 })
18467
18468 (define_insn "fxam<mode>2_i387"
18469   [(set (match_operand:HI 0 "register_operand" "=a")
18470         (unspec:HI
18471           [(match_operand:X87MODEF 1 "register_operand" "f")]
18472           UNSPEC_FXAM))]
18473   "TARGET_USE_FANCY_MATH_387"
18474   "fxam\n\tfnstsw\t%0"
18475   [(set_attr "type" "multi")
18476    (set_attr "unit" "i387")
18477    (set_attr "mode" "<MODE>")])
18478
18479 (define_expand "isinf<mode>2"
18480   [(use (match_operand:SI 0 "register_operand" ""))
18481    (use (match_operand:X87MODEF 1 "register_operand" ""))]
18482   "TARGET_USE_FANCY_MATH_387
18483    && TARGET_C99_FUNCTIONS
18484    && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
18485 {
18486   rtx mask = GEN_INT (0x45);
18487   rtx val = GEN_INT (0x05);
18488
18489   rtx cond;
18490
18491   rtx scratch = gen_reg_rtx (HImode);
18492   rtx res = gen_reg_rtx (QImode);
18493
18494   emit_insn (gen_fxam<mode>2_i387 (scratch, operands[1]));
18495   emit_insn (gen_andqi_ext_0 (scratch, scratch, mask));
18496   emit_insn (gen_cmpqi_ext_3 (scratch, val));
18497   cond = gen_rtx_fmt_ee (EQ, QImode,
18498                          gen_rtx_REG (CCmode, FLAGS_REG),
18499                          const0_rtx);
18500   emit_insn (gen_rtx_SET (VOIDmode, res, cond));
18501   emit_insn (gen_zero_extendqisi2 (operands[0], res));
18502   DONE;
18503 })
18504
18505 (define_expand "signbit<mode>2"
18506   [(use (match_operand:SI 0 "register_operand" ""))
18507    (use (match_operand:X87MODEF 1 "register_operand" ""))]
18508   "TARGET_USE_FANCY_MATH_387
18509    && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH)"
18510 {
18511   rtx mask = GEN_INT (0x0200);
18512
18513   rtx scratch = gen_reg_rtx (HImode);
18514
18515   emit_insn (gen_fxam<mode>2_i387 (scratch, operands[1]));
18516   emit_insn (gen_andsi3 (operands[0], gen_lowpart (SImode, scratch), mask));
18517   DONE;
18518 })
18519 \f
18520 ;; Block operation instructions
18521
18522 (define_expand "movmemsi"
18523   [(use (match_operand:BLK 0 "memory_operand" ""))
18524    (use (match_operand:BLK 1 "memory_operand" ""))
18525    (use (match_operand:SI 2 "nonmemory_operand" ""))
18526    (use (match_operand:SI 3 "const_int_operand" ""))
18527    (use (match_operand:SI 4 "const_int_operand" ""))
18528    (use (match_operand:SI 5 "const_int_operand" ""))]
18529   ""
18530 {
18531  if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3],
18532                          operands[4], operands[5]))
18533    DONE;
18534  else
18535    FAIL;
18536 })
18537
18538 (define_expand "movmemdi"
18539   [(use (match_operand:BLK 0 "memory_operand" ""))
18540    (use (match_operand:BLK 1 "memory_operand" ""))
18541    (use (match_operand:DI 2 "nonmemory_operand" ""))
18542    (use (match_operand:DI 3 "const_int_operand" ""))
18543    (use (match_operand:SI 4 "const_int_operand" ""))
18544    (use (match_operand:SI 5 "const_int_operand" ""))]
18545   "TARGET_64BIT"
18546 {
18547  if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3],
18548                          operands[4], operands[5]))
18549    DONE;
18550  else
18551    FAIL;
18552 })
18553
18554 ;; Most CPUs don't like single string operations
18555 ;; Handle this case here to simplify previous expander.
18556
18557 (define_expand "strmov"
18558   [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
18559    (set (match_operand 1 "memory_operand" "") (match_dup 4))
18560    (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
18561               (clobber (reg:CC FLAGS_REG))])
18562    (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
18563               (clobber (reg:CC FLAGS_REG))])]
18564   ""
18565 {
18566   rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
18567
18568   /* If .md ever supports :P for Pmode, these can be directly
18569      in the pattern above.  */
18570   operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
18571   operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
18572
18573   /* Can't use this if the user has appropriated esi or edi.  */
18574   if ((TARGET_SINGLE_STRINGOP || optimize_size)
18575       && !(fixed_regs[SI_REG] || fixed_regs[DI_REG]))
18576     {
18577       emit_insn (gen_strmov_singleop (operands[0], operands[1],
18578                                       operands[2], operands[3],
18579                                       operands[5], operands[6]));
18580       DONE;
18581     }
18582
18583   operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
18584 })
18585
18586 (define_expand "strmov_singleop"
18587   [(parallel [(set (match_operand 1 "memory_operand" "")
18588                    (match_operand 3 "memory_operand" ""))
18589               (set (match_operand 0 "register_operand" "")
18590                    (match_operand 4 "" ""))
18591               (set (match_operand 2 "register_operand" "")
18592                    (match_operand 5 "" ""))])]
18593   "TARGET_SINGLE_STRINGOP || optimize_size"
18594   "")
18595
18596 (define_insn "*strmovdi_rex_1"
18597   [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
18598         (mem:DI (match_operand:DI 3 "register_operand" "1")))
18599    (set (match_operand:DI 0 "register_operand" "=D")
18600         (plus:DI (match_dup 2)
18601                  (const_int 8)))
18602    (set (match_operand:DI 1 "register_operand" "=S")
18603         (plus:DI (match_dup 3)
18604                  (const_int 8)))]
18605   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18606   "movsq"
18607   [(set_attr "type" "str")
18608    (set_attr "mode" "DI")
18609    (set_attr "memory" "both")])
18610
18611 (define_insn "*strmovsi_1"
18612   [(set (mem:SI (match_operand:SI 2 "register_operand" "0"))
18613         (mem:SI (match_operand:SI 3 "register_operand" "1")))
18614    (set (match_operand:SI 0 "register_operand" "=D")
18615         (plus:SI (match_dup 2)
18616                  (const_int 4)))
18617    (set (match_operand:SI 1 "register_operand" "=S")
18618         (plus:SI (match_dup 3)
18619                  (const_int 4)))]
18620   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18621   "{movsl|movsd}"
18622   [(set_attr "type" "str")
18623    (set_attr "mode" "SI")
18624    (set_attr "memory" "both")])
18625
18626 (define_insn "*strmovsi_rex_1"
18627   [(set (mem:SI (match_operand:DI 2 "register_operand" "0"))
18628         (mem:SI (match_operand:DI 3 "register_operand" "1")))
18629    (set (match_operand:DI 0 "register_operand" "=D")
18630         (plus:DI (match_dup 2)
18631                  (const_int 4)))
18632    (set (match_operand:DI 1 "register_operand" "=S")
18633         (plus:DI (match_dup 3)
18634                  (const_int 4)))]
18635   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18636   "{movsl|movsd}"
18637   [(set_attr "type" "str")
18638    (set_attr "mode" "SI")
18639    (set_attr "memory" "both")])
18640
18641 (define_insn "*strmovhi_1"
18642   [(set (mem:HI (match_operand:SI 2 "register_operand" "0"))
18643         (mem:HI (match_operand:SI 3 "register_operand" "1")))
18644    (set (match_operand:SI 0 "register_operand" "=D")
18645         (plus:SI (match_dup 2)
18646                  (const_int 2)))
18647    (set (match_operand:SI 1 "register_operand" "=S")
18648         (plus:SI (match_dup 3)
18649                  (const_int 2)))]
18650   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18651   "movsw"
18652   [(set_attr "type" "str")
18653    (set_attr "memory" "both")
18654    (set_attr "mode" "HI")])
18655
18656 (define_insn "*strmovhi_rex_1"
18657   [(set (mem:HI (match_operand:DI 2 "register_operand" "0"))
18658         (mem:HI (match_operand:DI 3 "register_operand" "1")))
18659    (set (match_operand:DI 0 "register_operand" "=D")
18660         (plus:DI (match_dup 2)
18661                  (const_int 2)))
18662    (set (match_operand:DI 1 "register_operand" "=S")
18663         (plus:DI (match_dup 3)
18664                  (const_int 2)))]
18665   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18666   "movsw"
18667   [(set_attr "type" "str")
18668    (set_attr "memory" "both")
18669    (set_attr "mode" "HI")])
18670
18671 (define_insn "*strmovqi_1"
18672   [(set (mem:QI (match_operand:SI 2 "register_operand" "0"))
18673         (mem:QI (match_operand:SI 3 "register_operand" "1")))
18674    (set (match_operand:SI 0 "register_operand" "=D")
18675         (plus:SI (match_dup 2)
18676                  (const_int 1)))
18677    (set (match_operand:SI 1 "register_operand" "=S")
18678         (plus:SI (match_dup 3)
18679                  (const_int 1)))]
18680   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18681   "movsb"
18682   [(set_attr "type" "str")
18683    (set_attr "memory" "both")
18684    (set_attr "mode" "QI")])
18685
18686 (define_insn "*strmovqi_rex_1"
18687   [(set (mem:QI (match_operand:DI 2 "register_operand" "0"))
18688         (mem:QI (match_operand:DI 3 "register_operand" "1")))
18689    (set (match_operand:DI 0 "register_operand" "=D")
18690         (plus:DI (match_dup 2)
18691                  (const_int 1)))
18692    (set (match_operand:DI 1 "register_operand" "=S")
18693         (plus:DI (match_dup 3)
18694                  (const_int 1)))]
18695   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18696   "movsb"
18697   [(set_attr "type" "str")
18698    (set_attr "memory" "both")
18699    (set_attr "mode" "QI")])
18700
18701 (define_expand "rep_mov"
18702   [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
18703               (set (match_operand 0 "register_operand" "")
18704                    (match_operand 5 "" ""))
18705               (set (match_operand 2 "register_operand" "")
18706                    (match_operand 6 "" ""))
18707               (set (match_operand 1 "memory_operand" "")
18708                    (match_operand 3 "memory_operand" ""))
18709               (use (match_dup 4))])]
18710   ""
18711   "")
18712
18713 (define_insn "*rep_movdi_rex64"
18714   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
18715    (set (match_operand:DI 0 "register_operand" "=D")
18716         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
18717                             (const_int 3))
18718                  (match_operand:DI 3 "register_operand" "0")))
18719    (set (match_operand:DI 1 "register_operand" "=S")
18720         (plus:DI (ashift:DI (match_dup 5) (const_int 3))
18721                  (match_operand:DI 4 "register_operand" "1")))
18722    (set (mem:BLK (match_dup 3))
18723         (mem:BLK (match_dup 4)))
18724    (use (match_dup 5))]
18725   "TARGET_64BIT"
18726   "rep movsq"
18727   [(set_attr "type" "str")
18728    (set_attr "prefix_rep" "1")
18729    (set_attr "memory" "both")
18730    (set_attr "mode" "DI")])
18731
18732 (define_insn "*rep_movsi"
18733   [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
18734    (set (match_operand:SI 0 "register_operand" "=D")
18735         (plus:SI (ashift:SI (match_operand:SI 5 "register_operand" "2")
18736                             (const_int 2))
18737                  (match_operand:SI 3 "register_operand" "0")))
18738    (set (match_operand:SI 1 "register_operand" "=S")
18739         (plus:SI (ashift:SI (match_dup 5) (const_int 2))
18740                  (match_operand:SI 4 "register_operand" "1")))
18741    (set (mem:BLK (match_dup 3))
18742         (mem:BLK (match_dup 4)))
18743    (use (match_dup 5))]
18744   "!TARGET_64BIT"
18745   "rep movs{l|d}"
18746   [(set_attr "type" "str")
18747    (set_attr "prefix_rep" "1")
18748    (set_attr "memory" "both")
18749    (set_attr "mode" "SI")])
18750
18751 (define_insn "*rep_movsi_rex64"
18752   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
18753    (set (match_operand:DI 0 "register_operand" "=D")
18754         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
18755                             (const_int 2))
18756                  (match_operand:DI 3 "register_operand" "0")))
18757    (set (match_operand:DI 1 "register_operand" "=S")
18758         (plus:DI (ashift:DI (match_dup 5) (const_int 2))
18759                  (match_operand:DI 4 "register_operand" "1")))
18760    (set (mem:BLK (match_dup 3))
18761         (mem:BLK (match_dup 4)))
18762    (use (match_dup 5))]
18763   "TARGET_64BIT"
18764   "rep movs{l|d}"
18765   [(set_attr "type" "str")
18766    (set_attr "prefix_rep" "1")
18767    (set_attr "memory" "both")
18768    (set_attr "mode" "SI")])
18769
18770 (define_insn "*rep_movqi"
18771   [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
18772    (set (match_operand:SI 0 "register_operand" "=D")
18773         (plus:SI (match_operand:SI 3 "register_operand" "0")
18774                  (match_operand:SI 5 "register_operand" "2")))
18775    (set (match_operand:SI 1 "register_operand" "=S")
18776         (plus:SI (match_operand:SI 4 "register_operand" "1") (match_dup 5)))
18777    (set (mem:BLK (match_dup 3))
18778         (mem:BLK (match_dup 4)))
18779    (use (match_dup 5))]
18780   "!TARGET_64BIT"
18781   "rep movsb"
18782   [(set_attr "type" "str")
18783    (set_attr "prefix_rep" "1")
18784    (set_attr "memory" "both")
18785    (set_attr "mode" "SI")])
18786
18787 (define_insn "*rep_movqi_rex64"
18788   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
18789    (set (match_operand:DI 0 "register_operand" "=D")
18790         (plus:DI (match_operand:DI 3 "register_operand" "0")
18791                  (match_operand:DI 5 "register_operand" "2")))
18792    (set (match_operand:DI 1 "register_operand" "=S")
18793         (plus:DI (match_operand:DI 4 "register_operand" "1") (match_dup 5)))
18794    (set (mem:BLK (match_dup 3))
18795         (mem:BLK (match_dup 4)))
18796    (use (match_dup 5))]
18797   "TARGET_64BIT"
18798   "rep movsb"
18799   [(set_attr "type" "str")
18800    (set_attr "prefix_rep" "1")
18801    (set_attr "memory" "both")
18802    (set_attr "mode" "SI")])
18803
18804 (define_expand "setmemsi"
18805    [(use (match_operand:BLK 0 "memory_operand" ""))
18806     (use (match_operand:SI 1 "nonmemory_operand" ""))
18807     (use (match_operand 2 "const_int_operand" ""))
18808     (use (match_operand 3 "const_int_operand" ""))
18809     (use (match_operand:SI 4 "const_int_operand" ""))
18810     (use (match_operand:SI 5 "const_int_operand" ""))]
18811   ""
18812 {
18813  if (ix86_expand_setmem (operands[0], operands[1],
18814                          operands[2], operands[3],
18815                          operands[4], operands[5]))
18816    DONE;
18817  else
18818    FAIL;
18819 })
18820
18821 (define_expand "setmemdi"
18822    [(use (match_operand:BLK 0 "memory_operand" ""))
18823     (use (match_operand:DI 1 "nonmemory_operand" ""))
18824     (use (match_operand 2 "const_int_operand" ""))
18825     (use (match_operand 3 "const_int_operand" ""))
18826     (use (match_operand 4 "const_int_operand" ""))
18827     (use (match_operand 5 "const_int_operand" ""))]
18828   "TARGET_64BIT"
18829 {
18830  if (ix86_expand_setmem (operands[0], operands[1],
18831                          operands[2], operands[3],
18832                          operands[4], operands[5]))
18833    DONE;
18834  else
18835    FAIL;
18836 })
18837
18838 ;; Most CPUs don't like single string operations
18839 ;; Handle this case here to simplify previous expander.
18840
18841 (define_expand "strset"
18842   [(set (match_operand 1 "memory_operand" "")
18843         (match_operand 2 "register_operand" ""))
18844    (parallel [(set (match_operand 0 "register_operand" "")
18845                    (match_dup 3))
18846               (clobber (reg:CC FLAGS_REG))])]
18847   ""
18848 {
18849   if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
18850     operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
18851
18852   /* If .md ever supports :P for Pmode, this can be directly
18853      in the pattern above.  */
18854   operands[3] = gen_rtx_PLUS (Pmode, operands[0],
18855                               GEN_INT (GET_MODE_SIZE (GET_MODE
18856                                                       (operands[2]))));
18857   if (TARGET_SINGLE_STRINGOP || optimize_size)
18858     {
18859       emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
18860                                       operands[3]));
18861       DONE;
18862     }
18863 })
18864
18865 (define_expand "strset_singleop"
18866   [(parallel [(set (match_operand 1 "memory_operand" "")
18867                    (match_operand 2 "register_operand" ""))
18868               (set (match_operand 0 "register_operand" "")
18869                    (match_operand 3 "" ""))])]
18870   "TARGET_SINGLE_STRINGOP || optimize_size"
18871   "")
18872
18873 (define_insn "*strsetdi_rex_1"
18874   [(set (mem:DI (match_operand:DI 1 "register_operand" "0"))
18875         (match_operand:DI 2 "register_operand" "a"))
18876    (set (match_operand:DI 0 "register_operand" "=D")
18877         (plus:DI (match_dup 1)
18878                  (const_int 8)))]
18879   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18880   "stosq"
18881   [(set_attr "type" "str")
18882    (set_attr "memory" "store")
18883    (set_attr "mode" "DI")])
18884
18885 (define_insn "*strsetsi_1"
18886   [(set (mem:SI (match_operand:SI 1 "register_operand" "0"))
18887         (match_operand:SI 2 "register_operand" "a"))
18888    (set (match_operand:SI 0 "register_operand" "=D")
18889         (plus:SI (match_dup 1)
18890                  (const_int 4)))]
18891   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18892   "{stosl|stosd}"
18893   [(set_attr "type" "str")
18894    (set_attr "memory" "store")
18895    (set_attr "mode" "SI")])
18896
18897 (define_insn "*strsetsi_rex_1"
18898   [(set (mem:SI (match_operand:DI 1 "register_operand" "0"))
18899         (match_operand:SI 2 "register_operand" "a"))
18900    (set (match_operand:DI 0 "register_operand" "=D")
18901         (plus:DI (match_dup 1)
18902                  (const_int 4)))]
18903   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18904   "{stosl|stosd}"
18905   [(set_attr "type" "str")
18906    (set_attr "memory" "store")
18907    (set_attr "mode" "SI")])
18908
18909 (define_insn "*strsethi_1"
18910   [(set (mem:HI (match_operand:SI 1 "register_operand" "0"))
18911         (match_operand:HI 2 "register_operand" "a"))
18912    (set (match_operand:SI 0 "register_operand" "=D")
18913         (plus:SI (match_dup 1)
18914                  (const_int 2)))]
18915   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18916   "stosw"
18917   [(set_attr "type" "str")
18918    (set_attr "memory" "store")
18919    (set_attr "mode" "HI")])
18920
18921 (define_insn "*strsethi_rex_1"
18922   [(set (mem:HI (match_operand:DI 1 "register_operand" "0"))
18923         (match_operand:HI 2 "register_operand" "a"))
18924    (set (match_operand:DI 0 "register_operand" "=D")
18925         (plus:DI (match_dup 1)
18926                  (const_int 2)))]
18927   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18928   "stosw"
18929   [(set_attr "type" "str")
18930    (set_attr "memory" "store")
18931    (set_attr "mode" "HI")])
18932
18933 (define_insn "*strsetqi_1"
18934   [(set (mem:QI (match_operand:SI 1 "register_operand" "0"))
18935         (match_operand:QI 2 "register_operand" "a"))
18936    (set (match_operand:SI 0 "register_operand" "=D")
18937         (plus:SI (match_dup 1)
18938                  (const_int 1)))]
18939   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18940   "stosb"
18941   [(set_attr "type" "str")
18942    (set_attr "memory" "store")
18943    (set_attr "mode" "QI")])
18944
18945 (define_insn "*strsetqi_rex_1"
18946   [(set (mem:QI (match_operand:DI 1 "register_operand" "0"))
18947         (match_operand:QI 2 "register_operand" "a"))
18948    (set (match_operand:DI 0 "register_operand" "=D")
18949         (plus:DI (match_dup 1)
18950                  (const_int 1)))]
18951   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
18952   "stosb"
18953   [(set_attr "type" "str")
18954    (set_attr "memory" "store")
18955    (set_attr "mode" "QI")])
18956
18957 (define_expand "rep_stos"
18958   [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
18959               (set (match_operand 0 "register_operand" "")
18960                    (match_operand 4 "" ""))
18961               (set (match_operand 2 "memory_operand" "") (const_int 0))
18962               (use (match_operand 3 "register_operand" ""))
18963               (use (match_dup 1))])]
18964   ""
18965   "")
18966
18967 (define_insn "*rep_stosdi_rex64"
18968   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
18969    (set (match_operand:DI 0 "register_operand" "=D")
18970         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
18971                             (const_int 3))
18972                  (match_operand:DI 3 "register_operand" "0")))
18973    (set (mem:BLK (match_dup 3))
18974         (const_int 0))
18975    (use (match_operand:DI 2 "register_operand" "a"))
18976    (use (match_dup 4))]
18977   "TARGET_64BIT"
18978   "rep stosq"
18979   [(set_attr "type" "str")
18980    (set_attr "prefix_rep" "1")
18981    (set_attr "memory" "store")
18982    (set_attr "mode" "DI")])
18983
18984 (define_insn "*rep_stossi"
18985   [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
18986    (set (match_operand:SI 0 "register_operand" "=D")
18987         (plus:SI (ashift:SI (match_operand:SI 4 "register_operand" "1")
18988                             (const_int 2))
18989                  (match_operand:SI 3 "register_operand" "0")))
18990    (set (mem:BLK (match_dup 3))
18991         (const_int 0))
18992    (use (match_operand:SI 2 "register_operand" "a"))
18993    (use (match_dup 4))]
18994   "!TARGET_64BIT"
18995   "rep stos{l|d}"
18996   [(set_attr "type" "str")
18997    (set_attr "prefix_rep" "1")
18998    (set_attr "memory" "store")
18999    (set_attr "mode" "SI")])
19000
19001 (define_insn "*rep_stossi_rex64"
19002   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
19003    (set (match_operand:DI 0 "register_operand" "=D")
19004         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
19005                             (const_int 2))
19006                  (match_operand:DI 3 "register_operand" "0")))
19007    (set (mem:BLK (match_dup 3))
19008         (const_int 0))
19009    (use (match_operand:SI 2 "register_operand" "a"))
19010    (use (match_dup 4))]
19011   "TARGET_64BIT"
19012   "rep stos{l|d}"
19013   [(set_attr "type" "str")
19014    (set_attr "prefix_rep" "1")
19015    (set_attr "memory" "store")
19016    (set_attr "mode" "SI")])
19017
19018 (define_insn "*rep_stosqi"
19019   [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
19020    (set (match_operand:SI 0 "register_operand" "=D")
19021         (plus:SI (match_operand:SI 3 "register_operand" "0")
19022                  (match_operand:SI 4 "register_operand" "1")))
19023    (set (mem:BLK (match_dup 3))
19024         (const_int 0))
19025    (use (match_operand:QI 2 "register_operand" "a"))
19026    (use (match_dup 4))]
19027   "!TARGET_64BIT"
19028   "rep stosb"
19029   [(set_attr "type" "str")
19030    (set_attr "prefix_rep" "1")
19031    (set_attr "memory" "store")
19032    (set_attr "mode" "QI")])
19033
19034 (define_insn "*rep_stosqi_rex64"
19035   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
19036    (set (match_operand:DI 0 "register_operand" "=D")
19037         (plus:DI (match_operand:DI 3 "register_operand" "0")
19038                  (match_operand:DI 4 "register_operand" "1")))
19039    (set (mem:BLK (match_dup 3))
19040         (const_int 0))
19041    (use (match_operand:QI 2 "register_operand" "a"))
19042    (use (match_dup 4))]
19043   "TARGET_64BIT"
19044   "rep stosb"
19045   [(set_attr "type" "str")
19046    (set_attr "prefix_rep" "1")
19047    (set_attr "memory" "store")
19048    (set_attr "mode" "QI")])
19049
19050 (define_expand "cmpstrnsi"
19051   [(set (match_operand:SI 0 "register_operand" "")
19052         (compare:SI (match_operand:BLK 1 "general_operand" "")
19053                     (match_operand:BLK 2 "general_operand" "")))
19054    (use (match_operand 3 "general_operand" ""))
19055    (use (match_operand 4 "immediate_operand" ""))]
19056   "! optimize_size || TARGET_INLINE_ALL_STRINGOPS"
19057 {
19058   rtx addr1, addr2, out, outlow, count, countreg, align;
19059
19060   /* Can't use this if the user has appropriated esi or edi.  */
19061   if (fixed_regs[SI_REG] || fixed_regs[DI_REG])
19062     FAIL;
19063
19064   out = operands[0];
19065   if (!REG_P (out))
19066     out = gen_reg_rtx (SImode);
19067
19068   addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
19069   addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
19070   if (addr1 != XEXP (operands[1], 0))
19071     operands[1] = replace_equiv_address_nv (operands[1], addr1);
19072   if (addr2 != XEXP (operands[2], 0))
19073     operands[2] = replace_equiv_address_nv (operands[2], addr2);
19074
19075   count = operands[3];
19076   countreg = ix86_zero_extend_to_Pmode (count);
19077
19078   /* %%% Iff we are testing strict equality, we can use known alignment
19079      to good advantage.  This may be possible with combine, particularly
19080      once cc0 is dead.  */
19081   align = operands[4];
19082
19083   if (CONST_INT_P (count))
19084     {
19085       if (INTVAL (count) == 0)
19086         {
19087           emit_move_insn (operands[0], const0_rtx);
19088           DONE;
19089         }
19090       emit_insn (gen_cmpstrnqi_nz_1 (addr1, addr2, countreg, align,
19091                                      operands[1], operands[2]));
19092     }
19093   else
19094     {
19095       if (TARGET_64BIT)
19096         emit_insn (gen_cmpdi_1_rex64 (countreg, countreg));
19097       else
19098         emit_insn (gen_cmpsi_1 (countreg, countreg));
19099       emit_insn (gen_cmpstrnqi_1 (addr1, addr2, countreg, align,
19100                                   operands[1], operands[2]));
19101     }
19102
19103   outlow = gen_lowpart (QImode, out);
19104   emit_insn (gen_cmpintqi (outlow));
19105   emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
19106
19107   if (operands[0] != out)
19108     emit_move_insn (operands[0], out);
19109
19110   DONE;
19111 })
19112
19113 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
19114
19115 (define_expand "cmpintqi"
19116   [(set (match_dup 1)
19117         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
19118    (set (match_dup 2)
19119         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
19120    (parallel [(set (match_operand:QI 0 "register_operand" "")
19121                    (minus:QI (match_dup 1)
19122                              (match_dup 2)))
19123               (clobber (reg:CC FLAGS_REG))])]
19124   ""
19125   "operands[1] = gen_reg_rtx (QImode);
19126    operands[2] = gen_reg_rtx (QImode);")
19127
19128 ;; memcmp recognizers.  The `cmpsb' opcode does nothing if the count is
19129 ;; zero.  Emit extra code to make sure that a zero-length compare is EQ.
19130
19131 (define_expand "cmpstrnqi_nz_1"
19132   [(parallel [(set (reg:CC FLAGS_REG)
19133                    (compare:CC (match_operand 4 "memory_operand" "")
19134                                (match_operand 5 "memory_operand" "")))
19135               (use (match_operand 2 "register_operand" ""))
19136               (use (match_operand:SI 3 "immediate_operand" ""))
19137               (clobber (match_operand 0 "register_operand" ""))
19138               (clobber (match_operand 1 "register_operand" ""))
19139               (clobber (match_dup 2))])]
19140   ""
19141   "")
19142
19143 (define_insn "*cmpstrnqi_nz_1"
19144   [(set (reg:CC FLAGS_REG)
19145         (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
19146                     (mem:BLK (match_operand:SI 5 "register_operand" "1"))))
19147    (use (match_operand:SI 6 "register_operand" "2"))
19148    (use (match_operand:SI 3 "immediate_operand" "i"))
19149    (clobber (match_operand:SI 0 "register_operand" "=S"))
19150    (clobber (match_operand:SI 1 "register_operand" "=D"))
19151    (clobber (match_operand:SI 2 "register_operand" "=c"))]
19152   "!TARGET_64BIT"
19153   "repz cmpsb"
19154   [(set_attr "type" "str")
19155    (set_attr "mode" "QI")
19156    (set_attr "prefix_rep" "1")])
19157
19158 (define_insn "*cmpstrnqi_nz_rex_1"
19159   [(set (reg:CC FLAGS_REG)
19160         (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
19161                     (mem:BLK (match_operand:DI 5 "register_operand" "1"))))
19162    (use (match_operand:DI 6 "register_operand" "2"))
19163    (use (match_operand:SI 3 "immediate_operand" "i"))
19164    (clobber (match_operand:DI 0 "register_operand" "=S"))
19165    (clobber (match_operand:DI 1 "register_operand" "=D"))
19166    (clobber (match_operand:DI 2 "register_operand" "=c"))]
19167   "TARGET_64BIT"
19168   "repz cmpsb"
19169   [(set_attr "type" "str")
19170    (set_attr "mode" "QI")
19171    (set_attr "prefix_rep" "1")])
19172
19173 ;; The same, but the count is not known to not be zero.
19174
19175 (define_expand "cmpstrnqi_1"
19176   [(parallel [(set (reg:CC FLAGS_REG)
19177                 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
19178                                      (const_int 0))
19179                   (compare:CC (match_operand 4 "memory_operand" "")
19180                               (match_operand 5 "memory_operand" ""))
19181                   (const_int 0)))
19182               (use (match_operand:SI 3 "immediate_operand" ""))
19183               (use (reg:CC FLAGS_REG))
19184               (clobber (match_operand 0 "register_operand" ""))
19185               (clobber (match_operand 1 "register_operand" ""))
19186               (clobber (match_dup 2))])]
19187   ""
19188   "")
19189
19190 (define_insn "*cmpstrnqi_1"
19191   [(set (reg:CC FLAGS_REG)
19192         (if_then_else:CC (ne (match_operand:SI 6 "register_operand" "2")
19193                              (const_int 0))
19194           (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
19195                       (mem:BLK (match_operand:SI 5 "register_operand" "1")))
19196           (const_int 0)))
19197    (use (match_operand:SI 3 "immediate_operand" "i"))
19198    (use (reg:CC FLAGS_REG))
19199    (clobber (match_operand:SI 0 "register_operand" "=S"))
19200    (clobber (match_operand:SI 1 "register_operand" "=D"))
19201    (clobber (match_operand:SI 2 "register_operand" "=c"))]
19202   "!TARGET_64BIT"
19203   "repz cmpsb"
19204   [(set_attr "type" "str")
19205    (set_attr "mode" "QI")
19206    (set_attr "prefix_rep" "1")])
19207
19208 (define_insn "*cmpstrnqi_rex_1"
19209   [(set (reg:CC FLAGS_REG)
19210         (if_then_else:CC (ne (match_operand:DI 6 "register_operand" "2")
19211                              (const_int 0))
19212           (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
19213                       (mem:BLK (match_operand:DI 5 "register_operand" "1")))
19214           (const_int 0)))
19215    (use (match_operand:SI 3 "immediate_operand" "i"))
19216    (use (reg:CC FLAGS_REG))
19217    (clobber (match_operand:DI 0 "register_operand" "=S"))
19218    (clobber (match_operand:DI 1 "register_operand" "=D"))
19219    (clobber (match_operand:DI 2 "register_operand" "=c"))]
19220   "TARGET_64BIT"
19221   "repz cmpsb"
19222   [(set_attr "type" "str")
19223    (set_attr "mode" "QI")
19224    (set_attr "prefix_rep" "1")])
19225
19226 (define_expand "strlensi"
19227   [(set (match_operand:SI 0 "register_operand" "")
19228         (unspec:SI [(match_operand:BLK 1 "general_operand" "")
19229                     (match_operand:QI 2 "immediate_operand" "")
19230                     (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
19231   ""
19232 {
19233  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
19234    DONE;
19235  else
19236    FAIL;
19237 })
19238
19239 (define_expand "strlendi"
19240   [(set (match_operand:DI 0 "register_operand" "")
19241         (unspec:DI [(match_operand:BLK 1 "general_operand" "")
19242                     (match_operand:QI 2 "immediate_operand" "")
19243                     (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
19244   ""
19245 {
19246  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
19247    DONE;
19248  else
19249    FAIL;
19250 })
19251
19252 (define_expand "strlenqi_1"
19253   [(parallel [(set (match_operand 0 "register_operand" "") (match_operand 2 "" ""))
19254               (clobber (match_operand 1 "register_operand" ""))
19255               (clobber (reg:CC FLAGS_REG))])]
19256   ""
19257   "")
19258
19259 (define_insn "*strlenqi_1"
19260   [(set (match_operand:SI 0 "register_operand" "=&c")
19261         (unspec:SI [(mem:BLK (match_operand:SI 5 "register_operand" "1"))
19262                     (match_operand:QI 2 "register_operand" "a")
19263                     (match_operand:SI 3 "immediate_operand" "i")
19264                     (match_operand:SI 4 "register_operand" "0")] UNSPEC_SCAS))
19265    (clobber (match_operand:SI 1 "register_operand" "=D"))
19266    (clobber (reg:CC FLAGS_REG))]
19267   "!TARGET_64BIT"
19268   "repnz scasb"
19269   [(set_attr "type" "str")
19270    (set_attr "mode" "QI")
19271    (set_attr "prefix_rep" "1")])
19272
19273 (define_insn "*strlenqi_rex_1"
19274   [(set (match_operand:DI 0 "register_operand" "=&c")
19275         (unspec:DI [(mem:BLK (match_operand:DI 5 "register_operand" "1"))
19276                     (match_operand:QI 2 "register_operand" "a")
19277                     (match_operand:DI 3 "immediate_operand" "i")
19278                     (match_operand:DI 4 "register_operand" "0")] UNSPEC_SCAS))
19279    (clobber (match_operand:DI 1 "register_operand" "=D"))
19280    (clobber (reg:CC FLAGS_REG))]
19281   "TARGET_64BIT"
19282   "repnz scasb"
19283   [(set_attr "type" "str")
19284    (set_attr "mode" "QI")
19285    (set_attr "prefix_rep" "1")])
19286
19287 ;; Peephole optimizations to clean up after cmpstrn*.  This should be
19288 ;; handled in combine, but it is not currently up to the task.
19289 ;; When used for their truth value, the cmpstrn* expanders generate
19290 ;; code like this:
19291 ;;
19292 ;;   repz cmpsb
19293 ;;   seta       %al
19294 ;;   setb       %dl
19295 ;;   cmpb       %al, %dl
19296 ;;   jcc        label
19297 ;;
19298 ;; The intermediate three instructions are unnecessary.
19299
19300 ;; This one handles cmpstrn*_nz_1...
19301 (define_peephole2
19302   [(parallel[
19303      (set (reg:CC FLAGS_REG)
19304           (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
19305                       (mem:BLK (match_operand 5 "register_operand" ""))))
19306      (use (match_operand 6 "register_operand" ""))
19307      (use (match_operand:SI 3 "immediate_operand" ""))
19308      (clobber (match_operand 0 "register_operand" ""))
19309      (clobber (match_operand 1 "register_operand" ""))
19310      (clobber (match_operand 2 "register_operand" ""))])
19311    (set (match_operand:QI 7 "register_operand" "")
19312         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
19313    (set (match_operand:QI 8 "register_operand" "")
19314         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
19315    (set (reg FLAGS_REG)
19316         (compare (match_dup 7) (match_dup 8)))
19317   ]
19318   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
19319   [(parallel[
19320      (set (reg:CC FLAGS_REG)
19321           (compare:CC (mem:BLK (match_dup 4))
19322                       (mem:BLK (match_dup 5))))
19323      (use (match_dup 6))
19324      (use (match_dup 3))
19325      (clobber (match_dup 0))
19326      (clobber (match_dup 1))
19327      (clobber (match_dup 2))])]
19328   "")
19329
19330 ;; ...and this one handles cmpstrn*_1.
19331 (define_peephole2
19332   [(parallel[
19333      (set (reg:CC FLAGS_REG)
19334           (if_then_else:CC (ne (match_operand 6 "register_operand" "")
19335                                (const_int 0))
19336             (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
19337                         (mem:BLK (match_operand 5 "register_operand" "")))
19338             (const_int 0)))
19339      (use (match_operand:SI 3 "immediate_operand" ""))
19340      (use (reg:CC FLAGS_REG))
19341      (clobber (match_operand 0 "register_operand" ""))
19342      (clobber (match_operand 1 "register_operand" ""))
19343      (clobber (match_operand 2 "register_operand" ""))])
19344    (set (match_operand:QI 7 "register_operand" "")
19345         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
19346    (set (match_operand:QI 8 "register_operand" "")
19347         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
19348    (set (reg FLAGS_REG)
19349         (compare (match_dup 7) (match_dup 8)))
19350   ]
19351   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
19352   [(parallel[
19353      (set (reg:CC FLAGS_REG)
19354           (if_then_else:CC (ne (match_dup 6)
19355                                (const_int 0))
19356             (compare:CC (mem:BLK (match_dup 4))
19357                         (mem:BLK (match_dup 5)))
19358             (const_int 0)))
19359      (use (match_dup 3))
19360      (use (reg:CC FLAGS_REG))
19361      (clobber (match_dup 0))
19362      (clobber (match_dup 1))
19363      (clobber (match_dup 2))])]
19364   "")
19365
19366
19367 \f
19368 ;; Conditional move instructions.
19369
19370 (define_expand "movdicc"
19371   [(set (match_operand:DI 0 "register_operand" "")
19372         (if_then_else:DI (match_operand 1 "comparison_operator" "")
19373                          (match_operand:DI 2 "general_operand" "")
19374                          (match_operand:DI 3 "general_operand" "")))]
19375   "TARGET_64BIT"
19376   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
19377
19378 (define_insn "x86_movdicc_0_m1_rex64"
19379   [(set (match_operand:DI 0 "register_operand" "=r")
19380         (if_then_else:DI (match_operand 1 "ix86_carry_flag_operator" "")
19381           (const_int -1)
19382           (const_int 0)))
19383    (clobber (reg:CC FLAGS_REG))]
19384   "TARGET_64BIT"
19385   "sbb{q}\t%0, %0"
19386   ; Since we don't have the proper number of operands for an alu insn,
19387   ; fill in all the blanks.
19388   [(set_attr "type" "alu")
19389    (set_attr "pent_pair" "pu")
19390    (set_attr "memory" "none")
19391    (set_attr "imm_disp" "false")
19392    (set_attr "mode" "DI")
19393    (set_attr "length_immediate" "0")])
19394
19395 (define_insn "*x86_movdicc_0_m1_se"
19396   [(set (match_operand:DI 0 "register_operand" "=r")
19397         (sign_extract:DI (match_operand 1 "ix86_carry_flag_operator" "")
19398                          (const_int 1)
19399                          (const_int 0)))
19400    (clobber (reg:CC FLAGS_REG))]
19401   ""
19402   "sbb{q}\t%0, %0"
19403   [(set_attr "type" "alu")
19404    (set_attr "pent_pair" "pu")
19405    (set_attr "memory" "none")
19406    (set_attr "imm_disp" "false")
19407    (set_attr "mode" "DI")
19408    (set_attr "length_immediate" "0")])
19409
19410 (define_insn "*movdicc_c_rex64"
19411   [(set (match_operand:DI 0 "register_operand" "=r,r")
19412         (if_then_else:DI (match_operator 1 "ix86_comparison_operator"
19413                                 [(reg FLAGS_REG) (const_int 0)])
19414                       (match_operand:DI 2 "nonimmediate_operand" "rm,0")
19415                       (match_operand:DI 3 "nonimmediate_operand" "0,rm")))]
19416   "TARGET_64BIT && TARGET_CMOVE
19417    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19418   "@
19419    cmov%O2%C1\t{%2, %0|%0, %2}
19420    cmov%O2%c1\t{%3, %0|%0, %3}"
19421   [(set_attr "type" "icmov")
19422    (set_attr "mode" "DI")])
19423
19424 (define_expand "movsicc"
19425   [(set (match_operand:SI 0 "register_operand" "")
19426         (if_then_else:SI (match_operand 1 "comparison_operator" "")
19427                          (match_operand:SI 2 "general_operand" "")
19428                          (match_operand:SI 3 "general_operand" "")))]
19429   ""
19430   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
19431
19432 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
19433 ;; the register first winds up with `sbbl $0,reg', which is also weird.
19434 ;; So just document what we're doing explicitly.
19435
19436 (define_insn "x86_movsicc_0_m1"
19437   [(set (match_operand:SI 0 "register_operand" "=r")
19438         (if_then_else:SI (match_operand 1 "ix86_carry_flag_operator" "")
19439           (const_int -1)
19440           (const_int 0)))
19441    (clobber (reg:CC FLAGS_REG))]
19442   ""
19443   "sbb{l}\t%0, %0"
19444   ; Since we don't have the proper number of operands for an alu insn,
19445   ; fill in all the blanks.
19446   [(set_attr "type" "alu")
19447    (set_attr "pent_pair" "pu")
19448    (set_attr "memory" "none")
19449    (set_attr "imm_disp" "false")
19450    (set_attr "mode" "SI")
19451    (set_attr "length_immediate" "0")])
19452
19453 (define_insn "*x86_movsicc_0_m1_se"
19454   [(set (match_operand:SI 0 "register_operand" "=r")
19455         (sign_extract:SI (match_operand 1 "ix86_carry_flag_operator" "")
19456                          (const_int 1)
19457                          (const_int 0)))
19458    (clobber (reg:CC FLAGS_REG))]
19459   ""
19460   "sbb{l}\t%0, %0"
19461   [(set_attr "type" "alu")
19462    (set_attr "pent_pair" "pu")
19463    (set_attr "memory" "none")
19464    (set_attr "imm_disp" "false")
19465    (set_attr "mode" "SI")
19466    (set_attr "length_immediate" "0")])
19467
19468 (define_insn "*movsicc_noc"
19469   [(set (match_operand:SI 0 "register_operand" "=r,r")
19470         (if_then_else:SI (match_operator 1 "ix86_comparison_operator"
19471                                 [(reg FLAGS_REG) (const_int 0)])
19472                       (match_operand:SI 2 "nonimmediate_operand" "rm,0")
19473                       (match_operand:SI 3 "nonimmediate_operand" "0,rm")))]
19474   "TARGET_CMOVE
19475    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19476   "@
19477    cmov%O2%C1\t{%2, %0|%0, %2}
19478    cmov%O2%c1\t{%3, %0|%0, %3}"
19479   [(set_attr "type" "icmov")
19480    (set_attr "mode" "SI")])
19481
19482 (define_expand "movhicc"
19483   [(set (match_operand:HI 0 "register_operand" "")
19484         (if_then_else:HI (match_operand 1 "comparison_operator" "")
19485                          (match_operand:HI 2 "general_operand" "")
19486                          (match_operand:HI 3 "general_operand" "")))]
19487   "TARGET_HIMODE_MATH"
19488   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
19489
19490 (define_insn "*movhicc_noc"
19491   [(set (match_operand:HI 0 "register_operand" "=r,r")
19492         (if_then_else:HI (match_operator 1 "ix86_comparison_operator"
19493                                 [(reg FLAGS_REG) (const_int 0)])
19494                       (match_operand:HI 2 "nonimmediate_operand" "rm,0")
19495                       (match_operand:HI 3 "nonimmediate_operand" "0,rm")))]
19496   "TARGET_CMOVE
19497    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19498   "@
19499    cmov%O2%C1\t{%2, %0|%0, %2}
19500    cmov%O2%c1\t{%3, %0|%0, %3}"
19501   [(set_attr "type" "icmov")
19502    (set_attr "mode" "HI")])
19503
19504 (define_expand "movqicc"
19505   [(set (match_operand:QI 0 "register_operand" "")
19506         (if_then_else:QI (match_operand 1 "comparison_operator" "")
19507                          (match_operand:QI 2 "general_operand" "")
19508                          (match_operand:QI 3 "general_operand" "")))]
19509   "TARGET_QIMODE_MATH"
19510   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
19511
19512 (define_insn_and_split "*movqicc_noc"
19513   [(set (match_operand:QI 0 "register_operand" "=r,r")
19514         (if_then_else:QI (match_operator 1 "ix86_comparison_operator"
19515                                 [(match_operand 4 "flags_reg_operand" "")
19516                                  (const_int 0)])
19517                       (match_operand:QI 2 "register_operand" "r,0")
19518                       (match_operand:QI 3 "register_operand" "0,r")))]
19519   "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
19520   "#"
19521   "&& reload_completed"
19522   [(set (match_dup 0)
19523         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
19524                       (match_dup 2)
19525                       (match_dup 3)))]
19526   "operands[0] = gen_lowpart (SImode, operands[0]);
19527    operands[2] = gen_lowpart (SImode, operands[2]);
19528    operands[3] = gen_lowpart (SImode, operands[3]);"
19529   [(set_attr "type" "icmov")
19530    (set_attr "mode" "SI")])
19531
19532 (define_expand "movsfcc"
19533   [(set (match_operand:SF 0 "register_operand" "")
19534         (if_then_else:SF (match_operand 1 "comparison_operator" "")
19535                          (match_operand:SF 2 "register_operand" "")
19536                          (match_operand:SF 3 "register_operand" "")))]
19537   "(TARGET_80387 && TARGET_CMOVE) || TARGET_SSE_MATH"
19538   "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
19539
19540 (define_insn "*movsfcc_1_387"
19541   [(set (match_operand:SF 0 "register_operand" "=f,f,r,r")
19542         (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
19543                                 [(reg FLAGS_REG) (const_int 0)])
19544                       (match_operand:SF 2 "nonimmediate_operand" "f,0,rm,0")
19545                       (match_operand:SF 3 "nonimmediate_operand" "0,f,0,rm")))]
19546   "TARGET_80387 && TARGET_CMOVE
19547    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19548   "@
19549    fcmov%F1\t{%2, %0|%0, %2}
19550    fcmov%f1\t{%3, %0|%0, %3}
19551    cmov%O2%C1\t{%2, %0|%0, %2}
19552    cmov%O2%c1\t{%3, %0|%0, %3}"
19553   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
19554    (set_attr "mode" "SF,SF,SI,SI")])
19555
19556 (define_expand "movdfcc"
19557   [(set (match_operand:DF 0 "register_operand" "")
19558         (if_then_else:DF (match_operand 1 "comparison_operator" "")
19559                          (match_operand:DF 2 "register_operand" "")
19560                          (match_operand:DF 3 "register_operand" "")))]
19561   "(TARGET_80387 && TARGET_CMOVE) || (TARGET_SSE2 && TARGET_SSE_MATH)"
19562   "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
19563
19564 (define_insn "*movdfcc_1"
19565   [(set (match_operand:DF 0 "register_operand" "=f,f,&r,&r")
19566         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
19567                                 [(reg FLAGS_REG) (const_int 0)])
19568                       (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
19569                       (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
19570   "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
19571    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19572   "@
19573    fcmov%F1\t{%2, %0|%0, %2}
19574    fcmov%f1\t{%3, %0|%0, %3}
19575    #
19576    #"
19577   [(set_attr "type" "fcmov,fcmov,multi,multi")
19578    (set_attr "mode" "DF")])
19579
19580 (define_insn "*movdfcc_1_rex64"
19581   [(set (match_operand:DF 0 "register_operand" "=f,f,r,r")
19582         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
19583                                 [(reg FLAGS_REG) (const_int 0)])
19584                       (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
19585                       (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
19586   "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
19587    && !(MEM_P (operands[2]) && MEM_P (operands[3]))"
19588   "@
19589    fcmov%F1\t{%2, %0|%0, %2}
19590    fcmov%f1\t{%3, %0|%0, %3}
19591    cmov%O2%C1\t{%2, %0|%0, %2}
19592    cmov%O2%c1\t{%3, %0|%0, %3}"
19593   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
19594    (set_attr "mode" "DF")])
19595
19596 (define_split
19597   [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand" "")
19598         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
19599                                 [(match_operand 4 "flags_reg_operand" "")
19600                                  (const_int 0)])
19601                       (match_operand:DF 2 "nonimmediate_operand" "")
19602                       (match_operand:DF 3 "nonimmediate_operand" "")))]
19603   "!TARGET_64BIT && reload_completed"
19604   [(set (match_dup 2)
19605         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
19606                       (match_dup 5)
19607                       (match_dup 7)))
19608    (set (match_dup 3)
19609         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
19610                       (match_dup 6)
19611                       (match_dup 8)))]
19612   "split_di (operands+2, 1, operands+5, operands+6);
19613    split_di (operands+3, 1, operands+7, operands+8);
19614    split_di (operands, 1, operands+2, operands+3);")
19615
19616 (define_expand "movxfcc"
19617   [(set (match_operand:XF 0 "register_operand" "")
19618         (if_then_else:XF (match_operand 1 "comparison_operator" "")
19619                          (match_operand:XF 2 "register_operand" "")
19620                          (match_operand:XF 3 "register_operand" "")))]
19621   "TARGET_80387 && TARGET_CMOVE"
19622   "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
19623
19624 (define_insn "*movxfcc_1"
19625   [(set (match_operand:XF 0 "register_operand" "=f,f")
19626         (if_then_else:XF (match_operator 1 "fcmov_comparison_operator"
19627                                 [(reg FLAGS_REG) (const_int 0)])
19628                       (match_operand:XF 2 "register_operand" "f,0")
19629                       (match_operand:XF 3 "register_operand" "0,f")))]
19630   "TARGET_80387 && TARGET_CMOVE"
19631   "@
19632    fcmov%F1\t{%2, %0|%0, %2}
19633    fcmov%f1\t{%3, %0|%0, %3}"
19634   [(set_attr "type" "fcmov")
19635    (set_attr "mode" "XF")])
19636
19637 ;; All moves in SSE5 pcmov instructions are 128 bits and hence we restrict
19638 ;; the scalar versions to have only XMM registers as operands.
19639
19640 ;; SSE5 conditional move
19641 (define_insn "*sse5_pcmov_<mode>"
19642   [(set (match_operand:MODEF 0 "register_operand" "=x,x")
19643         (if_then_else:MODEF
19644           (match_operand:MODEF 1 "register_operand" "x,0")
19645           (match_operand:MODEF 2 "register_operand" "0,x")
19646           (match_operand:MODEF 3 "register_operand" "x,x")))]
19647   "TARGET_SSE5 && ix86_sse5_valid_op_p (operands, insn, 4, true, 1)"
19648   "pcmov\t{%1, %3, %2, %0|%0, %2, %3, %1}"
19649   [(set_attr "type" "sse4arg")])
19650
19651 ;; These versions of the min/max patterns are intentionally ignorant of
19652 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
19653 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
19654 ;; are undefined in this condition, we're certain this is correct.
19655
19656 (define_insn "smin<mode>3"
19657   [(set (match_operand:MODEF 0 "register_operand" "=x")
19658         (smin:MODEF
19659           (match_operand:MODEF 1 "nonimmediate_operand" "%0")
19660           (match_operand:MODEF 2 "nonimmediate_operand" "xm")))]
19661   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
19662   "mins<ssemodefsuffix>\t{%2, %0|%0, %2}"
19663   [(set_attr "type" "sseadd")
19664    (set_attr "mode" "<MODE>")])
19665
19666 (define_insn "smax<mode>3"
19667   [(set (match_operand:MODEF 0 "register_operand" "=x")
19668         (smax:MODEF
19669           (match_operand:MODEF 1 "nonimmediate_operand" "%0")
19670           (match_operand:MODEF 2 "nonimmediate_operand" "xm")))]
19671   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
19672   "maxs<ssemodefsuffix>\t{%2, %0|%0, %2}"
19673   [(set_attr "type" "sseadd")
19674    (set_attr "mode" "<MODE>")])
19675
19676 ;; These versions of the min/max patterns implement exactly the operations
19677 ;;   min = (op1 < op2 ? op1 : op2)
19678 ;;   max = (!(op1 < op2) ? op1 : op2)
19679 ;; Their operands are not commutative, and thus they may be used in the
19680 ;; presence of -0.0 and NaN.
19681
19682 (define_insn "*ieee_smin<mode>3"
19683   [(set (match_operand:MODEF 0 "register_operand" "=x")
19684         (unspec:MODEF
19685           [(match_operand:MODEF 1 "register_operand" "0")
19686            (match_operand:MODEF 2 "nonimmediate_operand" "xm")]
19687          UNSPEC_IEEE_MIN))]
19688   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
19689   "mins<ssemodefsuffix>\t{%2, %0|%0, %2}"
19690   [(set_attr "type" "sseadd")
19691    (set_attr "mode" "<MODE>")])
19692
19693 (define_insn "*ieee_smax<mode>3"
19694   [(set (match_operand:MODEF 0 "register_operand" "=x")
19695         (unspec:MODEF
19696           [(match_operand:MODEF 1 "register_operand" "0")
19697            (match_operand:MODEF 2 "nonimmediate_operand" "xm")]
19698          UNSPEC_IEEE_MAX))]
19699   "SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH"
19700   "maxs<ssemodefsuffix>\t{%2, %0|%0, %2}"
19701   [(set_attr "type" "sseadd")
19702    (set_attr "mode" "<MODE>")])
19703
19704 ;; Make two stack loads independent:
19705 ;;   fld aa              fld aa
19706 ;;   fld %st(0)     ->   fld bb
19707 ;;   fmul bb             fmul %st(1), %st
19708 ;;
19709 ;; Actually we only match the last two instructions for simplicity.
19710 (define_peephole2
19711   [(set (match_operand 0 "fp_register_operand" "")
19712         (match_operand 1 "fp_register_operand" ""))
19713    (set (match_dup 0)
19714         (match_operator 2 "binary_fp_operator"
19715            [(match_dup 0)
19716             (match_operand 3 "memory_operand" "")]))]
19717   "REGNO (operands[0]) != REGNO (operands[1])"
19718   [(set (match_dup 0) (match_dup 3))
19719    (set (match_dup 0) (match_dup 4))]
19720
19721   ;; The % modifier is not operational anymore in peephole2's, so we have to
19722   ;; swap the operands manually in the case of addition and multiplication.
19723   "if (COMMUTATIVE_ARITH_P (operands[2]))
19724      operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), GET_MODE (operands[2]),
19725                                  operands[0], operands[1]);
19726    else
19727      operands[4] = gen_rtx_fmt_ee (GET_CODE (operands[2]), GET_MODE (operands[2]),
19728                                  operands[1], operands[0]);")
19729
19730 ;; Conditional addition patterns
19731 (define_expand "addqicc"
19732   [(match_operand:QI 0 "register_operand" "")
19733    (match_operand 1 "comparison_operator" "")
19734    (match_operand:QI 2 "register_operand" "")
19735    (match_operand:QI 3 "const_int_operand" "")]
19736   ""
19737   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
19738
19739 (define_expand "addhicc"
19740   [(match_operand:HI 0 "register_operand" "")
19741    (match_operand 1 "comparison_operator" "")
19742    (match_operand:HI 2 "register_operand" "")
19743    (match_operand:HI 3 "const_int_operand" "")]
19744   ""
19745   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
19746
19747 (define_expand "addsicc"
19748   [(match_operand:SI 0 "register_operand" "")
19749    (match_operand 1 "comparison_operator" "")
19750    (match_operand:SI 2 "register_operand" "")
19751    (match_operand:SI 3 "const_int_operand" "")]
19752   ""
19753   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
19754
19755 (define_expand "adddicc"
19756   [(match_operand:DI 0 "register_operand" "")
19757    (match_operand 1 "comparison_operator" "")
19758    (match_operand:DI 2 "register_operand" "")
19759    (match_operand:DI 3 "const_int_operand" "")]
19760   "TARGET_64BIT"
19761   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
19762
19763 \f
19764 ;; Misc patterns (?)
19765
19766 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
19767 ;; Otherwise there will be nothing to keep
19768 ;;
19769 ;; [(set (reg ebp) (reg esp))]
19770 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
19771 ;;  (clobber (eflags)]
19772 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
19773 ;;
19774 ;; in proper program order.
19775 (define_insn "pro_epilogue_adjust_stack_1"
19776   [(set (match_operand:SI 0 "register_operand" "=r,r")
19777         (plus:SI (match_operand:SI 1 "register_operand" "0,r")
19778                  (match_operand:SI 2 "immediate_operand" "i,i")))
19779    (clobber (reg:CC FLAGS_REG))
19780    (clobber (mem:BLK (scratch)))]
19781   "!TARGET_64BIT"
19782 {
19783   switch (get_attr_type (insn))
19784     {
19785     case TYPE_IMOV:
19786       return "mov{l}\t{%1, %0|%0, %1}";
19787
19788     case TYPE_ALU:
19789       if (CONST_INT_P (operands[2])
19790           && (INTVAL (operands[2]) == 128
19791               || (INTVAL (operands[2]) < 0
19792                   && INTVAL (operands[2]) != -128)))
19793         {
19794           operands[2] = GEN_INT (-INTVAL (operands[2]));
19795           return "sub{l}\t{%2, %0|%0, %2}";
19796         }
19797       return "add{l}\t{%2, %0|%0, %2}";
19798
19799     case TYPE_LEA:
19800       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
19801       return "lea{l}\t{%a2, %0|%0, %a2}";
19802
19803     default:
19804       gcc_unreachable ();
19805     }
19806 }
19807   [(set (attr "type")
19808         (cond [(eq_attr "alternative" "0")
19809                  (const_string "alu")
19810                (match_operand:SI 2 "const0_operand" "")
19811                  (const_string "imov")
19812               ]
19813               (const_string "lea")))
19814    (set_attr "mode" "SI")])
19815
19816 (define_insn "pro_epilogue_adjust_stack_rex64"
19817   [(set (match_operand:DI 0 "register_operand" "=r,r")
19818         (plus:DI (match_operand:DI 1 "register_operand" "0,r")
19819                  (match_operand:DI 2 "x86_64_immediate_operand" "e,e")))
19820    (clobber (reg:CC FLAGS_REG))
19821    (clobber (mem:BLK (scratch)))]
19822   "TARGET_64BIT"
19823 {
19824   switch (get_attr_type (insn))
19825     {
19826     case TYPE_IMOV:
19827       return "mov{q}\t{%1, %0|%0, %1}";
19828
19829     case TYPE_ALU:
19830       if (CONST_INT_P (operands[2])
19831           /* Avoid overflows.  */
19832           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
19833           && (INTVAL (operands[2]) == 128
19834               || (INTVAL (operands[2]) < 0
19835                   && INTVAL (operands[2]) != -128)))
19836         {
19837           operands[2] = GEN_INT (-INTVAL (operands[2]));
19838           return "sub{q}\t{%2, %0|%0, %2}";
19839         }
19840       return "add{q}\t{%2, %0|%0, %2}";
19841
19842     case TYPE_LEA:
19843       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
19844       return "lea{q}\t{%a2, %0|%0, %a2}";
19845
19846     default:
19847       gcc_unreachable ();
19848     }
19849 }
19850   [(set (attr "type")
19851         (cond [(eq_attr "alternative" "0")
19852                  (const_string "alu")
19853                (match_operand:DI 2 "const0_operand" "")
19854                  (const_string "imov")
19855               ]
19856               (const_string "lea")))
19857    (set_attr "mode" "DI")])
19858
19859 (define_insn "pro_epilogue_adjust_stack_rex64_2"
19860   [(set (match_operand:DI 0 "register_operand" "=r,r")
19861         (plus:DI (match_operand:DI 1 "register_operand" "0,r")
19862                  (match_operand:DI 3 "immediate_operand" "i,i")))
19863    (use (match_operand:DI 2 "register_operand" "r,r"))
19864    (clobber (reg:CC FLAGS_REG))
19865    (clobber (mem:BLK (scratch)))]
19866   "TARGET_64BIT"
19867 {
19868   switch (get_attr_type (insn))
19869     {
19870     case TYPE_ALU:
19871       return "add{q}\t{%2, %0|%0, %2}";
19872
19873     case TYPE_LEA:
19874       operands[2] = gen_rtx_PLUS (DImode, operands[1], operands[2]);
19875       return "lea{q}\t{%a2, %0|%0, %a2}";
19876
19877     default:
19878       gcc_unreachable ();
19879     }
19880 }
19881   [(set_attr "type" "alu,lea")
19882    (set_attr "mode" "DI")])
19883
19884 (define_insn "allocate_stack_worker_32"
19885   [(set (match_operand:SI 0 "register_operand" "+a")
19886         (unspec_volatile:SI [(match_dup 0)] UNSPECV_STACK_PROBE))
19887    (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0)))
19888    (clobber (reg:CC FLAGS_REG))]
19889   "!TARGET_64BIT && TARGET_STACK_PROBE"
19890   "call\t__alloca"
19891   [(set_attr "type" "multi")
19892    (set_attr "length" "5")])
19893
19894 (define_insn "allocate_stack_worker_64"
19895   [(set (match_operand:DI 0 "register_operand" "=a")
19896         (unspec_volatile:DI [(match_dup 0)] UNSPECV_STACK_PROBE))
19897    (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0)))
19898    (clobber (reg:DI R10_REG))
19899    (clobber (reg:DI R11_REG))
19900    (clobber (reg:CC FLAGS_REG))]
19901   "TARGET_64BIT && TARGET_STACK_PROBE"
19902   "call\t___chkstk"
19903   [(set_attr "type" "multi")
19904    (set_attr "length" "5")])
19905
19906 (define_expand "allocate_stack"
19907   [(match_operand 0 "register_operand" "")
19908    (match_operand 1 "general_operand" "")]
19909   "TARGET_STACK_PROBE"
19910 {
19911   rtx x;
19912
19913 #ifndef CHECK_STACK_LIMIT
19914 #define CHECK_STACK_LIMIT 0
19915 #endif
19916
19917   if (CHECK_STACK_LIMIT && CONST_INT_P (operands[1])
19918       && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
19919     {
19920       x = expand_simple_binop (Pmode, MINUS, stack_pointer_rtx, operands[1],
19921                                stack_pointer_rtx, 0, OPTAB_DIRECT);
19922       if (x != stack_pointer_rtx)
19923         emit_move_insn (stack_pointer_rtx, x);
19924     }
19925   else
19926     {
19927       x = copy_to_mode_reg (Pmode, operands[1]);
19928       if (TARGET_64BIT)
19929         x = gen_allocate_stack_worker_64 (x);
19930       else
19931         x = gen_allocate_stack_worker_32 (x);
19932       emit_insn (x);
19933     }
19934
19935   emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
19936   DONE;
19937 })
19938
19939 (define_expand "builtin_setjmp_receiver"
19940   [(label_ref (match_operand 0 "" ""))]
19941   "!TARGET_64BIT && flag_pic"
19942 {
19943   if (TARGET_MACHO)
19944     {
19945       rtx xops[3];
19946       rtx picreg = gen_rtx_REG (Pmode, PIC_OFFSET_TABLE_REGNUM);
19947       rtx label_rtx = gen_label_rtx ();
19948       emit_insn (gen_set_got_labelled (pic_offset_table_rtx, label_rtx));
19949       xops[0] = xops[1] = picreg;
19950       xops[2] = gen_rtx_CONST (SImode,
19951                   gen_rtx_MINUS (SImode,
19952                     gen_rtx_LABEL_REF (SImode, label_rtx),
19953                     gen_rtx_SYMBOL_REF (SImode, GOT_SYMBOL_NAME)));
19954       ix86_expand_binary_operator (MINUS, SImode, xops);
19955     }
19956   else
19957     emit_insn (gen_set_got (pic_offset_table_rtx));
19958   DONE;
19959 })
19960 \f
19961 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
19962
19963 (define_split
19964   [(set (match_operand 0 "register_operand" "")
19965         (match_operator 3 "promotable_binary_operator"
19966            [(match_operand 1 "register_operand" "")
19967             (match_operand 2 "aligned_operand" "")]))
19968    (clobber (reg:CC FLAGS_REG))]
19969   "! TARGET_PARTIAL_REG_STALL && reload_completed
19970    && ((GET_MODE (operands[0]) == HImode
19971         && ((!optimize_size && !TARGET_FAST_PREFIX)
19972             /* ??? next two lines just !satisfies_constraint_K (...) */
19973             || !CONST_INT_P (operands[2])
19974             || satisfies_constraint_K (operands[2])))
19975        || (GET_MODE (operands[0]) == QImode
19976            && (TARGET_PROMOTE_QImode || optimize_size)))"
19977   [(parallel [(set (match_dup 0)
19978                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
19979               (clobber (reg:CC FLAGS_REG))])]
19980   "operands[0] = gen_lowpart (SImode, operands[0]);
19981    operands[1] = gen_lowpart (SImode, operands[1]);
19982    if (GET_CODE (operands[3]) != ASHIFT)
19983      operands[2] = gen_lowpart (SImode, operands[2]);
19984    PUT_MODE (operands[3], SImode);")
19985
19986 ; Promote the QImode tests, as i386 has encoding of the AND
19987 ; instruction with 32-bit sign-extended immediate and thus the
19988 ; instruction size is unchanged, except in the %eax case for
19989 ; which it is increased by one byte, hence the ! optimize_size.
19990 (define_split
19991   [(set (match_operand 0 "flags_reg_operand" "")
19992         (match_operator 2 "compare_operator"
19993           [(and (match_operand 3 "aligned_operand" "")
19994                 (match_operand 4 "const_int_operand" ""))
19995            (const_int 0)]))
19996    (set (match_operand 1 "register_operand" "")
19997         (and (match_dup 3) (match_dup 4)))]
19998   "! TARGET_PARTIAL_REG_STALL && reload_completed
19999    && ! optimize_size
20000    && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
20001        || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))
20002    /* Ensure that the operand will remain sign-extended immediate.  */
20003    && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)"
20004   [(parallel [(set (match_dup 0)
20005                    (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
20006                                     (const_int 0)]))
20007               (set (match_dup 1)
20008                    (and:SI (match_dup 3) (match_dup 4)))])]
20009 {
20010   operands[4]
20011     = gen_int_mode (INTVAL (operands[4])
20012                     & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
20013   operands[1] = gen_lowpart (SImode, operands[1]);
20014   operands[3] = gen_lowpart (SImode, operands[3]);
20015 })
20016
20017 ; Don't promote the QImode tests, as i386 doesn't have encoding of
20018 ; the TEST instruction with 32-bit sign-extended immediate and thus
20019 ; the instruction size would at least double, which is not what we
20020 ; want even with ! optimize_size.
20021 (define_split
20022   [(set (match_operand 0 "flags_reg_operand" "")
20023         (match_operator 1 "compare_operator"
20024           [(and (match_operand:HI 2 "aligned_operand" "")
20025                 (match_operand:HI 3 "const_int_operand" ""))
20026            (const_int 0)]))]
20027   "! TARGET_PARTIAL_REG_STALL && reload_completed
20028    && ! TARGET_FAST_PREFIX
20029    && ! optimize_size
20030    /* Ensure that the operand will remain sign-extended immediate.  */
20031    && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)"
20032   [(set (match_dup 0)
20033         (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
20034                          (const_int 0)]))]
20035 {
20036   operands[3]
20037     = gen_int_mode (INTVAL (operands[3])
20038                     & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
20039   operands[2] = gen_lowpart (SImode, operands[2]);
20040 })
20041
20042 (define_split
20043   [(set (match_operand 0 "register_operand" "")
20044         (neg (match_operand 1 "register_operand" "")))
20045    (clobber (reg:CC FLAGS_REG))]
20046   "! TARGET_PARTIAL_REG_STALL && reload_completed
20047    && (GET_MODE (operands[0]) == HImode
20048        || (GET_MODE (operands[0]) == QImode
20049            && (TARGET_PROMOTE_QImode || optimize_size)))"
20050   [(parallel [(set (match_dup 0)
20051                    (neg:SI (match_dup 1)))
20052               (clobber (reg:CC FLAGS_REG))])]
20053   "operands[0] = gen_lowpart (SImode, operands[0]);
20054    operands[1] = gen_lowpart (SImode, operands[1]);")
20055
20056 (define_split
20057   [(set (match_operand 0 "register_operand" "")
20058         (not (match_operand 1 "register_operand" "")))]
20059   "! TARGET_PARTIAL_REG_STALL && reload_completed
20060    && (GET_MODE (operands[0]) == HImode
20061        || (GET_MODE (operands[0]) == QImode
20062            && (TARGET_PROMOTE_QImode || optimize_size)))"
20063   [(set (match_dup 0)
20064         (not:SI (match_dup 1)))]
20065   "operands[0] = gen_lowpart (SImode, operands[0]);
20066    operands[1] = gen_lowpart (SImode, operands[1]);")
20067
20068 (define_split
20069   [(set (match_operand 0 "register_operand" "")
20070         (if_then_else (match_operator 1 "comparison_operator"
20071                                 [(reg FLAGS_REG) (const_int 0)])
20072                       (match_operand 2 "register_operand" "")
20073                       (match_operand 3 "register_operand" "")))]
20074   "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE
20075    && (GET_MODE (operands[0]) == HImode
20076        || (GET_MODE (operands[0]) == QImode
20077            && (TARGET_PROMOTE_QImode || optimize_size)))"
20078   [(set (match_dup 0)
20079         (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
20080   "operands[0] = gen_lowpart (SImode, operands[0]);
20081    operands[2] = gen_lowpart (SImode, operands[2]);
20082    operands[3] = gen_lowpart (SImode, operands[3]);")
20083
20084 \f
20085 ;; RTL Peephole optimizations, run before sched2.  These primarily look to
20086 ;; transform a complex memory operation into two memory to register operations.
20087
20088 ;; Don't push memory operands
20089 (define_peephole2
20090   [(set (match_operand:SI 0 "push_operand" "")
20091         (match_operand:SI 1 "memory_operand" ""))
20092    (match_scratch:SI 2 "r")]
20093   "!optimize_size && !TARGET_PUSH_MEMORY
20094    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
20095   [(set (match_dup 2) (match_dup 1))
20096    (set (match_dup 0) (match_dup 2))]
20097   "")
20098
20099 (define_peephole2
20100   [(set (match_operand:DI 0 "push_operand" "")
20101         (match_operand:DI 1 "memory_operand" ""))
20102    (match_scratch:DI 2 "r")]
20103   "!optimize_size && !TARGET_PUSH_MEMORY
20104    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
20105   [(set (match_dup 2) (match_dup 1))
20106    (set (match_dup 0) (match_dup 2))]
20107   "")
20108
20109 ;; We need to handle SFmode only, because DFmode and XFmode is split to
20110 ;; SImode pushes.
20111 (define_peephole2
20112   [(set (match_operand:SF 0 "push_operand" "")
20113         (match_operand:SF 1 "memory_operand" ""))
20114    (match_scratch:SF 2 "r")]
20115   "!optimize_size && !TARGET_PUSH_MEMORY
20116    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
20117   [(set (match_dup 2) (match_dup 1))
20118    (set (match_dup 0) (match_dup 2))]
20119   "")
20120
20121 (define_peephole2
20122   [(set (match_operand:HI 0 "push_operand" "")
20123         (match_operand:HI 1 "memory_operand" ""))
20124    (match_scratch:HI 2 "r")]
20125   "!optimize_size && !TARGET_PUSH_MEMORY
20126    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
20127   [(set (match_dup 2) (match_dup 1))
20128    (set (match_dup 0) (match_dup 2))]
20129   "")
20130
20131 (define_peephole2
20132   [(set (match_operand:QI 0 "push_operand" "")
20133         (match_operand:QI 1 "memory_operand" ""))
20134    (match_scratch:QI 2 "q")]
20135   "!optimize_size && !TARGET_PUSH_MEMORY
20136    && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
20137   [(set (match_dup 2) (match_dup 1))
20138    (set (match_dup 0) (match_dup 2))]
20139   "")
20140
20141 ;; Don't move an immediate directly to memory when the instruction
20142 ;; gets too big.
20143 (define_peephole2
20144   [(match_scratch:SI 1 "r")
20145    (set (match_operand:SI 0 "memory_operand" "")
20146         (const_int 0))]
20147   "! optimize_size
20148    && ! TARGET_USE_MOV0
20149    && TARGET_SPLIT_LONG_MOVES
20150    && get_attr_length (insn) >= ix86_cost->large_insn
20151    && peep2_regno_dead_p (0, FLAGS_REG)"
20152   [(parallel [(set (match_dup 1) (const_int 0))
20153               (clobber (reg:CC FLAGS_REG))])
20154    (set (match_dup 0) (match_dup 1))]
20155   "")
20156
20157 (define_peephole2
20158   [(match_scratch:HI 1 "r")
20159    (set (match_operand:HI 0 "memory_operand" "")
20160         (const_int 0))]
20161   "! optimize_size
20162    && ! TARGET_USE_MOV0
20163    && TARGET_SPLIT_LONG_MOVES
20164    && get_attr_length (insn) >= ix86_cost->large_insn
20165    && peep2_regno_dead_p (0, FLAGS_REG)"
20166   [(parallel [(set (match_dup 2) (const_int 0))
20167               (clobber (reg:CC FLAGS_REG))])
20168    (set (match_dup 0) (match_dup 1))]
20169   "operands[2] = gen_lowpart (SImode, operands[1]);")
20170
20171 (define_peephole2
20172   [(match_scratch:QI 1 "q")
20173    (set (match_operand:QI 0 "memory_operand" "")
20174         (const_int 0))]
20175   "! optimize_size
20176    && ! TARGET_USE_MOV0
20177    && TARGET_SPLIT_LONG_MOVES
20178    && get_attr_length (insn) >= ix86_cost->large_insn
20179    && peep2_regno_dead_p (0, FLAGS_REG)"
20180   [(parallel [(set (match_dup 2) (const_int 0))
20181               (clobber (reg:CC FLAGS_REG))])
20182    (set (match_dup 0) (match_dup 1))]
20183   "operands[2] = gen_lowpart (SImode, operands[1]);")
20184
20185 (define_peephole2
20186   [(match_scratch:SI 2 "r")
20187    (set (match_operand:SI 0 "memory_operand" "")
20188         (match_operand:SI 1 "immediate_operand" ""))]
20189   "! optimize_size
20190    && TARGET_SPLIT_LONG_MOVES
20191    && get_attr_length (insn) >= ix86_cost->large_insn"
20192   [(set (match_dup 2) (match_dup 1))
20193    (set (match_dup 0) (match_dup 2))]
20194   "")
20195
20196 (define_peephole2
20197   [(match_scratch:HI 2 "r")
20198    (set (match_operand:HI 0 "memory_operand" "")
20199         (match_operand:HI 1 "immediate_operand" ""))]
20200   "! optimize_size
20201    && TARGET_SPLIT_LONG_MOVES
20202    && get_attr_length (insn) >= ix86_cost->large_insn"
20203   [(set (match_dup 2) (match_dup 1))
20204    (set (match_dup 0) (match_dup 2))]
20205   "")
20206
20207 (define_peephole2
20208   [(match_scratch:QI 2 "q")
20209    (set (match_operand:QI 0 "memory_operand" "")
20210         (match_operand:QI 1 "immediate_operand" ""))]
20211   "! optimize_size
20212    && TARGET_SPLIT_LONG_MOVES
20213    && get_attr_length (insn) >= ix86_cost->large_insn"
20214   [(set (match_dup 2) (match_dup 1))
20215    (set (match_dup 0) (match_dup 2))]
20216   "")
20217
20218 ;; Don't compare memory with zero, load and use a test instead.
20219 (define_peephole2
20220   [(set (match_operand 0 "flags_reg_operand" "")
20221         (match_operator 1 "compare_operator"
20222           [(match_operand:SI 2 "memory_operand" "")
20223            (const_int 0)]))
20224    (match_scratch:SI 3 "r")]
20225   " ! optimize_size && ix86_match_ccmode (insn, CCNOmode)"
20226   [(set (match_dup 3) (match_dup 2))
20227    (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))]
20228   "")
20229
20230 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer.
20231 ;; Don't split NOTs with a displacement operand, because resulting XOR
20232 ;; will not be pairable anyway.
20233 ;;
20234 ;; On AMD K6, NOT is vector decoded with memory operand that cannot be
20235 ;; represented using a modRM byte.  The XOR replacement is long decoded,
20236 ;; so this split helps here as well.
20237 ;;
20238 ;; Note: Can't do this as a regular split because we can't get proper
20239 ;; lifetime information then.
20240
20241 (define_peephole2
20242   [(set (match_operand:SI 0 "nonimmediate_operand" "")
20243         (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
20244   "!optimize_size
20245    && ((TARGET_NOT_UNPAIRABLE
20246         && (!MEM_P (operands[0])
20247             || !memory_displacement_operand (operands[0], SImode)))
20248        || (TARGET_NOT_VECTORMODE && long_memory_operand (operands[0], SImode)))
20249    && peep2_regno_dead_p (0, FLAGS_REG)"
20250   [(parallel [(set (match_dup 0)
20251                    (xor:SI (match_dup 1) (const_int -1)))
20252               (clobber (reg:CC FLAGS_REG))])]
20253   "")
20254
20255 (define_peephole2
20256   [(set (match_operand:HI 0 "nonimmediate_operand" "")
20257         (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
20258   "!optimize_size
20259    && ((TARGET_NOT_UNPAIRABLE
20260         && (!MEM_P (operands[0])
20261             || !memory_displacement_operand (operands[0], HImode)))
20262        || (TARGET_NOT_VECTORMODE && long_memory_operand (operands[0], HImode)))
20263    && peep2_regno_dead_p (0, FLAGS_REG)"
20264   [(parallel [(set (match_dup 0)
20265                    (xor:HI (match_dup 1) (const_int -1)))
20266               (clobber (reg:CC FLAGS_REG))])]
20267   "")
20268
20269 (define_peephole2
20270   [(set (match_operand:QI 0 "nonimmediate_operand" "")
20271         (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
20272   "!optimize_size
20273    && ((TARGET_NOT_UNPAIRABLE
20274         && (!MEM_P (operands[0])
20275             || !memory_displacement_operand (operands[0], QImode)))
20276        || (TARGET_NOT_VECTORMODE && long_memory_operand (operands[0], QImode)))
20277    && peep2_regno_dead_p (0, FLAGS_REG)"
20278   [(parallel [(set (match_dup 0)
20279                    (xor:QI (match_dup 1) (const_int -1)))
20280               (clobber (reg:CC FLAGS_REG))])]
20281   "")
20282
20283 ;; Non pairable "test imm, reg" instructions can be translated to
20284 ;; "and imm, reg" if reg dies.  The "and" form is also shorter (one
20285 ;; byte opcode instead of two, have a short form for byte operands),
20286 ;; so do it for other CPUs as well.  Given that the value was dead,
20287 ;; this should not create any new dependencies.  Pass on the sub-word
20288 ;; versions if we're concerned about partial register stalls.
20289
20290 (define_peephole2
20291   [(set (match_operand 0 "flags_reg_operand" "")
20292         (match_operator 1 "compare_operator"
20293           [(and:SI (match_operand:SI 2 "register_operand" "")
20294                    (match_operand:SI 3 "immediate_operand" ""))
20295            (const_int 0)]))]
20296   "ix86_match_ccmode (insn, CCNOmode)
20297    && (true_regnum (operands[2]) != AX_REG
20298        || satisfies_constraint_K (operands[3]))
20299    && peep2_reg_dead_p (1, operands[2])"
20300   [(parallel
20301      [(set (match_dup 0)
20302            (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
20303                             (const_int 0)]))
20304       (set (match_dup 2)
20305            (and:SI (match_dup 2) (match_dup 3)))])]
20306   "")
20307
20308 ;; We don't need to handle HImode case, because it will be promoted to SImode
20309 ;; on ! TARGET_PARTIAL_REG_STALL
20310
20311 (define_peephole2
20312   [(set (match_operand 0 "flags_reg_operand" "")
20313         (match_operator 1 "compare_operator"
20314           [(and:QI (match_operand:QI 2 "register_operand" "")
20315                    (match_operand:QI 3 "immediate_operand" ""))
20316            (const_int 0)]))]
20317   "! TARGET_PARTIAL_REG_STALL
20318    && ix86_match_ccmode (insn, CCNOmode)
20319    && true_regnum (operands[2]) != AX_REG
20320    && peep2_reg_dead_p (1, operands[2])"
20321   [(parallel
20322      [(set (match_dup 0)
20323            (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
20324                             (const_int 0)]))
20325       (set (match_dup 2)
20326            (and:QI (match_dup 2) (match_dup 3)))])]
20327   "")
20328
20329 (define_peephole2
20330   [(set (match_operand 0 "flags_reg_operand" "")
20331         (match_operator 1 "compare_operator"
20332           [(and:SI
20333              (zero_extract:SI
20334                (match_operand 2 "ext_register_operand" "")
20335                (const_int 8)
20336                (const_int 8))
20337              (match_operand 3 "const_int_operand" ""))
20338            (const_int 0)]))]
20339   "! TARGET_PARTIAL_REG_STALL
20340    && ix86_match_ccmode (insn, CCNOmode)
20341    && true_regnum (operands[2]) != AX_REG
20342    && peep2_reg_dead_p (1, operands[2])"
20343   [(parallel [(set (match_dup 0)
20344                    (match_op_dup 1
20345                      [(and:SI
20346                         (zero_extract:SI
20347                           (match_dup 2)
20348                           (const_int 8)
20349                           (const_int 8))
20350                         (match_dup 3))
20351                       (const_int 0)]))
20352               (set (zero_extract:SI (match_dup 2)
20353                                     (const_int 8)
20354                                     (const_int 8))
20355                    (and:SI
20356                      (zero_extract:SI
20357                        (match_dup 2)
20358                        (const_int 8)
20359                        (const_int 8))
20360                      (match_dup 3)))])]
20361   "")
20362
20363 ;; Don't do logical operations with memory inputs.
20364 (define_peephole2
20365   [(match_scratch:SI 2 "r")
20366    (parallel [(set (match_operand:SI 0 "register_operand" "")
20367                    (match_operator:SI 3 "arith_or_logical_operator"
20368                      [(match_dup 0)
20369                       (match_operand:SI 1 "memory_operand" "")]))
20370               (clobber (reg:CC FLAGS_REG))])]
20371   "! optimize_size && ! TARGET_READ_MODIFY"
20372   [(set (match_dup 2) (match_dup 1))
20373    (parallel [(set (match_dup 0)
20374                    (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
20375               (clobber (reg:CC FLAGS_REG))])]
20376   "")
20377
20378 (define_peephole2
20379   [(match_scratch:SI 2 "r")
20380    (parallel [(set (match_operand:SI 0 "register_operand" "")
20381                    (match_operator:SI 3 "arith_or_logical_operator"
20382                      [(match_operand:SI 1 "memory_operand" "")
20383                       (match_dup 0)]))
20384               (clobber (reg:CC FLAGS_REG))])]
20385   "! optimize_size && ! TARGET_READ_MODIFY"
20386   [(set (match_dup 2) (match_dup 1))
20387    (parallel [(set (match_dup 0)
20388                    (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
20389               (clobber (reg:CC FLAGS_REG))])]
20390   "")
20391
20392 ; Don't do logical operations with memory outputs
20393 ;
20394 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
20395 ; instruction into two 1-uop insns plus a 2-uop insn.  That last has
20396 ; the same decoder scheduling characteristics as the original.
20397
20398 (define_peephole2
20399   [(match_scratch:SI 2 "r")
20400    (parallel [(set (match_operand:SI 0 "memory_operand" "")
20401                    (match_operator:SI 3 "arith_or_logical_operator"
20402                      [(match_dup 0)
20403                       (match_operand:SI 1 "nonmemory_operand" "")]))
20404               (clobber (reg:CC FLAGS_REG))])]
20405   "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
20406   [(set (match_dup 2) (match_dup 0))
20407    (parallel [(set (match_dup 2)
20408                    (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
20409               (clobber (reg:CC FLAGS_REG))])
20410    (set (match_dup 0) (match_dup 2))]
20411   "")
20412
20413 (define_peephole2
20414   [(match_scratch:SI 2 "r")
20415    (parallel [(set (match_operand:SI 0 "memory_operand" "")
20416                    (match_operator:SI 3 "arith_or_logical_operator"
20417                      [(match_operand:SI 1 "nonmemory_operand" "")
20418                       (match_dup 0)]))
20419               (clobber (reg:CC FLAGS_REG))])]
20420   "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
20421   [(set (match_dup 2) (match_dup 0))
20422    (parallel [(set (match_dup 2)
20423                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
20424               (clobber (reg:CC FLAGS_REG))])
20425    (set (match_dup 0) (match_dup 2))]
20426   "")
20427
20428 ;; Attempt to always use XOR for zeroing registers.
20429 (define_peephole2
20430   [(set (match_operand 0 "register_operand" "")
20431         (match_operand 1 "const0_operand" ""))]
20432   "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD
20433    && (! TARGET_USE_MOV0 || optimize_size)
20434    && GENERAL_REG_P (operands[0])
20435    && peep2_regno_dead_p (0, FLAGS_REG)"
20436   [(parallel [(set (match_dup 0) (const_int 0))
20437               (clobber (reg:CC FLAGS_REG))])]
20438 {
20439   operands[0] = gen_lowpart (word_mode, operands[0]);
20440 })
20441
20442 (define_peephole2
20443   [(set (strict_low_part (match_operand 0 "register_operand" ""))
20444         (const_int 0))]
20445   "(GET_MODE (operands[0]) == QImode
20446     || GET_MODE (operands[0]) == HImode)
20447    && (! TARGET_USE_MOV0 || optimize_size)
20448    && peep2_regno_dead_p (0, FLAGS_REG)"
20449   [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
20450               (clobber (reg:CC FLAGS_REG))])])
20451
20452 ;; For HI and SI modes, or $-1,reg is smaller than mov $-1,reg.
20453 (define_peephole2
20454   [(set (match_operand 0 "register_operand" "")
20455         (const_int -1))]
20456   "(GET_MODE (operands[0]) == HImode
20457     || GET_MODE (operands[0]) == SImode
20458     || (GET_MODE (operands[0]) == DImode && TARGET_64BIT))
20459    && (optimize_size || TARGET_MOVE_M1_VIA_OR)
20460    && peep2_regno_dead_p (0, FLAGS_REG)"
20461   [(parallel [(set (match_dup 0) (const_int -1))
20462               (clobber (reg:CC FLAGS_REG))])]
20463   "operands[0] = gen_lowpart (GET_MODE (operands[0]) == DImode ? DImode : SImode,
20464                               operands[0]);")
20465
20466 ;; Attempt to convert simple leas to adds. These can be created by
20467 ;; move expanders.
20468 (define_peephole2
20469   [(set (match_operand:SI 0 "register_operand" "")
20470         (plus:SI (match_dup 0)
20471                  (match_operand:SI 1 "nonmemory_operand" "")))]
20472   "peep2_regno_dead_p (0, FLAGS_REG)"
20473   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
20474               (clobber (reg:CC FLAGS_REG))])]
20475   "")
20476
20477 (define_peephole2
20478   [(set (match_operand:SI 0 "register_operand" "")
20479         (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
20480                             (match_operand:DI 2 "nonmemory_operand" "")) 0))]
20481   "peep2_regno_dead_p (0, FLAGS_REG) && REGNO (operands[0]) == REGNO (operands[1])"
20482   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
20483               (clobber (reg:CC FLAGS_REG))])]
20484   "operands[2] = gen_lowpart (SImode, operands[2]);")
20485
20486 (define_peephole2
20487   [(set (match_operand:DI 0 "register_operand" "")
20488         (plus:DI (match_dup 0)
20489                  (match_operand:DI 1 "x86_64_general_operand" "")))]
20490   "peep2_regno_dead_p (0, FLAGS_REG)"
20491   [(parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
20492               (clobber (reg:CC FLAGS_REG))])]
20493   "")
20494
20495 (define_peephole2
20496   [(set (match_operand:SI 0 "register_operand" "")
20497         (mult:SI (match_dup 0)
20498                  (match_operand:SI 1 "const_int_operand" "")))]
20499   "exact_log2 (INTVAL (operands[1])) >= 0
20500    && peep2_regno_dead_p (0, FLAGS_REG)"
20501   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
20502               (clobber (reg:CC FLAGS_REG))])]
20503   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
20504
20505 (define_peephole2
20506   [(set (match_operand:DI 0 "register_operand" "")
20507         (mult:DI (match_dup 0)
20508                  (match_operand:DI 1 "const_int_operand" "")))]
20509   "exact_log2 (INTVAL (operands[1])) >= 0
20510    && peep2_regno_dead_p (0, FLAGS_REG)"
20511   [(parallel [(set (match_dup 0) (ashift:DI (match_dup 0) (match_dup 2)))
20512               (clobber (reg:CC FLAGS_REG))])]
20513   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
20514
20515 (define_peephole2
20516   [(set (match_operand:SI 0 "register_operand" "")
20517         (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
20518                    (match_operand:DI 2 "const_int_operand" "")) 0))]
20519   "exact_log2 (INTVAL (operands[2])) >= 0
20520    && REGNO (operands[0]) == REGNO (operands[1])
20521    && peep2_regno_dead_p (0, FLAGS_REG)"
20522   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
20523               (clobber (reg:CC FLAGS_REG))])]
20524   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
20525
20526 ;; The ESP adjustments can be done by the push and pop instructions.  Resulting
20527 ;; code is shorter, since push is only 1 byte, while add imm, %esp 3 bytes.  On
20528 ;; many CPUs it is also faster, since special hardware to avoid esp
20529 ;; dependencies is present.
20530
20531 ;; While some of these conversions may be done using splitters, we use peepholes
20532 ;; in order to allow combine_stack_adjustments pass to see nonobfuscated RTL.
20533
20534 ;; Convert prologue esp subtractions to push.
20535 ;; We need register to push.  In order to keep verify_flow_info happy we have
20536 ;; two choices
20537 ;; - use scratch and clobber it in order to avoid dependencies
20538 ;; - use already live register
20539 ;; We can't use the second way right now, since there is no reliable way how to
20540 ;; verify that given register is live.  First choice will also most likely in
20541 ;; fewer dependencies.  On the place of esp adjustments it is very likely that
20542 ;; call clobbered registers are dead.  We may want to use base pointer as an
20543 ;; alternative when no register is available later.
20544
20545 (define_peephole2
20546   [(match_scratch:SI 0 "r")
20547    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
20548               (clobber (reg:CC FLAGS_REG))
20549               (clobber (mem:BLK (scratch)))])]
20550   "optimize_size || !TARGET_SUB_ESP_4"
20551   [(clobber (match_dup 0))
20552    (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
20553               (clobber (mem:BLK (scratch)))])])
20554
20555 (define_peephole2
20556   [(match_scratch:SI 0 "r")
20557    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
20558               (clobber (reg:CC FLAGS_REG))
20559               (clobber (mem:BLK (scratch)))])]
20560   "optimize_size || !TARGET_SUB_ESP_8"
20561   [(clobber (match_dup 0))
20562    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
20563    (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
20564               (clobber (mem:BLK (scratch)))])])
20565
20566 ;; Convert esp subtractions to push.
20567 (define_peephole2
20568   [(match_scratch:SI 0 "r")
20569    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
20570               (clobber (reg:CC FLAGS_REG))])]
20571   "optimize_size || !TARGET_SUB_ESP_4"
20572   [(clobber (match_dup 0))
20573    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
20574
20575 (define_peephole2
20576   [(match_scratch:SI 0 "r")
20577    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
20578               (clobber (reg:CC FLAGS_REG))])]
20579   "optimize_size || !TARGET_SUB_ESP_8"
20580   [(clobber (match_dup 0))
20581    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
20582    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
20583
20584 ;; Convert epilogue deallocator to pop.
20585 (define_peephole2
20586   [(match_scratch:SI 0 "r")
20587    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
20588               (clobber (reg:CC FLAGS_REG))
20589               (clobber (mem:BLK (scratch)))])]
20590   "optimize_size || !TARGET_ADD_ESP_4"
20591   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20592               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
20593               (clobber (mem:BLK (scratch)))])]
20594   "")
20595
20596 ;; Two pops case is tricky, since pop causes dependency on destination register.
20597 ;; We use two registers if available.
20598 (define_peephole2
20599   [(match_scratch:SI 0 "r")
20600    (match_scratch:SI 1 "r")
20601    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
20602               (clobber (reg:CC FLAGS_REG))
20603               (clobber (mem:BLK (scratch)))])]
20604   "optimize_size || !TARGET_ADD_ESP_8"
20605   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20606               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
20607               (clobber (mem:BLK (scratch)))])
20608    (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
20609               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
20610   "")
20611
20612 (define_peephole2
20613   [(match_scratch:SI 0 "r")
20614    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
20615               (clobber (reg:CC FLAGS_REG))
20616               (clobber (mem:BLK (scratch)))])]
20617   "optimize_size"
20618   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20619               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
20620               (clobber (mem:BLK (scratch)))])
20621    (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20622               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
20623   "")
20624
20625 ;; Convert esp additions to pop.
20626 (define_peephole2
20627   [(match_scratch:SI 0 "r")
20628    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
20629               (clobber (reg:CC FLAGS_REG))])]
20630   ""
20631   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20632               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
20633   "")
20634
20635 ;; Two pops case is tricky, since pop causes dependency on destination register.
20636 ;; We use two registers if available.
20637 (define_peephole2
20638   [(match_scratch:SI 0 "r")
20639    (match_scratch:SI 1 "r")
20640    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
20641               (clobber (reg:CC FLAGS_REG))])]
20642   ""
20643   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20644               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
20645    (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
20646               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
20647   "")
20648
20649 (define_peephole2
20650   [(match_scratch:SI 0 "r")
20651    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
20652               (clobber (reg:CC FLAGS_REG))])]
20653   "optimize_size"
20654   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20655               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
20656    (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
20657               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
20658   "")
20659 \f
20660 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
20661 ;; required and register dies.  Similarly for 128 to plus -128.
20662 (define_peephole2
20663   [(set (match_operand 0 "flags_reg_operand" "")
20664         (match_operator 1 "compare_operator"
20665           [(match_operand 2 "register_operand" "")
20666            (match_operand 3 "const_int_operand" "")]))]
20667   "(INTVAL (operands[3]) == -1
20668     || INTVAL (operands[3]) == 1
20669     || INTVAL (operands[3]) == 128)
20670    && ix86_match_ccmode (insn, CCGCmode)
20671    && peep2_reg_dead_p (1, operands[2])"
20672   [(parallel [(set (match_dup 0)
20673                    (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
20674               (clobber (match_dup 2))])]
20675   "")
20676 \f
20677 (define_peephole2
20678   [(match_scratch:DI 0 "r")
20679    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
20680               (clobber (reg:CC FLAGS_REG))
20681               (clobber (mem:BLK (scratch)))])]
20682   "optimize_size || !TARGET_SUB_ESP_4"
20683   [(clobber (match_dup 0))
20684    (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
20685               (clobber (mem:BLK (scratch)))])])
20686
20687 (define_peephole2
20688   [(match_scratch:DI 0 "r")
20689    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
20690               (clobber (reg:CC FLAGS_REG))
20691               (clobber (mem:BLK (scratch)))])]
20692   "optimize_size || !TARGET_SUB_ESP_8"
20693   [(clobber (match_dup 0))
20694    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
20695    (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
20696               (clobber (mem:BLK (scratch)))])])
20697
20698 ;; Convert esp subtractions to push.
20699 (define_peephole2
20700   [(match_scratch:DI 0 "r")
20701    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
20702               (clobber (reg:CC FLAGS_REG))])]
20703   "optimize_size || !TARGET_SUB_ESP_4"
20704   [(clobber (match_dup 0))
20705    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
20706
20707 (define_peephole2
20708   [(match_scratch:DI 0 "r")
20709    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
20710               (clobber (reg:CC FLAGS_REG))])]
20711   "optimize_size || !TARGET_SUB_ESP_8"
20712   [(clobber (match_dup 0))
20713    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
20714    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
20715
20716 ;; Convert epilogue deallocator to pop.
20717 (define_peephole2
20718   [(match_scratch:DI 0 "r")
20719    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
20720               (clobber (reg:CC FLAGS_REG))
20721               (clobber (mem:BLK (scratch)))])]
20722   "optimize_size || !TARGET_ADD_ESP_4"
20723   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20724               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
20725               (clobber (mem:BLK (scratch)))])]
20726   "")
20727
20728 ;; Two pops case is tricky, since pop causes dependency on destination register.
20729 ;; We use two registers if available.
20730 (define_peephole2
20731   [(match_scratch:DI 0 "r")
20732    (match_scratch:DI 1 "r")
20733    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
20734               (clobber (reg:CC FLAGS_REG))
20735               (clobber (mem:BLK (scratch)))])]
20736   "optimize_size || !TARGET_ADD_ESP_8"
20737   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20738               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
20739               (clobber (mem:BLK (scratch)))])
20740    (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
20741               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
20742   "")
20743
20744 (define_peephole2
20745   [(match_scratch:DI 0 "r")
20746    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
20747               (clobber (reg:CC FLAGS_REG))
20748               (clobber (mem:BLK (scratch)))])]
20749   "optimize_size"
20750   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20751               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
20752               (clobber (mem:BLK (scratch)))])
20753    (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20754               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
20755   "")
20756
20757 ;; Convert esp additions to pop.
20758 (define_peephole2
20759   [(match_scratch:DI 0 "r")
20760    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
20761               (clobber (reg:CC FLAGS_REG))])]
20762   ""
20763   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20764               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
20765   "")
20766
20767 ;; Two pops case is tricky, since pop causes dependency on destination register.
20768 ;; We use two registers if available.
20769 (define_peephole2
20770   [(match_scratch:DI 0 "r")
20771    (match_scratch:DI 1 "r")
20772    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
20773               (clobber (reg:CC FLAGS_REG))])]
20774   ""
20775   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20776               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
20777    (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
20778               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
20779   "")
20780
20781 (define_peephole2
20782   [(match_scratch:DI 0 "r")
20783    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
20784               (clobber (reg:CC FLAGS_REG))])]
20785   "optimize_size"
20786   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20787               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
20788    (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
20789               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
20790   "")
20791 \f
20792 ;; Convert imul by three, five and nine into lea
20793 (define_peephole2
20794   [(parallel
20795     [(set (match_operand:SI 0 "register_operand" "")
20796           (mult:SI (match_operand:SI 1 "register_operand" "")
20797                    (match_operand:SI 2 "const_int_operand" "")))
20798      (clobber (reg:CC FLAGS_REG))])]
20799   "INTVAL (operands[2]) == 3
20800    || INTVAL (operands[2]) == 5
20801    || INTVAL (operands[2]) == 9"
20802   [(set (match_dup 0)
20803         (plus:SI (mult:SI (match_dup 1) (match_dup 2))
20804                  (match_dup 1)))]
20805   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
20806
20807 (define_peephole2
20808   [(parallel
20809     [(set (match_operand:SI 0 "register_operand" "")
20810           (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
20811                    (match_operand:SI 2 "const_int_operand" "")))
20812      (clobber (reg:CC FLAGS_REG))])]
20813   "!optimize_size
20814    && (INTVAL (operands[2]) == 3
20815        || INTVAL (operands[2]) == 5
20816        || INTVAL (operands[2]) == 9)"
20817   [(set (match_dup 0) (match_dup 1))
20818    (set (match_dup 0)
20819         (plus:SI (mult:SI (match_dup 0) (match_dup 2))
20820                  (match_dup 0)))]
20821   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
20822
20823 (define_peephole2
20824   [(parallel
20825     [(set (match_operand:DI 0 "register_operand" "")
20826           (mult:DI (match_operand:DI 1 "register_operand" "")
20827                    (match_operand:DI 2 "const_int_operand" "")))
20828      (clobber (reg:CC FLAGS_REG))])]
20829   "TARGET_64BIT
20830    && (INTVAL (operands[2]) == 3
20831        || INTVAL (operands[2]) == 5
20832        || INTVAL (operands[2]) == 9)"
20833   [(set (match_dup 0)
20834         (plus:DI (mult:DI (match_dup 1) (match_dup 2))
20835                  (match_dup 1)))]
20836   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
20837
20838 (define_peephole2
20839   [(parallel
20840     [(set (match_operand:DI 0 "register_operand" "")
20841           (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
20842                    (match_operand:DI 2 "const_int_operand" "")))
20843      (clobber (reg:CC FLAGS_REG))])]
20844   "TARGET_64BIT
20845    && !optimize_size
20846    && (INTVAL (operands[2]) == 3
20847        || INTVAL (operands[2]) == 5
20848        || INTVAL (operands[2]) == 9)"
20849   [(set (match_dup 0) (match_dup 1))
20850    (set (match_dup 0)
20851         (plus:DI (mult:DI (match_dup 0) (match_dup 2))
20852                  (match_dup 0)))]
20853   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
20854
20855 ;; Imul $32bit_imm, mem, reg is vector decoded, while
20856 ;; imul $32bit_imm, reg, reg is direct decoded.
20857 (define_peephole2
20858   [(match_scratch:DI 3 "r")
20859    (parallel [(set (match_operand:DI 0 "register_operand" "")
20860                    (mult:DI (match_operand:DI 1 "memory_operand" "")
20861                             (match_operand:DI 2 "immediate_operand" "")))
20862               (clobber (reg:CC FLAGS_REG))])]
20863   "TARGET_SLOW_IMUL_IMM32_MEM && !optimize_size
20864    && !satisfies_constraint_K (operands[2])"
20865   [(set (match_dup 3) (match_dup 1))
20866    (parallel [(set (match_dup 0) (mult:DI (match_dup 3) (match_dup 2)))
20867               (clobber (reg:CC FLAGS_REG))])]
20868 "")
20869
20870 (define_peephole2
20871   [(match_scratch:SI 3 "r")
20872    (parallel [(set (match_operand:SI 0 "register_operand" "")
20873                    (mult:SI (match_operand:SI 1 "memory_operand" "")
20874                             (match_operand:SI 2 "immediate_operand" "")))
20875               (clobber (reg:CC FLAGS_REG))])]
20876   "TARGET_SLOW_IMUL_IMM32_MEM && !optimize_size
20877    && !satisfies_constraint_K (operands[2])"
20878   [(set (match_dup 3) (match_dup 1))
20879    (parallel [(set (match_dup 0) (mult:SI (match_dup 3) (match_dup 2)))
20880               (clobber (reg:CC FLAGS_REG))])]
20881 "")
20882
20883 (define_peephole2
20884   [(match_scratch:SI 3 "r")
20885    (parallel [(set (match_operand:DI 0 "register_operand" "")
20886                    (zero_extend:DI
20887                      (mult:SI (match_operand:SI 1 "memory_operand" "")
20888                               (match_operand:SI 2 "immediate_operand" ""))))
20889               (clobber (reg:CC FLAGS_REG))])]
20890   "TARGET_SLOW_IMUL_IMM32_MEM && !optimize_size
20891    && !satisfies_constraint_K (operands[2])"
20892   [(set (match_dup 3) (match_dup 1))
20893    (parallel [(set (match_dup 0) (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
20894               (clobber (reg:CC FLAGS_REG))])]
20895 "")
20896
20897 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
20898 ;; Convert it into imul reg, reg
20899 ;; It would be better to force assembler to encode instruction using long
20900 ;; immediate, but there is apparently no way to do so.
20901 (define_peephole2
20902   [(parallel [(set (match_operand:DI 0 "register_operand" "")
20903                    (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
20904                             (match_operand:DI 2 "const_int_operand" "")))
20905               (clobber (reg:CC FLAGS_REG))])
20906    (match_scratch:DI 3 "r")]
20907   "TARGET_SLOW_IMUL_IMM8 && !optimize_size
20908    && satisfies_constraint_K (operands[2])"
20909   [(set (match_dup 3) (match_dup 2))
20910    (parallel [(set (match_dup 0) (mult:DI (match_dup 0) (match_dup 3)))
20911               (clobber (reg:CC FLAGS_REG))])]
20912 {
20913   if (!rtx_equal_p (operands[0], operands[1]))
20914     emit_move_insn (operands[0], operands[1]);
20915 })
20916
20917 (define_peephole2
20918   [(parallel [(set (match_operand:SI 0 "register_operand" "")
20919                    (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
20920                             (match_operand:SI 2 "const_int_operand" "")))
20921               (clobber (reg:CC FLAGS_REG))])
20922    (match_scratch:SI 3 "r")]
20923   "TARGET_SLOW_IMUL_IMM8 && !optimize_size
20924    && satisfies_constraint_K (operands[2])"
20925   [(set (match_dup 3) (match_dup 2))
20926    (parallel [(set (match_dup 0) (mult:SI (match_dup 0) (match_dup 3)))
20927               (clobber (reg:CC FLAGS_REG))])]
20928 {
20929   if (!rtx_equal_p (operands[0], operands[1]))
20930     emit_move_insn (operands[0], operands[1]);
20931 })
20932
20933 (define_peephole2
20934   [(parallel [(set (match_operand:HI 0 "register_operand" "")
20935                    (mult:HI (match_operand:HI 1 "nonimmediate_operand" "")
20936                             (match_operand:HI 2 "immediate_operand" "")))
20937               (clobber (reg:CC FLAGS_REG))])
20938    (match_scratch:HI 3 "r")]
20939   "TARGET_SLOW_IMUL_IMM8 && !optimize_size"
20940   [(set (match_dup 3) (match_dup 2))
20941    (parallel [(set (match_dup 0) (mult:HI (match_dup 0) (match_dup 3)))
20942               (clobber (reg:CC FLAGS_REG))])]
20943 {
20944   if (!rtx_equal_p (operands[0], operands[1]))
20945     emit_move_insn (operands[0], operands[1]);
20946 })
20947
20948 ;; After splitting up read-modify operations, array accesses with memory
20949 ;; operands might end up in form:
20950 ;;  sall    $2, %eax
20951 ;;  movl    4(%esp), %edx
20952 ;;  addl    %edx, %eax
20953 ;; instead of pre-splitting:
20954 ;;  sall    $2, %eax
20955 ;;  addl    4(%esp), %eax
20956 ;; Turn it into:
20957 ;;  movl    4(%esp), %edx
20958 ;;  leal    (%edx,%eax,4), %eax
20959
20960 (define_peephole2
20961   [(parallel [(set (match_operand 0 "register_operand" "")
20962                    (ashift (match_operand 1 "register_operand" "")
20963                            (match_operand 2 "const_int_operand" "")))
20964                (clobber (reg:CC FLAGS_REG))])
20965    (set (match_operand 3 "register_operand")
20966         (match_operand 4 "x86_64_general_operand" ""))
20967    (parallel [(set (match_operand 5 "register_operand" "")
20968                    (plus (match_operand 6 "register_operand" "")
20969                          (match_operand 7 "register_operand" "")))
20970                    (clobber (reg:CC FLAGS_REG))])]
20971   "INTVAL (operands[2]) >= 0 && INTVAL (operands[2]) <= 3
20972    /* Validate MODE for lea.  */
20973    && ((!TARGET_PARTIAL_REG_STALL
20974         && (GET_MODE (operands[0]) == QImode
20975             || GET_MODE (operands[0]) == HImode))
20976        || GET_MODE (operands[0]) == SImode
20977        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
20978    /* We reorder load and the shift.  */
20979    && !rtx_equal_p (operands[1], operands[3])
20980    && !reg_overlap_mentioned_p (operands[0], operands[4])
20981    /* Last PLUS must consist of operand 0 and 3.  */
20982    && !rtx_equal_p (operands[0], operands[3])
20983    && (rtx_equal_p (operands[3], operands[6])
20984        || rtx_equal_p (operands[3], operands[7]))
20985    && (rtx_equal_p (operands[0], operands[6])
20986        || rtx_equal_p (operands[0], operands[7]))
20987    /* The intermediate operand 0 must die or be same as output.  */
20988    && (rtx_equal_p (operands[0], operands[5])
20989        || peep2_reg_dead_p (3, operands[0]))"
20990   [(set (match_dup 3) (match_dup 4))
20991    (set (match_dup 0) (match_dup 1))]
20992 {
20993   enum machine_mode mode = GET_MODE (operands[5]) == DImode ? DImode : SImode;
20994   int scale = 1 << INTVAL (operands[2]);
20995   rtx index = gen_lowpart (Pmode, operands[1]);
20996   rtx base = gen_lowpart (Pmode, operands[3]);
20997   rtx dest = gen_lowpart (mode, operands[5]);
20998
20999   operands[1] = gen_rtx_PLUS (Pmode, base,
21000                               gen_rtx_MULT (Pmode, index, GEN_INT (scale)));
21001   if (mode != Pmode)
21002     operands[1] = gen_rtx_SUBREG (mode, operands[1], 0);
21003   operands[0] = dest;
21004 })
21005 \f
21006 ;; Call-value patterns last so that the wildcard operand does not
21007 ;; disrupt insn-recog's switch tables.
21008
21009 (define_insn "*call_value_pop_0"
21010   [(set (match_operand 0 "" "")
21011         (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
21012               (match_operand:SI 2 "" "")))
21013    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
21014                             (match_operand:SI 3 "immediate_operand" "")))]
21015   "!TARGET_64BIT"
21016 {
21017   if (SIBLING_CALL_P (insn))
21018     return "jmp\t%P1";
21019   else
21020     return "call\t%P1";
21021 }
21022   [(set_attr "type" "callv")])
21023
21024 (define_insn "*call_value_pop_1"
21025   [(set (match_operand 0 "" "")
21026         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
21027               (match_operand:SI 2 "" "")))
21028    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
21029                             (match_operand:SI 3 "immediate_operand" "i")))]
21030   "!TARGET_64BIT"
21031 {
21032   if (constant_call_address_operand (operands[1], Pmode))
21033     {
21034       if (SIBLING_CALL_P (insn))
21035         return "jmp\t%P1";
21036       else
21037         return "call\t%P1";
21038     }
21039   if (SIBLING_CALL_P (insn))
21040     return "jmp\t%A1";
21041   else
21042     return "call\t%A1";
21043 }
21044   [(set_attr "type" "callv")])
21045
21046 (define_insn "*call_value_0"
21047   [(set (match_operand 0 "" "")
21048         (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
21049               (match_operand:SI 2 "" "")))]
21050   "!TARGET_64BIT"
21051 {
21052   if (SIBLING_CALL_P (insn))
21053     return "jmp\t%P1";
21054   else
21055     return "call\t%P1";
21056 }
21057   [(set_attr "type" "callv")])
21058
21059 (define_insn "*call_value_0_rex64"
21060   [(set (match_operand 0 "" "")
21061         (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
21062               (match_operand:DI 2 "const_int_operand" "")))]
21063   "TARGET_64BIT"
21064 {
21065   if (SIBLING_CALL_P (insn))
21066     return "jmp\t%P1";
21067   else
21068     return "call\t%P1";
21069 }
21070   [(set_attr "type" "callv")])
21071
21072 (define_insn "*call_value_1"
21073   [(set (match_operand 0 "" "")
21074         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
21075               (match_operand:SI 2 "" "")))]
21076   "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
21077 {
21078   if (constant_call_address_operand (operands[1], Pmode))
21079     return "call\t%P1";
21080   return "call\t%A1";
21081 }
21082   [(set_attr "type" "callv")])
21083
21084 (define_insn "*sibcall_value_1"
21085   [(set (match_operand 0 "" "")
21086         (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "s,c,d,a"))
21087               (match_operand:SI 2 "" "")))]
21088   "SIBLING_CALL_P (insn) && !TARGET_64BIT"
21089 {
21090   if (constant_call_address_operand (operands[1], Pmode))
21091     return "jmp\t%P1";
21092   return "jmp\t%A1";
21093 }
21094   [(set_attr "type" "callv")])
21095
21096 (define_insn "*call_value_1_rex64"
21097   [(set (match_operand 0 "" "")
21098         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rsm"))
21099               (match_operand:DI 2 "" "")))]
21100   "!SIBLING_CALL_P (insn) && TARGET_64BIT
21101    && ix86_cmodel != CM_LARGE && ix86_cmodel != CM_LARGE_PIC"
21102 {
21103   if (constant_call_address_operand (operands[1], Pmode))
21104     return "call\t%P1";
21105   return "call\t%A1";
21106 }
21107   [(set_attr "type" "callv")])
21108
21109 (define_insn "*call_value_1_rex64_large"
21110   [(set (match_operand 0 "" "")
21111         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rm"))
21112               (match_operand:DI 2 "" "")))]
21113   "!SIBLING_CALL_P (insn) && TARGET_64BIT"
21114   "call\t%A1"
21115   [(set_attr "type" "callv")])
21116
21117 (define_insn "*sibcall_value_1_rex64"
21118   [(set (match_operand 0 "" "")
21119         (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
21120               (match_operand:DI 2 "" "")))]
21121   "SIBLING_CALL_P (insn) && TARGET_64BIT"
21122   "jmp\t%P1"
21123   [(set_attr "type" "callv")])
21124
21125 (define_insn "*sibcall_value_1_rex64_v"
21126   [(set (match_operand 0 "" "")
21127         (call (mem:QI (reg:DI R11_REG))
21128               (match_operand:DI 1 "" "")))]
21129   "SIBLING_CALL_P (insn) && TARGET_64BIT"
21130   "jmp\t{*%%}r11"
21131   [(set_attr "type" "callv")])
21132 \f
21133 ;; We used to use "int $5", in honor of #BR which maps to interrupt vector 5.
21134 ;; That, however, is usually mapped by the OS to SIGSEGV, which is often
21135 ;; caught for use by garbage collectors and the like.  Using an insn that
21136 ;; maps to SIGILL makes it more likely the program will rightfully die.
21137 ;; Keeping with tradition, "6" is in honor of #UD.
21138 (define_insn "trap"
21139   [(trap_if (const_int 1) (const_int 6))]
21140   ""
21141   { return ASM_SHORT "0x0b0f"; }
21142   [(set_attr "length" "2")])
21143
21144 (define_expand "sse_prologue_save"
21145   [(parallel [(set (match_operand:BLK 0 "" "")
21146                    (unspec:BLK [(reg:DI 21)
21147                                 (reg:DI 22)
21148                                 (reg:DI 23)
21149                                 (reg:DI 24)
21150                                 (reg:DI 25)
21151                                 (reg:DI 26)
21152                                 (reg:DI 27)
21153                                 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
21154               (use (match_operand:DI 1 "register_operand" ""))
21155               (use (match_operand:DI 2 "immediate_operand" ""))
21156               (use (label_ref:DI (match_operand 3 "" "")))])]
21157   "TARGET_64BIT"
21158   "")
21159
21160 (define_insn "*sse_prologue_save_insn"
21161   [(set (mem:BLK (plus:DI (match_operand:DI 0 "register_operand" "R")
21162                           (match_operand:DI 4 "const_int_operand" "n")))
21163         (unspec:BLK [(reg:DI 21)
21164                      (reg:DI 22)
21165                      (reg:DI 23)
21166                      (reg:DI 24)
21167                      (reg:DI 25)
21168                      (reg:DI 26)
21169                      (reg:DI 27)
21170                      (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
21171    (use (match_operand:DI 1 "register_operand" "r"))
21172    (use (match_operand:DI 2 "const_int_operand" "i"))
21173    (use (label_ref:DI (match_operand 3 "" "X")))]
21174   "TARGET_64BIT
21175    && INTVAL (operands[4]) + SSE_REGPARM_MAX * 16 - 16 < 128
21176    && INTVAL (operands[4]) + INTVAL (operands[2]) * 16 >= -128"
21177   "*
21178 {
21179   int i;
21180   operands[0] = gen_rtx_MEM (Pmode,
21181                              gen_rtx_PLUS (Pmode, operands[0], operands[4]));
21182   output_asm_insn (\"jmp\\t%A1\", operands);
21183   for (i = SSE_REGPARM_MAX - 1; i >= INTVAL (operands[2]); i--)
21184     {
21185       operands[4] = adjust_address (operands[0], DImode, i*16);
21186       operands[5] = gen_rtx_REG (TImode, SSE_REGNO (i));
21187       PUT_MODE (operands[4], TImode);
21188       if (GET_CODE (XEXP (operands[0], 0)) != PLUS)
21189         output_asm_insn (\"rex\", operands);
21190       output_asm_insn (\"movaps\\t{%5, %4|%4, %5}\", operands);
21191     }
21192   (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
21193                              CODE_LABEL_NUMBER (operands[3]));
21194   return \"\";
21195 }
21196   "
21197   [(set_attr "type" "other")
21198    (set_attr "length_immediate" "0")
21199    (set_attr "length_address" "0")
21200    (set_attr "length" "135")
21201    (set_attr "memory" "store")
21202    (set_attr "modrm" "0")
21203    (set_attr "mode" "DI")])
21204
21205 (define_expand "prefetch"
21206   [(prefetch (match_operand 0 "address_operand" "")
21207              (match_operand:SI 1 "const_int_operand" "")
21208              (match_operand:SI 2 "const_int_operand" ""))]
21209   "TARGET_PREFETCH_SSE || TARGET_3DNOW"
21210 {
21211   int rw = INTVAL (operands[1]);
21212   int locality = INTVAL (operands[2]);
21213
21214   gcc_assert (rw == 0 || rw == 1);
21215   gcc_assert (locality >= 0 && locality <= 3);
21216   gcc_assert (GET_MODE (operands[0]) == Pmode
21217               || GET_MODE (operands[0]) == VOIDmode);
21218
21219   /* Use 3dNOW prefetch in case we are asking for write prefetch not
21220      supported by SSE counterpart or the SSE prefetch is not available
21221      (K6 machines).  Otherwise use SSE prefetch as it allows specifying
21222      of locality.  */
21223   if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
21224     operands[2] = GEN_INT (3);
21225   else
21226     operands[1] = const0_rtx;
21227 })
21228
21229 (define_insn "*prefetch_sse"
21230   [(prefetch (match_operand:SI 0 "address_operand" "p")
21231              (const_int 0)
21232              (match_operand:SI 1 "const_int_operand" ""))]
21233   "TARGET_PREFETCH_SSE && !TARGET_64BIT"
21234 {
21235   static const char * const patterns[4] = {
21236    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
21237   };
21238
21239   int locality = INTVAL (operands[1]);
21240   gcc_assert (locality >= 0 && locality <= 3);
21241
21242   return patterns[locality];
21243 }
21244   [(set_attr "type" "sse")
21245    (set_attr "memory" "none")])
21246
21247 (define_insn "*prefetch_sse_rex"
21248   [(prefetch (match_operand:DI 0 "address_operand" "p")
21249              (const_int 0)
21250              (match_operand:SI 1 "const_int_operand" ""))]
21251   "TARGET_PREFETCH_SSE && TARGET_64BIT"
21252 {
21253   static const char * const patterns[4] = {
21254    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
21255   };
21256
21257   int locality = INTVAL (operands[1]);
21258   gcc_assert (locality >= 0 && locality <= 3);
21259
21260   return patterns[locality];
21261 }
21262   [(set_attr "type" "sse")
21263    (set_attr "memory" "none")])
21264
21265 (define_insn "*prefetch_3dnow"
21266   [(prefetch (match_operand:SI 0 "address_operand" "p")
21267              (match_operand:SI 1 "const_int_operand" "n")
21268              (const_int 3))]
21269   "TARGET_3DNOW && !TARGET_64BIT"
21270 {
21271   if (INTVAL (operands[1]) == 0)
21272     return "prefetch\t%a0";
21273   else
21274     return "prefetchw\t%a0";
21275 }
21276   [(set_attr "type" "mmx")
21277    (set_attr "memory" "none")])
21278
21279 (define_insn "*prefetch_3dnow_rex"
21280   [(prefetch (match_operand:DI 0 "address_operand" "p")
21281              (match_operand:SI 1 "const_int_operand" "n")
21282              (const_int 3))]
21283   "TARGET_3DNOW && TARGET_64BIT"
21284 {
21285   if (INTVAL (operands[1]) == 0)
21286     return "prefetch\t%a0";
21287   else
21288     return "prefetchw\t%a0";
21289 }
21290   [(set_attr "type" "mmx")
21291    (set_attr "memory" "none")])
21292
21293 (define_expand "stack_protect_set"
21294   [(match_operand 0 "memory_operand" "")
21295    (match_operand 1 "memory_operand" "")]
21296   ""
21297 {
21298 #ifdef TARGET_THREAD_SSP_OFFSET
21299   if (TARGET_64BIT)
21300     emit_insn (gen_stack_tls_protect_set_di (operands[0],
21301                                         GEN_INT (TARGET_THREAD_SSP_OFFSET)));
21302   else
21303     emit_insn (gen_stack_tls_protect_set_si (operands[0],
21304                                         GEN_INT (TARGET_THREAD_SSP_OFFSET)));
21305 #else
21306   if (TARGET_64BIT)
21307     emit_insn (gen_stack_protect_set_di (operands[0], operands[1]));
21308   else
21309     emit_insn (gen_stack_protect_set_si (operands[0], operands[1]));
21310 #endif
21311   DONE;
21312 })
21313
21314 (define_insn "stack_protect_set_si"
21315   [(set (match_operand:SI 0 "memory_operand" "=m")
21316         (unspec:SI [(match_operand:SI 1 "memory_operand" "m")] UNSPEC_SP_SET))
21317    (set (match_scratch:SI 2 "=&r") (const_int 0))
21318    (clobber (reg:CC FLAGS_REG))]
21319   ""
21320   "mov{l}\t{%1, %2|%2, %1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
21321   [(set_attr "type" "multi")])
21322
21323 (define_insn "stack_protect_set_di"
21324   [(set (match_operand:DI 0 "memory_operand" "=m")
21325         (unspec:DI [(match_operand:DI 1 "memory_operand" "m")] UNSPEC_SP_SET))
21326    (set (match_scratch:DI 2 "=&r") (const_int 0))
21327    (clobber (reg:CC FLAGS_REG))]
21328   "TARGET_64BIT"
21329   "mov{q}\t{%1, %2|%2, %1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
21330   [(set_attr "type" "multi")])
21331
21332 (define_insn "stack_tls_protect_set_si"
21333   [(set (match_operand:SI 0 "memory_operand" "=m")
21334         (unspec:SI [(match_operand:SI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
21335    (set (match_scratch:SI 2 "=&r") (const_int 0))
21336    (clobber (reg:CC FLAGS_REG))]
21337   ""
21338   "mov{l}\t{%%gs:%P1, %2|%2, DWORD PTR gs:%P1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
21339   [(set_attr "type" "multi")])
21340
21341 (define_insn "stack_tls_protect_set_di"
21342   [(set (match_operand:DI 0 "memory_operand" "=m")
21343         (unspec:DI [(match_operand:DI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
21344    (set (match_scratch:DI 2 "=&r") (const_int 0))
21345    (clobber (reg:CC FLAGS_REG))]
21346   "TARGET_64BIT"
21347   {
21348      /* The kernel uses a different segment register for performance reasons; a
21349         system call would not have to trash the userspace segment register,
21350         which would be expensive */
21351      if (ix86_cmodel != CM_KERNEL)
21352         return "mov{q}\t{%%fs:%P1, %2|%2, QWORD PTR fs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2";
21353      else
21354         return "mov{q}\t{%%gs:%P1, %2|%2, QWORD PTR gs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2";
21355   }
21356   [(set_attr "type" "multi")])
21357
21358 (define_expand "stack_protect_test"
21359   [(match_operand 0 "memory_operand" "")
21360    (match_operand 1 "memory_operand" "")
21361    (match_operand 2 "" "")]
21362   ""
21363 {
21364   rtx flags = gen_rtx_REG (CCZmode, FLAGS_REG);
21365   ix86_compare_op0 = operands[0];
21366   ix86_compare_op1 = operands[1];
21367   ix86_compare_emitted = flags;
21368
21369 #ifdef TARGET_THREAD_SSP_OFFSET
21370   if (TARGET_64BIT)
21371     emit_insn (gen_stack_tls_protect_test_di (flags, operands[0],
21372                                         GEN_INT (TARGET_THREAD_SSP_OFFSET)));
21373   else
21374     emit_insn (gen_stack_tls_protect_test_si (flags, operands[0],
21375                                         GEN_INT (TARGET_THREAD_SSP_OFFSET)));
21376 #else
21377   if (TARGET_64BIT)
21378     emit_insn (gen_stack_protect_test_di (flags, operands[0], operands[1]));
21379   else
21380     emit_insn (gen_stack_protect_test_si (flags, operands[0], operands[1]));
21381 #endif
21382   emit_jump_insn (gen_beq (operands[2]));
21383   DONE;
21384 })
21385
21386 (define_insn "stack_protect_test_si"
21387   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
21388         (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
21389                      (match_operand:SI 2 "memory_operand" "m")]
21390                     UNSPEC_SP_TEST))
21391    (clobber (match_scratch:SI 3 "=&r"))]
21392   ""
21393   "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%2, %3|%3, %2}"
21394   [(set_attr "type" "multi")])
21395
21396 (define_insn "stack_protect_test_di"
21397   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
21398         (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
21399                      (match_operand:DI 2 "memory_operand" "m")]
21400                     UNSPEC_SP_TEST))
21401    (clobber (match_scratch:DI 3 "=&r"))]
21402   "TARGET_64BIT"
21403   "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%2, %3|%3, %2}"
21404   [(set_attr "type" "multi")])
21405
21406 (define_insn "stack_tls_protect_test_si"
21407   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
21408         (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
21409                      (match_operand:SI 2 "const_int_operand" "i")]
21410                     UNSPEC_SP_TLS_TEST))
21411    (clobber (match_scratch:SI 3 "=r"))]
21412   ""
21413   "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%%gs:%P2, %3|%3, DWORD PTR gs:%P2}"
21414   [(set_attr "type" "multi")])
21415
21416 (define_insn "stack_tls_protect_test_di"
21417   [(set (match_operand:CCZ 0 "flags_reg_operand" "")
21418         (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
21419                      (match_operand:DI 2 "const_int_operand" "i")]
21420                     UNSPEC_SP_TLS_TEST))
21421    (clobber (match_scratch:DI 3 "=r"))]
21422   "TARGET_64BIT"
21423   {
21424      /* The kernel uses a different segment register for performance reasons; a
21425         system call would not have to trash the userspace segment register,
21426         which would be expensive */
21427      if (ix86_cmodel != CM_KERNEL)
21428         return "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%fs:%P2, %3|%3, QWORD PTR fs:%P2}";
21429      else
21430         return "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%gs:%P2, %3|%3, QWORD PTR gs:%P2}";
21431   }
21432   [(set_attr "type" "multi")])
21433
21434 (define_mode_iterator CRC32MODE [QI HI SI])
21435 (define_mode_attr crc32modesuffix [(QI "b") (HI "w") (SI "l")])
21436 (define_mode_attr crc32modeconstraint [(QI "qm") (HI "rm") (SI "rm")])
21437
21438 (define_insn "sse4_2_crc32<mode>"
21439   [(set (match_operand:SI 0 "register_operand" "=r")
21440         (unspec:SI
21441           [(match_operand:SI 1 "register_operand" "0")
21442            (match_operand:CRC32MODE 2 "nonimmediate_operand" "<crc32modeconstraint>")]
21443           UNSPEC_CRC32))]
21444   "TARGET_SSE4_2"
21445   "crc32<crc32modesuffix>\t{%2, %0|%0, %2}"
21446   [(set_attr "type" "sselog1")
21447    (set_attr "prefix_rep" "1")
21448    (set_attr "prefix_extra" "1")
21449    (set_attr "mode" "SI")])
21450
21451 (define_insn "sse4_2_crc32di"
21452   [(set (match_operand:DI 0 "register_operand" "=r")
21453         (unspec:DI
21454           [(match_operand:DI 1 "register_operand" "0")
21455            (match_operand:DI 2 "nonimmediate_operand" "rm")]
21456           UNSPEC_CRC32))]
21457   "TARGET_SSE4_2 && TARGET_64BIT"
21458   "crc32q\t{%2, %0|%0, %2}"
21459   [(set_attr "type" "sselog1")
21460    (set_attr "prefix_rep" "1")
21461    (set_attr "prefix_extra" "1")
21462    (set_attr "mode" "DI")])
21463
21464 (include "mmx.md")
21465 (include "sse.md")
21466 (include "sync.md")