* config/i386/i386.md (*fp_jcc_7_387): Use 'const0_operand' instead
[official-gcc.git] / gcc / config / i386 / i386.md
blob1abc191966cd0f5be216432241cac8728776d5a0
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
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 2, or (at your option)
13 ;; any later version.
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.
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GCC; see the file COPYING.  If not, write to
22 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
23 ;; Boston, MA 02111-1307, USA.  */
25 ;; The original PO technology requires these to be ordered by speed,
26 ;; so that assigner will pick the fastest.
28 ;; See file "rtl.def" for documentation on define_insn, match_*, et. al.
30 ;; Macro REG_CLASS_FROM_LETTER in file i386.h defines the register
31 ;; constraint letters.
33 ;; The special asm out single letter directives following a '%' are:
34 ;; 'z' mov%z1 would be movl, movw, or movb depending on the mode of
35 ;;     operands[1].
36 ;; 'L' Print the opcode suffix for a 32-bit integer opcode.
37 ;; 'W' Print the opcode suffix for a 16-bit integer opcode.
38 ;; 'B' Print the opcode suffix for an 8-bit integer opcode.
39 ;; 'Q' Print the opcode suffix for a 64-bit float opcode.
40 ;; 'S' Print the opcode suffix for a 32-bit float opcode.
41 ;; 'T' Print the opcode suffix for an 80-bit extended real XFmode float opcode.
42 ;; 'J' Print the appropriate jump operand.
44 ;; 'b' Print the QImode name of the register for the indicated operand.
45 ;;     %b0 would print %al if operands[0] is reg 0.
46 ;; 'w' Likewise, print the HImode name of the register.
47 ;; 'k' Likewise, print the SImode name of the register.
48 ;; 'h' Print the QImode name for a "high" register, either ah, bh, ch or dh.
49 ;; 'y' Print "st(0)" instead of "st" as a register.
51 ;; UNSPEC usage:
53 (define_constants
54   [; Relocation specifiers
55    (UNSPEC_GOT                  0)
56    (UNSPEC_GOTOFF               1)
57    (UNSPEC_GOTPCREL             2)
58    (UNSPEC_GOTTPOFF             3)
59    (UNSPEC_TPOFF                4)
60    (UNSPEC_NTPOFF               5)
61    (UNSPEC_DTPOFF               6)
62    (UNSPEC_GOTNTPOFF            7)
63    (UNSPEC_INDNTPOFF            8)
65    ; Prologue support
66    (UNSPEC_STACK_ALLOC          11)
67    (UNSPEC_SET_GOT              12)
68    (UNSPEC_SSE_PROLOGUE_SAVE    13)
70    ; TLS support
71    (UNSPEC_TP                   15)
72    (UNSPEC_TLS_GD               16)
73    (UNSPEC_TLS_LD_BASE          17)
75    ; Other random patterns
76    (UNSPEC_SCAS                 20)
77    (UNSPEC_SIN                  21)
78    (UNSPEC_COS                  22)
79    (UNSPEC_FNSTSW               24)
80    (UNSPEC_SAHF                 25)
81    (UNSPEC_FSTCW                26)
82    (UNSPEC_ADD_CARRY            27)
83    (UNSPEC_FLDCW                28)
85    ; For SSE/MMX support:
86    (UNSPEC_FIX                  30)
87    (UNSPEC_FIX_NOTRUNC          31)
88    (UNSPEC_MASKMOV              32)
89    (UNSPEC_MOVMSK               33)
90    (UNSPEC_MOVNT                34)
91    (UNSPEC_MOVA                 38)
92    (UNSPEC_MOVU                 39)
93    (UNSPEC_SHUFFLE              41)
94    (UNSPEC_RCP                  42)
95    (UNSPEC_RSQRT                43)
96    (UNSPEC_SFENCE               44)
97    (UNSPEC_NOP                  45)     ; prevents combiner cleverness
98    (UNSPEC_PAVGUSB              49)
99    (UNSPEC_PFRCP                50)
100    (UNSPEC_PFRCPIT1             51)
101    (UNSPEC_PFRCPIT2             52)
102    (UNSPEC_PFRSQRT              53)
103    (UNSPEC_PFRSQIT1             54)
104    (UNSPEC_PSHUFLW              55)
105    (UNSPEC_PSHUFHW              56)
106    (UNSPEC_MFENCE               59)
107    (UNSPEC_LFENCE               60)
108    (UNSPEC_PSADBW               61)
109    (UNSPEC_ADDSUB               71)
110    (UNSPEC_HADD                 72)
111    (UNSPEC_HSUB                 73)
112    (UNSPEC_MOVSHDUP             74)
113    (UNSPEC_MOVSLDUP             75)
114    (UNSPEC_LDQQU                76)
115    (UNSPEC_MOVDDUP              77)
117    ; x87 Floating point
118    (UNSPEC_FPATAN               65)
119    (UNSPEC_FYL2X                66)
120    (UNSPEC_FYL2XP1              67)
121    (UNSPEC_FRNDINT              68)
122    (UNSPEC_FIST                 69)
123    (UNSPEC_F2XM1                70)
125    ; x87 Double output FP
126    (UNSPEC_SINCOS_COS           80)
127    (UNSPEC_SINCOS_SIN           81)
128    (UNSPEC_TAN_ONE              82)
129    (UNSPEC_TAN_TAN              83)
130    (UNSPEC_XTRACT_FRACT         84)
131    (UNSPEC_XTRACT_EXP           85)
132    (UNSPEC_FSCALE_FRACT         86)
133    (UNSPEC_FSCALE_EXP           87)
134    (UNSPEC_FPREM_F              88)
135    (UNSPEC_FPREM_U              89)
136    (UNSPEC_FPREM1_F             90)
137    (UNSPEC_FPREM1_U             91)
139    ; x87 Rounding
140    (UNSPEC_FRNDINT_FLOOR        96)
141    (UNSPEC_FRNDINT_CEIL         97)
142    (UNSPEC_FRNDINT_TRUNC        98)
143    (UNSPEC_FRNDINT_MASK_PM      99)
145    ; REP instruction
146    (UNSPEC_REP                  75)
148    (UNSPEC_EH_RETURN            76)
150    (UNSPEC_COPYSIGN             100)
151   ])
153 (define_constants
154   [(UNSPECV_BLOCKAGE            0)
155    (UNSPECV_STACK_PROBE         10)
156    (UNSPECV_EMMS                31)
157    (UNSPECV_LDMXCSR             37)
158    (UNSPECV_STMXCSR             40)
159    (UNSPECV_FEMMS               46)
160    (UNSPECV_CLFLUSH             57)
161    (UNSPECV_ALIGN               68)
162    (UNSPECV_MONITOR             69)
163    (UNSPECV_MWAIT               70)
164   ])
166 ;; Registers by name.
167 (define_constants
168   [(BP_REG                       6)
169    (SP_REG                       7)
170    (FLAGS_REG                   17)
171    (FPSR_REG                    18)
172    (DIRFLAG_REG                 19)
173   ])
175 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
176 ;; from i386.c.
178 ;; In C guard expressions, put expressions which may be compile-time
179 ;; constants first.  This allows for better optimization.  For
180 ;; example, write "TARGET_64BIT && reload_completed", not
181 ;; "reload_completed && TARGET_64BIT".
184 ;; Processor type.  This attribute must exactly match the processor_type
185 ;; enumeration in i386.h.
186 (define_attr "cpu" "i386,i486,pentium,pentiumpro,k6,athlon,pentium4,k8,nocona"
187   (const (symbol_ref "ix86_tune")))
189 ;; A basic instruction type.  Refinements due to arguments to be
190 ;; provided in other attributes.
191 (define_attr "type"
192   "other,multi,
193    alu,alu1,negnot,imov,imovx,lea,
194    incdec,ishift,ishift1,rotate,rotate1,imul,idiv,
195    icmp,test,ibr,setcc,icmov,
196    push,pop,call,callv,leave,
197    str,cld,
198    fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint,
199    sselog,sselog1,sseiadd,sseishft,sseimul,
200    sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv,
201    mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft"
202   (const_string "other"))
204 ;; Main data type used by the insn
205 (define_attr "mode"
206   "unknown,none,QI,HI,SI,DI,SF,DF,XF,TI,V4SF,V2DF,V2SF,V1DF"
207   (const_string "unknown"))
209 ;; The CPU unit operations uses.
210 (define_attr "unit" "integer,i387,sse,mmx,unknown"
211   (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint")
212            (const_string "i387")
213          (eq_attr "type" "sselog,sselog1,sseiadd,sseishft,sseimul,
214                           sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv")
215            (const_string "sse")
216          (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft")
217            (const_string "mmx")
218          (eq_attr "type" "other")
219            (const_string "unknown")]
220          (const_string "integer")))
222 ;; The (bounding maximum) length of an instruction immediate.
223 (define_attr "length_immediate" ""
224   (cond [(eq_attr "type" "incdec,setcc,icmov,str,cld,lea,other,multi,idiv,leave")
225            (const_int 0)
226          (eq_attr "unit" "i387,sse,mmx")
227            (const_int 0)
228          (eq_attr "type" "alu,alu1,negnot,imovx,ishift,rotate,ishift1,rotate1,
229                           imul,icmp,push,pop")
230            (symbol_ref "ix86_attr_length_immediate_default(insn,1)")
231          (eq_attr "type" "imov,test")
232            (symbol_ref "ix86_attr_length_immediate_default(insn,0)")
233          (eq_attr "type" "call")
234            (if_then_else (match_operand 0 "constant_call_address_operand" "")
235              (const_int 4)
236              (const_int 0))
237          (eq_attr "type" "callv")
238            (if_then_else (match_operand 1 "constant_call_address_operand" "")
239              (const_int 4)
240              (const_int 0))
241          ;; We don't know the size before shorten_branches.  Expect
242          ;; the instruction to fit for better scheduling.
243          (eq_attr "type" "ibr")
244            (const_int 1)
245          ]
246          (symbol_ref "/* Update immediate_length and other attributes! */
247                       abort(),1")))
249 ;; The (bounding maximum) length of an instruction address.
250 (define_attr "length_address" ""
251   (cond [(eq_attr "type" "str,cld,other,multi,fxch")
252            (const_int 0)
253          (and (eq_attr "type" "call")
254               (match_operand 0 "constant_call_address_operand" ""))
255              (const_int 0)
256          (and (eq_attr "type" "callv")
257               (match_operand 1 "constant_call_address_operand" ""))
258              (const_int 0)
259          ]
260          (symbol_ref "ix86_attr_length_address_default (insn)")))
262 ;; Set when length prefix is used.
263 (define_attr "prefix_data16" ""
264   (if_then_else (ior (eq_attr "mode" "HI")
265                      (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF")))
266     (const_int 1)
267     (const_int 0)))
269 ;; Set when string REP prefix is used.
270 (define_attr "prefix_rep" "" 
271   (if_then_else (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF"))
272     (const_int 1)
273     (const_int 0)))
275 ;; Set when 0f opcode prefix is used.
276 (define_attr "prefix_0f" ""
277   (if_then_else 
278     (ior (eq_attr "type" "imovx,setcc,icmov")
279          (eq_attr "unit" "sse,mmx"))
280     (const_int 1)
281     (const_int 0)))
283 ;; Set when REX opcode prefix is used.
284 (define_attr "prefix_rex" ""
285   (cond [(and (eq_attr "mode" "DI")
286               (eq_attr "type" "!push,pop,call,callv,leave,ibr"))
287            (const_int 1)
288          (and (eq_attr "mode" "QI")
289               (ne (symbol_ref "x86_extended_QIreg_mentioned_p (insn)")
290                   (const_int 0)))
291            (const_int 1)
292          (ne (symbol_ref "x86_extended_reg_mentioned_p (insn)")
293              (const_int 0))
294            (const_int 1)
295         ]
296         (const_int 0)))
298 ;; Set when modrm byte is used.
299 (define_attr "modrm" ""
300   (cond [(eq_attr "type" "str,cld,leave")
301            (const_int 0)
302          (eq_attr "unit" "i387")
303            (const_int 0)
304          (and (eq_attr "type" "incdec")
305               (ior (match_operand:SI 1 "register_operand" "")
306                    (match_operand:HI 1 "register_operand" "")))
307            (const_int 0)
308          (and (eq_attr "type" "push")
309               (not (match_operand 1 "memory_operand" "")))
310            (const_int 0)
311          (and (eq_attr "type" "pop")
312               (not (match_operand 0 "memory_operand" "")))
313            (const_int 0)
314          (and (eq_attr "type" "imov")
315               (and (match_operand 0 "register_operand" "")
316                    (match_operand 1 "immediate_operand" "")))
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          (const_int 1)))
327 ;; The (bounding maximum) length of an instruction in bytes.
328 ;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences.
329 ;; Later we may want to split them and compute proper length as for
330 ;; other insns.
331 (define_attr "length" ""
332   (cond [(eq_attr "type" "other,multi,fistp,frndint")
333            (const_int 16)
334          (eq_attr "type" "fcmp")
335            (const_int 4)
336          (eq_attr "unit" "i387")
337            (plus (const_int 2)
338                  (plus (attr "prefix_data16")
339                        (attr "length_address")))]
340          (plus (plus (attr "modrm")
341                      (plus (attr "prefix_0f")
342                            (plus (attr "prefix_rex")
343                                  (const_int 1))))
344                (plus (attr "prefix_rep")
345                      (plus (attr "prefix_data16")
346                            (plus (attr "length_immediate")
347                                  (attr "length_address")))))))
349 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
350 ;; `store' if there is a simple memory reference therein, or `unknown'
351 ;; if the instruction is complex.
353 (define_attr "memory" "none,load,store,both,unknown"
354   (cond [(eq_attr "type" "other,multi,str")
355            (const_string "unknown")
356          (eq_attr "type" "lea,fcmov,fpspc,cld")
357            (const_string "none")
358          (eq_attr "type" "fistp,leave")
359            (const_string "both")
360          (eq_attr "type" "frndint")
361            (const_string "load")
362          (eq_attr "type" "push")
363            (if_then_else (match_operand 1 "memory_operand" "")
364              (const_string "both")
365              (const_string "store"))
366          (eq_attr "type" "pop")
367            (if_then_else (match_operand 0 "memory_operand" "")
368              (const_string "both")
369              (const_string "load"))
370          (eq_attr "type" "setcc")
371            (if_then_else (match_operand 0 "memory_operand" "")
372              (const_string "store")
373              (const_string "none"))
374          (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp")
375            (if_then_else (ior (match_operand 0 "memory_operand" "")
376                               (match_operand 1 "memory_operand" ""))
377              (const_string "load")
378              (const_string "none"))
379          (eq_attr "type" "ibr")
380            (if_then_else (match_operand 0 "memory_operand" "")
381              (const_string "load")
382              (const_string "none"))
383          (eq_attr "type" "call")
384            (if_then_else (match_operand 0 "constant_call_address_operand" "")
385              (const_string "none")
386              (const_string "load"))
387          (eq_attr "type" "callv")
388            (if_then_else (match_operand 1 "constant_call_address_operand" "")
389              (const_string "none")
390              (const_string "load"))
391          (and (eq_attr "type" "alu1,negnot,ishift1,sselog1")
392               (match_operand 1 "memory_operand" ""))
393            (const_string "both")
394          (and (match_operand 0 "memory_operand" "")
395               (match_operand 1 "memory_operand" ""))
396            (const_string "both")
397          (match_operand 0 "memory_operand" "")
398            (const_string "store")
399          (match_operand 1 "memory_operand" "")
400            (const_string "load")
401          (and (eq_attr "type"
402                  "!alu1,negnot,ishift1,
403                    imov,imovx,icmp,test,
404                    fmov,fcmp,fsgn,
405                    sse,ssemov,ssecmp,ssecomi,ssecvt,sseicvt,sselog1,
406                    mmx,mmxmov,mmxcmp,mmxcvt")
407               (match_operand 2 "memory_operand" ""))
408            (const_string "load")
409          (and (eq_attr "type" "icmov")
410               (match_operand 3 "memory_operand" ""))
411            (const_string "load")
412         ]
413         (const_string "none")))
415 ;; Indicates if an instruction has both an immediate and a displacement.
417 (define_attr "imm_disp" "false,true,unknown"
418   (cond [(eq_attr "type" "other,multi")
419            (const_string "unknown")
420          (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1")
421               (and (match_operand 0 "memory_displacement_operand" "")
422                    (match_operand 1 "immediate_operand" "")))
423            (const_string "true")
424          (and (eq_attr "type" "alu,ishift,rotate,imul,idiv")
425               (and (match_operand 0 "memory_displacement_operand" "")
426                    (match_operand 2 "immediate_operand" "")))
427            (const_string "true")
428         ]
429         (const_string "false")))
431 ;; Indicates if an FP operation has an integer source.
433 (define_attr "fp_int_src" "false,true"
434   (const_string "false"))
436 ;; Defines rounding mode of an FP operation.
438 (define_attr "i387_cw" "floor,ceil,trunc,mask_pm,uninitialized,any"
439   (const_string "any"))
441 ;; Describe a user's asm statement.
442 (define_asm_attributes
443   [(set_attr "length" "128")
444    (set_attr "type" "multi")])
446 ;; All x87 floating point modes
447 (define_mode_macro X87MODEF [SF DF XF])
449 ;; All integer modes handled by x87 fisttp operator.
450 (define_mode_macro X87MODEI [HI SI DI])
452 ;; All integer modes handled by integer x87 operators.
453 (define_mode_macro X87MODEI12 [HI SI])
455 ;; All SSE floating point modes
456 (define_mode_macro SSEMODEF [SF DF])
458 ;; All integer modes handled by SSE cvtts?2si* operators.
459 (define_mode_macro SSEMODEI24 [SI DI])
462 ;; Scheduling descriptions
464 (include "pentium.md")
465 (include "ppro.md")
466 (include "k6.md")
467 (include "athlon.md")
470 ;; Operand and operator predicates
472 (include "predicates.md")
475 ;; Compare instructions.
477 ;; All compare insns have expanders that save the operands away without
478 ;; actually generating RTL.  The bCOND or sCOND (emitted immediately
479 ;; after the cmp) will actually emit the cmpM.
481 (define_expand "cmpdi"
482   [(set (reg:CC FLAGS_REG)
483         (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
484                     (match_operand:DI 1 "x86_64_general_operand" "")))]
485   ""
487   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
488     operands[0] = force_reg (DImode, operands[0]);
489   ix86_compare_op0 = operands[0];
490   ix86_compare_op1 = operands[1];
491   DONE;
494 (define_expand "cmpsi"
495   [(set (reg:CC FLAGS_REG)
496         (compare:CC (match_operand:SI 0 "cmpsi_operand" "")
497                     (match_operand:SI 1 "general_operand" "")))]
498   ""
500   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
501     operands[0] = force_reg (SImode, operands[0]);
502   ix86_compare_op0 = operands[0];
503   ix86_compare_op1 = operands[1];
504   DONE;
507 (define_expand "cmphi"
508   [(set (reg:CC FLAGS_REG)
509         (compare:CC (match_operand:HI 0 "nonimmediate_operand" "")
510                     (match_operand:HI 1 "general_operand" "")))]
511   ""
513   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
514     operands[0] = force_reg (HImode, operands[0]);
515   ix86_compare_op0 = operands[0];
516   ix86_compare_op1 = operands[1];
517   DONE;
520 (define_expand "cmpqi"
521   [(set (reg:CC FLAGS_REG)
522         (compare:CC (match_operand:QI 0 "nonimmediate_operand" "")
523                     (match_operand:QI 1 "general_operand" "")))]
524   "TARGET_QIMODE_MATH"
526   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
527     operands[0] = force_reg (QImode, operands[0]);
528   ix86_compare_op0 = operands[0];
529   ix86_compare_op1 = operands[1];
530   DONE;
533 (define_insn "cmpdi_ccno_1_rex64"
534   [(set (reg FLAGS_REG)
535         (compare (match_operand:DI 0 "nonimmediate_operand" "r,?mr")
536                  (match_operand:DI 1 "const0_operand" "n,n")))]
537   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
538   "@
539    test{q}\t{%0, %0|%0, %0}
540    cmp{q}\t{%1, %0|%0, %1}"
541   [(set_attr "type" "test,icmp")
542    (set_attr "length_immediate" "0,1")
543    (set_attr "mode" "DI")])
545 (define_insn "*cmpdi_minus_1_rex64"
546   [(set (reg FLAGS_REG)
547         (compare (minus:DI (match_operand:DI 0 "nonimmediate_operand" "rm,r")
548                            (match_operand:DI 1 "x86_64_general_operand" "re,mr"))
549                  (const_int 0)))]
550   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)"
551   "cmp{q}\t{%1, %0|%0, %1}"
552   [(set_attr "type" "icmp")
553    (set_attr "mode" "DI")])
555 (define_expand "cmpdi_1_rex64"
556   [(set (reg:CC FLAGS_REG)
557         (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
558                     (match_operand:DI 1 "general_operand" "")))]
559   "TARGET_64BIT"
560   "")
562 (define_insn "cmpdi_1_insn_rex64"
563   [(set (reg FLAGS_REG)
564         (compare (match_operand:DI 0 "nonimmediate_operand" "mr,r")
565                  (match_operand:DI 1 "x86_64_general_operand" "re,mr")))]
566   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
567   "cmp{q}\t{%1, %0|%0, %1}"
568   [(set_attr "type" "icmp")
569    (set_attr "mode" "DI")])
572 (define_insn "*cmpsi_ccno_1"
573   [(set (reg FLAGS_REG)
574         (compare (match_operand:SI 0 "nonimmediate_operand" "r,?mr")
575                  (match_operand:SI 1 "const0_operand" "n,n")))]
576   "ix86_match_ccmode (insn, CCNOmode)"
577   "@
578    test{l}\t{%0, %0|%0, %0}
579    cmp{l}\t{%1, %0|%0, %1}"
580   [(set_attr "type" "test,icmp")
581    (set_attr "length_immediate" "0,1")
582    (set_attr "mode" "SI")])
584 (define_insn "*cmpsi_minus_1"
585   [(set (reg FLAGS_REG)
586         (compare (minus:SI (match_operand:SI 0 "nonimmediate_operand" "rm,r")
587                            (match_operand:SI 1 "general_operand" "ri,mr"))
588                  (const_int 0)))]
589   "ix86_match_ccmode (insn, CCGOCmode)"
590   "cmp{l}\t{%1, %0|%0, %1}"
591   [(set_attr "type" "icmp")
592    (set_attr "mode" "SI")])
594 (define_expand "cmpsi_1"
595   [(set (reg:CC FLAGS_REG)
596         (compare:CC (match_operand:SI 0 "nonimmediate_operand" "rm,r")
597                     (match_operand:SI 1 "general_operand" "ri,mr")))]
598   ""
599   "")
601 (define_insn "*cmpsi_1_insn"
602   [(set (reg FLAGS_REG)
603         (compare (match_operand:SI 0 "nonimmediate_operand" "rm,r")
604                  (match_operand:SI 1 "general_operand" "ri,mr")))]
605   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
606     && ix86_match_ccmode (insn, CCmode)"
607   "cmp{l}\t{%1, %0|%0, %1}"
608   [(set_attr "type" "icmp")
609    (set_attr "mode" "SI")])
611 (define_insn "*cmphi_ccno_1"
612   [(set (reg FLAGS_REG)
613         (compare (match_operand:HI 0 "nonimmediate_operand" "r,?mr")
614                  (match_operand:HI 1 "const0_operand" "n,n")))]
615   "ix86_match_ccmode (insn, CCNOmode)"
616   "@
617    test{w}\t{%0, %0|%0, %0}
618    cmp{w}\t{%1, %0|%0, %1}"
619   [(set_attr "type" "test,icmp")
620    (set_attr "length_immediate" "0,1")
621    (set_attr "mode" "HI")])
623 (define_insn "*cmphi_minus_1"
624   [(set (reg FLAGS_REG)
625         (compare (minus:HI (match_operand:HI 0 "nonimmediate_operand" "rm,r")
626                            (match_operand:HI 1 "general_operand" "ri,mr"))
627                  (const_int 0)))]
628   "ix86_match_ccmode (insn, CCGOCmode)"
629   "cmp{w}\t{%1, %0|%0, %1}"
630   [(set_attr "type" "icmp")
631    (set_attr "mode" "HI")])
633 (define_insn "*cmphi_1"
634   [(set (reg FLAGS_REG)
635         (compare (match_operand:HI 0 "nonimmediate_operand" "rm,r")
636                  (match_operand:HI 1 "general_operand" "ri,mr")))]
637   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
638    && ix86_match_ccmode (insn, CCmode)"
639   "cmp{w}\t{%1, %0|%0, %1}"
640   [(set_attr "type" "icmp")
641    (set_attr "mode" "HI")])
643 (define_insn "*cmpqi_ccno_1"
644   [(set (reg FLAGS_REG)
645         (compare (match_operand:QI 0 "nonimmediate_operand" "q,?mq")
646                  (match_operand:QI 1 "const0_operand" "n,n")))]
647   "ix86_match_ccmode (insn, CCNOmode)"
648   "@
649    test{b}\t{%0, %0|%0, %0}
650    cmp{b}\t{$0, %0|%0, 0}"
651   [(set_attr "type" "test,icmp")
652    (set_attr "length_immediate" "0,1")
653    (set_attr "mode" "QI")])
655 (define_insn "*cmpqi_1"
656   [(set (reg FLAGS_REG)
657         (compare (match_operand:QI 0 "nonimmediate_operand" "qm,q")
658                  (match_operand:QI 1 "general_operand" "qi,mq")))]
659   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
660     && ix86_match_ccmode (insn, CCmode)"
661   "cmp{b}\t{%1, %0|%0, %1}"
662   [(set_attr "type" "icmp")
663    (set_attr "mode" "QI")])
665 (define_insn "*cmpqi_minus_1"
666   [(set (reg FLAGS_REG)
667         (compare (minus:QI (match_operand:QI 0 "nonimmediate_operand" "qm,q")
668                            (match_operand:QI 1 "general_operand" "qi,mq"))
669                  (const_int 0)))]
670   "ix86_match_ccmode (insn, CCGOCmode)"
671   "cmp{b}\t{%1, %0|%0, %1}"
672   [(set_attr "type" "icmp")
673    (set_attr "mode" "QI")])
675 (define_insn "*cmpqi_ext_1"
676   [(set (reg FLAGS_REG)
677         (compare
678           (match_operand:QI 0 "general_operand" "Qm")
679           (subreg:QI
680             (zero_extract:SI
681               (match_operand 1 "ext_register_operand" "Q")
682               (const_int 8)
683               (const_int 8)) 0)))]
684   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
685   "cmp{b}\t{%h1, %0|%0, %h1}"
686   [(set_attr "type" "icmp")
687    (set_attr "mode" "QI")])
689 (define_insn "*cmpqi_ext_1_rex64"
690   [(set (reg FLAGS_REG)
691         (compare
692           (match_operand:QI 0 "register_operand" "Q")
693           (subreg:QI
694             (zero_extract:SI
695               (match_operand 1 "ext_register_operand" "Q")
696               (const_int 8)
697               (const_int 8)) 0)))]
698   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
699   "cmp{b}\t{%h1, %0|%0, %h1}"
700   [(set_attr "type" "icmp")
701    (set_attr "mode" "QI")])
703 (define_insn "*cmpqi_ext_2"
704   [(set (reg FLAGS_REG)
705         (compare
706           (subreg:QI
707             (zero_extract:SI
708               (match_operand 0 "ext_register_operand" "Q")
709               (const_int 8)
710               (const_int 8)) 0)
711           (match_operand:QI 1 "const0_operand" "n")))]
712   "ix86_match_ccmode (insn, CCNOmode)"
713   "test{b}\t%h0, %h0"
714   [(set_attr "type" "test")
715    (set_attr "length_immediate" "0")
716    (set_attr "mode" "QI")])
718 (define_expand "cmpqi_ext_3"
719   [(set (reg:CC FLAGS_REG)
720         (compare:CC
721           (subreg:QI
722             (zero_extract:SI
723               (match_operand 0 "ext_register_operand" "")
724               (const_int 8)
725               (const_int 8)) 0)
726           (match_operand:QI 1 "general_operand" "")))]
727   ""
728   "")
730 (define_insn "cmpqi_ext_3_insn"
731   [(set (reg FLAGS_REG)
732         (compare
733           (subreg:QI
734             (zero_extract:SI
735               (match_operand 0 "ext_register_operand" "Q")
736               (const_int 8)
737               (const_int 8)) 0)
738           (match_operand:QI 1 "general_operand" "Qmn")))]
739   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
740   "cmp{b}\t{%1, %h0|%h0, %1}"
741   [(set_attr "type" "icmp")
742    (set_attr "mode" "QI")])
744 (define_insn "cmpqi_ext_3_insn_rex64"
745   [(set (reg FLAGS_REG)
746         (compare
747           (subreg:QI
748             (zero_extract:SI
749               (match_operand 0 "ext_register_operand" "Q")
750               (const_int 8)
751               (const_int 8)) 0)
752           (match_operand:QI 1 "nonmemory_operand" "Qn")))]
753   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
754   "cmp{b}\t{%1, %h0|%h0, %1}"
755   [(set_attr "type" "icmp")
756    (set_attr "mode" "QI")])
758 (define_insn "*cmpqi_ext_4"
759   [(set (reg FLAGS_REG)
760         (compare
761           (subreg:QI
762             (zero_extract:SI
763               (match_operand 0 "ext_register_operand" "Q")
764               (const_int 8)
765               (const_int 8)) 0)
766           (subreg:QI
767             (zero_extract:SI
768               (match_operand 1 "ext_register_operand" "Q")
769               (const_int 8)
770               (const_int 8)) 0)))]
771   "ix86_match_ccmode (insn, CCmode)"
772   "cmp{b}\t{%h1, %h0|%h0, %h1}"
773   [(set_attr "type" "icmp")
774    (set_attr "mode" "QI")])
776 ;; These implement float point compares.
777 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
778 ;; which would allow mix and match FP modes on the compares.  Which is what
779 ;; the old patterns did, but with many more of them.
781 (define_expand "cmpxf"
782   [(set (reg:CC FLAGS_REG)
783         (compare:CC (match_operand:XF 0 "cmp_fp_expander_operand" "")
784                     (match_operand:XF 1 "cmp_fp_expander_operand" "")))]
785   "TARGET_80387"
787   ix86_compare_op0 = operands[0];
788   ix86_compare_op1 = operands[1];
789   DONE;
792 (define_expand "cmpdf"
793   [(set (reg:CC FLAGS_REG)
794         (compare:CC (match_operand:DF 0 "cmp_fp_expander_operand" "")
795                     (match_operand:DF 1 "cmp_fp_expander_operand" "")))]
796   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
798   ix86_compare_op0 = operands[0];
799   ix86_compare_op1 = operands[1];
800   DONE;
803 (define_expand "cmpsf"
804   [(set (reg:CC FLAGS_REG)
805         (compare:CC (match_operand:SF 0 "cmp_fp_expander_operand" "")
806                     (match_operand:SF 1 "cmp_fp_expander_operand" "")))]
807   "TARGET_80387 || TARGET_SSE_MATH"
809   ix86_compare_op0 = operands[0];
810   ix86_compare_op1 = operands[1];
811   DONE;
814 ;; FP compares, step 1:
815 ;; Set the FP condition codes.
817 ;; CCFPmode     compare with exceptions
818 ;; CCFPUmode    compare with no exceptions
820 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
821 ;; used to manage the reg stack popping would not be preserved.
823 (define_insn "*cmpfp_0_sf"
824   [(set (match_operand:HI 0 "register_operand" "=a")
825         (unspec:HI
826           [(compare:CCFP
827              (match_operand:SF 1 "register_operand" "f")
828              (match_operand:SF 2 "const0_operand" "X"))]
829         UNSPEC_FNSTSW))]
830   "TARGET_80387"
831   "* return output_fp_compare (insn, operands, 0, 0);"
832   [(set_attr "type" "multi")
833    (set_attr "mode" "SF")])
835 (define_insn "*cmpfp_0_df"
836   [(set (match_operand:HI 0 "register_operand" "=a")
837         (unspec:HI
838           [(compare:CCFP
839              (match_operand:DF 1 "register_operand" "f")
840              (match_operand:DF 2 "const0_operand" "X"))]
841         UNSPEC_FNSTSW))]
842   "TARGET_80387"
843   "* return output_fp_compare (insn, operands, 0, 0);"
844   [(set_attr "type" "multi")
845    (set_attr "mode" "DF")])
847 (define_insn "*cmpfp_0_xf"
848   [(set (match_operand:HI 0 "register_operand" "=a")
849         (unspec:HI
850           [(compare:CCFP
851              (match_operand:XF 1 "register_operand" "f")
852              (match_operand:XF 2 "const0_operand" "X"))]
853         UNSPEC_FNSTSW))]
854   "TARGET_80387"
855   "* return output_fp_compare (insn, operands, 0, 0);"
856   [(set_attr "type" "multi")
857    (set_attr "mode" "XF")])
859 (define_insn "*cmpfp_sf"
860   [(set (match_operand:HI 0 "register_operand" "=a")
861         (unspec:HI
862           [(compare:CCFP
863              (match_operand:SF 1 "register_operand" "f")
864              (match_operand:SF 2 "nonimmediate_operand" "fm"))]
865           UNSPEC_FNSTSW))]
866   "TARGET_80387"
867   "* return output_fp_compare (insn, operands, 0, 0);"
868   [(set_attr "type" "multi")
869    (set_attr "mode" "SF")])
871 (define_insn "*cmpfp_df"
872   [(set (match_operand:HI 0 "register_operand" "=a")
873         (unspec:HI
874           [(compare:CCFP
875              (match_operand:DF 1 "register_operand" "f")
876              (match_operand:DF 2 "nonimmediate_operand" "fm"))]
877           UNSPEC_FNSTSW))]
878   "TARGET_80387"
879   "* return output_fp_compare (insn, operands, 0, 0);"
880   [(set_attr "type" "multi")
881    (set_attr "mode" "DF")])
883 (define_insn "*cmpfp_xf"
884   [(set (match_operand:HI 0 "register_operand" "=a")
885         (unspec:HI
886           [(compare:CCFP
887              (match_operand:XF 1 "register_operand" "f")
888              (match_operand:XF 2 "register_operand" "f"))]
889           UNSPEC_FNSTSW))]
890   "TARGET_80387"
891   "* return output_fp_compare (insn, operands, 0, 0);"
892   [(set_attr "type" "multi")
893    (set_attr "mode" "XF")])
895 (define_insn "*cmpfp_u"
896   [(set (match_operand:HI 0 "register_operand" "=a")
897         (unspec:HI
898           [(compare:CCFPU
899              (match_operand 1 "register_operand" "f")
900              (match_operand 2 "register_operand" "f"))]
901           UNSPEC_FNSTSW))]
902   "TARGET_80387
903    && FLOAT_MODE_P (GET_MODE (operands[1]))
904    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
905   "* return output_fp_compare (insn, operands, 0, 1);"
906   [(set_attr "type" "multi")
907    (set (attr "mode")
908      (cond [(match_operand:SF 1 "" "")
909               (const_string "SF")
910             (match_operand:DF 1 "" "")
911               (const_string "DF")
912            ]
913            (const_string "XF")))])
915 (define_insn "*cmpfp_<mode>"
916   [(set (match_operand:HI 0 "register_operand" "=a")
917         (unspec:HI
918           [(compare:CCFP
919              (match_operand 1 "register_operand" "f")
920              (match_operator 3 "float_operator"
921                [(match_operand:X87MODEI12 2 "memory_operand" "m")]))]
922           UNSPEC_FNSTSW))]
923   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
924    && FLOAT_MODE_P (GET_MODE (operands[1]))
925    && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
926   "* return output_fp_compare (insn, operands, 0, 0);"
927   [(set_attr "type" "multi")
928    (set_attr "fp_int_src" "true")
929    (set_attr "mode" "<MODE>")])
931 ;; FP compares, step 2
932 ;; Move the fpsw to ax.
934 (define_insn "x86_fnstsw_1"
935   [(set (match_operand:HI 0 "register_operand" "=a")
936         (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))]
937   "TARGET_80387"
938   "fnstsw\t%0"
939   [(set_attr "length" "2")
940    (set_attr "mode" "SI")
941    (set_attr "unit" "i387")])
943 ;; FP compares, step 3
944 ;; Get ax into flags, general case.
946 (define_insn "x86_sahf_1"
947   [(set (reg:CC FLAGS_REG)
948         (unspec:CC [(match_operand:HI 0 "register_operand" "a")] UNSPEC_SAHF))]
949   "!TARGET_64BIT"
950   "sahf"
951   [(set_attr "length" "1")
952    (set_attr "athlon_decode" "vector")
953    (set_attr "mode" "SI")])
955 ;; Pentium Pro can do steps 1 through 3 in one go.
957 (define_insn "*cmpfp_i_mixed"
958   [(set (reg:CCFP FLAGS_REG)
959         (compare:CCFP (match_operand 0 "register_operand" "f#x,x#f")
960                       (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
961   "TARGET_MIX_SSE_I387
962    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
963    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
964   "* return output_fp_compare (insn, operands, 1, 0);"
965   [(set_attr "type" "fcmp,ssecomi")
966    (set (attr "mode")
967      (if_then_else (match_operand:SF 1 "" "")
968         (const_string "SF")
969         (const_string "DF")))
970    (set_attr "athlon_decode" "vector")])
972 (define_insn "*cmpfp_i_sse"
973   [(set (reg:CCFP FLAGS_REG)
974         (compare:CCFP (match_operand 0 "register_operand" "x")
975                       (match_operand 1 "nonimmediate_operand" "xm")))]
976   "TARGET_SSE_MATH
977    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
978    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
979   "* return output_fp_compare (insn, operands, 1, 0);"
980   [(set_attr "type" "ssecomi")
981    (set (attr "mode")
982      (if_then_else (match_operand:SF 1 "" "")
983         (const_string "SF")
984         (const_string "DF")))
985    (set_attr "athlon_decode" "vector")])
987 (define_insn "*cmpfp_i_i387"
988   [(set (reg:CCFP FLAGS_REG)
989         (compare:CCFP (match_operand 0 "register_operand" "f")
990                       (match_operand 1 "register_operand" "f")))]
991   "TARGET_80387 && TARGET_CMOVE
992    && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0])))
993    && FLOAT_MODE_P (GET_MODE (operands[0]))
994    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
995   "* return output_fp_compare (insn, operands, 1, 0);"
996   [(set_attr "type" "fcmp")
997    (set (attr "mode")
998      (cond [(match_operand:SF 1 "" "")
999               (const_string "SF")
1000             (match_operand:DF 1 "" "")
1001               (const_string "DF")
1002            ]
1003            (const_string "XF")))
1004    (set_attr "athlon_decode" "vector")])
1006 (define_insn "*cmpfp_iu_mixed"
1007   [(set (reg:CCFPU FLAGS_REG)
1008         (compare:CCFPU (match_operand 0 "register_operand" "f#x,x#f")
1009                        (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
1010   "TARGET_MIX_SSE_I387
1011    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1012    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1013   "* return output_fp_compare (insn, operands, 1, 1);"
1014   [(set_attr "type" "fcmp,ssecomi")
1015    (set (attr "mode")
1016      (if_then_else (match_operand:SF 1 "" "")
1017         (const_string "SF")
1018         (const_string "DF")))
1019    (set_attr "athlon_decode" "vector")])
1021 (define_insn "*cmpfp_iu_sse"
1022   [(set (reg:CCFPU FLAGS_REG)
1023         (compare:CCFPU (match_operand 0 "register_operand" "x")
1024                        (match_operand 1 "nonimmediate_operand" "xm")))]
1025   "TARGET_SSE_MATH
1026    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1027    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1028   "* return output_fp_compare (insn, operands, 1, 1);"
1029   [(set_attr "type" "ssecomi")
1030    (set (attr "mode")
1031      (if_then_else (match_operand:SF 1 "" "")
1032         (const_string "SF")
1033         (const_string "DF")))
1034    (set_attr "athlon_decode" "vector")])
1036 (define_insn "*cmpfp_iu_387"
1037   [(set (reg:CCFPU FLAGS_REG)
1038         (compare:CCFPU (match_operand 0 "register_operand" "f")
1039                        (match_operand 1 "register_operand" "f")))]
1040   "TARGET_80387 && TARGET_CMOVE
1041    && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0])))
1042    && FLOAT_MODE_P (GET_MODE (operands[0]))
1043    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1044   "* return output_fp_compare (insn, operands, 1, 1);"
1045   [(set_attr "type" "fcmp")
1046    (set (attr "mode")
1047      (cond [(match_operand:SF 1 "" "")
1048               (const_string "SF")
1049             (match_operand:DF 1 "" "")
1050               (const_string "DF")
1051            ]
1052            (const_string "XF")))
1053    (set_attr "athlon_decode" "vector")])
1055 ;; Move instructions.
1057 ;; General case of fullword move.
1059 (define_expand "movsi"
1060   [(set (match_operand:SI 0 "nonimmediate_operand" "")
1061         (match_operand:SI 1 "general_operand" ""))]
1062   ""
1063   "ix86_expand_move (SImode, operands); DONE;")
1065 ;; Push/pop instructions.  They are separate since autoinc/dec is not a
1066 ;; general_operand.
1068 ;; %%% We don't use a post-inc memory reference because x86 is not a 
1069 ;; general AUTO_INC_DEC host, which impacts how it is treated in flow.
1070 ;; Changing this impacts compiler performance on other non-AUTO_INC_DEC
1071 ;; targets without our curiosities, and it is just as easy to represent
1072 ;; this differently.
1074 (define_insn "*pushsi2"
1075   [(set (match_operand:SI 0 "push_operand" "=<")
1076         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1077   "!TARGET_64BIT"
1078   "push{l}\t%1"
1079   [(set_attr "type" "push")
1080    (set_attr "mode" "SI")])
1082 ;; For 64BIT abi we always round up to 8 bytes.
1083 (define_insn "*pushsi2_rex64"
1084   [(set (match_operand:SI 0 "push_operand" "=X")
1085         (match_operand:SI 1 "nonmemory_no_elim_operand" "ri"))]
1086   "TARGET_64BIT"
1087   "push{q}\t%q1"
1088   [(set_attr "type" "push")
1089    (set_attr "mode" "SI")])
1091 (define_insn "*pushsi2_prologue"
1092   [(set (match_operand:SI 0 "push_operand" "=<")
1093         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))
1094    (clobber (mem:BLK (scratch)))]
1095   "!TARGET_64BIT"
1096   "push{l}\t%1"
1097   [(set_attr "type" "push")
1098    (set_attr "mode" "SI")])
1100 (define_insn "*popsi1_epilogue"
1101   [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1102         (mem:SI (reg:SI SP_REG)))
1103    (set (reg:SI SP_REG)
1104         (plus:SI (reg:SI SP_REG) (const_int 4)))
1105    (clobber (mem:BLK (scratch)))]
1106   "!TARGET_64BIT"
1107   "pop{l}\t%0"
1108   [(set_attr "type" "pop")
1109    (set_attr "mode" "SI")])
1111 (define_insn "popsi1"
1112   [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1113         (mem:SI (reg:SI SP_REG)))
1114    (set (reg:SI SP_REG)
1115         (plus:SI (reg:SI SP_REG) (const_int 4)))]
1116   "!TARGET_64BIT"
1117   "pop{l}\t%0"
1118   [(set_attr "type" "pop")
1119    (set_attr "mode" "SI")])
1121 (define_insn "*movsi_xor"
1122   [(set (match_operand:SI 0 "register_operand" "=r")
1123         (match_operand:SI 1 "const0_operand" "i"))
1124    (clobber (reg:CC FLAGS_REG))]
1125   "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1126   "xor{l}\t{%0, %0|%0, %0}"
1127   [(set_attr "type" "alu1")
1128    (set_attr "mode" "SI")
1129    (set_attr "length_immediate" "0")])
1131 (define_insn "*movsi_or"
1132   [(set (match_operand:SI 0 "register_operand" "=r")
1133         (match_operand:SI 1 "immediate_operand" "i"))
1134    (clobber (reg:CC FLAGS_REG))]
1135   "reload_completed
1136    && operands[1] == constm1_rtx
1137    && (TARGET_PENTIUM || optimize_size)"
1139   operands[1] = constm1_rtx;
1140   return "or{l}\t{%1, %0|%0, %1}";
1142   [(set_attr "type" "alu1")
1143    (set_attr "mode" "SI")
1144    (set_attr "length_immediate" "1")])
1146 (define_insn "*movsi_1"
1147   [(set (match_operand:SI 0 "nonimmediate_operand"
1148                         "=r  ,m  ,*y,*y,?rm,?*y,*x,*x,?r,m ,?*Y,*x")
1149         (match_operand:SI 1 "general_operand"
1150                         "rinm,rin,C ,*y,*y ,rm ,C ,*x,*Y,*x,r  ,m "))]
1151   "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1153   switch (get_attr_type (insn))
1154     {
1155     case TYPE_SSELOG1:
1156       if (get_attr_mode (insn) == MODE_TI)
1157         return "pxor\t%0, %0";
1158       return "xorps\t%0, %0";
1160     case TYPE_SSEMOV:
1161       switch (get_attr_mode (insn))
1162         {
1163         case MODE_TI:
1164           return "movdqa\t{%1, %0|%0, %1}";
1165         case MODE_V4SF:
1166           return "movaps\t{%1, %0|%0, %1}";
1167         case MODE_SI:
1168           return "movd\t{%1, %0|%0, %1}";
1169         case MODE_SF:
1170           return "movss\t{%1, %0|%0, %1}";
1171         default:
1172           gcc_unreachable ();
1173         }
1175     case TYPE_MMXADD:
1176       return "pxor\t%0, %0";
1178     case TYPE_MMXMOV:
1179       if (get_attr_mode (insn) == MODE_DI)
1180         return "movq\t{%1, %0|%0, %1}";
1181       return "movd\t{%1, %0|%0, %1}";
1183     case TYPE_LEA:
1184       return "lea{l}\t{%1, %0|%0, %1}";
1186     default:
1187       if (flag_pic && !LEGITIMATE_PIC_OPERAND_P (operands[1]))
1188         abort();
1189       return "mov{l}\t{%1, %0|%0, %1}";
1190     }
1192   [(set (attr "type")
1193      (cond [(eq_attr "alternative" "2")
1194               (const_string "mmx")
1195             (eq_attr "alternative" "3,4,5")
1196               (const_string "mmxmov")
1197             (eq_attr "alternative" "6")
1198               (const_string "sselog1")
1199             (eq_attr "alternative" "7,8,9,10,11")
1200               (const_string "ssemov")
1201             (and (ne (symbol_ref "flag_pic") (const_int 0))
1202                  (match_operand:SI 1 "symbolic_operand" ""))
1203               (const_string "lea")
1204            ]
1205            (const_string "imov")))
1206    (set (attr "mode")
1207      (cond [(eq_attr "alternative" "2,3")
1208               (const_string "DI")
1209             (eq_attr "alternative" "6,7")
1210               (if_then_else
1211                 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
1212                 (const_string "V4SF")
1213                 (const_string "TI"))
1214             (and (eq_attr "alternative" "8,9,10,11")
1215                  (eq (symbol_ref "TARGET_SSE2") (const_int 0)))
1216               (const_string "SF")
1217            ]
1218            (const_string "SI")))])
1220 ;; Stores and loads of ax to arbitrary constant address.
1221 ;; We fake an second form of instruction to force reload to load address
1222 ;; into register when rax is not available
1223 (define_insn "*movabssi_1_rex64"
1224   [(set (mem:SI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1225         (match_operand:SI 1 "nonmemory_operand" "a,er"))]
1226   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1227   "@
1228    movabs{l}\t{%1, %P0|%P0, %1}
1229    mov{l}\t{%1, %a0|%a0, %1}"
1230   [(set_attr "type" "imov")
1231    (set_attr "modrm" "0,*")
1232    (set_attr "length_address" "8,0")
1233    (set_attr "length_immediate" "0,*")
1234    (set_attr "memory" "store")
1235    (set_attr "mode" "SI")])
1237 (define_insn "*movabssi_2_rex64"
1238   [(set (match_operand:SI 0 "register_operand" "=a,r")
1239         (mem:SI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1240   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1241   "@
1242    movabs{l}\t{%P1, %0|%0, %P1}
1243    mov{l}\t{%a1, %0|%0, %a1}"
1244   [(set_attr "type" "imov")
1245    (set_attr "modrm" "0,*")
1246    (set_attr "length_address" "8,0")
1247    (set_attr "length_immediate" "0")
1248    (set_attr "memory" "load")
1249    (set_attr "mode" "SI")])
1251 (define_insn "*swapsi"
1252   [(set (match_operand:SI 0 "register_operand" "+r")
1253         (match_operand:SI 1 "register_operand" "+r"))
1254    (set (match_dup 1)
1255         (match_dup 0))]
1256   ""
1257   "xchg{l}\t%1, %0"
1258   [(set_attr "type" "imov")
1259    (set_attr "mode" "SI")
1260    (set_attr "pent_pair" "np")
1261    (set_attr "athlon_decode" "vector")])
1263 (define_expand "movhi"
1264   [(set (match_operand:HI 0 "nonimmediate_operand" "")
1265         (match_operand:HI 1 "general_operand" ""))]
1266   ""
1267   "ix86_expand_move (HImode, operands); DONE;")
1269 (define_insn "*pushhi2"
1270   [(set (match_operand:HI 0 "push_operand" "=<,<")
1271         (match_operand:HI 1 "general_no_elim_operand" "n,r*m"))]
1272   "!TARGET_64BIT"
1273   "@
1274    push{w}\t{|WORD PTR }%1
1275    push{w}\t%1"
1276   [(set_attr "type" "push")
1277    (set_attr "mode" "HI")])
1279 ;; For 64BIT abi we always round up to 8 bytes.
1280 (define_insn "*pushhi2_rex64"
1281   [(set (match_operand:HI 0 "push_operand" "=X")
1282         (match_operand:HI 1 "nonmemory_no_elim_operand" "ri"))]
1283   "TARGET_64BIT"
1284   "push{q}\t%q1"
1285   [(set_attr "type" "push")
1286    (set_attr "mode" "QI")])
1288 (define_insn "*movhi_1"
1289   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
1290         (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
1291   "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1293   switch (get_attr_type (insn))
1294     {
1295     case TYPE_IMOVX:
1296       /* movzwl is faster than movw on p2 due to partial word stalls,
1297          though not as fast as an aligned movl.  */
1298       return "movz{wl|x}\t{%1, %k0|%k0, %1}";
1299     default:
1300       if (get_attr_mode (insn) == MODE_SI)
1301         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1302       else
1303         return "mov{w}\t{%1, %0|%0, %1}";
1304     }
1306   [(set (attr "type")
1307      (cond [(ne (symbol_ref "optimize_size") (const_int 0))
1308               (const_string "imov")
1309             (and (eq_attr "alternative" "0")
1310                  (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1311                           (const_int 0))
1312                       (eq (symbol_ref "TARGET_HIMODE_MATH")
1313                           (const_int 0))))
1314               (const_string "imov")
1315             (and (eq_attr "alternative" "1,2")
1316                  (match_operand:HI 1 "aligned_operand" ""))
1317               (const_string "imov")
1318             (and (ne (symbol_ref "TARGET_MOVX")
1319                      (const_int 0))
1320                  (eq_attr "alternative" "0,2"))
1321               (const_string "imovx")
1322            ]
1323            (const_string "imov")))
1324     (set (attr "mode")
1325       (cond [(eq_attr "type" "imovx")
1326                (const_string "SI")
1327              (and (eq_attr "alternative" "1,2")
1328                   (match_operand:HI 1 "aligned_operand" ""))
1329                (const_string "SI")
1330              (and (eq_attr "alternative" "0")
1331                   (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1332                            (const_int 0))
1333                        (eq (symbol_ref "TARGET_HIMODE_MATH")
1334                            (const_int 0))))
1335                (const_string "SI")
1336             ]
1337             (const_string "HI")))])
1339 ;; Stores and loads of ax to arbitrary constant address.
1340 ;; We fake an second form of instruction to force reload to load address
1341 ;; into register when rax is not available
1342 (define_insn "*movabshi_1_rex64"
1343   [(set (mem:HI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1344         (match_operand:HI 1 "nonmemory_operand" "a,er"))]
1345   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1346   "@
1347    movabs{w}\t{%1, %P0|%P0, %1}
1348    mov{w}\t{%1, %a0|%a0, %1}"
1349   [(set_attr "type" "imov")
1350    (set_attr "modrm" "0,*")
1351    (set_attr "length_address" "8,0")
1352    (set_attr "length_immediate" "0,*")
1353    (set_attr "memory" "store")
1354    (set_attr "mode" "HI")])
1356 (define_insn "*movabshi_2_rex64"
1357   [(set (match_operand:HI 0 "register_operand" "=a,r")
1358         (mem:HI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1359   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1360   "@
1361    movabs{w}\t{%P1, %0|%0, %P1}
1362    mov{w}\t{%a1, %0|%0, %a1}"
1363   [(set_attr "type" "imov")
1364    (set_attr "modrm" "0,*")
1365    (set_attr "length_address" "8,0")
1366    (set_attr "length_immediate" "0")
1367    (set_attr "memory" "load")
1368    (set_attr "mode" "HI")])
1370 (define_insn "*swaphi_1"
1371   [(set (match_operand:HI 0 "register_operand" "+r")
1372         (match_operand:HI 1 "register_operand" "+r"))
1373    (set (match_dup 1)
1374         (match_dup 0))]
1375   "!TARGET_PARTIAL_REG_STALL || optimize_size"
1376   "xchg{l}\t%k1, %k0"
1377   [(set_attr "type" "imov")
1378    (set_attr "mode" "SI")
1379    (set_attr "pent_pair" "np")
1380    (set_attr "athlon_decode" "vector")])
1382 (define_insn "*swaphi_2"
1383   [(set (match_operand:HI 0 "register_operand" "+r")
1384         (match_operand:HI 1 "register_operand" "+r"))
1385    (set (match_dup 1)
1386         (match_dup 0))]
1387   "TARGET_PARTIAL_REG_STALL"
1388   "xchg{w}\t%1, %0"
1389   [(set_attr "type" "imov")
1390    (set_attr "mode" "HI")
1391    (set_attr "pent_pair" "np")
1392    (set_attr "athlon_decode" "vector")])
1394 (define_expand "movstricthi"
1395   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" ""))
1396         (match_operand:HI 1 "general_operand" ""))]
1397   "! TARGET_PARTIAL_REG_STALL || optimize_size"
1399   /* Don't generate memory->memory moves, go through a register */
1400   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1401     operands[1] = force_reg (HImode, operands[1]);
1404 (define_insn "*movstricthi_1"
1405   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+rm,r"))
1406         (match_operand:HI 1 "general_operand" "rn,m"))]
1407   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1408    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1409   "mov{w}\t{%1, %0|%0, %1}"
1410   [(set_attr "type" "imov")
1411    (set_attr "mode" "HI")])
1413 (define_insn "*movstricthi_xor"
1414   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
1415         (match_operand:HI 1 "const0_operand" "i"))
1416    (clobber (reg:CC FLAGS_REG))]
1417   "reload_completed
1418    && ((!TARGET_USE_MOV0 && !TARGET_PARTIAL_REG_STALL) || optimize_size)"
1419   "xor{w}\t{%0, %0|%0, %0}"
1420   [(set_attr "type" "alu1")
1421    (set_attr "mode" "HI")
1422    (set_attr "length_immediate" "0")])
1424 (define_expand "movqi"
1425   [(set (match_operand:QI 0 "nonimmediate_operand" "")
1426         (match_operand:QI 1 "general_operand" ""))]
1427   ""
1428   "ix86_expand_move (QImode, operands); DONE;")
1430 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1431 ;; "push a byte".  But actually we use pushw, which has the effect
1432 ;; of rounding the amount pushed up to a halfword.
1434 (define_insn "*pushqi2"
1435   [(set (match_operand:QI 0 "push_operand" "=X,X")
1436         (match_operand:QI 1 "nonmemory_no_elim_operand" "n,r"))]
1437   "!TARGET_64BIT"
1438   "@
1439    push{w}\t{|word ptr }%1
1440    push{w}\t%w1"
1441   [(set_attr "type" "push")
1442    (set_attr "mode" "HI")])
1444 ;; For 64BIT abi we always round up to 8 bytes.
1445 (define_insn "*pushqi2_rex64"
1446   [(set (match_operand:QI 0 "push_operand" "=X")
1447         (match_operand:QI 1 "nonmemory_no_elim_operand" "qi"))]
1448   "TARGET_64BIT"
1449   "push{q}\t%q1"
1450   [(set_attr "type" "push")
1451    (set_attr "mode" "QI")])
1453 ;; Situation is quite tricky about when to choose full sized (SImode) move
1454 ;; over QImode moves.  For Q_REG -> Q_REG move we use full size only for
1455 ;; partial register dependency machines (such as AMD Athlon), where QImode
1456 ;; moves issue extra dependency and for partial register stalls machines
1457 ;; that don't use QImode patterns (and QImode move cause stall on the next
1458 ;; instruction).
1460 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
1461 ;; register stall machines with, where we use QImode instructions, since
1462 ;; partial register stall can be caused there.  Then we use movzx.
1463 (define_insn "*movqi_1"
1464   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
1465         (match_operand:QI 1 "general_operand"      " q,qn,qm,q,rn,qm,qn"))]
1466   "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1468   switch (get_attr_type (insn))
1469     {
1470     case TYPE_IMOVX:
1471       if (!ANY_QI_REG_P (operands[1]) && GET_CODE (operands[1]) != MEM)
1472         abort ();
1473       return "movz{bl|x}\t{%1, %k0|%k0, %1}";
1474     default:
1475       if (get_attr_mode (insn) == MODE_SI)
1476         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1477       else
1478         return "mov{b}\t{%1, %0|%0, %1}";
1479     }
1481   [(set (attr "type")
1482      (cond [(ne (symbol_ref "optimize_size") (const_int 0))
1483               (const_string "imov")
1484             (and (eq_attr "alternative" "3")
1485                  (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1486                           (const_int 0))
1487                       (eq (symbol_ref "TARGET_QIMODE_MATH")
1488                           (const_int 0))))
1489               (const_string "imov")
1490             (eq_attr "alternative" "3,5")
1491               (const_string "imovx")
1492             (and (ne (symbol_ref "TARGET_MOVX")
1493                      (const_int 0))
1494                  (eq_attr "alternative" "2"))
1495               (const_string "imovx")
1496            ]
1497            (const_string "imov")))
1498    (set (attr "mode")
1499       (cond [(eq_attr "alternative" "3,4,5")
1500                (const_string "SI")
1501              (eq_attr "alternative" "6")
1502                (const_string "QI")
1503              (eq_attr "type" "imovx")
1504                (const_string "SI")
1505              (and (eq_attr "type" "imov")
1506                   (and (eq_attr "alternative" "0,1")
1507                        (ne (symbol_ref "TARGET_PARTIAL_REG_DEPENDENCY")
1508                            (const_int 0))))
1509                (const_string "SI")
1510              ;; Avoid partial register stalls when not using QImode arithmetic
1511              (and (eq_attr "type" "imov")
1512                   (and (eq_attr "alternative" "0,1")
1513                        (and (ne (symbol_ref "TARGET_PARTIAL_REG_STALL")
1514                                 (const_int 0))
1515                             (eq (symbol_ref "TARGET_QIMODE_MATH")
1516                                 (const_int 0)))))
1517                (const_string "SI")
1518            ]
1519            (const_string "QI")))])
1521 (define_expand "reload_outqi"
1522   [(parallel [(match_operand:QI 0 "" "=m")
1523               (match_operand:QI 1 "register_operand" "r")
1524               (match_operand:QI 2 "register_operand" "=&q")])]
1525   ""
1527   rtx op0, op1, op2;
1528   op0 = operands[0]; op1 = operands[1]; op2 = operands[2];
1530   if (reg_overlap_mentioned_p (op2, op0))
1531     abort ();
1532   if (! q_regs_operand (op1, QImode))
1533     {
1534       emit_insn (gen_movqi (op2, op1));
1535       op1 = op2;
1536     }
1537   emit_insn (gen_movqi (op0, op1));
1538   DONE;
1541 (define_insn "*swapqi_1"
1542   [(set (match_operand:QI 0 "register_operand" "+r")
1543         (match_operand:QI 1 "register_operand" "+r"))
1544    (set (match_dup 1)
1545         (match_dup 0))]
1546   "!TARGET_PARTIAL_REG_STALL || optimize_size"
1547   "xchg{l}\t%k1, %k0"
1548   [(set_attr "type" "imov")
1549    (set_attr "mode" "SI")
1550    (set_attr "pent_pair" "np")
1551    (set_attr "athlon_decode" "vector")])
1553 (define_insn "*swapqi_2"
1554   [(set (match_operand:QI 0 "register_operand" "+q")
1555         (match_operand:QI 1 "register_operand" "+q"))
1556    (set (match_dup 1)
1557         (match_dup 0))]
1558   "TARGET_PARTIAL_REG_STALL"
1559   "xchg{b}\t%1, %0"
1560   [(set_attr "type" "imov")
1561    (set_attr "mode" "QI")
1562    (set_attr "pent_pair" "np")
1563    (set_attr "athlon_decode" "vector")])
1565 (define_expand "movstrictqi"
1566   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
1567         (match_operand:QI 1 "general_operand" ""))]
1568   "! TARGET_PARTIAL_REG_STALL || optimize_size"
1570   /* Don't generate memory->memory moves, go through a register.  */
1571   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1572     operands[1] = force_reg (QImode, operands[1]);
1575 (define_insn "*movstrictqi_1"
1576   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
1577         (match_operand:QI 1 "general_operand" "*qn,m"))]
1578   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1579    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1580   "mov{b}\t{%1, %0|%0, %1}"
1581   [(set_attr "type" "imov")
1582    (set_attr "mode" "QI")])
1584 (define_insn "*movstrictqi_xor"
1585   [(set (strict_low_part (match_operand:QI 0 "q_regs_operand" "+q"))
1586         (match_operand:QI 1 "const0_operand" "i"))
1587    (clobber (reg:CC FLAGS_REG))]
1588   "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1589   "xor{b}\t{%0, %0|%0, %0}"
1590   [(set_attr "type" "alu1")
1591    (set_attr "mode" "QI")
1592    (set_attr "length_immediate" "0")])
1594 (define_insn "*movsi_extv_1"
1595   [(set (match_operand:SI 0 "register_operand" "=R")
1596         (sign_extract:SI (match_operand 1 "ext_register_operand" "Q")
1597                          (const_int 8)
1598                          (const_int 8)))]
1599   ""
1600   "movs{bl|x}\t{%h1, %0|%0, %h1}"
1601   [(set_attr "type" "imovx")
1602    (set_attr "mode" "SI")])
1604 (define_insn "*movhi_extv_1"
1605   [(set (match_operand:HI 0 "register_operand" "=R")
1606         (sign_extract:HI (match_operand 1 "ext_register_operand" "Q")
1607                          (const_int 8)
1608                          (const_int 8)))]
1609   ""
1610   "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
1611   [(set_attr "type" "imovx")
1612    (set_attr "mode" "SI")])
1614 (define_insn "*movqi_extv_1"
1615   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
1616         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1617                          (const_int 8)
1618                          (const_int 8)))]
1619   "!TARGET_64BIT"
1621   switch (get_attr_type (insn))
1622     {
1623     case TYPE_IMOVX:
1624       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1625     default:
1626       return "mov{b}\t{%h1, %0|%0, %h1}";
1627     }
1629   [(set (attr "type")
1630      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1631                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1632                              (ne (symbol_ref "TARGET_MOVX")
1633                                  (const_int 0))))
1634         (const_string "imovx")
1635         (const_string "imov")))
1636    (set (attr "mode")
1637      (if_then_else (eq_attr "type" "imovx")
1638         (const_string "SI")
1639         (const_string "QI")))])
1641 (define_insn "*movqi_extv_1_rex64"
1642   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1643         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1644                          (const_int 8)
1645                          (const_int 8)))]
1646   "TARGET_64BIT"
1648   switch (get_attr_type (insn))
1649     {
1650     case TYPE_IMOVX:
1651       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1652     default:
1653       return "mov{b}\t{%h1, %0|%0, %h1}";
1654     }
1656   [(set (attr "type")
1657      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1658                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1659                              (ne (symbol_ref "TARGET_MOVX")
1660                                  (const_int 0))))
1661         (const_string "imovx")
1662         (const_string "imov")))
1663    (set (attr "mode")
1664      (if_then_else (eq_attr "type" "imovx")
1665         (const_string "SI")
1666         (const_string "QI")))])
1668 ;; Stores and loads of ax to arbitrary constant address.
1669 ;; We fake an second form of instruction to force reload to load address
1670 ;; into register when rax is not available
1671 (define_insn "*movabsqi_1_rex64"
1672   [(set (mem:QI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1673         (match_operand:QI 1 "nonmemory_operand" "a,er"))]
1674   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1675   "@
1676    movabs{b}\t{%1, %P0|%P0, %1}
1677    mov{b}\t{%1, %a0|%a0, %1}"
1678   [(set_attr "type" "imov")
1679    (set_attr "modrm" "0,*")
1680    (set_attr "length_address" "8,0")
1681    (set_attr "length_immediate" "0,*")
1682    (set_attr "memory" "store")
1683    (set_attr "mode" "QI")])
1685 (define_insn "*movabsqi_2_rex64"
1686   [(set (match_operand:QI 0 "register_operand" "=a,r")
1687         (mem:QI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1688   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1689   "@
1690    movabs{b}\t{%P1, %0|%0, %P1}
1691    mov{b}\t{%a1, %0|%0, %a1}"
1692   [(set_attr "type" "imov")
1693    (set_attr "modrm" "0,*")
1694    (set_attr "length_address" "8,0")
1695    (set_attr "length_immediate" "0")
1696    (set_attr "memory" "load")
1697    (set_attr "mode" "QI")])
1699 (define_insn "*movsi_extzv_1"
1700   [(set (match_operand:SI 0 "register_operand" "=R")
1701         (zero_extract:SI (match_operand 1 "ext_register_operand" "Q")
1702                          (const_int 8)
1703                          (const_int 8)))]
1704   ""
1705   "movz{bl|x}\t{%h1, %0|%0, %h1}"
1706   [(set_attr "type" "imovx")
1707    (set_attr "mode" "SI")])
1709 (define_insn "*movqi_extzv_2"
1710   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
1711         (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1712                                     (const_int 8)
1713                                     (const_int 8)) 0))]
1714   "!TARGET_64BIT"
1716   switch (get_attr_type (insn))
1717     {
1718     case TYPE_IMOVX:
1719       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1720     default:
1721       return "mov{b}\t{%h1, %0|%0, %h1}";
1722     }
1724   [(set (attr "type")
1725      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1726                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1727                              (ne (symbol_ref "TARGET_MOVX")
1728                                  (const_int 0))))
1729         (const_string "imovx")
1730         (const_string "imov")))
1731    (set (attr "mode")
1732      (if_then_else (eq_attr "type" "imovx")
1733         (const_string "SI")
1734         (const_string "QI")))])
1736 (define_insn "*movqi_extzv_2_rex64"
1737   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1738         (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1739                                     (const_int 8)
1740                                     (const_int 8)) 0))]
1741   "TARGET_64BIT"
1743   switch (get_attr_type (insn))
1744     {
1745     case TYPE_IMOVX:
1746       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1747     default:
1748       return "mov{b}\t{%h1, %0|%0, %h1}";
1749     }
1751   [(set (attr "type")
1752      (if_then_else (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1753                         (ne (symbol_ref "TARGET_MOVX")
1754                             (const_int 0)))
1755         (const_string "imovx")
1756         (const_string "imov")))
1757    (set (attr "mode")
1758      (if_then_else (eq_attr "type" "imovx")
1759         (const_string "SI")
1760         (const_string "QI")))])
1762 (define_insn "movsi_insv_1"
1763   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
1764                          (const_int 8)
1765                          (const_int 8))
1766         (match_operand:SI 1 "general_operand" "Qmn"))]
1767   "!TARGET_64BIT"
1768   "mov{b}\t{%b1, %h0|%h0, %b1}"
1769   [(set_attr "type" "imov")
1770    (set_attr "mode" "QI")])
1772 (define_insn "movdi_insv_1_rex64"
1773   [(set (zero_extract:DI (match_operand 0 "ext_register_operand" "+Q")
1774                          (const_int 8)
1775                          (const_int 8))
1776         (match_operand:DI 1 "nonmemory_operand" "Qn"))]
1777   "TARGET_64BIT"
1778   "mov{b}\t{%b1, %h0|%h0, %b1}"
1779   [(set_attr "type" "imov")
1780    (set_attr "mode" "QI")])
1782 (define_insn "*movqi_insv_2"
1783   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
1784                          (const_int 8)
1785                          (const_int 8))
1786         (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
1787                      (const_int 8)))]
1788   ""
1789   "mov{b}\t{%h1, %h0|%h0, %h1}"
1790   [(set_attr "type" "imov")
1791    (set_attr "mode" "QI")])
1793 (define_expand "movdi"
1794   [(set (match_operand:DI 0 "nonimmediate_operand" "")
1795         (match_operand:DI 1 "general_operand" ""))]
1796   ""
1797   "ix86_expand_move (DImode, operands); DONE;")
1799 (define_insn "*pushdi"
1800   [(set (match_operand:DI 0 "push_operand" "=<")
1801         (match_operand:DI 1 "general_no_elim_operand" "riF*m"))]
1802   "!TARGET_64BIT"
1803   "#")
1805 (define_insn "*pushdi2_rex64"
1806   [(set (match_operand:DI 0 "push_operand" "=<,!<")
1807         (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
1808   "TARGET_64BIT"
1809   "@
1810    push{q}\t%1
1811    #"
1812   [(set_attr "type" "push,multi")
1813    (set_attr "mode" "DI")])
1815 ;; Convert impossible pushes of immediate to existing instructions.
1816 ;; First try to get scratch register and go through it.  In case this
1817 ;; fails, push sign extended lower part first and then overwrite
1818 ;; upper part by 32bit move.
1819 (define_peephole2
1820   [(match_scratch:DI 2 "r")
1821    (set (match_operand:DI 0 "push_operand" "")
1822         (match_operand:DI 1 "immediate_operand" ""))]
1823   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1824    && !x86_64_immediate_operand (operands[1], DImode)"
1825   [(set (match_dup 2) (match_dup 1))
1826    (set (match_dup 0) (match_dup 2))]
1827   "")
1829 ;; We need to define this as both peepholer and splitter for case
1830 ;; peephole2 pass is not run.
1831 ;; "&& 1" is needed to keep it from matching the previous pattern.
1832 (define_peephole2
1833   [(set (match_operand:DI 0 "push_operand" "")
1834         (match_operand:DI 1 "immediate_operand" ""))]
1835   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1836    && !x86_64_immediate_operand (operands[1], DImode) && 1"
1837   [(set (match_dup 0) (match_dup 1))
1838    (set (match_dup 2) (match_dup 3))]
1839   "split_di (operands + 1, 1, operands + 2, operands + 3);
1840    operands[1] = gen_lowpart (DImode, operands[2]);
1841    operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1842                                                     GEN_INT (4)));
1843   ")
1845 (define_split
1846   [(set (match_operand:DI 0 "push_operand" "")
1847         (match_operand:DI 1 "immediate_operand" ""))]
1848   "TARGET_64BIT && (flag_peephole2 ? flow2_completed : reload_completed)
1849    && !symbolic_operand (operands[1], DImode)
1850    && !x86_64_immediate_operand (operands[1], DImode)"
1851   [(set (match_dup 0) (match_dup 1))
1852    (set (match_dup 2) (match_dup 3))]
1853   "split_di (operands + 1, 1, operands + 2, operands + 3);
1854    operands[1] = gen_lowpart (DImode, operands[2]);
1855    operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1856                                                     GEN_INT (4)));
1857   ")
1859 (define_insn "*pushdi2_prologue_rex64"
1860   [(set (match_operand:DI 0 "push_operand" "=<")
1861         (match_operand:DI 1 "general_no_elim_operand" "re*m"))
1862    (clobber (mem:BLK (scratch)))]
1863   "TARGET_64BIT"
1864   "push{q}\t%1"
1865   [(set_attr "type" "push")
1866    (set_attr "mode" "DI")])
1868 (define_insn "*popdi1_epilogue_rex64"
1869   [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
1870         (mem:DI (reg:DI SP_REG)))
1871    (set (reg:DI SP_REG)
1872         (plus:DI (reg:DI SP_REG) (const_int 8)))
1873    (clobber (mem:BLK (scratch)))]
1874   "TARGET_64BIT"
1875   "pop{q}\t%0"
1876   [(set_attr "type" "pop")
1877    (set_attr "mode" "DI")])
1879 (define_insn "popdi1"
1880   [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
1881         (mem:DI (reg:DI SP_REG)))
1882    (set (reg:DI SP_REG)
1883         (plus:DI (reg:DI SP_REG) (const_int 8)))]
1884   "TARGET_64BIT"
1885   "pop{q}\t%0"
1886   [(set_attr "type" "pop")
1887    (set_attr "mode" "DI")])
1889 (define_insn "*movdi_xor_rex64"
1890   [(set (match_operand:DI 0 "register_operand" "=r")
1891         (match_operand:DI 1 "const0_operand" "i"))
1892    (clobber (reg:CC FLAGS_REG))]
1893   "TARGET_64BIT && (!TARGET_USE_MOV0 || optimize_size)
1894    && reload_completed"
1895   "xor{l}\t{%k0, %k0|%k0, %k0}"
1896   [(set_attr "type" "alu1")
1897    (set_attr "mode" "SI")
1898    (set_attr "length_immediate" "0")])
1900 (define_insn "*movdi_or_rex64"
1901   [(set (match_operand:DI 0 "register_operand" "=r")
1902         (match_operand:DI 1 "const_int_operand" "i"))
1903    (clobber (reg:CC FLAGS_REG))]
1904   "TARGET_64BIT && (TARGET_PENTIUM || optimize_size)
1905    && reload_completed
1906    && operands[1] == constm1_rtx"
1908   operands[1] = constm1_rtx;
1909   return "or{q}\t{%1, %0|%0, %1}";
1911   [(set_attr "type" "alu1")
1912    (set_attr "mode" "DI")
1913    (set_attr "length_immediate" "1")])
1915 (define_insn "*movdi_2"
1916   [(set (match_operand:DI 0 "nonimmediate_operand"
1917                                 "=r  ,o  ,*y,m*y,*y,*Y,m ,*Y,*Y,*x,m ,*x,*x")
1918         (match_operand:DI 1 "general_operand"
1919                                 "riFo,riF,C ,*y ,m ,C ,*Y,*Y,m ,C ,*x,*x,m "))]
1920   "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1921   "@
1922    #
1923    #
1924    pxor\t%0, %0
1925    movq\t{%1, %0|%0, %1}
1926    movq\t{%1, %0|%0, %1}
1927    pxor\t%0, %0
1928    movq\t{%1, %0|%0, %1}
1929    movdqa\t{%1, %0|%0, %1}
1930    movq\t{%1, %0|%0, %1}
1931    xorps\t%0, %0
1932    movlps\t{%1, %0|%0, %1}
1933    movaps\t{%1, %0|%0, %1}
1934    movlps\t{%1, %0|%0, %1}"
1935   [(set_attr "type" "*,*,mmx,mmxmov,mmxmov,sselog1,ssemov,ssemov,ssemov,sselog1,ssemov,ssemov,ssemov")
1936    (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF")])
1938 (define_split
1939   [(set (match_operand:DI 0 "push_operand" "")
1940         (match_operand:DI 1 "general_operand" ""))]
1941   "!TARGET_64BIT && reload_completed
1942    && (! MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
1943   [(const_int 0)]
1944   "ix86_split_long_move (operands); DONE;")
1946 ;; %%% This multiword shite has got to go.
1947 (define_split
1948   [(set (match_operand:DI 0 "nonimmediate_operand" "")
1949         (match_operand:DI 1 "general_operand" ""))]
1950   "!TARGET_64BIT && reload_completed
1951    && (!MMX_REG_P (operands[0]) && !SSE_REG_P (operands[0]))
1952    && (!MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
1953   [(const_int 0)]
1954   "ix86_split_long_move (operands); DONE;")
1956 (define_insn "*movdi_1_rex64"
1957   [(set (match_operand:DI 0 "nonimmediate_operand"
1958                 "=r,r  ,r,m ,!m,*y,*y,?rm,?*y,*x,*x,?rm,?*x,?*x,?*y")
1959         (match_operand:DI 1 "general_operand"
1960                 "Z ,rem,i,re,n ,C ,*y,*y ,rm ,C ,*x,*x ,rm ,*y ,*x"))]
1961   "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1963   switch (get_attr_type (insn))
1964     {
1965     case TYPE_SSECVT:
1966       if (which_alternative == 13)
1967         return "movq2dq\t{%1, %0|%0, %1}";
1968       else
1969         return "movdq2q\t{%1, %0|%0, %1}";
1970     case TYPE_SSEMOV:
1971       if (get_attr_mode (insn) == MODE_TI)
1972           return "movdqa\t{%1, %0|%0, %1}";
1973       /* FALLTHRU */
1974     case TYPE_MMXMOV:
1975       /* Moves from and into integer register is done using movd opcode with
1976          REX prefix.  */
1977       if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
1978           return "movd\t{%1, %0|%0, %1}";
1979       return "movq\t{%1, %0|%0, %1}";
1980     case TYPE_SSELOG1:
1981     case TYPE_MMXADD:
1982       return "pxor\t%0, %0";
1983     case TYPE_MULTI:
1984       return "#";
1985     case TYPE_LEA:
1986       return "lea{q}\t{%a1, %0|%0, %a1}";
1987     default:
1988       if (flag_pic && !LEGITIMATE_PIC_OPERAND_P (operands[1]))
1989         abort ();
1990       if (get_attr_mode (insn) == MODE_SI)
1991         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1992       else if (which_alternative == 2)
1993         return "movabs{q}\t{%1, %0|%0, %1}";
1994       else
1995         return "mov{q}\t{%1, %0|%0, %1}";
1996     }
1998   [(set (attr "type")
1999      (cond [(eq_attr "alternative" "5")
2000               (const_string "mmx")
2001             (eq_attr "alternative" "6,7,8")
2002               (const_string "mmxmov")
2003             (eq_attr "alternative" "9")
2004               (const_string "sselog1")
2005             (eq_attr "alternative" "10,11,12")
2006               (const_string "ssemov")
2007             (eq_attr "alternative" "13,14")
2008               (const_string "ssecvt")
2009             (eq_attr "alternative" "4")
2010               (const_string "multi")
2011             (and (ne (symbol_ref "flag_pic") (const_int 0))
2012                  (match_operand:DI 1 "symbolic_operand" ""))
2013               (const_string "lea")
2014            ]
2015            (const_string "imov")))
2016    (set_attr "modrm" "*,0,0,*,*,*,*,*,*,*,*,*,*,*,*")
2017    (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*,*,*,*,*,*,*")
2018    (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,TI,TI,DI,DI,DI,DI")])
2020 ;; Stores and loads of ax to arbitrary constant address.
2021 ;; We fake an second form of instruction to force reload to load address
2022 ;; into register when rax is not available
2023 (define_insn "*movabsdi_1_rex64"
2024   [(set (mem:DI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2025         (match_operand:DI 1 "nonmemory_operand" "a,er"))]
2026   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
2027   "@
2028    movabs{q}\t{%1, %P0|%P0, %1}
2029    mov{q}\t{%1, %a0|%a0, %1}"
2030   [(set_attr "type" "imov")
2031    (set_attr "modrm" "0,*")
2032    (set_attr "length_address" "8,0")
2033    (set_attr "length_immediate" "0,*")
2034    (set_attr "memory" "store")
2035    (set_attr "mode" "DI")])
2037 (define_insn "*movabsdi_2_rex64"
2038   [(set (match_operand:DI 0 "register_operand" "=a,r")
2039         (mem:DI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2040   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
2041   "@
2042    movabs{q}\t{%P1, %0|%0, %P1}
2043    mov{q}\t{%a1, %0|%0, %a1}"
2044   [(set_attr "type" "imov")
2045    (set_attr "modrm" "0,*")
2046    (set_attr "length_address" "8,0")
2047    (set_attr "length_immediate" "0")
2048    (set_attr "memory" "load")
2049    (set_attr "mode" "DI")])
2051 ;; Convert impossible stores of immediate to existing instructions.
2052 ;; First try to get scratch register and go through it.  In case this
2053 ;; fails, move by 32bit parts.
2054 (define_peephole2
2055   [(match_scratch:DI 2 "r")
2056    (set (match_operand:DI 0 "memory_operand" "")
2057         (match_operand:DI 1 "immediate_operand" ""))]
2058   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2059    && !x86_64_immediate_operand (operands[1], DImode)"
2060   [(set (match_dup 2) (match_dup 1))
2061    (set (match_dup 0) (match_dup 2))]
2062   "")
2064 ;; We need to define this as both peepholer and splitter for case
2065 ;; peephole2 pass is not run.
2066 ;; "&& 1" is needed to keep it from matching the previous pattern.
2067 (define_peephole2
2068   [(set (match_operand:DI 0 "memory_operand" "")
2069         (match_operand:DI 1 "immediate_operand" ""))]
2070   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2071    && !x86_64_immediate_operand (operands[1], DImode) && 1"
2072   [(set (match_dup 2) (match_dup 3))
2073    (set (match_dup 4) (match_dup 5))]
2074   "split_di (operands, 2, operands + 2, operands + 4);")
2076 (define_split
2077   [(set (match_operand:DI 0 "memory_operand" "")
2078         (match_operand:DI 1 "immediate_operand" ""))]
2079   "TARGET_64BIT && (flag_peephole2 ? flow2_completed : reload_completed)
2080    && !symbolic_operand (operands[1], DImode)
2081    && !x86_64_immediate_operand (operands[1], DImode)"
2082   [(set (match_dup 2) (match_dup 3))
2083    (set (match_dup 4) (match_dup 5))]
2084   "split_di (operands, 2, operands + 2, operands + 4);")
2086 (define_insn "*swapdi_rex64"
2087   [(set (match_operand:DI 0 "register_operand" "+r")
2088         (match_operand:DI 1 "register_operand" "+r"))
2089    (set (match_dup 1)
2090         (match_dup 0))]
2091   "TARGET_64BIT"
2092   "xchg{q}\t%1, %0"
2093   [(set_attr "type" "imov")
2094    (set_attr "mode" "DI")
2095    (set_attr "pent_pair" "np")
2096    (set_attr "athlon_decode" "vector")])
2098 (define_expand "movti"
2099   [(set (match_operand:TI 0 "nonimmediate_operand" "")
2100         (match_operand:TI 1 "nonimmediate_operand" ""))]
2101   "TARGET_SSE || TARGET_64BIT"
2103   if (TARGET_64BIT)
2104     ix86_expand_move (TImode, operands);
2105   else
2106     ix86_expand_vector_move (TImode, operands);
2107   DONE;
2110 (define_insn "*movti_internal"
2111   [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
2112         (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
2113   "TARGET_SSE && !TARGET_64BIT
2114    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2116   switch (which_alternative)
2117     {
2118     case 0:
2119       if (get_attr_mode (insn) == MODE_V4SF)
2120         return "xorps\t%0, %0";
2121       else
2122         return "pxor\t%0, %0";
2123     case 1:
2124     case 2:
2125       if (get_attr_mode (insn) == MODE_V4SF)
2126         return "movaps\t{%1, %0|%0, %1}";
2127       else
2128         return "movdqa\t{%1, %0|%0, %1}";
2129     default:
2130       abort ();
2131     }
2133   [(set_attr "type" "ssemov,ssemov,ssemov")
2134    (set (attr "mode")
2135         (cond [(eq (symbol_ref "TARGET_SSE2") (const_int 0))
2136                  (const_string "V4SF")
2138                (eq_attr "alternative" "0,1")
2139                  (if_then_else
2140                    (ne (symbol_ref "optimize_size")
2141                        (const_int 0))
2142                    (const_string "V4SF")
2143                    (const_string "TI"))
2144                (eq_attr "alternative" "2")
2145                  (if_then_else
2146                    (ne (symbol_ref "optimize_size")
2147                        (const_int 0))
2148                    (const_string "V4SF")
2149                    (const_string "TI"))]
2150                (const_string "TI")))])
2152 (define_insn "*movti_rex64"
2153   [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o,x,x,xm")
2154         (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
2155   "TARGET_64BIT
2156    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2158   switch (which_alternative)
2159     {
2160     case 0:
2161     case 1:
2162       return "#";
2163     case 2:
2164       if (get_attr_mode (insn) == MODE_V4SF)
2165         return "xorps\t%0, %0";
2166       else
2167         return "pxor\t%0, %0";
2168     case 3:
2169     case 4:
2170       if (get_attr_mode (insn) == MODE_V4SF)
2171         return "movaps\t{%1, %0|%0, %1}";
2172       else
2173         return "movdqa\t{%1, %0|%0, %1}";
2174     default:
2175       abort ();
2176     }
2178   [(set_attr "type" "*,*,ssemov,ssemov,ssemov")
2179    (set (attr "mode")
2180         (cond [(eq_attr "alternative" "2,3")
2181                  (if_then_else
2182                    (ne (symbol_ref "optimize_size")
2183                        (const_int 0))
2184                    (const_string "V4SF")
2185                    (const_string "TI"))
2186                (eq_attr "alternative" "4")
2187                  (if_then_else
2188                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2189                             (const_int 0))
2190                         (ne (symbol_ref "optimize_size")
2191                             (const_int 0)))
2192                    (const_string "V4SF")
2193                    (const_string "TI"))]
2194                (const_string "DI")))])
2196 (define_split
2197   [(set (match_operand:TI 0 "nonimmediate_operand" "")
2198         (match_operand:TI 1 "general_operand" ""))]
2199   "reload_completed && !SSE_REG_P (operands[0])
2200    && !SSE_REG_P (operands[1])"
2201   [(const_int 0)]
2202   "ix86_split_long_move (operands); DONE;")
2204 (define_expand "movsf"
2205   [(set (match_operand:SF 0 "nonimmediate_operand" "")
2206         (match_operand:SF 1 "general_operand" ""))]
2207   ""
2208   "ix86_expand_move (SFmode, operands); DONE;")
2210 (define_insn "*pushsf"
2211   [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2212         (match_operand:SF 1 "general_no_elim_operand" "f#rx,rFm#fx,x#rf"))]
2213   "!TARGET_64BIT"
2215   switch (which_alternative)
2216     {
2217     case 1:
2218       return "push{l}\t%1";
2220     default:
2221       /* This insn should be already split before reg-stack.  */
2222       abort ();
2223     }
2225   [(set_attr "type" "multi,push,multi")
2226    (set_attr "mode" "SF,SI,SF")])
2228 (define_insn "*pushsf_rex64"
2229   [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2230         (match_operand:SF 1 "nonmemory_no_elim_operand" "f#rx,rF#fx,x#rf"))]
2231   "TARGET_64BIT"
2233   switch (which_alternative)
2234     {
2235     case 1:
2236       return "push{q}\t%q1";
2238     default:
2239       /* This insn should be already split before reg-stack.  */
2240       abort ();
2241     }
2243   [(set_attr "type" "multi,push,multi")
2244    (set_attr "mode" "SF,DI,SF")])
2246 (define_split
2247   [(set (match_operand:SF 0 "push_operand" "")
2248         (match_operand:SF 1 "memory_operand" ""))]
2249   "reload_completed
2250    && GET_CODE (operands[1]) == MEM
2251    && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
2252    && CONSTANT_POOL_ADDRESS_P (XEXP (operands[1], 0))"
2253   [(set (match_dup 0)
2254         (match_dup 1))]
2255   "operands[1] = get_pool_constant (XEXP (operands[1], 0));")
2258 ;; %%% Kill this when call knows how to work this out.
2259 (define_split
2260   [(set (match_operand:SF 0 "push_operand" "")
2261         (match_operand:SF 1 "any_fp_register_operand" ""))]
2262   "!TARGET_64BIT"
2263   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
2264    (set (mem:SF (reg:SI SP_REG)) (match_dup 1))])
2266 (define_split
2267   [(set (match_operand:SF 0 "push_operand" "")
2268         (match_operand:SF 1 "any_fp_register_operand" ""))]
2269   "TARGET_64BIT"
2270   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2271    (set (mem:SF (reg:DI SP_REG)) (match_dup 1))])
2273 (define_insn "*movsf_1"
2274   [(set (match_operand:SF 0 "nonimmediate_operand"
2275           "=f#xr,m   ,f#xr,r#xf  ,m    ,x#rf,x#rf,x#rf ,m   ,!*y,!rm,!*y")
2276         (match_operand:SF 1 "general_operand"
2277           "fm#rx,f#rx,G   ,rmF#fx,Fr#fx,C   ,x   ,xm#rf,x#rf,rm ,*y ,*y"))]
2278   "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2279    && (reload_in_progress || reload_completed
2280        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2281        || GET_CODE (operands[1]) != CONST_DOUBLE
2282        || memory_operand (operands[0], SFmode))" 
2284   switch (which_alternative)
2285     {
2286     case 0:
2287       return output_387_reg_move (insn, operands);
2289     case 1:
2290       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2291         return "fstp%z0\t%y0";
2292       else
2293         return "fst%z0\t%y0";
2295     case 2:
2296       return standard_80387_constant_opcode (operands[1]);
2298     case 3:
2299     case 4:
2300       return "mov{l}\t{%1, %0|%0, %1}";
2301     case 5:
2302       if (get_attr_mode (insn) == MODE_TI)
2303         return "pxor\t%0, %0";
2304       else
2305         return "xorps\t%0, %0";
2306     case 6:
2307       if (get_attr_mode (insn) == MODE_V4SF)
2308         return "movaps\t{%1, %0|%0, %1}";
2309       else
2310         return "movss\t{%1, %0|%0, %1}";
2311     case 7:
2312     case 8:
2313       return "movss\t{%1, %0|%0, %1}";
2315     case 9:
2316     case 10:
2317       return "movd\t{%1, %0|%0, %1}";
2319     case 11:
2320       return "movq\t{%1, %0|%0, %1}";
2322     default:
2323       abort();
2324     }
2326   [(set_attr "type" "fmov,fmov,fmov,imov,imov,ssemov,ssemov,ssemov,ssemov,mmxmov,mmxmov,mmxmov")
2327    (set (attr "mode")
2328         (cond [(eq_attr "alternative" "3,4,9,10")
2329                  (const_string "SI")
2330                (eq_attr "alternative" "5")
2331                  (if_then_else
2332                    (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2333                                  (const_int 0))
2334                              (ne (symbol_ref "TARGET_SSE2")
2335                                  (const_int 0)))
2336                         (eq (symbol_ref "optimize_size")
2337                             (const_int 0)))
2338                    (const_string "TI")
2339                    (const_string "V4SF"))
2340                /* For architectures resolving dependencies on
2341                   whole SSE registers use APS move to break dependency
2342                   chains, otherwise use short move to avoid extra work. 
2344                   Do the same for architectures resolving dependencies on
2345                   the parts.  While in DF mode it is better to always handle
2346                   just register parts, the SF mode is different due to lack
2347                   of instructions to load just part of the register.  It is
2348                   better to maintain the whole registers in single format
2349                   to avoid problems on using packed logical operations.  */
2350                (eq_attr "alternative" "6")
2351                  (if_then_else
2352                    (ior (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2353                             (const_int 0))
2354                         (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2355                             (const_int 0)))
2356                    (const_string "V4SF")
2357                    (const_string "SF"))
2358                (eq_attr "alternative" "11")
2359                  (const_string "DI")]
2360                (const_string "SF")))])
2362 (define_insn "*swapsf"
2363   [(set (match_operand:SF 0 "fp_register_operand" "+f")
2364         (match_operand:SF 1 "fp_register_operand" "+f"))
2365    (set (match_dup 1)
2366         (match_dup 0))]
2367   "reload_completed || TARGET_80387"
2369   if (STACK_TOP_P (operands[0]))
2370     return "fxch\t%1";
2371   else
2372     return "fxch\t%0";
2374   [(set_attr "type" "fxch")
2375    (set_attr "mode" "SF")])
2377 (define_expand "movdf"
2378   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2379         (match_operand:DF 1 "general_operand" ""))]
2380   ""
2381   "ix86_expand_move (DFmode, operands); DONE;")
2383 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2384 ;; Size of pushdf using integer instructions is 2+2*memory operand size
2385 ;; On the average, pushdf using integers can be still shorter.  Allow this
2386 ;; pattern for optimize_size too.
2388 (define_insn "*pushdf_nointeger"
2389   [(set (match_operand:DF 0 "push_operand" "=<,<,<,<")
2390         (match_operand:DF 1 "general_no_elim_operand" "f#Y,Fo#fY,*r#fY,Y#f"))]
2391   "!TARGET_64BIT && !TARGET_INTEGER_DFMODE_MOVES"
2393   /* This insn should be already split before reg-stack.  */
2394   abort ();
2396   [(set_attr "type" "multi")
2397    (set_attr "mode" "DF,SI,SI,DF")])
2399 (define_insn "*pushdf_integer"
2400   [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2401         (match_operand:DF 1 "general_no_elim_operand" "f#rY,rFo#fY,Y#rf"))]
2402   "TARGET_64BIT || TARGET_INTEGER_DFMODE_MOVES"
2404   /* This insn should be already split before reg-stack.  */
2405   abort ();
2407   [(set_attr "type" "multi")
2408    (set_attr "mode" "DF,SI,DF")])
2410 ;; %%% Kill this when call knows how to work this out.
2411 (define_split
2412   [(set (match_operand:DF 0 "push_operand" "")
2413         (match_operand:DF 1 "any_fp_register_operand" ""))]
2414   "!TARGET_64BIT && reload_completed"
2415   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
2416    (set (mem:DF (reg:SI SP_REG)) (match_dup 1))]
2417   "")
2419 (define_split
2420   [(set (match_operand:DF 0 "push_operand" "")
2421         (match_operand:DF 1 "any_fp_register_operand" ""))]
2422   "TARGET_64BIT && reload_completed"
2423   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2424    (set (mem:DF (reg:DI SP_REG)) (match_dup 1))]
2425   "")
2427 (define_split
2428   [(set (match_operand:DF 0 "push_operand" "")
2429         (match_operand:DF 1 "general_operand" ""))]
2430   "reload_completed"
2431   [(const_int 0)]
2432   "ix86_split_long_move (operands); DONE;")
2434 ;; Moving is usually shorter when only FP registers are used. This separate
2435 ;; movdf pattern avoids the use of integer registers for FP operations
2436 ;; when optimizing for size.
2438 (define_insn "*movdf_nointeger"
2439   [(set (match_operand:DF 0 "nonimmediate_operand"
2440                         "=f#Y,m  ,f#Y,*r  ,o  ,Y*x#f,Y*x#f,Y*x#f  ,m    ")
2441         (match_operand:DF 1 "general_operand"
2442                         "fm#Y,f#Y,G  ,*roF,F*r,C    ,Y*x#f,HmY*x#f,Y*x#f"))]
2443   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2444    && ((optimize_size || !TARGET_INTEGER_DFMODE_MOVES) && !TARGET_64BIT)
2445    && (reload_in_progress || reload_completed
2446        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2447        || GET_CODE (operands[1]) != CONST_DOUBLE
2448        || memory_operand (operands[0], DFmode))" 
2450   switch (which_alternative)
2451     {
2452     case 0:
2453       return output_387_reg_move (insn, operands);
2455     case 1:
2456       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2457         return "fstp%z0\t%y0";
2458       else
2459         return "fst%z0\t%y0";
2461     case 2:
2462       return standard_80387_constant_opcode (operands[1]);
2464     case 3:
2465     case 4:
2466       return "#";
2467     case 5:
2468       switch (get_attr_mode (insn))
2469         {
2470         case MODE_V4SF:
2471           return "xorps\t%0, %0";
2472         case MODE_V2DF:
2473           return "xorpd\t%0, %0";
2474         case MODE_TI:
2475           return "pxor\t%0, %0";
2476         default:
2477           abort ();
2478         }
2479     case 6:
2480     case 7:
2481     case 8:
2482       switch (get_attr_mode (insn))
2483         {
2484         case MODE_V4SF:
2485           return "movaps\t{%1, %0|%0, %1}";
2486         case MODE_V2DF:
2487           return "movapd\t{%1, %0|%0, %1}";
2488         case MODE_TI:
2489           return "movdqa\t{%1, %0|%0, %1}";
2490         case MODE_DI:
2491           return "movq\t{%1, %0|%0, %1}";
2492         case MODE_DF:
2493           return "movsd\t{%1, %0|%0, %1}";
2494         case MODE_V1DF:
2495           return "movlpd\t{%1, %0|%0, %1}";
2496         case MODE_V2SF:
2497           return "movlps\t{%1, %0|%0, %1}";
2498         default:
2499           abort ();
2500         }
2502     default:
2503       abort();
2504     }
2506   [(set_attr "type" "fmov,fmov,fmov,multi,multi,ssemov,ssemov,ssemov,ssemov")
2507    (set (attr "mode")
2508         (cond [(eq_attr "alternative" "0,1,2")
2509                  (const_string "DF")
2510                (eq_attr "alternative" "3,4")
2511                  (const_string "SI")
2513                /* For SSE1, we have many fewer alternatives.  */
2514                (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2515                  (cond [(eq_attr "alternative" "5,6")
2516                           (const_string "V4SF")
2517                        ]
2518                    (const_string "V2SF"))
2520                /* xorps is one byte shorter.  */
2521                (eq_attr "alternative" "5")
2522                  (cond [(ne (symbol_ref "optimize_size")
2523                             (const_int 0))
2524                           (const_string "V4SF")
2525                         (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2526                             (const_int 0))
2527                           (const_string "TI")
2528                        ]
2529                        (const_string "V2DF"))
2531                /* For architectures resolving dependencies on
2532                   whole SSE registers use APD move to break dependency
2533                   chains, otherwise use short move to avoid extra work.
2535                   movaps encodes one byte shorter.  */
2536                (eq_attr "alternative" "6")
2537                  (cond
2538                    [(ne (symbol_ref "optimize_size")
2539                         (const_int 0))
2540                       (const_string "V4SF")
2541                     (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2542                         (const_int 0))
2543                       (const_string "V2DF")
2544                    ]
2545                    (const_string "DF"))
2546                /* For architectures resolving dependencies on register
2547                   parts we may avoid extra work to zero out upper part
2548                   of register.  */
2549                (eq_attr "alternative" "7")
2550                  (if_then_else
2551                    (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2552                        (const_int 0))
2553                    (const_string "V1DF")
2554                    (const_string "DF"))
2555               ]
2556               (const_string "DF")))])
2558 (define_insn "*movdf_integer"
2559   [(set (match_operand:DF 0 "nonimmediate_operand"
2560                 "=f#Yr,m   ,f#Yr,r#Yf  ,o    ,Y*x#rf,Y*x#rf,Y*x#rf,m")
2561         (match_operand:DF 1 "general_operand"
2562                 "fm#Yr,f#Yr,G   ,roF#Yf,Fr#Yf,C     ,Y*x#rf,m     ,Y*x#rf"))]
2563   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2564    && ((!optimize_size && TARGET_INTEGER_DFMODE_MOVES) || TARGET_64BIT)
2565    && (reload_in_progress || reload_completed
2566        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2567        || GET_CODE (operands[1]) != CONST_DOUBLE
2568        || memory_operand (operands[0], DFmode))" 
2570   switch (which_alternative)
2571     {
2572     case 0:
2573       return output_387_reg_move (insn, operands);
2575     case 1:
2576       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2577         return "fstp%z0\t%y0";
2578       else
2579         return "fst%z0\t%y0";
2581     case 2:
2582       return standard_80387_constant_opcode (operands[1]);
2584     case 3:
2585     case 4:
2586       return "#";
2588     case 5:
2589       switch (get_attr_mode (insn))
2590         {
2591         case MODE_V4SF:
2592           return "xorps\t%0, %0";
2593         case MODE_V2DF:
2594           return "xorpd\t%0, %0";
2595         case MODE_TI:
2596           return "pxor\t%0, %0";
2597         default:
2598           abort ();
2599         }
2600     case 6:
2601     case 7:
2602     case 8:
2603       switch (get_attr_mode (insn))
2604         {
2605         case MODE_V4SF:
2606           return "movaps\t{%1, %0|%0, %1}";
2607         case MODE_V2DF:
2608           return "movapd\t{%1, %0|%0, %1}";
2609         case MODE_TI:
2610           return "movdqa\t{%1, %0|%0, %1}";
2611         case MODE_DI:
2612           return "movq\t{%1, %0|%0, %1}";
2613         case MODE_DF:
2614           return "movsd\t{%1, %0|%0, %1}";
2615         case MODE_V1DF:
2616           return "movlpd\t{%1, %0|%0, %1}";
2617         case MODE_V2SF:
2618           return "movlps\t{%1, %0|%0, %1}";
2619         default:
2620           abort ();
2621         }
2623     default:
2624       abort();
2625     }
2627   [(set_attr "type" "fmov,fmov,fmov,multi,multi,ssemov,ssemov,ssemov,ssemov")
2628    (set (attr "mode")
2629         (cond [(eq_attr "alternative" "0,1,2")
2630                  (const_string "DF")
2631                (eq_attr "alternative" "3,4")
2632                  (const_string "SI")
2634                /* For SSE1, we have many fewer alternatives.  */
2635                (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2636                  (cond [(eq_attr "alternative" "5,6")
2637                           (const_string "V4SF")
2638                        ]
2639                    (const_string "V2SF"))
2641                /* xorps is one byte shorter.  */
2642                (eq_attr "alternative" "5")
2643                  (cond [(ne (symbol_ref "optimize_size")
2644                             (const_int 0))
2645                           (const_string "V4SF")
2646                         (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2647                             (const_int 0))
2648                           (const_string "TI")
2649                        ]
2650                        (const_string "V2DF"))
2652                /* For architectures resolving dependencies on
2653                   whole SSE registers use APD move to break dependency
2654                   chains, otherwise use short move to avoid extra work.
2656                   movaps encodes one byte shorter.  */
2657                (eq_attr "alternative" "6")
2658                  (cond
2659                    [(ne (symbol_ref "optimize_size")
2660                         (const_int 0))
2661                       (const_string "V4SF")
2662                     (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2663                         (const_int 0))
2664                       (const_string "V2DF")
2665                    ]
2666                    (const_string "DF"))
2667                /* For architectures resolving dependencies on register
2668                   parts we may avoid extra work to zero out upper part
2669                   of register.  */
2670                (eq_attr "alternative" "7")
2671                  (if_then_else
2672                    (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2673                        (const_int 0))
2674                    (const_string "V1DF")
2675                    (const_string "DF"))
2676               ]
2677               (const_string "DF")))])
2679 (define_split
2680   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2681         (match_operand:DF 1 "general_operand" ""))]
2682   "reload_completed
2683    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2684    && ! (ANY_FP_REG_P (operands[0]) || 
2685          (GET_CODE (operands[0]) == SUBREG
2686           && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2687    && ! (ANY_FP_REG_P (operands[1]) || 
2688          (GET_CODE (operands[1]) == SUBREG
2689           && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2690   [(const_int 0)]
2691   "ix86_split_long_move (operands); DONE;")
2693 (define_insn "*swapdf"
2694   [(set (match_operand:DF 0 "fp_register_operand" "+f")
2695         (match_operand:DF 1 "fp_register_operand" "+f"))
2696    (set (match_dup 1)
2697         (match_dup 0))]
2698   "reload_completed || TARGET_80387"
2700   if (STACK_TOP_P (operands[0]))
2701     return "fxch\t%1";
2702   else
2703     return "fxch\t%0";
2705   [(set_attr "type" "fxch")
2706    (set_attr "mode" "DF")])
2708 (define_expand "movxf"
2709   [(set (match_operand:XF 0 "nonimmediate_operand" "")
2710         (match_operand:XF 1 "general_operand" ""))]
2711   ""
2712   "ix86_expand_move (XFmode, operands); DONE;")
2714 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2715 ;; Size of pushdf using integer instructions is 3+3*memory operand size
2716 ;; Pushing using integer instructions is longer except for constants
2717 ;; and direct memory references.
2718 ;; (assuming that any given constant is pushed only once, but this ought to be
2719 ;;  handled elsewhere).
2721 (define_insn "*pushxf_nointeger"
2722   [(set (match_operand:XF 0 "push_operand" "=X,X,X")
2723         (match_operand:XF 1 "general_no_elim_operand" "f,Fo,*r"))]
2724   "optimize_size"
2726   /* This insn should be already split before reg-stack.  */
2727   abort ();
2729   [(set_attr "type" "multi")
2730    (set_attr "mode" "XF,SI,SI")])
2732 (define_insn "*pushxf_integer"
2733   [(set (match_operand:XF 0 "push_operand" "=<,<")
2734         (match_operand:XF 1 "general_no_elim_operand" "f#r,ro#f"))]
2735   "!optimize_size"
2737   /* This insn should be already split before reg-stack.  */
2738   abort ();
2740   [(set_attr "type" "multi")
2741    (set_attr "mode" "XF,SI")])
2743 (define_split
2744   [(set (match_operand 0 "push_operand" "")
2745         (match_operand 1 "general_operand" ""))]
2746   "reload_completed
2747    && (GET_MODE (operands[0]) == XFmode
2748        || GET_MODE (operands[0]) == DFmode)
2749    && !ANY_FP_REG_P (operands[1])"
2750   [(const_int 0)]
2751   "ix86_split_long_move (operands); DONE;")
2753 (define_split
2754   [(set (match_operand:XF 0 "push_operand" "")
2755         (match_operand:XF 1 "any_fp_register_operand" ""))]
2756   "!TARGET_64BIT"
2757   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
2758    (set (mem:XF (reg:SI SP_REG)) (match_dup 1))]
2759   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
2761 (define_split
2762   [(set (match_operand:XF 0 "push_operand" "")
2763         (match_operand:XF 1 "any_fp_register_operand" ""))]
2764   "TARGET_64BIT"
2765   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
2766    (set (mem:XF (reg:DI SP_REG)) (match_dup 1))]
2767   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
2769 ;; Do not use integer registers when optimizing for size
2770 (define_insn "*movxf_nointeger"
2771   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,*r,o")
2772         (match_operand:XF 1 "general_operand" "fm,f,G,*roF,F*r"))]
2773   "optimize_size
2774    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2775    && (reload_in_progress || reload_completed
2776        || GET_CODE (operands[1]) != CONST_DOUBLE
2777        || memory_operand (operands[0], XFmode))" 
2779   switch (which_alternative)
2780     {
2781     case 0:
2782       return output_387_reg_move (insn, operands);
2784     case 1:
2785       /* There is no non-popping store to memory for XFmode.  So if
2786          we need one, follow the store with a load.  */
2787       if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2788         return "fstp%z0\t%y0\;fld%z0\t%y0";
2789       else
2790         return "fstp%z0\t%y0";
2792     case 2:
2793       return standard_80387_constant_opcode (operands[1]);
2795     case 3: case 4:
2796       return "#";
2797     }
2798   abort();
2800   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2801    (set_attr "mode" "XF,XF,XF,SI,SI")])
2803 (define_insn "*movxf_integer"
2804   [(set (match_operand:XF 0 "nonimmediate_operand" "=f#r,m,f#r,r#f,o")
2805         (match_operand:XF 1 "general_operand" "fm#r,f#r,G,roF#f,Fr#f"))]
2806   "!optimize_size
2807    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2808    && (reload_in_progress || reload_completed
2809        || GET_CODE (operands[1]) != CONST_DOUBLE
2810        || memory_operand (operands[0], XFmode))" 
2812   switch (which_alternative)
2813     {
2814     case 0:
2815       return output_387_reg_move (insn, operands);
2817     case 1:
2818       /* There is no non-popping store to memory for XFmode.  So if
2819          we need one, follow the store with a load.  */
2820       if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2821         return "fstp%z0\t%y0\;fld%z0\t%y0";
2822       else
2823         return "fstp%z0\t%y0";
2825     case 2:
2826       return standard_80387_constant_opcode (operands[1]);
2828     case 3: case 4:
2829       return "#";
2830     }
2831   abort();
2833   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2834    (set_attr "mode" "XF,XF,XF,SI,SI")])
2836 (define_split
2837   [(set (match_operand 0 "nonimmediate_operand" "")
2838         (match_operand 1 "general_operand" ""))]
2839   "reload_completed
2840    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2841    && GET_MODE (operands[0]) == XFmode
2842    && ! (ANY_FP_REG_P (operands[0]) || 
2843          (GET_CODE (operands[0]) == SUBREG
2844           && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2845    && ! (ANY_FP_REG_P (operands[1]) || 
2846          (GET_CODE (operands[1]) == SUBREG
2847           && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2848   [(const_int 0)]
2849   "ix86_split_long_move (operands); DONE;")
2851 (define_split
2852   [(set (match_operand 0 "register_operand" "")
2853         (match_operand 1 "memory_operand" ""))]
2854   "reload_completed
2855    && GET_CODE (operands[1]) == MEM
2856    && (GET_MODE (operands[0]) == XFmode
2857        || GET_MODE (operands[0]) == SFmode || GET_MODE (operands[0]) == DFmode)
2858    && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
2859    && CONSTANT_POOL_ADDRESS_P (XEXP (operands[1], 0))"
2860   [(set (match_dup 0) (match_dup 1))]
2862   rtx c = get_pool_constant (XEXP (operands[1], 0));
2863   rtx r = operands[0];
2865   if (GET_CODE (r) == SUBREG)
2866     r = SUBREG_REG (r);
2868   if (SSE_REG_P (r))
2869     {
2870       if (!standard_sse_constant_p (c))
2871         FAIL;
2872     }
2873   else if (FP_REG_P (r))
2874     {
2875       if (!standard_80387_constant_p (c))
2876         FAIL;
2877     }
2878   else if (MMX_REG_P (r))
2879     FAIL;
2881   operands[1] = c;
2884 (define_insn "swapxf"
2885   [(set (match_operand:XF 0 "register_operand" "+f")
2886         (match_operand:XF 1 "register_operand" "+f"))
2887    (set (match_dup 1)
2888         (match_dup 0))]
2889   "TARGET_80387"
2891   if (STACK_TOP_P (operands[0]))
2892     return "fxch\t%1";
2893   else
2894     return "fxch\t%0";
2896   [(set_attr "type" "fxch")
2897    (set_attr "mode" "XF")])
2899 (define_expand "movtf"
2900   [(set (match_operand:TF 0 "nonimmediate_operand" "")
2901         (match_operand:TF 1 "nonimmediate_operand" ""))]
2902   "TARGET_64BIT"
2904   ix86_expand_move (TFmode, operands);
2905   DONE;
2908 (define_insn "*movtf_internal"
2909   [(set (match_operand:TF 0 "nonimmediate_operand" "=r,o,x,x,xm")
2910         (match_operand:TF 1 "general_operand" "riFo,riF,C,xm,x"))]
2911   "TARGET_64BIT
2912    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2914   switch (which_alternative)
2915     {
2916     case 0:
2917     case 1:
2918       return "#";
2919     case 2:
2920       if (get_attr_mode (insn) == MODE_V4SF)
2921         return "xorps\t%0, %0";
2922       else
2923         return "pxor\t%0, %0";
2924     case 3:
2925     case 4:
2926       if (get_attr_mode (insn) == MODE_V4SF)
2927         return "movaps\t{%1, %0|%0, %1}";
2928       else
2929         return "movdqa\t{%1, %0|%0, %1}";
2930     default:
2931       abort ();
2932     }
2934   [(set_attr "type" "*,*,ssemov,ssemov,ssemov")
2935    (set (attr "mode")
2936         (cond [(eq_attr "alternative" "2,3")
2937                  (if_then_else
2938                    (ne (symbol_ref "optimize_size")
2939                        (const_int 0))
2940                    (const_string "V4SF")
2941                    (const_string "TI"))
2942                (eq_attr "alternative" "4")
2943                  (if_then_else
2944                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2945                             (const_int 0))
2946                         (ne (symbol_ref "optimize_size")
2947                             (const_int 0)))
2948                    (const_string "V4SF")
2949                    (const_string "TI"))]
2950                (const_string "DI")))])
2952 (define_split
2953   [(set (match_operand:TF 0 "nonimmediate_operand" "")
2954         (match_operand:TF 1 "general_operand" ""))]
2955   "reload_completed && !SSE_REG_P (operands[0])
2956    && !SSE_REG_P (operands[1])"
2957   [(const_int 0)]
2958   "ix86_split_long_move (operands); DONE;")
2960 ;; Zero extension instructions
2962 (define_expand "zero_extendhisi2"
2963   [(set (match_operand:SI 0 "register_operand" "")
2964      (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
2965   ""
2967   if (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
2968     {
2969       operands[1] = force_reg (HImode, operands[1]);
2970       emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
2971       DONE;
2972     }
2975 (define_insn "zero_extendhisi2_and"
2976   [(set (match_operand:SI 0 "register_operand" "=r")
2977      (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
2978    (clobber (reg:CC FLAGS_REG))]
2979   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
2980   "#"
2981   [(set_attr "type" "alu1")
2982    (set_attr "mode" "SI")])
2984 (define_split
2985   [(set (match_operand:SI 0 "register_operand" "")
2986         (zero_extend:SI (match_operand:HI 1 "register_operand" "")))
2987    (clobber (reg:CC FLAGS_REG))]
2988   "reload_completed && TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
2989   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
2990               (clobber (reg:CC FLAGS_REG))])]
2991   "")
2993 (define_insn "*zero_extendhisi2_movzwl"
2994   [(set (match_operand:SI 0 "register_operand" "=r")
2995      (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
2996   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
2997   "movz{wl|x}\t{%1, %0|%0, %1}"
2998   [(set_attr "type" "imovx")
2999    (set_attr "mode" "SI")])
3001 (define_expand "zero_extendqihi2"
3002   [(parallel
3003     [(set (match_operand:HI 0 "register_operand" "")
3004        (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3005      (clobber (reg:CC FLAGS_REG))])]
3006   ""
3007   "")
3009 (define_insn "*zero_extendqihi2_and"
3010   [(set (match_operand:HI 0 "register_operand" "=r,?&q")
3011      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3012    (clobber (reg:CC FLAGS_REG))]
3013   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3014   "#"
3015   [(set_attr "type" "alu1")
3016    (set_attr "mode" "HI")])
3018 (define_insn "*zero_extendqihi2_movzbw_and"
3019   [(set (match_operand:HI 0 "register_operand" "=r,r")
3020      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3021    (clobber (reg:CC FLAGS_REG))]
3022   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3023   "#"
3024   [(set_attr "type" "imovx,alu1")
3025    (set_attr "mode" "HI")])
3027 (define_insn "*zero_extendqihi2_movzbw"
3028   [(set (match_operand:HI 0 "register_operand" "=r")
3029      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3030   "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3031   "movz{bw|x}\t{%1, %0|%0, %1}"
3032   [(set_attr "type" "imovx")
3033    (set_attr "mode" "HI")])
3035 ;; For the movzbw case strip only the clobber
3036 (define_split
3037   [(set (match_operand:HI 0 "register_operand" "")
3038         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3039    (clobber (reg:CC FLAGS_REG))]
3040   "reload_completed 
3041    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3042    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3043   [(set (match_operand:HI 0 "register_operand" "")
3044         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))])
3046 ;; When source and destination does not overlap, clear destination
3047 ;; first and then do the movb
3048 (define_split
3049   [(set (match_operand:HI 0 "register_operand" "")
3050         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3051    (clobber (reg:CC FLAGS_REG))]
3052   "reload_completed
3053    && ANY_QI_REG_P (operands[0])
3054    && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3055    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3056   [(set (match_dup 0) (const_int 0))
3057    (set (strict_low_part (match_dup 2)) (match_dup 1))]
3058   "operands[2] = gen_lowpart (QImode, operands[0]);")
3060 ;; Rest is handled by single and.
3061 (define_split
3062   [(set (match_operand:HI 0 "register_operand" "")
3063         (zero_extend:HI (match_operand:QI 1 "register_operand" "")))
3064    (clobber (reg:CC FLAGS_REG))]
3065   "reload_completed
3066    && true_regnum (operands[0]) == true_regnum (operands[1])"
3067   [(parallel [(set (match_dup 0) (and:HI (match_dup 0) (const_int 255)))
3068               (clobber (reg:CC FLAGS_REG))])]
3069   "")
3071 (define_expand "zero_extendqisi2"
3072   [(parallel
3073     [(set (match_operand:SI 0 "register_operand" "")
3074        (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3075      (clobber (reg:CC FLAGS_REG))])]
3076   ""
3077   "")
3079 (define_insn "*zero_extendqisi2_and"
3080   [(set (match_operand:SI 0 "register_operand" "=r,?&q")
3081      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3082    (clobber (reg:CC FLAGS_REG))]
3083   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3084   "#"
3085   [(set_attr "type" "alu1")
3086    (set_attr "mode" "SI")])
3088 (define_insn "*zero_extendqisi2_movzbw_and"
3089   [(set (match_operand:SI 0 "register_operand" "=r,r")
3090      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3091    (clobber (reg:CC FLAGS_REG))]
3092   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3093   "#"
3094   [(set_attr "type" "imovx,alu1")
3095    (set_attr "mode" "SI")])
3097 (define_insn "*zero_extendqisi2_movzbw"
3098   [(set (match_operand:SI 0 "register_operand" "=r")
3099      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3100   "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3101   "movz{bl|x}\t{%1, %0|%0, %1}"
3102   [(set_attr "type" "imovx")
3103    (set_attr "mode" "SI")])
3105 ;; For the movzbl case strip only the clobber
3106 (define_split
3107   [(set (match_operand:SI 0 "register_operand" "")
3108         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3109    (clobber (reg:CC FLAGS_REG))]
3110   "reload_completed 
3111    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3112    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3113   [(set (match_dup 0)
3114         (zero_extend:SI (match_dup 1)))])
3116 ;; When source and destination does not overlap, clear destination
3117 ;; first and then do the movb
3118 (define_split
3119   [(set (match_operand:SI 0 "register_operand" "")
3120         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3121    (clobber (reg:CC FLAGS_REG))]
3122   "reload_completed
3123    && ANY_QI_REG_P (operands[0])
3124    && (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM)
3125    && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3126    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3127   [(set (match_dup 0) (const_int 0))
3128    (set (strict_low_part (match_dup 2)) (match_dup 1))]
3129   "operands[2] = gen_lowpart (QImode, operands[0]);")
3131 ;; Rest is handled by single and.
3132 (define_split
3133   [(set (match_operand:SI 0 "register_operand" "")
3134         (zero_extend:SI (match_operand:QI 1 "register_operand" "")))
3135    (clobber (reg:CC FLAGS_REG))]
3136   "reload_completed
3137    && true_regnum (operands[0]) == true_regnum (operands[1])"
3138   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 255)))
3139               (clobber (reg:CC FLAGS_REG))])]
3140   "")
3142 ;; %%% Kill me once multi-word ops are sane.
3143 (define_expand "zero_extendsidi2"
3144   [(set (match_operand:DI 0 "register_operand" "=r")
3145      (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm")))]
3146   ""
3147   "if (!TARGET_64BIT)
3148      {
3149        emit_insn (gen_zero_extendsidi2_32 (operands[0], operands[1]));
3150        DONE;
3151      }
3152   ")
3154 (define_insn "zero_extendsidi2_32"
3155   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?*o,?*y,?*Y")
3156         (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "0,rm,r,rm,rm")))
3157    (clobber (reg:CC FLAGS_REG))]
3158   "!TARGET_64BIT"
3159   "@
3160    #
3161    #
3162    #
3163    movd\t{%1, %0|%0, %1}
3164    movd\t{%1, %0|%0, %1}"
3165   [(set_attr "mode" "SI,SI,SI,DI,TI")
3166    (set_attr "type" "multi,multi,multi,mmxmov,ssemov")])
3168 (define_insn "zero_extendsidi2_rex64"
3169   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,?*y,?*Y")
3170      (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm,0,rm,rm")))]
3171   "TARGET_64BIT"
3172   "@
3173    mov\t{%k1, %k0|%k0, %k1}
3174    #
3175    movd\t{%1, %0|%0, %1}
3176    movd\t{%1, %0|%0, %1}"
3177   [(set_attr "type" "imovx,imov,mmxmov,ssemov")
3178    (set_attr "mode" "SI,DI,SI,SI")])
3180 (define_split
3181   [(set (match_operand:DI 0 "memory_operand" "")
3182      (zero_extend:DI (match_dup 0)))]
3183   "TARGET_64BIT"
3184   [(set (match_dup 4) (const_int 0))]
3185   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3187 (define_split 
3188   [(set (match_operand:DI 0 "register_operand" "")
3189         (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3190    (clobber (reg:CC FLAGS_REG))]
3191   "!TARGET_64BIT && reload_completed
3192    && true_regnum (operands[0]) == true_regnum (operands[1])"
3193   [(set (match_dup 4) (const_int 0))]
3194   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3196 (define_split 
3197   [(set (match_operand:DI 0 "nonimmediate_operand" "")
3198         (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3199    (clobber (reg:CC FLAGS_REG))]
3200   "!TARGET_64BIT && reload_completed
3201    && !SSE_REG_P (operands[0]) && !MMX_REG_P (operands[0])"
3202   [(set (match_dup 3) (match_dup 1))
3203    (set (match_dup 4) (const_int 0))]
3204   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3206 (define_insn "zero_extendhidi2"
3207   [(set (match_operand:DI 0 "register_operand" "=r,r")
3208      (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "r,m")))]
3209   "TARGET_64BIT"
3210   "@
3211    movz{wl|x}\t{%1, %k0|%k0, %1}
3212    movz{wq|x}\t{%1, %0|%0, %1}"
3213   [(set_attr "type" "imovx")
3214    (set_attr "mode" "SI,DI")])
3216 (define_insn "zero_extendqidi2"
3217   [(set (match_operand:DI 0 "register_operand" "=r,r")
3218      (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "Q,m")))]
3219   "TARGET_64BIT"
3220   "@
3221    movz{bl|x}\t{%1, %k0|%k0, %1}
3222    movz{bq|x}\t{%1, %0|%0, %1}"
3223   [(set_attr "type" "imovx")
3224    (set_attr "mode" "SI,DI")])
3226 ;; Sign extension instructions
3228 (define_expand "extendsidi2"
3229   [(parallel [(set (match_operand:DI 0 "register_operand" "")
3230                    (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3231               (clobber (reg:CC FLAGS_REG))
3232               (clobber (match_scratch:SI 2 ""))])]
3233   ""
3235   if (TARGET_64BIT)
3236     {
3237       emit_insn (gen_extendsidi2_rex64 (operands[0], operands[1]));
3238       DONE;
3239     }
3242 (define_insn "*extendsidi2_1"
3243   [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3244         (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3245    (clobber (reg:CC FLAGS_REG))
3246    (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3247   "!TARGET_64BIT"
3248   "#")
3250 (define_insn "extendsidi2_rex64"
3251   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3252         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3253   "TARGET_64BIT"
3254   "@
3255    {cltq|cdqe}
3256    movs{lq|x}\t{%1,%0|%0, %1}"
3257   [(set_attr "type" "imovx")
3258    (set_attr "mode" "DI")
3259    (set_attr "prefix_0f" "0")
3260    (set_attr "modrm" "0,1")])
3262 (define_insn "extendhidi2"
3263   [(set (match_operand:DI 0 "register_operand" "=r")
3264         (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3265   "TARGET_64BIT"
3266   "movs{wq|x}\t{%1,%0|%0, %1}"
3267   [(set_attr "type" "imovx")
3268    (set_attr "mode" "DI")])
3270 (define_insn "extendqidi2"
3271   [(set (match_operand:DI 0 "register_operand" "=r")
3272         (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3273   "TARGET_64BIT"
3274   "movs{bq|x}\t{%1,%0|%0, %1}"
3275    [(set_attr "type" "imovx")
3276     (set_attr "mode" "DI")])
3278 ;; Extend to memory case when source register does die.
3279 (define_split 
3280   [(set (match_operand:DI 0 "memory_operand" "")
3281         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3282    (clobber (reg:CC FLAGS_REG))
3283    (clobber (match_operand:SI 2 "register_operand" ""))]
3284   "(reload_completed
3285     && dead_or_set_p (insn, operands[1])
3286     && !reg_mentioned_p (operands[1], operands[0]))"
3287   [(set (match_dup 3) (match_dup 1))
3288    (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3289               (clobber (reg:CC FLAGS_REG))])
3290    (set (match_dup 4) (match_dup 1))]
3291   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3293 ;; Extend to memory case when source register does not die.
3294 (define_split 
3295   [(set (match_operand:DI 0 "memory_operand" "")
3296         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3297    (clobber (reg:CC FLAGS_REG))
3298    (clobber (match_operand:SI 2 "register_operand" ""))]
3299   "reload_completed"
3300   [(const_int 0)]
3302   split_di (&operands[0], 1, &operands[3], &operands[4]);
3304   emit_move_insn (operands[3], operands[1]);
3306   /* Generate a cltd if possible and doing so it profitable.  */
3307   if (true_regnum (operands[1]) == 0
3308       && true_regnum (operands[2]) == 1
3309       && (optimize_size || TARGET_USE_CLTD))
3310     {
3311       emit_insn (gen_ashrsi3_31 (operands[2], operands[1], GEN_INT (31)));
3312     }
3313   else
3314     {
3315       emit_move_insn (operands[2], operands[1]);
3316       emit_insn (gen_ashrsi3_31 (operands[2], operands[2], GEN_INT (31)));
3317     }
3318   emit_move_insn (operands[4], operands[2]);
3319   DONE;
3322 ;; Extend to register case.  Optimize case where source and destination
3323 ;; registers match and cases where we can use cltd.
3324 (define_split 
3325   [(set (match_operand:DI 0 "register_operand" "")
3326         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3327    (clobber (reg:CC FLAGS_REG))
3328    (clobber (match_scratch:SI 2 ""))]
3329   "reload_completed"
3330   [(const_int 0)]
3332   split_di (&operands[0], 1, &operands[3], &operands[4]);
3334   if (true_regnum (operands[3]) != true_regnum (operands[1]))
3335     emit_move_insn (operands[3], operands[1]);
3337   /* Generate a cltd if possible and doing so it profitable.  */
3338   if (true_regnum (operands[3]) == 0
3339       && (optimize_size || TARGET_USE_CLTD))
3340     {
3341       emit_insn (gen_ashrsi3_31 (operands[4], operands[3], GEN_INT (31)));
3342       DONE;
3343     }
3345   if (true_regnum (operands[4]) != true_regnum (operands[1]))
3346     emit_move_insn (operands[4], operands[1]);
3348   emit_insn (gen_ashrsi3_31 (operands[4], operands[4], GEN_INT (31)));
3349   DONE;
3352 (define_insn "extendhisi2"
3353   [(set (match_operand:SI 0 "register_operand" "=*a,r")
3354         (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3355   ""
3357   switch (get_attr_prefix_0f (insn))
3358     {
3359     case 0:
3360       return "{cwtl|cwde}";
3361     default:
3362       return "movs{wl|x}\t{%1,%0|%0, %1}";
3363     }
3365   [(set_attr "type" "imovx")
3366    (set_attr "mode" "SI")
3367    (set (attr "prefix_0f")
3368      ;; movsx is short decodable while cwtl is vector decoded.
3369      (if_then_else (and (eq_attr "cpu" "!k6")
3370                         (eq_attr "alternative" "0"))
3371         (const_string "0")
3372         (const_string "1")))
3373    (set (attr "modrm")
3374      (if_then_else (eq_attr "prefix_0f" "0")
3375         (const_string "0")
3376         (const_string "1")))])
3378 (define_insn "*extendhisi2_zext"
3379   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3380         (zero_extend:DI
3381           (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3382   "TARGET_64BIT"
3384   switch (get_attr_prefix_0f (insn))
3385     {
3386     case 0:
3387       return "{cwtl|cwde}";
3388     default:
3389       return "movs{wl|x}\t{%1,%k0|%k0, %1}";
3390     }
3392   [(set_attr "type" "imovx")
3393    (set_attr "mode" "SI")
3394    (set (attr "prefix_0f")
3395      ;; movsx is short decodable while cwtl is vector decoded.
3396      (if_then_else (and (eq_attr "cpu" "!k6")
3397                         (eq_attr "alternative" "0"))
3398         (const_string "0")
3399         (const_string "1")))
3400    (set (attr "modrm")
3401      (if_then_else (eq_attr "prefix_0f" "0")
3402         (const_string "0")
3403         (const_string "1")))])
3405 (define_insn "extendqihi2"
3406   [(set (match_operand:HI 0 "register_operand" "=*a,r")
3407         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3408   ""
3410   switch (get_attr_prefix_0f (insn))
3411     {
3412     case 0:
3413       return "{cbtw|cbw}";
3414     default:
3415       return "movs{bw|x}\t{%1,%0|%0, %1}";
3416     }
3418   [(set_attr "type" "imovx")
3419    (set_attr "mode" "HI")
3420    (set (attr "prefix_0f")
3421      ;; movsx is short decodable while cwtl is vector decoded.
3422      (if_then_else (and (eq_attr "cpu" "!k6")
3423                         (eq_attr "alternative" "0"))
3424         (const_string "0")
3425         (const_string "1")))
3426    (set (attr "modrm")
3427      (if_then_else (eq_attr "prefix_0f" "0")
3428         (const_string "0")
3429         (const_string "1")))])
3431 (define_insn "extendqisi2"
3432   [(set (match_operand:SI 0 "register_operand" "=r")
3433         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3434   ""
3435   "movs{bl|x}\t{%1,%0|%0, %1}"
3436    [(set_attr "type" "imovx")
3437     (set_attr "mode" "SI")])
3439 (define_insn "*extendqisi2_zext"
3440   [(set (match_operand:DI 0 "register_operand" "=r")
3441         (zero_extend:DI
3442           (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3443   "TARGET_64BIT"
3444   "movs{bl|x}\t{%1,%k0|%k0, %1}"
3445    [(set_attr "type" "imovx")
3446     (set_attr "mode" "SI")])
3448 ;; Conversions between float and double.
3450 ;; These are all no-ops in the model used for the 80387.  So just
3451 ;; emit moves.
3453 ;; %%% Kill these when call knows how to work out a DFmode push earlier. 
3454 (define_insn "*dummy_extendsfdf2"
3455   [(set (match_operand:DF 0 "push_operand" "=<")
3456         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fY")))]
3457   "0"
3458   "#")
3460 (define_split
3461   [(set (match_operand:DF 0 "push_operand" "")
3462         (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3463   "!TARGET_64BIT"
3464   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
3465    (set (mem:DF (reg:SI SP_REG)) (float_extend:DF (match_dup 1)))])
3467 (define_split
3468   [(set (match_operand:DF 0 "push_operand" "")
3469         (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3470   "TARGET_64BIT"
3471   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
3472    (set (mem:DF (reg:DI SP_REG)) (float_extend:DF (match_dup 1)))])
3474 (define_insn "*dummy_extendsfxf2"
3475   [(set (match_operand:XF 0 "push_operand" "=<")
3476         (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "f")))]
3477   "0"
3478   "#")
3480 (define_split
3481   [(set (match_operand:XF 0 "push_operand" "")
3482         (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3483   ""
3484   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3485    (set (mem:XF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))]
3486   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3488 (define_split
3489   [(set (match_operand:XF 0 "push_operand" "")
3490         (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3491   "TARGET_64BIT"
3492   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3493    (set (mem:DF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))]
3494   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3496 (define_split
3497   [(set (match_operand:XF 0 "push_operand" "")
3498         (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3499   ""
3500   [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3501    (set (mem:DF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))]
3502   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3504 (define_split
3505   [(set (match_operand:XF 0 "push_operand" "")
3506         (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3507   "TARGET_64BIT"
3508   [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3509    (set (mem:XF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))]
3510   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3512 (define_expand "extendsfdf2"
3513   [(set (match_operand:DF 0 "nonimmediate_operand" "")
3514         (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
3515   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3517   /* ??? Needed for compress_float_constant since all fp constants
3518      are LEGITIMATE_CONSTANT_P.  */
3519   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3520     operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3521   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3522     operands[1] = force_reg (SFmode, operands[1]);
3525 (define_insn "*extendsfdf2_mixed"
3526   [(set (match_operand:DF 0 "nonimmediate_operand" "=f#Y,m#fY,Y#f")
3527         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm#Y,f#Y,mY#f")))]
3528   "TARGET_SSE2 && TARGET_MIX_SSE_I387
3529    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3531   switch (which_alternative)
3532     {
3533     case 0:
3534       return output_387_reg_move (insn, operands);
3536     case 1:
3537       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3538         return "fstp%z0\t%y0";
3539       else
3540         return "fst%z0\t%y0";
3542     case 2:
3543       return "cvtss2sd\t{%1, %0|%0, %1}";
3545     default:
3546       abort ();
3547     }
3549   [(set_attr "type" "fmov,fmov,ssecvt")
3550    (set_attr "mode" "SF,XF,DF")])
3552 (define_insn "*extendsfdf2_sse"
3553   [(set (match_operand:DF 0 "nonimmediate_operand" "=Y")
3554         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "mY")))]
3555   "TARGET_SSE2 && TARGET_SSE_MATH
3556    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3557   "cvtss2sd\t{%1, %0|%0, %1}"
3558   [(set_attr "type" "ssecvt")
3559    (set_attr "mode" "DF")])
3561 (define_insn "*extendsfdf2_i387"
3562   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
3563         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3564   "TARGET_80387
3565    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3567   switch (which_alternative)
3568     {
3569     case 0:
3570       return output_387_reg_move (insn, operands);
3572     case 1:
3573       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3574         return "fstp%z0\t%y0";
3575       else
3576         return "fst%z0\t%y0";
3578     default:
3579       abort ();
3580     }
3582   [(set_attr "type" "fmov")
3583    (set_attr "mode" "SF,XF")])
3585 (define_expand "extendsfxf2"
3586   [(set (match_operand:XF 0 "nonimmediate_operand" "")
3587         (float_extend:XF (match_operand:SF 1 "general_operand" "")))]
3588   "TARGET_80387"
3590   /* ??? Needed for compress_float_constant since all fp constants
3591      are LEGITIMATE_CONSTANT_P.  */
3592   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3593     operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3594   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3595     operands[1] = force_reg (SFmode, operands[1]);
3598 (define_insn "*extendsfxf2_i387"
3599   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3600         (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3601   "TARGET_80387
3602    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3604   switch (which_alternative)
3605     {
3606     case 0:
3607       return output_387_reg_move (insn, operands);
3609     case 1:
3610       /* There is no non-popping store to memory for XFmode.  So if
3611          we need one, follow the store with a load.  */
3612       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3613         return "fstp%z0\t%y0";
3614       else
3615         return "fstp%z0\t%y0\n\tfld%z0\t%y0";
3617     default:
3618       abort ();
3619     }
3621   [(set_attr "type" "fmov")
3622    (set_attr "mode" "SF,XF")])
3624 (define_expand "extenddfxf2"
3625   [(set (match_operand:XF 0 "nonimmediate_operand" "")
3626         (float_extend:XF (match_operand:DF 1 "general_operand" "")))]
3627   "TARGET_80387"
3629   /* ??? Needed for compress_float_constant since all fp constants
3630      are LEGITIMATE_CONSTANT_P.  */
3631   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3632     operands[1] = validize_mem (force_const_mem (DFmode, operands[1]));
3633   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3634     operands[1] = force_reg (DFmode, operands[1]);
3637 (define_insn "*extenddfxf2_i387"
3638   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3639         (float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "fm,f")))]
3640   "TARGET_80387
3641    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3643   switch (which_alternative)
3644     {
3645     case 0:
3646       return output_387_reg_move (insn, operands);
3648     case 1:
3649       /* There is no non-popping store to memory for XFmode.  So if
3650          we need one, follow the store with a load.  */
3651       if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3652         return "fstp%z0\t%y0\n\tfld%z0\t%y0";
3653       else
3654         return "fstp%z0\t%y0";
3656     default:
3657       abort ();
3658     }
3660   [(set_attr "type" "fmov")
3661    (set_attr "mode" "DF,XF")])
3663 ;; %%% This seems bad bad news.
3664 ;; This cannot output into an f-reg because there is no way to be sure
3665 ;; of truncating in that case.  Otherwise this is just like a simple move
3666 ;; insn.  So we pretend we can output to a reg in order to get better
3667 ;; register preferencing, but we really use a stack slot.
3669 ;; Conversion from DFmode to SFmode.
3671 (define_expand "truncdfsf2"
3672   [(set (match_operand:SF 0 "nonimmediate_operand" "")
3673         (float_truncate:SF
3674           (match_operand:DF 1 "nonimmediate_operand" "")))]
3675   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3677   if (MEM_P (operands[0]) && MEM_P (operands[1]))
3678     operands[1] = force_reg (DFmode, operands[1]);
3680   if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387)
3681     ;
3682   else if (flag_unsafe_math_optimizations)
3683     ;
3684   else
3685     {
3686       rtx temp = assign_386_stack_local (SFmode, 0);
3687       emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp));
3688       DONE;
3689     }
3692 (define_expand "truncdfsf2_with_temp"
3693   [(parallel [(set (match_operand:SF 0 "" "")
3694                    (float_truncate:SF (match_operand:DF 1 "" "")))
3695               (clobber (match_operand:SF 2 "" ""))])]
3696   "")
3698 (define_insn "*truncdfsf_fast_mixed"
3699   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,f,Y")
3700         (float_truncate:SF
3701           (match_operand:DF 1 "nonimmediate_operand" "f ,f,Ym")))]
3702   "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations"
3704   switch (which_alternative)
3705     {
3706     case 0:
3707       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3708         return "fstp%z0\t%y0";
3709       else
3710         return "fst%z0\t%y0";
3711     case 1:
3712       return output_387_reg_move (insn, operands);
3713     case 2:
3714       return "cvtsd2ss\t{%1, %0|%0, %1}";
3715     default:
3716       abort ();
3717     }
3719   [(set_attr "type" "fmov,fmov,ssecvt")
3720    (set_attr "mode" "SF")])
3722 ;; Yes, this one doesn't depend on flag_unsafe_math_optimizations,
3723 ;; because nothing we do here is unsafe.
3724 (define_insn "*truncdfsf_fast_sse"
3725   [(set (match_operand:SF 0 "nonimmediate_operand"   "=Y")
3726         (float_truncate:SF
3727           (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
3728   "TARGET_SSE2 && TARGET_SSE_MATH"
3729   "cvtsd2ss\t{%1, %0|%0, %1}"
3730   [(set_attr "type" "ssecvt")
3731    (set_attr "mode" "SF")])
3733 (define_insn "*truncdfsf_fast_i387"
3734   [(set (match_operand:SF 0 "nonimmediate_operand"   "=fm")
3735         (float_truncate:SF
3736           (match_operand:DF 1 "nonimmediate_operand" "f")))]
3737   "TARGET_80387 && flag_unsafe_math_optimizations"
3738   "* return output_387_reg_move (insn, operands);"
3739   [(set_attr "type" "fmov")
3740    (set_attr "mode" "SF")])
3742 (define_insn "*truncdfsf_mixed"
3743   [(set (match_operand:SF 0 "nonimmediate_operand"   "=m,?fx*r,Y")
3744         (float_truncate:SF
3745           (match_operand:DF 1 "nonimmediate_operand" "f ,f    ,Ym")))
3746    (clobber (match_operand:SF 2 "memory_operand"     "=X,m    ,X"))]
3747   "TARGET_MIX_SSE_I387"
3749   switch (which_alternative)
3750     {
3751     case 0:
3752       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3753         return "fstp%z0\t%y0";
3754       else
3755         return "fst%z0\t%y0";
3756     case 1:
3757       return "#";
3758     case 2:
3759       return "cvtsd2ss\t{%1, %0|%0, %1}";
3760     default:
3761       abort ();
3762     }
3764   [(set_attr "type" "fmov,multi,ssecvt")
3765    (set_attr "mode" "SF")])
3767 (define_insn "*truncdfsf_i387"
3768   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r")
3769         (float_truncate:SF
3770           (match_operand:DF 1 "nonimmediate_operand" "f,f")))
3771    (clobber (match_operand:SF 2 "memory_operand" "=X,m"))]
3772   "TARGET_80387"
3774   switch (which_alternative)
3775     {
3776     case 0:
3777       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3778         return "fstp%z0\t%y0";
3779       else
3780         return "fst%z0\t%y0";
3781     case 1:
3782       return "#";
3783     default:
3784       abort ();
3785     }
3787   [(set_attr "type" "fmov,multi")
3788    (set_attr "mode" "SF")])
3790 (define_insn "*truncdfsf2_i387_1"
3791   [(set (match_operand:SF 0 "memory_operand" "=m")
3792         (float_truncate:SF
3793           (match_operand:DF 1 "register_operand" "f")))]
3794   "TARGET_80387
3795    && !(TARGET_SSE2 && TARGET_SSE_MATH)
3796    && !TARGET_MIX_SSE_I387"
3798   if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3799     return "fstp%z0\t%y0";
3800   else
3801     return "fst%z0\t%y0";
3803   [(set_attr "type" "fmov")
3804    (set_attr "mode" "SF")])
3806 (define_split
3807   [(set (match_operand:SF 0 "register_operand" "")
3808         (float_truncate:SF
3809          (match_operand:DF 1 "fp_register_operand" "")))
3810    (clobber (match_operand 2 "" ""))]
3811   "reload_completed"
3812   [(set (match_dup 2) (match_dup 1))
3813    (set (match_dup 0) (match_dup 2))]
3815   operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1]));
3818 ;; Conversion from XFmode to SFmode.
3820 (define_expand "truncxfsf2"
3821   [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
3822                    (float_truncate:SF
3823                     (match_operand:XF 1 "register_operand" "")))
3824               (clobber (match_dup 2))])]
3825   "TARGET_80387"
3827   if (flag_unsafe_math_optimizations)
3828     {
3829       rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SFmode);
3830       emit_insn (gen_truncxfsf2_i387_noop (reg, operands[1]));
3831       if (reg != operands[0])
3832         emit_move_insn (operands[0], reg);
3833       DONE;
3834     }
3835   else
3836     operands[2] = assign_386_stack_local (SFmode, 0);
3839 (define_insn "*truncxfsf2_mixed"
3840   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f#rx,?r#fx,?x#rf")
3841         (float_truncate:SF
3842          (match_operand:XF 1 "register_operand" "f,f,f,f")))
3843    (clobber (match_operand:SF 2 "memory_operand" "=X,m,m,m"))]
3844   "TARGET_MIX_SSE_I387"
3846   switch (which_alternative)
3847     {
3848     case 0:
3849       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3850         return "fstp%z0\t%y0";
3851       else
3852         return "fst%z0\t%y0";
3853     default:
3854       abort();
3855     }
3857   [(set_attr "type" "fmov,multi,multi,multi")
3858    (set_attr "mode" "SF")])
3860 (define_insn "truncxfsf2_i387_noop"
3861   [(set (match_operand:SF 0 "register_operand" "=f")
3862         (float_truncate:SF (match_operand:XF 1 "register_operand" "f")))]
3863   "TARGET_80387 && flag_unsafe_math_optimizations"
3865   return output_387_reg_move (insn, operands);
3867   [(set_attr "type" "fmov")
3868    (set_attr "mode" "SF")])
3870 (define_insn "*truncxfsf2_i387"
3871   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f#r,?r#f")
3872         (float_truncate:SF
3873          (match_operand:XF 1 "register_operand" "f,f,f")))
3874    (clobber (match_operand:SF 2 "memory_operand" "=X,m,m"))]
3875   "TARGET_80387"
3877   switch (which_alternative)
3878     {
3879     case 0:
3880       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3881         return "fstp%z0\t%y0";
3882       else
3883         return "fst%z0\t%y0";
3884     default:
3885       abort ();
3886     }
3888   [(set_attr "type" "fmov,multi,multi")
3889    (set_attr "mode" "SF")])
3891 (define_insn "*truncxfsf2_i387_1"
3892   [(set (match_operand:SF 0 "memory_operand" "=m")
3893         (float_truncate:SF
3894          (match_operand:XF 1 "register_operand" "f")))]
3895   "TARGET_80387"
3897   if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3898     return "fstp%z0\t%y0";
3899   else
3900     return "fst%z0\t%y0";
3902   [(set_attr "type" "fmov")
3903    (set_attr "mode" "SF")])
3905 (define_split
3906   [(set (match_operand:SF 0 "register_operand" "")
3907         (float_truncate:SF
3908          (match_operand:XF 1 "register_operand" "")))
3909    (clobber (match_operand:SF 2 "memory_operand" ""))]
3910   "TARGET_80387 && reload_completed"
3911   [(set (match_dup 2) (float_truncate:SF (match_dup 1)))
3912    (set (match_dup 0) (match_dup 2))]
3913   "")
3915 (define_split
3916   [(set (match_operand:SF 0 "memory_operand" "")
3917         (float_truncate:SF
3918          (match_operand:XF 1 "register_operand" "")))
3919    (clobber (match_operand:SF 2 "memory_operand" ""))]
3920   "TARGET_80387"
3921   [(set (match_dup 0) (float_truncate:SF (match_dup 1)))]
3922   "")
3924 ;; Conversion from XFmode to DFmode.
3926 (define_expand "truncxfdf2"
3927   [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
3928                    (float_truncate:DF
3929                     (match_operand:XF 1 "register_operand" "")))
3930               (clobber (match_dup 2))])]
3931   "TARGET_80387"
3933   if (flag_unsafe_math_optimizations)
3934     {
3935       rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DFmode);
3936       emit_insn (gen_truncxfdf2_i387_noop (reg, operands[1]));
3937       if (reg != operands[0])
3938         emit_move_insn (operands[0], reg);
3939       DONE;
3940     }
3941   else
3942     operands[2] = assign_386_stack_local (DFmode, 0);
3945 (define_insn "*truncxfdf2_mixed"
3946   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f#rY,?r#fY,?Y#rf")
3947         (float_truncate:DF
3948          (match_operand:XF 1 "register_operand" "f,f,f,f")))
3949    (clobber (match_operand:DF 2 "memory_operand" "=X,m,m,m"))]
3950   "TARGET_SSE2 && TARGET_MIX_SSE_I387"
3952   switch (which_alternative)
3953     {
3954     case 0:
3955       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3956         return "fstp%z0\t%y0";
3957       else
3958         return "fst%z0\t%y0";
3959     default:
3960       abort();
3961     }
3962   abort ();
3964   [(set_attr "type" "fmov,multi,multi,multi")
3965    (set_attr "mode" "DF")])
3967 (define_insn "truncxfdf2_i387_noop"
3968   [(set (match_operand:DF 0 "register_operand" "=f")
3969         (float_truncate:DF (match_operand:XF 1 "register_operand" "f")))]
3970   "TARGET_80387 && flag_unsafe_math_optimizations"
3972   return output_387_reg_move (insn, operands);
3974   [(set_attr "type" "fmov")
3975    (set_attr "mode" "DF")])
3977 (define_insn "*truncxfdf2_i387"
3978   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f#r,?r#f")
3979         (float_truncate:DF
3980          (match_operand:XF 1 "register_operand" "f,f,f")))
3981    (clobber (match_operand:DF 2 "memory_operand" "=X,m,m"))]
3982   "TARGET_80387"
3984   switch (which_alternative)
3985     {
3986     case 0:
3987       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3988         return "fstp%z0\t%y0";
3989       else
3990         return "fst%z0\t%y0";
3991     default:
3992       abort ();
3993     }
3995   [(set_attr "type" "fmov,multi,multi")
3996    (set_attr "mode" "DF")])
3998 (define_insn "*truncxfdf2_i387_1"
3999   [(set (match_operand:DF 0 "memory_operand" "=m")
4000         (float_truncate:DF
4001           (match_operand:XF 1 "register_operand" "f")))]
4002   "TARGET_80387"
4004   if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4005     return "fstp%z0\t%y0";
4006   else
4007     return "fst%z0\t%y0";
4009   [(set_attr "type" "fmov")
4010    (set_attr "mode" "DF")])
4012 (define_split
4013   [(set (match_operand:DF 0 "register_operand" "")
4014         (float_truncate:DF
4015          (match_operand:XF 1 "register_operand" "")))
4016    (clobber (match_operand:DF 2 "memory_operand" ""))]
4017   "TARGET_80387 && reload_completed"
4018   [(set (match_dup 2) (float_truncate:DF (match_dup 1)))
4019    (set (match_dup 0) (match_dup 2))]
4020   "")
4022 (define_split
4023   [(set (match_operand:DF 0 "memory_operand" "")
4024         (float_truncate:DF
4025          (match_operand:XF 1 "register_operand" "")))
4026    (clobber (match_operand:DF 2 "memory_operand" ""))]
4027   "TARGET_80387"
4028   [(set (match_dup 0) (float_truncate:DF (match_dup 1)))]
4029   "")
4031 ;; Signed conversion to DImode.
4033 (define_expand "fix_truncxfdi2"
4034   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4035                    (fix:DI (match_operand:XF 1 "register_operand" "")))
4036               (clobber (reg:CC FLAGS_REG))])]
4037   "TARGET_80387"
4039   if (TARGET_FISTTP)
4040    {
4041      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4042      DONE;
4043    }
4046 (define_expand "fix_trunc<mode>di2"
4047   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4048                    (fix:DI (match_operand:SSEMODEF 1 "register_operand" "")))
4049               (clobber (reg:CC FLAGS_REG))])]
4050   "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))"
4052   if (TARGET_FISTTP
4053       && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4054    {
4055      emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4056      DONE;
4057    }
4058   if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))
4059    {
4060      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4061      emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1]));
4062      if (out != operands[0])
4063         emit_move_insn (operands[0], out);
4064      DONE;
4065    }
4068 ;; Signed conversion to SImode.
4070 (define_expand "fix_truncxfsi2"
4071   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4072                    (fix:SI (match_operand:XF 1 "register_operand" "")))
4073               (clobber (reg:CC FLAGS_REG))])]
4074   "TARGET_80387"
4076   if (TARGET_FISTTP)
4077    {
4078      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4079      DONE;
4080    }
4083 (define_expand "fix_trunc<mode>si2"
4084   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4085                    (fix:SI (match_operand:SSEMODEF 1 "register_operand" "")))
4086               (clobber (reg:CC FLAGS_REG))])]
4087   "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode))"
4089   if (TARGET_FISTTP
4090       && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4091    {
4092      emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4093      DONE;
4094    }
4095   if (SSE_FLOAT_MODE_P (<MODE>mode))
4096    {
4097      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4098      emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1]));
4099      if (out != operands[0])
4100         emit_move_insn (operands[0], out);
4101      DONE;
4102    }
4105 ;; Signed conversion to HImode.
4107 (define_expand "fix_trunc<mode>hi2"
4108   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4109                    (fix:HI (match_operand:X87MODEF 1 "register_operand" "")))
4110               (clobber (reg:CC FLAGS_REG))])]
4111   "TARGET_80387
4112    && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))"
4114   if (TARGET_FISTTP)
4115    {
4116      emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1]));
4117      DONE;
4118    }
4121 ;; When SSE is available, it is always faster to use it!
4122 (define_insn "fix_truncsfdi_sse"
4123   [(set (match_operand:DI 0 "register_operand" "=r,r")
4124         (fix:DI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))]
4125   "TARGET_64BIT && TARGET_SSE && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4126   "cvttss2si{q}\t{%1, %0|%0, %1}"
4127   [(set_attr "type" "sseicvt")
4128    (set_attr "mode" "SF")
4129    (set_attr "athlon_decode" "double,vector")])
4131 (define_insn "fix_truncdfdi_sse"
4132   [(set (match_operand:DI 0 "register_operand" "=r,r")
4133         (fix:DI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))]
4134   "TARGET_64BIT && TARGET_SSE2 && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4135   "cvttsd2si{q}\t{%1, %0|%0, %1}"
4136   [(set_attr "type" "sseicvt")
4137    (set_attr "mode" "DF")
4138    (set_attr "athlon_decode" "double,vector")])
4140 (define_insn "fix_truncsfsi_sse"
4141   [(set (match_operand:SI 0 "register_operand" "=r,r")
4142         (fix:SI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))]
4143   "TARGET_SSE && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4144   "cvttss2si\t{%1, %0|%0, %1}"
4145   [(set_attr "type" "sseicvt")
4146    (set_attr "mode" "DF")
4147    (set_attr "athlon_decode" "double,vector")])
4149 (define_insn "fix_truncdfsi_sse"
4150   [(set (match_operand:SI 0 "register_operand" "=r,r")
4151         (fix:SI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))]
4152   "TARGET_SSE2 && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4153   "cvttsd2si\t{%1, %0|%0, %1}"
4154   [(set_attr "type" "sseicvt")
4155    (set_attr "mode" "DF")
4156    (set_attr "athlon_decode" "double,vector")])
4158 ;; Avoid vector decoded forms of the instruction.
4159 (define_peephole2
4160   [(match_scratch:DF 2 "Y")
4161    (set (match_operand:SSEMODEI24 0 "register_operand" "")
4162         (fix:SSEMODEI24 (match_operand:DF 1 "memory_operand" "")))]
4163   "TARGET_K8 && !optimize_size"
4164   [(set (match_dup 2) (match_dup 1))
4165    (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4166   "")
4168 (define_peephole2
4169   [(match_scratch:SF 2 "x")
4170    (set (match_operand:SSEMODEI24 0 "register_operand" "")
4171         (fix:SSEMODEI24 (match_operand:SF 1 "memory_operand" "")))]
4172   "TARGET_K8 && !optimize_size"
4173   [(set (match_dup 2) (match_dup 1))
4174    (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4175   "")
4177 (define_insn_and_split "fix_trunc<mode>_fisttp_i387_1"
4178   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4179         (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))]
4180   "TARGET_80387 && TARGET_FISTTP
4181    && FLOAT_MODE_P (GET_MODE (operands[1]))
4182    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4183          && (TARGET_64BIT || <MODE>mode != DImode))
4184         && TARGET_SSE_MATH)
4185    && !(reload_completed || reload_in_progress)"
4186   "#"
4187   "&& 1"
4188   [(const_int 0)]
4190   if (memory_operand (operands[0], VOIDmode))
4191     emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1]));
4192   else
4193     {
4194       operands[2] = assign_386_stack_local (<MODE>mode, 0);
4195       emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0],
4196                                                             operands[1],
4197                                                             operands[2]));
4198     }
4199   DONE;
4201   [(set_attr "type" "fisttp")
4202    (set_attr "mode" "<MODE>")])
4204 (define_insn "fix_trunc<mode>_i387_fisttp"
4205   [(set (match_operand:X87MODEI 0 "memory_operand" "=m")
4206         (fix:X87MODEI (match_operand 1 "register_operand" "f")))
4207    (clobber (match_scratch:XF 2 "=&1f"))]
4208   "TARGET_80387 && TARGET_FISTTP
4209    && FLOAT_MODE_P (GET_MODE (operands[1]))
4210    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4211          && (TARGET_64BIT || <MODE>mode != DImode))
4212         && TARGET_SSE_MATH)"
4213   "* return output_fix_trunc (insn, operands, 1);"
4214   [(set_attr "type" "fisttp")
4215    (set_attr "mode" "<MODE>")])
4217 (define_insn "fix_trunc<mode>_i387_fisttp_with_temp"
4218   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4219         (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
4220    (clobber (match_operand:X87MODEI 2 "memory_operand" "=m,m"))
4221    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
4222   "TARGET_80387 && TARGET_FISTTP
4223    && FLOAT_MODE_P (GET_MODE (operands[1]))
4224    && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4225         && (TARGET_64BIT || <MODE>mode != DImode))
4226         && TARGET_SSE_MATH)"
4227   "#"
4228   [(set_attr "type" "fisttp")
4229    (set_attr "mode" "<MODE>")])
4231 (define_split
4232   [(set (match_operand:X87MODEI 0 "register_operand" "")
4233         (fix:X87MODEI (match_operand 1 "register_operand" "")))
4234    (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4235    (clobber (match_scratch 3 ""))]
4236   "reload_completed"
4237   [(parallel [(set (match_dup 2) (fix:X87MODEI (match_dup 1)))
4238               (clobber (match_dup 3))])
4239    (set (match_dup 0) (match_dup 2))]
4240   "")
4242 (define_split
4243   [(set (match_operand:X87MODEI 0 "memory_operand" "")
4244         (fix:X87MODEI (match_operand 1 "register_operand" "")))
4245    (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4246    (clobber (match_scratch 3 ""))]
4247   "reload_completed"
4248   [(parallel [(set (match_dup 0) (fix:X87MODEI (match_dup 1)))
4249               (clobber (match_dup 3))])]
4250   "")
4252 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4253 ;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control
4254 ;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG
4255 ;; clobbering insns can be used. Look at emit_i387_cw_initialization ()
4256 ;; function in i386.c.
4257 (define_insn_and_split "*fix_trunc<mode>_i387_1"
4258   [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4259         (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
4260    (clobber (reg:CC FLAGS_REG))]
4261   "TARGET_80387 && !TARGET_FISTTP
4262    && FLOAT_MODE_P (GET_MODE (operands[1]))
4263    && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4264          && (TARGET_64BIT || <MODE>mode != DImode))
4265    && !(reload_completed || reload_in_progress)"
4266   "#"
4267   "&& 1"
4268   [(const_int 0)]
4270   ix86_optimize_mode_switching = 1;
4271   operands[2] = assign_386_stack_local (HImode, 1);
4272   operands[3] = assign_386_stack_local (HImode, 2);
4273   if (memory_operand (operands[0], VOIDmode))
4274     emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1],
4275                                          operands[2], operands[3]));
4276   else
4277     {
4278       operands[4] = assign_386_stack_local (<MODE>mode, 0);
4279       emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1],
4280                                                      operands[2], operands[3],
4281                                                      operands[4]));
4282     }
4283   DONE;
4285   [(set_attr "type" "fistp")
4286    (set_attr "i387_cw" "trunc")
4287    (set_attr "mode" "<MODE>")])
4289 (define_insn "fix_truncdi_i387"
4290   [(set (match_operand:DI 0 "memory_operand" "=m")
4291         (fix:DI (match_operand 1 "register_operand" "f")))
4292    (use (match_operand:HI 2 "memory_operand" "m"))
4293    (use (match_operand:HI 3 "memory_operand" "m"))
4294    (clobber (match_scratch:XF 4 "=&1f"))]
4295   "TARGET_80387 && !TARGET_FISTTP
4296    && FLOAT_MODE_P (GET_MODE (operands[1]))
4297    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4298   "* return output_fix_trunc (insn, operands, 0);"
4299   [(set_attr "type" "fistp")
4300    (set_attr "i387_cw" "trunc")
4301    (set_attr "mode" "DI")])
4303 (define_insn "fix_truncdi_i387_with_temp"
4304   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4305         (fix:DI (match_operand 1 "register_operand" "f,f")))
4306    (use (match_operand:HI 2 "memory_operand" "m,m"))
4307    (use (match_operand:HI 3 "memory_operand" "m,m"))
4308    (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
4309    (clobber (match_scratch:XF 5 "=&1f,&1f"))]
4310   "TARGET_80387 && !TARGET_FISTTP
4311    && FLOAT_MODE_P (GET_MODE (operands[1]))
4312    && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4313   "#"
4314   [(set_attr "type" "fistp")
4315    (set_attr "i387_cw" "trunc")
4316    (set_attr "mode" "DI")])
4318 (define_split 
4319   [(set (match_operand:DI 0 "register_operand" "")
4320         (fix:DI (match_operand 1 "register_operand" "")))
4321    (use (match_operand:HI 2 "memory_operand" ""))
4322    (use (match_operand:HI 3 "memory_operand" ""))
4323    (clobber (match_operand:DI 4 "memory_operand" ""))
4324    (clobber (match_scratch 5 ""))]
4325   "reload_completed"
4326   [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
4327               (use (match_dup 2))
4328               (use (match_dup 3))
4329               (clobber (match_dup 5))])
4330    (set (match_dup 0) (match_dup 4))]
4331   "")
4333 (define_split 
4334   [(set (match_operand:DI 0 "memory_operand" "")
4335         (fix:DI (match_operand 1 "register_operand" "")))
4336    (use (match_operand:HI 2 "memory_operand" ""))
4337    (use (match_operand:HI 3 "memory_operand" ""))
4338    (clobber (match_operand:DI 4 "memory_operand" ""))
4339    (clobber (match_scratch 5 ""))]
4340   "reload_completed"
4341   [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
4342               (use (match_dup 2))
4343               (use (match_dup 3))
4344               (clobber (match_dup 5))])]
4345   "")
4347 (define_insn "fix_trunc<mode>_i387"
4348   [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
4349         (fix:X87MODEI12 (match_operand 1 "register_operand" "f")))
4350    (use (match_operand:HI 2 "memory_operand" "m"))
4351    (use (match_operand:HI 3 "memory_operand" "m"))]
4352   "TARGET_80387 && !TARGET_FISTTP
4353    && FLOAT_MODE_P (GET_MODE (operands[1]))
4354    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4355   "* return output_fix_trunc (insn, operands, 0);"
4356   [(set_attr "type" "fistp")
4357    (set_attr "i387_cw" "trunc")
4358    (set_attr "mode" "<MODE>")])
4360 (define_insn "fix_trunc<mode>_i387_with_temp"
4361   [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
4362         (fix:X87MODEI12 (match_operand 1 "register_operand" "f,f")))
4363    (use (match_operand:HI 2 "memory_operand" "m,m"))
4364    (use (match_operand:HI 3 "memory_operand" "m,m"))
4365    (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
4366   "TARGET_80387 && !TARGET_FISTTP
4367    && FLOAT_MODE_P (GET_MODE (operands[1]))
4368    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4369   "#"
4370   [(set_attr "type" "fistp")
4371    (set_attr "i387_cw" "trunc")
4372    (set_attr "mode" "<MODE>")])
4374 (define_split 
4375   [(set (match_operand:X87MODEI12 0 "register_operand" "")
4376         (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4377    (use (match_operand:HI 2 "memory_operand" ""))
4378    (use (match_operand:HI 3 "memory_operand" ""))
4379    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4380   "reload_completed"
4381   [(parallel [(set (match_dup 4) (fix:X87MODEI12 (match_dup 1)))
4382               (use (match_dup 2))
4383               (use (match_dup 3))])
4384    (set (match_dup 0) (match_dup 4))]
4385   "")
4387 (define_split 
4388   [(set (match_operand:X87MODEI12 0 "memory_operand" "")
4389         (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4390    (use (match_operand:HI 2 "memory_operand" ""))
4391    (use (match_operand:HI 3 "memory_operand" ""))
4392    (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4393   "reload_completed"
4394   [(parallel [(set (match_dup 0) (fix:X87MODEI12 (match_dup 1)))
4395               (use (match_dup 2))
4396               (use (match_dup 3))])]
4397   "")
4399 (define_insn "x86_fnstcw_1"
4400   [(set (match_operand:HI 0 "memory_operand" "=m")
4401         (unspec:HI [(reg:HI FPSR_REG)] UNSPEC_FSTCW))]
4402   "TARGET_80387"
4403   "fnstcw\t%0"
4404   [(set_attr "length" "2")
4405    (set_attr "mode" "HI")
4406    (set_attr "unit" "i387")])
4408 (define_insn "x86_fldcw_1"
4409   [(set (reg:HI FPSR_REG)
4410         (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
4411   "TARGET_80387"
4412   "fldcw\t%0"
4413   [(set_attr "length" "2")
4414    (set_attr "mode" "HI")
4415    (set_attr "unit" "i387")
4416    (set_attr "athlon_decode" "vector")])
4418 ;; Conversion between fixed point and floating point.
4420 ;; Even though we only accept memory inputs, the backend _really_
4421 ;; wants to be able to do this between registers.
4423 (define_expand "floathisf2"
4424   [(set (match_operand:SF 0 "register_operand" "")
4425         (float:SF (match_operand:HI 1 "nonimmediate_operand" "")))]
4426   "TARGET_80387 || TARGET_SSE_MATH"
4428   if (TARGET_SSE_MATH)
4429     {
4430       emit_insn (gen_floatsisf2 (operands[0],
4431                                  convert_to_mode (SImode, operands[1], 0)));
4432       DONE;
4433     }
4436 (define_insn "*floathisf2_i387"
4437   [(set (match_operand:SF 0 "register_operand" "=f,f")
4438         (float:SF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4439   "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
4440   "@
4441    fild%z1\t%1
4442    #"
4443   [(set_attr "type" "fmov,multi")
4444    (set_attr "mode" "SF")
4445    (set_attr "fp_int_src" "true")])
4447 (define_expand "floatsisf2"
4448   [(set (match_operand:SF 0 "register_operand" "")
4449         (float:SF (match_operand:SI 1 "nonimmediate_operand" "")))]
4450   "TARGET_80387 || TARGET_SSE_MATH"
4451   "")
4453 (define_insn "*floatsisf2_mixed"
4454   [(set (match_operand:SF 0 "register_operand" "=f#x,?f#x,x#f,x#f")
4455         (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))]
4456   "TARGET_MIX_SSE_I387"
4457   "@
4458    fild%z1\t%1
4459    #
4460    cvtsi2ss\t{%1, %0|%0, %1}
4461    cvtsi2ss\t{%1, %0|%0, %1}"
4462   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4463    (set_attr "mode" "SF")
4464    (set_attr "athlon_decode" "*,*,vector,double")
4465    (set_attr "fp_int_src" "true")])
4467 (define_insn "*floatsisf2_sse"
4468   [(set (match_operand:SF 0 "register_operand" "=x,x")
4469         (float:SF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))]
4470   "TARGET_SSE_MATH"
4471   "cvtsi2ss\t{%1, %0|%0, %1}"
4472   [(set_attr "type" "sseicvt")
4473    (set_attr "mode" "SF")
4474    (set_attr "athlon_decode" "vector,double")
4475    (set_attr "fp_int_src" "true")])
4477 (define_insn "*floatsisf2_i387"
4478   [(set (match_operand:SF 0 "register_operand" "=f,f")
4479         (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4480   "TARGET_80387"
4481   "@
4482    fild%z1\t%1
4483    #"
4484   [(set_attr "type" "fmov,multi")
4485    (set_attr "mode" "SF")
4486    (set_attr "fp_int_src" "true")])
4488 (define_expand "floatdisf2"
4489   [(set (match_operand:SF 0 "register_operand" "")
4490         (float:SF (match_operand:DI 1 "nonimmediate_operand" "")))]
4491   "TARGET_80387 || (TARGET_64BIT && TARGET_SSE_MATH)"
4492   "")
4494 (define_insn "*floatdisf2_mixed"
4495   [(set (match_operand:SF 0 "register_operand" "=f#x,?f#x,x#f,x#f")
4496         (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))]
4497   "TARGET_64BIT && TARGET_MIX_SSE_I387"
4498   "@
4499    fild%z1\t%1
4500    #
4501    cvtsi2ss{q}\t{%1, %0|%0, %1}
4502    cvtsi2ss{q}\t{%1, %0|%0, %1}"
4503   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4504    (set_attr "mode" "SF")
4505    (set_attr "athlon_decode" "*,*,vector,double")
4506    (set_attr "fp_int_src" "true")])
4508 (define_insn "*floatdisf2_sse"
4509   [(set (match_operand:SF 0 "register_operand" "=x,x")
4510         (float:SF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))]
4511   "TARGET_64BIT && TARGET_SSE_MATH"
4512   "cvtsi2ss{q}\t{%1, %0|%0, %1}"
4513   [(set_attr "type" "sseicvt")
4514    (set_attr "mode" "SF")
4515    (set_attr "athlon_decode" "vector,double")
4516    (set_attr "fp_int_src" "true")])
4518 (define_insn "*floatdisf2_i387"
4519   [(set (match_operand:SF 0 "register_operand" "=f,f")
4520         (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4521   "TARGET_80387"
4522   "@
4523    fild%z1\t%1
4524    #"
4525   [(set_attr "type" "fmov,multi")
4526    (set_attr "mode" "SF")
4527    (set_attr "fp_int_src" "true")])
4529 (define_expand "floathidf2"
4530   [(set (match_operand:DF 0 "register_operand" "")
4531         (float:DF (match_operand:HI 1 "nonimmediate_operand" "")))]
4532   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4534   if (TARGET_SSE2 && TARGET_SSE_MATH)
4535     {
4536       emit_insn (gen_floatsidf2 (operands[0],
4537                                  convert_to_mode (SImode, operands[1], 0)));
4538       DONE;
4539     }
4542 (define_insn "*floathidf2_i387"
4543   [(set (match_operand:DF 0 "register_operand" "=f,f")
4544         (float:DF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4545   "TARGET_80387 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)"
4546   "@
4547    fild%z1\t%1
4548    #"
4549   [(set_attr "type" "fmov,multi")
4550    (set_attr "mode" "DF")
4551    (set_attr "fp_int_src" "true")])
4553 (define_expand "floatsidf2"
4554   [(set (match_operand:DF 0 "register_operand" "")
4555         (float:DF (match_operand:SI 1 "nonimmediate_operand" "")))]
4556   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4557   "")
4559 (define_insn "*floatsidf2_mixed"
4560   [(set (match_operand:DF 0 "register_operand" "=f#Y,?f#Y,Y#f,Y#f")
4561         (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))]
4562   "TARGET_SSE2 && TARGET_MIX_SSE_I387"
4563   "@
4564    fild%z1\t%1
4565    #
4566    cvtsi2sd\t{%1, %0|%0, %1}
4567    cvtsi2sd\t{%1, %0|%0, %1}"
4568   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4569    (set_attr "mode" "DF")
4570    (set_attr "athlon_decode" "*,*,double,direct")
4571    (set_attr "fp_int_src" "true")])
4573 (define_insn "*floatsidf2_sse"
4574   [(set (match_operand:DF 0 "register_operand" "=Y,Y")
4575         (float:DF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))]
4576   "TARGET_SSE2 && TARGET_SSE_MATH"
4577   "cvtsi2sd\t{%1, %0|%0, %1}"
4578   [(set_attr "type" "sseicvt")
4579    (set_attr "mode" "DF")
4580    (set_attr "athlon_decode" "double,direct")
4581    (set_attr "fp_int_src" "true")])
4583 (define_insn "*floatsidf2_i387"
4584   [(set (match_operand:DF 0 "register_operand" "=f,f")
4585         (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4586   "TARGET_80387"
4587   "@
4588    fild%z1\t%1
4589    #"
4590   [(set_attr "type" "fmov,multi")
4591    (set_attr "mode" "DF")
4592    (set_attr "fp_int_src" "true")])
4594 (define_expand "floatdidf2"
4595   [(set (match_operand:DF 0 "register_operand" "")
4596         (float:DF (match_operand:DI 1 "nonimmediate_operand" "")))]
4597   "TARGET_80387 || (TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH)"
4598   "")
4600 (define_insn "*floatdidf2_mixed"
4601   [(set (match_operand:DF 0 "register_operand" "=f#Y,?f#Y,Y#f,Y#f")
4602         (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))]
4603   "TARGET_64BIT && TARGET_SSE2 && TARGET_MIX_SSE_I387"
4604   "@
4605    fild%z1\t%1
4606    #
4607    cvtsi2sd{q}\t{%1, %0|%0, %1}
4608    cvtsi2sd{q}\t{%1, %0|%0, %1}"
4609   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4610    (set_attr "mode" "DF")
4611    (set_attr "athlon_decode" "*,*,double,direct")
4612    (set_attr "fp_int_src" "true")])
4614 (define_insn "*floatdidf2_sse"
4615   [(set (match_operand:DF 0 "register_operand" "=Y,Y")
4616         (float:DF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))]
4617   "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4618   "cvtsi2sd{q}\t{%1, %0|%0, %1}"
4619   [(set_attr "type" "sseicvt")
4620    (set_attr "mode" "DF")
4621    (set_attr "athlon_decode" "double,direct")
4622    (set_attr "fp_int_src" "true")])
4624 (define_insn "*floatdidf2_i387"
4625   [(set (match_operand:DF 0 "register_operand" "=f,f")
4626         (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4627   "TARGET_80387"
4628   "@
4629    fild%z1\t%1
4630    #"
4631   [(set_attr "type" "fmov,multi")
4632    (set_attr "mode" "DF")
4633    (set_attr "fp_int_src" "true")])
4635 (define_insn "floathixf2"
4636   [(set (match_operand:XF 0 "register_operand" "=f,f")
4637         (float:XF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4638   "TARGET_80387"
4639   "@
4640    fild%z1\t%1
4641    #"
4642   [(set_attr "type" "fmov,multi")
4643    (set_attr "mode" "XF")
4644    (set_attr "fp_int_src" "true")])
4646 (define_insn "floatsixf2"
4647   [(set (match_operand:XF 0 "register_operand" "=f,f")
4648         (float:XF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4649   "TARGET_80387"
4650   "@
4651    fild%z1\t%1
4652    #"
4653   [(set_attr "type" "fmov,multi")
4654    (set_attr "mode" "XF")
4655    (set_attr "fp_int_src" "true")])
4657 (define_insn "floatdixf2"
4658   [(set (match_operand:XF 0 "register_operand" "=f,f")
4659         (float:XF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4660   "TARGET_80387"
4661   "@
4662    fild%z1\t%1
4663    #"
4664   [(set_attr "type" "fmov,multi")
4665    (set_attr "mode" "XF")
4666    (set_attr "fp_int_src" "true")])
4668 ;; %%% Kill these when reload knows how to do it.
4669 (define_split
4670   [(set (match_operand 0 "fp_register_operand" "")
4671         (float (match_operand 1 "register_operand" "")))]
4672   "reload_completed
4673    && TARGET_80387
4674    && FLOAT_MODE_P (GET_MODE (operands[0]))"
4675   [(const_int 0)]
4677   operands[2] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
4678   operands[2] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[2]);
4679   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[2]));
4680   ix86_free_from_memory (GET_MODE (operands[1]));
4681   DONE;
4684 (define_expand "floatunssisf2"
4685   [(use (match_operand:SF 0 "register_operand" ""))
4686    (use (match_operand:SI 1 "register_operand" ""))]
4687   "!TARGET_64BIT && TARGET_SSE_MATH"
4688   "x86_emit_floatuns (operands); DONE;")
4690 (define_expand "floatunsdisf2"
4691   [(use (match_operand:SF 0 "register_operand" ""))
4692    (use (match_operand:DI 1 "register_operand" ""))]
4693   "TARGET_64BIT && TARGET_SSE_MATH"
4694   "x86_emit_floatuns (operands); DONE;")
4696 (define_expand "floatunsdidf2"
4697   [(use (match_operand:DF 0 "register_operand" ""))
4698    (use (match_operand:DI 1 "register_operand" ""))]
4699   "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4700   "x86_emit_floatuns (operands); DONE;")
4702 ;; SSE extract/set expanders
4705 ;; Add instructions
4707 ;; %%% splits for addsidi3
4708 ;  [(set (match_operand:DI 0 "nonimmediate_operand" "")
4709 ;       (plus:DI (match_operand:DI 1 "general_operand" "")
4710 ;                (zero_extend:DI (match_operand:SI 2 "general_operand" ""))))]
4712 (define_expand "adddi3"
4713   [(set (match_operand:DI 0 "nonimmediate_operand" "")
4714         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4715                  (match_operand:DI 2 "x86_64_general_operand" "")))
4716    (clobber (reg:CC FLAGS_REG))]
4717   ""
4718   "ix86_expand_binary_operator (PLUS, DImode, operands); DONE;")
4720 (define_insn "*adddi3_1"
4721   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
4722         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
4723                  (match_operand:DI 2 "general_operand" "roiF,riF")))
4724    (clobber (reg:CC FLAGS_REG))]
4725   "!TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4726   "#")
4728 (define_split
4729   [(set (match_operand:DI 0 "nonimmediate_operand" "")
4730         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4731                  (match_operand:DI 2 "general_operand" "")))
4732    (clobber (reg:CC FLAGS_REG))]
4733   "!TARGET_64BIT && reload_completed"
4734   [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
4735                                           UNSPEC_ADD_CARRY))
4736               (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))])
4737    (parallel [(set (match_dup 3)
4738                    (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
4739                                      (match_dup 4))
4740                             (match_dup 5)))
4741               (clobber (reg:CC FLAGS_REG))])]
4742   "split_di (operands+0, 1, operands+0, operands+3);
4743    split_di (operands+1, 1, operands+1, operands+4);
4744    split_di (operands+2, 1, operands+2, operands+5);")
4746 (define_insn "adddi3_carry_rex64"
4747   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
4748           (plus:DI (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
4749                             (match_operand:DI 1 "nonimmediate_operand" "%0,0"))
4750                    (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
4751    (clobber (reg:CC FLAGS_REG))]
4752   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4753   "adc{q}\t{%2, %0|%0, %2}"
4754   [(set_attr "type" "alu")
4755    (set_attr "pent_pair" "pu")
4756    (set_attr "mode" "DI")])
4758 (define_insn "*adddi3_cc_rex64"
4759   [(set (reg:CC FLAGS_REG)
4760         (unspec:CC [(match_operand:DI 1 "nonimmediate_operand" "%0,0")
4761                     (match_operand:DI 2 "x86_64_general_operand" "re,rm")]
4762                    UNSPEC_ADD_CARRY))
4763    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
4764         (plus:DI (match_dup 1) (match_dup 2)))]
4765   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4766   "add{q}\t{%2, %0|%0, %2}"
4767   [(set_attr "type" "alu")
4768    (set_attr "mode" "DI")])
4770 (define_insn "addqi3_carry"
4771   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
4772           (plus:QI (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
4773                             (match_operand:QI 1 "nonimmediate_operand" "%0,0"))
4774                    (match_operand:QI 2 "general_operand" "qi,qm")))
4775    (clobber (reg:CC FLAGS_REG))]
4776   "ix86_binary_operator_ok (PLUS, QImode, operands)"
4777   "adc{b}\t{%2, %0|%0, %2}"
4778   [(set_attr "type" "alu")
4779    (set_attr "pent_pair" "pu")
4780    (set_attr "mode" "QI")])
4782 (define_insn "addhi3_carry"
4783   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
4784           (plus:HI (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
4785                             (match_operand:HI 1 "nonimmediate_operand" "%0,0"))
4786                    (match_operand:HI 2 "general_operand" "ri,rm")))
4787    (clobber (reg:CC FLAGS_REG))]
4788   "ix86_binary_operator_ok (PLUS, HImode, operands)"
4789   "adc{w}\t{%2, %0|%0, %2}"
4790   [(set_attr "type" "alu")
4791    (set_attr "pent_pair" "pu")
4792    (set_attr "mode" "HI")])
4794 (define_insn "addsi3_carry"
4795   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
4796           (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
4797                             (match_operand:SI 1 "nonimmediate_operand" "%0,0"))
4798                    (match_operand:SI 2 "general_operand" "ri,rm")))
4799    (clobber (reg:CC FLAGS_REG))]
4800   "ix86_binary_operator_ok (PLUS, SImode, operands)"
4801   "adc{l}\t{%2, %0|%0, %2}"
4802   [(set_attr "type" "alu")
4803    (set_attr "pent_pair" "pu")
4804    (set_attr "mode" "SI")])
4806 (define_insn "*addsi3_carry_zext"
4807   [(set (match_operand:DI 0 "register_operand" "=r")
4808           (zero_extend:DI 
4809             (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
4810                               (match_operand:SI 1 "nonimmediate_operand" "%0"))
4811                      (match_operand:SI 2 "general_operand" "rim"))))
4812    (clobber (reg:CC FLAGS_REG))]
4813   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
4814   "adc{l}\t{%2, %k0|%k0, %2}"
4815   [(set_attr "type" "alu")
4816    (set_attr "pent_pair" "pu")
4817    (set_attr "mode" "SI")])
4819 (define_insn "*addsi3_cc"
4820   [(set (reg:CC FLAGS_REG)
4821         (unspec:CC [(match_operand:SI 1 "nonimmediate_operand" "%0,0")
4822                     (match_operand:SI 2 "general_operand" "ri,rm")]
4823                    UNSPEC_ADD_CARRY))
4824    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
4825         (plus:SI (match_dup 1) (match_dup 2)))]
4826   "ix86_binary_operator_ok (PLUS, SImode, operands)"
4827   "add{l}\t{%2, %0|%0, %2}"
4828   [(set_attr "type" "alu")
4829    (set_attr "mode" "SI")])
4831 (define_insn "addqi3_cc"
4832   [(set (reg:CC FLAGS_REG)
4833         (unspec:CC [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
4834                     (match_operand:QI 2 "general_operand" "qi,qm")]
4835                    UNSPEC_ADD_CARRY))
4836    (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
4837         (plus:QI (match_dup 1) (match_dup 2)))]
4838   "ix86_binary_operator_ok (PLUS, QImode, operands)"
4839   "add{b}\t{%2, %0|%0, %2}"
4840   [(set_attr "type" "alu")
4841    (set_attr "mode" "QI")])
4843 (define_expand "addsi3"
4844   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4845                    (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
4846                             (match_operand:SI 2 "general_operand" "")))
4847               (clobber (reg:CC FLAGS_REG))])]
4848   ""
4849   "ix86_expand_binary_operator (PLUS, SImode, operands); DONE;")
4851 (define_insn "*lea_1"
4852   [(set (match_operand:SI 0 "register_operand" "=r")
4853         (match_operand:SI 1 "no_seg_address_operand" "p"))]
4854   "!TARGET_64BIT"
4855   "lea{l}\t{%a1, %0|%0, %a1}"
4856   [(set_attr "type" "lea")
4857    (set_attr "mode" "SI")])
4859 (define_insn "*lea_1_rex64"
4860   [(set (match_operand:SI 0 "register_operand" "=r")
4861         (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0))]
4862   "TARGET_64BIT"
4863   "lea{l}\t{%a1, %0|%0, %a1}"
4864   [(set_attr "type" "lea")
4865    (set_attr "mode" "SI")])
4867 (define_insn "*lea_1_zext"
4868   [(set (match_operand:DI 0 "register_operand" "=r")
4869         (zero_extend:DI
4870          (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0)))]
4871   "TARGET_64BIT"
4872   "lea{l}\t{%a1, %k0|%k0, %a1}"
4873   [(set_attr "type" "lea")
4874    (set_attr "mode" "SI")])
4876 (define_insn "*lea_2_rex64"
4877   [(set (match_operand:DI 0 "register_operand" "=r")
4878         (match_operand:DI 1 "no_seg_address_operand" "p"))]
4879   "TARGET_64BIT"
4880   "lea{q}\t{%a1, %0|%0, %a1}"
4881   [(set_attr "type" "lea")
4882    (set_attr "mode" "DI")])
4884 ;; The lea patterns for non-Pmodes needs to be matched by several
4885 ;; insns converted to real lea by splitters.
4887 (define_insn_and_split "*lea_general_1"
4888   [(set (match_operand 0 "register_operand" "=r")
4889         (plus (plus (match_operand 1 "index_register_operand" "l")
4890                     (match_operand 2 "register_operand" "r"))
4891               (match_operand 3 "immediate_operand" "i")))]
4892   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
4893     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
4894    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
4895    && GET_MODE (operands[0]) == GET_MODE (operands[1])
4896    && GET_MODE (operands[0]) == GET_MODE (operands[2])
4897    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
4898        || GET_MODE (operands[3]) == VOIDmode)"
4899   "#"
4900   "&& reload_completed"
4901   [(const_int 0)]
4903   rtx pat;
4904   operands[0] = gen_lowpart (SImode, operands[0]);
4905   operands[1] = gen_lowpart (Pmode, operands[1]);
4906   operands[2] = gen_lowpart (Pmode, operands[2]);
4907   operands[3] = gen_lowpart (Pmode, operands[3]);
4908   pat = gen_rtx_PLUS (Pmode, gen_rtx_PLUS (Pmode, operands[1], operands[2]),
4909                       operands[3]);
4910   if (Pmode != SImode)
4911     pat = gen_rtx_SUBREG (SImode, pat, 0);
4912   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
4913   DONE;
4915   [(set_attr "type" "lea")
4916    (set_attr "mode" "SI")])
4918 (define_insn_and_split "*lea_general_1_zext"
4919   [(set (match_operand:DI 0 "register_operand" "=r")
4920         (zero_extend:DI
4921           (plus:SI (plus:SI (match_operand:SI 1 "index_register_operand" "l")
4922                             (match_operand:SI 2 "register_operand" "r"))
4923                    (match_operand:SI 3 "immediate_operand" "i"))))]
4924   "TARGET_64BIT"
4925   "#"
4926   "&& reload_completed"
4927   [(set (match_dup 0)
4928         (zero_extend:DI (subreg:SI (plus:DI (plus:DI (match_dup 1)
4929                                                      (match_dup 2))
4930                                             (match_dup 3)) 0)))]
4932   operands[1] = gen_lowpart (Pmode, operands[1]);
4933   operands[2] = gen_lowpart (Pmode, operands[2]);
4934   operands[3] = gen_lowpart (Pmode, operands[3]);
4936   [(set_attr "type" "lea")
4937    (set_attr "mode" "SI")])
4939 (define_insn_and_split "*lea_general_2"
4940   [(set (match_operand 0 "register_operand" "=r")
4941         (plus (mult (match_operand 1 "index_register_operand" "l")
4942                     (match_operand 2 "const248_operand" "i"))
4943               (match_operand 3 "nonmemory_operand" "ri")))]
4944   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
4945     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
4946    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
4947    && GET_MODE (operands[0]) == GET_MODE (operands[1])
4948    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
4949        || GET_MODE (operands[3]) == VOIDmode)"
4950   "#"
4951   "&& reload_completed"
4952   [(const_int 0)]
4954   rtx pat;
4955   operands[0] = gen_lowpart (SImode, operands[0]);
4956   operands[1] = gen_lowpart (Pmode, operands[1]);
4957   operands[3] = gen_lowpart (Pmode, operands[3]);
4958   pat = gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], operands[2]),
4959                       operands[3]);
4960   if (Pmode != SImode)
4961     pat = gen_rtx_SUBREG (SImode, pat, 0);
4962   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
4963   DONE;
4965   [(set_attr "type" "lea")
4966    (set_attr "mode" "SI")])
4968 (define_insn_and_split "*lea_general_2_zext"
4969   [(set (match_operand:DI 0 "register_operand" "=r")
4970         (zero_extend:DI
4971           (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "l")
4972                             (match_operand:SI 2 "const248_operand" "n"))
4973                    (match_operand:SI 3 "nonmemory_operand" "ri"))))]
4974   "TARGET_64BIT"
4975   "#"
4976   "&& reload_completed"
4977   [(set (match_dup 0)
4978         (zero_extend:DI (subreg:SI (plus:DI (mult:DI (match_dup 1)
4979                                                      (match_dup 2))
4980                                             (match_dup 3)) 0)))]
4982   operands[1] = gen_lowpart (Pmode, operands[1]);
4983   operands[3] = gen_lowpart (Pmode, operands[3]);
4985   [(set_attr "type" "lea")
4986    (set_attr "mode" "SI")])
4988 (define_insn_and_split "*lea_general_3"
4989   [(set (match_operand 0 "register_operand" "=r")
4990         (plus (plus (mult (match_operand 1 "index_register_operand" "l")
4991                           (match_operand 2 "const248_operand" "i"))
4992                     (match_operand 3 "register_operand" "r"))
4993               (match_operand 4 "immediate_operand" "i")))]
4994   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
4995     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
4996    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
4997    && GET_MODE (operands[0]) == GET_MODE (operands[1])
4998    && GET_MODE (operands[0]) == GET_MODE (operands[3])"
4999   "#"
5000   "&& reload_completed"
5001   [(const_int 0)]
5003   rtx pat;
5004   operands[0] = gen_lowpart (SImode, operands[0]);
5005   operands[1] = gen_lowpart (Pmode, operands[1]);
5006   operands[3] = gen_lowpart (Pmode, operands[3]);
5007   operands[4] = gen_lowpart (Pmode, operands[4]);
5008   pat = gen_rtx_PLUS (Pmode,
5009                       gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1],
5010                                                          operands[2]),
5011                                     operands[3]),
5012                       operands[4]);
5013   if (Pmode != SImode)
5014     pat = gen_rtx_SUBREG (SImode, pat, 0);
5015   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5016   DONE;
5018   [(set_attr "type" "lea")
5019    (set_attr "mode" "SI")])
5021 (define_insn_and_split "*lea_general_3_zext"
5022   [(set (match_operand:DI 0 "register_operand" "=r")
5023         (zero_extend:DI
5024           (plus:SI (plus:SI (mult:SI
5025                               (match_operand:SI 1 "index_register_operand" "l")
5026                               (match_operand:SI 2 "const248_operand" "n"))
5027                             (match_operand:SI 3 "register_operand" "r"))
5028                    (match_operand:SI 4 "immediate_operand" "i"))))]
5029   "TARGET_64BIT"
5030   "#"
5031   "&& reload_completed"
5032   [(set (match_dup 0)
5033         (zero_extend:DI (subreg:SI (plus:DI (plus:DI (mult:DI (match_dup 1)
5034                                                               (match_dup 2))
5035                                                      (match_dup 3))
5036                                             (match_dup 4)) 0)))]
5038   operands[1] = gen_lowpart (Pmode, operands[1]);
5039   operands[3] = gen_lowpart (Pmode, operands[3]);
5040   operands[4] = gen_lowpart (Pmode, operands[4]);
5042   [(set_attr "type" "lea")
5043    (set_attr "mode" "SI")])
5045 (define_insn "*adddi_1_rex64"
5046   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r")
5047         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,r")
5048                  (match_operand:DI 2 "x86_64_general_operand" "rme,re,le")))
5049    (clobber (reg:CC FLAGS_REG))]
5050   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5052   switch (get_attr_type (insn))
5053     {
5054     case TYPE_LEA:
5055       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5056       return "lea{q}\t{%a2, %0|%0, %a2}";
5058     case TYPE_INCDEC:
5059       if (! rtx_equal_p (operands[0], operands[1]))
5060         abort ();
5061       if (operands[2] == const1_rtx)
5062         return "inc{q}\t%0";
5063       else if (operands[2] == constm1_rtx)
5064         return "dec{q}\t%0";
5065       else
5066         abort ();
5068     default:
5069       if (! rtx_equal_p (operands[0], operands[1]))
5070         abort ();
5072       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5073          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5074       if (GET_CODE (operands[2]) == CONST_INT
5075           /* Avoid overflows.  */
5076           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5077           && (INTVAL (operands[2]) == 128
5078               || (INTVAL (operands[2]) < 0
5079                   && INTVAL (operands[2]) != -128)))
5080         {
5081           operands[2] = GEN_INT (-INTVAL (operands[2]));
5082           return "sub{q}\t{%2, %0|%0, %2}";
5083         }
5084       return "add{q}\t{%2, %0|%0, %2}";
5085     }
5087   [(set (attr "type")
5088      (cond [(eq_attr "alternative" "2")
5089               (const_string "lea")
5090             ; Current assemblers are broken and do not allow @GOTOFF in
5091             ; ought but a memory context.
5092             (match_operand:DI 2 "pic_symbolic_operand" "")
5093               (const_string "lea")
5094             (match_operand:DI 2 "incdec_operand" "")
5095               (const_string "incdec")
5096            ]
5097            (const_string "alu")))
5098    (set_attr "mode" "DI")])
5100 ;; Convert lea to the lea pattern to avoid flags dependency.
5101 (define_split
5102   [(set (match_operand:DI 0 "register_operand" "")
5103         (plus:DI (match_operand:DI 1 "register_operand" "")
5104                  (match_operand:DI 2 "x86_64_nonmemory_operand" "")))
5105    (clobber (reg:CC FLAGS_REG))]
5106   "TARGET_64BIT && reload_completed
5107    && true_regnum (operands[0]) != true_regnum (operands[1])"
5108   [(set (match_dup 0)
5109         (plus:DI (match_dup 1)
5110                  (match_dup 2)))]
5111   "")
5113 (define_insn "*adddi_2_rex64"
5114   [(set (reg FLAGS_REG)
5115         (compare
5116           (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5117                    (match_operand:DI 2 "x86_64_general_operand" "rme,re"))
5118           (const_int 0)))                       
5119    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
5120         (plus:DI (match_dup 1) (match_dup 2)))]
5121   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5122    && ix86_binary_operator_ok (PLUS, DImode, operands)
5123    /* Current assemblers are broken and do not allow @GOTOFF in
5124       ought but a memory context.  */
5125    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5127   switch (get_attr_type (insn))
5128     {
5129     case TYPE_INCDEC:
5130       if (! rtx_equal_p (operands[0], operands[1]))
5131         abort ();
5132       if (operands[2] == const1_rtx)
5133         return "inc{q}\t%0";
5134       else if (operands[2] == constm1_rtx)
5135         return "dec{q}\t%0";
5136       else
5137         abort ();
5139     default:
5140       if (! rtx_equal_p (operands[0], operands[1]))
5141         abort ();
5142       /* ???? We ought to handle there the 32bit case too
5143          - do we need new constraint?  */
5144       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5145          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5146       if (GET_CODE (operands[2]) == CONST_INT
5147           /* Avoid overflows.  */
5148           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5149           && (INTVAL (operands[2]) == 128
5150               || (INTVAL (operands[2]) < 0
5151                   && INTVAL (operands[2]) != -128)))
5152         {
5153           operands[2] = GEN_INT (-INTVAL (operands[2]));
5154           return "sub{q}\t{%2, %0|%0, %2}";
5155         }
5156       return "add{q}\t{%2, %0|%0, %2}";
5157     }
5159   [(set (attr "type")
5160      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5161         (const_string "incdec")
5162         (const_string "alu")))
5163    (set_attr "mode" "DI")])
5165 (define_insn "*adddi_3_rex64"
5166   [(set (reg FLAGS_REG)
5167         (compare (neg:DI (match_operand:DI 2 "x86_64_general_operand" "rme"))
5168                  (match_operand:DI 1 "x86_64_general_operand" "%0")))
5169    (clobber (match_scratch:DI 0 "=r"))]
5170   "TARGET_64BIT
5171    && ix86_match_ccmode (insn, CCZmode)
5172    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5173    /* Current assemblers are broken and do not allow @GOTOFF in
5174       ought but a memory context.  */
5175    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5177   switch (get_attr_type (insn))
5178     {
5179     case TYPE_INCDEC:
5180       if (! rtx_equal_p (operands[0], operands[1]))
5181         abort ();
5182       if (operands[2] == const1_rtx)
5183         return "inc{q}\t%0";
5184       else if (operands[2] == constm1_rtx)
5185         return "dec{q}\t%0";
5186       else
5187         abort ();
5189     default:
5190       if (! rtx_equal_p (operands[0], operands[1]))
5191         abort ();
5192       /* ???? We ought to handle there the 32bit case too
5193          - do we need new constraint?  */
5194       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5195          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5196       if (GET_CODE (operands[2]) == CONST_INT
5197           /* Avoid overflows.  */
5198           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5199           && (INTVAL (operands[2]) == 128
5200               || (INTVAL (operands[2]) < 0
5201                   && INTVAL (operands[2]) != -128)))
5202         {
5203           operands[2] = GEN_INT (-INTVAL (operands[2]));
5204           return "sub{q}\t{%2, %0|%0, %2}";
5205         }
5206       return "add{q}\t{%2, %0|%0, %2}";
5207     }
5209   [(set (attr "type")
5210      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5211         (const_string "incdec")
5212         (const_string "alu")))
5213    (set_attr "mode" "DI")])
5215 ; For comparisons against 1, -1 and 128, we may generate better code
5216 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
5217 ; is matched then.  We can't accept general immediate, because for
5218 ; case of overflows,  the result is messed up.
5219 ; This pattern also don't hold of 0x8000000000000000, since the value overflows
5220 ; when negated.
5221 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5222 ; only for comparisons not depending on it.
5223 (define_insn "*adddi_4_rex64"
5224   [(set (reg FLAGS_REG)
5225         (compare (match_operand:DI 1 "nonimmediate_operand" "0")
5226                  (match_operand:DI 2 "x86_64_immediate_operand" "e")))
5227    (clobber (match_scratch:DI 0 "=rm"))]
5228   "TARGET_64BIT
5229    &&  ix86_match_ccmode (insn, CCGCmode)"
5231   switch (get_attr_type (insn))
5232     {
5233     case TYPE_INCDEC:
5234       if (operands[2] == constm1_rtx)
5235         return "inc{q}\t%0";
5236       else if (operands[2] == const1_rtx)
5237         return "dec{q}\t%0";
5238       else
5239         abort();
5241     default:
5242       if (! rtx_equal_p (operands[0], operands[1]))
5243         abort ();
5244       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5245          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5246       if ((INTVAL (operands[2]) == -128
5247            || (INTVAL (operands[2]) > 0
5248                && INTVAL (operands[2]) != 128))
5249           /* Avoid overflows.  */
5250           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))))
5251         return "sub{q}\t{%2, %0|%0, %2}";
5252       operands[2] = GEN_INT (-INTVAL (operands[2]));
5253       return "add{q}\t{%2, %0|%0, %2}";
5254     }
5256   [(set (attr "type")
5257      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5258         (const_string "incdec")
5259         (const_string "alu")))
5260    (set_attr "mode" "DI")])
5262 (define_insn "*adddi_5_rex64"
5263   [(set (reg FLAGS_REG)
5264         (compare
5265           (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5266                    (match_operand:DI 2 "x86_64_general_operand" "rme"))
5267           (const_int 0)))                       
5268    (clobber (match_scratch:DI 0 "=r"))]
5269   "TARGET_64BIT
5270    && ix86_match_ccmode (insn, CCGOCmode)
5271    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5272    /* Current assemblers are broken and do not allow @GOTOFF in
5273       ought but a memory context.  */
5274    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5276   switch (get_attr_type (insn))
5277     {
5278     case TYPE_INCDEC:
5279       if (! rtx_equal_p (operands[0], operands[1]))
5280         abort ();
5281       if (operands[2] == const1_rtx)
5282         return "inc{q}\t%0";
5283       else if (operands[2] == constm1_rtx)
5284         return "dec{q}\t%0";
5285       else
5286         abort();
5288     default:
5289       if (! rtx_equal_p (operands[0], operands[1]))
5290         abort ();
5291       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5292          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5293       if (GET_CODE (operands[2]) == CONST_INT
5294           /* Avoid overflows.  */
5295           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5296           && (INTVAL (operands[2]) == 128
5297               || (INTVAL (operands[2]) < 0
5298                   && INTVAL (operands[2]) != -128)))
5299         {
5300           operands[2] = GEN_INT (-INTVAL (operands[2]));
5301           return "sub{q}\t{%2, %0|%0, %2}";
5302         }
5303       return "add{q}\t{%2, %0|%0, %2}";
5304     }
5306   [(set (attr "type")
5307      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5308         (const_string "incdec")
5309         (const_string "alu")))
5310    (set_attr "mode" "DI")])
5313 (define_insn "*addsi_1"
5314   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,rm,r")
5315         (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,r")
5316                  (match_operand:SI 2 "general_operand" "rmni,rni,lni")))
5317    (clobber (reg:CC FLAGS_REG))]
5318   "ix86_binary_operator_ok (PLUS, SImode, operands)"
5320   switch (get_attr_type (insn))
5321     {
5322     case TYPE_LEA:
5323       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5324       return "lea{l}\t{%a2, %0|%0, %a2}";
5326     case TYPE_INCDEC:
5327       if (! rtx_equal_p (operands[0], operands[1]))
5328         abort ();
5329       if (operands[2] == const1_rtx)
5330         return "inc{l}\t%0";
5331       else if (operands[2] == constm1_rtx)
5332         return "dec{l}\t%0";
5333       else
5334         abort();
5336     default:
5337       if (! rtx_equal_p (operands[0], operands[1]))
5338         abort ();
5340       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5341          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5342       if (GET_CODE (operands[2]) == CONST_INT
5343           && (INTVAL (operands[2]) == 128
5344               || (INTVAL (operands[2]) < 0
5345                   && INTVAL (operands[2]) != -128)))
5346         {
5347           operands[2] = GEN_INT (-INTVAL (operands[2]));
5348           return "sub{l}\t{%2, %0|%0, %2}";
5349         }
5350       return "add{l}\t{%2, %0|%0, %2}";
5351     }
5353   [(set (attr "type")
5354      (cond [(eq_attr "alternative" "2")
5355               (const_string "lea")
5356             ; Current assemblers are broken and do not allow @GOTOFF in
5357             ; ought but a memory context.
5358             (match_operand:SI 2 "pic_symbolic_operand" "")
5359               (const_string "lea")
5360             (match_operand:SI 2 "incdec_operand" "")
5361               (const_string "incdec")
5362            ]
5363            (const_string "alu")))
5364    (set_attr "mode" "SI")])
5366 ;; Convert lea to the lea pattern to avoid flags dependency.
5367 (define_split
5368   [(set (match_operand 0 "register_operand" "")
5369         (plus (match_operand 1 "register_operand" "")
5370               (match_operand 2 "nonmemory_operand" "")))
5371    (clobber (reg:CC FLAGS_REG))]
5372   "reload_completed
5373    && true_regnum (operands[0]) != true_regnum (operands[1])"
5374   [(const_int 0)]
5376   rtx pat;
5377   /* In -fPIC mode the constructs like (const (unspec [symbol_ref]))
5378      may confuse gen_lowpart.  */
5379   if (GET_MODE (operands[0]) != Pmode)
5380     {
5381       operands[1] = gen_lowpart (Pmode, operands[1]);
5382       operands[2] = gen_lowpart (Pmode, operands[2]);
5383     }
5384   operands[0] = gen_lowpart (SImode, operands[0]);
5385   pat = gen_rtx_PLUS (Pmode, operands[1], operands[2]);
5386   if (Pmode != SImode)
5387     pat = gen_rtx_SUBREG (SImode, pat, 0);
5388   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5389   DONE;
5392 ;; It may seem that nonimmediate operand is proper one for operand 1.
5393 ;; The addsi_1 pattern allows nonimmediate operand at that place and
5394 ;; we take care in ix86_binary_operator_ok to not allow two memory
5395 ;; operands so proper swapping will be done in reload.  This allow
5396 ;; patterns constructed from addsi_1 to match.
5397 (define_insn "addsi_1_zext"
5398   [(set (match_operand:DI 0 "register_operand" "=r,r")
5399         (zero_extend:DI
5400           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r")
5401                    (match_operand:SI 2 "general_operand" "rmni,lni"))))
5402    (clobber (reg:CC FLAGS_REG))]
5403   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5405   switch (get_attr_type (insn))
5406     {
5407     case TYPE_LEA:
5408       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5409       return "lea{l}\t{%a2, %k0|%k0, %a2}";
5411     case TYPE_INCDEC:
5412       if (operands[2] == const1_rtx)
5413         return "inc{l}\t%k0";
5414       else if (operands[2] == constm1_rtx)
5415         return "dec{l}\t%k0";
5416       else
5417         abort();
5419     default:
5420       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5421          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5422       if (GET_CODE (operands[2]) == CONST_INT
5423           && (INTVAL (operands[2]) == 128
5424               || (INTVAL (operands[2]) < 0
5425                   && INTVAL (operands[2]) != -128)))
5426         {
5427           operands[2] = GEN_INT (-INTVAL (operands[2]));
5428           return "sub{l}\t{%2, %k0|%k0, %2}";
5429         }
5430       return "add{l}\t{%2, %k0|%k0, %2}";
5431     }
5433   [(set (attr "type")
5434      (cond [(eq_attr "alternative" "1")
5435               (const_string "lea")
5436             ; Current assemblers are broken and do not allow @GOTOFF in
5437             ; ought but a memory context.
5438             (match_operand:SI 2 "pic_symbolic_operand" "")
5439               (const_string "lea")
5440             (match_operand:SI 2 "incdec_operand" "")
5441               (const_string "incdec")
5442            ]
5443            (const_string "alu")))
5444    (set_attr "mode" "SI")])
5446 ;; Convert lea to the lea pattern to avoid flags dependency.
5447 (define_split
5448   [(set (match_operand:DI 0 "register_operand" "")
5449         (zero_extend:DI
5450           (plus:SI (match_operand:SI 1 "register_operand" "")
5451                    (match_operand:SI 2 "nonmemory_operand" ""))))
5452    (clobber (reg:CC FLAGS_REG))]
5453   "TARGET_64BIT && reload_completed
5454    && true_regnum (operands[0]) != true_regnum (operands[1])"
5455   [(set (match_dup 0)
5456         (zero_extend:DI (subreg:SI (plus:DI (match_dup 1) (match_dup 2)) 0)))]
5458   operands[1] = gen_lowpart (Pmode, operands[1]);
5459   operands[2] = gen_lowpart (Pmode, operands[2]);
5462 (define_insn "*addsi_2"
5463   [(set (reg FLAGS_REG)
5464         (compare
5465           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
5466                    (match_operand:SI 2 "general_operand" "rmni,rni"))
5467           (const_int 0)))                       
5468    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
5469         (plus:SI (match_dup 1) (match_dup 2)))]
5470   "ix86_match_ccmode (insn, CCGOCmode)
5471    && ix86_binary_operator_ok (PLUS, SImode, operands)
5472    /* Current assemblers are broken and do not allow @GOTOFF in
5473       ought but a memory context.  */
5474    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5476   switch (get_attr_type (insn))
5477     {
5478     case TYPE_INCDEC:
5479       if (! rtx_equal_p (operands[0], operands[1]))
5480         abort ();
5481       if (operands[2] == const1_rtx)
5482         return "inc{l}\t%0";
5483       else if (operands[2] == constm1_rtx)
5484         return "dec{l}\t%0";
5485       else
5486         abort();
5488     default:
5489       if (! rtx_equal_p (operands[0], operands[1]))
5490         abort ();
5491       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5492          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5493       if (GET_CODE (operands[2]) == CONST_INT
5494           && (INTVAL (operands[2]) == 128
5495               || (INTVAL (operands[2]) < 0
5496                   && INTVAL (operands[2]) != -128)))
5497         {
5498           operands[2] = GEN_INT (-INTVAL (operands[2]));
5499           return "sub{l}\t{%2, %0|%0, %2}";
5500         }
5501       return "add{l}\t{%2, %0|%0, %2}";
5502     }
5504   [(set (attr "type")
5505      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5506         (const_string "incdec")
5507         (const_string "alu")))
5508    (set_attr "mode" "SI")])
5510 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5511 (define_insn "*addsi_2_zext"
5512   [(set (reg FLAGS_REG)
5513         (compare
5514           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5515                    (match_operand:SI 2 "general_operand" "rmni"))
5516           (const_int 0)))                       
5517    (set (match_operand:DI 0 "register_operand" "=r")
5518         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5519   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5520    && ix86_binary_operator_ok (PLUS, SImode, operands)
5521    /* Current assemblers are broken and do not allow @GOTOFF in
5522       ought but a memory context.  */
5523    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5525   switch (get_attr_type (insn))
5526     {
5527     case TYPE_INCDEC:
5528       if (operands[2] == const1_rtx)
5529         return "inc{l}\t%k0";
5530       else if (operands[2] == constm1_rtx)
5531         return "dec{l}\t%k0";
5532       else
5533         abort();
5535     default:
5536       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5537          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5538       if (GET_CODE (operands[2]) == CONST_INT
5539           && (INTVAL (operands[2]) == 128
5540               || (INTVAL (operands[2]) < 0
5541                   && INTVAL (operands[2]) != -128)))
5542         {
5543           operands[2] = GEN_INT (-INTVAL (operands[2]));
5544           return "sub{l}\t{%2, %k0|%k0, %2}";
5545         }
5546       return "add{l}\t{%2, %k0|%k0, %2}";
5547     }
5549   [(set (attr "type")
5550      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5551         (const_string "incdec")
5552         (const_string "alu")))
5553    (set_attr "mode" "SI")])
5555 (define_insn "*addsi_3"
5556   [(set (reg FLAGS_REG)
5557         (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5558                  (match_operand:SI 1 "nonimmediate_operand" "%0")))
5559    (clobber (match_scratch:SI 0 "=r"))]
5560   "ix86_match_ccmode (insn, CCZmode)
5561    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5562    /* Current assemblers are broken and do not allow @GOTOFF in
5563       ought but a memory context.  */
5564    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5566   switch (get_attr_type (insn))
5567     {
5568     case TYPE_INCDEC:
5569       if (! rtx_equal_p (operands[0], operands[1]))
5570         abort ();
5571       if (operands[2] == const1_rtx)
5572         return "inc{l}\t%0";
5573       else if (operands[2] == constm1_rtx)
5574         return "dec{l}\t%0";
5575       else
5576         abort();
5578     default:
5579       if (! rtx_equal_p (operands[0], operands[1]))
5580         abort ();
5581       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5582          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5583       if (GET_CODE (operands[2]) == CONST_INT
5584           && (INTVAL (operands[2]) == 128
5585               || (INTVAL (operands[2]) < 0
5586                   && INTVAL (operands[2]) != -128)))
5587         {
5588           operands[2] = GEN_INT (-INTVAL (operands[2]));
5589           return "sub{l}\t{%2, %0|%0, %2}";
5590         }
5591       return "add{l}\t{%2, %0|%0, %2}";
5592     }
5594   [(set (attr "type")
5595      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5596         (const_string "incdec")
5597         (const_string "alu")))
5598    (set_attr "mode" "SI")])
5600 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5601 (define_insn "*addsi_3_zext"
5602   [(set (reg FLAGS_REG)
5603         (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5604                  (match_operand:SI 1 "nonimmediate_operand" "%0")))
5605    (set (match_operand:DI 0 "register_operand" "=r")
5606         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5607   "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
5608    && ix86_binary_operator_ok (PLUS, SImode, operands)
5609    /* Current assemblers are broken and do not allow @GOTOFF in
5610       ought but a memory context.  */
5611    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5613   switch (get_attr_type (insn))
5614     {
5615     case TYPE_INCDEC:
5616       if (operands[2] == const1_rtx)
5617         return "inc{l}\t%k0";
5618       else if (operands[2] == constm1_rtx)
5619         return "dec{l}\t%k0";
5620       else
5621         abort();
5623     default:
5624       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5625          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5626       if (GET_CODE (operands[2]) == CONST_INT
5627           && (INTVAL (operands[2]) == 128
5628               || (INTVAL (operands[2]) < 0
5629                   && INTVAL (operands[2]) != -128)))
5630         {
5631           operands[2] = GEN_INT (-INTVAL (operands[2]));
5632           return "sub{l}\t{%2, %k0|%k0, %2}";
5633         }
5634       return "add{l}\t{%2, %k0|%k0, %2}";
5635     }
5637   [(set (attr "type")
5638      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5639         (const_string "incdec")
5640         (const_string "alu")))
5641    (set_attr "mode" "SI")])
5643 ; For comparisons against 1, -1 and 128, we may generate better code
5644 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
5645 ; is matched then.  We can't accept general immediate, because for
5646 ; case of overflows,  the result is messed up.
5647 ; This pattern also don't hold of 0x80000000, since the value overflows
5648 ; when negated.
5649 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5650 ; only for comparisons not depending on it.
5651 (define_insn "*addsi_4"
5652   [(set (reg FLAGS_REG)
5653         (compare (match_operand:SI 1 "nonimmediate_operand" "0")
5654                  (match_operand:SI 2 "const_int_operand" "n")))
5655    (clobber (match_scratch:SI 0 "=rm"))]
5656   "ix86_match_ccmode (insn, CCGCmode)
5657    && (INTVAL (operands[2]) & 0xffffffff) != 0x80000000"
5659   switch (get_attr_type (insn))
5660     {
5661     case TYPE_INCDEC:
5662       if (operands[2] == constm1_rtx)
5663         return "inc{l}\t%0";
5664       else if (operands[2] == const1_rtx)
5665         return "dec{l}\t%0";
5666       else
5667         abort();
5669     default:
5670       if (! rtx_equal_p (operands[0], operands[1]))
5671         abort ();
5672       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5673          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5674       if ((INTVAL (operands[2]) == -128
5675            || (INTVAL (operands[2]) > 0
5676                && INTVAL (operands[2]) != 128)))
5677         return "sub{l}\t{%2, %0|%0, %2}";
5678       operands[2] = GEN_INT (-INTVAL (operands[2]));
5679       return "add{l}\t{%2, %0|%0, %2}";
5680     }
5682   [(set (attr "type")
5683      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5684         (const_string "incdec")
5685         (const_string "alu")))
5686    (set_attr "mode" "SI")])
5688 (define_insn "*addsi_5"
5689   [(set (reg FLAGS_REG)
5690         (compare
5691           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5692                    (match_operand:SI 2 "general_operand" "rmni"))
5693           (const_int 0)))                       
5694    (clobber (match_scratch:SI 0 "=r"))]
5695   "ix86_match_ccmode (insn, CCGOCmode)
5696    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5697    /* Current assemblers are broken and do not allow @GOTOFF in
5698       ought but a memory context.  */
5699    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5701   switch (get_attr_type (insn))
5702     {
5703     case TYPE_INCDEC:
5704       if (! rtx_equal_p (operands[0], operands[1]))
5705         abort ();
5706       if (operands[2] == const1_rtx)
5707         return "inc{l}\t%0";
5708       else if (operands[2] == constm1_rtx)
5709         return "dec{l}\t%0";
5710       else
5711         abort();
5713     default:
5714       if (! rtx_equal_p (operands[0], operands[1]))
5715         abort ();
5716       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5717          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5718       if (GET_CODE (operands[2]) == CONST_INT
5719           && (INTVAL (operands[2]) == 128
5720               || (INTVAL (operands[2]) < 0
5721                   && INTVAL (operands[2]) != -128)))
5722         {
5723           operands[2] = GEN_INT (-INTVAL (operands[2]));
5724           return "sub{l}\t{%2, %0|%0, %2}";
5725         }
5726       return "add{l}\t{%2, %0|%0, %2}";
5727     }
5729   [(set (attr "type")
5730      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5731         (const_string "incdec")
5732         (const_string "alu")))
5733    (set_attr "mode" "SI")])
5735 (define_expand "addhi3"
5736   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
5737                    (plus:HI (match_operand:HI 1 "nonimmediate_operand" "")
5738                             (match_operand:HI 2 "general_operand" "")))
5739               (clobber (reg:CC FLAGS_REG))])]
5740   "TARGET_HIMODE_MATH"
5741   "ix86_expand_binary_operator (PLUS, HImode, operands); DONE;")
5743 ;; %%% After Dave's SUBREG_BYTE stuff goes in, re-enable incb %ah
5744 ;; type optimizations enabled by define-splits.  This is not important
5745 ;; for PII, and in fact harmful because of partial register stalls.
5747 (define_insn "*addhi_1_lea"
5748   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
5749         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r")
5750                  (match_operand:HI 2 "general_operand" "ri,rm,lni")))
5751    (clobber (reg:CC FLAGS_REG))]
5752   "!TARGET_PARTIAL_REG_STALL
5753    && ix86_binary_operator_ok (PLUS, HImode, operands)"
5755   switch (get_attr_type (insn))
5756     {
5757     case TYPE_LEA:
5758       return "#";
5759     case TYPE_INCDEC:
5760       if (operands[2] == const1_rtx)
5761         return "inc{w}\t%0";
5762       else if (operands[2] == constm1_rtx)
5763         return "dec{w}\t%0";
5764       abort();
5766     default:
5767       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5768          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5769       if (GET_CODE (operands[2]) == CONST_INT
5770           && (INTVAL (operands[2]) == 128
5771               || (INTVAL (operands[2]) < 0
5772                   && INTVAL (operands[2]) != -128)))
5773         {
5774           operands[2] = GEN_INT (-INTVAL (operands[2]));
5775           return "sub{w}\t{%2, %0|%0, %2}";
5776         }
5777       return "add{w}\t{%2, %0|%0, %2}";
5778     }
5780   [(set (attr "type")
5781      (if_then_else (eq_attr "alternative" "2")
5782         (const_string "lea")
5783         (if_then_else (match_operand:HI 2 "incdec_operand" "")
5784            (const_string "incdec")
5785            (const_string "alu"))))
5786    (set_attr "mode" "HI,HI,SI")])
5788 (define_insn "*addhi_1"
5789   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
5790         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
5791                  (match_operand:HI 2 "general_operand" "ri,rm")))
5792    (clobber (reg:CC FLAGS_REG))]
5793   "TARGET_PARTIAL_REG_STALL
5794    && ix86_binary_operator_ok (PLUS, HImode, operands)"
5796   switch (get_attr_type (insn))
5797     {
5798     case TYPE_INCDEC:
5799       if (operands[2] == const1_rtx)
5800         return "inc{w}\t%0";
5801       else if (operands[2] == constm1_rtx)
5802         return "dec{w}\t%0";
5803       abort();
5805     default:
5806       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5807          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5808       if (GET_CODE (operands[2]) == CONST_INT
5809           && (INTVAL (operands[2]) == 128
5810               || (INTVAL (operands[2]) < 0
5811                   && INTVAL (operands[2]) != -128)))
5812         {
5813           operands[2] = GEN_INT (-INTVAL (operands[2]));
5814           return "sub{w}\t{%2, %0|%0, %2}";
5815         }
5816       return "add{w}\t{%2, %0|%0, %2}";
5817     }
5819   [(set (attr "type")
5820      (if_then_else (match_operand:HI 2 "incdec_operand" "")
5821         (const_string "incdec")
5822         (const_string "alu")))
5823    (set_attr "mode" "HI")])
5825 (define_insn "*addhi_2"
5826   [(set (reg FLAGS_REG)
5827         (compare
5828           (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
5829                    (match_operand:HI 2 "general_operand" "rmni,rni"))
5830           (const_int 0)))                       
5831    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
5832         (plus:HI (match_dup 1) (match_dup 2)))]
5833   "ix86_match_ccmode (insn, CCGOCmode)
5834    && ix86_binary_operator_ok (PLUS, HImode, operands)"
5836   switch (get_attr_type (insn))
5837     {
5838     case TYPE_INCDEC:
5839       if (operands[2] == const1_rtx)
5840         return "inc{w}\t%0";
5841       else if (operands[2] == constm1_rtx)
5842         return "dec{w}\t%0";
5843       abort();
5845     default:
5846       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5847          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5848       if (GET_CODE (operands[2]) == CONST_INT
5849           && (INTVAL (operands[2]) == 128
5850               || (INTVAL (operands[2]) < 0
5851                   && INTVAL (operands[2]) != -128)))
5852         {
5853           operands[2] = GEN_INT (-INTVAL (operands[2]));
5854           return "sub{w}\t{%2, %0|%0, %2}";
5855         }
5856       return "add{w}\t{%2, %0|%0, %2}";
5857     }
5859   [(set (attr "type")
5860      (if_then_else (match_operand:HI 2 "incdec_operand" "")
5861         (const_string "incdec")
5862         (const_string "alu")))
5863    (set_attr "mode" "HI")])
5865 (define_insn "*addhi_3"
5866   [(set (reg FLAGS_REG)
5867         (compare (neg:HI (match_operand:HI 2 "general_operand" "rmni"))
5868                  (match_operand:HI 1 "nonimmediate_operand" "%0")))
5869    (clobber (match_scratch:HI 0 "=r"))]
5870   "ix86_match_ccmode (insn, CCZmode)
5871    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5873   switch (get_attr_type (insn))
5874     {
5875     case TYPE_INCDEC:
5876       if (operands[2] == const1_rtx)
5877         return "inc{w}\t%0";
5878       else if (operands[2] == constm1_rtx)
5879         return "dec{w}\t%0";
5880       abort();
5882     default:
5883       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5884          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5885       if (GET_CODE (operands[2]) == CONST_INT
5886           && (INTVAL (operands[2]) == 128
5887               || (INTVAL (operands[2]) < 0
5888                   && INTVAL (operands[2]) != -128)))
5889         {
5890           operands[2] = GEN_INT (-INTVAL (operands[2]));
5891           return "sub{w}\t{%2, %0|%0, %2}";
5892         }
5893       return "add{w}\t{%2, %0|%0, %2}";
5894     }
5896   [(set (attr "type")
5897      (if_then_else (match_operand:HI 2 "incdec_operand" "")
5898         (const_string "incdec")
5899         (const_string "alu")))
5900    (set_attr "mode" "HI")])
5902 ; See comments above addsi_4 for details.
5903 (define_insn "*addhi_4"
5904   [(set (reg FLAGS_REG)
5905         (compare (match_operand:HI 1 "nonimmediate_operand" "0")
5906                  (match_operand:HI 2 "const_int_operand" "n")))
5907    (clobber (match_scratch:HI 0 "=rm"))]
5908   "ix86_match_ccmode (insn, CCGCmode)
5909    && (INTVAL (operands[2]) & 0xffff) != 0x8000"
5911   switch (get_attr_type (insn))
5912     {
5913     case TYPE_INCDEC:
5914       if (operands[2] == constm1_rtx)
5915         return "inc{w}\t%0";
5916       else if (operands[2] == const1_rtx)
5917         return "dec{w}\t%0";
5918       else
5919         abort();
5921     default:
5922       if (! rtx_equal_p (operands[0], operands[1]))
5923         abort ();
5924       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5925          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5926       if ((INTVAL (operands[2]) == -128
5927            || (INTVAL (operands[2]) > 0
5928                && INTVAL (operands[2]) != 128)))
5929         return "sub{w}\t{%2, %0|%0, %2}";
5930       operands[2] = GEN_INT (-INTVAL (operands[2]));
5931       return "add{w}\t{%2, %0|%0, %2}";
5932     }
5934   [(set (attr "type")
5935      (if_then_else (match_operand:HI 2 "incdec_operand" "")
5936         (const_string "incdec")
5937         (const_string "alu")))
5938    (set_attr "mode" "SI")])
5941 (define_insn "*addhi_5"
5942   [(set (reg FLAGS_REG)
5943         (compare
5944           (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
5945                    (match_operand:HI 2 "general_operand" "rmni"))
5946           (const_int 0)))                       
5947    (clobber (match_scratch:HI 0 "=r"))]
5948   "ix86_match_ccmode (insn, CCGOCmode)
5949    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5951   switch (get_attr_type (insn))
5952     {
5953     case TYPE_INCDEC:
5954       if (operands[2] == const1_rtx)
5955         return "inc{w}\t%0";
5956       else if (operands[2] == constm1_rtx)
5957         return "dec{w}\t%0";
5958       abort();
5960     default:
5961       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5962          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5963       if (GET_CODE (operands[2]) == CONST_INT
5964           && (INTVAL (operands[2]) == 128
5965               || (INTVAL (operands[2]) < 0
5966                   && INTVAL (operands[2]) != -128)))
5967         {
5968           operands[2] = GEN_INT (-INTVAL (operands[2]));
5969           return "sub{w}\t{%2, %0|%0, %2}";
5970         }
5971       return "add{w}\t{%2, %0|%0, %2}";
5972     }
5974   [(set (attr "type")
5975      (if_then_else (match_operand:HI 2 "incdec_operand" "")
5976         (const_string "incdec")
5977         (const_string "alu")))
5978    (set_attr "mode" "HI")])
5980 (define_expand "addqi3"
5981   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
5982                    (plus:QI (match_operand:QI 1 "nonimmediate_operand" "")
5983                             (match_operand:QI 2 "general_operand" "")))
5984               (clobber (reg:CC FLAGS_REG))])]
5985   "TARGET_QIMODE_MATH"
5986   "ix86_expand_binary_operator (PLUS, QImode, operands); DONE;")
5988 ;; %%% Potential partial reg stall on alternative 2.  What to do?
5989 (define_insn "*addqi_1_lea"
5990   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r,r")
5991         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,r")
5992                  (match_operand:QI 2 "general_operand" "qn,qmn,rn,ln")))
5993    (clobber (reg:CC FLAGS_REG))]
5994   "!TARGET_PARTIAL_REG_STALL
5995    && ix86_binary_operator_ok (PLUS, QImode, operands)"
5997   int widen = (which_alternative == 2);
5998   switch (get_attr_type (insn))
5999     {
6000     case TYPE_LEA:
6001       return "#";
6002     case TYPE_INCDEC:
6003       if (operands[2] == const1_rtx)
6004         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6005       else if (operands[2] == constm1_rtx)
6006         return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6007       abort();
6009     default:
6010       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6011          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6012       if (GET_CODE (operands[2]) == CONST_INT
6013           && (INTVAL (operands[2]) == 128
6014               || (INTVAL (operands[2]) < 0
6015                   && INTVAL (operands[2]) != -128)))
6016         {
6017           operands[2] = GEN_INT (-INTVAL (operands[2]));
6018           if (widen)
6019             return "sub{l}\t{%2, %k0|%k0, %2}";
6020           else
6021             return "sub{b}\t{%2, %0|%0, %2}";
6022         }
6023       if (widen)
6024         return "add{l}\t{%k2, %k0|%k0, %k2}";
6025       else
6026         return "add{b}\t{%2, %0|%0, %2}";
6027     }
6029   [(set (attr "type")
6030      (if_then_else (eq_attr "alternative" "3")
6031         (const_string "lea")
6032         (if_then_else (match_operand:QI 2 "incdec_operand" "")
6033            (const_string "incdec")
6034            (const_string "alu"))))
6035    (set_attr "mode" "QI,QI,SI,SI")])
6037 (define_insn "*addqi_1"
6038   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
6039         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
6040                  (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
6041    (clobber (reg:CC FLAGS_REG))]
6042   "TARGET_PARTIAL_REG_STALL
6043    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6045   int widen = (which_alternative == 2);
6046   switch (get_attr_type (insn))
6047     {
6048     case TYPE_INCDEC:
6049       if (operands[2] == const1_rtx)
6050         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6051       else if (operands[2] == constm1_rtx)
6052         return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6053       abort();
6055     default:
6056       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6057          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6058       if (GET_CODE (operands[2]) == CONST_INT
6059           && (INTVAL (operands[2]) == 128
6060               || (INTVAL (operands[2]) < 0
6061                   && INTVAL (operands[2]) != -128)))
6062         {
6063           operands[2] = GEN_INT (-INTVAL (operands[2]));
6064           if (widen)
6065             return "sub{l}\t{%2, %k0|%k0, %2}";
6066           else
6067             return "sub{b}\t{%2, %0|%0, %2}";
6068         }
6069       if (widen)
6070         return "add{l}\t{%k2, %k0|%k0, %k2}";
6071       else
6072         return "add{b}\t{%2, %0|%0, %2}";
6073     }
6075   [(set (attr "type")
6076      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6077         (const_string "incdec")
6078         (const_string "alu")))
6079    (set_attr "mode" "QI,QI,SI")])
6081 (define_insn "*addqi_1_slp"
6082   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6083         (plus:QI (match_dup 0)
6084                  (match_operand:QI 1 "general_operand" "qn,qnm")))
6085    (clobber (reg:CC FLAGS_REG))]
6086   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6087    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
6089   switch (get_attr_type (insn))
6090     {
6091     case TYPE_INCDEC:
6092       if (operands[1] == const1_rtx)
6093         return "inc{b}\t%0";
6094       else if (operands[1] == constm1_rtx)
6095         return "dec{b}\t%0";
6096       abort();
6098     default:
6099       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.  */
6100       if (GET_CODE (operands[1]) == CONST_INT
6101           && INTVAL (operands[1]) < 0)
6102         {
6103           operands[1] = GEN_INT (-INTVAL (operands[1]));
6104           return "sub{b}\t{%1, %0|%0, %1}";
6105         }
6106       return "add{b}\t{%1, %0|%0, %1}";
6107     }
6109   [(set (attr "type")
6110      (if_then_else (match_operand:QI 1 "incdec_operand" "")
6111         (const_string "incdec")
6112         (const_string "alu1")))
6113    (set (attr "memory")
6114      (if_then_else (match_operand 1 "memory_operand" "")
6115         (const_string "load")
6116         (const_string "none")))
6117    (set_attr "mode" "QI")])
6119 (define_insn "*addqi_2"
6120   [(set (reg FLAGS_REG)
6121         (compare
6122           (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
6123                    (match_operand:QI 2 "general_operand" "qmni,qni"))
6124           (const_int 0)))
6125    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
6126         (plus:QI (match_dup 1) (match_dup 2)))]
6127   "ix86_match_ccmode (insn, CCGOCmode)
6128    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6130   switch (get_attr_type (insn))
6131     {
6132     case TYPE_INCDEC:
6133       if (operands[2] == const1_rtx)
6134         return "inc{b}\t%0";
6135       else if (operands[2] == constm1_rtx
6136                || (GET_CODE (operands[2]) == CONST_INT
6137                    && INTVAL (operands[2]) == 255))
6138         return "dec{b}\t%0";
6139       abort();
6141     default:
6142       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
6143       if (GET_CODE (operands[2]) == CONST_INT
6144           && INTVAL (operands[2]) < 0)
6145         {
6146           operands[2] = GEN_INT (-INTVAL (operands[2]));
6147           return "sub{b}\t{%2, %0|%0, %2}";
6148         }
6149       return "add{b}\t{%2, %0|%0, %2}";
6150     }
6152   [(set (attr "type")
6153      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6154         (const_string "incdec")
6155         (const_string "alu")))
6156    (set_attr "mode" "QI")])
6158 (define_insn "*addqi_3"
6159   [(set (reg FLAGS_REG)
6160         (compare (neg:QI (match_operand:QI 2 "general_operand" "qmni"))
6161                  (match_operand:QI 1 "nonimmediate_operand" "%0")))
6162    (clobber (match_scratch:QI 0 "=q"))]
6163   "ix86_match_ccmode (insn, CCZmode)
6164    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6166   switch (get_attr_type (insn))
6167     {
6168     case TYPE_INCDEC:
6169       if (operands[2] == const1_rtx)
6170         return "inc{b}\t%0";
6171       else if (operands[2] == constm1_rtx
6172                || (GET_CODE (operands[2]) == CONST_INT
6173                    && INTVAL (operands[2]) == 255))
6174         return "dec{b}\t%0";
6175       abort();
6177     default:
6178       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
6179       if (GET_CODE (operands[2]) == CONST_INT
6180           && INTVAL (operands[2]) < 0)
6181         {
6182           operands[2] = GEN_INT (-INTVAL (operands[2]));
6183           return "sub{b}\t{%2, %0|%0, %2}";
6184         }
6185       return "add{b}\t{%2, %0|%0, %2}";
6186     }
6188   [(set (attr "type")
6189      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6190         (const_string "incdec")
6191         (const_string "alu")))
6192    (set_attr "mode" "QI")])
6194 ; See comments above addsi_4 for details.
6195 (define_insn "*addqi_4"
6196   [(set (reg FLAGS_REG)
6197         (compare (match_operand:QI 1 "nonimmediate_operand" "0")
6198                  (match_operand:QI 2 "const_int_operand" "n")))
6199    (clobber (match_scratch:QI 0 "=qm"))]
6200   "ix86_match_ccmode (insn, CCGCmode)
6201    && (INTVAL (operands[2]) & 0xff) != 0x80"
6203   switch (get_attr_type (insn))
6204     {
6205     case TYPE_INCDEC:
6206       if (operands[2] == constm1_rtx
6207           || (GET_CODE (operands[2]) == CONST_INT
6208               && INTVAL (operands[2]) == 255))
6209         return "inc{b}\t%0";
6210       else if (operands[2] == const1_rtx)
6211         return "dec{b}\t%0";
6212       else
6213         abort();
6215     default:
6216       if (! rtx_equal_p (operands[0], operands[1]))
6217         abort ();
6218       if (INTVAL (operands[2]) < 0)
6219         {
6220           operands[2] = GEN_INT (-INTVAL (operands[2]));
6221           return "add{b}\t{%2, %0|%0, %2}";
6222         }
6223       return "sub{b}\t{%2, %0|%0, %2}";
6224     }
6226   [(set (attr "type")
6227      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6228         (const_string "incdec")
6229         (const_string "alu")))
6230    (set_attr "mode" "QI")])
6233 (define_insn "*addqi_5"
6234   [(set (reg FLAGS_REG)
6235         (compare
6236           (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6237                    (match_operand:QI 2 "general_operand" "qmni"))
6238           (const_int 0)))
6239    (clobber (match_scratch:QI 0 "=q"))]
6240   "ix86_match_ccmode (insn, CCGOCmode)
6241    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6243   switch (get_attr_type (insn))
6244     {
6245     case TYPE_INCDEC:
6246       if (operands[2] == const1_rtx)
6247         return "inc{b}\t%0";
6248       else if (operands[2] == constm1_rtx
6249                || (GET_CODE (operands[2]) == CONST_INT
6250                    && INTVAL (operands[2]) == 255))
6251         return "dec{b}\t%0";
6252       abort();
6254     default:
6255       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
6256       if (GET_CODE (operands[2]) == CONST_INT
6257           && INTVAL (operands[2]) < 0)
6258         {
6259           operands[2] = GEN_INT (-INTVAL (operands[2]));
6260           return "sub{b}\t{%2, %0|%0, %2}";
6261         }
6262       return "add{b}\t{%2, %0|%0, %2}";
6263     }
6265   [(set (attr "type")
6266      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6267         (const_string "incdec")
6268         (const_string "alu")))
6269    (set_attr "mode" "QI")])
6272 (define_insn "addqi_ext_1"
6273   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6274                          (const_int 8)
6275                          (const_int 8))
6276         (plus:SI
6277           (zero_extract:SI
6278             (match_operand 1 "ext_register_operand" "0")
6279             (const_int 8)
6280             (const_int 8))
6281           (match_operand:QI 2 "general_operand" "Qmn")))
6282    (clobber (reg:CC FLAGS_REG))]
6283   "!TARGET_64BIT"
6285   switch (get_attr_type (insn))
6286     {
6287     case TYPE_INCDEC:
6288       if (operands[2] == const1_rtx)
6289         return "inc{b}\t%h0";
6290       else if (operands[2] == constm1_rtx
6291                || (GET_CODE (operands[2]) == CONST_INT
6292                    && INTVAL (operands[2]) == 255))
6293         return "dec{b}\t%h0";
6294       abort();
6296     default:
6297       return "add{b}\t{%2, %h0|%h0, %2}";
6298     }
6300   [(set (attr "type")
6301      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6302         (const_string "incdec")
6303         (const_string "alu")))
6304    (set_attr "mode" "QI")])
6306 (define_insn "*addqi_ext_1_rex64"
6307   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6308                          (const_int 8)
6309                          (const_int 8))
6310         (plus:SI
6311           (zero_extract:SI
6312             (match_operand 1 "ext_register_operand" "0")
6313             (const_int 8)
6314             (const_int 8))
6315           (match_operand:QI 2 "nonmemory_operand" "Qn")))
6316    (clobber (reg:CC FLAGS_REG))]
6317   "TARGET_64BIT"
6319   switch (get_attr_type (insn))
6320     {
6321     case TYPE_INCDEC:
6322       if (operands[2] == const1_rtx)
6323         return "inc{b}\t%h0";
6324       else if (operands[2] == constm1_rtx
6325                || (GET_CODE (operands[2]) == CONST_INT
6326                    && INTVAL (operands[2]) == 255))
6327         return "dec{b}\t%h0";
6328       abort();
6330     default:
6331       return "add{b}\t{%2, %h0|%h0, %2}";
6332     }
6334   [(set (attr "type")
6335      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6336         (const_string "incdec")
6337         (const_string "alu")))
6338    (set_attr "mode" "QI")])
6340 (define_insn "*addqi_ext_2"
6341   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6342                          (const_int 8)
6343                          (const_int 8))
6344         (plus:SI
6345           (zero_extract:SI
6346             (match_operand 1 "ext_register_operand" "%0")
6347             (const_int 8)
6348             (const_int 8))
6349           (zero_extract:SI
6350             (match_operand 2 "ext_register_operand" "Q")
6351             (const_int 8)
6352             (const_int 8))))
6353    (clobber (reg:CC FLAGS_REG))]
6354   ""
6355   "add{b}\t{%h2, %h0|%h0, %h2}"
6356   [(set_attr "type" "alu")
6357    (set_attr "mode" "QI")])
6359 ;; The patterns that match these are at the end of this file.
6361 (define_expand "addxf3"
6362   [(set (match_operand:XF 0 "register_operand" "")
6363         (plus:XF (match_operand:XF 1 "register_operand" "")
6364                  (match_operand:XF 2 "register_operand" "")))]
6365   "TARGET_80387"
6366   "")
6368 (define_expand "adddf3"
6369   [(set (match_operand:DF 0 "register_operand" "")
6370         (plus:DF (match_operand:DF 1 "register_operand" "")
6371                  (match_operand:DF 2 "nonimmediate_operand" "")))]
6372   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
6373   "")
6375 (define_expand "addsf3"
6376   [(set (match_operand:SF 0 "register_operand" "")
6377         (plus:SF (match_operand:SF 1 "register_operand" "")
6378                  (match_operand:SF 2 "nonimmediate_operand" "")))]
6379   "TARGET_80387 || TARGET_SSE_MATH"
6380   "")
6382 ;; Subtract instructions
6384 ;; %%% splits for subsidi3
6386 (define_expand "subdi3"
6387   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
6388                    (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6389                              (match_operand:DI 2 "x86_64_general_operand" "")))
6390               (clobber (reg:CC FLAGS_REG))])]
6391   ""
6392   "ix86_expand_binary_operator (MINUS, DImode, operands); DONE;")
6394 (define_insn "*subdi3_1"
6395   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
6396         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6397                   (match_operand:DI 2 "general_operand" "roiF,riF")))
6398    (clobber (reg:CC FLAGS_REG))]
6399   "!TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6400   "#")
6402 (define_split
6403   [(set (match_operand:DI 0 "nonimmediate_operand" "")
6404         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6405                   (match_operand:DI 2 "general_operand" "")))
6406    (clobber (reg:CC FLAGS_REG))]
6407   "!TARGET_64BIT && reload_completed"
6408   [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
6409               (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 2)))])
6410    (parallel [(set (match_dup 3)
6411                    (minus:SI (match_dup 4)
6412                              (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
6413                                       (match_dup 5))))
6414               (clobber (reg:CC FLAGS_REG))])]
6415   "split_di (operands+0, 1, operands+0, operands+3);
6416    split_di (operands+1, 1, operands+1, operands+4);
6417    split_di (operands+2, 1, operands+2, operands+5);")
6419 (define_insn "subdi3_carry_rex64"
6420   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6421           (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6422             (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
6423                (match_operand:DI 2 "x86_64_general_operand" "re,rm"))))
6424    (clobber (reg:CC FLAGS_REG))]
6425   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6426   "sbb{q}\t{%2, %0|%0, %2}"
6427   [(set_attr "type" "alu")
6428    (set_attr "pent_pair" "pu")
6429    (set_attr "mode" "DI")])
6431 (define_insn "*subdi_1_rex64"
6432   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6433         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6434                   (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6435    (clobber (reg:CC FLAGS_REG))]
6436   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6437   "sub{q}\t{%2, %0|%0, %2}"
6438   [(set_attr "type" "alu")
6439    (set_attr "mode" "DI")])
6441 (define_insn "*subdi_2_rex64"
6442   [(set (reg FLAGS_REG)
6443         (compare
6444           (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6445                     (match_operand:DI 2 "x86_64_general_operand" "re,rm"))
6446           (const_int 0)))
6447    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6448         (minus:DI (match_dup 1) (match_dup 2)))]
6449   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6450    && ix86_binary_operator_ok (MINUS, DImode, operands)"
6451   "sub{q}\t{%2, %0|%0, %2}"
6452   [(set_attr "type" "alu")
6453    (set_attr "mode" "DI")])
6455 (define_insn "*subdi_3_rex63"
6456   [(set (reg FLAGS_REG)
6457         (compare (match_operand:DI 1 "nonimmediate_operand" "0,0")
6458                  (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6459    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6460         (minus:DI (match_dup 1) (match_dup 2)))]
6461   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6462    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6463   "sub{q}\t{%2, %0|%0, %2}"
6464   [(set_attr "type" "alu")
6465    (set_attr "mode" "DI")])
6467 (define_insn "subqi3_carry"
6468   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6469           (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6470             (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
6471                (match_operand:QI 2 "general_operand" "qi,qm"))))
6472    (clobber (reg:CC FLAGS_REG))]
6473   "ix86_binary_operator_ok (MINUS, QImode, operands)"
6474   "sbb{b}\t{%2, %0|%0, %2}"
6475   [(set_attr "type" "alu")
6476    (set_attr "pent_pair" "pu")
6477    (set_attr "mode" "QI")])
6479 (define_insn "subhi3_carry"
6480   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6481           (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6482             (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
6483                (match_operand:HI 2 "general_operand" "ri,rm"))))
6484    (clobber (reg:CC FLAGS_REG))]
6485   "ix86_binary_operator_ok (MINUS, HImode, operands)"
6486   "sbb{w}\t{%2, %0|%0, %2}"
6487   [(set_attr "type" "alu")
6488    (set_attr "pent_pair" "pu")
6489    (set_attr "mode" "HI")])
6491 (define_insn "subsi3_carry"
6492   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6493           (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6494             (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6495                (match_operand:SI 2 "general_operand" "ri,rm"))))
6496    (clobber (reg:CC FLAGS_REG))]
6497   "ix86_binary_operator_ok (MINUS, SImode, operands)"
6498   "sbb{l}\t{%2, %0|%0, %2}"
6499   [(set_attr "type" "alu")
6500    (set_attr "pent_pair" "pu")
6501    (set_attr "mode" "SI")])
6503 (define_insn "subsi3_carry_zext"
6504   [(set (match_operand:DI 0 "register_operand" "=rm,r")
6505           (zero_extend:DI
6506             (minus:SI (match_operand:SI 1 "register_operand" "0,0")
6507               (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6508                  (match_operand:SI 2 "general_operand" "ri,rm")))))
6509    (clobber (reg:CC FLAGS_REG))]
6510   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6511   "sbb{l}\t{%2, %k0|%k0, %2}"
6512   [(set_attr "type" "alu")
6513    (set_attr "pent_pair" "pu")
6514    (set_attr "mode" "SI")])
6516 (define_expand "subsi3"
6517   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
6518                    (minus:SI (match_operand:SI 1 "nonimmediate_operand" "")
6519                              (match_operand:SI 2 "general_operand" "")))
6520               (clobber (reg:CC FLAGS_REG))])]
6521   ""
6522   "ix86_expand_binary_operator (MINUS, SImode, operands); DONE;")
6524 (define_insn "*subsi_1"
6525   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6526         (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6527                   (match_operand:SI 2 "general_operand" "ri,rm")))
6528    (clobber (reg:CC FLAGS_REG))]
6529   "ix86_binary_operator_ok (MINUS, SImode, operands)"
6530   "sub{l}\t{%2, %0|%0, %2}"
6531   [(set_attr "type" "alu")
6532    (set_attr "mode" "SI")])
6534 (define_insn "*subsi_1_zext"
6535   [(set (match_operand:DI 0 "register_operand" "=r")
6536         (zero_extend:DI
6537           (minus:SI (match_operand:SI 1 "register_operand" "0")
6538                     (match_operand:SI 2 "general_operand" "rim"))))
6539    (clobber (reg:CC FLAGS_REG))]
6540   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6541   "sub{l}\t{%2, %k0|%k0, %2}"
6542   [(set_attr "type" "alu")
6543    (set_attr "mode" "SI")])
6545 (define_insn "*subsi_2"
6546   [(set (reg FLAGS_REG)
6547         (compare
6548           (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6549                     (match_operand:SI 2 "general_operand" "ri,rm"))
6550           (const_int 0)))
6551    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6552         (minus:SI (match_dup 1) (match_dup 2)))]
6553   "ix86_match_ccmode (insn, CCGOCmode)
6554    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6555   "sub{l}\t{%2, %0|%0, %2}"
6556   [(set_attr "type" "alu")
6557    (set_attr "mode" "SI")])
6559 (define_insn "*subsi_2_zext"
6560   [(set (reg FLAGS_REG)
6561         (compare
6562           (minus:SI (match_operand:SI 1 "register_operand" "0")
6563                     (match_operand:SI 2 "general_operand" "rim"))
6564           (const_int 0)))
6565    (set (match_operand:DI 0 "register_operand" "=r")
6566         (zero_extend:DI
6567           (minus:SI (match_dup 1)
6568                     (match_dup 2))))]
6569   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6570    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6571   "sub{l}\t{%2, %k0|%k0, %2}"
6572   [(set_attr "type" "alu")
6573    (set_attr "mode" "SI")])
6575 (define_insn "*subsi_3"
6576   [(set (reg FLAGS_REG)
6577         (compare (match_operand:SI 1 "nonimmediate_operand" "0,0")
6578                  (match_operand:SI 2 "general_operand" "ri,rm")))
6579    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6580         (minus:SI (match_dup 1) (match_dup 2)))]
6581   "ix86_match_ccmode (insn, CCmode)
6582    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6583   "sub{l}\t{%2, %0|%0, %2}"
6584   [(set_attr "type" "alu")
6585    (set_attr "mode" "SI")])
6587 (define_insn "*subsi_3_zext"
6588   [(set (reg FLAGS_REG)
6589         (compare (match_operand:SI 1 "register_operand" "0")
6590                  (match_operand:SI 2 "general_operand" "rim")))
6591    (set (match_operand:DI 0 "register_operand" "=r")
6592         (zero_extend:DI
6593           (minus:SI (match_dup 1)
6594                     (match_dup 2))))]
6595   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6596    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6597   "sub{q}\t{%2, %0|%0, %2}"
6598   [(set_attr "type" "alu")
6599    (set_attr "mode" "DI")])
6601 (define_expand "subhi3"
6602   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
6603                    (minus:HI (match_operand:HI 1 "nonimmediate_operand" "")
6604                              (match_operand:HI 2 "general_operand" "")))
6605               (clobber (reg:CC FLAGS_REG))])]
6606   "TARGET_HIMODE_MATH"
6607   "ix86_expand_binary_operator (MINUS, HImode, operands); DONE;")
6609 (define_insn "*subhi_1"
6610   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6611         (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6612                   (match_operand:HI 2 "general_operand" "ri,rm")))
6613    (clobber (reg:CC FLAGS_REG))]
6614   "ix86_binary_operator_ok (MINUS, HImode, operands)"
6615   "sub{w}\t{%2, %0|%0, %2}"
6616   [(set_attr "type" "alu")
6617    (set_attr "mode" "HI")])
6619 (define_insn "*subhi_2"
6620   [(set (reg FLAGS_REG)
6621         (compare
6622           (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6623                     (match_operand:HI 2 "general_operand" "ri,rm"))
6624           (const_int 0)))
6625    (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6626         (minus:HI (match_dup 1) (match_dup 2)))]
6627   "ix86_match_ccmode (insn, CCGOCmode)
6628    && ix86_binary_operator_ok (MINUS, HImode, operands)"
6629   "sub{w}\t{%2, %0|%0, %2}"
6630   [(set_attr "type" "alu")
6631    (set_attr "mode" "HI")])
6633 (define_insn "*subhi_3"
6634   [(set (reg FLAGS_REG)
6635         (compare (match_operand:HI 1 "nonimmediate_operand" "0,0")
6636                  (match_operand:HI 2 "general_operand" "ri,rm")))
6637    (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6638         (minus:HI (match_dup 1) (match_dup 2)))]
6639   "ix86_match_ccmode (insn, CCmode)
6640    && ix86_binary_operator_ok (MINUS, HImode, operands)"
6641   "sub{w}\t{%2, %0|%0, %2}"
6642   [(set_attr "type" "alu")
6643    (set_attr "mode" "HI")])
6645 (define_expand "subqi3"
6646   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6647                    (minus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6648                              (match_operand:QI 2 "general_operand" "")))
6649               (clobber (reg:CC FLAGS_REG))])]
6650   "TARGET_QIMODE_MATH"
6651   "ix86_expand_binary_operator (MINUS, QImode, operands); DONE;")
6653 (define_insn "*subqi_1"
6654   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6655         (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6656                   (match_operand:QI 2 "general_operand" "qn,qmn")))
6657    (clobber (reg:CC FLAGS_REG))]
6658   "ix86_binary_operator_ok (MINUS, QImode, operands)"
6659   "sub{b}\t{%2, %0|%0, %2}"
6660   [(set_attr "type" "alu")
6661    (set_attr "mode" "QI")])
6663 (define_insn "*subqi_1_slp"
6664   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6665         (minus:QI (match_dup 0)
6666                   (match_operand:QI 1 "general_operand" "qn,qmn")))
6667    (clobber (reg:CC FLAGS_REG))]
6668   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6669    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
6670   "sub{b}\t{%1, %0|%0, %1}"
6671   [(set_attr "type" "alu1")
6672    (set_attr "mode" "QI")])
6674 (define_insn "*subqi_2"
6675   [(set (reg FLAGS_REG)
6676         (compare
6677           (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6678                     (match_operand:QI 2 "general_operand" "qi,qm"))
6679           (const_int 0)))
6680    (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6681         (minus:HI (match_dup 1) (match_dup 2)))]
6682   "ix86_match_ccmode (insn, CCGOCmode)
6683    && ix86_binary_operator_ok (MINUS, QImode, operands)"
6684   "sub{b}\t{%2, %0|%0, %2}"
6685   [(set_attr "type" "alu")
6686    (set_attr "mode" "QI")])
6688 (define_insn "*subqi_3"
6689   [(set (reg FLAGS_REG)
6690         (compare (match_operand:QI 1 "nonimmediate_operand" "0,0")
6691                  (match_operand:QI 2 "general_operand" "qi,qm")))
6692    (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6693         (minus:HI (match_dup 1) (match_dup 2)))]
6694   "ix86_match_ccmode (insn, CCmode)
6695    && ix86_binary_operator_ok (MINUS, QImode, operands)"
6696   "sub{b}\t{%2, %0|%0, %2}"
6697   [(set_attr "type" "alu")
6698    (set_attr "mode" "QI")])
6700 ;; The patterns that match these are at the end of this file.
6702 (define_expand "subxf3"
6703   [(set (match_operand:XF 0 "register_operand" "")
6704         (minus:XF (match_operand:XF 1 "register_operand" "")
6705                   (match_operand:XF 2 "register_operand" "")))]
6706   "TARGET_80387"
6707   "")
6709 (define_expand "subdf3"
6710   [(set (match_operand:DF 0 "register_operand" "")
6711         (minus:DF (match_operand:DF 1 "register_operand" "")
6712                   (match_operand:DF 2 "nonimmediate_operand" "")))]
6713   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
6714   "")
6716 (define_expand "subsf3"
6717   [(set (match_operand:SF 0 "register_operand" "")
6718         (minus:SF (match_operand:SF 1 "register_operand" "")
6719                   (match_operand:SF 2 "nonimmediate_operand" "")))]
6720   "TARGET_80387 || TARGET_SSE_MATH"
6721   "")
6723 ;; Multiply instructions
6725 (define_expand "muldi3"
6726   [(parallel [(set (match_operand:DI 0 "register_operand" "")
6727                    (mult:DI (match_operand:DI 1 "register_operand" "")
6728                             (match_operand:DI 2 "x86_64_general_operand" "")))
6729               (clobber (reg:CC FLAGS_REG))])]
6730   "TARGET_64BIT"
6731   "")
6733 (define_insn "*muldi3_1_rex64"
6734   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6735         (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%rm,rm,0")
6736                  (match_operand:DI 2 "x86_64_general_operand" "K,e,mr")))
6737    (clobber (reg:CC FLAGS_REG))]
6738   "TARGET_64BIT
6739    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6740   "@
6741    imul{q}\t{%2, %1, %0|%0, %1, %2}
6742    imul{q}\t{%2, %1, %0|%0, %1, %2}
6743    imul{q}\t{%2, %0|%0, %2}"
6744   [(set_attr "type" "imul")
6745    (set_attr "prefix_0f" "0,0,1")
6746    (set (attr "athlon_decode")
6747         (cond [(eq_attr "cpu" "athlon")
6748                   (const_string "vector")
6749                (eq_attr "alternative" "1")
6750                   (const_string "vector")
6751                (and (eq_attr "alternative" "2")
6752                     (match_operand 1 "memory_operand" ""))
6753                   (const_string "vector")]
6754               (const_string "direct")))
6755    (set_attr "mode" "DI")])
6757 (define_expand "mulsi3"
6758   [(parallel [(set (match_operand:SI 0 "register_operand" "")
6759                    (mult:SI (match_operand:SI 1 "register_operand" "")
6760                             (match_operand:SI 2 "general_operand" "")))
6761               (clobber (reg:CC FLAGS_REG))])]
6762   ""
6763   "")
6765 (define_insn "*mulsi3_1"
6766   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
6767         (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6768                  (match_operand:SI 2 "general_operand" "K,i,mr")))
6769    (clobber (reg:CC FLAGS_REG))]
6770   "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6771   "@
6772    imul{l}\t{%2, %1, %0|%0, %1, %2}
6773    imul{l}\t{%2, %1, %0|%0, %1, %2}
6774    imul{l}\t{%2, %0|%0, %2}"
6775   [(set_attr "type" "imul")
6776    (set_attr "prefix_0f" "0,0,1")
6777    (set (attr "athlon_decode")
6778         (cond [(eq_attr "cpu" "athlon")
6779                   (const_string "vector")
6780                (eq_attr "alternative" "1")
6781                   (const_string "vector")
6782                (and (eq_attr "alternative" "2")
6783                     (match_operand 1 "memory_operand" ""))
6784                   (const_string "vector")]
6785               (const_string "direct")))
6786    (set_attr "mode" "SI")])
6788 (define_insn "*mulsi3_1_zext"
6789   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6790         (zero_extend:DI
6791           (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6792                    (match_operand:SI 2 "general_operand" "K,i,mr"))))
6793    (clobber (reg:CC FLAGS_REG))]
6794   "TARGET_64BIT
6795    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6796   "@
6797    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6798    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6799    imul{l}\t{%2, %k0|%k0, %2}"
6800   [(set_attr "type" "imul")
6801    (set_attr "prefix_0f" "0,0,1")
6802    (set (attr "athlon_decode")
6803         (cond [(eq_attr "cpu" "athlon")
6804                   (const_string "vector")
6805                (eq_attr "alternative" "1")
6806                   (const_string "vector")
6807                (and (eq_attr "alternative" "2")
6808                     (match_operand 1 "memory_operand" ""))
6809                   (const_string "vector")]
6810               (const_string "direct")))
6811    (set_attr "mode" "SI")])
6813 (define_expand "mulhi3"
6814   [(parallel [(set (match_operand:HI 0 "register_operand" "")
6815                    (mult:HI (match_operand:HI 1 "register_operand" "")
6816                             (match_operand:HI 2 "general_operand" "")))
6817               (clobber (reg:CC FLAGS_REG))])]
6818   "TARGET_HIMODE_MATH"
6819   "")
6821 (define_insn "*mulhi3_1"
6822   [(set (match_operand:HI 0 "register_operand" "=r,r,r")
6823         (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
6824                  (match_operand:HI 2 "general_operand" "K,i,mr")))
6825    (clobber (reg:CC FLAGS_REG))]
6826   "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6827   "@
6828    imul{w}\t{%2, %1, %0|%0, %1, %2}
6829    imul{w}\t{%2, %1, %0|%0, %1, %2}
6830    imul{w}\t{%2, %0|%0, %2}"
6831   [(set_attr "type" "imul")
6832    (set_attr "prefix_0f" "0,0,1")
6833    (set (attr "athlon_decode")
6834         (cond [(eq_attr "cpu" "athlon")
6835                   (const_string "vector")
6836                (eq_attr "alternative" "1,2")
6837                   (const_string "vector")]
6838               (const_string "direct")))
6839    (set_attr "mode" "HI")])
6841 (define_expand "mulqi3"
6842   [(parallel [(set (match_operand:QI 0 "register_operand" "")
6843                    (mult:QI (match_operand:QI 1 "nonimmediate_operand" "")
6844                             (match_operand:QI 2 "register_operand" "")))
6845               (clobber (reg:CC FLAGS_REG))])]
6846   "TARGET_QIMODE_MATH"
6847   "")
6849 (define_insn "*mulqi3_1"
6850   [(set (match_operand:QI 0 "register_operand" "=a")
6851         (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6852                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
6853    (clobber (reg:CC FLAGS_REG))]
6854   "TARGET_QIMODE_MATH
6855    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6856   "mul{b}\t%2"
6857   [(set_attr "type" "imul")
6858    (set_attr "length_immediate" "0")
6859    (set (attr "athlon_decode")
6860      (if_then_else (eq_attr "cpu" "athlon")
6861         (const_string "vector")
6862         (const_string "direct")))
6863    (set_attr "mode" "QI")])
6865 (define_expand "umulqihi3"
6866   [(parallel [(set (match_operand:HI 0 "register_operand" "")
6867                    (mult:HI (zero_extend:HI
6868                               (match_operand:QI 1 "nonimmediate_operand" ""))
6869                             (zero_extend:HI
6870                               (match_operand:QI 2 "register_operand" ""))))
6871               (clobber (reg:CC FLAGS_REG))])]
6872   "TARGET_QIMODE_MATH"
6873   "")
6875 (define_insn "*umulqihi3_1"
6876   [(set (match_operand:HI 0 "register_operand" "=a")
6877         (mult:HI (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
6878                  (zero_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6879    (clobber (reg:CC FLAGS_REG))]
6880   "TARGET_QIMODE_MATH
6881    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6882   "mul{b}\t%2"
6883   [(set_attr "type" "imul")
6884    (set_attr "length_immediate" "0")
6885    (set (attr "athlon_decode")
6886      (if_then_else (eq_attr "cpu" "athlon")
6887         (const_string "vector")
6888         (const_string "direct")))
6889    (set_attr "mode" "QI")])
6891 (define_expand "mulqihi3"
6892   [(parallel [(set (match_operand:HI 0 "register_operand" "")
6893                    (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))
6894                             (sign_extend:HI (match_operand:QI 2 "register_operand" ""))))
6895               (clobber (reg:CC FLAGS_REG))])]
6896   "TARGET_QIMODE_MATH"
6897   "")
6899 (define_insn "*mulqihi3_insn"
6900   [(set (match_operand:HI 0 "register_operand" "=a")
6901         (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
6902                  (sign_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6903    (clobber (reg:CC FLAGS_REG))]
6904   "TARGET_QIMODE_MATH
6905    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6906   "imul{b}\t%2"
6907   [(set_attr "type" "imul")
6908    (set_attr "length_immediate" "0")
6909    (set (attr "athlon_decode")
6910      (if_then_else (eq_attr "cpu" "athlon")
6911         (const_string "vector")
6912         (const_string "direct")))
6913    (set_attr "mode" "QI")])
6915 (define_expand "umulditi3"
6916   [(parallel [(set (match_operand:TI 0 "register_operand" "")
6917                    (mult:TI (zero_extend:TI
6918                               (match_operand:DI 1 "nonimmediate_operand" ""))
6919                             (zero_extend:TI
6920                               (match_operand:DI 2 "register_operand" ""))))
6921               (clobber (reg:CC FLAGS_REG))])]
6922   "TARGET_64BIT"
6923   "")
6925 (define_insn "*umulditi3_insn"
6926   [(set (match_operand:TI 0 "register_operand" "=A")
6927         (mult:TI (zero_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
6928                  (zero_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
6929    (clobber (reg:CC FLAGS_REG))]
6930   "TARGET_64BIT
6931    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6932   "mul{q}\t%2"
6933   [(set_attr "type" "imul")
6934    (set_attr "length_immediate" "0")
6935    (set (attr "athlon_decode")
6936      (if_then_else (eq_attr "cpu" "athlon")
6937         (const_string "vector")
6938         (const_string "double")))
6939    (set_attr "mode" "DI")])
6941 ;; We can't use this pattern in 64bit mode, since it results in two separate 32bit registers
6942 (define_expand "umulsidi3"
6943   [(parallel [(set (match_operand:DI 0 "register_operand" "")
6944                    (mult:DI (zero_extend:DI
6945                               (match_operand:SI 1 "nonimmediate_operand" ""))
6946                             (zero_extend:DI
6947                               (match_operand:SI 2 "register_operand" ""))))
6948               (clobber (reg:CC FLAGS_REG))])]
6949   "!TARGET_64BIT"
6950   "")
6952 (define_insn "*umulsidi3_insn"
6953   [(set (match_operand:DI 0 "register_operand" "=A")
6954         (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
6955                  (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
6956    (clobber (reg:CC FLAGS_REG))]
6957   "!TARGET_64BIT
6958    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6959   "mul{l}\t%2"
6960   [(set_attr "type" "imul")
6961    (set_attr "length_immediate" "0")
6962    (set (attr "athlon_decode")
6963      (if_then_else (eq_attr "cpu" "athlon")
6964         (const_string "vector")
6965         (const_string "double")))
6966    (set_attr "mode" "SI")])
6968 (define_expand "mulditi3"
6969   [(parallel [(set (match_operand:TI 0 "register_operand" "")
6970                    (mult:TI (sign_extend:TI
6971                               (match_operand:DI 1 "nonimmediate_operand" ""))
6972                             (sign_extend:TI
6973                               (match_operand:DI 2 "register_operand" ""))))
6974               (clobber (reg:CC FLAGS_REG))])]
6975   "TARGET_64BIT"
6976   "")
6978 (define_insn "*mulditi3_insn"
6979   [(set (match_operand:TI 0 "register_operand" "=A")
6980         (mult:TI (sign_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
6981                  (sign_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
6982    (clobber (reg:CC FLAGS_REG))]
6983   "TARGET_64BIT
6984    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6985   "imul{q}\t%2"
6986   [(set_attr "type" "imul")
6987    (set_attr "length_immediate" "0")
6988    (set (attr "athlon_decode")
6989      (if_then_else (eq_attr "cpu" "athlon")
6990         (const_string "vector")
6991         (const_string "double")))
6992    (set_attr "mode" "DI")])
6994 (define_expand "mulsidi3"
6995   [(parallel [(set (match_operand:DI 0 "register_operand" "")
6996                    (mult:DI (sign_extend:DI
6997                               (match_operand:SI 1 "nonimmediate_operand" ""))
6998                             (sign_extend:DI
6999                               (match_operand:SI 2 "register_operand" ""))))
7000               (clobber (reg:CC FLAGS_REG))])]
7001   "!TARGET_64BIT"
7002   "")
7004 (define_insn "*mulsidi3_insn"
7005   [(set (match_operand:DI 0 "register_operand" "=A")
7006         (mult:DI (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7007                  (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7008    (clobber (reg:CC FLAGS_REG))]
7009   "!TARGET_64BIT
7010    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7011   "imul{l}\t%2"
7012   [(set_attr "type" "imul")
7013    (set_attr "length_immediate" "0")
7014    (set (attr "athlon_decode")
7015      (if_then_else (eq_attr "cpu" "athlon")
7016         (const_string "vector")
7017         (const_string "double")))
7018    (set_attr "mode" "SI")])
7020 (define_expand "umuldi3_highpart"
7021   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7022                    (truncate:DI
7023                      (lshiftrt:TI
7024                        (mult:TI (zero_extend:TI
7025                                   (match_operand:DI 1 "nonimmediate_operand" ""))
7026                                 (zero_extend:TI
7027                                   (match_operand:DI 2 "register_operand" "")))
7028                        (const_int 64))))
7029               (clobber (match_scratch:DI 3 ""))
7030               (clobber (reg:CC FLAGS_REG))])]
7031   "TARGET_64BIT"
7032   "")
7034 (define_insn "*umuldi3_highpart_rex64"
7035   [(set (match_operand:DI 0 "register_operand" "=d")
7036         (truncate:DI
7037           (lshiftrt:TI
7038             (mult:TI (zero_extend:TI
7039                        (match_operand:DI 1 "nonimmediate_operand" "%a"))
7040                      (zero_extend:TI
7041                        (match_operand:DI 2 "nonimmediate_operand" "rm")))
7042             (const_int 64))))
7043    (clobber (match_scratch:DI 3 "=1"))
7044    (clobber (reg:CC FLAGS_REG))]
7045   "TARGET_64BIT
7046    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7047   "mul{q}\t%2"
7048   [(set_attr "type" "imul")
7049    (set_attr "length_immediate" "0")
7050    (set (attr "athlon_decode")
7051      (if_then_else (eq_attr "cpu" "athlon")
7052         (const_string "vector")
7053         (const_string "double")))
7054    (set_attr "mode" "DI")])
7056 (define_expand "umulsi3_highpart"
7057   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7058                    (truncate:SI
7059                      (lshiftrt:DI
7060                        (mult:DI (zero_extend:DI
7061                                   (match_operand:SI 1 "nonimmediate_operand" ""))
7062                                 (zero_extend:DI
7063                                   (match_operand:SI 2 "register_operand" "")))
7064                        (const_int 32))))
7065               (clobber (match_scratch:SI 3 ""))
7066               (clobber (reg:CC FLAGS_REG))])]
7067   ""
7068   "")
7070 (define_insn "*umulsi3_highpart_insn"
7071   [(set (match_operand:SI 0 "register_operand" "=d")
7072         (truncate:SI
7073           (lshiftrt:DI
7074             (mult:DI (zero_extend:DI
7075                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7076                      (zero_extend:DI
7077                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7078             (const_int 32))))
7079    (clobber (match_scratch:SI 3 "=1"))
7080    (clobber (reg:CC FLAGS_REG))]
7081   "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7082   "mul{l}\t%2"
7083   [(set_attr "type" "imul")
7084    (set_attr "length_immediate" "0")
7085    (set (attr "athlon_decode")
7086      (if_then_else (eq_attr "cpu" "athlon")
7087         (const_string "vector")
7088         (const_string "double")))
7089    (set_attr "mode" "SI")])
7091 (define_insn "*umulsi3_highpart_zext"
7092   [(set (match_operand:DI 0 "register_operand" "=d")
7093         (zero_extend:DI (truncate:SI
7094           (lshiftrt:DI
7095             (mult:DI (zero_extend:DI
7096                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7097                      (zero_extend:DI
7098                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7099             (const_int 32)))))
7100    (clobber (match_scratch:SI 3 "=1"))
7101    (clobber (reg:CC FLAGS_REG))]
7102   "TARGET_64BIT
7103    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7104   "mul{l}\t%2"
7105   [(set_attr "type" "imul")
7106    (set_attr "length_immediate" "0")
7107    (set (attr "athlon_decode")
7108      (if_then_else (eq_attr "cpu" "athlon")
7109         (const_string "vector")
7110         (const_string "double")))
7111    (set_attr "mode" "SI")])
7113 (define_expand "smuldi3_highpart"
7114   [(parallel [(set (match_operand:DI 0 "register_operand" "=d")
7115                    (truncate:DI
7116                      (lshiftrt:TI
7117                        (mult:TI (sign_extend:TI
7118                                   (match_operand:DI 1 "nonimmediate_operand" ""))
7119                                 (sign_extend:TI
7120                                   (match_operand:DI 2 "register_operand" "")))
7121                        (const_int 64))))
7122               (clobber (match_scratch:DI 3 ""))
7123               (clobber (reg:CC FLAGS_REG))])]
7124   "TARGET_64BIT"
7125   "")
7127 (define_insn "*smuldi3_highpart_rex64"
7128   [(set (match_operand:DI 0 "register_operand" "=d")
7129         (truncate:DI
7130           (lshiftrt:TI
7131             (mult:TI (sign_extend:TI
7132                        (match_operand:DI 1 "nonimmediate_operand" "%a"))
7133                      (sign_extend:TI
7134                        (match_operand:DI 2 "nonimmediate_operand" "rm")))
7135             (const_int 64))))
7136    (clobber (match_scratch:DI 3 "=1"))
7137    (clobber (reg:CC FLAGS_REG))]
7138   "TARGET_64BIT
7139    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7140   "imul{q}\t%2"
7141   [(set_attr "type" "imul")
7142    (set (attr "athlon_decode")
7143      (if_then_else (eq_attr "cpu" "athlon")
7144         (const_string "vector")
7145         (const_string "double")))
7146    (set_attr "mode" "DI")])
7148 (define_expand "smulsi3_highpart"
7149   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7150                    (truncate:SI
7151                      (lshiftrt:DI
7152                        (mult:DI (sign_extend:DI
7153                                   (match_operand:SI 1 "nonimmediate_operand" ""))
7154                                 (sign_extend:DI
7155                                   (match_operand:SI 2 "register_operand" "")))
7156                        (const_int 32))))
7157               (clobber (match_scratch:SI 3 ""))
7158               (clobber (reg:CC FLAGS_REG))])]
7159   ""
7160   "")
7162 (define_insn "*smulsi3_highpart_insn"
7163   [(set (match_operand:SI 0 "register_operand" "=d")
7164         (truncate:SI
7165           (lshiftrt:DI
7166             (mult:DI (sign_extend:DI
7167                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7168                      (sign_extend:DI
7169                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7170             (const_int 32))))
7171    (clobber (match_scratch:SI 3 "=1"))
7172    (clobber (reg:CC FLAGS_REG))]
7173   "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7174   "imul{l}\t%2"
7175   [(set_attr "type" "imul")
7176    (set (attr "athlon_decode")
7177      (if_then_else (eq_attr "cpu" "athlon")
7178         (const_string "vector")
7179         (const_string "double")))
7180    (set_attr "mode" "SI")])
7182 (define_insn "*smulsi3_highpart_zext"
7183   [(set (match_operand:DI 0 "register_operand" "=d")
7184         (zero_extend:DI (truncate:SI
7185           (lshiftrt:DI
7186             (mult:DI (sign_extend:DI
7187                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7188                      (sign_extend:DI
7189                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7190             (const_int 32)))))
7191    (clobber (match_scratch:SI 3 "=1"))
7192    (clobber (reg:CC FLAGS_REG))]
7193   "TARGET_64BIT
7194    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7195   "imul{l}\t%2"
7196   [(set_attr "type" "imul")
7197    (set (attr "athlon_decode")
7198      (if_then_else (eq_attr "cpu" "athlon")
7199         (const_string "vector")
7200         (const_string "double")))
7201    (set_attr "mode" "SI")])
7203 ;; The patterns that match these are at the end of this file.
7205 (define_expand "mulxf3"
7206   [(set (match_operand:XF 0 "register_operand" "")
7207         (mult:XF (match_operand:XF 1 "register_operand" "")
7208                  (match_operand:XF 2 "register_operand" "")))]
7209   "TARGET_80387"
7210   "")
7212 (define_expand "muldf3"
7213   [(set (match_operand:DF 0 "register_operand" "")
7214         (mult:DF (match_operand:DF 1 "register_operand" "")
7215                  (match_operand:DF 2 "nonimmediate_operand" "")))]
7216   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
7217   "")
7219 (define_expand "mulsf3"
7220   [(set (match_operand:SF 0 "register_operand" "")
7221         (mult:SF (match_operand:SF 1 "register_operand" "")
7222                  (match_operand:SF 2 "nonimmediate_operand" "")))]
7223   "TARGET_80387 || TARGET_SSE_MATH"
7224   "")
7226 ;; Divide instructions
7228 (define_insn "divqi3"
7229   [(set (match_operand:QI 0 "register_operand" "=a")
7230         (div:QI (match_operand:HI 1 "register_operand" "0")
7231                 (match_operand:QI 2 "nonimmediate_operand" "qm")))
7232    (clobber (reg:CC FLAGS_REG))]
7233   "TARGET_QIMODE_MATH"
7234   "idiv{b}\t%2"
7235   [(set_attr "type" "idiv")
7236    (set_attr "mode" "QI")])
7238 (define_insn "udivqi3"
7239   [(set (match_operand:QI 0 "register_operand" "=a")
7240         (udiv:QI (match_operand:HI 1 "register_operand" "0")
7241                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
7242    (clobber (reg:CC FLAGS_REG))]
7243   "TARGET_QIMODE_MATH"
7244   "div{b}\t%2"
7245   [(set_attr "type" "idiv")
7246    (set_attr "mode" "QI")])
7248 ;; The patterns that match these are at the end of this file.
7250 (define_expand "divxf3"
7251   [(set (match_operand:XF 0 "register_operand" "")
7252         (div:XF (match_operand:XF 1 "register_operand" "")
7253                 (match_operand:XF 2 "register_operand" "")))]
7254   "TARGET_80387"
7255   "")
7257 (define_expand "divdf3"
7258   [(set (match_operand:DF 0 "register_operand" "")
7259         (div:DF (match_operand:DF 1 "register_operand" "")
7260                 (match_operand:DF 2 "nonimmediate_operand" "")))]
7261    "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
7262    "")
7264 (define_expand "divsf3"
7265   [(set (match_operand:SF 0 "register_operand" "")
7266         (div:SF (match_operand:SF 1 "register_operand" "")
7267                 (match_operand:SF 2 "nonimmediate_operand" "")))]
7268   "TARGET_80387 || TARGET_SSE_MATH"
7269   "")
7271 ;; Remainder instructions.
7273 (define_expand "divmoddi4"
7274   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7275                    (div:DI (match_operand:DI 1 "register_operand" "")
7276                            (match_operand:DI 2 "nonimmediate_operand" "")))
7277               (set (match_operand:DI 3 "register_operand" "")
7278                    (mod:DI (match_dup 1) (match_dup 2)))
7279               (clobber (reg:CC FLAGS_REG))])]
7280   "TARGET_64BIT"
7281   "")
7283 ;; Allow to come the parameter in eax or edx to avoid extra moves.
7284 ;; Penalize eax case slightly because it results in worse scheduling
7285 ;; of code.
7286 (define_insn "*divmoddi4_nocltd_rex64"
7287   [(set (match_operand:DI 0 "register_operand" "=&a,?a")
7288         (div:DI (match_operand:DI 2 "register_operand" "1,0")
7289                 (match_operand:DI 3 "nonimmediate_operand" "rm,rm")))
7290    (set (match_operand:DI 1 "register_operand" "=&d,&d")
7291         (mod:DI (match_dup 2) (match_dup 3)))
7292    (clobber (reg:CC FLAGS_REG))]
7293   "TARGET_64BIT && !optimize_size && !TARGET_USE_CLTD"
7294   "#"
7295   [(set_attr "type" "multi")])
7297 (define_insn "*divmoddi4_cltd_rex64"
7298   [(set (match_operand:DI 0 "register_operand" "=a")
7299         (div:DI (match_operand:DI 2 "register_operand" "a")
7300                 (match_operand:DI 3 "nonimmediate_operand" "rm")))
7301    (set (match_operand:DI 1 "register_operand" "=&d")
7302         (mod:DI (match_dup 2) (match_dup 3)))
7303    (clobber (reg:CC FLAGS_REG))]
7304   "TARGET_64BIT && (optimize_size || TARGET_USE_CLTD)"
7305   "#"
7306   [(set_attr "type" "multi")])
7308 (define_insn "*divmoddi_noext_rex64"
7309   [(set (match_operand:DI 0 "register_operand" "=a")
7310         (div:DI (match_operand:DI 1 "register_operand" "0")
7311                 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7312    (set (match_operand:DI 3 "register_operand" "=d")
7313         (mod:DI (match_dup 1) (match_dup 2)))
7314    (use (match_operand:DI 4 "register_operand" "3"))
7315    (clobber (reg:CC FLAGS_REG))]
7316   "TARGET_64BIT"
7317   "idiv{q}\t%2"
7318   [(set_attr "type" "idiv")
7319    (set_attr "mode" "DI")])
7321 (define_split
7322   [(set (match_operand:DI 0 "register_operand" "")
7323         (div:DI (match_operand:DI 1 "register_operand" "")
7324                 (match_operand:DI 2 "nonimmediate_operand" "")))
7325    (set (match_operand:DI 3 "register_operand" "")
7326         (mod:DI (match_dup 1) (match_dup 2)))
7327    (clobber (reg:CC FLAGS_REG))]
7328   "TARGET_64BIT && reload_completed"
7329   [(parallel [(set (match_dup 3)
7330                    (ashiftrt:DI (match_dup 4) (const_int 63)))
7331               (clobber (reg:CC FLAGS_REG))])
7332    (parallel [(set (match_dup 0)
7333                    (div:DI (reg:DI 0) (match_dup 2)))
7334               (set (match_dup 3)
7335                    (mod:DI (reg:DI 0) (match_dup 2)))
7336               (use (match_dup 3))
7337               (clobber (reg:CC FLAGS_REG))])]
7339   /* Avoid use of cltd in favor of a mov+shift.  */
7340   if (!TARGET_USE_CLTD && !optimize_size)
7341     {
7342       if (true_regnum (operands[1]))
7343         emit_move_insn (operands[0], operands[1]);
7344       else
7345         emit_move_insn (operands[3], operands[1]);
7346       operands[4] = operands[3];
7347     }
7348   else
7349     {
7350       if (true_regnum (operands[1]))
7351         abort();
7352       operands[4] = operands[1];
7353     }
7357 (define_expand "divmodsi4"
7358   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7359                    (div:SI (match_operand:SI 1 "register_operand" "")
7360                            (match_operand:SI 2 "nonimmediate_operand" "")))
7361               (set (match_operand:SI 3 "register_operand" "")
7362                    (mod:SI (match_dup 1) (match_dup 2)))
7363               (clobber (reg:CC FLAGS_REG))])]
7364   ""
7365   "")
7367 ;; Allow to come the parameter in eax or edx to avoid extra moves.
7368 ;; Penalize eax case slightly because it results in worse scheduling
7369 ;; of code.
7370 (define_insn "*divmodsi4_nocltd"
7371   [(set (match_operand:SI 0 "register_operand" "=&a,?a")
7372         (div:SI (match_operand:SI 2 "register_operand" "1,0")
7373                 (match_operand:SI 3 "nonimmediate_operand" "rm,rm")))
7374    (set (match_operand:SI 1 "register_operand" "=&d,&d")
7375         (mod:SI (match_dup 2) (match_dup 3)))
7376    (clobber (reg:CC FLAGS_REG))]
7377   "!optimize_size && !TARGET_USE_CLTD"
7378   "#"
7379   [(set_attr "type" "multi")])
7381 (define_insn "*divmodsi4_cltd"
7382   [(set (match_operand:SI 0 "register_operand" "=a")
7383         (div:SI (match_operand:SI 2 "register_operand" "a")
7384                 (match_operand:SI 3 "nonimmediate_operand" "rm")))
7385    (set (match_operand:SI 1 "register_operand" "=&d")
7386         (mod:SI (match_dup 2) (match_dup 3)))
7387    (clobber (reg:CC FLAGS_REG))]
7388   "optimize_size || TARGET_USE_CLTD"
7389   "#"
7390   [(set_attr "type" "multi")])
7392 (define_insn "*divmodsi_noext"
7393   [(set (match_operand:SI 0 "register_operand" "=a")
7394         (div:SI (match_operand:SI 1 "register_operand" "0")
7395                 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7396    (set (match_operand:SI 3 "register_operand" "=d")
7397         (mod:SI (match_dup 1) (match_dup 2)))
7398    (use (match_operand:SI 4 "register_operand" "3"))
7399    (clobber (reg:CC FLAGS_REG))]
7400   ""
7401   "idiv{l}\t%2"
7402   [(set_attr "type" "idiv")
7403    (set_attr "mode" "SI")])
7405 (define_split
7406   [(set (match_operand:SI 0 "register_operand" "")
7407         (div:SI (match_operand:SI 1 "register_operand" "")
7408                 (match_operand:SI 2 "nonimmediate_operand" "")))
7409    (set (match_operand:SI 3 "register_operand" "")
7410         (mod:SI (match_dup 1) (match_dup 2)))
7411    (clobber (reg:CC FLAGS_REG))]
7412   "reload_completed"
7413   [(parallel [(set (match_dup 3)
7414                    (ashiftrt:SI (match_dup 4) (const_int 31)))
7415               (clobber (reg:CC FLAGS_REG))])
7416    (parallel [(set (match_dup 0)
7417                    (div:SI (reg:SI 0) (match_dup 2)))
7418               (set (match_dup 3)
7419                    (mod:SI (reg:SI 0) (match_dup 2)))
7420               (use (match_dup 3))
7421               (clobber (reg:CC FLAGS_REG))])]
7423   /* Avoid use of cltd in favor of a mov+shift.  */
7424   if (!TARGET_USE_CLTD && !optimize_size)
7425     {
7426       if (true_regnum (operands[1]))
7427         emit_move_insn (operands[0], operands[1]);
7428       else
7429         emit_move_insn (operands[3], operands[1]);
7430       operands[4] = operands[3];
7431     }
7432   else
7433     {
7434       if (true_regnum (operands[1]))
7435         abort();
7436       operands[4] = operands[1];
7437     }
7439 ;; %%% Split me.
7440 (define_insn "divmodhi4"
7441   [(set (match_operand:HI 0 "register_operand" "=a")
7442         (div:HI (match_operand:HI 1 "register_operand" "0")
7443                 (match_operand:HI 2 "nonimmediate_operand" "rm")))
7444    (set (match_operand:HI 3 "register_operand" "=&d")
7445         (mod:HI (match_dup 1) (match_dup 2)))
7446    (clobber (reg:CC FLAGS_REG))]
7447   "TARGET_HIMODE_MATH"
7448   "cwtd\;idiv{w}\t%2"
7449   [(set_attr "type" "multi")
7450    (set_attr "length_immediate" "0")
7451    (set_attr "mode" "SI")])
7453 (define_insn "udivmoddi4"
7454   [(set (match_operand:DI 0 "register_operand" "=a")
7455         (udiv:DI (match_operand:DI 1 "register_operand" "0")
7456                  (match_operand:DI 2 "nonimmediate_operand" "rm")))
7457    (set (match_operand:DI 3 "register_operand" "=&d")
7458         (umod:DI (match_dup 1) (match_dup 2)))
7459    (clobber (reg:CC FLAGS_REG))]
7460   "TARGET_64BIT"
7461   "xor{q}\t%3, %3\;div{q}\t%2"
7462   [(set_attr "type" "multi")
7463    (set_attr "length_immediate" "0")
7464    (set_attr "mode" "DI")])
7466 (define_insn "*udivmoddi4_noext"
7467   [(set (match_operand:DI 0 "register_operand" "=a")
7468         (udiv:DI (match_operand:DI 1 "register_operand" "0")
7469                  (match_operand:DI 2 "nonimmediate_operand" "rm")))
7470    (set (match_operand:DI 3 "register_operand" "=d")
7471         (umod:DI (match_dup 1) (match_dup 2)))
7472    (use (match_dup 3))
7473    (clobber (reg:CC FLAGS_REG))]
7474   "TARGET_64BIT"
7475   "div{q}\t%2"
7476   [(set_attr "type" "idiv")
7477    (set_attr "mode" "DI")])
7479 (define_split
7480   [(set (match_operand:DI 0 "register_operand" "")
7481         (udiv:DI (match_operand:DI 1 "register_operand" "")
7482                  (match_operand:DI 2 "nonimmediate_operand" "")))
7483    (set (match_operand:DI 3 "register_operand" "")
7484         (umod:DI (match_dup 1) (match_dup 2)))
7485    (clobber (reg:CC FLAGS_REG))]
7486   "TARGET_64BIT && reload_completed"
7487   [(set (match_dup 3) (const_int 0))
7488    (parallel [(set (match_dup 0)
7489                    (udiv:DI (match_dup 1) (match_dup 2)))
7490               (set (match_dup 3)
7491                    (umod:DI (match_dup 1) (match_dup 2)))
7492               (use (match_dup 3))
7493               (clobber (reg:CC FLAGS_REG))])]
7494   "")
7496 (define_insn "udivmodsi4"
7497   [(set (match_operand:SI 0 "register_operand" "=a")
7498         (udiv:SI (match_operand:SI 1 "register_operand" "0")
7499                  (match_operand:SI 2 "nonimmediate_operand" "rm")))
7500    (set (match_operand:SI 3 "register_operand" "=&d")
7501         (umod:SI (match_dup 1) (match_dup 2)))
7502    (clobber (reg:CC FLAGS_REG))]
7503   ""
7504   "xor{l}\t%3, %3\;div{l}\t%2"
7505   [(set_attr "type" "multi")
7506    (set_attr "length_immediate" "0")
7507    (set_attr "mode" "SI")])
7509 (define_insn "*udivmodsi4_noext"
7510   [(set (match_operand:SI 0 "register_operand" "=a")
7511         (udiv:SI (match_operand:SI 1 "register_operand" "0")
7512                  (match_operand:SI 2 "nonimmediate_operand" "rm")))
7513    (set (match_operand:SI 3 "register_operand" "=d")
7514         (umod:SI (match_dup 1) (match_dup 2)))
7515    (use (match_dup 3))
7516    (clobber (reg:CC FLAGS_REG))]
7517   ""
7518   "div{l}\t%2"
7519   [(set_attr "type" "idiv")
7520    (set_attr "mode" "SI")])
7522 (define_split
7523   [(set (match_operand:SI 0 "register_operand" "")
7524         (udiv:SI (match_operand:SI 1 "register_operand" "")
7525                  (match_operand:SI 2 "nonimmediate_operand" "")))
7526    (set (match_operand:SI 3 "register_operand" "")
7527         (umod:SI (match_dup 1) (match_dup 2)))
7528    (clobber (reg:CC FLAGS_REG))]
7529   "reload_completed"
7530   [(set (match_dup 3) (const_int 0))
7531    (parallel [(set (match_dup 0)
7532                    (udiv:SI (match_dup 1) (match_dup 2)))
7533               (set (match_dup 3)
7534                    (umod:SI (match_dup 1) (match_dup 2)))
7535               (use (match_dup 3))
7536               (clobber (reg:CC FLAGS_REG))])]
7537   "")
7539 (define_expand "udivmodhi4"
7540   [(set (match_dup 4) (const_int 0))
7541    (parallel [(set (match_operand:HI 0 "register_operand" "")
7542                    (udiv:HI (match_operand:HI 1 "register_operand" "")
7543                             (match_operand:HI 2 "nonimmediate_operand" "")))
7544               (set (match_operand:HI 3 "register_operand" "")
7545                    (umod:HI (match_dup 1) (match_dup 2)))
7546               (use (match_dup 4))
7547               (clobber (reg:CC FLAGS_REG))])]
7548   "TARGET_HIMODE_MATH"
7549   "operands[4] = gen_reg_rtx (HImode);")
7551 (define_insn "*udivmodhi_noext"
7552   [(set (match_operand:HI 0 "register_operand" "=a")
7553         (udiv:HI (match_operand:HI 1 "register_operand" "0")
7554                  (match_operand:HI 2 "nonimmediate_operand" "rm")))
7555    (set (match_operand:HI 3 "register_operand" "=d")
7556         (umod:HI (match_dup 1) (match_dup 2)))
7557    (use (match_operand:HI 4 "register_operand" "3"))
7558    (clobber (reg:CC FLAGS_REG))]
7559   ""
7560   "div{w}\t%2"
7561   [(set_attr "type" "idiv")
7562    (set_attr "mode" "HI")])
7564 ;; We cannot use div/idiv for double division, because it causes
7565 ;; "division by zero" on the overflow and that's not what we expect
7566 ;; from truncate.  Because true (non truncating) double division is
7567 ;; never generated, we can't create this insn anyway.
7569 ;(define_insn ""
7570 ;  [(set (match_operand:SI 0 "register_operand" "=a")
7571 ;       (truncate:SI
7572 ;         (udiv:DI (match_operand:DI 1 "register_operand" "A")
7573 ;                  (zero_extend:DI
7574 ;                    (match_operand:SI 2 "nonimmediate_operand" "rm")))))
7575 ;   (set (match_operand:SI 3 "register_operand" "=d")
7576 ;       (truncate:SI
7577 ;         (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
7578 ;   (clobber (reg:CC FLAGS_REG))]
7579 ;  ""
7580 ;  "div{l}\t{%2, %0|%0, %2}"
7581 ;  [(set_attr "type" "idiv")])
7583 ;;- Logical AND instructions
7585 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
7586 ;; Note that this excludes ah.
7588 (define_insn "*testdi_1_rex64"
7589   [(set (reg FLAGS_REG)
7590         (compare
7591           (and:DI (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
7592                   (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
7593           (const_int 0)))]
7594   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7595    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7596   "@
7597    test{l}\t{%k1, %k0|%k0, %k1}
7598    test{l}\t{%k1, %k0|%k0, %k1}
7599    test{q}\t{%1, %0|%0, %1}
7600    test{q}\t{%1, %0|%0, %1}
7601    test{q}\t{%1, %0|%0, %1}"
7602   [(set_attr "type" "test")
7603    (set_attr "modrm" "0,1,0,1,1")
7604    (set_attr "mode" "SI,SI,DI,DI,DI")
7605    (set_attr "pent_pair" "uv,np,uv,np,uv")])
7607 (define_insn "testsi_1"
7608   [(set (reg FLAGS_REG)
7609         (compare
7610           (and:SI (match_operand:SI 0 "nonimmediate_operand" "%!*a,r,rm")
7611                   (match_operand:SI 1 "general_operand" "in,in,rin"))
7612           (const_int 0)))]
7613   "ix86_match_ccmode (insn, CCNOmode)
7614    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7615   "test{l}\t{%1, %0|%0, %1}"
7616   [(set_attr "type" "test")
7617    (set_attr "modrm" "0,1,1")
7618    (set_attr "mode" "SI")
7619    (set_attr "pent_pair" "uv,np,uv")])
7621 (define_expand "testsi_ccno_1"
7622   [(set (reg:CCNO FLAGS_REG)
7623         (compare:CCNO
7624           (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
7625                   (match_operand:SI 1 "nonmemory_operand" ""))
7626           (const_int 0)))]
7627   ""
7628   "")
7630 (define_insn "*testhi_1"
7631   [(set (reg FLAGS_REG)
7632         (compare (and:HI (match_operand:HI 0 "nonimmediate_operand" "%!*a,r,rm")
7633                          (match_operand:HI 1 "general_operand" "n,n,rn"))
7634                  (const_int 0)))]
7635   "ix86_match_ccmode (insn, CCNOmode)
7636    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7637   "test{w}\t{%1, %0|%0, %1}"
7638   [(set_attr "type" "test")
7639    (set_attr "modrm" "0,1,1")
7640    (set_attr "mode" "HI")
7641    (set_attr "pent_pair" "uv,np,uv")])
7643 (define_expand "testqi_ccz_1"
7644   [(set (reg:CCZ FLAGS_REG)
7645         (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
7646                              (match_operand:QI 1 "nonmemory_operand" ""))
7647                  (const_int 0)))]
7648   ""
7649   "")
7651 (define_insn "*testqi_1_maybe_si"
7652   [(set (reg FLAGS_REG)
7653         (compare
7654           (and:QI
7655             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
7656             (match_operand:QI 1 "general_operand" "n,n,qn,n"))
7657           (const_int 0)))]
7658    "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
7659     && ix86_match_ccmode (insn,
7660                          GET_CODE (operands[1]) == CONST_INT
7661                          && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
7663   if (which_alternative == 3)
7664     {
7665       if (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) < 0)
7666         operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
7667       return "test{l}\t{%1, %k0|%k0, %1}";
7668     }
7669   return "test{b}\t{%1, %0|%0, %1}";
7671   [(set_attr "type" "test")
7672    (set_attr "modrm" "0,1,1,1")
7673    (set_attr "mode" "QI,QI,QI,SI")
7674    (set_attr "pent_pair" "uv,np,uv,np")])
7676 (define_insn "*testqi_1"
7677   [(set (reg FLAGS_REG)
7678         (compare
7679           (and:QI
7680             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm")
7681             (match_operand:QI 1 "general_operand" "n,n,qn"))
7682           (const_int 0)))]
7683   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
7684    && ix86_match_ccmode (insn, CCNOmode)"
7685   "test{b}\t{%1, %0|%0, %1}"
7686   [(set_attr "type" "test")
7687    (set_attr "modrm" "0,1,1")
7688    (set_attr "mode" "QI")
7689    (set_attr "pent_pair" "uv,np,uv")])
7691 (define_expand "testqi_ext_ccno_0"
7692   [(set (reg:CCNO FLAGS_REG)
7693         (compare:CCNO
7694           (and:SI
7695             (zero_extract:SI
7696               (match_operand 0 "ext_register_operand" "")
7697               (const_int 8)
7698               (const_int 8))
7699             (match_operand 1 "const_int_operand" ""))
7700           (const_int 0)))]
7701   ""
7702   "")
7704 (define_insn "*testqi_ext_0"
7705   [(set (reg FLAGS_REG)
7706         (compare
7707           (and:SI
7708             (zero_extract:SI
7709               (match_operand 0 "ext_register_operand" "Q")
7710               (const_int 8)
7711               (const_int 8))
7712             (match_operand 1 "const_int_operand" "n"))
7713           (const_int 0)))]
7714   "ix86_match_ccmode (insn, CCNOmode)"
7715   "test{b}\t{%1, %h0|%h0, %1}"
7716   [(set_attr "type" "test")
7717    (set_attr "mode" "QI")
7718    (set_attr "length_immediate" "1")
7719    (set_attr "pent_pair" "np")])
7721 (define_insn "*testqi_ext_1"
7722   [(set (reg FLAGS_REG)
7723         (compare
7724           (and:SI
7725             (zero_extract:SI
7726               (match_operand 0 "ext_register_operand" "Q")
7727               (const_int 8)
7728               (const_int 8))
7729             (zero_extend:SI
7730               (match_operand:QI 1 "general_operand" "Qm")))
7731           (const_int 0)))]
7732   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7733    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7734   "test{b}\t{%1, %h0|%h0, %1}"
7735   [(set_attr "type" "test")
7736    (set_attr "mode" "QI")])
7738 (define_insn "*testqi_ext_1_rex64"
7739   [(set (reg FLAGS_REG)
7740         (compare
7741           (and:SI
7742             (zero_extract:SI
7743               (match_operand 0 "ext_register_operand" "Q")
7744               (const_int 8)
7745               (const_int 8))
7746             (zero_extend:SI
7747               (match_operand:QI 1 "register_operand" "Q")))
7748           (const_int 0)))]
7749   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7750   "test{b}\t{%1, %h0|%h0, %1}"
7751   [(set_attr "type" "test")
7752    (set_attr "mode" "QI")])
7754 (define_insn "*testqi_ext_2"
7755   [(set (reg FLAGS_REG)
7756         (compare
7757           (and:SI
7758             (zero_extract:SI
7759               (match_operand 0 "ext_register_operand" "Q")
7760               (const_int 8)
7761               (const_int 8))
7762             (zero_extract:SI
7763               (match_operand 1 "ext_register_operand" "Q")
7764               (const_int 8)
7765               (const_int 8)))
7766           (const_int 0)))]
7767   "ix86_match_ccmode (insn, CCNOmode)"
7768   "test{b}\t{%h1, %h0|%h0, %h1}"
7769   [(set_attr "type" "test")
7770    (set_attr "mode" "QI")])
7772 ;; Combine likes to form bit extractions for some tests.  Humor it.
7773 (define_insn "*testqi_ext_3"
7774   [(set (reg FLAGS_REG)
7775         (compare (zero_extract:SI
7776                    (match_operand 0 "nonimmediate_operand" "rm")
7777                    (match_operand:SI 1 "const_int_operand" "")
7778                    (match_operand:SI 2 "const_int_operand" ""))
7779                  (const_int 0)))]
7780   "ix86_match_ccmode (insn, CCNOmode)
7781    && (GET_MODE (operands[0]) == SImode
7782        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
7783        || GET_MODE (operands[0]) == HImode
7784        || GET_MODE (operands[0]) == QImode)"
7785   "#")
7787 (define_insn "*testqi_ext_3_rex64"
7788   [(set (reg FLAGS_REG)
7789         (compare (zero_extract:DI
7790                    (match_operand 0 "nonimmediate_operand" "rm")
7791                    (match_operand:DI 1 "const_int_operand" "")
7792                    (match_operand:DI 2 "const_int_operand" ""))
7793                  (const_int 0)))]
7794   "TARGET_64BIT
7795    && ix86_match_ccmode (insn, CCNOmode)
7796    /* The code below cannot deal with constants outside HOST_WIDE_INT.  */
7797    && INTVAL (operands[1]) + INTVAL (operands[2]) < HOST_BITS_PER_WIDE_INT
7798    /* Ensure that resulting mask is zero or sign extended operand.  */
7799    && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7800        || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
7801            && INTVAL (operands[1]) > 32))
7802    && (GET_MODE (operands[0]) == SImode
7803        || GET_MODE (operands[0]) == DImode
7804        || GET_MODE (operands[0]) == HImode
7805        || GET_MODE (operands[0]) == QImode)"
7806   "#")
7808 (define_split
7809   [(set (match_operand 0 "flags_reg_operand" "")
7810         (match_operator 1 "compare_operator"
7811           [(zero_extract
7812              (match_operand 2 "nonimmediate_operand" "")
7813              (match_operand 3 "const_int_operand" "")
7814              (match_operand 4 "const_int_operand" ""))
7815            (const_int 0)]))]
7816   "ix86_match_ccmode (insn, CCNOmode)"
7817   [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
7819   rtx val = operands[2];
7820   HOST_WIDE_INT len = INTVAL (operands[3]);
7821   HOST_WIDE_INT pos = INTVAL (operands[4]);
7822   HOST_WIDE_INT mask;
7823   enum machine_mode mode, submode;
7825   mode = GET_MODE (val);
7826   if (GET_CODE (val) == MEM)
7827     {
7828       /* ??? Combine likes to put non-volatile mem extractions in QImode
7829          no matter the size of the test.  So find a mode that works.  */
7830       if (! MEM_VOLATILE_P (val))
7831         {
7832           mode = smallest_mode_for_size (pos + len, MODE_INT);
7833           val = adjust_address (val, mode, 0);
7834         }
7835     }
7836   else if (GET_CODE (val) == SUBREG
7837            && (submode = GET_MODE (SUBREG_REG (val)),
7838                GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
7839            && pos + len <= GET_MODE_BITSIZE (submode))
7840     {
7841       /* Narrow a paradoxical subreg to prevent partial register stalls.  */
7842       mode = submode;
7843       val = SUBREG_REG (val);
7844     }
7845   else if (mode == HImode && pos + len <= 8)
7846     {
7847       /* Small HImode tests can be converted to QImode.  */
7848       mode = QImode;
7849       val = gen_lowpart (QImode, val);
7850     }
7852   mask  = ((HOST_WIDE_INT)1 << (pos + len)) - 1;
7853   mask &= ~(((HOST_WIDE_INT)1 << pos) - 1);
7855   operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
7858 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
7859 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
7860 ;; this is relatively important trick.
7861 ;; Do the conversion only post-reload to avoid limiting of the register class
7862 ;; to QI regs.
7863 (define_split
7864   [(set (match_operand 0 "flags_reg_operand" "")
7865         (match_operator 1 "compare_operator"
7866           [(and (match_operand 2 "register_operand" "")
7867                 (match_operand 3 "const_int_operand" ""))
7868            (const_int 0)]))]
7869    "reload_completed
7870     && QI_REG_P (operands[2])
7871     && GET_MODE (operands[2]) != QImode
7872     && ((ix86_match_ccmode (insn, CCZmode)
7873          && !(INTVAL (operands[3]) & ~(255 << 8)))
7874         || (ix86_match_ccmode (insn, CCNOmode)
7875             && !(INTVAL (operands[3]) & ~(127 << 8))))"
7876   [(set (match_dup 0)
7877         (match_op_dup 1
7878           [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
7879                    (match_dup 3))
7880            (const_int 0)]))]
7881   "operands[2] = gen_lowpart (SImode, operands[2]);
7882    operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);")
7884 (define_split
7885   [(set (match_operand 0 "flags_reg_operand" "")
7886         (match_operator 1 "compare_operator"
7887           [(and (match_operand 2 "nonimmediate_operand" "")
7888                 (match_operand 3 "const_int_operand" ""))
7889            (const_int 0)]))]
7890    "reload_completed
7891     && GET_MODE (operands[2]) != QImode
7892     && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
7893     && ((ix86_match_ccmode (insn, CCZmode)
7894          && !(INTVAL (operands[3]) & ~255))
7895         || (ix86_match_ccmode (insn, CCNOmode)
7896             && !(INTVAL (operands[3]) & ~127)))"
7897   [(set (match_dup 0)
7898         (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
7899                          (const_int 0)]))]
7900   "operands[2] = gen_lowpart (QImode, operands[2]);
7901    operands[3] = gen_lowpart (QImode, operands[3]);")
7904 ;; %%% This used to optimize known byte-wide and operations to memory,
7905 ;; and sometimes to QImode registers.  If this is considered useful,
7906 ;; it should be done with splitters.
7908 (define_expand "anddi3"
7909   [(set (match_operand:DI 0 "nonimmediate_operand" "")
7910         (and:DI (match_operand:DI 1 "nonimmediate_operand" "")
7911                 (match_operand:DI 2 "x86_64_szext_general_operand" "")))
7912    (clobber (reg:CC FLAGS_REG))]
7913   "TARGET_64BIT"
7914   "ix86_expand_binary_operator (AND, DImode, operands); DONE;")
7916 (define_insn "*anddi_1_rex64"
7917   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
7918         (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
7919                 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
7920    (clobber (reg:CC FLAGS_REG))]
7921   "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
7923   switch (get_attr_type (insn))
7924     {
7925     case TYPE_IMOVX:
7926       {
7927         enum machine_mode mode;
7929         if (GET_CODE (operands[2]) != CONST_INT)
7930           abort ();
7931         if (INTVAL (operands[2]) == 0xff)
7932           mode = QImode;
7933         else if (INTVAL (operands[2]) == 0xffff)
7934           mode = HImode;
7935         else
7936           abort ();
7937         
7938         operands[1] = gen_lowpart (mode, operands[1]);
7939         if (mode == QImode)
7940           return "movz{bq|x}\t{%1,%0|%0, %1}";
7941         else
7942           return "movz{wq|x}\t{%1,%0|%0, %1}";
7943       }
7945     default:
7946       if (! rtx_equal_p (operands[0], operands[1]))
7947         abort ();
7948       if (get_attr_mode (insn) == MODE_SI)
7949         return "and{l}\t{%k2, %k0|%k0, %k2}";
7950       else
7951         return "and{q}\t{%2, %0|%0, %2}";
7952     }
7954   [(set_attr "type" "alu,alu,alu,imovx")
7955    (set_attr "length_immediate" "*,*,*,0")
7956    (set_attr "mode" "SI,DI,DI,DI")])
7958 (define_insn "*anddi_2"
7959   [(set (reg FLAGS_REG)
7960         (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
7961                          (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
7962                  (const_int 0)))
7963    (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
7964         (and:DI (match_dup 1) (match_dup 2)))]
7965   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7966    && ix86_binary_operator_ok (AND, DImode, operands)"
7967   "@
7968    and{l}\t{%k2, %k0|%k0, %k2}
7969    and{q}\t{%2, %0|%0, %2}
7970    and{q}\t{%2, %0|%0, %2}"
7971   [(set_attr "type" "alu")
7972    (set_attr "mode" "SI,DI,DI")])
7974 (define_expand "andsi3"
7975   [(set (match_operand:SI 0 "nonimmediate_operand" "")
7976         (and:SI (match_operand:SI 1 "nonimmediate_operand" "")
7977                 (match_operand:SI 2 "general_operand" "")))
7978    (clobber (reg:CC FLAGS_REG))]
7979   ""
7980   "ix86_expand_binary_operator (AND, SImode, operands); DONE;")
7982 (define_insn "*andsi_1"
7983   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
7984         (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
7985                 (match_operand:SI 2 "general_operand" "ri,rm,L")))
7986    (clobber (reg:CC FLAGS_REG))]
7987   "ix86_binary_operator_ok (AND, SImode, operands)"
7989   switch (get_attr_type (insn))
7990     {
7991     case TYPE_IMOVX:
7992       {
7993         enum machine_mode mode;
7995         if (GET_CODE (operands[2]) != CONST_INT)
7996           abort ();
7997         if (INTVAL (operands[2]) == 0xff)
7998           mode = QImode;
7999         else if (INTVAL (operands[2]) == 0xffff)
8000           mode = HImode;
8001         else
8002           abort ();
8003         
8004         operands[1] = gen_lowpart (mode, operands[1]);
8005         if (mode == QImode)
8006           return "movz{bl|x}\t{%1,%0|%0, %1}";
8007         else
8008           return "movz{wl|x}\t{%1,%0|%0, %1}";
8009       }
8011     default:
8012       if (! rtx_equal_p (operands[0], operands[1]))
8013         abort ();
8014       return "and{l}\t{%2, %0|%0, %2}";
8015     }
8017   [(set_attr "type" "alu,alu,imovx")
8018    (set_attr "length_immediate" "*,*,0")
8019    (set_attr "mode" "SI")])
8021 (define_split
8022   [(set (match_operand 0 "register_operand" "")
8023         (and (match_dup 0)
8024              (const_int -65536)))
8025    (clobber (reg:CC FLAGS_REG))]
8026   "optimize_size || (TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)"
8027   [(set (strict_low_part (match_dup 1)) (const_int 0))]
8028   "operands[1] = gen_lowpart (HImode, operands[0]);")
8030 (define_split
8031   [(set (match_operand 0 "ext_register_operand" "")
8032         (and (match_dup 0)
8033              (const_int -256)))
8034    (clobber (reg:CC FLAGS_REG))]
8035   "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8036   [(set (strict_low_part (match_dup 1)) (const_int 0))]
8037   "operands[1] = gen_lowpart (QImode, operands[0]);")
8039 (define_split
8040   [(set (match_operand 0 "ext_register_operand" "")
8041         (and (match_dup 0)
8042              (const_int -65281)))
8043    (clobber (reg:CC FLAGS_REG))]
8044   "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8045   [(parallel [(set (zero_extract:SI (match_dup 0)
8046                                     (const_int 8)
8047                                     (const_int 8))
8048                    (xor:SI 
8049                      (zero_extract:SI (match_dup 0)
8050                                       (const_int 8)
8051                                       (const_int 8))
8052                      (zero_extract:SI (match_dup 0)
8053                                       (const_int 8)
8054                                       (const_int 8))))
8055               (clobber (reg:CC FLAGS_REG))])]
8056   "operands[0] = gen_lowpart (SImode, operands[0]);")
8058 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8059 (define_insn "*andsi_1_zext"
8060   [(set (match_operand:DI 0 "register_operand" "=r")
8061         (zero_extend:DI
8062           (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8063                   (match_operand:SI 2 "general_operand" "rim"))))
8064    (clobber (reg:CC FLAGS_REG))]
8065   "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
8066   "and{l}\t{%2, %k0|%k0, %2}"
8067   [(set_attr "type" "alu")
8068    (set_attr "mode" "SI")])
8070 (define_insn "*andsi_2"
8071   [(set (reg FLAGS_REG)
8072         (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8073                          (match_operand:SI 2 "general_operand" "rim,ri"))
8074                  (const_int 0)))
8075    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8076         (and:SI (match_dup 1) (match_dup 2)))]
8077   "ix86_match_ccmode (insn, CCNOmode)
8078    && ix86_binary_operator_ok (AND, SImode, operands)"
8079   "and{l}\t{%2, %0|%0, %2}"
8080   [(set_attr "type" "alu")
8081    (set_attr "mode" "SI")])
8083 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8084 (define_insn "*andsi_2_zext"
8085   [(set (reg FLAGS_REG)
8086         (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8087                          (match_operand:SI 2 "general_operand" "rim"))
8088                  (const_int 0)))
8089    (set (match_operand:DI 0 "register_operand" "=r")
8090         (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
8091   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8092    && ix86_binary_operator_ok (AND, SImode, operands)"
8093   "and{l}\t{%2, %k0|%k0, %2}"
8094   [(set_attr "type" "alu")
8095    (set_attr "mode" "SI")])
8097 (define_expand "andhi3"
8098   [(set (match_operand:HI 0 "nonimmediate_operand" "")
8099         (and:HI (match_operand:HI 1 "nonimmediate_operand" "")
8100                 (match_operand:HI 2 "general_operand" "")))
8101    (clobber (reg:CC FLAGS_REG))]
8102   "TARGET_HIMODE_MATH"
8103   "ix86_expand_binary_operator (AND, HImode, operands); DONE;")
8105 (define_insn "*andhi_1"
8106   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
8107         (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
8108                 (match_operand:HI 2 "general_operand" "ri,rm,L")))
8109    (clobber (reg:CC FLAGS_REG))]
8110   "ix86_binary_operator_ok (AND, HImode, operands)"
8112   switch (get_attr_type (insn))
8113     {
8114     case TYPE_IMOVX:
8115       if (GET_CODE (operands[2]) != CONST_INT)
8116         abort ();
8117       if (INTVAL (operands[2]) == 0xff)
8118         return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
8119       abort ();
8121     default:
8122       if (! rtx_equal_p (operands[0], operands[1]))
8123         abort ();
8125       return "and{w}\t{%2, %0|%0, %2}";
8126     }
8128   [(set_attr "type" "alu,alu,imovx")
8129    (set_attr "length_immediate" "*,*,0")
8130    (set_attr "mode" "HI,HI,SI")])
8132 (define_insn "*andhi_2"
8133   [(set (reg FLAGS_REG)
8134         (compare (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8135                          (match_operand:HI 2 "general_operand" "rim,ri"))
8136                  (const_int 0)))
8137    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8138         (and:HI (match_dup 1) (match_dup 2)))]
8139   "ix86_match_ccmode (insn, CCNOmode)
8140    && ix86_binary_operator_ok (AND, HImode, operands)"
8141   "and{w}\t{%2, %0|%0, %2}"
8142   [(set_attr "type" "alu")
8143    (set_attr "mode" "HI")])
8145 (define_expand "andqi3"
8146   [(set (match_operand:QI 0 "nonimmediate_operand" "")
8147         (and:QI (match_operand:QI 1 "nonimmediate_operand" "")
8148                 (match_operand:QI 2 "general_operand" "")))
8149    (clobber (reg:CC FLAGS_REG))]
8150   "TARGET_QIMODE_MATH"
8151   "ix86_expand_binary_operator (AND, QImode, operands); DONE;")
8153 ;; %%% Potential partial reg stall on alternative 2.  What to do?
8154 (define_insn "*andqi_1"
8155   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
8156         (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8157                 (match_operand:QI 2 "general_operand" "qi,qmi,ri")))
8158    (clobber (reg:CC FLAGS_REG))]
8159   "ix86_binary_operator_ok (AND, QImode, operands)"
8160   "@
8161    and{b}\t{%2, %0|%0, %2}
8162    and{b}\t{%2, %0|%0, %2}
8163    and{l}\t{%k2, %k0|%k0, %k2}"
8164   [(set_attr "type" "alu")
8165    (set_attr "mode" "QI,QI,SI")])
8167 (define_insn "*andqi_1_slp"
8168   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
8169         (and:QI (match_dup 0)
8170                 (match_operand:QI 1 "general_operand" "qi,qmi")))
8171    (clobber (reg:CC FLAGS_REG))]
8172   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8173    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8174   "and{b}\t{%1, %0|%0, %1}"
8175   [(set_attr "type" "alu1")
8176    (set_attr "mode" "QI")])
8178 (define_insn "*andqi_2_maybe_si"
8179   [(set (reg FLAGS_REG)
8180         (compare (and:QI
8181                       (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8182                       (match_operand:QI 2 "general_operand" "qim,qi,i"))
8183                  (const_int 0)))
8184    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
8185         (and:QI (match_dup 1) (match_dup 2)))]
8186   "ix86_binary_operator_ok (AND, QImode, operands)
8187    && ix86_match_ccmode (insn,
8188                          GET_CODE (operands[2]) == CONST_INT
8189                          && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
8191   if (which_alternative == 2)
8192     {
8193       if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
8194         operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
8195       return "and{l}\t{%2, %k0|%k0, %2}";
8196     }
8197   return "and{b}\t{%2, %0|%0, %2}";
8199   [(set_attr "type" "alu")
8200    (set_attr "mode" "QI,QI,SI")])
8202 (define_insn "*andqi_2"
8203   [(set (reg FLAGS_REG)
8204         (compare (and:QI
8205                    (match_operand:QI 1 "nonimmediate_operand" "%0,0")
8206                    (match_operand:QI 2 "general_operand" "qim,qi"))
8207                  (const_int 0)))
8208    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
8209         (and:QI (match_dup 1) (match_dup 2)))]
8210   "ix86_match_ccmode (insn, CCNOmode)
8211    && ix86_binary_operator_ok (AND, QImode, operands)"
8212   "and{b}\t{%2, %0|%0, %2}"
8213   [(set_attr "type" "alu")
8214    (set_attr "mode" "QI")])
8216 (define_insn "*andqi_2_slp"
8217   [(set (reg FLAGS_REG)
8218         (compare (and:QI
8219                    (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8220                    (match_operand:QI 1 "nonimmediate_operand" "qmi,qi"))
8221                  (const_int 0)))
8222    (set (strict_low_part (match_dup 0))
8223         (and:QI (match_dup 0) (match_dup 1)))]
8224   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8225    && ix86_match_ccmode (insn, CCNOmode)
8226    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8227   "and{b}\t{%1, %0|%0, %1}"
8228   [(set_attr "type" "alu1")
8229    (set_attr "mode" "QI")])
8231 ;; ??? A bug in recog prevents it from recognizing a const_int as an
8232 ;; operand to zero_extend in andqi_ext_1.  It was checking explicitly
8233 ;; for a QImode operand, which of course failed.
8235 (define_insn "andqi_ext_0"
8236   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8237                          (const_int 8)
8238                          (const_int 8))
8239         (and:SI 
8240           (zero_extract:SI
8241             (match_operand 1 "ext_register_operand" "0")
8242             (const_int 8)
8243             (const_int 8))
8244           (match_operand 2 "const_int_operand" "n")))
8245    (clobber (reg:CC FLAGS_REG))]
8246   ""
8247   "and{b}\t{%2, %h0|%h0, %2}"
8248   [(set_attr "type" "alu")
8249    (set_attr "length_immediate" "1")
8250    (set_attr "mode" "QI")])
8252 ;; Generated by peephole translating test to and.  This shows up
8253 ;; often in fp comparisons.
8255 (define_insn "*andqi_ext_0_cc"
8256   [(set (reg FLAGS_REG)
8257         (compare
8258           (and:SI
8259             (zero_extract:SI
8260               (match_operand 1 "ext_register_operand" "0")
8261               (const_int 8)
8262               (const_int 8))
8263             (match_operand 2 "const_int_operand" "n"))
8264           (const_int 0)))
8265    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8266                          (const_int 8)
8267                          (const_int 8))
8268         (and:SI 
8269           (zero_extract:SI
8270             (match_dup 1)
8271             (const_int 8)
8272             (const_int 8))
8273           (match_dup 2)))]
8274   "ix86_match_ccmode (insn, CCNOmode)"
8275   "and{b}\t{%2, %h0|%h0, %2}"
8276   [(set_attr "type" "alu")
8277    (set_attr "length_immediate" "1")
8278    (set_attr "mode" "QI")])
8280 (define_insn "*andqi_ext_1"
8281   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8282                          (const_int 8)
8283                          (const_int 8))
8284         (and:SI 
8285           (zero_extract:SI
8286             (match_operand 1 "ext_register_operand" "0")
8287             (const_int 8)
8288             (const_int 8))
8289           (zero_extend:SI
8290             (match_operand:QI 2 "general_operand" "Qm"))))
8291    (clobber (reg:CC FLAGS_REG))]
8292   "!TARGET_64BIT"
8293   "and{b}\t{%2, %h0|%h0, %2}"
8294   [(set_attr "type" "alu")
8295    (set_attr "length_immediate" "0")
8296    (set_attr "mode" "QI")])
8298 (define_insn "*andqi_ext_1_rex64"
8299   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8300                          (const_int 8)
8301                          (const_int 8))
8302         (and:SI 
8303           (zero_extract:SI
8304             (match_operand 1 "ext_register_operand" "0")
8305             (const_int 8)
8306             (const_int 8))
8307           (zero_extend:SI
8308             (match_operand 2 "ext_register_operand" "Q"))))
8309    (clobber (reg:CC FLAGS_REG))]
8310   "TARGET_64BIT"
8311   "and{b}\t{%2, %h0|%h0, %2}"
8312   [(set_attr "type" "alu")
8313    (set_attr "length_immediate" "0")
8314    (set_attr "mode" "QI")])
8316 (define_insn "*andqi_ext_2"
8317   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8318                          (const_int 8)
8319                          (const_int 8))
8320         (and:SI
8321           (zero_extract:SI
8322             (match_operand 1 "ext_register_operand" "%0")
8323             (const_int 8)
8324             (const_int 8))
8325           (zero_extract:SI
8326             (match_operand 2 "ext_register_operand" "Q")
8327             (const_int 8)
8328             (const_int 8))))
8329    (clobber (reg:CC FLAGS_REG))]
8330   ""
8331   "and{b}\t{%h2, %h0|%h0, %h2}"
8332   [(set_attr "type" "alu")
8333    (set_attr "length_immediate" "0")
8334    (set_attr "mode" "QI")])
8336 ;; Convert wide AND instructions with immediate operand to shorter QImode
8337 ;; equivalents when possible.
8338 ;; Don't do the splitting with memory operands, since it introduces risk
8339 ;; of memory mismatch stalls.  We may want to do the splitting for optimizing
8340 ;; for size, but that can (should?) be handled by generic code instead.
8341 (define_split
8342   [(set (match_operand 0 "register_operand" "")
8343         (and (match_operand 1 "register_operand" "")
8344              (match_operand 2 "const_int_operand" "")))
8345    (clobber (reg:CC FLAGS_REG))]
8346    "reload_completed
8347     && QI_REG_P (operands[0])
8348     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8349     && !(~INTVAL (operands[2]) & ~(255 << 8))
8350     && GET_MODE (operands[0]) != QImode"
8351   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8352                    (and:SI (zero_extract:SI (match_dup 1)
8353                                             (const_int 8) (const_int 8))
8354                            (match_dup 2)))
8355               (clobber (reg:CC FLAGS_REG))])]
8356   "operands[0] = gen_lowpart (SImode, operands[0]);
8357    operands[1] = gen_lowpart (SImode, operands[1]);
8358    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8360 ;; Since AND can be encoded with sign extended immediate, this is only
8361 ;; profitable when 7th bit is not set.
8362 (define_split
8363   [(set (match_operand 0 "register_operand" "")
8364         (and (match_operand 1 "general_operand" "")
8365              (match_operand 2 "const_int_operand" "")))
8366    (clobber (reg:CC FLAGS_REG))]
8367    "reload_completed
8368     && ANY_QI_REG_P (operands[0])
8369     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8370     && !(~INTVAL (operands[2]) & ~255)
8371     && !(INTVAL (operands[2]) & 128)
8372     && GET_MODE (operands[0]) != QImode"
8373   [(parallel [(set (strict_low_part (match_dup 0))
8374                    (and:QI (match_dup 1)
8375                            (match_dup 2)))
8376               (clobber (reg:CC FLAGS_REG))])]
8377   "operands[0] = gen_lowpart (QImode, operands[0]);
8378    operands[1] = gen_lowpart (QImode, operands[1]);
8379    operands[2] = gen_lowpart (QImode, operands[2]);")
8381 ;; Logical inclusive OR instructions
8383 ;; %%% This used to optimize known byte-wide and operations to memory.
8384 ;; If this is considered useful, it should be done with splitters.
8386 (define_expand "iordi3"
8387   [(set (match_operand:DI 0 "nonimmediate_operand" "")
8388         (ior:DI (match_operand:DI 1 "nonimmediate_operand" "")
8389                 (match_operand:DI 2 "x86_64_general_operand" "")))
8390    (clobber (reg:CC FLAGS_REG))]
8391   "TARGET_64BIT"
8392   "ix86_expand_binary_operator (IOR, DImode, operands); DONE;")
8394 (define_insn "*iordi_1_rex64"
8395   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
8396         (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8397                 (match_operand:DI 2 "x86_64_general_operand" "re,rme")))
8398    (clobber (reg:CC FLAGS_REG))]
8399   "TARGET_64BIT
8400    && ix86_binary_operator_ok (IOR, DImode, operands)"
8401   "or{q}\t{%2, %0|%0, %2}"
8402   [(set_attr "type" "alu")
8403    (set_attr "mode" "DI")])
8405 (define_insn "*iordi_2_rex64"
8406   [(set (reg FLAGS_REG)
8407         (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8408                          (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
8409                  (const_int 0)))
8410    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
8411         (ior:DI (match_dup 1) (match_dup 2)))]
8412   "TARGET_64BIT
8413    && ix86_match_ccmode (insn, CCNOmode)
8414    && ix86_binary_operator_ok (IOR, DImode, operands)"
8415   "or{q}\t{%2, %0|%0, %2}"
8416   [(set_attr "type" "alu")
8417    (set_attr "mode" "DI")])
8419 (define_insn "*iordi_3_rex64"
8420   [(set (reg FLAGS_REG)
8421         (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
8422                          (match_operand:DI 2 "x86_64_general_operand" "rem"))
8423                  (const_int 0)))
8424    (clobber (match_scratch:DI 0 "=r"))]
8425   "TARGET_64BIT
8426    && ix86_match_ccmode (insn, CCNOmode)
8427    && ix86_binary_operator_ok (IOR, DImode, operands)"
8428   "or{q}\t{%2, %0|%0, %2}"
8429   [(set_attr "type" "alu")
8430    (set_attr "mode" "DI")])
8433 (define_expand "iorsi3"
8434   [(set (match_operand:SI 0 "nonimmediate_operand" "")
8435         (ior:SI (match_operand:SI 1 "nonimmediate_operand" "")
8436                 (match_operand:SI 2 "general_operand" "")))
8437    (clobber (reg:CC FLAGS_REG))]
8438   ""
8439   "ix86_expand_binary_operator (IOR, SImode, operands); DONE;")
8441 (define_insn "*iorsi_1"
8442   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
8443         (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8444                 (match_operand:SI 2 "general_operand" "ri,rmi")))
8445    (clobber (reg:CC FLAGS_REG))]
8446   "ix86_binary_operator_ok (IOR, SImode, operands)"
8447   "or{l}\t{%2, %0|%0, %2}"
8448   [(set_attr "type" "alu")
8449    (set_attr "mode" "SI")])
8451 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8452 (define_insn "*iorsi_1_zext"
8453   [(set (match_operand:DI 0 "register_operand" "=rm")
8454         (zero_extend:DI
8455           (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8456                   (match_operand:SI 2 "general_operand" "rim"))))
8457    (clobber (reg:CC FLAGS_REG))]
8458   "TARGET_64BIT && ix86_binary_operator_ok (IOR, SImode, operands)"
8459   "or{l}\t{%2, %k0|%k0, %2}"
8460   [(set_attr "type" "alu")
8461    (set_attr "mode" "SI")])
8463 (define_insn "*iorsi_1_zext_imm"
8464   [(set (match_operand:DI 0 "register_operand" "=rm")
8465         (ior:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8466                 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8467    (clobber (reg:CC FLAGS_REG))]
8468   "TARGET_64BIT"
8469   "or{l}\t{%2, %k0|%k0, %2}"
8470   [(set_attr "type" "alu")
8471    (set_attr "mode" "SI")])
8473 (define_insn "*iorsi_2"
8474   [(set (reg FLAGS_REG)
8475         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8476                          (match_operand:SI 2 "general_operand" "rim,ri"))
8477                  (const_int 0)))
8478    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8479         (ior:SI (match_dup 1) (match_dup 2)))]
8480   "ix86_match_ccmode (insn, CCNOmode)
8481    && ix86_binary_operator_ok (IOR, SImode, operands)"
8482   "or{l}\t{%2, %0|%0, %2}"
8483   [(set_attr "type" "alu")
8484    (set_attr "mode" "SI")])
8486 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8487 ;; ??? Special case for immediate operand is missing - it is tricky.
8488 (define_insn "*iorsi_2_zext"
8489   [(set (reg FLAGS_REG)
8490         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8491                          (match_operand:SI 2 "general_operand" "rim"))
8492                  (const_int 0)))
8493    (set (match_operand:DI 0 "register_operand" "=r")
8494         (zero_extend:DI (ior:SI (match_dup 1) (match_dup 2))))]
8495   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8496    && ix86_binary_operator_ok (IOR, SImode, operands)"
8497   "or{l}\t{%2, %k0|%k0, %2}"
8498   [(set_attr "type" "alu")
8499    (set_attr "mode" "SI")])
8501 (define_insn "*iorsi_2_zext_imm"
8502   [(set (reg FLAGS_REG)
8503         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8504                          (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
8505                  (const_int 0)))
8506    (set (match_operand:DI 0 "register_operand" "=r")
8507         (ior:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8508   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8509    && ix86_binary_operator_ok (IOR, SImode, operands)"
8510   "or{l}\t{%2, %k0|%k0, %2}"
8511   [(set_attr "type" "alu")
8512    (set_attr "mode" "SI")])
8514 (define_insn "*iorsi_3"
8515   [(set (reg FLAGS_REG)
8516         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8517                          (match_operand:SI 2 "general_operand" "rim"))
8518                  (const_int 0)))
8519    (clobber (match_scratch:SI 0 "=r"))]
8520   "ix86_match_ccmode (insn, CCNOmode)
8521    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8522   "or{l}\t{%2, %0|%0, %2}"
8523   [(set_attr "type" "alu")
8524    (set_attr "mode" "SI")])
8526 (define_expand "iorhi3"
8527   [(set (match_operand:HI 0 "nonimmediate_operand" "")
8528         (ior:HI (match_operand:HI 1 "nonimmediate_operand" "")
8529                 (match_operand:HI 2 "general_operand" "")))
8530    (clobber (reg:CC FLAGS_REG))]
8531   "TARGET_HIMODE_MATH"
8532   "ix86_expand_binary_operator (IOR, HImode, operands); DONE;")
8534 (define_insn "*iorhi_1"
8535   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
8536         (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8537                 (match_operand:HI 2 "general_operand" "rmi,ri")))
8538    (clobber (reg:CC FLAGS_REG))]
8539   "ix86_binary_operator_ok (IOR, HImode, operands)"
8540   "or{w}\t{%2, %0|%0, %2}"
8541   [(set_attr "type" "alu")
8542    (set_attr "mode" "HI")])
8544 (define_insn "*iorhi_2"
8545   [(set (reg FLAGS_REG)
8546         (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8547                          (match_operand:HI 2 "general_operand" "rim,ri"))
8548                  (const_int 0)))
8549    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8550         (ior:HI (match_dup 1) (match_dup 2)))]
8551   "ix86_match_ccmode (insn, CCNOmode)
8552    && ix86_binary_operator_ok (IOR, HImode, operands)"
8553   "or{w}\t{%2, %0|%0, %2}"
8554   [(set_attr "type" "alu")
8555    (set_attr "mode" "HI")])
8557 (define_insn "*iorhi_3"
8558   [(set (reg FLAGS_REG)
8559         (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
8560                          (match_operand:HI 2 "general_operand" "rim"))
8561                  (const_int 0)))
8562    (clobber (match_scratch:HI 0 "=r"))]
8563   "ix86_match_ccmode (insn, CCNOmode)
8564    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8565   "or{w}\t{%2, %0|%0, %2}"
8566   [(set_attr "type" "alu")
8567    (set_attr "mode" "HI")])
8569 (define_expand "iorqi3"
8570   [(set (match_operand:QI 0 "nonimmediate_operand" "")
8571         (ior:QI (match_operand:QI 1 "nonimmediate_operand" "")
8572                 (match_operand:QI 2 "general_operand" "")))
8573    (clobber (reg:CC FLAGS_REG))]
8574   "TARGET_QIMODE_MATH"
8575   "ix86_expand_binary_operator (IOR, QImode, operands); DONE;")
8577 ;; %%% Potential partial reg stall on alternative 2.  What to do?
8578 (define_insn "*iorqi_1"
8579   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
8580         (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8581                 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
8582    (clobber (reg:CC FLAGS_REG))]
8583   "ix86_binary_operator_ok (IOR, QImode, operands)"
8584   "@
8585    or{b}\t{%2, %0|%0, %2}
8586    or{b}\t{%2, %0|%0, %2}
8587    or{l}\t{%k2, %k0|%k0, %k2}"
8588   [(set_attr "type" "alu")
8589    (set_attr "mode" "QI,QI,SI")])
8591 (define_insn "*iorqi_1_slp"
8592   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
8593         (ior:QI (match_dup 0)
8594                 (match_operand:QI 1 "general_operand" "qmi,qi")))
8595    (clobber (reg:CC FLAGS_REG))]
8596   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8597    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8598   "or{b}\t{%1, %0|%0, %1}"
8599   [(set_attr "type" "alu1")
8600    (set_attr "mode" "QI")])
8602 (define_insn "*iorqi_2"
8603   [(set (reg FLAGS_REG)
8604         (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
8605                          (match_operand:QI 2 "general_operand" "qim,qi"))
8606                  (const_int 0)))
8607    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
8608         (ior:QI (match_dup 1) (match_dup 2)))]
8609   "ix86_match_ccmode (insn, CCNOmode)
8610    && ix86_binary_operator_ok (IOR, QImode, operands)"
8611   "or{b}\t{%2, %0|%0, %2}"
8612   [(set_attr "type" "alu")
8613    (set_attr "mode" "QI")])
8615 (define_insn "*iorqi_2_slp"
8616   [(set (reg FLAGS_REG)
8617         (compare (ior:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8618                          (match_operand:QI 1 "general_operand" "qim,qi"))
8619                  (const_int 0)))
8620    (set (strict_low_part (match_dup 0))
8621         (ior:QI (match_dup 0) (match_dup 1)))]
8622   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8623    && ix86_match_ccmode (insn, CCNOmode)
8624    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8625   "or{b}\t{%1, %0|%0, %1}"
8626   [(set_attr "type" "alu1")
8627    (set_attr "mode" "QI")])
8629 (define_insn "*iorqi_3"
8630   [(set (reg FLAGS_REG)
8631         (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
8632                          (match_operand:QI 2 "general_operand" "qim"))
8633                  (const_int 0)))
8634    (clobber (match_scratch:QI 0 "=q"))]
8635   "ix86_match_ccmode (insn, CCNOmode)
8636    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8637   "or{b}\t{%2, %0|%0, %2}"
8638   [(set_attr "type" "alu")
8639    (set_attr "mode" "QI")])
8641 (define_insn "iorqi_ext_0"
8642   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8643                          (const_int 8)
8644                          (const_int 8))
8645         (ior:SI 
8646           (zero_extract:SI
8647             (match_operand 1 "ext_register_operand" "0")
8648             (const_int 8)
8649             (const_int 8))
8650           (match_operand 2 "const_int_operand" "n")))
8651    (clobber (reg:CC FLAGS_REG))]
8652   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8653   "or{b}\t{%2, %h0|%h0, %2}"
8654   [(set_attr "type" "alu")
8655    (set_attr "length_immediate" "1")
8656    (set_attr "mode" "QI")])
8658 (define_insn "*iorqi_ext_1"
8659   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8660                          (const_int 8)
8661                          (const_int 8))
8662         (ior:SI 
8663           (zero_extract:SI
8664             (match_operand 1 "ext_register_operand" "0")
8665             (const_int 8)
8666             (const_int 8))
8667           (zero_extend:SI
8668             (match_operand:QI 2 "general_operand" "Qm"))))
8669    (clobber (reg:CC FLAGS_REG))]
8670   "!TARGET_64BIT
8671    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
8672   "or{b}\t{%2, %h0|%h0, %2}"
8673   [(set_attr "type" "alu")
8674    (set_attr "length_immediate" "0")
8675    (set_attr "mode" "QI")])
8677 (define_insn "*iorqi_ext_1_rex64"
8678   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8679                          (const_int 8)
8680                          (const_int 8))
8681         (ior:SI 
8682           (zero_extract:SI
8683             (match_operand 1 "ext_register_operand" "0")
8684             (const_int 8)
8685             (const_int 8))
8686           (zero_extend:SI
8687             (match_operand 2 "ext_register_operand" "Q"))))
8688    (clobber (reg:CC FLAGS_REG))]
8689   "TARGET_64BIT
8690    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
8691   "or{b}\t{%2, %h0|%h0, %2}"
8692   [(set_attr "type" "alu")
8693    (set_attr "length_immediate" "0")
8694    (set_attr "mode" "QI")])
8696 (define_insn "*iorqi_ext_2"
8697   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8698                          (const_int 8)
8699                          (const_int 8))
8700         (ior:SI 
8701           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
8702                            (const_int 8)
8703                            (const_int 8))
8704           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
8705                            (const_int 8)
8706                            (const_int 8))))
8707    (clobber (reg:CC FLAGS_REG))]
8708   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8709   "ior{b}\t{%h2, %h0|%h0, %h2}"
8710   [(set_attr "type" "alu")
8711    (set_attr "length_immediate" "0")
8712    (set_attr "mode" "QI")])
8714 (define_split
8715   [(set (match_operand 0 "register_operand" "")
8716         (ior (match_operand 1 "register_operand" "")
8717              (match_operand 2 "const_int_operand" "")))
8718    (clobber (reg:CC FLAGS_REG))]
8719    "reload_completed
8720     && QI_REG_P (operands[0])
8721     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8722     && !(INTVAL (operands[2]) & ~(255 << 8))
8723     && GET_MODE (operands[0]) != QImode"
8724   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8725                    (ior:SI (zero_extract:SI (match_dup 1)
8726                                             (const_int 8) (const_int 8))
8727                            (match_dup 2)))
8728               (clobber (reg:CC FLAGS_REG))])]
8729   "operands[0] = gen_lowpart (SImode, operands[0]);
8730    operands[1] = gen_lowpart (SImode, operands[1]);
8731    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8733 ;; Since OR can be encoded with sign extended immediate, this is only
8734 ;; profitable when 7th bit is set.
8735 (define_split
8736   [(set (match_operand 0 "register_operand" "")
8737         (ior (match_operand 1 "general_operand" "")
8738              (match_operand 2 "const_int_operand" "")))
8739    (clobber (reg:CC FLAGS_REG))]
8740    "reload_completed
8741     && ANY_QI_REG_P (operands[0])
8742     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8743     && !(INTVAL (operands[2]) & ~255)
8744     && (INTVAL (operands[2]) & 128)
8745     && GET_MODE (operands[0]) != QImode"
8746   [(parallel [(set (strict_low_part (match_dup 0))
8747                    (ior:QI (match_dup 1)
8748                            (match_dup 2)))
8749               (clobber (reg:CC FLAGS_REG))])]
8750   "operands[0] = gen_lowpart (QImode, operands[0]);
8751    operands[1] = gen_lowpart (QImode, operands[1]);
8752    operands[2] = gen_lowpart (QImode, operands[2]);")
8754 ;; Logical XOR instructions
8756 ;; %%% This used to optimize known byte-wide and operations to memory.
8757 ;; If this is considered useful, it should be done with splitters.
8759 (define_expand "xordi3"
8760   [(set (match_operand:DI 0 "nonimmediate_operand" "")
8761         (xor:DI (match_operand:DI 1 "nonimmediate_operand" "")
8762                 (match_operand:DI 2 "x86_64_general_operand" "")))
8763    (clobber (reg:CC FLAGS_REG))]
8764   "TARGET_64BIT"
8765   "ix86_expand_binary_operator (XOR, DImode, operands); DONE;")
8767 (define_insn "*xordi_1_rex64"
8768   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
8769         (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8770                 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
8771    (clobber (reg:CC FLAGS_REG))]
8772   "TARGET_64BIT
8773    && ix86_binary_operator_ok (XOR, DImode, operands)"
8774   "@
8775    xor{q}\t{%2, %0|%0, %2}
8776    xor{q}\t{%2, %0|%0, %2}"
8777   [(set_attr "type" "alu")
8778    (set_attr "mode" "DI,DI")])
8780 (define_insn "*xordi_2_rex64"
8781   [(set (reg FLAGS_REG)
8782         (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8783                          (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
8784                  (const_int 0)))
8785    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
8786         (xor:DI (match_dup 1) (match_dup 2)))]
8787   "TARGET_64BIT
8788    && ix86_match_ccmode (insn, CCNOmode)
8789    && ix86_binary_operator_ok (XOR, DImode, operands)"
8790   "@
8791    xor{q}\t{%2, %0|%0, %2}
8792    xor{q}\t{%2, %0|%0, %2}"
8793   [(set_attr "type" "alu")
8794    (set_attr "mode" "DI,DI")])
8796 (define_insn "*xordi_3_rex64"
8797   [(set (reg FLAGS_REG)
8798         (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
8799                          (match_operand:DI 2 "x86_64_general_operand" "rem"))
8800                  (const_int 0)))
8801    (clobber (match_scratch:DI 0 "=r"))]
8802   "TARGET_64BIT
8803    && ix86_match_ccmode (insn, CCNOmode)
8804    && ix86_binary_operator_ok (XOR, DImode, operands)"
8805   "xor{q}\t{%2, %0|%0, %2}"
8806   [(set_attr "type" "alu")
8807    (set_attr "mode" "DI")])
8809 (define_expand "xorsi3"
8810   [(set (match_operand:SI 0 "nonimmediate_operand" "")
8811         (xor:SI (match_operand:SI 1 "nonimmediate_operand" "")
8812                 (match_operand:SI 2 "general_operand" "")))
8813    (clobber (reg:CC FLAGS_REG))]
8814   ""
8815   "ix86_expand_binary_operator (XOR, SImode, operands); DONE;")
8817 (define_insn "*xorsi_1"
8818   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
8819         (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8820                 (match_operand:SI 2 "general_operand" "ri,rm")))
8821    (clobber (reg:CC FLAGS_REG))]
8822   "ix86_binary_operator_ok (XOR, SImode, operands)"
8823   "xor{l}\t{%2, %0|%0, %2}"
8824   [(set_attr "type" "alu")
8825    (set_attr "mode" "SI")])
8827 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8828 ;; Add speccase for immediates
8829 (define_insn "*xorsi_1_zext"
8830   [(set (match_operand:DI 0 "register_operand" "=r")
8831         (zero_extend:DI
8832           (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8833                   (match_operand:SI 2 "general_operand" "rim"))))
8834    (clobber (reg:CC FLAGS_REG))]
8835   "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
8836   "xor{l}\t{%2, %k0|%k0, %2}"
8837   [(set_attr "type" "alu")
8838    (set_attr "mode" "SI")])
8840 (define_insn "*xorsi_1_zext_imm"
8841   [(set (match_operand:DI 0 "register_operand" "=r")
8842         (xor:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8843                 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8844    (clobber (reg:CC FLAGS_REG))]
8845   "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
8846   "xor{l}\t{%2, %k0|%k0, %2}"
8847   [(set_attr "type" "alu")
8848    (set_attr "mode" "SI")])
8850 (define_insn "*xorsi_2"
8851   [(set (reg FLAGS_REG)
8852         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8853                          (match_operand:SI 2 "general_operand" "rim,ri"))
8854                  (const_int 0)))
8855    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8856         (xor:SI (match_dup 1) (match_dup 2)))]
8857   "ix86_match_ccmode (insn, CCNOmode)
8858    && ix86_binary_operator_ok (XOR, SImode, operands)"
8859   "xor{l}\t{%2, %0|%0, %2}"
8860   [(set_attr "type" "alu")
8861    (set_attr "mode" "SI")])
8863 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8864 ;; ??? Special case for immediate operand is missing - it is tricky.
8865 (define_insn "*xorsi_2_zext"
8866   [(set (reg FLAGS_REG)
8867         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8868                          (match_operand:SI 2 "general_operand" "rim"))
8869                  (const_int 0)))
8870    (set (match_operand:DI 0 "register_operand" "=r")
8871         (zero_extend:DI (xor:SI (match_dup 1) (match_dup 2))))]
8872   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8873    && ix86_binary_operator_ok (XOR, SImode, operands)"
8874   "xor{l}\t{%2, %k0|%k0, %2}"
8875   [(set_attr "type" "alu")
8876    (set_attr "mode" "SI")])
8878 (define_insn "*xorsi_2_zext_imm"
8879   [(set (reg FLAGS_REG)
8880         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8881                          (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
8882                  (const_int 0)))
8883    (set (match_operand:DI 0 "register_operand" "=r")
8884         (xor:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8885   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8886    && ix86_binary_operator_ok (XOR, SImode, operands)"
8887   "xor{l}\t{%2, %k0|%k0, %2}"
8888   [(set_attr "type" "alu")
8889    (set_attr "mode" "SI")])
8891 (define_insn "*xorsi_3"
8892   [(set (reg FLAGS_REG)
8893         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8894                          (match_operand:SI 2 "general_operand" "rim"))
8895                  (const_int 0)))
8896    (clobber (match_scratch:SI 0 "=r"))]
8897   "ix86_match_ccmode (insn, CCNOmode)
8898    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8899   "xor{l}\t{%2, %0|%0, %2}"
8900   [(set_attr "type" "alu")
8901    (set_attr "mode" "SI")])
8903 (define_expand "xorhi3"
8904   [(set (match_operand:HI 0 "nonimmediate_operand" "")
8905         (xor:HI (match_operand:HI 1 "nonimmediate_operand" "")
8906                 (match_operand:HI 2 "general_operand" "")))
8907    (clobber (reg:CC FLAGS_REG))]
8908   "TARGET_HIMODE_MATH"
8909   "ix86_expand_binary_operator (XOR, HImode, operands); DONE;")
8911 (define_insn "*xorhi_1"
8912   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
8913         (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8914                 (match_operand:HI 2 "general_operand" "rmi,ri")))
8915    (clobber (reg:CC FLAGS_REG))]
8916   "ix86_binary_operator_ok (XOR, HImode, operands)"
8917   "xor{w}\t{%2, %0|%0, %2}"
8918   [(set_attr "type" "alu")
8919    (set_attr "mode" "HI")])
8921 (define_insn "*xorhi_2"
8922   [(set (reg FLAGS_REG)
8923         (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8924                          (match_operand:HI 2 "general_operand" "rim,ri"))
8925                  (const_int 0)))
8926    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8927         (xor:HI (match_dup 1) (match_dup 2)))]
8928   "ix86_match_ccmode (insn, CCNOmode)
8929    && ix86_binary_operator_ok (XOR, HImode, operands)"
8930   "xor{w}\t{%2, %0|%0, %2}"
8931   [(set_attr "type" "alu")
8932    (set_attr "mode" "HI")])
8934 (define_insn "*xorhi_3"
8935   [(set (reg FLAGS_REG)
8936         (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
8937                          (match_operand:HI 2 "general_operand" "rim"))
8938                  (const_int 0)))
8939    (clobber (match_scratch:HI 0 "=r"))]
8940   "ix86_match_ccmode (insn, CCNOmode)
8941    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8942   "xor{w}\t{%2, %0|%0, %2}"
8943   [(set_attr "type" "alu")
8944    (set_attr "mode" "HI")])
8946 (define_expand "xorqi3"
8947   [(set (match_operand:QI 0 "nonimmediate_operand" "")
8948         (xor:QI (match_operand:QI 1 "nonimmediate_operand" "")
8949                 (match_operand:QI 2 "general_operand" "")))
8950    (clobber (reg:CC FLAGS_REG))]
8951   "TARGET_QIMODE_MATH"
8952   "ix86_expand_binary_operator (XOR, QImode, operands); DONE;")
8954 ;; %%% Potential partial reg stall on alternative 2.  What to do?
8955 (define_insn "*xorqi_1"
8956   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
8957         (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8958                 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
8959    (clobber (reg:CC FLAGS_REG))]
8960   "ix86_binary_operator_ok (XOR, QImode, operands)"
8961   "@
8962    xor{b}\t{%2, %0|%0, %2}
8963    xor{b}\t{%2, %0|%0, %2}
8964    xor{l}\t{%k2, %k0|%k0, %k2}"
8965   [(set_attr "type" "alu")
8966    (set_attr "mode" "QI,QI,SI")])
8968 (define_insn "*xorqi_1_slp"
8969   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
8970         (xor:QI (match_dup 0)
8971                 (match_operand:QI 1 "general_operand" "qi,qmi")))
8972    (clobber (reg:CC FLAGS_REG))]
8973   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8974    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8975   "xor{b}\t{%1, %0|%0, %1}"
8976   [(set_attr "type" "alu1")
8977    (set_attr "mode" "QI")])
8979 (define_insn "xorqi_ext_0"
8980   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8981                          (const_int 8)
8982                          (const_int 8))
8983         (xor:SI 
8984           (zero_extract:SI
8985             (match_operand 1 "ext_register_operand" "0")
8986             (const_int 8)
8987             (const_int 8))
8988           (match_operand 2 "const_int_operand" "n")))
8989    (clobber (reg:CC FLAGS_REG))]
8990   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8991   "xor{b}\t{%2, %h0|%h0, %2}"
8992   [(set_attr "type" "alu")
8993    (set_attr "length_immediate" "1")
8994    (set_attr "mode" "QI")])
8996 (define_insn "*xorqi_ext_1"
8997   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8998                          (const_int 8)
8999                          (const_int 8))
9000         (xor:SI 
9001           (zero_extract:SI
9002             (match_operand 1 "ext_register_operand" "0")
9003             (const_int 8)
9004             (const_int 8))
9005           (zero_extend:SI
9006             (match_operand:QI 2 "general_operand" "Qm"))))
9007    (clobber (reg:CC FLAGS_REG))]
9008   "!TARGET_64BIT
9009    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9010   "xor{b}\t{%2, %h0|%h0, %2}"
9011   [(set_attr "type" "alu")
9012    (set_attr "length_immediate" "0")
9013    (set_attr "mode" "QI")])
9015 (define_insn "*xorqi_ext_1_rex64"
9016   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9017                          (const_int 8)
9018                          (const_int 8))
9019         (xor:SI 
9020           (zero_extract:SI
9021             (match_operand 1 "ext_register_operand" "0")
9022             (const_int 8)
9023             (const_int 8))
9024           (zero_extend:SI
9025             (match_operand 2 "ext_register_operand" "Q"))))
9026    (clobber (reg:CC FLAGS_REG))]
9027   "TARGET_64BIT
9028    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9029   "xor{b}\t{%2, %h0|%h0, %2}"
9030   [(set_attr "type" "alu")
9031    (set_attr "length_immediate" "0")
9032    (set_attr "mode" "QI")])
9034 (define_insn "*xorqi_ext_2"
9035   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9036                          (const_int 8)
9037                          (const_int 8))
9038         (xor:SI 
9039           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
9040                            (const_int 8)
9041                            (const_int 8))
9042           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
9043                            (const_int 8)
9044                            (const_int 8))))
9045    (clobber (reg:CC FLAGS_REG))]
9046   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9047   "xor{b}\t{%h2, %h0|%h0, %h2}"
9048   [(set_attr "type" "alu")
9049    (set_attr "length_immediate" "0")
9050    (set_attr "mode" "QI")])
9052 (define_insn "*xorqi_cc_1"
9053   [(set (reg FLAGS_REG)
9054         (compare
9055           (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9056                   (match_operand:QI 2 "general_operand" "qim,qi"))
9057           (const_int 0)))
9058    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9059         (xor:QI (match_dup 1) (match_dup 2)))]
9060   "ix86_match_ccmode (insn, CCNOmode)
9061    && ix86_binary_operator_ok (XOR, QImode, operands)"
9062   "xor{b}\t{%2, %0|%0, %2}"
9063   [(set_attr "type" "alu")
9064    (set_attr "mode" "QI")])
9066 (define_insn "*xorqi_2_slp"
9067   [(set (reg FLAGS_REG)
9068         (compare (xor:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9069                          (match_operand:QI 1 "general_operand" "qim,qi"))
9070                  (const_int 0)))
9071    (set (strict_low_part (match_dup 0))
9072         (xor:QI (match_dup 0) (match_dup 1)))]
9073   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9074    && ix86_match_ccmode (insn, CCNOmode)
9075    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
9076   "xor{b}\t{%1, %0|%0, %1}"
9077   [(set_attr "type" "alu1")
9078    (set_attr "mode" "QI")])
9080 (define_insn "*xorqi_cc_2"
9081   [(set (reg FLAGS_REG)
9082         (compare
9083           (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
9084                   (match_operand:QI 2 "general_operand" "qim"))
9085           (const_int 0)))
9086    (clobber (match_scratch:QI 0 "=q"))]
9087   "ix86_match_ccmode (insn, CCNOmode)
9088    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
9089   "xor{b}\t{%2, %0|%0, %2}"
9090   [(set_attr "type" "alu")
9091    (set_attr "mode" "QI")])
9093 (define_insn "*xorqi_cc_ext_1"
9094   [(set (reg FLAGS_REG)
9095         (compare
9096           (xor:SI
9097             (zero_extract:SI
9098               (match_operand 1 "ext_register_operand" "0")
9099               (const_int 8)
9100               (const_int 8))
9101             (match_operand:QI 2 "general_operand" "qmn"))
9102           (const_int 0)))
9103    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
9104                          (const_int 8)
9105                          (const_int 8))
9106         (xor:SI 
9107           (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9108           (match_dup 2)))]
9109   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9110   "xor{b}\t{%2, %h0|%h0, %2}"
9111   [(set_attr "type" "alu")
9112    (set_attr "mode" "QI")])
9114 (define_insn "*xorqi_cc_ext_1_rex64"
9115   [(set (reg FLAGS_REG)
9116         (compare
9117           (xor:SI
9118             (zero_extract:SI
9119               (match_operand 1 "ext_register_operand" "0")
9120               (const_int 8)
9121               (const_int 8))
9122             (match_operand:QI 2 "nonmemory_operand" "Qn"))
9123           (const_int 0)))
9124    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9125                          (const_int 8)
9126                          (const_int 8))
9127         (xor:SI 
9128           (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9129           (match_dup 2)))]
9130   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9131   "xor{b}\t{%2, %h0|%h0, %2}"
9132   [(set_attr "type" "alu")
9133    (set_attr "mode" "QI")])
9135 (define_expand "xorqi_cc_ext_1"
9136   [(parallel [
9137      (set (reg:CCNO FLAGS_REG)
9138           (compare:CCNO
9139             (xor:SI
9140               (zero_extract:SI
9141                 (match_operand 1 "ext_register_operand" "")
9142                 (const_int 8)
9143                 (const_int 8))
9144               (match_operand:QI 2 "general_operand" ""))
9145             (const_int 0)))
9146      (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
9147                            (const_int 8)
9148                            (const_int 8))
9149           (xor:SI 
9150             (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9151             (match_dup 2)))])]
9152   ""
9153   "")
9155 (define_split
9156   [(set (match_operand 0 "register_operand" "")
9157         (xor (match_operand 1 "register_operand" "")
9158              (match_operand 2 "const_int_operand" "")))
9159    (clobber (reg:CC FLAGS_REG))]
9160    "reload_completed
9161     && QI_REG_P (operands[0])
9162     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9163     && !(INTVAL (operands[2]) & ~(255 << 8))
9164     && GET_MODE (operands[0]) != QImode"
9165   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9166                    (xor:SI (zero_extract:SI (match_dup 1)
9167                                             (const_int 8) (const_int 8))
9168                            (match_dup 2)))
9169               (clobber (reg:CC FLAGS_REG))])]
9170   "operands[0] = gen_lowpart (SImode, operands[0]);
9171    operands[1] = gen_lowpart (SImode, operands[1]);
9172    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9174 ;; Since XOR can be encoded with sign extended immediate, this is only
9175 ;; profitable when 7th bit is set.
9176 (define_split
9177   [(set (match_operand 0 "register_operand" "")
9178         (xor (match_operand 1 "general_operand" "")
9179              (match_operand 2 "const_int_operand" "")))
9180    (clobber (reg:CC FLAGS_REG))]
9181    "reload_completed
9182     && ANY_QI_REG_P (operands[0])
9183     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9184     && !(INTVAL (operands[2]) & ~255)
9185     && (INTVAL (operands[2]) & 128)
9186     && GET_MODE (operands[0]) != QImode"
9187   [(parallel [(set (strict_low_part (match_dup 0))
9188                    (xor:QI (match_dup 1)
9189                            (match_dup 2)))
9190               (clobber (reg:CC FLAGS_REG))])]
9191   "operands[0] = gen_lowpart (QImode, operands[0]);
9192    operands[1] = gen_lowpart (QImode, operands[1]);
9193    operands[2] = gen_lowpart (QImode, operands[2]);")
9195 ;; Negation instructions
9197 (define_expand "negdi2"
9198   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
9199                    (neg:DI (match_operand:DI 1 "nonimmediate_operand" "")))
9200               (clobber (reg:CC FLAGS_REG))])]
9201   ""
9202   "ix86_expand_unary_operator (NEG, DImode, operands); DONE;")
9204 (define_insn "*negdi2_1"
9205   [(set (match_operand:DI 0 "nonimmediate_operand" "=ro")
9206         (neg:DI (match_operand:DI 1 "general_operand" "0")))
9207    (clobber (reg:CC FLAGS_REG))]
9208   "!TARGET_64BIT
9209    && ix86_unary_operator_ok (NEG, DImode, operands)"
9210   "#")
9212 (define_split
9213   [(set (match_operand:DI 0 "nonimmediate_operand" "")
9214         (neg:DI (match_operand:DI 1 "general_operand" "")))
9215    (clobber (reg:CC FLAGS_REG))]
9216   "!TARGET_64BIT && reload_completed"
9217   [(parallel
9218     [(set (reg:CCZ FLAGS_REG)
9219           (compare:CCZ (neg:SI (match_dup 2)) (const_int 0)))
9220      (set (match_dup 0) (neg:SI (match_dup 2)))])
9221    (parallel
9222     [(set (match_dup 1)
9223           (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
9224                             (match_dup 3))
9225                    (const_int 0)))
9226      (clobber (reg:CC FLAGS_REG))])
9227    (parallel
9228     [(set (match_dup 1)
9229           (neg:SI (match_dup 1)))
9230      (clobber (reg:CC FLAGS_REG))])]
9231   "split_di (operands+1, 1, operands+2, operands+3);
9232    split_di (operands+0, 1, operands+0, operands+1);")
9234 (define_insn "*negdi2_1_rex64"
9235   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9236         (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0")))
9237    (clobber (reg:CC FLAGS_REG))]
9238   "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
9239   "neg{q}\t%0"
9240   [(set_attr "type" "negnot")
9241    (set_attr "mode" "DI")])
9243 ;; The problem with neg is that it does not perform (compare x 0),
9244 ;; it really performs (compare 0 x), which leaves us with the zero
9245 ;; flag being the only useful item.
9247 (define_insn "*negdi2_cmpz_rex64"
9248   [(set (reg:CCZ FLAGS_REG)
9249         (compare:CCZ (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
9250                      (const_int 0)))
9251    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9252         (neg:DI (match_dup 1)))]
9253   "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
9254   "neg{q}\t%0"
9255   [(set_attr "type" "negnot")
9256    (set_attr "mode" "DI")])
9259 (define_expand "negsi2"
9260   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
9261                    (neg:SI (match_operand:SI 1 "nonimmediate_operand" "")))
9262               (clobber (reg:CC FLAGS_REG))])]
9263   ""
9264   "ix86_expand_unary_operator (NEG, SImode, operands); DONE;")
9266 (define_insn "*negsi2_1"
9267   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9268         (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0")))
9269    (clobber (reg:CC FLAGS_REG))]
9270   "ix86_unary_operator_ok (NEG, SImode, operands)"
9271   "neg{l}\t%0"
9272   [(set_attr "type" "negnot")
9273    (set_attr "mode" "SI")])
9275 ;; Combine is quite creative about this pattern.
9276 (define_insn "*negsi2_1_zext"
9277   [(set (match_operand:DI 0 "register_operand" "=r")
9278         (lshiftrt:DI (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
9279                                         (const_int 32)))
9280                      (const_int 32)))
9281    (clobber (reg:CC FLAGS_REG))]
9282   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
9283   "neg{l}\t%k0"
9284   [(set_attr "type" "negnot")
9285    (set_attr "mode" "SI")])
9287 ;; The problem with neg is that it does not perform (compare x 0),
9288 ;; it really performs (compare 0 x), which leaves us with the zero
9289 ;; flag being the only useful item.
9291 (define_insn "*negsi2_cmpz"
9292   [(set (reg:CCZ FLAGS_REG)
9293         (compare:CCZ (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
9294                      (const_int 0)))
9295    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9296         (neg:SI (match_dup 1)))]
9297   "ix86_unary_operator_ok (NEG, SImode, operands)"
9298   "neg{l}\t%0"
9299   [(set_attr "type" "negnot")
9300    (set_attr "mode" "SI")])
9302 (define_insn "*negsi2_cmpz_zext"
9303   [(set (reg:CCZ FLAGS_REG)
9304         (compare:CCZ (lshiftrt:DI
9305                        (neg:DI (ashift:DI
9306                                  (match_operand:DI 1 "register_operand" "0")
9307                                  (const_int 32)))
9308                        (const_int 32))
9309                      (const_int 0)))
9310    (set (match_operand:DI 0 "register_operand" "=r")
9311         (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
9312                                         (const_int 32)))
9313                      (const_int 32)))]
9314   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
9315   "neg{l}\t%k0"
9316   [(set_attr "type" "negnot")
9317    (set_attr "mode" "SI")])
9319 (define_expand "neghi2"
9320   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
9321                    (neg:HI (match_operand:HI 1 "nonimmediate_operand" "")))
9322               (clobber (reg:CC FLAGS_REG))])]
9323   "TARGET_HIMODE_MATH"
9324   "ix86_expand_unary_operator (NEG, HImode, operands); DONE;")
9326 (define_insn "*neghi2_1"
9327   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9328         (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0")))
9329    (clobber (reg:CC FLAGS_REG))]
9330   "ix86_unary_operator_ok (NEG, HImode, operands)"
9331   "neg{w}\t%0"
9332   [(set_attr "type" "negnot")
9333    (set_attr "mode" "HI")])
9335 (define_insn "*neghi2_cmpz"
9336   [(set (reg:CCZ FLAGS_REG)
9337         (compare:CCZ (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
9338                      (const_int 0)))
9339    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9340         (neg:HI (match_dup 1)))]
9341   "ix86_unary_operator_ok (NEG, HImode, operands)"
9342   "neg{w}\t%0"
9343   [(set_attr "type" "negnot")
9344    (set_attr "mode" "HI")])
9346 (define_expand "negqi2"
9347   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
9348                    (neg:QI (match_operand:QI 1 "nonimmediate_operand" "")))
9349               (clobber (reg:CC FLAGS_REG))])]
9350   "TARGET_QIMODE_MATH"
9351   "ix86_expand_unary_operator (NEG, QImode, operands); DONE;")
9353 (define_insn "*negqi2_1"
9354   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9355         (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0")))
9356    (clobber (reg:CC FLAGS_REG))]
9357   "ix86_unary_operator_ok (NEG, QImode, operands)"
9358   "neg{b}\t%0"
9359   [(set_attr "type" "negnot")
9360    (set_attr "mode" "QI")])
9362 (define_insn "*negqi2_cmpz"
9363   [(set (reg:CCZ FLAGS_REG)
9364         (compare:CCZ (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
9365                      (const_int 0)))
9366    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9367         (neg:QI (match_dup 1)))]
9368   "ix86_unary_operator_ok (NEG, QImode, operands)"
9369   "neg{b}\t%0"
9370   [(set_attr "type" "negnot")
9371    (set_attr "mode" "QI")])
9373 ;; Changing of sign for FP values is doable using integer unit too.
9375 (define_expand "negsf2"
9376   [(set (match_operand:SF 0 "nonimmediate_operand" "")
9377         (neg:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
9378   "TARGET_80387 || TARGET_SSE_MATH"
9379   "ix86_expand_fp_absneg_operator (NEG, SFmode, operands); DONE;")
9381 (define_expand "abssf2"
9382   [(set (match_operand:SF 0 "nonimmediate_operand" "")
9383         (abs:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
9384   "TARGET_80387 || TARGET_SSE_MATH"
9385   "ix86_expand_fp_absneg_operator (ABS, SFmode, operands); DONE;")
9387 (define_insn "*absnegsf2_mixed"
9388   [(set (match_operand:SF 0 "nonimmediate_operand"    "=x#f,x#f,f#x,rm")
9389         (match_operator:SF 3 "absneg_operator"
9390           [(match_operand:SF 1 "nonimmediate_operand" "0   ,x#f,0  ,0")]))
9391    (use (match_operand:V4SF 2 "nonimmediate_operand"  "xm  ,0  ,X  ,X"))
9392    (clobber (reg:CC FLAGS_REG))]
9393   "TARGET_SSE_MATH && TARGET_MIX_SSE_I387
9394    && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9395   "#")
9397 (define_insn "*absnegsf2_sse"
9398   [(set (match_operand:SF 0 "nonimmediate_operand"    "=x,x,rm")
9399         (match_operator:SF 3 "absneg_operator"
9400           [(match_operand:SF 1 "nonimmediate_operand" "0 ,x,0")]))
9401    (use (match_operand:V4SF 2 "nonimmediate_operand"  "xm,0,X"))
9402    (clobber (reg:CC FLAGS_REG))]
9403   "TARGET_SSE_MATH
9404    && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9405   "#")
9407 (define_insn "*absnegsf2_i387"
9408   [(set (match_operand:SF 0 "nonimmediate_operand" "=f,rm")
9409         (match_operator:SF 3 "absneg_operator"
9410           [(match_operand:SF 1 "nonimmediate_operand" "0,0")]))
9411    (use (match_operand 2 "" ""))
9412    (clobber (reg:CC FLAGS_REG))]
9413   "TARGET_80387 && !TARGET_SSE_MATH
9414    && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9415   "#")
9417 (define_expand "copysignsf3"
9418   [(match_operand:SF 0 "register_operand" "")
9419    (match_operand:SF 1 "nonmemory_operand" "")
9420    (match_operand:SF 2 "register_operand" "")]
9421   "TARGET_SSE_MATH"
9423   ix86_expand_copysign (operands);
9424   DONE;
9427 (define_insn_and_split "copysignsf3_const"
9428   [(set (match_operand:SF 0 "register_operand"          "=x")
9429         (unspec:SF
9430           [(match_operand:V4SF 1 "vector_move_operand"  "xmC")
9431            (match_operand:SF 2 "register_operand"       "0")
9432            (match_operand:V4SF 3 "nonimmediate_operand" "xm")]
9433           UNSPEC_COPYSIGN))]
9434   "TARGET_SSE_MATH"
9435   "#"
9436   "&& reload_completed"
9437   [(const_int 0)]
9439   ix86_split_copysign_const (operands);
9440   DONE;
9443 (define_insn "copysignsf3_var"
9444   [(set (match_operand:SF 0 "register_operand"          "=x, x, x, x,x")
9445         (unspec:SF
9446           [(match_operand:SF 2 "register_operand"       " x, 0, 0, x,x")
9447            (match_operand:SF 3 "register_operand"       " 1, 1, x, 1,x")
9448            (match_operand:V4SF 4 "nonimmediate_operand" " X,xm,xm, 0,0")
9449            (match_operand:V4SF 5 "nonimmediate_operand" " 0,xm, 1,xm,1")]
9450           UNSPEC_COPYSIGN))
9451    (clobber (match_scratch:V4SF 1                       "=x, x, x, x,x"))]
9452   "TARGET_SSE_MATH"
9453   "#")
9455 (define_split
9456   [(set (match_operand:SF 0 "register_operand" "")
9457         (unspec:SF
9458           [(match_operand:SF 2 "register_operand" "")
9459            (match_operand:SF 3 "register_operand" "")
9460            (match_operand:V4SF 4 "" "")
9461            (match_operand:V4SF 5 "" "")]
9462           UNSPEC_COPYSIGN))
9463    (clobber (match_scratch:V4SF 1 ""))]
9464   "TARGET_SSE_MATH && reload_completed"
9465   [(const_int 0)]
9467   ix86_split_copysign_var (operands);
9468   DONE;
9471 (define_expand "negdf2"
9472   [(set (match_operand:DF 0 "nonimmediate_operand" "")
9473         (neg:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
9474   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
9475   "ix86_expand_fp_absneg_operator (NEG, DFmode, operands); DONE;")
9477 (define_expand "absdf2"
9478   [(set (match_operand:DF 0 "nonimmediate_operand" "")
9479         (abs:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
9480   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
9481   "ix86_expand_fp_absneg_operator (ABS, DFmode, operands); DONE;")
9483 (define_insn "*absnegdf2_mixed"
9484   [(set (match_operand:DF 0 "nonimmediate_operand"    "=Y#f,Y#f,f#Y,rm")
9485         (match_operator:DF 3 "absneg_operator"
9486           [(match_operand:DF 1 "nonimmediate_operand" "0   ,Y#f,0  ,0")]))
9487    (use (match_operand:V2DF 2 "nonimmediate_operand"  "Ym  ,0  ,X  ,X"))
9488    (clobber (reg:CC FLAGS_REG))]
9489   "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
9490    && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9491   "#")
9493 (define_insn "*absnegdf2_sse"
9494   [(set (match_operand:DF 0 "nonimmediate_operand"    "=Y,Y,rm")
9495         (match_operator:DF 3 "absneg_operator"
9496           [(match_operand:DF 1 "nonimmediate_operand" "0 ,Y,0")]))
9497    (use (match_operand:V2DF 2 "nonimmediate_operand"  "Ym,0,X"))
9498    (clobber (reg:CC FLAGS_REG))]
9499   "TARGET_SSE2 && TARGET_SSE_MATH
9500    && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9501   "#")
9503 (define_insn "*absnegdf2_i387"
9504   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,rm")
9505         (match_operator:DF 3 "absneg_operator"
9506           [(match_operand:DF 1 "nonimmediate_operand" "0,0")]))
9507    (use (match_operand 2 "" ""))
9508    (clobber (reg:CC FLAGS_REG))]
9509   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
9510    && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9511   "#")
9513 (define_expand "copysigndf3"
9514   [(match_operand:DF 0 "register_operand" "")
9515    (match_operand:DF 1 "nonmemory_operand" "")
9516    (match_operand:DF 2 "register_operand" "")]
9517   "TARGET_SSE2 && TARGET_SSE_MATH"
9519   ix86_expand_copysign (operands);
9520   DONE;
9523 (define_insn_and_split "copysigndf3_const"
9524   [(set (match_operand:DF 0 "register_operand"          "=x")
9525         (unspec:DF
9526           [(match_operand:V2DF 1 "vector_move_operand"  "xmC")
9527            (match_operand:DF 2 "register_operand"       "0")
9528            (match_operand:V2DF 3 "nonimmediate_operand" "xm")]
9529           UNSPEC_COPYSIGN))]
9530   "TARGET_SSE2 && TARGET_SSE_MATH"
9531   "#"
9532   "&& reload_completed"
9533   [(const_int 0)]
9535   ix86_split_copysign_const (operands);
9536   DONE;
9539 (define_insn "copysigndf3_var"
9540   [(set (match_operand:DF 0 "register_operand"          "=x, x, x, x,x")
9541         (unspec:DF
9542           [(match_operand:DF 2 "register_operand"       " x, 0, 0, x,x")
9543            (match_operand:DF 3 "register_operand"       " 1, 1, x, 1,x")
9544            (match_operand:V2DF 4 "nonimmediate_operand" " X,xm,xm, 0,0")
9545            (match_operand:V2DF 5 "nonimmediate_operand" " 0,xm, 1,xm,1")]
9546           UNSPEC_COPYSIGN))
9547    (clobber (match_scratch:V2DF 1                       "=x, x, x, x,x"))]
9548   "TARGET_SSE2 && TARGET_SSE_MATH"
9549   "#")
9551 (define_split
9552   [(set (match_operand:DF 0 "register_operand" "")
9553         (unspec:DF
9554           [(match_operand:DF 2 "register_operand" "")
9555            (match_operand:DF 3 "register_operand" "")
9556            (match_operand:V2DF 4 "" "")
9557            (match_operand:V2DF 5 "" "")]
9558           UNSPEC_COPYSIGN))
9559    (clobber (match_scratch:V2DF 1 ""))]
9560   "TARGET_SSE2 && TARGET_SSE_MATH && reload_completed"
9561   [(const_int 0)]
9563   ix86_split_copysign_var (operands);
9564   DONE;
9567 (define_expand "negxf2"
9568   [(set (match_operand:XF 0 "nonimmediate_operand" "")
9569         (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))]
9570   "TARGET_80387"
9571   "ix86_expand_fp_absneg_operator (NEG, XFmode, operands); DONE;")
9573 (define_expand "absxf2"
9574   [(set (match_operand:XF 0 "nonimmediate_operand" "")
9575         (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))]
9576   "TARGET_80387"
9577   "ix86_expand_fp_absneg_operator (ABS, XFmode, operands); DONE;")
9579 (define_insn "*absnegxf2_i387"
9580   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,?rm")
9581         (match_operator:XF 3 "absneg_operator"
9582           [(match_operand:XF 1 "nonimmediate_operand" "0,0")]))
9583    (use (match_operand 2 "" ""))
9584    (clobber (reg:CC FLAGS_REG))]
9585   "TARGET_80387
9586    && ix86_unary_operator_ok (GET_CODE (operands[3]), XFmode, operands)"
9587   "#")
9589 ;; Splitters for fp abs and neg.
9591 (define_split
9592   [(set (match_operand 0 "fp_register_operand" "")
9593         (match_operator 1 "absneg_operator" [(match_dup 0)]))
9594    (use (match_operand 2 "" ""))
9595    (clobber (reg:CC FLAGS_REG))]
9596   "reload_completed"
9597   [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))])
9599 (define_split
9600   [(set (match_operand 0 "register_operand" "")
9601         (match_operator 3 "absneg_operator"
9602           [(match_operand 1 "register_operand" "")]))
9603    (use (match_operand 2 "nonimmediate_operand" ""))
9604    (clobber (reg:CC FLAGS_REG))]
9605   "reload_completed && SSE_REG_P (operands[0])"
9606   [(set (match_dup 0) (match_dup 3))]
9608   enum machine_mode mode = GET_MODE (operands[0]);
9609   enum machine_mode vmode = GET_MODE (operands[2]);
9610   rtx tmp;
9611   
9612   operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0);
9613   operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0);
9614   if (operands_match_p (operands[0], operands[2]))
9615     {
9616       tmp = operands[1];
9617       operands[1] = operands[2];
9618       operands[2] = tmp;
9619     }
9620   if (GET_CODE (operands[3]) == ABS)
9621     tmp = gen_rtx_AND (vmode, operands[1], operands[2]);
9622   else
9623     tmp = gen_rtx_XOR (vmode, operands[1], operands[2]);
9624   operands[3] = tmp;
9627 (define_split
9628   [(set (match_operand:SF 0 "register_operand" "")
9629         (match_operator:SF 1 "absneg_operator" [(match_dup 0)]))
9630    (use (match_operand:V4SF 2 "" ""))
9631    (clobber (reg:CC FLAGS_REG))]
9632   "reload_completed"
9633   [(parallel [(set (match_dup 0) (match_dup 1))
9634               (clobber (reg:CC FLAGS_REG))])]
9636   rtx tmp;
9637   operands[0] = gen_lowpart (SImode, operands[0]);
9638   if (GET_CODE (operands[1]) == ABS)
9639     {
9640       tmp = gen_int_mode (0x7fffffff, SImode);
9641       tmp = gen_rtx_AND (SImode, operands[0], tmp);
9642     }
9643   else
9644     {
9645       tmp = gen_int_mode (0x80000000, SImode);
9646       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9647     }
9648   operands[1] = tmp;
9651 (define_split
9652   [(set (match_operand:DF 0 "register_operand" "")
9653         (match_operator:DF 1 "absneg_operator" [(match_dup 0)]))
9654    (use (match_operand 2 "" ""))
9655    (clobber (reg:CC FLAGS_REG))]
9656   "reload_completed"
9657   [(parallel [(set (match_dup 0) (match_dup 1))
9658               (clobber (reg:CC FLAGS_REG))])]
9660   rtx tmp;
9661   if (TARGET_64BIT)
9662     {
9663       tmp = gen_lowpart (DImode, operands[0]);
9664       tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63));
9665       operands[0] = tmp;
9667       if (GET_CODE (operands[1]) == ABS)
9668         tmp = const0_rtx;
9669       else
9670         tmp = gen_rtx_NOT (DImode, tmp);
9671     }
9672   else
9673     {
9674       operands[0] = gen_highpart (SImode, operands[0]);
9675       if (GET_CODE (operands[1]) == ABS)
9676         {
9677           tmp = gen_int_mode (0x7fffffff, SImode);
9678           tmp = gen_rtx_AND (SImode, operands[0], tmp);
9679         }
9680       else
9681         {
9682           tmp = gen_int_mode (0x80000000, SImode);
9683           tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9684         }
9685     }
9686   operands[1] = tmp;
9689 (define_split
9690   [(set (match_operand:XF 0 "register_operand" "")
9691         (match_operator:XF 1 "absneg_operator" [(match_dup 0)]))
9692    (use (match_operand 2 "" ""))
9693    (clobber (reg:CC FLAGS_REG))]
9694   "reload_completed"
9695   [(parallel [(set (match_dup 0) (match_dup 1))
9696               (clobber (reg:CC FLAGS_REG))])]
9698   rtx tmp;
9699   operands[0] = gen_rtx_REG (SImode,
9700                              true_regnum (operands[0])
9701                              + (TARGET_64BIT ? 1 : 2));
9702   if (GET_CODE (operands[1]) == ABS)
9703     {
9704       tmp = GEN_INT (0x7fff);
9705       tmp = gen_rtx_AND (SImode, operands[0], tmp);
9706     }
9707   else
9708     {
9709       tmp = GEN_INT (0x8000);
9710       tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9711     }
9712   operands[1] = tmp;
9715 (define_split
9716   [(set (match_operand 0 "memory_operand" "")
9717         (match_operator 1 "absneg_operator" [(match_dup 0)]))
9718    (use (match_operand 2 "" ""))
9719    (clobber (reg:CC FLAGS_REG))]
9720   "reload_completed"
9721   [(parallel [(set (match_dup 0) (match_dup 1))
9722               (clobber (reg:CC FLAGS_REG))])]
9724   enum machine_mode mode = GET_MODE (operands[0]);
9725   int size = mode == XFmode ? 10 : GET_MODE_SIZE (mode);
9726   rtx tmp;
9728   operands[0] = adjust_address (operands[0], QImode, size - 1);
9729   if (GET_CODE (operands[1]) == ABS)
9730     {
9731       tmp = gen_int_mode (0x7f, QImode);
9732       tmp = gen_rtx_AND (QImode, operands[0], tmp);
9733     }
9734   else
9735     {
9736       tmp = gen_int_mode (0x80, QImode);
9737       tmp = gen_rtx_XOR (QImode, operands[0], tmp);
9738     }
9739   operands[1] = tmp;
9742 ;; Conditionalize these after reload. If they match before reload, we 
9743 ;; lose the clobber and ability to use integer instructions.
9745 (define_insn "*negsf2_1"
9746   [(set (match_operand:SF 0 "register_operand" "=f")
9747         (neg:SF (match_operand:SF 1 "register_operand" "0")))]
9748   "TARGET_80387 && reload_completed"
9749   "fchs"
9750   [(set_attr "type" "fsgn")
9751    (set_attr "mode" "SF")])
9753 (define_insn "*negdf2_1"
9754   [(set (match_operand:DF 0 "register_operand" "=f")
9755         (neg:DF (match_operand:DF 1 "register_operand" "0")))]
9756   "TARGET_80387 && reload_completed"
9757   "fchs"
9758   [(set_attr "type" "fsgn")
9759    (set_attr "mode" "DF")])
9761 (define_insn "*negxf2_1"
9762   [(set (match_operand:XF 0 "register_operand" "=f")
9763         (neg:XF (match_operand:XF 1 "register_operand" "0")))]
9764   "TARGET_80387 && reload_completed"
9765   "fchs"
9766   [(set_attr "type" "fsgn")
9767    (set_attr "mode" "XF")])
9769 (define_insn "*abssf2_1"
9770   [(set (match_operand:SF 0 "register_operand" "=f")
9771         (abs:SF (match_operand:SF 1 "register_operand" "0")))]
9772   "TARGET_80387 && reload_completed"
9773   "fabs"
9774   [(set_attr "type" "fsgn")
9775    (set_attr "mode" "SF")])
9777 (define_insn "*absdf2_1"
9778   [(set (match_operand:DF 0 "register_operand" "=f")
9779         (abs:DF (match_operand:DF 1 "register_operand" "0")))]
9780   "TARGET_80387 && reload_completed"
9781   "fabs"
9782   [(set_attr "type" "fsgn")
9783    (set_attr "mode" "DF")])
9785 (define_insn "*absxf2_1"
9786   [(set (match_operand:XF 0 "register_operand" "=f")
9787         (abs:XF (match_operand:XF 1 "register_operand" "0")))]
9788   "TARGET_80387 && reload_completed"
9789   "fabs"
9790   [(set_attr "type" "fsgn")
9791    (set_attr "mode" "DF")])
9793 (define_insn "*negextendsfdf2"
9794   [(set (match_operand:DF 0 "register_operand" "=f")
9795         (neg:DF (float_extend:DF
9796                   (match_operand:SF 1 "register_operand" "0"))))]
9797   "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
9798   "fchs"
9799   [(set_attr "type" "fsgn")
9800    (set_attr "mode" "DF")])
9802 (define_insn "*negextenddfxf2"
9803   [(set (match_operand:XF 0 "register_operand" "=f")
9804         (neg:XF (float_extend:XF
9805                   (match_operand:DF 1 "register_operand" "0"))))]
9806   "TARGET_80387"
9807   "fchs"
9808   [(set_attr "type" "fsgn")
9809    (set_attr "mode" "XF")])
9811 (define_insn "*negextendsfxf2"
9812   [(set (match_operand:XF 0 "register_operand" "=f")
9813         (neg:XF (float_extend:XF
9814                   (match_operand:SF 1 "register_operand" "0"))))]
9815   "TARGET_80387"
9816   "fchs"
9817   [(set_attr "type" "fsgn")
9818    (set_attr "mode" "XF")])
9820 (define_insn "*absextendsfdf2"
9821   [(set (match_operand:DF 0 "register_operand" "=f")
9822         (abs:DF (float_extend:DF
9823                   (match_operand:SF 1 "register_operand" "0"))))]
9824   "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
9825   "fabs"
9826   [(set_attr "type" "fsgn")
9827    (set_attr "mode" "DF")])
9829 (define_insn "*absextenddfxf2"
9830   [(set (match_operand:XF 0 "register_operand" "=f")
9831         (abs:XF (float_extend:XF
9832           (match_operand:DF 1 "register_operand" "0"))))]
9833   "TARGET_80387"
9834   "fabs"
9835   [(set_attr "type" "fsgn")
9836    (set_attr "mode" "XF")])
9838 (define_insn "*absextendsfxf2"
9839   [(set (match_operand:XF 0 "register_operand" "=f")
9840         (abs:XF (float_extend:XF
9841           (match_operand:SF 1 "register_operand" "0"))))]
9842   "TARGET_80387"
9843   "fabs"
9844   [(set_attr "type" "fsgn")
9845    (set_attr "mode" "XF")])
9847 ;; One complement instructions
9849 (define_expand "one_cmpldi2"
9850   [(set (match_operand:DI 0 "nonimmediate_operand" "")
9851         (not:DI (match_operand:DI 1 "nonimmediate_operand" "")))]
9852   "TARGET_64BIT"
9853   "ix86_expand_unary_operator (NOT, DImode, operands); DONE;")
9855 (define_insn "*one_cmpldi2_1_rex64"
9856   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9857         (not:DI (match_operand:DI 1 "nonimmediate_operand" "0")))]
9858   "TARGET_64BIT && ix86_unary_operator_ok (NOT, DImode, operands)"
9859   "not{q}\t%0"
9860   [(set_attr "type" "negnot")
9861    (set_attr "mode" "DI")])
9863 (define_insn "*one_cmpldi2_2_rex64"
9864   [(set (reg FLAGS_REG)
9865         (compare (not:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
9866                  (const_int 0)))
9867    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9868         (not:DI (match_dup 1)))]
9869   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9870    && ix86_unary_operator_ok (NOT, DImode, operands)"
9871   "#"
9872   [(set_attr "type" "alu1")
9873    (set_attr "mode" "DI")])
9875 (define_split
9876   [(set (match_operand 0 "flags_reg_operand" "")
9877         (match_operator 2 "compare_operator"
9878           [(not:DI (match_operand:DI 3 "nonimmediate_operand" ""))
9879            (const_int 0)]))
9880    (set (match_operand:DI 1 "nonimmediate_operand" "")
9881         (not:DI (match_dup 3)))]
9882   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9883   [(parallel [(set (match_dup 0)
9884                    (match_op_dup 2
9885                      [(xor:DI (match_dup 3) (const_int -1))
9886                       (const_int 0)]))
9887               (set (match_dup 1)
9888                    (xor:DI (match_dup 3) (const_int -1)))])]
9889   "")
9891 (define_expand "one_cmplsi2"
9892   [(set (match_operand:SI 0 "nonimmediate_operand" "")
9893         (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
9894   ""
9895   "ix86_expand_unary_operator (NOT, SImode, operands); DONE;")
9897 (define_insn "*one_cmplsi2_1"
9898   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9899         (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))]
9900   "ix86_unary_operator_ok (NOT, SImode, operands)"
9901   "not{l}\t%0"
9902   [(set_attr "type" "negnot")
9903    (set_attr "mode" "SI")])
9905 ;; ??? Currently never generated - xor is used instead.
9906 (define_insn "*one_cmplsi2_1_zext"
9907   [(set (match_operand:DI 0 "register_operand" "=r")
9908         (zero_extend:DI (not:SI (match_operand:SI 1 "register_operand" "0"))))]
9909   "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
9910   "not{l}\t%k0"
9911   [(set_attr "type" "negnot")
9912    (set_attr "mode" "SI")])
9914 (define_insn "*one_cmplsi2_2"
9915   [(set (reg FLAGS_REG)
9916         (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
9917                  (const_int 0)))
9918    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9919         (not:SI (match_dup 1)))]
9920   "ix86_match_ccmode (insn, CCNOmode)
9921    && ix86_unary_operator_ok (NOT, SImode, operands)"
9922   "#"
9923   [(set_attr "type" "alu1")
9924    (set_attr "mode" "SI")])
9926 (define_split
9927   [(set (match_operand 0 "flags_reg_operand" "")
9928         (match_operator 2 "compare_operator"
9929           [(not:SI (match_operand:SI 3 "nonimmediate_operand" ""))
9930            (const_int 0)]))
9931    (set (match_operand:SI 1 "nonimmediate_operand" "")
9932         (not:SI (match_dup 3)))]
9933   "ix86_match_ccmode (insn, CCNOmode)"
9934   [(parallel [(set (match_dup 0)
9935                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
9936                                     (const_int 0)]))
9937               (set (match_dup 1)
9938                    (xor:SI (match_dup 3) (const_int -1)))])]
9939   "")
9941 ;; ??? Currently never generated - xor is used instead.
9942 (define_insn "*one_cmplsi2_2_zext"
9943   [(set (reg FLAGS_REG)
9944         (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
9945                  (const_int 0)))
9946    (set (match_operand:DI 0 "register_operand" "=r")
9947         (zero_extend:DI (not:SI (match_dup 1))))]
9948   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9949    && ix86_unary_operator_ok (NOT, SImode, operands)"
9950   "#"
9951   [(set_attr "type" "alu1")
9952    (set_attr "mode" "SI")])
9954 (define_split
9955   [(set (match_operand 0 "flags_reg_operand" "")
9956         (match_operator 2 "compare_operator"
9957           [(not:SI (match_operand:SI 3 "register_operand" ""))
9958            (const_int 0)]))
9959    (set (match_operand:DI 1 "register_operand" "")
9960         (zero_extend:DI (not:SI (match_dup 3))))]
9961   "ix86_match_ccmode (insn, CCNOmode)"
9962   [(parallel [(set (match_dup 0)
9963                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
9964                                     (const_int 0)]))
9965               (set (match_dup 1)
9966                    (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])]
9967   "")
9969 (define_expand "one_cmplhi2"
9970   [(set (match_operand:HI 0 "nonimmediate_operand" "")
9971         (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
9972   "TARGET_HIMODE_MATH"
9973   "ix86_expand_unary_operator (NOT, HImode, operands); DONE;")
9975 (define_insn "*one_cmplhi2_1"
9976   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9977         (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))]
9978   "ix86_unary_operator_ok (NOT, HImode, operands)"
9979   "not{w}\t%0"
9980   [(set_attr "type" "negnot")
9981    (set_attr "mode" "HI")])
9983 (define_insn "*one_cmplhi2_2"
9984   [(set (reg FLAGS_REG)
9985         (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
9986                  (const_int 0)))
9987    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9988         (not:HI (match_dup 1)))]
9989   "ix86_match_ccmode (insn, CCNOmode)
9990    && ix86_unary_operator_ok (NEG, HImode, operands)"
9991   "#"
9992   [(set_attr "type" "alu1")
9993    (set_attr "mode" "HI")])
9995 (define_split
9996   [(set (match_operand 0 "flags_reg_operand" "")
9997         (match_operator 2 "compare_operator"
9998           [(not:HI (match_operand:HI 3 "nonimmediate_operand" ""))
9999            (const_int 0)]))
10000    (set (match_operand:HI 1 "nonimmediate_operand" "")
10001         (not:HI (match_dup 3)))]
10002   "ix86_match_ccmode (insn, CCNOmode)"
10003   [(parallel [(set (match_dup 0)
10004                    (match_op_dup 2 [(xor:HI (match_dup 3) (const_int -1))
10005                                     (const_int 0)]))
10006               (set (match_dup 1)
10007                    (xor:HI (match_dup 3) (const_int -1)))])]
10008   "")
10010 ;; %%% Potential partial reg stall on alternative 1.  What to do?
10011 (define_expand "one_cmplqi2"
10012   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10013         (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
10014   "TARGET_QIMODE_MATH"
10015   "ix86_expand_unary_operator (NOT, QImode, operands); DONE;")
10017 (define_insn "*one_cmplqi2_1"
10018   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10019         (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
10020   "ix86_unary_operator_ok (NOT, QImode, operands)"
10021   "@
10022    not{b}\t%0
10023    not{l}\t%k0"
10024   [(set_attr "type" "negnot")
10025    (set_attr "mode" "QI,SI")])
10027 (define_insn "*one_cmplqi2_2"
10028   [(set (reg FLAGS_REG)
10029         (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
10030                  (const_int 0)))
10031    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10032         (not:QI (match_dup 1)))]
10033   "ix86_match_ccmode (insn, CCNOmode)
10034    && ix86_unary_operator_ok (NOT, QImode, operands)"
10035   "#"
10036   [(set_attr "type" "alu1")
10037    (set_attr "mode" "QI")])
10039 (define_split
10040   [(set (match_operand 0 "flags_reg_operand" "")
10041         (match_operator 2 "compare_operator"
10042           [(not:QI (match_operand:QI 3 "nonimmediate_operand" ""))
10043            (const_int 0)]))
10044    (set (match_operand:QI 1 "nonimmediate_operand" "")
10045         (not:QI (match_dup 3)))]
10046   "ix86_match_ccmode (insn, CCNOmode)"
10047   [(parallel [(set (match_dup 0)
10048                    (match_op_dup 2 [(xor:QI (match_dup 3) (const_int -1))
10049                                     (const_int 0)]))
10050               (set (match_dup 1)
10051                    (xor:QI (match_dup 3) (const_int -1)))])]
10052   "")
10054 ;; Arithmetic shift instructions
10056 ;; DImode shifts are implemented using the i386 "shift double" opcode,
10057 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem".  If the shift count
10058 ;; is variable, then the count is in %cl and the "imm" operand is dropped
10059 ;; from the assembler input.
10061 ;; This instruction shifts the target reg/mem as usual, but instead of
10062 ;; shifting in zeros, bits are shifted in from reg operand.  If the insn
10063 ;; is a left shift double, bits are taken from the high order bits of
10064 ;; reg, else if the insn is a shift right double, bits are taken from the
10065 ;; low order bits of reg.  So if %eax is "1234" and %edx is "5678",
10066 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
10068 ;; Since sh[lr]d does not change the `reg' operand, that is done
10069 ;; separately, making all shifts emit pairs of shift double and normal
10070 ;; shift.  Since sh[lr]d does not shift more than 31 bits, and we wish to
10071 ;; support a 63 bit shift, each shift where the count is in a reg expands
10072 ;; to a pair of shifts, a branch, a shift by 32 and a label.
10074 ;; If the shift count is a constant, we need never emit more than one
10075 ;; shift pair, instead using moves and sign extension for counts greater
10076 ;; than 31.
10078 (define_expand "ashldi3"
10079   [(set (match_operand:DI 0 "shiftdi_operand" "")
10080         (ashift:DI (match_operand:DI 1 "ashldi_input_operand" "")
10081                    (match_operand:QI 2 "nonmemory_operand" "")))]
10082   ""
10083   "ix86_expand_binary_operator (ASHIFT, DImode, operands); DONE;")
10085 (define_insn "*ashldi3_1_rex64"
10086   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
10087         (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0,l")
10088                    (match_operand:QI 2 "nonmemory_operand" "cJ,M")))
10089    (clobber (reg:CC FLAGS_REG))]
10090   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10092   switch (get_attr_type (insn))
10093     {
10094     case TYPE_ALU:
10095       if (operands[2] != const1_rtx)
10096         abort ();
10097       if (!rtx_equal_p (operands[0], operands[1]))
10098         abort ();
10099       return "add{q}\t{%0, %0|%0, %0}";
10101     case TYPE_LEA:
10102       if (GET_CODE (operands[2]) != CONST_INT
10103           || (unsigned HOST_WIDE_INT) INTVAL (operands[2]) > 3)
10104         abort ();
10105       operands[1] = gen_rtx_MULT (DImode, operands[1],
10106                                   GEN_INT (1 << INTVAL (operands[2])));
10107       return "lea{q}\t{%a1, %0|%0, %a1}";
10109     default:
10110       if (REG_P (operands[2]))
10111         return "sal{q}\t{%b2, %0|%0, %b2}";
10112       else if (operands[2] == const1_rtx
10113                && (TARGET_SHIFT1 || optimize_size))
10114         return "sal{q}\t%0";
10115       else
10116         return "sal{q}\t{%2, %0|%0, %2}";
10117     }
10119   [(set (attr "type")
10120      (cond [(eq_attr "alternative" "1")
10121               (const_string "lea")
10122             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10123                           (const_int 0))
10124                       (match_operand 0 "register_operand" ""))
10125                  (match_operand 2 "const1_operand" ""))
10126               (const_string "alu")
10127            ]
10128            (const_string "ishift")))
10129    (set_attr "mode" "DI")])
10131 ;; Convert lea to the lea pattern to avoid flags dependency.
10132 (define_split
10133   [(set (match_operand:DI 0 "register_operand" "")
10134         (ashift:DI (match_operand:DI 1 "index_register_operand" "")
10135                    (match_operand:QI 2 "immediate_operand" "")))
10136    (clobber (reg:CC FLAGS_REG))]
10137   "TARGET_64BIT && reload_completed
10138    && true_regnum (operands[0]) != true_regnum (operands[1])"
10139   [(set (match_dup 0)
10140         (mult:DI (match_dup 1)
10141                  (match_dup 2)))]
10142   "operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);")
10144 ;; This pattern can't accept a variable shift count, since shifts by
10145 ;; zero don't affect the flags.  We assume that shifts by constant
10146 ;; zero are optimized away.
10147 (define_insn "*ashldi3_cmp_rex64"
10148   [(set (reg FLAGS_REG)
10149         (compare
10150           (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10151                      (match_operand:QI 2 "immediate_operand" "e"))
10152           (const_int 0)))
10153    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10154         (ashift:DI (match_dup 1) (match_dup 2)))]
10155   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10156    && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10158   switch (get_attr_type (insn))
10159     {
10160     case TYPE_ALU:
10161       if (operands[2] != const1_rtx)
10162         abort ();
10163       return "add{q}\t{%0, %0|%0, %0}";
10165     default:
10166       if (REG_P (operands[2]))
10167         return "sal{q}\t{%b2, %0|%0, %b2}";
10168       else if (operands[2] == const1_rtx
10169                && (TARGET_SHIFT1 || optimize_size))
10170         return "sal{q}\t%0";
10171       else
10172         return "sal{q}\t{%2, %0|%0, %2}";
10173     }
10175   [(set (attr "type")
10176      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10177                           (const_int 0))
10178                       (match_operand 0 "register_operand" ""))
10179                  (match_operand 2 "const1_operand" ""))
10180               (const_string "alu")
10181            ]
10182            (const_string "ishift")))
10183    (set_attr "mode" "DI")])
10185 (define_insn "*ashldi3_1"
10186   [(set (match_operand:DI 0 "register_operand" "=&r,r")
10187         (ashift:DI (match_operand:DI 1 "reg_or_pm1_operand" "n,0")
10188                    (match_operand:QI 2 "nonmemory_operand" "Jc,Jc")))
10189    (clobber (reg:CC FLAGS_REG))]
10190   "!TARGET_64BIT"
10191   "#"
10192   [(set_attr "type" "multi")])
10194 ;; By default we don't ask for a scratch register, because when DImode
10195 ;; values are manipulated, registers are already at a premium.  But if
10196 ;; we have one handy, we won't turn it away.
10197 (define_peephole2
10198   [(match_scratch:SI 3 "r")
10199    (parallel [(set (match_operand:DI 0 "register_operand" "")
10200                    (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
10201                               (match_operand:QI 2 "nonmemory_operand" "")))
10202               (clobber (reg:CC FLAGS_REG))])
10203    (match_dup 3)]
10204   "!TARGET_64BIT && TARGET_CMOVE"
10205   [(const_int 0)]
10206   "ix86_split_ashldi (operands, operands[3]); DONE;")
10208 (define_split
10209   [(set (match_operand:DI 0 "register_operand" "")
10210         (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
10211                    (match_operand:QI 2 "nonmemory_operand" "")))
10212    (clobber (reg:CC FLAGS_REG))]
10213   "!TARGET_64BIT && (flag_peephole2 ? flow2_completed : reload_completed)"
10214   [(const_int 0)]
10215   "ix86_split_ashldi (operands, NULL_RTX); DONE;")
10217 (define_insn "x86_shld_1"
10218   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
10219         (ior:SI (ashift:SI (match_dup 0)
10220                   (match_operand:QI 2 "nonmemory_operand" "I,c"))
10221                 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
10222                   (minus:QI (const_int 32) (match_dup 2)))))
10223    (clobber (reg:CC FLAGS_REG))]
10224   ""
10225   "@
10226    shld{l}\t{%2, %1, %0|%0, %1, %2}
10227    shld{l}\t{%s2%1, %0|%0, %1, %2}"
10228   [(set_attr "type" "ishift")
10229    (set_attr "prefix_0f" "1")
10230    (set_attr "mode" "SI")
10231    (set_attr "pent_pair" "np")
10232    (set_attr "athlon_decode" "vector")])
10234 (define_expand "x86_shift_adj_1"
10235   [(set (reg:CCZ FLAGS_REG)
10236         (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
10237                              (const_int 32))
10238                      (const_int 0)))
10239    (set (match_operand:SI 0 "register_operand" "")
10240         (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10241                          (match_operand:SI 1 "register_operand" "")
10242                          (match_dup 0)))
10243    (set (match_dup 1)
10244         (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10245                          (match_operand:SI 3 "register_operand" "r")
10246                          (match_dup 1)))]
10247   "TARGET_CMOVE"
10248   "")
10250 (define_expand "x86_shift_adj_2"
10251   [(use (match_operand:SI 0 "register_operand" ""))
10252    (use (match_operand:SI 1 "register_operand" ""))
10253    (use (match_operand:QI 2 "register_operand" ""))]
10254   ""
10256   rtx label = gen_label_rtx ();
10257   rtx tmp;
10259   emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
10261   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
10262   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
10263   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
10264                               gen_rtx_LABEL_REF (VOIDmode, label),
10265                               pc_rtx);
10266   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
10267   JUMP_LABEL (tmp) = label;
10269   emit_move_insn (operands[0], operands[1]);
10270   ix86_expand_clear (operands[1]);
10272   emit_label (label);
10273   LABEL_NUSES (label) = 1;
10275   DONE;
10278 (define_expand "ashlsi3"
10279   [(set (match_operand:SI 0 "nonimmediate_operand" "")
10280         (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
10281                    (match_operand:QI 2 "nonmemory_operand" "")))
10282    (clobber (reg:CC FLAGS_REG))]
10283   ""
10284   "ix86_expand_binary_operator (ASHIFT, SImode, operands); DONE;")
10286 (define_insn "*ashlsi3_1"
10287   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
10288         (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l")
10289                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
10290    (clobber (reg:CC FLAGS_REG))]
10291   "ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10293   switch (get_attr_type (insn))
10294     {
10295     case TYPE_ALU:
10296       if (operands[2] != const1_rtx)
10297         abort ();
10298       if (!rtx_equal_p (operands[0], operands[1]))
10299         abort ();
10300       return "add{l}\t{%0, %0|%0, %0}";
10302     case TYPE_LEA:
10303       return "#";
10305     default:
10306       if (REG_P (operands[2]))
10307         return "sal{l}\t{%b2, %0|%0, %b2}";
10308       else if (operands[2] == const1_rtx
10309                && (TARGET_SHIFT1 || optimize_size))
10310         return "sal{l}\t%0";
10311       else
10312         return "sal{l}\t{%2, %0|%0, %2}";
10313     }
10315   [(set (attr "type")
10316      (cond [(eq_attr "alternative" "1")
10317               (const_string "lea")
10318             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10319                           (const_int 0))
10320                       (match_operand 0 "register_operand" ""))
10321                  (match_operand 2 "const1_operand" ""))
10322               (const_string "alu")
10323            ]
10324            (const_string "ishift")))
10325    (set_attr "mode" "SI")])
10327 ;; Convert lea to the lea pattern to avoid flags dependency.
10328 (define_split
10329   [(set (match_operand 0 "register_operand" "")
10330         (ashift (match_operand 1 "index_register_operand" "")
10331                 (match_operand:QI 2 "const_int_operand" "")))
10332    (clobber (reg:CC FLAGS_REG))]
10333   "reload_completed
10334    && true_regnum (operands[0]) != true_regnum (operands[1])
10335    && GET_MODE_SIZE (GET_MODE (operands[0])) <= 4"
10336   [(const_int 0)]
10338   rtx pat;
10339   enum machine_mode mode = GET_MODE (operands[0]);
10341   if (GET_MODE_SIZE (mode) < 4)
10342     operands[0] = gen_lowpart (SImode, operands[0]);
10343   if (mode != Pmode)
10344     operands[1] = gen_lowpart (Pmode, operands[1]);
10345   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
10347   pat = gen_rtx_MULT (Pmode, operands[1], operands[2]);
10348   if (Pmode != SImode)
10349     pat = gen_rtx_SUBREG (SImode, pat, 0);
10350   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
10351   DONE;
10354 ;; Rare case of shifting RSP is handled by generating move and shift
10355 (define_split
10356   [(set (match_operand 0 "register_operand" "")
10357         (ashift (match_operand 1 "register_operand" "")
10358                 (match_operand:QI 2 "const_int_operand" "")))
10359    (clobber (reg:CC FLAGS_REG))]
10360   "reload_completed
10361    && true_regnum (operands[0]) != true_regnum (operands[1])"
10362   [(const_int 0)]
10364   rtx pat, clob;
10365   emit_move_insn (operands[1], operands[0]);
10366   pat = gen_rtx_SET (VOIDmode, operands[0],
10367                      gen_rtx_ASHIFT (GET_MODE (operands[0]),
10368                                      operands[0], operands[2]));
10369   clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
10370   emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, pat, clob)));
10371   DONE;
10374 (define_insn "*ashlsi3_1_zext"
10375   [(set (match_operand:DI 0 "register_operand" "=r,r")
10376         (zero_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "0,l")
10377                         (match_operand:QI 2 "nonmemory_operand" "cI,M"))))
10378    (clobber (reg:CC FLAGS_REG))]
10379   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10381   switch (get_attr_type (insn))
10382     {
10383     case TYPE_ALU:
10384       if (operands[2] != const1_rtx)
10385         abort ();
10386       return "add{l}\t{%k0, %k0|%k0, %k0}";
10388     case TYPE_LEA:
10389       return "#";
10391     default:
10392       if (REG_P (operands[2]))
10393         return "sal{l}\t{%b2, %k0|%k0, %b2}";
10394       else if (operands[2] == const1_rtx
10395                && (TARGET_SHIFT1 || optimize_size))
10396         return "sal{l}\t%k0";
10397       else
10398         return "sal{l}\t{%2, %k0|%k0, %2}";
10399     }
10401   [(set (attr "type")
10402      (cond [(eq_attr "alternative" "1")
10403               (const_string "lea")
10404             (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10405                      (const_int 0))
10406                  (match_operand 2 "const1_operand" ""))
10407               (const_string "alu")
10408            ]
10409            (const_string "ishift")))
10410    (set_attr "mode" "SI")])
10412 ;; Convert lea to the lea pattern to avoid flags dependency.
10413 (define_split
10414   [(set (match_operand:DI 0 "register_operand" "")
10415         (zero_extend:DI (ashift (match_operand 1 "register_operand" "")
10416                                 (match_operand:QI 2 "const_int_operand" ""))))
10417    (clobber (reg:CC FLAGS_REG))]
10418   "TARGET_64BIT && reload_completed
10419    && true_regnum (operands[0]) != true_regnum (operands[1])"
10420   [(set (match_dup 0) (zero_extend:DI
10421                         (subreg:SI (mult:SI (match_dup 1)
10422                                             (match_dup 2)) 0)))]
10424   operands[1] = gen_lowpart (Pmode, operands[1]);
10425   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
10428 ;; This pattern can't accept a variable shift count, since shifts by
10429 ;; zero don't affect the flags.  We assume that shifts by constant
10430 ;; zero are optimized away.
10431 (define_insn "*ashlsi3_cmp"
10432   [(set (reg FLAGS_REG)
10433         (compare
10434           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
10435                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
10436           (const_int 0)))
10437    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10438         (ashift:SI (match_dup 1) (match_dup 2)))]
10439   "ix86_match_ccmode (insn, CCGOCmode)
10440    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10442   switch (get_attr_type (insn))
10443     {
10444     case TYPE_ALU:
10445       if (operands[2] != const1_rtx)
10446         abort ();
10447       return "add{l}\t{%0, %0|%0, %0}";
10449     default:
10450       if (REG_P (operands[2]))
10451         return "sal{l}\t{%b2, %0|%0, %b2}";
10452       else if (operands[2] == const1_rtx
10453                && (TARGET_SHIFT1 || optimize_size))
10454         return "sal{l}\t%0";
10455       else
10456         return "sal{l}\t{%2, %0|%0, %2}";
10457     }
10459   [(set (attr "type")
10460      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10461                           (const_int 0))
10462                       (match_operand 0 "register_operand" ""))
10463                  (match_operand 2 "const1_operand" ""))
10464               (const_string "alu")
10465            ]
10466            (const_string "ishift")))
10467    (set_attr "mode" "SI")])
10469 (define_insn "*ashlsi3_cmp_zext"
10470   [(set (reg FLAGS_REG)
10471         (compare
10472           (ashift:SI (match_operand:SI 1 "register_operand" "0")
10473                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
10474           (const_int 0)))
10475    (set (match_operand:DI 0 "register_operand" "=r")
10476         (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
10477   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10478    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10480   switch (get_attr_type (insn))
10481     {
10482     case TYPE_ALU:
10483       if (operands[2] != const1_rtx)
10484         abort ();
10485       return "add{l}\t{%k0, %k0|%k0, %k0}";
10487     default:
10488       if (REG_P (operands[2]))
10489         return "sal{l}\t{%b2, %k0|%k0, %b2}";
10490       else if (operands[2] == const1_rtx
10491                && (TARGET_SHIFT1 || optimize_size))
10492         return "sal{l}\t%k0";
10493       else
10494         return "sal{l}\t{%2, %k0|%k0, %2}";
10495     }
10497   [(set (attr "type")
10498      (cond [(and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10499                      (const_int 0))
10500                  (match_operand 2 "const1_operand" ""))
10501               (const_string "alu")
10502            ]
10503            (const_string "ishift")))
10504    (set_attr "mode" "SI")])
10506 (define_expand "ashlhi3"
10507   [(set (match_operand:HI 0 "nonimmediate_operand" "")
10508         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "")
10509                    (match_operand:QI 2 "nonmemory_operand" "")))
10510    (clobber (reg:CC FLAGS_REG))]
10511   "TARGET_HIMODE_MATH"
10512   "ix86_expand_binary_operator (ASHIFT, HImode, operands); DONE;")
10514 (define_insn "*ashlhi3_1_lea"
10515   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
10516         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
10517                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
10518    (clobber (reg:CC FLAGS_REG))]
10519   "!TARGET_PARTIAL_REG_STALL
10520    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10522   switch (get_attr_type (insn))
10523     {
10524     case TYPE_LEA:
10525       return "#";
10526     case TYPE_ALU:
10527       if (operands[2] != const1_rtx)
10528         abort ();
10529       return "add{w}\t{%0, %0|%0, %0}";
10531     default:
10532       if (REG_P (operands[2]))
10533         return "sal{w}\t{%b2, %0|%0, %b2}";
10534       else if (operands[2] == const1_rtx
10535                && (TARGET_SHIFT1 || optimize_size))
10536         return "sal{w}\t%0";
10537       else
10538         return "sal{w}\t{%2, %0|%0, %2}";
10539     }
10541   [(set (attr "type")
10542      (cond [(eq_attr "alternative" "1")
10543               (const_string "lea")
10544             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10545                           (const_int 0))
10546                       (match_operand 0 "register_operand" ""))
10547                  (match_operand 2 "const1_operand" ""))
10548               (const_string "alu")
10549            ]
10550            (const_string "ishift")))
10551    (set_attr "mode" "HI,SI")])
10553 (define_insn "*ashlhi3_1"
10554   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10555         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
10556                    (match_operand:QI 2 "nonmemory_operand" "cI")))
10557    (clobber (reg:CC FLAGS_REG))]
10558   "TARGET_PARTIAL_REG_STALL
10559    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10561   switch (get_attr_type (insn))
10562     {
10563     case TYPE_ALU:
10564       if (operands[2] != const1_rtx)
10565         abort ();
10566       return "add{w}\t{%0, %0|%0, %0}";
10568     default:
10569       if (REG_P (operands[2]))
10570         return "sal{w}\t{%b2, %0|%0, %b2}";
10571       else if (operands[2] == const1_rtx
10572                && (TARGET_SHIFT1 || optimize_size))
10573         return "sal{w}\t%0";
10574       else
10575         return "sal{w}\t{%2, %0|%0, %2}";
10576     }
10578   [(set (attr "type")
10579      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10580                           (const_int 0))
10581                       (match_operand 0 "register_operand" ""))
10582                  (match_operand 2 "const1_operand" ""))
10583               (const_string "alu")
10584            ]
10585            (const_string "ishift")))
10586    (set_attr "mode" "HI")])
10588 ;; This pattern can't accept a variable shift count, since shifts by
10589 ;; zero don't affect the flags.  We assume that shifts by constant
10590 ;; zero are optimized away.
10591 (define_insn "*ashlhi3_cmp"
10592   [(set (reg FLAGS_REG)
10593         (compare
10594           (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
10595                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
10596           (const_int 0)))
10597    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10598         (ashift:HI (match_dup 1) (match_dup 2)))]
10599   "ix86_match_ccmode (insn, CCGOCmode)
10600    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10602   switch (get_attr_type (insn))
10603     {
10604     case TYPE_ALU:
10605       if (operands[2] != const1_rtx)
10606         abort ();
10607       return "add{w}\t{%0, %0|%0, %0}";
10609     default:
10610       if (REG_P (operands[2]))
10611         return "sal{w}\t{%b2, %0|%0, %b2}";
10612       else if (operands[2] == const1_rtx
10613                && (TARGET_SHIFT1 || optimize_size))
10614         return "sal{w}\t%0";
10615       else
10616         return "sal{w}\t{%2, %0|%0, %2}";
10617     }
10619   [(set (attr "type")
10620      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10621                           (const_int 0))
10622                       (match_operand 0 "register_operand" ""))
10623                  (match_operand 2 "const1_operand" ""))
10624               (const_string "alu")
10625            ]
10626            (const_string "ishift")))
10627    (set_attr "mode" "HI")])
10629 (define_expand "ashlqi3"
10630   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10631         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "")
10632                    (match_operand:QI 2 "nonmemory_operand" "")))
10633    (clobber (reg:CC FLAGS_REG))]
10634   "TARGET_QIMODE_MATH"
10635   "ix86_expand_binary_operator (ASHIFT, QImode, operands); DONE;")
10637 ;; %%% Potential partial reg stall on alternative 2.  What to do?
10639 (define_insn "*ashlqi3_1_lea"
10640   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r")
10641         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
10642                    (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
10643    (clobber (reg:CC FLAGS_REG))]
10644   "!TARGET_PARTIAL_REG_STALL
10645    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10647   switch (get_attr_type (insn))
10648     {
10649     case TYPE_LEA:
10650       return "#";
10651     case TYPE_ALU:
10652       if (operands[2] != const1_rtx)
10653         abort ();
10654       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
10655         return "add{l}\t{%k0, %k0|%k0, %k0}";
10656       else
10657         return "add{b}\t{%0, %0|%0, %0}";
10659     default:
10660       if (REG_P (operands[2]))
10661         {
10662           if (get_attr_mode (insn) == MODE_SI)
10663             return "sal{l}\t{%b2, %k0|%k0, %b2}";
10664           else
10665             return "sal{b}\t{%b2, %0|%0, %b2}";
10666         }
10667       else if (operands[2] == const1_rtx
10668                && (TARGET_SHIFT1 || optimize_size))
10669         {
10670           if (get_attr_mode (insn) == MODE_SI)
10671             return "sal{l}\t%0";
10672           else
10673             return "sal{b}\t%0";
10674         }
10675       else
10676         {
10677           if (get_attr_mode (insn) == MODE_SI)
10678             return "sal{l}\t{%2, %k0|%k0, %2}";
10679           else
10680             return "sal{b}\t{%2, %0|%0, %2}";
10681         }
10682     }
10684   [(set (attr "type")
10685      (cond [(eq_attr "alternative" "2")
10686               (const_string "lea")
10687             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10688                           (const_int 0))
10689                       (match_operand 0 "register_operand" ""))
10690                  (match_operand 2 "const1_operand" ""))
10691               (const_string "alu")
10692            ]
10693            (const_string "ishift")))
10694    (set_attr "mode" "QI,SI,SI")])
10696 (define_insn "*ashlqi3_1"
10697   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10698         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
10699                    (match_operand:QI 2 "nonmemory_operand" "cI,cI")))
10700    (clobber (reg:CC FLAGS_REG))]
10701   "TARGET_PARTIAL_REG_STALL
10702    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10704   switch (get_attr_type (insn))
10705     {
10706     case TYPE_ALU:
10707       if (operands[2] != const1_rtx)
10708         abort ();
10709       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
10710         return "add{l}\t{%k0, %k0|%k0, %k0}";
10711       else
10712         return "add{b}\t{%0, %0|%0, %0}";
10714     default:
10715       if (REG_P (operands[2]))
10716         {
10717           if (get_attr_mode (insn) == MODE_SI)
10718             return "sal{l}\t{%b2, %k0|%k0, %b2}";
10719           else
10720             return "sal{b}\t{%b2, %0|%0, %b2}";
10721         }
10722       else if (operands[2] == const1_rtx
10723                && (TARGET_SHIFT1 || optimize_size))
10724         {
10725           if (get_attr_mode (insn) == MODE_SI)
10726             return "sal{l}\t%0";
10727           else
10728             return "sal{b}\t%0";
10729         }
10730       else
10731         {
10732           if (get_attr_mode (insn) == MODE_SI)
10733             return "sal{l}\t{%2, %k0|%k0, %2}";
10734           else
10735             return "sal{b}\t{%2, %0|%0, %2}";
10736         }
10737     }
10739   [(set (attr "type")
10740      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10741                           (const_int 0))
10742                       (match_operand 0 "register_operand" ""))
10743                  (match_operand 2 "const1_operand" ""))
10744               (const_string "alu")
10745            ]
10746            (const_string "ishift")))
10747    (set_attr "mode" "QI,SI")])
10749 ;; This pattern can't accept a variable shift count, since shifts by
10750 ;; zero don't affect the flags.  We assume that shifts by constant
10751 ;; zero are optimized away.
10752 (define_insn "*ashlqi3_cmp"
10753   [(set (reg FLAGS_REG)
10754         (compare
10755           (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
10756                      (match_operand:QI 2 "const_1_to_31_operand" "I"))
10757           (const_int 0)))
10758    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10759         (ashift:QI (match_dup 1) (match_dup 2)))]
10760   "ix86_match_ccmode (insn, CCGOCmode)
10761    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10763   switch (get_attr_type (insn))
10764     {
10765     case TYPE_ALU:
10766       if (operands[2] != const1_rtx)
10767         abort ();
10768       return "add{b}\t{%0, %0|%0, %0}";
10770     default:
10771       if (REG_P (operands[2]))
10772         return "sal{b}\t{%b2, %0|%0, %b2}";
10773       else if (operands[2] == const1_rtx
10774                && (TARGET_SHIFT1 || optimize_size))
10775         return "sal{b}\t%0";
10776       else
10777         return "sal{b}\t{%2, %0|%0, %2}";
10778     }
10780   [(set (attr "type")
10781      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10782                           (const_int 0))
10783                       (match_operand 0 "register_operand" ""))
10784                  (match_operand 2 "const1_operand" ""))
10785               (const_string "alu")
10786            ]
10787            (const_string "ishift")))
10788    (set_attr "mode" "QI")])
10790 ;; See comment above `ashldi3' about how this works.
10792 (define_expand "ashrdi3"
10793   [(set (match_operand:DI 0 "shiftdi_operand" "")
10794         (ashiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
10795                      (match_operand:QI 2 "nonmemory_operand" "")))]
10796   ""
10797   "ix86_expand_binary_operator (ASHIFTRT, DImode, operands); DONE;")
10799 (define_insn "*ashrdi3_63_rex64"
10800   [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
10801         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
10802                      (match_operand:DI 2 "const_int_operand" "i,i")))
10803    (clobber (reg:CC FLAGS_REG))]
10804   "TARGET_64BIT && INTVAL (operands[2]) == 63
10805    && (TARGET_USE_CLTD || optimize_size)
10806    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
10807   "@
10808    {cqto|cqo}
10809    sar{q}\t{%2, %0|%0, %2}"
10810   [(set_attr "type" "imovx,ishift")
10811    (set_attr "prefix_0f" "0,*")
10812    (set_attr "length_immediate" "0,*")
10813    (set_attr "modrm" "0,1")
10814    (set_attr "mode" "DI")])
10816 (define_insn "*ashrdi3_1_one_bit_rex64"
10817   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10818         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10819                      (match_operand:QI 2 "const1_operand" "")))
10820    (clobber (reg:CC FLAGS_REG))]
10821   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)
10822    && (TARGET_SHIFT1 || optimize_size)"
10823   "sar{q}\t%0"
10824   [(set_attr "type" "ishift")
10825    (set (attr "length") 
10826      (if_then_else (match_operand:DI 0 "register_operand" "") 
10827         (const_string "2")
10828         (const_string "*")))])
10830 (define_insn "*ashrdi3_1_rex64"
10831   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
10832         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
10833                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
10834    (clobber (reg:CC FLAGS_REG))]
10835   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
10836   "@
10837    sar{q}\t{%2, %0|%0, %2}
10838    sar{q}\t{%b2, %0|%0, %b2}"
10839   [(set_attr "type" "ishift")
10840    (set_attr "mode" "DI")])
10842 ;; This pattern can't accept a variable shift count, since shifts by
10843 ;; zero don't affect the flags.  We assume that shifts by constant
10844 ;; zero are optimized away.
10845 (define_insn "*ashrdi3_one_bit_cmp_rex64"
10846   [(set (reg FLAGS_REG)
10847         (compare
10848           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10849                        (match_operand:QI 2 "const1_operand" ""))
10850           (const_int 0)))
10851    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10852         (ashiftrt:DI (match_dup 1) (match_dup 2)))]
10853   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10854    && (TARGET_SHIFT1 || optimize_size)
10855    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
10856   "sar{q}\t%0"
10857   [(set_attr "type" "ishift")
10858    (set (attr "length") 
10859      (if_then_else (match_operand:DI 0 "register_operand" "") 
10860         (const_string "2")
10861         (const_string "*")))])
10863 ;; This pattern can't accept a variable shift count, since shifts by
10864 ;; zero don't affect the flags.  We assume that shifts by constant
10865 ;; zero are optimized away.
10866 (define_insn "*ashrdi3_cmp_rex64"
10867   [(set (reg FLAGS_REG)
10868         (compare
10869           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10870                        (match_operand:QI 2 "const_int_operand" "n"))
10871           (const_int 0)))
10872    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10873         (ashiftrt:DI (match_dup 1) (match_dup 2)))]
10874   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10875    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
10876   "sar{q}\t{%2, %0|%0, %2}"
10877   [(set_attr "type" "ishift")
10878    (set_attr "mode" "DI")])
10880 (define_insn "*ashrdi3_1"
10881   [(set (match_operand:DI 0 "register_operand" "=r")
10882         (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
10883                      (match_operand:QI 2 "nonmemory_operand" "Jc")))
10884    (clobber (reg:CC FLAGS_REG))]
10885   "!TARGET_64BIT"
10886   "#"
10887   [(set_attr "type" "multi")])
10889 ;; By default we don't ask for a scratch register, because when DImode
10890 ;; values are manipulated, registers are already at a premium.  But if
10891 ;; we have one handy, we won't turn it away.
10892 (define_peephole2
10893   [(match_scratch:SI 3 "r")
10894    (parallel [(set (match_operand:DI 0 "register_operand" "")
10895                    (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
10896                                 (match_operand:QI 2 "nonmemory_operand" "")))
10897               (clobber (reg:CC FLAGS_REG))])
10898    (match_dup 3)]
10899   "!TARGET_64BIT && TARGET_CMOVE"
10900   [(const_int 0)]
10901   "ix86_split_ashrdi (operands, operands[3]); DONE;")
10903 (define_split
10904   [(set (match_operand:DI 0 "register_operand" "")
10905         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
10906                      (match_operand:QI 2 "nonmemory_operand" "")))
10907    (clobber (reg:CC FLAGS_REG))]
10908   "!TARGET_64BIT && (flag_peephole2 ? flow2_completed : reload_completed)"
10909   [(const_int 0)]
10910   "ix86_split_ashrdi (operands, NULL_RTX); DONE;")
10912 (define_insn "x86_shrd_1"
10913   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
10914         (ior:SI (ashiftrt:SI (match_dup 0)
10915                   (match_operand:QI 2 "nonmemory_operand" "I,c"))
10916                 (ashift:SI (match_operand:SI 1 "register_operand" "r,r")
10917                   (minus:QI (const_int 32) (match_dup 2)))))
10918    (clobber (reg:CC FLAGS_REG))]
10919   ""
10920   "@
10921    shrd{l}\t{%2, %1, %0|%0, %1, %2}
10922    shrd{l}\t{%s2%1, %0|%0, %1, %2}"
10923   [(set_attr "type" "ishift")
10924    (set_attr "prefix_0f" "1")
10925    (set_attr "pent_pair" "np")
10926    (set_attr "mode" "SI")])
10928 (define_expand "x86_shift_adj_3"
10929   [(use (match_operand:SI 0 "register_operand" ""))
10930    (use (match_operand:SI 1 "register_operand" ""))
10931    (use (match_operand:QI 2 "register_operand" ""))]
10932   ""
10934   rtx label = gen_label_rtx ();
10935   rtx tmp;
10937   emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
10939   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
10940   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
10941   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
10942                               gen_rtx_LABEL_REF (VOIDmode, label),
10943                               pc_rtx);
10944   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
10945   JUMP_LABEL (tmp) = label;
10947   emit_move_insn (operands[0], operands[1]);
10948   emit_insn (gen_ashrsi3_31 (operands[1], operands[1], GEN_INT (31)));
10950   emit_label (label);
10951   LABEL_NUSES (label) = 1;
10953   DONE;
10956 (define_insn "ashrsi3_31"
10957   [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
10958         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
10959                      (match_operand:SI 2 "const_int_operand" "i,i")))
10960    (clobber (reg:CC FLAGS_REG))]
10961   "INTVAL (operands[2]) == 31 && (TARGET_USE_CLTD || optimize_size)
10962    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
10963   "@
10964    {cltd|cdq}
10965    sar{l}\t{%2, %0|%0, %2}"
10966   [(set_attr "type" "imovx,ishift")
10967    (set_attr "prefix_0f" "0,*")
10968    (set_attr "length_immediate" "0,*")
10969    (set_attr "modrm" "0,1")
10970    (set_attr "mode" "SI")])
10972 (define_insn "*ashrsi3_31_zext"
10973   [(set (match_operand:DI 0 "register_operand" "=*d,r")
10974         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
10975                                      (match_operand:SI 2 "const_int_operand" "i,i"))))
10976    (clobber (reg:CC FLAGS_REG))]
10977   "TARGET_64BIT && (TARGET_USE_CLTD || optimize_size)
10978    && INTVAL (operands[2]) == 31
10979    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
10980   "@
10981    {cltd|cdq}
10982    sar{l}\t{%2, %k0|%k0, %2}"
10983   [(set_attr "type" "imovx,ishift")
10984    (set_attr "prefix_0f" "0,*")
10985    (set_attr "length_immediate" "0,*")
10986    (set_attr "modrm" "0,1")
10987    (set_attr "mode" "SI")])
10989 (define_expand "ashrsi3"
10990   [(set (match_operand:SI 0 "nonimmediate_operand" "")
10991         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
10992                      (match_operand:QI 2 "nonmemory_operand" "")))
10993    (clobber (reg:CC FLAGS_REG))]
10994   ""
10995   "ix86_expand_binary_operator (ASHIFTRT, SImode, operands); DONE;")
10997 (define_insn "*ashrsi3_1_one_bit"
10998   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10999         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11000                      (match_operand:QI 2 "const1_operand" "")))
11001    (clobber (reg:CC FLAGS_REG))]
11002   "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
11003    && (TARGET_SHIFT1 || optimize_size)"
11004   "sar{l}\t%0"
11005   [(set_attr "type" "ishift")
11006    (set (attr "length") 
11007      (if_then_else (match_operand:SI 0 "register_operand" "") 
11008         (const_string "2")
11009         (const_string "*")))])
11011 (define_insn "*ashrsi3_1_one_bit_zext"
11012   [(set (match_operand:DI 0 "register_operand" "=r")
11013         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11014                                      (match_operand:QI 2 "const1_operand" ""))))
11015    (clobber (reg:CC FLAGS_REG))]
11016   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
11017    && (TARGET_SHIFT1 || optimize_size)"
11018   "sar{l}\t%k0"
11019   [(set_attr "type" "ishift")
11020    (set_attr "length" "2")])
11022 (define_insn "*ashrsi3_1"
11023   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11024         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11025                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
11026    (clobber (reg:CC FLAGS_REG))]
11027   "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11028   "@
11029    sar{l}\t{%2, %0|%0, %2}
11030    sar{l}\t{%b2, %0|%0, %b2}"
11031   [(set_attr "type" "ishift")
11032    (set_attr "mode" "SI")])
11034 (define_insn "*ashrsi3_1_zext"
11035   [(set (match_operand:DI 0 "register_operand" "=r,r")
11036         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0")
11037                                      (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11038    (clobber (reg:CC FLAGS_REG))]
11039   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11040   "@
11041    sar{l}\t{%2, %k0|%k0, %2}
11042    sar{l}\t{%b2, %k0|%k0, %b2}"
11043   [(set_attr "type" "ishift")
11044    (set_attr "mode" "SI")])
11046 ;; This pattern can't accept a variable shift count, since shifts by
11047 ;; zero don't affect the flags.  We assume that shifts by constant
11048 ;; zero are optimized away.
11049 (define_insn "*ashrsi3_one_bit_cmp"
11050   [(set (reg FLAGS_REG)
11051         (compare
11052           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11053                        (match_operand:QI 2 "const1_operand" ""))
11054           (const_int 0)))
11055    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11056         (ashiftrt:SI (match_dup 1) (match_dup 2)))]
11057   "ix86_match_ccmode (insn, CCGOCmode)
11058    && (TARGET_SHIFT1 || optimize_size)
11059    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11060   "sar{l}\t%0"
11061   [(set_attr "type" "ishift")
11062    (set (attr "length") 
11063      (if_then_else (match_operand:SI 0 "register_operand" "") 
11064         (const_string "2")
11065         (const_string "*")))])
11067 (define_insn "*ashrsi3_one_bit_cmp_zext"
11068   [(set (reg FLAGS_REG)
11069         (compare
11070           (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11071                        (match_operand:QI 2 "const1_operand" ""))
11072           (const_int 0)))
11073    (set (match_operand:DI 0 "register_operand" "=r")
11074         (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
11075   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
11076    && (TARGET_SHIFT1 || optimize_size)
11077    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11078   "sar{l}\t%k0"
11079   [(set_attr "type" "ishift")
11080    (set_attr "length" "2")])
11082 ;; This pattern can't accept a variable shift count, since shifts by
11083 ;; zero don't affect the flags.  We assume that shifts by constant
11084 ;; zero are optimized away.
11085 (define_insn "*ashrsi3_cmp"
11086   [(set (reg FLAGS_REG)
11087         (compare
11088           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11089                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
11090           (const_int 0)))
11091    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11092         (ashiftrt:SI (match_dup 1) (match_dup 2)))]
11093   "ix86_match_ccmode (insn, CCGOCmode)
11094    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11095   "sar{l}\t{%2, %0|%0, %2}"
11096   [(set_attr "type" "ishift")
11097    (set_attr "mode" "SI")])
11099 (define_insn "*ashrsi3_cmp_zext"
11100   [(set (reg FLAGS_REG)
11101         (compare
11102           (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11103                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
11104           (const_int 0)))
11105    (set (match_operand:DI 0 "register_operand" "=r")
11106         (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
11107   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11108    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11109   "sar{l}\t{%2, %k0|%k0, %2}"
11110   [(set_attr "type" "ishift")
11111    (set_attr "mode" "SI")])
11113 (define_expand "ashrhi3"
11114   [(set (match_operand:HI 0 "nonimmediate_operand" "")
11115         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
11116                      (match_operand:QI 2 "nonmemory_operand" "")))
11117    (clobber (reg:CC FLAGS_REG))]
11118   "TARGET_HIMODE_MATH"
11119   "ix86_expand_binary_operator (ASHIFTRT, HImode, operands); DONE;")
11121 (define_insn "*ashrhi3_1_one_bit"
11122   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11123         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11124                      (match_operand:QI 2 "const1_operand" "")))
11125    (clobber (reg:CC FLAGS_REG))]
11126   "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)
11127    && (TARGET_SHIFT1 || optimize_size)"
11128   "sar{w}\t%0"
11129   [(set_attr "type" "ishift")
11130    (set (attr "length") 
11131      (if_then_else (match_operand 0 "register_operand" "") 
11132         (const_string "2")
11133         (const_string "*")))])
11135 (define_insn "*ashrhi3_1"
11136   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11137         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11138                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
11139    (clobber (reg:CC FLAGS_REG))]
11140   "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11141   "@
11142    sar{w}\t{%2, %0|%0, %2}
11143    sar{w}\t{%b2, %0|%0, %b2}"
11144   [(set_attr "type" "ishift")
11145    (set_attr "mode" "HI")])
11147 ;; This pattern can't accept a variable shift count, since shifts by
11148 ;; zero don't affect the flags.  We assume that shifts by constant
11149 ;; zero are optimized away.
11150 (define_insn "*ashrhi3_one_bit_cmp"
11151   [(set (reg FLAGS_REG)
11152         (compare
11153           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11154                        (match_operand:QI 2 "const1_operand" ""))
11155           (const_int 0)))
11156    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11157         (ashiftrt:HI (match_dup 1) (match_dup 2)))]
11158   "ix86_match_ccmode (insn, CCGOCmode)
11159    && (TARGET_SHIFT1 || optimize_size)
11160    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11161   "sar{w}\t%0"
11162   [(set_attr "type" "ishift")
11163    (set (attr "length") 
11164      (if_then_else (match_operand 0 "register_operand" "") 
11165         (const_string "2")
11166         (const_string "*")))])
11168 ;; This pattern can't accept a variable shift count, since shifts by
11169 ;; zero don't affect the flags.  We assume that shifts by constant
11170 ;; zero are optimized away.
11171 (define_insn "*ashrhi3_cmp"
11172   [(set (reg FLAGS_REG)
11173         (compare
11174           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11175                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
11176           (const_int 0)))
11177    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11178         (ashiftrt:HI (match_dup 1) (match_dup 2)))]
11179   "ix86_match_ccmode (insn, CCGOCmode)
11180    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11181   "sar{w}\t{%2, %0|%0, %2}"
11182   [(set_attr "type" "ishift")
11183    (set_attr "mode" "HI")])
11185 (define_expand "ashrqi3"
11186   [(set (match_operand:QI 0 "nonimmediate_operand" "")
11187         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
11188                      (match_operand:QI 2 "nonmemory_operand" "")))
11189    (clobber (reg:CC FLAGS_REG))]
11190   "TARGET_QIMODE_MATH"
11191   "ix86_expand_binary_operator (ASHIFTRT, QImode, operands); DONE;")
11193 (define_insn "*ashrqi3_1_one_bit"
11194   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11195         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11196                      (match_operand:QI 2 "const1_operand" "")))
11197    (clobber (reg:CC FLAGS_REG))]
11198   "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
11199    && (TARGET_SHIFT1 || optimize_size)"
11200   "sar{b}\t%0"
11201   [(set_attr "type" "ishift")
11202    (set (attr "length") 
11203      (if_then_else (match_operand 0 "register_operand" "") 
11204         (const_string "2")
11205         (const_string "*")))])
11207 (define_insn "*ashrqi3_1_one_bit_slp"
11208   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11209         (ashiftrt:QI (match_dup 0)
11210                      (match_operand:QI 1 "const1_operand" "")))
11211    (clobber (reg:CC FLAGS_REG))]
11212   "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
11213    && (! TARGET_PARTIAL_REG_STALL || optimize_size)
11214    && (TARGET_SHIFT1 || optimize_size)"
11215   "sar{b}\t%0"
11216   [(set_attr "type" "ishift1")
11217    (set (attr "length") 
11218      (if_then_else (match_operand 0 "register_operand" "") 
11219         (const_string "2")
11220         (const_string "*")))])
11222 (define_insn "*ashrqi3_1"
11223   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11224         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11225                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
11226    (clobber (reg:CC FLAGS_REG))]
11227   "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11228   "@
11229    sar{b}\t{%2, %0|%0, %2}
11230    sar{b}\t{%b2, %0|%0, %b2}"
11231   [(set_attr "type" "ishift")
11232    (set_attr "mode" "QI")])
11234 (define_insn "*ashrqi3_1_slp"
11235   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11236         (ashiftrt:QI (match_dup 0)
11237                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
11238    (clobber (reg:CC FLAGS_REG))]
11239   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11240    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11241   "@
11242    sar{b}\t{%1, %0|%0, %1}
11243    sar{b}\t{%b1, %0|%0, %b1}"
11244   [(set_attr "type" "ishift1")
11245    (set_attr "mode" "QI")])
11247 ;; This pattern can't accept a variable shift count, since shifts by
11248 ;; zero don't affect the flags.  We assume that shifts by constant
11249 ;; zero are optimized away.
11250 (define_insn "*ashrqi3_one_bit_cmp"
11251   [(set (reg FLAGS_REG)
11252         (compare
11253           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11254                        (match_operand:QI 2 "const1_operand" "I"))
11255           (const_int 0)))
11256    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11257         (ashiftrt:QI (match_dup 1) (match_dup 2)))]
11258   "ix86_match_ccmode (insn, CCGOCmode)
11259    && (TARGET_SHIFT1 || optimize_size)
11260    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11261   "sar{b}\t%0"
11262   [(set_attr "type" "ishift")
11263    (set (attr "length") 
11264      (if_then_else (match_operand 0 "register_operand" "") 
11265         (const_string "2")
11266         (const_string "*")))])
11268 ;; This pattern can't accept a variable shift count, since shifts by
11269 ;; zero don't affect the flags.  We assume that shifts by constant
11270 ;; zero are optimized away.
11271 (define_insn "*ashrqi3_cmp"
11272   [(set (reg FLAGS_REG)
11273         (compare
11274           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11275                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
11276           (const_int 0)))
11277    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11278         (ashiftrt:QI (match_dup 1) (match_dup 2)))]
11279   "ix86_match_ccmode (insn, CCGOCmode)
11280    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11281   "sar{b}\t{%2, %0|%0, %2}"
11282   [(set_attr "type" "ishift")
11283    (set_attr "mode" "QI")])
11285 ;; Logical shift instructions
11287 ;; See comment above `ashldi3' about how this works.
11289 (define_expand "lshrdi3"
11290   [(set (match_operand:DI 0 "shiftdi_operand" "")
11291         (lshiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
11292                      (match_operand:QI 2 "nonmemory_operand" "")))]
11293   ""
11294   "ix86_expand_binary_operator (LSHIFTRT, DImode, operands); DONE;")
11296 (define_insn "*lshrdi3_1_one_bit_rex64"
11297   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11298         (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11299                      (match_operand:QI 2 "const1_operand" "")))
11300    (clobber (reg:CC FLAGS_REG))]
11301   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11302    && (TARGET_SHIFT1 || optimize_size)"
11303   "shr{q}\t%0"
11304   [(set_attr "type" "ishift")
11305    (set (attr "length") 
11306      (if_then_else (match_operand:DI 0 "register_operand" "") 
11307         (const_string "2")
11308         (const_string "*")))])
11310 (define_insn "*lshrdi3_1_rex64"
11311   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11312         (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11313                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
11314    (clobber (reg:CC FLAGS_REG))]
11315   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11316   "@
11317    shr{q}\t{%2, %0|%0, %2}
11318    shr{q}\t{%b2, %0|%0, %b2}"
11319   [(set_attr "type" "ishift")
11320    (set_attr "mode" "DI")])
11322 ;; This pattern can't accept a variable shift count, since shifts by
11323 ;; zero don't affect the flags.  We assume that shifts by constant
11324 ;; zero are optimized away.
11325 (define_insn "*lshrdi3_cmp_one_bit_rex64"
11326   [(set (reg FLAGS_REG)
11327         (compare
11328           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11329                        (match_operand:QI 2 "const1_operand" ""))
11330           (const_int 0)))
11331    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11332         (lshiftrt:DI (match_dup 1) (match_dup 2)))]
11333   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11334    && (TARGET_SHIFT1 || optimize_size)
11335    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11336   "shr{q}\t%0"
11337   [(set_attr "type" "ishift")
11338    (set (attr "length") 
11339      (if_then_else (match_operand:DI 0 "register_operand" "") 
11340         (const_string "2")
11341         (const_string "*")))])
11343 ;; This pattern can't accept a variable shift count, since shifts by
11344 ;; zero don't affect the flags.  We assume that shifts by constant
11345 ;; zero are optimized away.
11346 (define_insn "*lshrdi3_cmp_rex64"
11347   [(set (reg FLAGS_REG)
11348         (compare
11349           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11350                        (match_operand:QI 2 "const_int_operand" "e"))
11351           (const_int 0)))
11352    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11353         (lshiftrt:DI (match_dup 1) (match_dup 2)))]
11354   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11355    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11356   "shr{q}\t{%2, %0|%0, %2}"
11357   [(set_attr "type" "ishift")
11358    (set_attr "mode" "DI")])
11360 (define_insn "*lshrdi3_1"
11361   [(set (match_operand:DI 0 "register_operand" "=r")
11362         (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
11363                      (match_operand:QI 2 "nonmemory_operand" "Jc")))
11364    (clobber (reg:CC FLAGS_REG))]
11365   "!TARGET_64BIT"
11366   "#"
11367   [(set_attr "type" "multi")])
11369 ;; By default we don't ask for a scratch register, because when DImode
11370 ;; values are manipulated, registers are already at a premium.  But if
11371 ;; we have one handy, we won't turn it away.
11372 (define_peephole2
11373   [(match_scratch:SI 3 "r")
11374    (parallel [(set (match_operand:DI 0 "register_operand" "")
11375                    (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
11376                                 (match_operand:QI 2 "nonmemory_operand" "")))
11377               (clobber (reg:CC FLAGS_REG))])
11378    (match_dup 3)]
11379   "!TARGET_64BIT && TARGET_CMOVE"
11380   [(const_int 0)]
11381   "ix86_split_lshrdi (operands, operands[3]); DONE;")
11383 (define_split 
11384   [(set (match_operand:DI 0 "register_operand" "")
11385         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
11386                      (match_operand:QI 2 "nonmemory_operand" "")))
11387    (clobber (reg:CC FLAGS_REG))]
11388   "!TARGET_64BIT && (flag_peephole2 ? flow2_completed : reload_completed)"
11389   [(const_int 0)]
11390   "ix86_split_lshrdi (operands, NULL_RTX); DONE;")
11392 (define_expand "lshrsi3"
11393   [(set (match_operand:SI 0 "nonimmediate_operand" "")
11394         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
11395                      (match_operand:QI 2 "nonmemory_operand" "")))
11396    (clobber (reg:CC FLAGS_REG))]
11397   ""
11398   "ix86_expand_binary_operator (LSHIFTRT, SImode, operands); DONE;")
11400 (define_insn "*lshrsi3_1_one_bit"
11401   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11402         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11403                      (match_operand:QI 2 "const1_operand" "")))
11404    (clobber (reg:CC FLAGS_REG))]
11405   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11406    && (TARGET_SHIFT1 || optimize_size)"
11407   "shr{l}\t%0"
11408   [(set_attr "type" "ishift")
11409    (set (attr "length") 
11410      (if_then_else (match_operand:SI 0 "register_operand" "") 
11411         (const_string "2")
11412         (const_string "*")))])
11414 (define_insn "*lshrsi3_1_one_bit_zext"
11415   [(set (match_operand:DI 0 "register_operand" "=r")
11416         (lshiftrt:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "0"))
11417                      (match_operand:QI 2 "const1_operand" "")))
11418    (clobber (reg:CC FLAGS_REG))]
11419   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11420    && (TARGET_SHIFT1 || optimize_size)"
11421   "shr{l}\t%k0"
11422   [(set_attr "type" "ishift")
11423    (set_attr "length" "2")])
11425 (define_insn "*lshrsi3_1"
11426   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11427         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11428                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
11429    (clobber (reg:CC FLAGS_REG))]
11430   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11431   "@
11432    shr{l}\t{%2, %0|%0, %2}
11433    shr{l}\t{%b2, %0|%0, %b2}"
11434   [(set_attr "type" "ishift")
11435    (set_attr "mode" "SI")])
11437 (define_insn "*lshrsi3_1_zext"
11438   [(set (match_operand:DI 0 "register_operand" "=r,r")
11439         (zero_extend:DI
11440           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11441                        (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11442    (clobber (reg:CC FLAGS_REG))]
11443   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11444   "@
11445    shr{l}\t{%2, %k0|%k0, %2}
11446    shr{l}\t{%b2, %k0|%k0, %b2}"
11447   [(set_attr "type" "ishift")
11448    (set_attr "mode" "SI")])
11450 ;; This pattern can't accept a variable shift count, since shifts by
11451 ;; zero don't affect the flags.  We assume that shifts by constant
11452 ;; zero are optimized away.
11453 (define_insn "*lshrsi3_one_bit_cmp"
11454   [(set (reg FLAGS_REG)
11455         (compare
11456           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11457                        (match_operand:QI 2 "const1_operand" ""))
11458           (const_int 0)))
11459    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11460         (lshiftrt:SI (match_dup 1) (match_dup 2)))]
11461   "ix86_match_ccmode (insn, CCGOCmode)
11462    && (TARGET_SHIFT1 || optimize_size)
11463    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11464   "shr{l}\t%0"
11465   [(set_attr "type" "ishift")
11466    (set (attr "length") 
11467      (if_then_else (match_operand:SI 0 "register_operand" "") 
11468         (const_string "2")
11469         (const_string "*")))])
11471 (define_insn "*lshrsi3_cmp_one_bit_zext"
11472   [(set (reg FLAGS_REG)
11473         (compare
11474           (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
11475                        (match_operand:QI 2 "const1_operand" ""))
11476           (const_int 0)))
11477    (set (match_operand:DI 0 "register_operand" "=r")
11478         (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
11479   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11480    && (TARGET_SHIFT1 || optimize_size)
11481    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11482   "shr{l}\t%k0"
11483   [(set_attr "type" "ishift")
11484    (set_attr "length" "2")])
11486 ;; This pattern can't accept a variable shift count, since shifts by
11487 ;; zero don't affect the flags.  We assume that shifts by constant
11488 ;; zero are optimized away.
11489 (define_insn "*lshrsi3_cmp"
11490   [(set (reg FLAGS_REG)
11491         (compare
11492           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11493                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
11494           (const_int 0)))
11495    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11496         (lshiftrt:SI (match_dup 1) (match_dup 2)))]
11497   "ix86_match_ccmode (insn, CCGOCmode)
11498    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11499   "shr{l}\t{%2, %0|%0, %2}"
11500   [(set_attr "type" "ishift")
11501    (set_attr "mode" "SI")])
11503 (define_insn "*lshrsi3_cmp_zext"
11504   [(set (reg FLAGS_REG)
11505         (compare
11506           (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
11507                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
11508           (const_int 0)))
11509    (set (match_operand:DI 0 "register_operand" "=r")
11510         (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
11511   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11512    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11513   "shr{l}\t{%2, %k0|%k0, %2}"
11514   [(set_attr "type" "ishift")
11515    (set_attr "mode" "SI")])
11517 (define_expand "lshrhi3"
11518   [(set (match_operand:HI 0 "nonimmediate_operand" "")
11519         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
11520                      (match_operand:QI 2 "nonmemory_operand" "")))
11521    (clobber (reg:CC FLAGS_REG))]
11522   "TARGET_HIMODE_MATH"
11523   "ix86_expand_binary_operator (LSHIFTRT, HImode, operands); DONE;")
11525 (define_insn "*lshrhi3_1_one_bit"
11526   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11527         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11528                      (match_operand:QI 2 "const1_operand" "")))
11529    (clobber (reg:CC FLAGS_REG))]
11530   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11531    && (TARGET_SHIFT1 || optimize_size)"
11532   "shr{w}\t%0"
11533   [(set_attr "type" "ishift")
11534    (set (attr "length") 
11535      (if_then_else (match_operand 0 "register_operand" "") 
11536         (const_string "2")
11537         (const_string "*")))])
11539 (define_insn "*lshrhi3_1"
11540   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11541         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11542                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
11543    (clobber (reg:CC FLAGS_REG))]
11544   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11545   "@
11546    shr{w}\t{%2, %0|%0, %2}
11547    shr{w}\t{%b2, %0|%0, %b2}"
11548   [(set_attr "type" "ishift")
11549    (set_attr "mode" "HI")])
11551 ;; This pattern can't accept a variable shift count, since shifts by
11552 ;; zero don't affect the flags.  We assume that shifts by constant
11553 ;; zero are optimized away.
11554 (define_insn "*lshrhi3_one_bit_cmp"
11555   [(set (reg FLAGS_REG)
11556         (compare
11557           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11558                        (match_operand:QI 2 "const1_operand" ""))
11559           (const_int 0)))
11560    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11561         (lshiftrt:HI (match_dup 1) (match_dup 2)))]
11562   "ix86_match_ccmode (insn, CCGOCmode)
11563    && (TARGET_SHIFT1 || optimize_size)
11564    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11565   "shr{w}\t%0"
11566   [(set_attr "type" "ishift")
11567    (set (attr "length") 
11568      (if_then_else (match_operand:SI 0 "register_operand" "") 
11569         (const_string "2")
11570         (const_string "*")))])
11572 ;; This pattern can't accept a variable shift count, since shifts by
11573 ;; zero don't affect the flags.  We assume that shifts by constant
11574 ;; zero are optimized away.
11575 (define_insn "*lshrhi3_cmp"
11576   [(set (reg FLAGS_REG)
11577         (compare
11578           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11579                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
11580           (const_int 0)))
11581    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11582         (lshiftrt:HI (match_dup 1) (match_dup 2)))]
11583   "ix86_match_ccmode (insn, CCGOCmode)
11584    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11585   "shr{w}\t{%2, %0|%0, %2}"
11586   [(set_attr "type" "ishift")
11587    (set_attr "mode" "HI")])
11589 (define_expand "lshrqi3"
11590   [(set (match_operand:QI 0 "nonimmediate_operand" "")
11591         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
11592                      (match_operand:QI 2 "nonmemory_operand" "")))
11593    (clobber (reg:CC FLAGS_REG))]
11594   "TARGET_QIMODE_MATH"
11595   "ix86_expand_binary_operator (LSHIFTRT, QImode, operands); DONE;")
11597 (define_insn "*lshrqi3_1_one_bit"
11598   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11599         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11600                      (match_operand:QI 2 "const1_operand" "")))
11601    (clobber (reg:CC FLAGS_REG))]
11602   "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)
11603    && (TARGET_SHIFT1 || optimize_size)"
11604   "shr{b}\t%0"
11605   [(set_attr "type" "ishift")
11606    (set (attr "length") 
11607      (if_then_else (match_operand 0 "register_operand" "") 
11608         (const_string "2")
11609         (const_string "*")))])
11611 (define_insn "*lshrqi3_1_one_bit_slp"
11612   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11613         (lshiftrt:QI (match_dup 0)
11614                      (match_operand:QI 1 "const1_operand" "")))
11615    (clobber (reg:CC FLAGS_REG))]
11616   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11617    && (TARGET_SHIFT1 || optimize_size)"
11618   "shr{b}\t%0"
11619   [(set_attr "type" "ishift1")
11620    (set (attr "length") 
11621      (if_then_else (match_operand 0 "register_operand" "") 
11622         (const_string "2")
11623         (const_string "*")))])
11625 (define_insn "*lshrqi3_1"
11626   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11627         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11628                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
11629    (clobber (reg:CC FLAGS_REG))]
11630   "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
11631   "@
11632    shr{b}\t{%2, %0|%0, %2}
11633    shr{b}\t{%b2, %0|%0, %b2}"
11634   [(set_attr "type" "ishift")
11635    (set_attr "mode" "QI")])
11637 (define_insn "*lshrqi3_1_slp"
11638   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11639         (lshiftrt:QI (match_dup 0)
11640                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
11641    (clobber (reg:CC FLAGS_REG))]
11642   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11643    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11644   "@
11645    shr{b}\t{%1, %0|%0, %1}
11646    shr{b}\t{%b1, %0|%0, %b1}"
11647   [(set_attr "type" "ishift1")
11648    (set_attr "mode" "QI")])
11650 ;; This pattern can't accept a variable shift count, since shifts by
11651 ;; zero don't affect the flags.  We assume that shifts by constant
11652 ;; zero are optimized away.
11653 (define_insn "*lshrqi2_one_bit_cmp"
11654   [(set (reg FLAGS_REG)
11655         (compare
11656           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11657                        (match_operand:QI 2 "const1_operand" ""))
11658           (const_int 0)))
11659    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11660         (lshiftrt:QI (match_dup 1) (match_dup 2)))]
11661   "ix86_match_ccmode (insn, CCGOCmode)
11662    && (TARGET_SHIFT1 || optimize_size)
11663    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
11664   "shr{b}\t%0"
11665   [(set_attr "type" "ishift")
11666    (set (attr "length") 
11667      (if_then_else (match_operand:SI 0 "register_operand" "") 
11668         (const_string "2")
11669         (const_string "*")))])
11671 ;; This pattern can't accept a variable shift count, since shifts by
11672 ;; zero don't affect the flags.  We assume that shifts by constant
11673 ;; zero are optimized away.
11674 (define_insn "*lshrqi2_cmp"
11675   [(set (reg FLAGS_REG)
11676         (compare
11677           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11678                        (match_operand:QI 2 "const_1_to_31_operand" "I"))
11679           (const_int 0)))
11680    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11681         (lshiftrt:QI (match_dup 1) (match_dup 2)))]
11682   "ix86_match_ccmode (insn, CCGOCmode)
11683    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
11684   "shr{b}\t{%2, %0|%0, %2}"
11685   [(set_attr "type" "ishift")
11686    (set_attr "mode" "QI")])
11688 ;; Rotate instructions
11690 (define_expand "rotldi3"
11691   [(set (match_operand:DI 0 "nonimmediate_operand" "")
11692         (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "")
11693                    (match_operand:QI 2 "nonmemory_operand" "")))
11694    (clobber (reg:CC FLAGS_REG))]
11695   "TARGET_64BIT"
11696   "ix86_expand_binary_operator (ROTATE, DImode, operands); DONE;")
11698 (define_insn "*rotlsi3_1_one_bit_rex64"
11699   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11700         (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11701                    (match_operand:QI 2 "const1_operand" "")))
11702    (clobber (reg:CC FLAGS_REG))]
11703   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)
11704    && (TARGET_SHIFT1 || optimize_size)"
11705   "rol{q}\t%0"
11706   [(set_attr "type" "rotate")
11707    (set (attr "length") 
11708      (if_then_else (match_operand:DI 0 "register_operand" "") 
11709         (const_string "2")
11710         (const_string "*")))])
11712 (define_insn "*rotldi3_1_rex64"
11713   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11714         (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11715                    (match_operand:QI 2 "nonmemory_operand" "e,c")))
11716    (clobber (reg:CC FLAGS_REG))]
11717   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)"
11718   "@
11719    rol{q}\t{%2, %0|%0, %2}
11720    rol{q}\t{%b2, %0|%0, %b2}"
11721   [(set_attr "type" "rotate")
11722    (set_attr "mode" "DI")])
11724 (define_expand "rotlsi3"
11725   [(set (match_operand:SI 0 "nonimmediate_operand" "")
11726         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
11727                    (match_operand:QI 2 "nonmemory_operand" "")))
11728    (clobber (reg:CC FLAGS_REG))]
11729   ""
11730   "ix86_expand_binary_operator (ROTATE, SImode, operands); DONE;")
11732 (define_insn "*rotlsi3_1_one_bit"
11733   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11734         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11735                    (match_operand:QI 2 "const1_operand" "")))
11736    (clobber (reg:CC FLAGS_REG))]
11737   "ix86_binary_operator_ok (ROTATE, SImode, operands)
11738    && (TARGET_SHIFT1 || optimize_size)"
11739   "rol{l}\t%0"
11740   [(set_attr "type" "rotate")
11741    (set (attr "length") 
11742      (if_then_else (match_operand:SI 0 "register_operand" "") 
11743         (const_string "2")
11744         (const_string "*")))])
11746 (define_insn "*rotlsi3_1_one_bit_zext"
11747   [(set (match_operand:DI 0 "register_operand" "=r")
11748         (zero_extend:DI
11749           (rotate:SI (match_operand:SI 1 "register_operand" "0")
11750                      (match_operand:QI 2 "const1_operand" ""))))
11751    (clobber (reg:CC FLAGS_REG))]
11752   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)
11753    && (TARGET_SHIFT1 || optimize_size)"
11754   "rol{l}\t%k0"
11755   [(set_attr "type" "rotate")
11756    (set_attr "length" "2")])
11758 (define_insn "*rotlsi3_1"
11759   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11760         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11761                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
11762    (clobber (reg:CC FLAGS_REG))]
11763   "ix86_binary_operator_ok (ROTATE, SImode, operands)"
11764   "@
11765    rol{l}\t{%2, %0|%0, %2}
11766    rol{l}\t{%b2, %0|%0, %b2}"
11767   [(set_attr "type" "rotate")
11768    (set_attr "mode" "SI")])
11770 (define_insn "*rotlsi3_1_zext"
11771   [(set (match_operand:DI 0 "register_operand" "=r,r")
11772         (zero_extend:DI
11773           (rotate:SI (match_operand:SI 1 "register_operand" "0,0")
11774                      (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11775    (clobber (reg:CC FLAGS_REG))]
11776   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)"
11777   "@
11778    rol{l}\t{%2, %k0|%k0, %2}
11779    rol{l}\t{%b2, %k0|%k0, %b2}"
11780   [(set_attr "type" "rotate")
11781    (set_attr "mode" "SI")])
11783 (define_expand "rotlhi3"
11784   [(set (match_operand:HI 0 "nonimmediate_operand" "")
11785         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "")
11786                    (match_operand:QI 2 "nonmemory_operand" "")))
11787    (clobber (reg:CC FLAGS_REG))]
11788   "TARGET_HIMODE_MATH"
11789   "ix86_expand_binary_operator (ROTATE, HImode, operands); DONE;")
11791 (define_insn "*rotlhi3_1_one_bit"
11792   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11793         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11794                    (match_operand:QI 2 "const1_operand" "")))
11795    (clobber (reg:CC FLAGS_REG))]
11796   "ix86_binary_operator_ok (ROTATE, HImode, operands)
11797    && (TARGET_SHIFT1 || optimize_size)"
11798   "rol{w}\t%0"
11799   [(set_attr "type" "rotate")
11800    (set (attr "length") 
11801      (if_then_else (match_operand 0 "register_operand" "") 
11802         (const_string "2")
11803         (const_string "*")))])
11805 (define_insn "*rotlhi3_1"
11806   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11807         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11808                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
11809    (clobber (reg:CC FLAGS_REG))]
11810   "ix86_binary_operator_ok (ROTATE, HImode, operands)"
11811   "@
11812    rol{w}\t{%2, %0|%0, %2}
11813    rol{w}\t{%b2, %0|%0, %b2}"
11814   [(set_attr "type" "rotate")
11815    (set_attr "mode" "HI")])
11817 (define_expand "rotlqi3"
11818   [(set (match_operand:QI 0 "nonimmediate_operand" "")
11819         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "")
11820                    (match_operand:QI 2 "nonmemory_operand" "")))
11821    (clobber (reg:CC FLAGS_REG))]
11822   "TARGET_QIMODE_MATH"
11823   "ix86_expand_binary_operator (ROTATE, QImode, operands); DONE;")
11825 (define_insn "*rotlqi3_1_one_bit_slp"
11826   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11827         (rotate:QI (match_dup 0)
11828                    (match_operand:QI 1 "const1_operand" "")))
11829    (clobber (reg:CC FLAGS_REG))]
11830   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11831    && (TARGET_SHIFT1 || optimize_size)"
11832   "rol{b}\t%0"
11833   [(set_attr "type" "rotate1")
11834    (set (attr "length") 
11835      (if_then_else (match_operand 0 "register_operand" "") 
11836         (const_string "2")
11837         (const_string "*")))])
11839 (define_insn "*rotlqi3_1_one_bit"
11840   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11841         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11842                    (match_operand:QI 2 "const1_operand" "")))
11843    (clobber (reg:CC FLAGS_REG))]
11844   "ix86_binary_operator_ok (ROTATE, QImode, operands)
11845    && (TARGET_SHIFT1 || optimize_size)"
11846   "rol{b}\t%0"
11847   [(set_attr "type" "rotate")
11848    (set (attr "length") 
11849      (if_then_else (match_operand 0 "register_operand" "") 
11850         (const_string "2")
11851         (const_string "*")))])
11853 (define_insn "*rotlqi3_1_slp"
11854   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11855         (rotate:QI (match_dup 0)
11856                    (match_operand:QI 1 "nonmemory_operand" "I,c")))
11857    (clobber (reg:CC FLAGS_REG))]
11858   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11859    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11860   "@
11861    rol{b}\t{%1, %0|%0, %1}
11862    rol{b}\t{%b1, %0|%0, %b1}"
11863   [(set_attr "type" "rotate1")
11864    (set_attr "mode" "QI")])
11866 (define_insn "*rotlqi3_1"
11867   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11868         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11869                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
11870    (clobber (reg:CC FLAGS_REG))]
11871   "ix86_binary_operator_ok (ROTATE, QImode, operands)"
11872   "@
11873    rol{b}\t{%2, %0|%0, %2}
11874    rol{b}\t{%b2, %0|%0, %b2}"
11875   [(set_attr "type" "rotate")
11876    (set_attr "mode" "QI")])
11878 (define_expand "rotrdi3"
11879   [(set (match_operand:DI 0 "nonimmediate_operand" "")
11880         (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "")
11881                      (match_operand:QI 2 "nonmemory_operand" "")))
11882    (clobber (reg:CC FLAGS_REG))]
11883   "TARGET_64BIT"
11884   "ix86_expand_binary_operator (ROTATERT, DImode, operands); DONE;")
11886 (define_insn "*rotrdi3_1_one_bit_rex64"
11887   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11888         (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11889                      (match_operand:QI 2 "const1_operand" "")))
11890    (clobber (reg:CC FLAGS_REG))]
11891   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)
11892    && (TARGET_SHIFT1 || optimize_size)"
11893   "ror{q}\t%0"
11894   [(set_attr "type" "rotate")
11895    (set (attr "length") 
11896      (if_then_else (match_operand:DI 0 "register_operand" "") 
11897         (const_string "2")
11898         (const_string "*")))])
11900 (define_insn "*rotrdi3_1_rex64"
11901   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11902         (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11903                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
11904    (clobber (reg:CC FLAGS_REG))]
11905   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
11906   "@
11907    ror{q}\t{%2, %0|%0, %2}
11908    ror{q}\t{%b2, %0|%0, %b2}"
11909   [(set_attr "type" "rotate")
11910    (set_attr "mode" "DI")])
11912 (define_expand "rotrsi3"
11913   [(set (match_operand:SI 0 "nonimmediate_operand" "")
11914         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
11915                      (match_operand:QI 2 "nonmemory_operand" "")))
11916    (clobber (reg:CC FLAGS_REG))]
11917   ""
11918   "ix86_expand_binary_operator (ROTATERT, SImode, operands); DONE;")
11920 (define_insn "*rotrsi3_1_one_bit"
11921   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11922         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11923                      (match_operand:QI 2 "const1_operand" "")))
11924    (clobber (reg:CC FLAGS_REG))]
11925   "ix86_binary_operator_ok (ROTATERT, SImode, operands)
11926    && (TARGET_SHIFT1 || optimize_size)"
11927   "ror{l}\t%0"
11928   [(set_attr "type" "rotate")
11929    (set (attr "length") 
11930      (if_then_else (match_operand:SI 0 "register_operand" "") 
11931         (const_string "2")
11932         (const_string "*")))])
11934 (define_insn "*rotrsi3_1_one_bit_zext"
11935   [(set (match_operand:DI 0 "register_operand" "=r")
11936         (zero_extend:DI
11937           (rotatert:SI (match_operand:SI 1 "register_operand" "0")
11938                        (match_operand:QI 2 "const1_operand" ""))))
11939    (clobber (reg:CC FLAGS_REG))]
11940   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)
11941    && (TARGET_SHIFT1 || optimize_size)"
11942   "ror{l}\t%k0"
11943   [(set_attr "type" "rotate")
11944    (set (attr "length") 
11945      (if_then_else (match_operand:SI 0 "register_operand" "") 
11946         (const_string "2")
11947         (const_string "*")))])
11949 (define_insn "*rotrsi3_1"
11950   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11951         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11952                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
11953    (clobber (reg:CC FLAGS_REG))]
11954   "ix86_binary_operator_ok (ROTATERT, SImode, operands)"
11955   "@
11956    ror{l}\t{%2, %0|%0, %2}
11957    ror{l}\t{%b2, %0|%0, %b2}"
11958   [(set_attr "type" "rotate")
11959    (set_attr "mode" "SI")])
11961 (define_insn "*rotrsi3_1_zext"
11962   [(set (match_operand:DI 0 "register_operand" "=r,r")
11963         (zero_extend:DI
11964           (rotatert:SI (match_operand:SI 1 "register_operand" "0,0")
11965                        (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11966    (clobber (reg:CC FLAGS_REG))]
11967   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
11968   "@
11969    ror{l}\t{%2, %k0|%k0, %2}
11970    ror{l}\t{%b2, %k0|%k0, %b2}"
11971   [(set_attr "type" "rotate")
11972    (set_attr "mode" "SI")])
11974 (define_expand "rotrhi3"
11975   [(set (match_operand:HI 0 "nonimmediate_operand" "")
11976         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "")
11977                      (match_operand:QI 2 "nonmemory_operand" "")))
11978    (clobber (reg:CC FLAGS_REG))]
11979   "TARGET_HIMODE_MATH"
11980   "ix86_expand_binary_operator (ROTATERT, HImode, operands); DONE;")
11982 (define_insn "*rotrhi3_one_bit"
11983   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11984         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11985                      (match_operand:QI 2 "const1_operand" "")))
11986    (clobber (reg:CC FLAGS_REG))]
11987   "ix86_binary_operator_ok (ROTATERT, HImode, operands)
11988    && (TARGET_SHIFT1 || optimize_size)"
11989   "ror{w}\t%0"
11990   [(set_attr "type" "rotate")
11991    (set (attr "length") 
11992      (if_then_else (match_operand 0 "register_operand" "") 
11993         (const_string "2")
11994         (const_string "*")))])
11996 (define_insn "*rotrhi3"
11997   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11998         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11999                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12000    (clobber (reg:CC FLAGS_REG))]
12001   "ix86_binary_operator_ok (ROTATERT, HImode, operands)"
12002   "@
12003    ror{w}\t{%2, %0|%0, %2}
12004    ror{w}\t{%b2, %0|%0, %b2}"
12005   [(set_attr "type" "rotate")
12006    (set_attr "mode" "HI")])
12008 (define_expand "rotrqi3"
12009   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12010         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "")
12011                      (match_operand:QI 2 "nonmemory_operand" "")))
12012    (clobber (reg:CC FLAGS_REG))]
12013   "TARGET_QIMODE_MATH"
12014   "ix86_expand_binary_operator (ROTATERT, QImode, operands); DONE;")
12016 (define_insn "*rotrqi3_1_one_bit"
12017   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12018         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12019                      (match_operand:QI 2 "const1_operand" "")))
12020    (clobber (reg:CC FLAGS_REG))]
12021   "ix86_binary_operator_ok (ROTATERT, QImode, operands)
12022    && (TARGET_SHIFT1 || optimize_size)"
12023   "ror{b}\t%0"
12024   [(set_attr "type" "rotate")
12025    (set (attr "length") 
12026      (if_then_else (match_operand 0 "register_operand" "") 
12027         (const_string "2")
12028         (const_string "*")))])
12030 (define_insn "*rotrqi3_1_one_bit_slp"
12031   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12032         (rotatert:QI (match_dup 0)
12033                      (match_operand:QI 1 "const1_operand" "")))
12034    (clobber (reg:CC FLAGS_REG))]
12035   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12036    && (TARGET_SHIFT1 || optimize_size)"
12037   "ror{b}\t%0"
12038   [(set_attr "type" "rotate1")
12039    (set (attr "length") 
12040      (if_then_else (match_operand 0 "register_operand" "") 
12041         (const_string "2")
12042         (const_string "*")))])
12044 (define_insn "*rotrqi3_1"
12045   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12046         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12047                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12048    (clobber (reg:CC FLAGS_REG))]
12049   "ix86_binary_operator_ok (ROTATERT, QImode, operands)"
12050   "@
12051    ror{b}\t{%2, %0|%0, %2}
12052    ror{b}\t{%b2, %0|%0, %b2}"
12053   [(set_attr "type" "rotate")
12054    (set_attr "mode" "QI")])
12056 (define_insn "*rotrqi3_1_slp"
12057   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12058         (rotatert:QI (match_dup 0)
12059                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
12060    (clobber (reg:CC FLAGS_REG))]
12061   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12062    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
12063   "@
12064    ror{b}\t{%1, %0|%0, %1}
12065    ror{b}\t{%b1, %0|%0, %b1}"
12066   [(set_attr "type" "rotate1")
12067    (set_attr "mode" "QI")])
12069 ;; Bit set / bit test instructions
12071 (define_expand "extv"
12072   [(set (match_operand:SI 0 "register_operand" "")
12073         (sign_extract:SI (match_operand:SI 1 "register_operand" "")
12074                          (match_operand:SI 2 "immediate_operand" "")
12075                          (match_operand:SI 3 "immediate_operand" "")))]
12076   ""
12078   /* Handle extractions from %ah et al.  */
12079   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
12080     FAIL;
12082   /* From mips.md: extract_bit_field doesn't verify that our source
12083      matches the predicate, so check it again here.  */
12084   if (! ext_register_operand (operands[1], VOIDmode))
12085     FAIL;
12088 (define_expand "extzv"
12089   [(set (match_operand:SI 0 "register_operand" "")
12090         (zero_extract:SI (match_operand 1 "ext_register_operand" "")
12091                          (match_operand:SI 2 "immediate_operand" "")
12092                          (match_operand:SI 3 "immediate_operand" "")))]
12093   ""
12095   /* Handle extractions from %ah et al.  */
12096   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
12097     FAIL;
12099   /* From mips.md: extract_bit_field doesn't verify that our source
12100      matches the predicate, so check it again here.  */
12101   if (! ext_register_operand (operands[1], VOIDmode))
12102     FAIL;
12105 (define_expand "insv"
12106   [(set (zero_extract (match_operand 0 "ext_register_operand" "")
12107                       (match_operand 1 "immediate_operand" "")
12108                       (match_operand 2 "immediate_operand" ""))
12109         (match_operand 3 "register_operand" ""))]
12110   ""
12112   /* Handle extractions from %ah et al.  */
12113   if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
12114     FAIL;
12116   /* From mips.md: insert_bit_field doesn't verify that our source
12117      matches the predicate, so check it again here.  */
12118   if (! ext_register_operand (operands[0], VOIDmode))
12119     FAIL;
12121   if (TARGET_64BIT)
12122     emit_insn (gen_movdi_insv_1_rex64 (operands[0], operands[3]));
12123   else
12124     emit_insn (gen_movsi_insv_1 (operands[0], operands[3]));
12126   DONE;
12129 ;; %%% bts, btr, btc, bt.
12130 ;; In general these instructions are *slow* when applied to memory,
12131 ;; since they enforce atomic operation.  When applied to registers,
12132 ;; it depends on the cpu implementation.  They're never faster than
12133 ;; the corresponding and/ior/xor operations, so with 32-bit there's
12134 ;; no point.  But in 64-bit, we can't hold the relevant immediates
12135 ;; within the instruction itself, so operating on bits in the high
12136 ;; 32-bits of a register becomes easier.
12138 ;; These are slow on Nocona, but fast on Athlon64.  We do require the use
12139 ;; of btrq and btcq for corner cases of post-reload expansion of absdf and
12140 ;; negdf respectively, so they can never be disabled entirely.
12142 (define_insn "*btsq"
12143   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12144                          (const_int 1)
12145                          (match_operand:DI 1 "const_0_to_63_operand" ""))
12146         (const_int 1))
12147    (clobber (reg:CC FLAGS_REG))]
12148   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12149   "bts{q} %1,%0"
12150   [(set_attr "type" "alu1")])
12152 (define_insn "*btrq"
12153   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12154                          (const_int 1)
12155                          (match_operand:DI 1 "const_0_to_63_operand" ""))
12156         (const_int 0))
12157    (clobber (reg:CC FLAGS_REG))]
12158   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12159   "btr{q} %1,%0"
12160   [(set_attr "type" "alu1")])
12162 (define_insn "*btcq"
12163   [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12164                          (const_int 1)
12165                          (match_operand:DI 1 "const_0_to_63_operand" ""))
12166         (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
12167    (clobber (reg:CC FLAGS_REG))]
12168   "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12169   "btc{q} %1,%0"
12170   [(set_attr "type" "alu1")])
12172 ;; Allow Nocona to avoid these instructions if a register is available.
12174 (define_peephole2
12175   [(match_scratch:DI 2 "r")
12176    (parallel [(set (zero_extract:DI
12177                      (match_operand:DI 0 "register_operand" "")
12178                      (const_int 1)
12179                      (match_operand:DI 1 "const_0_to_63_operand" ""))
12180                    (const_int 1))
12181               (clobber (reg:CC FLAGS_REG))])]
12182   "TARGET_64BIT && !TARGET_USE_BT"
12183   [(const_int 0)]
12185   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12186   rtx op1;
12188   if (HOST_BITS_PER_WIDE_INT >= 64)
12189     lo = (HOST_WIDE_INT)1 << i, hi = 0;
12190   else if (i < HOST_BITS_PER_WIDE_INT)
12191     lo = (HOST_WIDE_INT)1 << i, hi = 0;
12192   else
12193     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12195   op1 = immed_double_const (lo, hi, DImode);
12196   if (i >= 31)
12197     {
12198       emit_move_insn (operands[2], op1);
12199       op1 = operands[2];
12200     }
12202   emit_insn (gen_iordi3 (operands[0], operands[0], op1));
12203   DONE;
12206 (define_peephole2
12207   [(match_scratch:DI 2 "r")
12208    (parallel [(set (zero_extract:DI
12209                      (match_operand:DI 0 "register_operand" "")
12210                      (const_int 1)
12211                      (match_operand:DI 1 "const_0_to_63_operand" ""))
12212                    (const_int 0))
12213               (clobber (reg:CC FLAGS_REG))])]
12214   "TARGET_64BIT && !TARGET_USE_BT"
12215   [(const_int 0)]
12217   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12218   rtx op1;
12220   if (HOST_BITS_PER_WIDE_INT >= 64)
12221     lo = (HOST_WIDE_INT)1 << i, hi = 0;
12222   else if (i < HOST_BITS_PER_WIDE_INT)
12223     lo = (HOST_WIDE_INT)1 << i, hi = 0;
12224   else
12225     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12227   op1 = immed_double_const (~lo, ~hi, DImode);
12228   if (i >= 32)
12229     {
12230       emit_move_insn (operands[2], op1);
12231       op1 = operands[2];
12232     }
12234   emit_insn (gen_anddi3 (operands[0], operands[0], op1));
12235   DONE;
12238 (define_peephole2
12239   [(match_scratch:DI 2 "r")
12240    (parallel [(set (zero_extract:DI
12241                      (match_operand:DI 0 "register_operand" "")
12242                      (const_int 1)
12243                      (match_operand:DI 1 "const_0_to_63_operand" ""))
12244               (not:DI (zero_extract:DI
12245                         (match_dup 0) (const_int 1) (match_dup 1))))
12246               (clobber (reg:CC FLAGS_REG))])]
12247   "TARGET_64BIT && !TARGET_USE_BT"
12248   [(const_int 0)]
12250   HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12251   rtx op1;
12253   if (HOST_BITS_PER_WIDE_INT >= 64)
12254     lo = (HOST_WIDE_INT)1 << i, hi = 0;
12255   else if (i < HOST_BITS_PER_WIDE_INT)
12256     lo = (HOST_WIDE_INT)1 << i, hi = 0;
12257   else
12258     lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12260   op1 = immed_double_const (lo, hi, DImode);
12261   if (i >= 31)
12262     {
12263       emit_move_insn (operands[2], op1);
12264       op1 = operands[2];
12265     }
12267   emit_insn (gen_xordi3 (operands[0], operands[0], op1));
12268   DONE;
12271 ;; Store-flag instructions.
12273 ;; For all sCOND expanders, also expand the compare or test insn that
12274 ;; generates cc0.  Generate an equality comparison if `seq' or `sne'.
12276 ;; %%% Do the expansion to SImode.  If PII, do things the xor+setcc way
12277 ;; to avoid partial register stalls.  Otherwise do things the setcc+movzx
12278 ;; way, which can later delete the movzx if only QImode is needed.
12280 (define_expand "seq"
12281   [(set (match_operand:QI 0 "register_operand" "")
12282         (eq:QI (reg:CC FLAGS_REG) (const_int 0)))]
12283   ""
12284   "if (ix86_expand_setcc (EQ, operands[0])) DONE; else FAIL;")
12286 (define_expand "sne"
12287   [(set (match_operand:QI 0 "register_operand" "")
12288         (ne:QI (reg:CC FLAGS_REG) (const_int 0)))]
12289   ""
12290   "if (ix86_expand_setcc (NE, operands[0])) DONE; else FAIL;")
12292 (define_expand "sgt"
12293   [(set (match_operand:QI 0 "register_operand" "")
12294         (gt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12295   ""
12296   "if (ix86_expand_setcc (GT, operands[0])) DONE; else FAIL;")
12298 (define_expand "sgtu"
12299   [(set (match_operand:QI 0 "register_operand" "")
12300         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12301   ""
12302   "if (ix86_expand_setcc (GTU, operands[0])) DONE; else FAIL;")
12304 (define_expand "slt"
12305   [(set (match_operand:QI 0 "register_operand" "")
12306         (lt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12307   ""
12308   "if (ix86_expand_setcc (LT, operands[0])) DONE; else FAIL;")
12310 (define_expand "sltu"
12311   [(set (match_operand:QI 0 "register_operand" "")
12312         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12313   ""
12314   "if (ix86_expand_setcc (LTU, operands[0])) DONE; else FAIL;")
12316 (define_expand "sge"
12317   [(set (match_operand:QI 0 "register_operand" "")
12318         (ge:QI (reg:CC FLAGS_REG) (const_int 0)))]
12319   ""
12320   "if (ix86_expand_setcc (GE, operands[0])) DONE; else FAIL;")
12322 (define_expand "sgeu"
12323   [(set (match_operand:QI 0 "register_operand" "")
12324         (geu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12325   ""
12326   "if (ix86_expand_setcc (GEU, operands[0])) DONE; else FAIL;")
12328 (define_expand "sle"
12329   [(set (match_operand:QI 0 "register_operand" "")
12330         (le:QI (reg:CC FLAGS_REG) (const_int 0)))]
12331   ""
12332   "if (ix86_expand_setcc (LE, operands[0])) DONE; else FAIL;")
12334 (define_expand "sleu"
12335   [(set (match_operand:QI 0 "register_operand" "")
12336         (leu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12337   ""
12338   "if (ix86_expand_setcc (LEU, operands[0])) DONE; else FAIL;")
12340 (define_expand "sunordered"
12341   [(set (match_operand:QI 0 "register_operand" "")
12342         (unordered:QI (reg:CC FLAGS_REG) (const_int 0)))]
12343   "TARGET_80387 || TARGET_SSE"
12344   "if (ix86_expand_setcc (UNORDERED, operands[0])) DONE; else FAIL;")
12346 (define_expand "sordered"
12347   [(set (match_operand:QI 0 "register_operand" "")
12348         (ordered:QI (reg:CC FLAGS_REG) (const_int 0)))]
12349   "TARGET_80387"
12350   "if (ix86_expand_setcc (ORDERED, operands[0])) DONE; else FAIL;")
12352 (define_expand "suneq"
12353   [(set (match_operand:QI 0 "register_operand" "")
12354         (uneq:QI (reg:CC FLAGS_REG) (const_int 0)))]
12355   "TARGET_80387 || TARGET_SSE"
12356   "if (ix86_expand_setcc (UNEQ, operands[0])) DONE; else FAIL;")
12358 (define_expand "sunge"
12359   [(set (match_operand:QI 0 "register_operand" "")
12360         (unge:QI (reg:CC FLAGS_REG) (const_int 0)))]
12361   "TARGET_80387 || TARGET_SSE"
12362   "if (ix86_expand_setcc (UNGE, operands[0])) DONE; else FAIL;")
12364 (define_expand "sungt"
12365   [(set (match_operand:QI 0 "register_operand" "")
12366         (ungt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12367   "TARGET_80387 || TARGET_SSE"
12368   "if (ix86_expand_setcc (UNGT, operands[0])) DONE; else FAIL;")
12370 (define_expand "sunle"
12371   [(set (match_operand:QI 0 "register_operand" "")
12372         (unle:QI (reg:CC FLAGS_REG) (const_int 0)))]
12373   "TARGET_80387 || TARGET_SSE"
12374   "if (ix86_expand_setcc (UNLE, operands[0])) DONE; else FAIL;")
12376 (define_expand "sunlt"
12377   [(set (match_operand:QI 0 "register_operand" "")
12378         (unlt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12379   "TARGET_80387 || TARGET_SSE"
12380   "if (ix86_expand_setcc (UNLT, operands[0])) DONE; else FAIL;")
12382 (define_expand "sltgt"
12383   [(set (match_operand:QI 0 "register_operand" "")
12384         (ltgt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12385   "TARGET_80387 || TARGET_SSE"
12386   "if (ix86_expand_setcc (LTGT, operands[0])) DONE; else FAIL;")
12388 (define_insn "*setcc_1"
12389   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12390         (match_operator:QI 1 "ix86_comparison_operator"
12391           [(reg FLAGS_REG) (const_int 0)]))]
12392   ""
12393   "set%C1\t%0"
12394   [(set_attr "type" "setcc")
12395    (set_attr "mode" "QI")])
12397 (define_insn "*setcc_2"
12398   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12399         (match_operator:QI 1 "ix86_comparison_operator"
12400           [(reg FLAGS_REG) (const_int 0)]))]
12401   ""
12402   "set%C1\t%0"
12403   [(set_attr "type" "setcc")
12404    (set_attr "mode" "QI")])
12406 ;; In general it is not safe to assume too much about CCmode registers,
12407 ;; so simplify-rtx stops when it sees a second one.  Under certain 
12408 ;; conditions this is safe on x86, so help combine not create
12410 ;;      seta    %al
12411 ;;      testb   %al, %al
12412 ;;      sete    %al
12414 (define_split 
12415   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12416         (ne:QI (match_operator 1 "ix86_comparison_operator"
12417                  [(reg FLAGS_REG) (const_int 0)])
12418             (const_int 0)))]
12419   ""
12420   [(set (match_dup 0) (match_dup 1))]
12422   PUT_MODE (operands[1], QImode);
12425 (define_split 
12426   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
12427         (ne:QI (match_operator 1 "ix86_comparison_operator"
12428                  [(reg FLAGS_REG) (const_int 0)])
12429             (const_int 0)))]
12430   ""
12431   [(set (match_dup 0) (match_dup 1))]
12433   PUT_MODE (operands[1], QImode);
12436 (define_split 
12437   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12438         (eq:QI (match_operator 1 "ix86_comparison_operator"
12439                  [(reg FLAGS_REG) (const_int 0)])
12440             (const_int 0)))]
12441   ""
12442   [(set (match_dup 0) (match_dup 1))]
12444   rtx new_op1 = copy_rtx (operands[1]);
12445   operands[1] = new_op1;
12446   PUT_MODE (new_op1, QImode);
12447   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
12448                                              GET_MODE (XEXP (new_op1, 0))));
12450   /* Make sure that (a) the CCmode we have for the flags is strong
12451      enough for the reversed compare or (b) we have a valid FP compare.  */
12452   if (! ix86_comparison_operator (new_op1, VOIDmode))
12453     FAIL;
12456 (define_split 
12457   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
12458         (eq:QI (match_operator 1 "ix86_comparison_operator"
12459                  [(reg FLAGS_REG) (const_int 0)])
12460             (const_int 0)))]
12461   ""
12462   [(set (match_dup 0) (match_dup 1))]
12464   rtx new_op1 = copy_rtx (operands[1]);
12465   operands[1] = new_op1;
12466   PUT_MODE (new_op1, QImode);
12467   PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
12468                                              GET_MODE (XEXP (new_op1, 0))));
12470   /* Make sure that (a) the CCmode we have for the flags is strong
12471      enough for the reversed compare or (b) we have a valid FP compare.  */
12472   if (! ix86_comparison_operator (new_op1, VOIDmode))
12473     FAIL;
12476 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
12477 ;; subsequent logical operations are used to imitate conditional moves.
12478 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
12479 ;; it directly.  Further holding this value in pseudo register might bring
12480 ;; problem in implicit normalization in spill code.
12481 ;; So we don't define FLOAT_STORE_FLAG_VALUE and create these
12482 ;; instructions after reload by splitting the conditional move patterns.
12484 (define_insn "*sse_setccsf"
12485   [(set (match_operand:SF 0 "register_operand" "=x")
12486         (match_operator:SF 1 "sse_comparison_operator"
12487           [(match_operand:SF 2 "register_operand" "0")
12488            (match_operand:SF 3 "nonimmediate_operand" "xm")]))]
12489   "TARGET_SSE && reload_completed"
12490   "cmp%D1ss\t{%3, %0|%0, %3}"
12491   [(set_attr "type" "ssecmp")
12492    (set_attr "mode" "SF")])
12494 (define_insn "*sse_setccdf"
12495   [(set (match_operand:DF 0 "register_operand" "=Y")
12496         (match_operator:DF 1 "sse_comparison_operator"
12497           [(match_operand:DF 2 "register_operand" "0")
12498            (match_operand:DF 3 "nonimmediate_operand" "Ym")]))]
12499   "TARGET_SSE2 && reload_completed"
12500   "cmp%D1sd\t{%3, %0|%0, %3}"
12501   [(set_attr "type" "ssecmp")
12502    (set_attr "mode" "DF")])
12504 ;; Basic conditional jump instructions.
12505 ;; We ignore the overflow flag for signed branch instructions.
12507 ;; For all bCOND expanders, also expand the compare or test insn that
12508 ;; generates reg FLAGS_REG.  Generate an equality comparison if `beq' or `bne'.
12510 (define_expand "beq"
12511   [(set (pc)
12512         (if_then_else (match_dup 1)
12513                       (label_ref (match_operand 0 "" ""))
12514                       (pc)))]
12515   ""
12516   "ix86_expand_branch (EQ, operands[0]); DONE;")
12518 (define_expand "bne"
12519   [(set (pc)
12520         (if_then_else (match_dup 1)
12521                       (label_ref (match_operand 0 "" ""))
12522                       (pc)))]
12523   ""
12524   "ix86_expand_branch (NE, operands[0]); DONE;")
12526 (define_expand "bgt"
12527   [(set (pc)
12528         (if_then_else (match_dup 1)
12529                       (label_ref (match_operand 0 "" ""))
12530                       (pc)))]
12531   ""
12532   "ix86_expand_branch (GT, operands[0]); DONE;")
12534 (define_expand "bgtu"
12535   [(set (pc)
12536         (if_then_else (match_dup 1)
12537                       (label_ref (match_operand 0 "" ""))
12538                       (pc)))]
12539   ""
12540   "ix86_expand_branch (GTU, operands[0]); DONE;")
12542 (define_expand "blt"
12543   [(set (pc)
12544         (if_then_else (match_dup 1)
12545                       (label_ref (match_operand 0 "" ""))
12546                       (pc)))]
12547   ""
12548   "ix86_expand_branch (LT, operands[0]); DONE;")
12550 (define_expand "bltu"
12551   [(set (pc)
12552         (if_then_else (match_dup 1)
12553                       (label_ref (match_operand 0 "" ""))
12554                       (pc)))]
12555   ""
12556   "ix86_expand_branch (LTU, operands[0]); DONE;")
12558 (define_expand "bge"
12559   [(set (pc)
12560         (if_then_else (match_dup 1)
12561                       (label_ref (match_operand 0 "" ""))
12562                       (pc)))]
12563   ""
12564   "ix86_expand_branch (GE, operands[0]); DONE;")
12566 (define_expand "bgeu"
12567   [(set (pc)
12568         (if_then_else (match_dup 1)
12569                       (label_ref (match_operand 0 "" ""))
12570                       (pc)))]
12571   ""
12572   "ix86_expand_branch (GEU, operands[0]); DONE;")
12574 (define_expand "ble"
12575   [(set (pc)
12576         (if_then_else (match_dup 1)
12577                       (label_ref (match_operand 0 "" ""))
12578                       (pc)))]
12579   ""
12580   "ix86_expand_branch (LE, operands[0]); DONE;")
12582 (define_expand "bleu"
12583   [(set (pc)
12584         (if_then_else (match_dup 1)
12585                       (label_ref (match_operand 0 "" ""))
12586                       (pc)))]
12587   ""
12588   "ix86_expand_branch (LEU, operands[0]); DONE;")
12590 (define_expand "bunordered"
12591   [(set (pc)
12592         (if_then_else (match_dup 1)
12593                       (label_ref (match_operand 0 "" ""))
12594                       (pc)))]
12595   "TARGET_80387 || TARGET_SSE_MATH"
12596   "ix86_expand_branch (UNORDERED, operands[0]); DONE;")
12598 (define_expand "bordered"
12599   [(set (pc)
12600         (if_then_else (match_dup 1)
12601                       (label_ref (match_operand 0 "" ""))
12602                       (pc)))]
12603   "TARGET_80387 || TARGET_SSE_MATH"
12604   "ix86_expand_branch (ORDERED, operands[0]); DONE;")
12606 (define_expand "buneq"
12607   [(set (pc)
12608         (if_then_else (match_dup 1)
12609                       (label_ref (match_operand 0 "" ""))
12610                       (pc)))]
12611   "TARGET_80387 || TARGET_SSE_MATH"
12612   "ix86_expand_branch (UNEQ, operands[0]); DONE;")
12614 (define_expand "bunge"
12615   [(set (pc)
12616         (if_then_else (match_dup 1)
12617                       (label_ref (match_operand 0 "" ""))
12618                       (pc)))]
12619   "TARGET_80387 || TARGET_SSE_MATH"
12620   "ix86_expand_branch (UNGE, operands[0]); DONE;")
12622 (define_expand "bungt"
12623   [(set (pc)
12624         (if_then_else (match_dup 1)
12625                       (label_ref (match_operand 0 "" ""))
12626                       (pc)))]
12627   "TARGET_80387 || TARGET_SSE_MATH"
12628   "ix86_expand_branch (UNGT, operands[0]); DONE;")
12630 (define_expand "bunle"
12631   [(set (pc)
12632         (if_then_else (match_dup 1)
12633                       (label_ref (match_operand 0 "" ""))
12634                       (pc)))]
12635   "TARGET_80387 || TARGET_SSE_MATH"
12636   "ix86_expand_branch (UNLE, operands[0]); DONE;")
12638 (define_expand "bunlt"
12639   [(set (pc)
12640         (if_then_else (match_dup 1)
12641                       (label_ref (match_operand 0 "" ""))
12642                       (pc)))]
12643   "TARGET_80387 || TARGET_SSE_MATH"
12644   "ix86_expand_branch (UNLT, operands[0]); DONE;")
12646 (define_expand "bltgt"
12647   [(set (pc)
12648         (if_then_else (match_dup 1)
12649                       (label_ref (match_operand 0 "" ""))
12650                       (pc)))]
12651   "TARGET_80387 || TARGET_SSE_MATH"
12652   "ix86_expand_branch (LTGT, operands[0]); DONE;")
12654 (define_insn "*jcc_1"
12655   [(set (pc)
12656         (if_then_else (match_operator 1 "ix86_comparison_operator"
12657                                       [(reg FLAGS_REG) (const_int 0)])
12658                       (label_ref (match_operand 0 "" ""))
12659                       (pc)))]
12660   ""
12661   "%+j%C1\t%l0"
12662   [(set_attr "type" "ibr")
12663    (set_attr "modrm" "0")
12664    (set (attr "length")
12665            (if_then_else (and (ge (minus (match_dup 0) (pc))
12666                                   (const_int -126))
12667                               (lt (minus (match_dup 0) (pc))
12668                                   (const_int 128)))
12669              (const_int 2)
12670              (const_int 6)))])
12672 (define_insn "*jcc_2"
12673   [(set (pc)
12674         (if_then_else (match_operator 1 "ix86_comparison_operator"
12675                                       [(reg FLAGS_REG) (const_int 0)])
12676                       (pc)
12677                       (label_ref (match_operand 0 "" ""))))]
12678   ""
12679   "%+j%c1\t%l0"
12680   [(set_attr "type" "ibr")
12681    (set_attr "modrm" "0")
12682    (set (attr "length")
12683            (if_then_else (and (ge (minus (match_dup 0) (pc))
12684                                   (const_int -126))
12685                               (lt (minus (match_dup 0) (pc))
12686                                   (const_int 128)))
12687              (const_int 2)
12688              (const_int 6)))])
12690 ;; In general it is not safe to assume too much about CCmode registers,
12691 ;; so simplify-rtx stops when it sees a second one.  Under certain 
12692 ;; conditions this is safe on x86, so help combine not create
12694 ;;      seta    %al
12695 ;;      testb   %al, %al
12696 ;;      je      Lfoo
12698 (define_split 
12699   [(set (pc)
12700         (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
12701                                       [(reg FLAGS_REG) (const_int 0)])
12702                           (const_int 0))
12703                       (label_ref (match_operand 1 "" ""))
12704                       (pc)))]
12705   ""
12706   [(set (pc)
12707         (if_then_else (match_dup 0)
12708                       (label_ref (match_dup 1))
12709                       (pc)))]
12711   PUT_MODE (operands[0], VOIDmode);
12713   
12714 (define_split 
12715   [(set (pc)
12716         (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
12717                                       [(reg FLAGS_REG) (const_int 0)])
12718                           (const_int 0))
12719                       (label_ref (match_operand 1 "" ""))
12720                       (pc)))]
12721   ""
12722   [(set (pc)
12723         (if_then_else (match_dup 0)
12724                       (label_ref (match_dup 1))
12725                       (pc)))]
12727   rtx new_op0 = copy_rtx (operands[0]);
12728   operands[0] = new_op0;
12729   PUT_MODE (new_op0, VOIDmode);
12730   PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0),
12731                                              GET_MODE (XEXP (new_op0, 0))));
12733   /* Make sure that (a) the CCmode we have for the flags is strong
12734      enough for the reversed compare or (b) we have a valid FP compare.  */
12735   if (! ix86_comparison_operator (new_op0, VOIDmode))
12736     FAIL;
12739 ;; Define combination compare-and-branch fp compare instructions to use
12740 ;; during early optimization.  Splitting the operation apart early makes
12741 ;; for bad code when we want to reverse the operation.
12743 (define_insn "*fp_jcc_1_mixed"
12744   [(set (pc)
12745         (if_then_else (match_operator 0 "comparison_operator"
12746                         [(match_operand 1 "register_operand" "f#x,x#f")
12747                          (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
12748           (label_ref (match_operand 3 "" ""))
12749           (pc)))
12750    (clobber (reg:CCFP FPSR_REG))
12751    (clobber (reg:CCFP FLAGS_REG))]
12752   "TARGET_MIX_SSE_I387
12753    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
12754    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12755    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12756   "#")
12758 (define_insn "*fp_jcc_1_sse"
12759   [(set (pc)
12760         (if_then_else (match_operator 0 "comparison_operator"
12761                         [(match_operand 1 "register_operand" "x")
12762                          (match_operand 2 "nonimmediate_operand" "xm")])
12763           (label_ref (match_operand 3 "" ""))
12764           (pc)))
12765    (clobber (reg:CCFP FPSR_REG))
12766    (clobber (reg:CCFP FLAGS_REG))]
12767   "TARGET_SSE_MATH
12768    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
12769    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12770    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12771   "#")
12773 (define_insn "*fp_jcc_1_387"
12774   [(set (pc)
12775         (if_then_else (match_operator 0 "comparison_operator"
12776                         [(match_operand 1 "register_operand" "f")
12777                          (match_operand 2 "register_operand" "f")])
12778           (label_ref (match_operand 3 "" ""))
12779           (pc)))
12780    (clobber (reg:CCFP FPSR_REG))
12781    (clobber (reg:CCFP FLAGS_REG))]
12782   "TARGET_CMOVE && TARGET_80387
12783    && FLOAT_MODE_P (GET_MODE (operands[1]))
12784    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12785    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12786   "#")
12788 (define_insn "*fp_jcc_2_mixed"
12789   [(set (pc)
12790         (if_then_else (match_operator 0 "comparison_operator"
12791                         [(match_operand 1 "register_operand" "f#x,x#f")
12792                          (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
12793           (pc)
12794           (label_ref (match_operand 3 "" ""))))
12795    (clobber (reg:CCFP FPSR_REG))
12796    (clobber (reg:CCFP FLAGS_REG))]
12797   "TARGET_MIX_SSE_I387
12798    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
12799    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12800    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12801   "#")
12803 (define_insn "*fp_jcc_2_sse"
12804   [(set (pc)
12805         (if_then_else (match_operator 0 "comparison_operator"
12806                         [(match_operand 1 "register_operand" "x")
12807                          (match_operand 2 "nonimmediate_operand" "xm")])
12808           (pc)
12809           (label_ref (match_operand 3 "" ""))))
12810    (clobber (reg:CCFP FPSR_REG))
12811    (clobber (reg:CCFP FLAGS_REG))]
12812   "TARGET_SSE_MATH
12813    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
12814    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12815    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12816   "#")
12818 (define_insn "*fp_jcc_2_387"
12819   [(set (pc)
12820         (if_then_else (match_operator 0 "comparison_operator"
12821                         [(match_operand 1 "register_operand" "f")
12822                          (match_operand 2 "register_operand" "f")])
12823           (pc)
12824           (label_ref (match_operand 3 "" ""))))
12825    (clobber (reg:CCFP FPSR_REG))
12826    (clobber (reg:CCFP FLAGS_REG))]
12827   "TARGET_CMOVE && TARGET_80387
12828    && FLOAT_MODE_P (GET_MODE (operands[1]))
12829    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12830    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12831   "#")
12833 (define_insn "*fp_jcc_3_387"
12834   [(set (pc)
12835         (if_then_else (match_operator 0 "comparison_operator"
12836                         [(match_operand 1 "register_operand" "f")
12837                          (match_operand 2 "nonimmediate_operand" "fm")])
12838           (label_ref (match_operand 3 "" ""))
12839           (pc)))
12840    (clobber (reg:CCFP FPSR_REG))
12841    (clobber (reg:CCFP FLAGS_REG))
12842    (clobber (match_scratch:HI 4 "=a"))]
12843   "TARGET_80387
12844    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
12845    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12846    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
12847    && SELECT_CC_MODE (GET_CODE (operands[0]),
12848                       operands[1], operands[2]) == CCFPmode
12849    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12850   "#")
12852 (define_insn "*fp_jcc_4_387"
12853   [(set (pc)
12854         (if_then_else (match_operator 0 "comparison_operator"
12855                         [(match_operand 1 "register_operand" "f")
12856                          (match_operand 2 "nonimmediate_operand" "fm")])
12857           (pc)
12858           (label_ref (match_operand 3 "" ""))))
12859    (clobber (reg:CCFP FPSR_REG))
12860    (clobber (reg:CCFP FLAGS_REG))
12861    (clobber (match_scratch:HI 4 "=a"))]
12862   "TARGET_80387
12863    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
12864    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12865    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
12866    && SELECT_CC_MODE (GET_CODE (operands[0]),
12867                       operands[1], operands[2]) == CCFPmode
12868    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12869   "#")
12871 (define_insn "*fp_jcc_5_387"
12872   [(set (pc)
12873         (if_then_else (match_operator 0 "comparison_operator"
12874                         [(match_operand 1 "register_operand" "f")
12875                          (match_operand 2 "register_operand" "f")])
12876           (label_ref (match_operand 3 "" ""))
12877           (pc)))
12878    (clobber (reg:CCFP FPSR_REG))
12879    (clobber (reg:CCFP FLAGS_REG))
12880    (clobber (match_scratch:HI 4 "=a"))]
12881   "TARGET_80387
12882    && FLOAT_MODE_P (GET_MODE (operands[1]))
12883    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12884    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12885   "#")
12887 (define_insn "*fp_jcc_6_387"
12888   [(set (pc)
12889         (if_then_else (match_operator 0 "comparison_operator"
12890                         [(match_operand 1 "register_operand" "f")
12891                          (match_operand 2 "register_operand" "f")])
12892           (pc)
12893           (label_ref (match_operand 3 "" ""))))
12894    (clobber (reg:CCFP FPSR_REG))
12895    (clobber (reg:CCFP FLAGS_REG))
12896    (clobber (match_scratch:HI 4 "=a"))]
12897   "TARGET_80387
12898    && FLOAT_MODE_P (GET_MODE (operands[1]))
12899    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12900    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12901   "#")
12903 (define_insn "*fp_jcc_7_387"
12904   [(set (pc)
12905         (if_then_else (match_operator 0 "comparison_operator"
12906                         [(match_operand 1 "register_operand" "f")
12907                          (match_operand 2 "const0_operand" "X")])
12908           (label_ref (match_operand 3 "" ""))
12909           (pc)))
12910    (clobber (reg:CCFP FPSR_REG))
12911    (clobber (reg:CCFP FLAGS_REG))
12912    (clobber (match_scratch:HI 4 "=a"))]
12913   "TARGET_80387
12914    && FLOAT_MODE_P (GET_MODE (operands[1]))
12915    && GET_MODE (operands[1]) == GET_MODE (operands[2])
12916    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
12917    && SELECT_CC_MODE (GET_CODE (operands[0]),
12918                       operands[1], operands[2]) == CCFPmode
12919    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12920   "#")
12922 ;; The order of operands in *fp_jcc_8_387 is forced by combine in
12923 ;; simplify_comparison () function. Float operator is treated as RTX_OBJ
12924 ;; with a precedence over other operators and is always put in the first
12925 ;; place. Swap condition and operands to match ficom instruction.
12927 (define_insn "*fp_jcc_8<mode>_387"
12928   [(set (pc)
12929         (if_then_else (match_operator 0 "comparison_operator"
12930                         [(match_operator 1 "float_operator"
12931                            [(match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r")])
12932                            (match_operand 3 "register_operand" "f,f")])
12933           (label_ref (match_operand 4 "" ""))
12934           (pc)))
12935    (clobber (reg:CCFP FPSR_REG))
12936    (clobber (reg:CCFP FLAGS_REG))
12937    (clobber (match_scratch:HI 5 "=a,a"))]
12938   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
12939    && FLOAT_MODE_P (GET_MODE (operands[3]))
12940    && GET_MODE (operands[1]) == GET_MODE (operands[3])
12941    && !ix86_use_fcomi_compare (swap_condition (GET_CODE (operands[0])))
12942    && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode
12943    && ix86_fp_jump_nontrivial_p (swap_condition (GET_CODE (operands[0])))"
12944   "#")
12946 (define_split
12947   [(set (pc)
12948         (if_then_else (match_operator 0 "comparison_operator"
12949                         [(match_operand 1 "register_operand" "")
12950                          (match_operand 2 "nonimmediate_operand" "")])
12951           (match_operand 3 "" "")
12952           (match_operand 4 "" "")))
12953    (clobber (reg:CCFP FPSR_REG))
12954    (clobber (reg:CCFP FLAGS_REG))]
12955   "reload_completed"
12956   [(const_int 0)]
12958   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
12959                         operands[3], operands[4], NULL_RTX, NULL_RTX);
12960   DONE;
12963 (define_split
12964   [(set (pc)
12965         (if_then_else (match_operator 0 "comparison_operator"
12966                         [(match_operand 1 "register_operand" "")
12967                          (match_operand 2 "general_operand" "")])
12968           (match_operand 3 "" "")
12969           (match_operand 4 "" "")))
12970    (clobber (reg:CCFP FPSR_REG))
12971    (clobber (reg:CCFP FLAGS_REG))
12972    (clobber (match_scratch:HI 5 "=a"))]
12973   "reload_completed"
12974   [(const_int 0)]
12976   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
12977                         operands[3], operands[4], operands[5], NULL_RTX);
12978   DONE;
12981 (define_split
12982   [(set (pc)
12983         (if_then_else (match_operator 0 "comparison_operator"
12984                         [(match_operator 1 "float_operator"
12985                            [(match_operand:X87MODEI12 2 "memory_operand" "")])
12986                            (match_operand 3 "register_operand" "")])
12987           (match_operand 4 "" "")
12988           (match_operand 5 "" "")))
12989    (clobber (reg:CCFP FPSR_REG))
12990    (clobber (reg:CCFP FLAGS_REG))
12991    (clobber (match_scratch:HI 6 "=a"))]
12992   "reload_completed"
12993   [(const_int 0)]
12995   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]);
12996   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
12997                         operands[3], operands[7],
12998                         operands[4], operands[5], operands[6], NULL_RTX);
12999   DONE;
13002 ;; %%% Kill this when reload knows how to do it.
13003 (define_split
13004   [(set (pc)
13005         (if_then_else (match_operator 0 "comparison_operator"
13006                         [(match_operator 1 "float_operator"
13007                            [(match_operand:X87MODEI12 2 "register_operand" "")])
13008                            (match_operand 3 "register_operand" "")])
13009           (match_operand 4 "" "")
13010           (match_operand 5 "" "")))
13011    (clobber (reg:CCFP FPSR_REG))
13012    (clobber (reg:CCFP FLAGS_REG))
13013    (clobber (match_scratch:HI 6 "=a"))]
13014   "reload_completed"
13015   [(const_int 0)]
13017   operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
13018   operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]);
13019   ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
13020                         operands[3], operands[7],
13021                         operands[4], operands[5], operands[6], operands[2]);
13022   DONE;
13025 ;; Unconditional and other jump instructions
13027 (define_insn "jump"
13028   [(set (pc)
13029         (label_ref (match_operand 0 "" "")))]
13030   ""
13031   "jmp\t%l0"
13032   [(set_attr "type" "ibr")
13033    (set (attr "length")
13034            (if_then_else (and (ge (minus (match_dup 0) (pc))
13035                                   (const_int -126))
13036                               (lt (minus (match_dup 0) (pc))
13037                                   (const_int 128)))
13038              (const_int 2)
13039              (const_int 5)))
13040    (set_attr "modrm" "0")])
13042 (define_expand "indirect_jump"
13043   [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))]
13044   ""
13045   "")
13047 (define_insn "*indirect_jump"
13048   [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))]
13049   "!TARGET_64BIT"
13050   "jmp\t%A0"
13051   [(set_attr "type" "ibr")
13052    (set_attr "length_immediate" "0")])
13054 (define_insn "*indirect_jump_rtx64"
13055   [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))]
13056   "TARGET_64BIT"
13057   "jmp\t%A0"
13058   [(set_attr "type" "ibr")
13059    (set_attr "length_immediate" "0")])
13061 (define_expand "tablejump"
13062   [(parallel [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))
13063               (use (label_ref (match_operand 1 "" "")))])]
13064   ""
13066   /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
13067      relative.  Convert the relative address to an absolute address.  */
13068   if (flag_pic)
13069     {
13070       rtx op0, op1;
13071       enum rtx_code code;
13073       if (TARGET_64BIT)
13074         {
13075           code = PLUS;
13076           op0 = operands[0];
13077           op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
13078         }
13079       else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
13080         {
13081           code = PLUS;
13082           op0 = operands[0];
13083           op1 = pic_offset_table_rtx;
13084         }
13085       else
13086         {
13087           code = MINUS;
13088           op0 = pic_offset_table_rtx;
13089           op1 = operands[0];
13090         }
13092       operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
13093                                          OPTAB_DIRECT);
13094     }
13097 (define_insn "*tablejump_1"
13098   [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))
13099    (use (label_ref (match_operand 1 "" "")))]
13100   "!TARGET_64BIT"
13101   "jmp\t%A0"
13102   [(set_attr "type" "ibr")
13103    (set_attr "length_immediate" "0")])
13105 (define_insn "*tablejump_1_rtx64"
13106   [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))
13107    (use (label_ref (match_operand 1 "" "")))]
13108   "TARGET_64BIT"
13109   "jmp\t%A0"
13110   [(set_attr "type" "ibr")
13111    (set_attr "length_immediate" "0")])
13113 ;; Loop instruction
13115 ;; This is all complicated by the fact that since this is a jump insn
13116 ;; we must handle our own reloads.
13118 (define_expand "doloop_end"
13119   [(use (match_operand 0 "" ""))        ; loop pseudo
13120    (use (match_operand 1 "" ""))        ; iterations; zero if unknown
13121    (use (match_operand 2 "" ""))        ; max iterations
13122    (use (match_operand 3 "" ""))        ; loop level 
13123    (use (match_operand 4 "" ""))]       ; label
13124   "!TARGET_64BIT && TARGET_USE_LOOP"
13125   "                                 
13127   /* Only use cloop on innermost loops.  */
13128   if (INTVAL (operands[3]) > 1)
13129     FAIL;
13130   if (GET_MODE (operands[0]) != SImode)
13131     FAIL;
13132   emit_jump_insn (gen_doloop_end_internal (operands[4], operands[0],
13133                                            operands[0]));
13134   DONE;
13137 (define_insn "doloop_end_internal"
13138   [(set (pc)
13139         (if_then_else (ne (match_operand:SI 1 "register_operand" "c,?*r,?*r")
13140                           (const_int 1))
13141                       (label_ref (match_operand 0 "" ""))
13142                       (pc)))
13143    (set (match_operand:SI 2 "nonimmediate_operand" "=1,1,*m*r")
13144         (plus:SI (match_dup 1)
13145                  (const_int -1)))
13146    (clobber (match_scratch:SI 3 "=X,X,r"))
13147    (clobber (reg:CC FLAGS_REG))]
13148   "!TARGET_64BIT && TARGET_USE_LOOP
13149    && (reload_in_progress || reload_completed
13150        || register_operand (operands[2], VOIDmode))"
13152   if (which_alternative != 0)
13153     return "#";
13154   if (get_attr_length (insn) == 2)
13155     return "%+loop\t%l0";
13156   else
13157     return "dec{l}\t%1\;%+jne\t%l0";
13159   [(set (attr "length")
13160         (if_then_else (and (eq_attr "alternative" "0")
13161                            (and (ge (minus (match_dup 0) (pc))
13162                                     (const_int -126))
13163                                 (lt (minus (match_dup 0) (pc))
13164                                     (const_int 128))))
13165                       (const_int 2)
13166                       (const_int 16)))
13167    ;; We don't know the type before shorten branches.  Optimistically expect
13168    ;; the loop instruction to match.
13169    (set (attr "type") (const_string "ibr"))])
13171 (define_split
13172   [(set (pc)
13173         (if_then_else (ne (match_operand:SI 1 "register_operand" "")
13174                           (const_int 1))
13175                       (match_operand 0 "" "")
13176                       (pc)))
13177    (set (match_dup 1)
13178         (plus:SI (match_dup 1)
13179                  (const_int -1)))
13180    (clobber (match_scratch:SI 2 ""))
13181    (clobber (reg:CC FLAGS_REG))]
13182   "!TARGET_64BIT && TARGET_USE_LOOP
13183    && reload_completed
13184    && REGNO (operands[1]) != 2"
13185   [(parallel [(set (reg:CCZ FLAGS_REG)
13186                    (compare:CCZ (plus:SI (match_dup 1) (const_int -1))
13187                                  (const_int 0)))
13188               (set (match_dup 1) (plus:SI (match_dup 1) (const_int -1)))])
13189    (set (pc) (if_then_else (ne (reg:CCZ FLAGS_REG) (const_int 0))
13190                            (match_dup 0)
13191                            (pc)))]
13192   "")
13193   
13194 (define_split
13195   [(set (pc)
13196         (if_then_else (ne (match_operand:SI 1 "register_operand" "")
13197                           (const_int 1))
13198                       (match_operand 0 "" "")
13199                       (pc)))
13200    (set (match_operand:SI 2 "nonimmediate_operand" "")
13201         (plus:SI (match_dup 1)
13202                  (const_int -1)))
13203    (clobber (match_scratch:SI 3 ""))
13204    (clobber (reg:CC FLAGS_REG))]
13205   "!TARGET_64BIT && TARGET_USE_LOOP
13206    && reload_completed
13207    && (! REG_P (operands[2])
13208        || ! rtx_equal_p (operands[1], operands[2]))"
13209   [(set (match_dup 3) (match_dup 1))
13210    (parallel [(set (reg:CCZ FLAGS_REG)
13211                    (compare:CCZ (plus:SI (match_dup 3) (const_int -1))
13212                                 (const_int 0)))
13213               (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
13214    (set (match_dup 2) (match_dup 3))
13215    (set (pc) (if_then_else (ne (reg:CCZ FLAGS_REG) (const_int 0))
13216                            (match_dup 0)
13217                            (pc)))]
13218   "")
13220 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
13222 (define_peephole2
13223   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
13224    (set (match_operand:QI 1 "register_operand" "")
13225         (match_operator:QI 2 "ix86_comparison_operator"
13226           [(reg FLAGS_REG) (const_int 0)]))
13227    (set (match_operand 3 "q_regs_operand" "")
13228         (zero_extend (match_dup 1)))]
13229   "(peep2_reg_dead_p (3, operands[1])
13230     || operands_match_p (operands[1], operands[3]))
13231    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
13232   [(set (match_dup 4) (match_dup 0))
13233    (set (strict_low_part (match_dup 5))
13234         (match_dup 2))]
13236   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), 17);
13237   operands[5] = gen_lowpart (QImode, operands[3]);
13238   ix86_expand_clear (operands[3]);
13241 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
13243 (define_peephole2
13244   [(set (reg FLAGS_REG) (match_operand 0 "" ""))
13245    (set (match_operand:QI 1 "register_operand" "")
13246         (match_operator:QI 2 "ix86_comparison_operator"
13247           [(reg FLAGS_REG) (const_int 0)]))
13248    (parallel [(set (match_operand 3 "q_regs_operand" "")
13249                    (zero_extend (match_dup 1)))
13250               (clobber (reg:CC FLAGS_REG))])]
13251   "(peep2_reg_dead_p (3, operands[1])
13252     || operands_match_p (operands[1], operands[3]))
13253    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
13254   [(set (match_dup 4) (match_dup 0))
13255    (set (strict_low_part (match_dup 5))
13256         (match_dup 2))]
13258   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), 17);
13259   operands[5] = gen_lowpart (QImode, operands[3]);
13260   ix86_expand_clear (operands[3]);
13263 ;; Call instructions.
13265 ;; The predicates normally associated with named expanders are not properly
13266 ;; checked for calls.  This is a bug in the generic code, but it isn't that
13267 ;; easy to fix.  Ignore it for now and be prepared to fix things up.
13269 ;; Call subroutine returning no value.
13271 (define_expand "call_pop"
13272   [(parallel [(call (match_operand:QI 0 "" "")
13273                     (match_operand:SI 1 "" ""))
13274               (set (reg:SI SP_REG)
13275                    (plus:SI (reg:SI SP_REG)
13276                             (match_operand:SI 3 "" "")))])]
13277   "!TARGET_64BIT"
13279   ix86_expand_call (NULL, operands[0], operands[1], operands[2], operands[3], 0);
13280   DONE;
13283 (define_insn "*call_pop_0"
13284   [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" ""))
13285          (match_operand:SI 1 "" ""))
13286    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
13287                             (match_operand:SI 2 "immediate_operand" "")))]
13288   "!TARGET_64BIT"
13290   if (SIBLING_CALL_P (insn))
13291     return "jmp\t%P0";
13292   else
13293     return "call\t%P0";
13295   [(set_attr "type" "call")])
13296   
13297 (define_insn "*call_pop_1"
13298   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
13299          (match_operand:SI 1 "" ""))
13300    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
13301                             (match_operand:SI 2 "immediate_operand" "i")))]
13302   "!TARGET_64BIT"
13304   if (constant_call_address_operand (operands[0], Pmode))
13305     {
13306       if (SIBLING_CALL_P (insn))
13307         return "jmp\t%P0";
13308       else
13309         return "call\t%P0";
13310     }
13311   if (SIBLING_CALL_P (insn))
13312     return "jmp\t%A0";
13313   else
13314     return "call\t%A0";
13316   [(set_attr "type" "call")])
13318 (define_expand "call"
13319   [(call (match_operand:QI 0 "" "")
13320          (match_operand 1 "" ""))
13321    (use (match_operand 2 "" ""))]
13322   ""
13324   ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 0);
13325   DONE;
13328 (define_expand "sibcall"
13329   [(call (match_operand:QI 0 "" "")
13330          (match_operand 1 "" ""))
13331    (use (match_operand 2 "" ""))]
13332   ""
13334   ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 1);
13335   DONE;
13338 (define_insn "*call_0"
13339   [(call (mem:QI (match_operand 0 "constant_call_address_operand" ""))
13340          (match_operand 1 "" ""))]
13341   ""
13343   if (SIBLING_CALL_P (insn))
13344     return "jmp\t%P0";
13345   else
13346     return "call\t%P0";
13348   [(set_attr "type" "call")])
13350 (define_insn "*call_1"
13351   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
13352          (match_operand 1 "" ""))]
13353   "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
13355   if (constant_call_address_operand (operands[0], Pmode))
13356     return "call\t%P0";
13357   return "call\t%A0";
13359   [(set_attr "type" "call")])
13361 (define_insn "*sibcall_1"
13362   [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "s,c,d,a"))
13363          (match_operand 1 "" ""))]
13364   "SIBLING_CALL_P (insn) && !TARGET_64BIT"
13366   if (constant_call_address_operand (operands[0], Pmode))
13367     return "jmp\t%P0";
13368   return "jmp\t%A0";
13370   [(set_attr "type" "call")])
13372 (define_insn "*call_1_rex64"
13373   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rsm"))
13374          (match_operand 1 "" ""))]
13375   "!SIBLING_CALL_P (insn) && TARGET_64BIT"
13377   if (constant_call_address_operand (operands[0], Pmode))
13378     return "call\t%P0";
13379   return "call\t%A0";
13381   [(set_attr "type" "call")])
13383 (define_insn "*sibcall_1_rex64"
13384   [(call (mem:QI (match_operand:DI 0 "constant_call_address_operand" ""))
13385          (match_operand 1 "" ""))]
13386   "SIBLING_CALL_P (insn) && TARGET_64BIT"
13387   "jmp\t%P0"
13388   [(set_attr "type" "call")])
13390 (define_insn "*sibcall_1_rex64_v"
13391   [(call (mem:QI (reg:DI 40))
13392          (match_operand 0 "" ""))]
13393   "SIBLING_CALL_P (insn) && TARGET_64BIT"
13394   "jmp\t*%%r11"
13395   [(set_attr "type" "call")])
13398 ;; Call subroutine, returning value in operand 0
13400 (define_expand "call_value_pop"
13401   [(parallel [(set (match_operand 0 "" "")
13402                    (call (match_operand:QI 1 "" "")
13403                          (match_operand:SI 2 "" "")))
13404               (set (reg:SI SP_REG)
13405                    (plus:SI (reg:SI SP_REG)
13406                             (match_operand:SI 4 "" "")))])]
13407   "!TARGET_64BIT"
13409   ix86_expand_call (operands[0], operands[1], operands[2],
13410                     operands[3], operands[4], 0);
13411   DONE;
13414 (define_expand "call_value"
13415   [(set (match_operand 0 "" "")
13416         (call (match_operand:QI 1 "" "")
13417               (match_operand:SI 2 "" "")))
13418    (use (match_operand:SI 3 "" ""))]
13419   ;; Operand 2 not used on the i386.
13420   ""
13422   ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 0);
13423   DONE;
13426 (define_expand "sibcall_value"
13427   [(set (match_operand 0 "" "")
13428         (call (match_operand:QI 1 "" "")
13429               (match_operand:SI 2 "" "")))
13430    (use (match_operand:SI 3 "" ""))]
13431   ;; Operand 2 not used on the i386.
13432   ""
13434   ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 1);
13435   DONE;
13438 ;; Call subroutine returning any type.
13440 (define_expand "untyped_call"
13441   [(parallel [(call (match_operand 0 "" "")
13442                     (const_int 0))
13443               (match_operand 1 "" "")
13444               (match_operand 2 "" "")])]
13445   ""
13447   int i;
13449   /* In order to give reg-stack an easier job in validating two
13450      coprocessor registers as containing a possible return value,
13451      simply pretend the untyped call returns a complex long double
13452      value.  */
13454   ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
13455                      ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
13456                     operands[0], const0_rtx, GEN_INT (SSE_REGPARM_MAX - 1),
13457                     NULL, 0);
13459   for (i = 0; i < XVECLEN (operands[2], 0); i++)
13460     {
13461       rtx set = XVECEXP (operands[2], 0, i);
13462       emit_move_insn (SET_DEST (set), SET_SRC (set));
13463     }
13465   /* The optimizer does not know that the call sets the function value
13466      registers we stored in the result block.  We avoid problems by
13467      claiming that all hard registers are used and clobbered at this
13468      point.  */
13469   emit_insn (gen_blockage (const0_rtx));
13471   DONE;
13474 ;; Prologue and epilogue instructions
13476 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
13477 ;; all of memory.  This blocks insns from being moved across this point.
13479 (define_insn "blockage"
13480   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_BLOCKAGE)]
13481   ""
13482   ""
13483   [(set_attr "length" "0")])
13485 ;; Insn emitted into the body of a function to return from a function.
13486 ;; This is only done if the function's epilogue is known to be simple.
13487 ;; See comments for ix86_can_use_return_insn_p in i386.c.
13489 (define_expand "return"
13490   [(return)]
13491   "ix86_can_use_return_insn_p ()"
13493   if (current_function_pops_args)
13494     {
13495       rtx popc = GEN_INT (current_function_pops_args);
13496       emit_jump_insn (gen_return_pop_internal (popc));
13497       DONE;
13498     }
13501 (define_insn "return_internal"
13502   [(return)]
13503   "reload_completed"
13504   "ret"
13505   [(set_attr "length" "1")
13506    (set_attr "length_immediate" "0")
13507    (set_attr "modrm" "0")])
13509 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
13510 ;; instruction Athlon and K8 have.
13512 (define_insn "return_internal_long"
13513   [(return)
13514    (unspec [(const_int 0)] UNSPEC_REP)]
13515   "reload_completed"
13516   "rep {;} ret"
13517   [(set_attr "length" "1")
13518    (set_attr "length_immediate" "0")
13519    (set_attr "prefix_rep" "1")
13520    (set_attr "modrm" "0")])
13522 (define_insn "return_pop_internal"
13523   [(return)
13524    (use (match_operand:SI 0 "const_int_operand" ""))]
13525   "reload_completed"
13526   "ret\t%0"
13527   [(set_attr "length" "3")
13528    (set_attr "length_immediate" "2")
13529    (set_attr "modrm" "0")])
13531 (define_insn "return_indirect_internal"
13532   [(return)
13533    (use (match_operand:SI 0 "register_operand" "r"))]
13534   "reload_completed"
13535   "jmp\t%A0"
13536   [(set_attr "type" "ibr")
13537    (set_attr "length_immediate" "0")])
13539 (define_insn "nop"
13540   [(const_int 0)]
13541   ""
13542   "nop"
13543   [(set_attr "length" "1")
13544    (set_attr "length_immediate" "0")
13545    (set_attr "modrm" "0")])
13547 ;; Align to 16-byte boundary, max skip in op0.  Used to avoid
13548 ;; branch prediction penalty for the third jump in a 16-byte
13549 ;; block on K8.
13551 (define_insn "align"
13552   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
13553   ""
13555 #ifdef ASM_OUTPUT_MAX_SKIP_ALIGN
13556   ASM_OUTPUT_MAX_SKIP_ALIGN (asm_out_file, 4, (int)INTVAL (operands[0]));
13557 #else
13558   /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
13559      The align insn is used to avoid 3 jump instructions in the row to improve
13560      branch prediction and the benefits hardly outweight the cost of extra 8
13561      nops on the average inserted by full alignment pseudo operation.  */
13562 #endif
13563   return "";
13565   [(set_attr "length" "16")])
13567 (define_expand "prologue"
13568   [(const_int 1)]
13569   ""
13570   "ix86_expand_prologue (); DONE;")
13572 (define_insn "set_got"
13573   [(set (match_operand:SI 0 "register_operand" "=r")
13574         (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
13575    (clobber (reg:CC FLAGS_REG))]
13576   "!TARGET_64BIT"
13577   { return output_set_got (operands[0]); }
13578   [(set_attr "type" "multi")
13579    (set_attr "length" "12")])
13581 (define_expand "epilogue"
13582   [(const_int 1)]
13583   ""
13584   "ix86_expand_epilogue (1); DONE;")
13586 (define_expand "sibcall_epilogue"
13587   [(const_int 1)]
13588   ""
13589   "ix86_expand_epilogue (0); DONE;")
13591 (define_expand "eh_return"
13592   [(use (match_operand 0 "register_operand" ""))]
13593   ""
13595   rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
13597   /* Tricky bit: we write the address of the handler to which we will
13598      be returning into someone else's stack frame, one word below the
13599      stack address we wish to restore.  */
13600   tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
13601   tmp = plus_constant (tmp, -UNITS_PER_WORD);
13602   tmp = gen_rtx_MEM (Pmode, tmp);
13603   emit_move_insn (tmp, ra);
13605   if (Pmode == SImode)
13606     emit_jump_insn (gen_eh_return_si (sa));
13607   else
13608     emit_jump_insn (gen_eh_return_di (sa));
13609   emit_barrier ();
13610   DONE;
13613 (define_insn_and_split "eh_return_si"
13614   [(set (pc) 
13615         (unspec [(match_operand:SI 0 "register_operand" "c")]
13616                  UNSPEC_EH_RETURN))]
13617   "!TARGET_64BIT"
13618   "#"
13619   "reload_completed"
13620   [(const_int 1)]
13621   "ix86_expand_epilogue (2); DONE;")
13623 (define_insn_and_split "eh_return_di"
13624   [(set (pc) 
13625         (unspec [(match_operand:DI 0 "register_operand" "c")]
13626                  UNSPEC_EH_RETURN))]
13627   "TARGET_64BIT"
13628   "#"
13629   "reload_completed"
13630   [(const_int 1)]
13631   "ix86_expand_epilogue (2); DONE;")
13633 (define_insn "leave"
13634   [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4)))
13635    (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG)))
13636    (clobber (mem:BLK (scratch)))]
13637   "!TARGET_64BIT"
13638   "leave"
13639   [(set_attr "type" "leave")])
13641 (define_insn "leave_rex64"
13642   [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8)))
13643    (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG)))
13644    (clobber (mem:BLK (scratch)))]
13645   "TARGET_64BIT"
13646   "leave"
13647   [(set_attr "type" "leave")])
13649 (define_expand "ffssi2"
13650   [(parallel
13651      [(set (match_operand:SI 0 "register_operand" "") 
13652            (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "")))
13653       (clobber (match_scratch:SI 2 ""))
13654       (clobber (reg:CC FLAGS_REG))])]
13655   ""
13656   "")
13658 (define_insn_and_split "*ffs_cmove"
13659   [(set (match_operand:SI 0 "register_operand" "=r") 
13660         (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
13661    (clobber (match_scratch:SI 2 "=&r"))
13662    (clobber (reg:CC FLAGS_REG))]
13663   "TARGET_CMOVE"
13664   "#"
13665   "&& reload_completed"
13666   [(set (match_dup 2) (const_int -1))
13667    (parallel [(set (reg:CCZ FLAGS_REG) (compare:CCZ (match_dup 1) (const_int 0)))
13668               (set (match_dup 0) (ctz:SI (match_dup 1)))])
13669    (set (match_dup 0) (if_then_else:SI
13670                         (eq (reg:CCZ FLAGS_REG) (const_int 0))
13671                         (match_dup 2)
13672                         (match_dup 0)))
13673    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
13674               (clobber (reg:CC FLAGS_REG))])]
13675   "")
13677 (define_insn_and_split "*ffs_no_cmove"
13678   [(set (match_operand:SI 0 "nonimmediate_operand" "=r") 
13679         (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
13680    (clobber (match_scratch:SI 2 "=&q"))
13681    (clobber (reg:CC FLAGS_REG))]
13682   ""
13683   "#"
13684   "reload_completed"
13685   [(parallel [(set (reg:CCZ FLAGS_REG) (compare:CCZ (match_dup 1) (const_int 0)))
13686               (set (match_dup 0) (ctz:SI (match_dup 1)))])
13687    (set (strict_low_part (match_dup 3))
13688         (eq:QI (reg:CCZ FLAGS_REG) (const_int 0)))
13689    (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
13690               (clobber (reg:CC FLAGS_REG))])
13691    (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
13692               (clobber (reg:CC FLAGS_REG))])
13693    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
13694               (clobber (reg:CC FLAGS_REG))])]
13696   operands[3] = gen_lowpart (QImode, operands[2]);
13697   ix86_expand_clear (operands[2]);
13700 (define_insn "*ffssi_1"
13701   [(set (reg:CCZ FLAGS_REG)
13702         (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "rm")
13703                      (const_int 0)))
13704    (set (match_operand:SI 0 "register_operand" "=r")
13705         (ctz:SI (match_dup 1)))]
13706   ""
13707   "bsf{l}\t{%1, %0|%0, %1}"
13708   [(set_attr "prefix_0f" "1")])
13710 (define_expand "ffsdi2"
13711   [(parallel
13712      [(set (match_operand:DI 0 "register_operand" "") 
13713            (ffs:DI (match_operand:DI 1 "nonimmediate_operand" "")))
13714       (clobber (match_scratch:DI 2 ""))
13715       (clobber (reg:CC FLAGS_REG))])]
13716   "TARGET_64BIT && TARGET_CMOVE"
13717   "")
13719 (define_insn_and_split "*ffs_rex64"
13720   [(set (match_operand:DI 0 "register_operand" "=r") 
13721         (ffs:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
13722    (clobber (match_scratch:DI 2 "=&r"))
13723    (clobber (reg:CC FLAGS_REG))]
13724   "TARGET_64BIT && TARGET_CMOVE"
13725   "#"
13726   "&& reload_completed"
13727   [(set (match_dup 2) (const_int -1))
13728    (parallel [(set (reg:CCZ FLAGS_REG)
13729                    (compare:CCZ (match_dup 1) (const_int 0)))
13730               (set (match_dup 0) (ctz:DI (match_dup 1)))])
13731    (set (match_dup 0) (if_then_else:DI
13732                         (eq (reg:CCZ FLAGS_REG) (const_int 0))
13733                         (match_dup 2)
13734                         (match_dup 0)))
13735    (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (const_int 1)))
13736               (clobber (reg:CC FLAGS_REG))])]
13737   "")
13739 (define_insn "*ffsdi_1"
13740   [(set (reg:CCZ FLAGS_REG)
13741         (compare:CCZ (match_operand:DI 1 "nonimmediate_operand" "rm")
13742                      (const_int 0)))
13743    (set (match_operand:DI 0 "register_operand" "=r")
13744         (ctz:DI (match_dup 1)))]
13745   "TARGET_64BIT"
13746   "bsf{q}\t{%1, %0|%0, %1}"
13747   [(set_attr "prefix_0f" "1")])
13749 (define_insn "ctzsi2"
13750   [(set (match_operand:SI 0 "register_operand" "=r")
13751         (ctz:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
13752    (clobber (reg:CC FLAGS_REG))]
13753   ""
13754   "bsf{l}\t{%1, %0|%0, %1}"
13755   [(set_attr "prefix_0f" "1")])
13757 (define_insn "ctzdi2"
13758   [(set (match_operand:DI 0 "register_operand" "=r")
13759         (ctz:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
13760    (clobber (reg:CC FLAGS_REG))]
13761   "TARGET_64BIT"
13762   "bsf{q}\t{%1, %0|%0, %1}"
13763   [(set_attr "prefix_0f" "1")])
13765 (define_expand "clzsi2"
13766   [(parallel
13767      [(set (match_operand:SI 0 "register_operand" "")
13768            (minus:SI (const_int 31)
13769                      (clz:SI (match_operand:SI 1 "nonimmediate_operand" ""))))
13770       (clobber (reg:CC FLAGS_REG))])
13771    (parallel
13772      [(set (match_dup 0) (xor:SI (match_dup 0) (const_int 31)))
13773       (clobber (reg:CC FLAGS_REG))])]
13774   ""
13775   "")
13777 (define_insn "*bsr"
13778   [(set (match_operand:SI 0 "register_operand" "=r")
13779         (minus:SI (const_int 31)
13780                   (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
13781    (clobber (reg:CC FLAGS_REG))]
13782   ""
13783   "bsr{l}\t{%1, %0|%0, %1}"
13784   [(set_attr "prefix_0f" "1")])
13786 (define_expand "clzdi2"
13787   [(parallel
13788      [(set (match_operand:DI 0 "register_operand" "")
13789            (minus:DI (const_int 63)
13790                      (clz:DI (match_operand:DI 1 "nonimmediate_operand" ""))))
13791       (clobber (reg:CC FLAGS_REG))])
13792    (parallel
13793      [(set (match_dup 0) (xor:DI (match_dup 0) (const_int 63)))
13794       (clobber (reg:CC FLAGS_REG))])]
13795   "TARGET_64BIT"
13796   "")
13798 (define_insn "*bsr_rex64"
13799   [(set (match_operand:DI 0 "register_operand" "=r")
13800         (minus:DI (const_int 63)
13801                   (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))))
13802    (clobber (reg:CC FLAGS_REG))]
13803   "TARGET_64BIT"
13804   "bsr{q}\t{%1, %0|%0, %1}"
13805   [(set_attr "prefix_0f" "1")])
13807 ;; Thread-local storage patterns for ELF.
13809 ;; Note that these code sequences must appear exactly as shown
13810 ;; in order to allow linker relaxation.
13812 (define_insn "*tls_global_dynamic_32_gnu"
13813   [(set (match_operand:SI 0 "register_operand" "=a")
13814         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
13815                     (match_operand:SI 2 "tls_symbolic_operand" "")
13816                     (match_operand:SI 3 "call_insn_operand" "")]
13817                     UNSPEC_TLS_GD))
13818    (clobber (match_scratch:SI 4 "=d"))
13819    (clobber (match_scratch:SI 5 "=c"))
13820    (clobber (reg:CC FLAGS_REG))]
13821   "!TARGET_64BIT && TARGET_GNU_TLS"
13822   "lea{l}\t{%a2@TLSGD(,%1,1), %0|%0, %a2@TLSGD[%1*1]}\;call\t%P3"
13823   [(set_attr "type" "multi")
13824    (set_attr "length" "12")])
13826 (define_insn "*tls_global_dynamic_32_sun"
13827   [(set (match_operand:SI 0 "register_operand" "=a")
13828         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
13829                     (match_operand:SI 2 "tls_symbolic_operand" "")
13830                     (match_operand:SI 3 "call_insn_operand" "")]
13831                     UNSPEC_TLS_GD))
13832    (clobber (match_scratch:SI 4 "=d"))
13833    (clobber (match_scratch:SI 5 "=c"))
13834    (clobber (reg:CC FLAGS_REG))]
13835   "!TARGET_64BIT && TARGET_SUN_TLS"
13836   "lea{l}\t{%a2@DTLNDX(%1), %4|%4, %a2@DTLNDX[%1]}
13837         push{l}\t%4\;call\t%a2@TLSPLT\;pop{l}\t%4\;nop"
13838   [(set_attr "type" "multi")
13839    (set_attr "length" "14")])
13841 (define_expand "tls_global_dynamic_32"
13842   [(parallel [(set (match_operand:SI 0 "register_operand" "")
13843                    (unspec:SI
13844                     [(match_dup 2)
13845                      (match_operand:SI 1 "tls_symbolic_operand" "")
13846                      (match_dup 3)]
13847                     UNSPEC_TLS_GD))
13848               (clobber (match_scratch:SI 4 ""))
13849               (clobber (match_scratch:SI 5 ""))
13850               (clobber (reg:CC FLAGS_REG))])]
13851   ""
13853   if (flag_pic)
13854     operands[2] = pic_offset_table_rtx;
13855   else
13856     {
13857       operands[2] = gen_reg_rtx (Pmode);
13858       emit_insn (gen_set_got (operands[2]));
13859     }
13860   operands[3] = ix86_tls_get_addr ();
13863 (define_insn "*tls_global_dynamic_64"
13864   [(set (match_operand:DI 0 "register_operand" "=a")
13865         (call (mem:QI (match_operand:DI 2 "call_insn_operand" ""))
13866                       (match_operand:DI 3 "" "")))
13867    (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
13868               UNSPEC_TLS_GD)]
13869   "TARGET_64BIT"
13870   ".byte\t0x66\;lea{q}\t{%a1@TLSGD(%%rip), %%rdi|%%rdi, %a1@TLSGD[%%rip]}\;.word\t0x6666\;rex64\;call\t%P2"
13871   [(set_attr "type" "multi")
13872    (set_attr "length" "16")])
13874 (define_expand "tls_global_dynamic_64"
13875   [(parallel [(set (match_operand:DI 0 "register_operand" "")
13876                    (call (mem:QI (match_dup 2)) (const_int 0)))
13877               (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
13878                          UNSPEC_TLS_GD)])]
13879   ""
13881   operands[2] = ix86_tls_get_addr ();
13884 (define_insn "*tls_local_dynamic_base_32_gnu"
13885   [(set (match_operand:SI 0 "register_operand" "=a")
13886         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
13887                     (match_operand:SI 2 "call_insn_operand" "")]
13888                    UNSPEC_TLS_LD_BASE))
13889    (clobber (match_scratch:SI 3 "=d"))
13890    (clobber (match_scratch:SI 4 "=c"))
13891    (clobber (reg:CC FLAGS_REG))]
13892   "!TARGET_64BIT && TARGET_GNU_TLS"
13893   "lea{l}\t{%&@TLSLDM(%1), %0|%0, %&@TLSLDM[%1]}\;call\t%P2"
13894   [(set_attr "type" "multi")
13895    (set_attr "length" "11")])
13897 (define_insn "*tls_local_dynamic_base_32_sun"
13898   [(set (match_operand:SI 0 "register_operand" "=a")
13899         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
13900                     (match_operand:SI 2 "call_insn_operand" "")]
13901                    UNSPEC_TLS_LD_BASE))
13902    (clobber (match_scratch:SI 3 "=d"))
13903    (clobber (match_scratch:SI 4 "=c"))
13904    (clobber (reg:CC FLAGS_REG))]
13905   "!TARGET_64BIT && TARGET_SUN_TLS"
13906   "lea{l}\t{%&@TMDNX(%1), %3|%3, %&@TMDNX[%1]}
13907         push{l}\t%3\;call\t%&@TLSPLT\;pop{l}\t%3"
13908   [(set_attr "type" "multi")
13909    (set_attr "length" "13")])
13911 (define_expand "tls_local_dynamic_base_32"
13912   [(parallel [(set (match_operand:SI 0 "register_operand" "")
13913                    (unspec:SI [(match_dup 1) (match_dup 2)]
13914                               UNSPEC_TLS_LD_BASE))
13915               (clobber (match_scratch:SI 3 ""))
13916               (clobber (match_scratch:SI 4 ""))
13917               (clobber (reg:CC FLAGS_REG))])]
13918   ""
13920   if (flag_pic)
13921     operands[1] = pic_offset_table_rtx;
13922   else
13923     {
13924       operands[1] = gen_reg_rtx (Pmode);
13925       emit_insn (gen_set_got (operands[1]));
13926     }
13927   operands[2] = ix86_tls_get_addr ();
13930 (define_insn "*tls_local_dynamic_base_64"
13931   [(set (match_operand:DI 0 "register_operand" "=a")
13932         (call (mem:QI (match_operand:DI 1 "call_insn_operand" ""))
13933                       (match_operand:DI 2 "" "")))
13934    (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
13935   "TARGET_64BIT"
13936   "lea{q}\t{%&@TLSLD(%%rip), %%rdi|%%rdi, %&@TLSLD[%%rip]}\;call\t%P1"
13937   [(set_attr "type" "multi")
13938    (set_attr "length" "12")])
13940 (define_expand "tls_local_dynamic_base_64"
13941   [(parallel [(set (match_operand:DI 0 "register_operand" "")
13942                    (call (mem:QI (match_dup 1)) (const_int 0)))
13943               (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])]
13944   ""
13946   operands[1] = ix86_tls_get_addr ();
13949 ;; Local dynamic of a single variable is a lose.  Show combine how
13950 ;; to convert that back to global dynamic.
13952 (define_insn_and_split "*tls_local_dynamic_32_once"
13953   [(set (match_operand:SI 0 "register_operand" "=a")
13954         (plus:SI (unspec:SI [(match_operand:SI 1 "register_operand" "b")
13955                              (match_operand:SI 2 "call_insn_operand" "")]
13956                             UNSPEC_TLS_LD_BASE)
13957                  (const:SI (unspec:SI
13958                             [(match_operand:SI 3 "tls_symbolic_operand" "")]
13959                             UNSPEC_DTPOFF))))
13960    (clobber (match_scratch:SI 4 "=d"))
13961    (clobber (match_scratch:SI 5 "=c"))
13962    (clobber (reg:CC FLAGS_REG))]
13963   ""
13964   "#"
13965   ""
13966   [(parallel [(set (match_dup 0)
13967                    (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
13968                               UNSPEC_TLS_GD))
13969               (clobber (match_dup 4))
13970               (clobber (match_dup 5))
13971               (clobber (reg:CC FLAGS_REG))])]
13972   "")
13974 ;; Load and add the thread base pointer from %gs:0.
13976 (define_insn "*load_tp_si"
13977   [(set (match_operand:SI 0 "register_operand" "=r")
13978         (unspec:SI [(const_int 0)] UNSPEC_TP))]
13979   "!TARGET_64BIT"
13980   "mov{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}"
13981   [(set_attr "type" "imov")
13982    (set_attr "modrm" "0")
13983    (set_attr "length" "7")
13984    (set_attr "memory" "load")
13985    (set_attr "imm_disp" "false")])
13987 (define_insn "*add_tp_si"
13988   [(set (match_operand:SI 0 "register_operand" "=r")
13989         (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
13990                  (match_operand:SI 1 "register_operand" "0")))
13991    (clobber (reg:CC FLAGS_REG))]
13992   "!TARGET_64BIT"
13993   "add{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}"
13994   [(set_attr "type" "alu")
13995    (set_attr "modrm" "0")
13996    (set_attr "length" "7")
13997    (set_attr "memory" "load")
13998    (set_attr "imm_disp" "false")])
14000 (define_insn "*load_tp_di"
14001   [(set (match_operand:DI 0 "register_operand" "=r")
14002         (unspec:DI [(const_int 0)] UNSPEC_TP))]
14003   "TARGET_64BIT"
14004   "mov{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}"
14005   [(set_attr "type" "imov")
14006    (set_attr "modrm" "0")
14007    (set_attr "length" "7")
14008    (set_attr "memory" "load")
14009    (set_attr "imm_disp" "false")])
14011 (define_insn "*add_tp_di"
14012   [(set (match_operand:DI 0 "register_operand" "=r")
14013         (plus:DI (unspec:DI [(const_int 0)] UNSPEC_TP)
14014                  (match_operand:DI 1 "register_operand" "0")))
14015    (clobber (reg:CC FLAGS_REG))]
14016   "TARGET_64BIT"
14017   "add{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}"
14018   [(set_attr "type" "alu")
14019    (set_attr "modrm" "0")
14020    (set_attr "length" "7")
14021    (set_attr "memory" "load")
14022    (set_attr "imm_disp" "false")])
14024 ;; These patterns match the binary 387 instructions for addM3, subM3,
14025 ;; mulM3 and divM3.  There are three patterns for each of DFmode and
14026 ;; SFmode.  The first is the normal insn, the second the same insn but
14027 ;; with one operand a conversion, and the third the same insn but with
14028 ;; the other operand a conversion.  The conversion may be SFmode or
14029 ;; SImode if the target mode DFmode, but only SImode if the target mode
14030 ;; is SFmode.
14032 ;; Gcc is slightly more smart about handling normal two address instructions
14033 ;; so use special patterns for add and mull.
14035 (define_insn "*fop_sf_comm_mixed"
14036   [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
14037         (match_operator:SF 3 "binary_fp_operator"
14038                         [(match_operand:SF 1 "nonimmediate_operand" "%0,0")
14039                          (match_operand:SF 2 "nonimmediate_operand" "fm#x,xm#f")]))]
14040   "TARGET_MIX_SSE_I387
14041    && COMMUTATIVE_ARITH_P (operands[3])
14042    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14043   "* return output_387_binary_op (insn, operands);"
14044   [(set (attr "type") 
14045         (if_then_else (eq_attr "alternative" "1")
14046            (if_then_else (match_operand:SF 3 "mult_operator" "") 
14047               (const_string "ssemul")
14048               (const_string "sseadd"))
14049            (if_then_else (match_operand:SF 3 "mult_operator" "") 
14050               (const_string "fmul")
14051               (const_string "fop"))))
14052    (set_attr "mode" "SF")])
14054 (define_insn "*fop_sf_comm_sse"
14055   [(set (match_operand:SF 0 "register_operand" "=x")
14056         (match_operator:SF 3 "binary_fp_operator"
14057                         [(match_operand:SF 1 "nonimmediate_operand" "%0")
14058                          (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
14059   "TARGET_SSE_MATH
14060    && COMMUTATIVE_ARITH_P (operands[3])
14061    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14062   "* return output_387_binary_op (insn, operands);"
14063   [(set (attr "type") 
14064         (if_then_else (match_operand:SF 3 "mult_operator" "") 
14065            (const_string "ssemul")
14066            (const_string "sseadd")))
14067    (set_attr "mode" "SF")])
14069 (define_insn "*fop_sf_comm_i387"
14070   [(set (match_operand:SF 0 "register_operand" "=f")
14071         (match_operator:SF 3 "binary_fp_operator"
14072                         [(match_operand:SF 1 "nonimmediate_operand" "%0")
14073                          (match_operand:SF 2 "nonimmediate_operand" "fm")]))]
14074   "TARGET_80387
14075    && COMMUTATIVE_ARITH_P (operands[3])
14076    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14077   "* return output_387_binary_op (insn, operands);"
14078   [(set (attr "type") 
14079         (if_then_else (match_operand:SF 3 "mult_operator" "") 
14080            (const_string "fmul")
14081            (const_string "fop")))
14082    (set_attr "mode" "SF")])
14084 (define_insn "*fop_sf_1_mixed"
14085   [(set (match_operand:SF 0 "register_operand" "=f,f,x")
14086         (match_operator:SF 3 "binary_fp_operator"
14087                         [(match_operand:SF 1 "nonimmediate_operand" "0,fm,0")
14088                          (match_operand:SF 2 "nonimmediate_operand" "fm,0,xm#f")]))]
14089   "TARGET_MIX_SSE_I387
14090    && !COMMUTATIVE_ARITH_P (operands[3])
14091    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14092   "* return output_387_binary_op (insn, operands);"
14093   [(set (attr "type") 
14094         (cond [(and (eq_attr "alternative" "2")
14095                     (match_operand:SF 3 "mult_operator" ""))
14096                  (const_string "ssemul")
14097                (and (eq_attr "alternative" "2")
14098                     (match_operand:SF 3 "div_operator" ""))
14099                  (const_string "ssediv")
14100                (eq_attr "alternative" "2")
14101                  (const_string "sseadd")
14102                (match_operand:SF 3 "mult_operator" "") 
14103                  (const_string "fmul")
14104                (match_operand:SF 3 "div_operator" "") 
14105                  (const_string "fdiv")
14106               ]
14107               (const_string "fop")))
14108    (set_attr "mode" "SF")])
14110 (define_insn "*fop_sf_1_sse"
14111   [(set (match_operand:SF 0 "register_operand" "=x")
14112         (match_operator:SF 3 "binary_fp_operator"
14113                         [(match_operand:SF 1 "register_operand" "0")
14114                          (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
14115   "TARGET_SSE_MATH
14116    && !COMMUTATIVE_ARITH_P (operands[3])"
14117   "* return output_387_binary_op (insn, operands);"
14118   [(set (attr "type") 
14119         (cond [(match_operand:SF 3 "mult_operator" "")
14120                  (const_string "ssemul")
14121                (match_operand:SF 3 "div_operator" "")
14122                  (const_string "ssediv")
14123               ]
14124               (const_string "sseadd")))
14125    (set_attr "mode" "SF")])
14127 ;; This pattern is not fully shadowed by the pattern above.
14128 (define_insn "*fop_sf_1_i387"
14129   [(set (match_operand:SF 0 "register_operand" "=f,f")
14130         (match_operator:SF 3 "binary_fp_operator"
14131                         [(match_operand:SF 1 "nonimmediate_operand" "0,fm")
14132                          (match_operand:SF 2 "nonimmediate_operand" "fm,0")]))]
14133   "TARGET_80387 && !TARGET_SSE_MATH
14134    && !COMMUTATIVE_ARITH_P (operands[3])
14135    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14136   "* return output_387_binary_op (insn, operands);"
14137   [(set (attr "type") 
14138         (cond [(match_operand:SF 3 "mult_operator" "") 
14139                  (const_string "fmul")
14140                (match_operand:SF 3 "div_operator" "") 
14141                  (const_string "fdiv")
14142               ]
14143               (const_string "fop")))
14144    (set_attr "mode" "SF")])
14146 ;; ??? Add SSE splitters for these!
14147 (define_insn "*fop_sf_2<mode>_i387"
14148   [(set (match_operand:SF 0 "register_operand" "=f,f")
14149         (match_operator:SF 3 "binary_fp_operator"
14150           [(float:SF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14151            (match_operand:SF 2 "register_operand" "0,0")]))]
14152   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH"
14153   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14154   [(set (attr "type") 
14155         (cond [(match_operand:SF 3 "mult_operator" "") 
14156                  (const_string "fmul")
14157                (match_operand:SF 3 "div_operator" "") 
14158                  (const_string "fdiv")
14159               ]
14160               (const_string "fop")))
14161    (set_attr "fp_int_src" "true")
14162    (set_attr "mode" "<MODE>")])
14164 (define_insn "*fop_sf_3<mode>_i387"
14165   [(set (match_operand:SF 0 "register_operand" "=f,f")
14166         (match_operator:SF 3 "binary_fp_operator"
14167           [(match_operand:SF 1 "register_operand" "0,0")
14168            (float:SF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14169   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH"
14170   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14171   [(set (attr "type") 
14172         (cond [(match_operand:SF 3 "mult_operator" "") 
14173                  (const_string "fmul")
14174                (match_operand:SF 3 "div_operator" "") 
14175                  (const_string "fdiv")
14176               ]
14177               (const_string "fop")))
14178    (set_attr "fp_int_src" "true")
14179    (set_attr "mode" "<MODE>")])
14181 (define_insn "*fop_df_comm_mixed"
14182   [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
14183         (match_operator:DF 3 "binary_fp_operator"
14184                         [(match_operand:DF 1 "nonimmediate_operand" "%0,0")
14185                          (match_operand:DF 2 "nonimmediate_operand" "fm#Y,Ym#f")]))]
14186   "TARGET_SSE2 && TARGET_MIX_SSE_I387
14187    && COMMUTATIVE_ARITH_P (operands[3])
14188    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14189   "* return output_387_binary_op (insn, operands);"
14190   [(set (attr "type") 
14191         (if_then_else (eq_attr "alternative" "1")
14192            (if_then_else (match_operand:SF 3 "mult_operator" "") 
14193               (const_string "ssemul")
14194               (const_string "sseadd"))
14195            (if_then_else (match_operand:SF 3 "mult_operator" "") 
14196               (const_string "fmul")
14197               (const_string "fop"))))
14198    (set_attr "mode" "DF")])
14200 (define_insn "*fop_df_comm_sse"
14201   [(set (match_operand:DF 0 "register_operand" "=Y")
14202         (match_operator:DF 3 "binary_fp_operator"
14203                         [(match_operand:DF 1 "nonimmediate_operand" "%0")
14204                          (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
14205   "TARGET_SSE2 && TARGET_SSE_MATH
14206    && COMMUTATIVE_ARITH_P (operands[3])
14207    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14208   "* return output_387_binary_op (insn, operands);"
14209   [(set (attr "type") 
14210         (if_then_else (match_operand:SF 3 "mult_operator" "") 
14211            (const_string "ssemul")
14212            (const_string "sseadd")))
14213    (set_attr "mode" "DF")])
14215 (define_insn "*fop_df_comm_i387"
14216   [(set (match_operand:DF 0 "register_operand" "=f")
14217         (match_operator:DF 3 "binary_fp_operator"
14218                         [(match_operand:DF 1 "nonimmediate_operand" "%0")
14219                          (match_operand:DF 2 "nonimmediate_operand" "fm")]))]
14220   "TARGET_80387
14221    && COMMUTATIVE_ARITH_P (operands[3])
14222    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14223   "* return output_387_binary_op (insn, operands);"
14224   [(set (attr "type") 
14225         (if_then_else (match_operand:SF 3 "mult_operator" "") 
14226            (const_string "fmul")
14227            (const_string "fop")))
14228    (set_attr "mode" "DF")])
14230 (define_insn "*fop_df_1_mixed"
14231   [(set (match_operand:DF 0 "register_operand" "=f#Y,f#Y,Y#f")
14232         (match_operator:DF 3 "binary_fp_operator"
14233                         [(match_operand:DF 1 "nonimmediate_operand" "0,fm,0")
14234                          (match_operand:DF 2 "nonimmediate_operand" "fm,0,Ym#f")]))]
14235   "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
14236    && !COMMUTATIVE_ARITH_P (operands[3])
14237    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14238   "* return output_387_binary_op (insn, operands);"
14239   [(set (attr "type") 
14240         (cond [(and (eq_attr "alternative" "2")
14241                     (match_operand:SF 3 "mult_operator" ""))
14242                  (const_string "ssemul")
14243                (and (eq_attr "alternative" "2")
14244                     (match_operand:SF 3 "div_operator" ""))
14245                  (const_string "ssediv")
14246                (eq_attr "alternative" "2")
14247                  (const_string "sseadd")
14248                (match_operand:DF 3 "mult_operator" "") 
14249                  (const_string "fmul")
14250                (match_operand:DF 3 "div_operator" "") 
14251                  (const_string "fdiv")
14252               ]
14253               (const_string "fop")))
14254    (set_attr "mode" "DF")])
14256 (define_insn "*fop_df_1_sse"
14257   [(set (match_operand:DF 0 "register_operand" "=Y")
14258         (match_operator:DF 3 "binary_fp_operator"
14259                         [(match_operand:DF 1 "register_operand" "0")
14260                          (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
14261   "TARGET_SSE2 && TARGET_SSE_MATH
14262    && !COMMUTATIVE_ARITH_P (operands[3])"
14263   "* return output_387_binary_op (insn, operands);"
14264   [(set_attr "mode" "DF")
14265    (set (attr "type") 
14266         (cond [(match_operand:SF 3 "mult_operator" "")
14267                  (const_string "ssemul")
14268                (match_operand:SF 3 "div_operator" "")
14269                  (const_string "ssediv")
14270               ]
14271               (const_string "sseadd")))])
14273 ;; This pattern is not fully shadowed by the pattern above.
14274 (define_insn "*fop_df_1_i387"
14275   [(set (match_operand:DF 0 "register_operand" "=f,f")
14276         (match_operator:DF 3 "binary_fp_operator"
14277                         [(match_operand:DF 1 "nonimmediate_operand" "0,fm")
14278                          (match_operand:DF 2 "nonimmediate_operand" "fm,0")]))]
14279   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
14280    && !COMMUTATIVE_ARITH_P (operands[3])
14281    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14282   "* return output_387_binary_op (insn, operands);"
14283   [(set (attr "type") 
14284         (cond [(match_operand:DF 3 "mult_operator" "") 
14285                  (const_string "fmul")
14286                (match_operand:DF 3 "div_operator" "")
14287                  (const_string "fdiv")
14288               ]
14289               (const_string "fop")))
14290    (set_attr "mode" "DF")])
14292 ;; ??? Add SSE splitters for these!
14293 (define_insn "*fop_df_2<mode>_i387"
14294   [(set (match_operand:DF 0 "register_operand" "=f,f")
14295         (match_operator:DF 3 "binary_fp_operator"
14296            [(float:DF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14297             (match_operand:DF 2 "register_operand" "0,0")]))]
14298   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
14299    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14300   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14301   [(set (attr "type") 
14302         (cond [(match_operand:DF 3 "mult_operator" "") 
14303                  (const_string "fmul")
14304                (match_operand:DF 3 "div_operator" "") 
14305                  (const_string "fdiv")
14306               ]
14307               (const_string "fop")))
14308    (set_attr "fp_int_src" "true")
14309    (set_attr "mode" "<MODE>")])
14311 (define_insn "*fop_df_3<mode>_i387"
14312   [(set (match_operand:DF 0 "register_operand" "=f,f")
14313         (match_operator:DF 3 "binary_fp_operator"
14314            [(match_operand:DF 1 "register_operand" "0,0")
14315             (float:DF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14316   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
14317    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14318   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14319   [(set (attr "type") 
14320         (cond [(match_operand:DF 3 "mult_operator" "") 
14321                  (const_string "fmul")
14322                (match_operand:DF 3 "div_operator" "") 
14323                  (const_string "fdiv")
14324               ]
14325               (const_string "fop")))
14326    (set_attr "fp_int_src" "true")
14327    (set_attr "mode" "<MODE>")])
14329 (define_insn "*fop_df_4_i387"
14330   [(set (match_operand:DF 0 "register_operand" "=f,f")
14331         (match_operator:DF 3 "binary_fp_operator"
14332            [(float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
14333             (match_operand:DF 2 "register_operand" "0,f")]))]
14334   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
14335    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14336   "* return output_387_binary_op (insn, operands);"
14337   [(set (attr "type") 
14338         (cond [(match_operand:DF 3 "mult_operator" "") 
14339                  (const_string "fmul")
14340                (match_operand:DF 3 "div_operator" "") 
14341                  (const_string "fdiv")
14342               ]
14343               (const_string "fop")))
14344    (set_attr "mode" "SF")])
14346 (define_insn "*fop_df_5_i387"
14347   [(set (match_operand:DF 0 "register_operand" "=f,f")
14348         (match_operator:DF 3 "binary_fp_operator"
14349           [(match_operand:DF 1 "register_operand" "0,f")
14350            (float_extend:DF
14351             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
14352   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14353   "* return output_387_binary_op (insn, operands);"
14354   [(set (attr "type") 
14355         (cond [(match_operand:DF 3 "mult_operator" "") 
14356                  (const_string "fmul")
14357                (match_operand:DF 3 "div_operator" "") 
14358                  (const_string "fdiv")
14359               ]
14360               (const_string "fop")))
14361    (set_attr "mode" "SF")])
14363 (define_insn "*fop_df_6_i387"
14364   [(set (match_operand:DF 0 "register_operand" "=f,f")
14365         (match_operator:DF 3 "binary_fp_operator"
14366           [(float_extend:DF
14367             (match_operand:SF 1 "register_operand" "0,f"))
14368            (float_extend:DF
14369             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
14370   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14371   "* return output_387_binary_op (insn, operands);"
14372   [(set (attr "type") 
14373         (cond [(match_operand:DF 3 "mult_operator" "") 
14374                  (const_string "fmul")
14375                (match_operand:DF 3 "div_operator" "") 
14376                  (const_string "fdiv")
14377               ]
14378               (const_string "fop")))
14379    (set_attr "mode" "SF")])
14381 (define_insn "*fop_xf_comm_i387"
14382   [(set (match_operand:XF 0 "register_operand" "=f")
14383         (match_operator:XF 3 "binary_fp_operator"
14384                         [(match_operand:XF 1 "register_operand" "%0")
14385                          (match_operand:XF 2 "register_operand" "f")]))]
14386   "TARGET_80387
14387    && COMMUTATIVE_ARITH_P (operands[3])"
14388   "* return output_387_binary_op (insn, operands);"
14389   [(set (attr "type") 
14390         (if_then_else (match_operand:XF 3 "mult_operator" "") 
14391            (const_string "fmul")
14392            (const_string "fop")))
14393    (set_attr "mode" "XF")])
14395 (define_insn "*fop_xf_1_i387"
14396   [(set (match_operand:XF 0 "register_operand" "=f,f")
14397         (match_operator:XF 3 "binary_fp_operator"
14398                         [(match_operand:XF 1 "register_operand" "0,f")
14399                          (match_operand:XF 2 "register_operand" "f,0")]))]
14400   "TARGET_80387
14401    && !COMMUTATIVE_ARITH_P (operands[3])"
14402   "* return output_387_binary_op (insn, operands);"
14403   [(set (attr "type") 
14404         (cond [(match_operand:XF 3 "mult_operator" "") 
14405                  (const_string "fmul")
14406                (match_operand:XF 3 "div_operator" "") 
14407                  (const_string "fdiv")
14408               ]
14409               (const_string "fop")))
14410    (set_attr "mode" "XF")])
14412 (define_insn "*fop_xf_2<mode>_i387"
14413   [(set (match_operand:XF 0 "register_operand" "=f,f")
14414         (match_operator:XF 3 "binary_fp_operator"
14415            [(float:XF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14416             (match_operand:XF 2 "register_operand" "0,0")]))]
14417   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP"
14418   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14419   [(set (attr "type") 
14420         (cond [(match_operand:XF 3 "mult_operator" "") 
14421                  (const_string "fmul")
14422                (match_operand:XF 3 "div_operator" "") 
14423                  (const_string "fdiv")
14424               ]
14425               (const_string "fop")))
14426    (set_attr "fp_int_src" "true")
14427    (set_attr "mode" "<MODE>")])
14429 (define_insn "*fop_xf_3<mode>_i387"
14430   [(set (match_operand:XF 0 "register_operand" "=f,f")
14431         (match_operator:XF 3 "binary_fp_operator"
14432           [(match_operand:XF 1 "register_operand" "0,0")
14433            (float:XF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14434   "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP"
14435   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14436   [(set (attr "type") 
14437         (cond [(match_operand:XF 3 "mult_operator" "") 
14438                  (const_string "fmul")
14439                (match_operand:XF 3 "div_operator" "") 
14440                  (const_string "fdiv")
14441               ]
14442               (const_string "fop")))
14443    (set_attr "fp_int_src" "true")
14444    (set_attr "mode" "<MODE>")])
14446 (define_insn "*fop_xf_4_i387"
14447   [(set (match_operand:XF 0 "register_operand" "=f,f")
14448         (match_operator:XF 3 "binary_fp_operator"
14449            [(float_extend:XF (match_operand 1 "nonimmediate_operand" "fm,0"))
14450             (match_operand:XF 2 "register_operand" "0,f")]))]
14451   "TARGET_80387"
14452   "* return output_387_binary_op (insn, operands);"
14453   [(set (attr "type") 
14454         (cond [(match_operand:XF 3 "mult_operator" "") 
14455                  (const_string "fmul")
14456                (match_operand:XF 3 "div_operator" "") 
14457                  (const_string "fdiv")
14458               ]
14459               (const_string "fop")))
14460    (set_attr "mode" "SF")])
14462 (define_insn "*fop_xf_5_i387"
14463   [(set (match_operand:XF 0 "register_operand" "=f,f")
14464         (match_operator:XF 3 "binary_fp_operator"
14465           [(match_operand:XF 1 "register_operand" "0,f")
14466            (float_extend:XF
14467             (match_operand 2 "nonimmediate_operand" "fm,0"))]))]
14468   "TARGET_80387"
14469   "* return output_387_binary_op (insn, operands);"
14470   [(set (attr "type") 
14471         (cond [(match_operand:XF 3 "mult_operator" "") 
14472                  (const_string "fmul")
14473                (match_operand:XF 3 "div_operator" "") 
14474                  (const_string "fdiv")
14475               ]
14476               (const_string "fop")))
14477    (set_attr "mode" "SF")])
14479 (define_insn "*fop_xf_6_i387"
14480   [(set (match_operand:XF 0 "register_operand" "=f,f")
14481         (match_operator:XF 3 "binary_fp_operator"
14482           [(float_extend:XF
14483             (match_operand 1 "register_operand" "0,f"))
14484            (float_extend:XF
14485             (match_operand 2 "nonimmediate_operand" "fm,0"))]))]
14486   "TARGET_80387"
14487   "* return output_387_binary_op (insn, operands);"
14488   [(set (attr "type") 
14489         (cond [(match_operand:XF 3 "mult_operator" "") 
14490                  (const_string "fmul")
14491                (match_operand:XF 3 "div_operator" "") 
14492                  (const_string "fdiv")
14493               ]
14494               (const_string "fop")))
14495    (set_attr "mode" "SF")])
14497 (define_split
14498   [(set (match_operand 0 "register_operand" "")
14499         (match_operator 3 "binary_fp_operator"
14500            [(float (match_operand:X87MODEI12 1 "register_operand" ""))
14501             (match_operand 2 "register_operand" "")]))]
14502   "TARGET_80387 && reload_completed
14503    && FLOAT_MODE_P (GET_MODE (operands[0]))"
14504   [(const_int 0)]
14506   operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
14507   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
14508   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
14509                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
14510                                           GET_MODE (operands[3]),
14511                                           operands[4],
14512                                           operands[2])));
14513   ix86_free_from_memory (GET_MODE (operands[1]));
14514   DONE;
14517 (define_split
14518   [(set (match_operand 0 "register_operand" "")
14519         (match_operator 3 "binary_fp_operator"
14520            [(match_operand 1 "register_operand" "")
14521             (float (match_operand:X87MODEI12 2 "register_operand" ""))]))]
14522   "TARGET_80387 && reload_completed
14523    && FLOAT_MODE_P (GET_MODE (operands[0]))"
14524   [(const_int 0)]
14526   operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
14527   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
14528   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
14529                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
14530                                           GET_MODE (operands[3]),
14531                                           operands[1],
14532                                           operands[4])));
14533   ix86_free_from_memory (GET_MODE (operands[2]));
14534   DONE;
14537 ;; FPU special functions.
14539 (define_expand "sqrtsf2"
14540   [(set (match_operand:SF 0 "register_operand" "")
14541         (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
14542   "TARGET_USE_FANCY_MATH_387 || TARGET_SSE_MATH"
14544   if (!TARGET_SSE_MATH)
14545     operands[1] = force_reg (SFmode, operands[1]);
14548 (define_insn "*sqrtsf2_mixed"
14549   [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
14550         (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "0#x,xm#f")))]
14551   "TARGET_USE_FANCY_MATH_387 && TARGET_MIX_SSE_I387"
14552   "@
14553    fsqrt
14554    sqrtss\t{%1, %0|%0, %1}"
14555   [(set_attr "type" "fpspc,sse")
14556    (set_attr "mode" "SF,SF")
14557    (set_attr "athlon_decode" "direct,*")])
14559 (define_insn "*sqrtsf2_sse"
14560   [(set (match_operand:SF 0 "register_operand" "=x")
14561         (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
14562   "TARGET_SSE_MATH"
14563   "sqrtss\t{%1, %0|%0, %1}"
14564   [(set_attr "type" "sse")
14565    (set_attr "mode" "SF")
14566    (set_attr "athlon_decode" "*")])
14568 (define_insn "*sqrtsf2_i387"
14569   [(set (match_operand:SF 0 "register_operand" "=f")
14570         (sqrt:SF (match_operand:SF 1 "register_operand" "0")))]
14571   "TARGET_USE_FANCY_MATH_387"
14572   "fsqrt"
14573   [(set_attr "type" "fpspc")
14574    (set_attr "mode" "SF")
14575    (set_attr "athlon_decode" "direct")])
14577 (define_expand "sqrtdf2"
14578   [(set (match_operand:DF 0 "register_operand" "")
14579         (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
14580   "TARGET_USE_FANCY_MATH_387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
14582   if (!(TARGET_SSE2 && TARGET_SSE_MATH))
14583     operands[1] = force_reg (DFmode, operands[1]);
14586 (define_insn "*sqrtdf2_mixed"
14587   [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
14588         (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "0#Y,Ym#f")))]
14589   "TARGET_USE_FANCY_MATH_387 && TARGET_SSE2 && TARGET_MIX_SSE_I387"
14590   "@
14591    fsqrt
14592    sqrtsd\t{%1, %0|%0, %1}"
14593   [(set_attr "type" "fpspc,sse")
14594    (set_attr "mode" "DF,DF")
14595    (set_attr "athlon_decode" "direct,*")])
14597 (define_insn "*sqrtdf2_sse"
14598   [(set (match_operand:DF 0 "register_operand" "=Y")
14599         (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
14600   "TARGET_SSE2 && TARGET_SSE_MATH"
14601   "sqrtsd\t{%1, %0|%0, %1}"
14602   [(set_attr "type" "sse")
14603    (set_attr "mode" "DF")
14604    (set_attr "athlon_decode" "*")])
14606 (define_insn "*sqrtdf2_i387"
14607   [(set (match_operand:DF 0 "register_operand" "=f")
14608         (sqrt:DF (match_operand:DF 1 "register_operand" "0")))]
14609   "TARGET_USE_FANCY_MATH_387"
14610   "fsqrt"
14611   [(set_attr "type" "fpspc")
14612    (set_attr "mode" "DF")
14613    (set_attr "athlon_decode" "direct")])
14615 (define_insn "*sqrtextendsfdf2_i387"
14616   [(set (match_operand:DF 0 "register_operand" "=f")
14617         (sqrt:DF (float_extend:DF
14618                   (match_operand:SF 1 "register_operand" "0"))))]
14619   "TARGET_USE_FANCY_MATH_387
14620    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)"
14621   "fsqrt"
14622   [(set_attr "type" "fpspc")
14623    (set_attr "mode" "DF")
14624    (set_attr "athlon_decode" "direct")])
14626 (define_insn "sqrtxf2"
14627   [(set (match_operand:XF 0 "register_operand" "=f")
14628         (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
14629   "TARGET_USE_FANCY_MATH_387 
14630    && (TARGET_IEEE_FP || flag_unsafe_math_optimizations) "
14631   "fsqrt"
14632   [(set_attr "type" "fpspc")
14633    (set_attr "mode" "XF")
14634    (set_attr "athlon_decode" "direct")])
14636 (define_insn "*sqrtextendsfxf2_i387"
14637   [(set (match_operand:XF 0 "register_operand" "=f")
14638         (sqrt:XF (float_extend:XF
14639                   (match_operand:SF 1 "register_operand" "0"))))]
14640   "TARGET_USE_FANCY_MATH_387"
14641   "fsqrt"
14642   [(set_attr "type" "fpspc")
14643    (set_attr "mode" "XF")
14644    (set_attr "athlon_decode" "direct")])
14646 (define_insn "*sqrtextenddfxf2_i387"
14647   [(set (match_operand:XF 0 "register_operand" "=f")
14648         (sqrt:XF (float_extend:XF
14649                   (match_operand:DF 1 "register_operand" "0"))))]
14650   "TARGET_USE_FANCY_MATH_387"
14651   "fsqrt"
14652   [(set_attr "type" "fpspc")
14653    (set_attr "mode" "XF")
14654    (set_attr "athlon_decode" "direct")])
14656 (define_insn "fpremxf4"
14657   [(set (match_operand:XF 0 "register_operand" "=f")
14658         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
14659                     (match_operand:XF 3 "register_operand" "1")]
14660                    UNSPEC_FPREM_F))
14661    (set (match_operand:XF 1 "register_operand" "=u")
14662         (unspec:XF [(match_dup 2) (match_dup 3)]
14663                    UNSPEC_FPREM_U))
14664    (set (reg:CCFP FPSR_REG)
14665         (unspec:CCFP [(const_int 0)] UNSPEC_NOP))]
14666   "TARGET_USE_FANCY_MATH_387
14667    && flag_unsafe_math_optimizations"
14668   "fprem"
14669   [(set_attr "type" "fpspc")
14670    (set_attr "mode" "XF")])
14672 (define_expand "fmodsf3"
14673   [(use (match_operand:SF 0 "register_operand" ""))
14674    (use (match_operand:SF 1 "register_operand" ""))
14675    (use (match_operand:SF 2 "register_operand" ""))]
14676   "TARGET_USE_FANCY_MATH_387
14677    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14678    && flag_unsafe_math_optimizations"
14680   rtx label = gen_label_rtx ();
14682   rtx op1 = gen_reg_rtx (XFmode);
14683   rtx op2 = gen_reg_rtx (XFmode);
14685   emit_insn(gen_extendsfxf2 (op1, operands[1]));
14686   emit_insn(gen_extendsfxf2 (op2, operands[2]));
14688   emit_label (label);
14690   emit_insn (gen_fpremxf4 (op1, op2, op1, op2));
14691   ix86_emit_fp_unordered_jump (label);
14693   emit_insn (gen_truncxfsf2_i387_noop (operands[0], op1));
14694   DONE;
14697 (define_expand "fmoddf3"
14698   [(use (match_operand:DF 0 "register_operand" ""))
14699    (use (match_operand:DF 1 "register_operand" ""))
14700    (use (match_operand:DF 2 "register_operand" ""))]
14701   "TARGET_USE_FANCY_MATH_387
14702    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14703    && flag_unsafe_math_optimizations"
14705   rtx label = gen_label_rtx ();
14707   rtx op1 = gen_reg_rtx (XFmode);
14708   rtx op2 = gen_reg_rtx (XFmode);
14710   emit_insn (gen_extenddfxf2 (op1, operands[1]));
14711   emit_insn (gen_extenddfxf2 (op2, operands[2]));
14713   emit_label (label);
14715   emit_insn (gen_fpremxf4 (op1, op2, op1, op2));
14716   ix86_emit_fp_unordered_jump (label);
14718   emit_insn (gen_truncxfdf2_i387_noop (operands[0], op1));
14719   DONE;
14722 (define_expand "fmodxf3"
14723   [(use (match_operand:XF 0 "register_operand" ""))
14724    (use (match_operand:XF 1 "register_operand" ""))
14725    (use (match_operand:XF 2 "register_operand" ""))]
14726   "TARGET_USE_FANCY_MATH_387
14727    && flag_unsafe_math_optimizations"
14729   rtx label = gen_label_rtx ();
14731   emit_label (label);
14733   emit_insn (gen_fpremxf4 (operands[1], operands[2],
14734                            operands[1], operands[2]));
14735   ix86_emit_fp_unordered_jump (label);
14737   emit_move_insn (operands[0], operands[1]);
14738   DONE;
14741 (define_insn "fprem1xf4"
14742   [(set (match_operand:XF 0 "register_operand" "=f")
14743         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
14744                     (match_operand:XF 3 "register_operand" "1")]
14745                    UNSPEC_FPREM1_F))
14746    (set (match_operand:XF 1 "register_operand" "=u")
14747         (unspec:XF [(match_dup 2) (match_dup 3)]
14748                    UNSPEC_FPREM1_U))
14749    (set (reg:CCFP FPSR_REG)
14750         (unspec:CCFP [(const_int 0)] UNSPEC_NOP))]
14751   "TARGET_USE_FANCY_MATH_387
14752    && flag_unsafe_math_optimizations"
14753   "fprem1"
14754   [(set_attr "type" "fpspc")
14755    (set_attr "mode" "XF")])
14757 (define_expand "dremsf3"
14758   [(use (match_operand:SF 0 "register_operand" ""))
14759    (use (match_operand:SF 1 "register_operand" ""))
14760    (use (match_operand:SF 2 "register_operand" ""))]
14761   "TARGET_USE_FANCY_MATH_387
14762    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14763    && flag_unsafe_math_optimizations"
14765   rtx label = gen_label_rtx ();
14767   rtx op1 = gen_reg_rtx (XFmode);
14768   rtx op2 = gen_reg_rtx (XFmode);
14770   emit_insn(gen_extendsfxf2 (op1, operands[1]));
14771   emit_insn(gen_extendsfxf2 (op2, operands[2]));
14773   emit_label (label);
14775   emit_insn (gen_fprem1xf4 (op1, op2, op1, op2));
14776   ix86_emit_fp_unordered_jump (label);
14778   emit_insn (gen_truncxfsf2_i387_noop (operands[0], op1));
14779   DONE;
14782 (define_expand "dremdf3"
14783   [(use (match_operand:DF 0 "register_operand" ""))
14784    (use (match_operand:DF 1 "register_operand" ""))
14785    (use (match_operand:DF 2 "register_operand" ""))]
14786   "TARGET_USE_FANCY_MATH_387
14787    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14788    && flag_unsafe_math_optimizations"
14790   rtx label = gen_label_rtx ();
14792   rtx op1 = gen_reg_rtx (XFmode);
14793   rtx op2 = gen_reg_rtx (XFmode);
14795   emit_insn (gen_extenddfxf2 (op1, operands[1]));
14796   emit_insn (gen_extenddfxf2 (op2, operands[2]));
14798   emit_label (label);
14800   emit_insn (gen_fprem1xf4 (op1, op2, op1, op2));
14801   ix86_emit_fp_unordered_jump (label);
14803   emit_insn (gen_truncxfdf2_i387_noop (operands[0], op1));
14804   DONE;
14807 (define_expand "dremxf3"
14808   [(use (match_operand:XF 0 "register_operand" ""))
14809    (use (match_operand:XF 1 "register_operand" ""))
14810    (use (match_operand:XF 2 "register_operand" ""))]
14811   "TARGET_USE_FANCY_MATH_387
14812    && flag_unsafe_math_optimizations"
14814   rtx label = gen_label_rtx ();
14816   emit_label (label);
14818   emit_insn (gen_fprem1xf4 (operands[1], operands[2],
14819                             operands[1], operands[2]));
14820   ix86_emit_fp_unordered_jump (label);
14822   emit_move_insn (operands[0], operands[1]);
14823   DONE;
14826 (define_insn "*sindf2"
14827   [(set (match_operand:DF 0 "register_operand" "=f")
14828         (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_SIN))]
14829   "TARGET_USE_FANCY_MATH_387
14830    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14831    && flag_unsafe_math_optimizations"
14832   "fsin"
14833   [(set_attr "type" "fpspc")
14834    (set_attr "mode" "DF")])
14836 (define_insn "*sinsf2"
14837   [(set (match_operand:SF 0 "register_operand" "=f")
14838         (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_SIN))]
14839   "TARGET_USE_FANCY_MATH_387
14840    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14841    && flag_unsafe_math_optimizations"
14842   "fsin"
14843   [(set_attr "type" "fpspc")
14844    (set_attr "mode" "SF")])
14846 (define_insn "*sinextendsfdf2"
14847   [(set (match_operand:DF 0 "register_operand" "=f")
14848         (unspec:DF [(float_extend:DF
14849                      (match_operand:SF 1 "register_operand" "0"))]
14850                    UNSPEC_SIN))]
14851   "TARGET_USE_FANCY_MATH_387
14852    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14853    && flag_unsafe_math_optimizations"
14854   "fsin"
14855   [(set_attr "type" "fpspc")
14856    (set_attr "mode" "DF")])
14858 (define_insn "*sinxf2"
14859   [(set (match_operand:XF 0 "register_operand" "=f")
14860         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
14861   "TARGET_USE_FANCY_MATH_387
14862    && flag_unsafe_math_optimizations"
14863   "fsin"
14864   [(set_attr "type" "fpspc")
14865    (set_attr "mode" "XF")])
14867 (define_insn "*cosdf2"
14868   [(set (match_operand:DF 0 "register_operand" "=f")
14869         (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_COS))]
14870   "TARGET_USE_FANCY_MATH_387
14871    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14872    && flag_unsafe_math_optimizations"
14873   "fcos"
14874   [(set_attr "type" "fpspc")
14875    (set_attr "mode" "DF")])
14877 (define_insn "*cossf2"
14878   [(set (match_operand:SF 0 "register_operand" "=f")
14879         (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_COS))]
14880   "TARGET_USE_FANCY_MATH_387
14881    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14882    && flag_unsafe_math_optimizations"
14883   "fcos"
14884   [(set_attr "type" "fpspc")
14885    (set_attr "mode" "SF")])
14887 (define_insn "*cosextendsfdf2"
14888   [(set (match_operand:DF 0 "register_operand" "=f")
14889         (unspec:DF [(float_extend:DF
14890                      (match_operand:SF 1 "register_operand" "0"))]
14891                    UNSPEC_COS))]
14892   "TARGET_USE_FANCY_MATH_387
14893    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14894    && flag_unsafe_math_optimizations"
14895   "fcos"
14896   [(set_attr "type" "fpspc")
14897    (set_attr "mode" "DF")])
14899 (define_insn "*cosxf2"
14900   [(set (match_operand:XF 0 "register_operand" "=f")
14901         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
14902   "TARGET_USE_FANCY_MATH_387
14903    && flag_unsafe_math_optimizations"
14904   "fcos"
14905   [(set_attr "type" "fpspc")
14906    (set_attr "mode" "XF")])
14908 ;; With sincos pattern defined, sin and cos builtin function will be
14909 ;; expanded to sincos pattern with one of its outputs left unused. 
14910 ;; Cse pass  will detected, if two sincos patterns can be combined,
14911 ;; otherwise sincos pattern will be split back to sin or cos pattern,
14912 ;; depending on the unused output.
14914 (define_insn "sincosdf3"
14915   [(set (match_operand:DF 0 "register_operand" "=f")
14916         (unspec:DF [(match_operand:DF 2 "register_operand" "0")]
14917                    UNSPEC_SINCOS_COS))
14918    (set (match_operand:DF 1 "register_operand" "=u")
14919         (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14920   "TARGET_USE_FANCY_MATH_387
14921    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14922    && flag_unsafe_math_optimizations"
14923   "fsincos"
14924   [(set_attr "type" "fpspc")
14925    (set_attr "mode" "DF")])
14927 (define_split
14928   [(set (match_operand:DF 0 "register_operand" "")
14929         (unspec:DF [(match_operand:DF 2 "register_operand" "")]
14930                    UNSPEC_SINCOS_COS))
14931    (set (match_operand:DF 1 "register_operand" "")
14932         (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14933   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
14934    && !reload_completed && !reload_in_progress"
14935   [(set (match_dup 1) (unspec:DF [(match_dup 2)] UNSPEC_SIN))]
14936   "")
14938 (define_split
14939   [(set (match_operand:DF 0 "register_operand" "")
14940         (unspec:DF [(match_operand:DF 2 "register_operand" "")]
14941                    UNSPEC_SINCOS_COS))
14942    (set (match_operand:DF 1 "register_operand" "")
14943         (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14944   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
14945    && !reload_completed && !reload_in_progress"
14946   [(set (match_dup 0) (unspec:DF [(match_dup 2)] UNSPEC_COS))]
14947   "")
14949 (define_insn "sincossf3"
14950   [(set (match_operand:SF 0 "register_operand" "=f")
14951         (unspec:SF [(match_operand:SF 2 "register_operand" "0")]
14952                    UNSPEC_SINCOS_COS))
14953    (set (match_operand:SF 1 "register_operand" "=u")
14954         (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14955   "TARGET_USE_FANCY_MATH_387
14956    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14957    && flag_unsafe_math_optimizations"
14958   "fsincos"
14959   [(set_attr "type" "fpspc")
14960    (set_attr "mode" "SF")])
14962 (define_split
14963   [(set (match_operand:SF 0 "register_operand" "")
14964         (unspec:SF [(match_operand:SF 2 "register_operand" "")]
14965                    UNSPEC_SINCOS_COS))
14966    (set (match_operand:SF 1 "register_operand" "")
14967         (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14968   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
14969    && !reload_completed && !reload_in_progress"
14970   [(set (match_dup 1) (unspec:SF [(match_dup 2)] UNSPEC_SIN))]
14971   "")
14973 (define_split
14974   [(set (match_operand:SF 0 "register_operand" "")
14975         (unspec:SF [(match_operand:SF 2 "register_operand" "")]
14976                    UNSPEC_SINCOS_COS))
14977    (set (match_operand:SF 1 "register_operand" "")
14978         (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14979   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
14980    && !reload_completed && !reload_in_progress"
14981   [(set (match_dup 0) (unspec:SF [(match_dup 2)] UNSPEC_COS))]
14982   "")
14984 (define_insn "*sincosextendsfdf3"
14985   [(set (match_operand:DF 0 "register_operand" "=f")
14986         (unspec:DF [(float_extend:DF
14987                      (match_operand:SF 2 "register_operand" "0"))]
14988                    UNSPEC_SINCOS_COS))
14989    (set (match_operand:DF 1 "register_operand" "=u")
14990         (unspec:DF [(float_extend:DF
14991                      (match_dup 2))] UNSPEC_SINCOS_SIN))]
14992   "TARGET_USE_FANCY_MATH_387
14993    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14994    && flag_unsafe_math_optimizations"
14995   "fsincos"
14996   [(set_attr "type" "fpspc")
14997    (set_attr "mode" "DF")])
14999 (define_split
15000   [(set (match_operand:DF 0 "register_operand" "")
15001         (unspec:DF [(float_extend:DF
15002                      (match_operand:SF 2 "register_operand" ""))]
15003                    UNSPEC_SINCOS_COS))
15004    (set (match_operand:DF 1 "register_operand" "")
15005         (unspec:DF [(float_extend:DF
15006                      (match_dup 2))] UNSPEC_SINCOS_SIN))]
15007   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
15008    && !reload_completed && !reload_in_progress"
15009   [(set (match_dup 1) (unspec:DF [(float_extend:DF
15010                                    (match_dup 2))] UNSPEC_SIN))]
15011   "")
15013 (define_split
15014   [(set (match_operand:DF 0 "register_operand" "")
15015         (unspec:DF [(float_extend:DF
15016                      (match_operand:SF 2 "register_operand" ""))]
15017                    UNSPEC_SINCOS_COS))
15018    (set (match_operand:DF 1 "register_operand" "")
15019         (unspec:DF [(float_extend:DF
15020                      (match_dup 2))] UNSPEC_SINCOS_SIN))]
15021   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
15022    && !reload_completed && !reload_in_progress"
15023   [(set (match_dup 0) (unspec:DF [(float_extend:DF
15024                                    (match_dup 2))] UNSPEC_COS))]
15025   "")
15027 (define_insn "sincosxf3"
15028   [(set (match_operand:XF 0 "register_operand" "=f")
15029         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15030                    UNSPEC_SINCOS_COS))
15031    (set (match_operand:XF 1 "register_operand" "=u")
15032         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15033   "TARGET_USE_FANCY_MATH_387
15034    && flag_unsafe_math_optimizations"
15035   "fsincos"
15036   [(set_attr "type" "fpspc")
15037    (set_attr "mode" "XF")])
15039 (define_split
15040   [(set (match_operand:XF 0 "register_operand" "")
15041         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
15042                    UNSPEC_SINCOS_COS))
15043    (set (match_operand:XF 1 "register_operand" "")
15044         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15045   "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
15046    && !reload_completed && !reload_in_progress"
15047   [(set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_SIN))]
15048   "")
15050 (define_split
15051   [(set (match_operand:XF 0 "register_operand" "")
15052         (unspec:XF [(match_operand:XF 2 "register_operand" "")]
15053                    UNSPEC_SINCOS_COS))
15054    (set (match_operand:XF 1 "register_operand" "")
15055         (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15056   "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
15057    && !reload_completed && !reload_in_progress"
15058   [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))]
15059   "")
15061 (define_insn "*tandf3_1"
15062   [(set (match_operand:DF 0 "register_operand" "=f")
15063         (unspec:DF [(match_operand:DF 2 "register_operand" "0")]
15064                    UNSPEC_TAN_ONE))
15065    (set (match_operand:DF 1 "register_operand" "=u")
15066         (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))]
15067   "TARGET_USE_FANCY_MATH_387
15068    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15069    && flag_unsafe_math_optimizations"
15070   "fptan"
15071   [(set_attr "type" "fpspc")
15072    (set_attr "mode" "DF")])
15074 ;; optimize sequence: fptan
15075 ;;                    fstp    %st(0)
15076 ;;                    fld1
15077 ;; into fptan insn.
15079 (define_peephole2
15080   [(parallel[(set (match_operand:DF 0 "register_operand" "")
15081                   (unspec:DF [(match_operand:DF 2 "register_operand" "")]
15082                              UNSPEC_TAN_ONE))
15083              (set (match_operand:DF 1 "register_operand" "")
15084                   (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))])
15085    (set (match_dup 0)
15086         (match_operand:DF 3 "immediate_operand" ""))]
15087   "standard_80387_constant_p (operands[3]) == 2"
15088   [(parallel[(set (match_dup 0) (unspec:DF [(match_dup 2)] UNSPEC_TAN_ONE))
15089              (set (match_dup 1) (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15090   "")
15092 (define_expand "tandf2"
15093   [(parallel [(set (match_dup 2)
15094                    (unspec:DF [(match_operand:DF 1 "register_operand" "")]
15095                               UNSPEC_TAN_ONE))
15096               (set (match_operand:DF 0 "register_operand" "")
15097                    (unspec:DF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15098   "TARGET_USE_FANCY_MATH_387
15099    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15100    && flag_unsafe_math_optimizations"
15102   operands[2] = gen_reg_rtx (DFmode);
15105 (define_insn "*tansf3_1"
15106   [(set (match_operand:SF 0 "register_operand" "=f")
15107         (unspec:SF [(match_operand:SF 2 "register_operand" "0")]
15108                    UNSPEC_TAN_ONE))
15109    (set (match_operand:SF 1 "register_operand" "=u")
15110         (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))]
15111   "TARGET_USE_FANCY_MATH_387
15112    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15113    && flag_unsafe_math_optimizations"
15114   "fptan"
15115   [(set_attr "type" "fpspc")
15116    (set_attr "mode" "SF")])
15118 ;; optimize sequence: fptan
15119 ;;                    fstp    %st(0)
15120 ;;                    fld1
15121 ;; into fptan insn.
15123 (define_peephole2
15124   [(parallel[(set (match_operand:SF 0 "register_operand" "")
15125                   (unspec:SF [(match_operand:SF 2 "register_operand" "")]
15126                              UNSPEC_TAN_ONE))
15127              (set (match_operand:SF 1 "register_operand" "")
15128                   (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))])
15129    (set (match_dup 0)
15130         (match_operand:SF 3 "immediate_operand" ""))]
15131   "standard_80387_constant_p (operands[3]) == 2"
15132   [(parallel[(set (match_dup 0) (unspec:SF [(match_dup 2)] UNSPEC_TAN_ONE))
15133              (set (match_dup 1) (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15134   "")
15136 (define_expand "tansf2"
15137   [(parallel [(set (match_dup 2)
15138                    (unspec:SF [(match_operand:SF 1 "register_operand" "")]
15139                               UNSPEC_TAN_ONE))
15140               (set (match_operand:SF 0 "register_operand" "")
15141                    (unspec:SF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15142   "TARGET_USE_FANCY_MATH_387
15143    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15144    && flag_unsafe_math_optimizations"
15146   operands[2] = gen_reg_rtx (SFmode);
15149 (define_insn "*tanxf3_1"
15150   [(set (match_operand:XF 0 "register_operand" "=f")
15151         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15152                    UNSPEC_TAN_ONE))
15153    (set (match_operand:XF 1 "register_operand" "=u")
15154         (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))]
15155   "TARGET_USE_FANCY_MATH_387
15156    && flag_unsafe_math_optimizations"
15157   "fptan"
15158   [(set_attr "type" "fpspc")
15159    (set_attr "mode" "XF")])
15161 ;; optimize sequence: fptan
15162 ;;                    fstp    %st(0)
15163 ;;                    fld1
15164 ;; into fptan insn.
15166 (define_peephole2
15167   [(parallel[(set (match_operand:XF 0 "register_operand" "")
15168                   (unspec:XF [(match_operand:XF 2 "register_operand" "")]
15169                              UNSPEC_TAN_ONE))
15170              (set (match_operand:XF 1 "register_operand" "")
15171                   (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))])
15172    (set (match_dup 0)
15173         (match_operand:XF 3 "immediate_operand" ""))]
15174   "standard_80387_constant_p (operands[3]) == 2"
15175   [(parallel[(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_TAN_ONE))
15176              (set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15177   "")
15179 (define_expand "tanxf2"
15180   [(parallel [(set (match_dup 2)
15181                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15182                               UNSPEC_TAN_ONE))
15183               (set (match_operand:XF 0 "register_operand" "")
15184                    (unspec:XF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15185   "TARGET_USE_FANCY_MATH_387
15186    && flag_unsafe_math_optimizations"
15188   operands[2] = gen_reg_rtx (XFmode);
15191 (define_insn "atan2df3_1"
15192   [(set (match_operand:DF 0 "register_operand" "=f")
15193         (unspec:DF [(match_operand:DF 2 "register_operand" "0")
15194                     (match_operand:DF 1 "register_operand" "u")]
15195                    UNSPEC_FPATAN))
15196    (clobber (match_scratch:DF 3 "=1"))]
15197   "TARGET_USE_FANCY_MATH_387
15198    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15199    && flag_unsafe_math_optimizations"
15200   "fpatan"
15201   [(set_attr "type" "fpspc")
15202    (set_attr "mode" "DF")])
15204 (define_expand "atan2df3"
15205   [(use (match_operand:DF 0 "register_operand" ""))
15206    (use (match_operand:DF 2 "register_operand" ""))
15207    (use (match_operand:DF 1 "register_operand" ""))]
15208   "TARGET_USE_FANCY_MATH_387
15209    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15210    && flag_unsafe_math_optimizations"
15212   rtx copy = gen_reg_rtx (DFmode);
15213   emit_move_insn (copy, operands[1]);
15214   emit_insn (gen_atan2df3_1 (operands[0], copy, operands[2]));
15215   DONE;
15218 (define_expand "atandf2"
15219   [(parallel [(set (match_operand:DF 0 "register_operand" "")
15220                    (unspec:DF [(match_dup 2)
15221                                (match_operand:DF 1 "register_operand" "")]
15222                     UNSPEC_FPATAN))
15223               (clobber (match_scratch:DF 3 ""))])]
15224   "TARGET_USE_FANCY_MATH_387
15225    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15226    && flag_unsafe_math_optimizations"
15228   operands[2] = gen_reg_rtx (DFmode);
15229   emit_move_insn (operands[2], CONST1_RTX (DFmode));  /* fld1 */
15232 (define_insn "atan2sf3_1"
15233   [(set (match_operand:SF 0 "register_operand" "=f")
15234         (unspec:SF [(match_operand:SF 2 "register_operand" "0")
15235                     (match_operand:SF 1 "register_operand" "u")]
15236                    UNSPEC_FPATAN))
15237    (clobber (match_scratch:SF 3 "=1"))]
15238   "TARGET_USE_FANCY_MATH_387
15239    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15240    && flag_unsafe_math_optimizations"
15241   "fpatan"
15242   [(set_attr "type" "fpspc")
15243    (set_attr "mode" "SF")])
15245 (define_expand "atan2sf3"
15246   [(use (match_operand:SF 0 "register_operand" ""))
15247    (use (match_operand:SF 2 "register_operand" ""))
15248    (use (match_operand:SF 1 "register_operand" ""))]
15249   "TARGET_USE_FANCY_MATH_387
15250    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15251    && flag_unsafe_math_optimizations"
15253   rtx copy = gen_reg_rtx (SFmode);
15254   emit_move_insn (copy, operands[1]);
15255   emit_insn (gen_atan2sf3_1 (operands[0], copy, operands[2]));
15256   DONE;
15259 (define_expand "atansf2"
15260   [(parallel [(set (match_operand:SF 0 "register_operand" "")
15261                    (unspec:SF [(match_dup 2)
15262                                (match_operand:SF 1 "register_operand" "")]
15263                     UNSPEC_FPATAN))
15264               (clobber (match_scratch:SF 3 ""))])]
15265   "TARGET_USE_FANCY_MATH_387
15266    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15267    && flag_unsafe_math_optimizations"
15269   operands[2] = gen_reg_rtx (SFmode);
15270   emit_move_insn (operands[2], CONST1_RTX (SFmode));  /* fld1 */
15273 (define_insn "atan2xf3_1"
15274   [(set (match_operand:XF 0 "register_operand" "=f")
15275         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15276                     (match_operand:XF 1 "register_operand" "u")]
15277                    UNSPEC_FPATAN))
15278    (clobber (match_scratch:XF 3 "=1"))]
15279   "TARGET_USE_FANCY_MATH_387
15280    && flag_unsafe_math_optimizations"
15281   "fpatan"
15282   [(set_attr "type" "fpspc")
15283    (set_attr "mode" "XF")])
15285 (define_expand "atan2xf3"
15286   [(use (match_operand:XF 0 "register_operand" ""))
15287    (use (match_operand:XF 2 "register_operand" ""))
15288    (use (match_operand:XF 1 "register_operand" ""))]
15289   "TARGET_USE_FANCY_MATH_387
15290    && flag_unsafe_math_optimizations"
15292   rtx copy = gen_reg_rtx (XFmode);
15293   emit_move_insn (copy, operands[1]);
15294   emit_insn (gen_atan2xf3_1 (operands[0], copy, operands[2]));
15295   DONE;
15298 (define_expand "atanxf2"
15299   [(parallel [(set (match_operand:XF 0 "register_operand" "")
15300                    (unspec:XF [(match_dup 2)
15301                                (match_operand:XF 1 "register_operand" "")]
15302                     UNSPEC_FPATAN))
15303               (clobber (match_scratch:XF 3 ""))])]
15304   "TARGET_USE_FANCY_MATH_387
15305    && flag_unsafe_math_optimizations"
15307   operands[2] = gen_reg_rtx (XFmode);
15308   emit_move_insn (operands[2], CONST1_RTX (XFmode));  /* fld1 */
15311 (define_expand "asindf2"
15312   [(set (match_dup 2)
15313         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15314    (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15315    (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15316    (set (match_dup 6) (sqrt:XF (match_dup 5)))
15317    (parallel [(set (match_dup 7)
15318                    (unspec:XF [(match_dup 6) (match_dup 2)]
15319                               UNSPEC_FPATAN))
15320               (clobber (match_scratch:XF 8 ""))])
15321    (set (match_operand:DF 0 "register_operand" "")
15322         (float_truncate:DF (match_dup 7)))]
15323   "TARGET_USE_FANCY_MATH_387
15324    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15325    && flag_unsafe_math_optimizations"
15327   int i;
15329   for (i=2; i<8; i++)
15330     operands[i] = gen_reg_rtx (XFmode);
15332   emit_move_insn (operands[4], CONST1_RTX (XFmode));  /* fld1 */
15335 (define_expand "asinsf2"
15336   [(set (match_dup 2)
15337         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15338    (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15339    (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15340    (set (match_dup 6) (sqrt:XF (match_dup 5)))
15341    (parallel [(set (match_dup 7)
15342                    (unspec:XF [(match_dup 6) (match_dup 2)]
15343                               UNSPEC_FPATAN))
15344               (clobber (match_scratch:XF 8 ""))])
15345    (set (match_operand:SF 0 "register_operand" "")
15346         (float_truncate:SF (match_dup 7)))]
15347   "TARGET_USE_FANCY_MATH_387
15348    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15349    && flag_unsafe_math_optimizations"
15351   int i;
15353   for (i=2; i<8; i++)
15354     operands[i] = gen_reg_rtx (XFmode);
15356   emit_move_insn (operands[4], CONST1_RTX (XFmode));  /* fld1 */
15359 (define_expand "asinxf2"
15360   [(set (match_dup 2)
15361         (mult:XF (match_operand:XF 1 "register_operand" "")
15362                  (match_dup 1)))
15363    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
15364    (set (match_dup 5) (sqrt:XF (match_dup 4)))
15365    (parallel [(set (match_operand:XF 0 "register_operand" "")
15366                    (unspec:XF [(match_dup 5) (match_dup 1)]
15367                               UNSPEC_FPATAN))
15368               (clobber (match_scratch:XF 6 ""))])]
15369   "TARGET_USE_FANCY_MATH_387
15370    && flag_unsafe_math_optimizations"
15372   int i;
15374   for (i=2; i<6; i++)
15375     operands[i] = gen_reg_rtx (XFmode);
15377   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
15380 (define_expand "acosdf2"
15381   [(set (match_dup 2)
15382         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15383    (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15384    (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15385    (set (match_dup 6) (sqrt:XF (match_dup 5)))
15386    (parallel [(set (match_dup 7)
15387                    (unspec:XF [(match_dup 2) (match_dup 6)]
15388                               UNSPEC_FPATAN))
15389               (clobber (match_scratch:XF 8 ""))])
15390    (set (match_operand:DF 0 "register_operand" "")
15391         (float_truncate:DF (match_dup 7)))]
15392   "TARGET_USE_FANCY_MATH_387
15393    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15394    && flag_unsafe_math_optimizations"
15396   int i;
15398   for (i=2; i<8; i++)
15399     operands[i] = gen_reg_rtx (XFmode);
15401   emit_move_insn (operands[4], CONST1_RTX (XFmode));  /* fld1 */
15404 (define_expand "acossf2"
15405   [(set (match_dup 2)
15406         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15407    (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15408    (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15409    (set (match_dup 6) (sqrt:XF (match_dup 5)))
15410    (parallel [(set (match_dup 7)
15411                    (unspec:XF [(match_dup 2) (match_dup 6)]
15412                               UNSPEC_FPATAN))
15413               (clobber (match_scratch:XF 8 ""))])
15414    (set (match_operand:SF 0 "register_operand" "")
15415         (float_truncate:SF (match_dup 7)))]
15416   "TARGET_USE_FANCY_MATH_387
15417    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15418    && flag_unsafe_math_optimizations"
15420   int i;
15422   for (i=2; i<8; i++)
15423     operands[i] = gen_reg_rtx (XFmode);
15425   emit_move_insn (operands[4], CONST1_RTX (XFmode));  /* fld1 */
15428 (define_expand "acosxf2"
15429   [(set (match_dup 2)
15430         (mult:XF (match_operand:XF 1 "register_operand" "")
15431                  (match_dup 1)))
15432    (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
15433    (set (match_dup 5) (sqrt:XF (match_dup 4)))
15434    (parallel [(set (match_operand:XF 0 "register_operand" "")
15435                    (unspec:XF [(match_dup 1) (match_dup 5)]
15436                               UNSPEC_FPATAN))
15437               (clobber (match_scratch:XF 6 ""))])]
15438   "TARGET_USE_FANCY_MATH_387
15439    && flag_unsafe_math_optimizations"
15441   int i;
15443   for (i=2; i<6; i++)
15444     operands[i] = gen_reg_rtx (XFmode);
15446   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
15449 (define_insn "fyl2x_xf3"
15450   [(set (match_operand:XF 0 "register_operand" "=f")
15451         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15452                     (match_operand:XF 1 "register_operand" "u")]
15453                    UNSPEC_FYL2X))
15454    (clobber (match_scratch:XF 3 "=1"))]
15455   "TARGET_USE_FANCY_MATH_387
15456    && flag_unsafe_math_optimizations"
15457   "fyl2x"
15458   [(set_attr "type" "fpspc")
15459    (set_attr "mode" "XF")])
15461 (define_expand "logsf2"
15462   [(set (match_dup 2)
15463         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15464    (parallel [(set (match_dup 4)
15465                    (unspec:XF [(match_dup 2)
15466                                (match_dup 3)] UNSPEC_FYL2X))
15467               (clobber (match_scratch:XF 5 ""))])
15468    (set (match_operand:SF 0 "register_operand" "")
15469         (float_truncate:SF (match_dup 4)))]
15470   "TARGET_USE_FANCY_MATH_387
15471    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15472    && flag_unsafe_math_optimizations"
15474   rtx temp;
15476   operands[2] = gen_reg_rtx (XFmode);
15477   operands[3] = gen_reg_rtx (XFmode);
15478   operands[4] = gen_reg_rtx (XFmode);
15480   temp = standard_80387_constant_rtx (4); /* fldln2 */
15481   emit_move_insn (operands[3], temp);
15484 (define_expand "logdf2"
15485   [(set (match_dup 2)
15486         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15487    (parallel [(set (match_dup 4)
15488                    (unspec:XF [(match_dup 2)
15489                                (match_dup 3)] UNSPEC_FYL2X))
15490               (clobber (match_scratch:XF 5 ""))])
15491    (set (match_operand:DF 0 "register_operand" "")
15492         (float_truncate:DF (match_dup 4)))]
15493   "TARGET_USE_FANCY_MATH_387
15494    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15495    && flag_unsafe_math_optimizations"
15497   rtx temp;
15499   operands[2] = gen_reg_rtx (XFmode);
15500   operands[3] = gen_reg_rtx (XFmode);
15501   operands[4] = gen_reg_rtx (XFmode);
15503   temp = standard_80387_constant_rtx (4); /* fldln2 */
15504   emit_move_insn (operands[3], temp);
15507 (define_expand "logxf2"
15508   [(parallel [(set (match_operand:XF 0 "register_operand" "")
15509                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
15510                                (match_dup 2)] UNSPEC_FYL2X))
15511               (clobber (match_scratch:XF 3 ""))])]
15512   "TARGET_USE_FANCY_MATH_387
15513    && flag_unsafe_math_optimizations"
15515   rtx temp;
15517   operands[2] = gen_reg_rtx (XFmode);
15518   temp = standard_80387_constant_rtx (4); /* fldln2 */
15519   emit_move_insn (operands[2], temp);
15522 (define_expand "log10sf2"
15523   [(set (match_dup 2)
15524         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15525    (parallel [(set (match_dup 4)
15526                    (unspec:XF [(match_dup 2)
15527                                (match_dup 3)] UNSPEC_FYL2X))
15528               (clobber (match_scratch:XF 5 ""))])
15529    (set (match_operand:SF 0 "register_operand" "")
15530         (float_truncate:SF (match_dup 4)))]
15531   "TARGET_USE_FANCY_MATH_387
15532    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15533    && flag_unsafe_math_optimizations"
15535   rtx temp;
15537   operands[2] = gen_reg_rtx (XFmode);
15538   operands[3] = gen_reg_rtx (XFmode);
15539   operands[4] = gen_reg_rtx (XFmode);
15541   temp = standard_80387_constant_rtx (3); /* fldlg2 */
15542   emit_move_insn (operands[3], temp);
15545 (define_expand "log10df2"
15546   [(set (match_dup 2)
15547         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15548    (parallel [(set (match_dup 4)
15549                    (unspec:XF [(match_dup 2)
15550                                (match_dup 3)] UNSPEC_FYL2X))
15551               (clobber (match_scratch:XF 5 ""))])
15552    (set (match_operand:DF 0 "register_operand" "")
15553         (float_truncate:DF (match_dup 4)))]
15554   "TARGET_USE_FANCY_MATH_387
15555    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15556    && flag_unsafe_math_optimizations"
15558   rtx temp;
15560   operands[2] = gen_reg_rtx (XFmode);
15561   operands[3] = gen_reg_rtx (XFmode);
15562   operands[4] = gen_reg_rtx (XFmode);
15564   temp = standard_80387_constant_rtx (3); /* fldlg2 */
15565   emit_move_insn (operands[3], temp);
15568 (define_expand "log10xf2"
15569   [(parallel [(set (match_operand:XF 0 "register_operand" "")
15570                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
15571                                (match_dup 2)] UNSPEC_FYL2X))
15572               (clobber (match_scratch:XF 3 ""))])]
15573   "TARGET_USE_FANCY_MATH_387
15574    && flag_unsafe_math_optimizations"
15576   rtx temp;
15578   operands[2] = gen_reg_rtx (XFmode);
15579   temp = standard_80387_constant_rtx (3); /* fldlg2 */
15580   emit_move_insn (operands[2], temp);
15583 (define_expand "log2sf2"
15584   [(set (match_dup 2)
15585         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15586    (parallel [(set (match_dup 4)
15587                    (unspec:XF [(match_dup 2)
15588                                (match_dup 3)] UNSPEC_FYL2X))
15589               (clobber (match_scratch:XF 5 ""))])
15590    (set (match_operand:SF 0 "register_operand" "")
15591         (float_truncate:SF (match_dup 4)))]
15592   "TARGET_USE_FANCY_MATH_387
15593    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15594    && flag_unsafe_math_optimizations"
15596   operands[2] = gen_reg_rtx (XFmode);
15597   operands[3] = gen_reg_rtx (XFmode);
15598   operands[4] = gen_reg_rtx (XFmode);
15600   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
15603 (define_expand "log2df2"
15604   [(set (match_dup 2)
15605         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15606    (parallel [(set (match_dup 4)
15607                    (unspec:XF [(match_dup 2)
15608                                (match_dup 3)] UNSPEC_FYL2X))
15609               (clobber (match_scratch:XF 5 ""))])
15610    (set (match_operand:DF 0 "register_operand" "")
15611         (float_truncate:DF (match_dup 4)))]
15612   "TARGET_USE_FANCY_MATH_387
15613    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15614    && flag_unsafe_math_optimizations"
15616   operands[2] = gen_reg_rtx (XFmode);
15617   operands[3] = gen_reg_rtx (XFmode);
15618   operands[4] = gen_reg_rtx (XFmode);
15620   emit_move_insn (operands[3], CONST1_RTX (XFmode));  /* fld1 */
15623 (define_expand "log2xf2"
15624   [(parallel [(set (match_operand:XF 0 "register_operand" "")
15625                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
15626                                (match_dup 2)] UNSPEC_FYL2X))
15627               (clobber (match_scratch:XF 3 ""))])]
15628   "TARGET_USE_FANCY_MATH_387
15629    && flag_unsafe_math_optimizations"
15631   operands[2] = gen_reg_rtx (XFmode);
15632   emit_move_insn (operands[2], CONST1_RTX (XFmode));  /* fld1 */
15635 (define_insn "fyl2xp1_xf3"
15636   [(set (match_operand:XF 0 "register_operand" "=f")
15637         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15638                     (match_operand:XF 1 "register_operand" "u")]
15639                    UNSPEC_FYL2XP1))
15640    (clobber (match_scratch:XF 3 "=1"))]
15641   "TARGET_USE_FANCY_MATH_387
15642    && flag_unsafe_math_optimizations"
15643   "fyl2xp1"
15644   [(set_attr "type" "fpspc")
15645    (set_attr "mode" "XF")])
15647 (define_expand "log1psf2"
15648   [(use (match_operand:SF 0 "register_operand" ""))
15649    (use (match_operand:SF 1 "register_operand" ""))]
15650   "TARGET_USE_FANCY_MATH_387
15651    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15652    && flag_unsafe_math_optimizations"
15654   rtx op0 = gen_reg_rtx (XFmode);
15655   rtx op1 = gen_reg_rtx (XFmode);
15657   emit_insn (gen_extendsfxf2 (op1, operands[1]));
15658   ix86_emit_i387_log1p (op0, op1);
15659   emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
15660   DONE;
15663 (define_expand "log1pdf2"
15664   [(use (match_operand:DF 0 "register_operand" ""))
15665    (use (match_operand:DF 1 "register_operand" ""))]
15666   "TARGET_USE_FANCY_MATH_387
15667    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15668    && flag_unsafe_math_optimizations"
15670   rtx op0 = gen_reg_rtx (XFmode);
15671   rtx op1 = gen_reg_rtx (XFmode);
15673   emit_insn (gen_extenddfxf2 (op1, operands[1]));
15674   ix86_emit_i387_log1p (op0, op1);
15675   emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
15676   DONE;
15679 (define_expand "log1pxf2"
15680   [(use (match_operand:XF 0 "register_operand" ""))
15681    (use (match_operand:XF 1 "register_operand" ""))]
15682   "TARGET_USE_FANCY_MATH_387
15683    && flag_unsafe_math_optimizations"
15685   ix86_emit_i387_log1p (operands[0], operands[1]);
15686   DONE;
15689 (define_insn "*fxtractxf3"
15690   [(set (match_operand:XF 0 "register_operand" "=f")
15691         (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15692                    UNSPEC_XTRACT_FRACT))
15693    (set (match_operand:XF 1 "register_operand" "=u")
15694         (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]
15695   "TARGET_USE_FANCY_MATH_387
15696    && flag_unsafe_math_optimizations"
15697   "fxtract"
15698   [(set_attr "type" "fpspc")
15699    (set_attr "mode" "XF")])
15701 (define_expand "logbsf2"
15702   [(set (match_dup 2)
15703         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15704    (parallel [(set (match_dup 3)
15705                    (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_FRACT))
15706               (set (match_dup 4)
15707                    (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))])
15708    (set (match_operand:SF 0 "register_operand" "")
15709         (float_truncate:SF (match_dup 4)))]
15710   "TARGET_USE_FANCY_MATH_387
15711    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15712    && flag_unsafe_math_optimizations"
15714   operands[2] = gen_reg_rtx (XFmode);
15715   operands[3] = gen_reg_rtx (XFmode);
15716   operands[4] = gen_reg_rtx (XFmode);
15719 (define_expand "logbdf2"
15720   [(set (match_dup 2)
15721         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15722    (parallel [(set (match_dup 3)
15723                    (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_FRACT))
15724               (set (match_dup 4)
15725                    (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))])
15726    (set (match_operand:DF 0 "register_operand" "")
15727         (float_truncate:DF (match_dup 4)))]
15728   "TARGET_USE_FANCY_MATH_387
15729    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15730    && flag_unsafe_math_optimizations"
15732   operands[2] = gen_reg_rtx (XFmode);
15733   operands[3] = gen_reg_rtx (XFmode);
15734   operands[4] = gen_reg_rtx (XFmode);
15737 (define_expand "logbxf2"
15738   [(parallel [(set (match_dup 2)
15739                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15740                               UNSPEC_XTRACT_FRACT))
15741               (set (match_operand:XF 0 "register_operand" "")
15742                    (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
15743   "TARGET_USE_FANCY_MATH_387
15744    && flag_unsafe_math_optimizations"
15746   operands[2] = gen_reg_rtx (XFmode);
15749 (define_expand "ilogbsi2"
15750   [(parallel [(set (match_dup 2)
15751                    (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15752                               UNSPEC_XTRACT_FRACT))
15753               (set (match_operand:XF 3 "register_operand" "")
15754                    (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])
15755    (parallel [(set (match_operand:SI 0 "register_operand" "")
15756                    (fix:SI (match_dup 3)))
15757               (clobber (reg:CC FLAGS_REG))])]
15758   "TARGET_USE_FANCY_MATH_387
15759    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15760    && flag_unsafe_math_optimizations"
15762   operands[2] = gen_reg_rtx (XFmode);
15763   operands[3] = gen_reg_rtx (XFmode);
15766 (define_insn "*f2xm1xf2"
15767   [(set (match_operand:XF 0 "register_operand" "=f")
15768         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15769          UNSPEC_F2XM1))]
15770   "TARGET_USE_FANCY_MATH_387
15771    && flag_unsafe_math_optimizations"
15772   "f2xm1"
15773   [(set_attr "type" "fpspc")
15774    (set_attr "mode" "XF")])
15776 (define_insn "*fscalexf4"
15777   [(set (match_operand:XF 0 "register_operand" "=f")
15778         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15779                     (match_operand:XF 3 "register_operand" "1")]
15780                    UNSPEC_FSCALE_FRACT))
15781    (set (match_operand:XF 1 "register_operand" "=u")
15782         (unspec:XF [(match_dup 2) (match_dup 3)]
15783                    UNSPEC_FSCALE_EXP))]
15784   "TARGET_USE_FANCY_MATH_387
15785    && flag_unsafe_math_optimizations"
15786   "fscale"
15787   [(set_attr "type" "fpspc")
15788    (set_attr "mode" "XF")])
15790 (define_expand "expsf2"
15791   [(set (match_dup 2)
15792         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15793    (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15794    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15795    (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15796    (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15797    (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
15798    (parallel [(set (match_dup 10)
15799                    (unspec:XF [(match_dup 9) (match_dup 5)]
15800                               UNSPEC_FSCALE_FRACT))
15801               (set (match_dup 11)
15802                    (unspec:XF [(match_dup 9) (match_dup 5)]
15803                               UNSPEC_FSCALE_EXP))])
15804    (set (match_operand:SF 0 "register_operand" "")
15805         (float_truncate:SF (match_dup 10)))]
15806   "TARGET_USE_FANCY_MATH_387
15807    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15808    && flag_unsafe_math_optimizations"
15810   rtx temp;
15811   int i;
15813   for (i=2; i<12; i++)
15814     operands[i] = gen_reg_rtx (XFmode);
15815   temp = standard_80387_constant_rtx (5); /* fldl2e */
15816   emit_move_insn (operands[3], temp);
15817   emit_move_insn (operands[8], CONST1_RTX (XFmode));  /* fld1 */
15820 (define_expand "expdf2"
15821   [(set (match_dup 2)
15822         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15823    (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15824    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15825    (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15826    (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15827    (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
15828    (parallel [(set (match_dup 10)
15829                    (unspec:XF [(match_dup 9) (match_dup 5)]
15830                               UNSPEC_FSCALE_FRACT))
15831               (set (match_dup 11)
15832                    (unspec:XF [(match_dup 9) (match_dup 5)]
15833                               UNSPEC_FSCALE_EXP))])
15834    (set (match_operand:DF 0 "register_operand" "")
15835         (float_truncate:DF (match_dup 10)))]
15836   "TARGET_USE_FANCY_MATH_387
15837    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15838    && flag_unsafe_math_optimizations"
15840   rtx temp;
15841   int i;
15843   for (i=2; i<12; i++)
15844     operands[i] = gen_reg_rtx (XFmode);
15845   temp = standard_80387_constant_rtx (5); /* fldl2e */
15846   emit_move_insn (operands[3], temp);
15847   emit_move_insn (operands[8], CONST1_RTX (XFmode));  /* fld1 */
15850 (define_expand "expxf2"
15851   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
15852                                (match_dup 2)))
15853    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
15854    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
15855    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
15856    (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
15857    (parallel [(set (match_operand:XF 0 "register_operand" "")
15858                    (unspec:XF [(match_dup 8) (match_dup 4)]
15859                               UNSPEC_FSCALE_FRACT))
15860               (set (match_dup 9)
15861                    (unspec:XF [(match_dup 8) (match_dup 4)]
15862                               UNSPEC_FSCALE_EXP))])]
15863   "TARGET_USE_FANCY_MATH_387
15864    && flag_unsafe_math_optimizations"
15866   rtx temp;
15867   int i;
15869   for (i=2; i<10; i++)
15870     operands[i] = gen_reg_rtx (XFmode);
15871   temp = standard_80387_constant_rtx (5); /* fldl2e */
15872   emit_move_insn (operands[2], temp);
15873   emit_move_insn (operands[7], CONST1_RTX (XFmode));  /* fld1 */
15876 (define_expand "exp10sf2"
15877   [(set (match_dup 2)
15878         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15879    (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15880    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15881    (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15882    (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15883    (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
15884    (parallel [(set (match_dup 10)
15885                    (unspec:XF [(match_dup 9) (match_dup 5)]
15886                               UNSPEC_FSCALE_FRACT))
15887               (set (match_dup 11)
15888                    (unspec:XF [(match_dup 9) (match_dup 5)]
15889                               UNSPEC_FSCALE_EXP))])
15890    (set (match_operand:SF 0 "register_operand" "")
15891         (float_truncate:SF (match_dup 10)))]
15892   "TARGET_USE_FANCY_MATH_387
15893    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15894    && flag_unsafe_math_optimizations"
15896   rtx temp;
15897   int i;
15899   for (i=2; i<12; i++)
15900     operands[i] = gen_reg_rtx (XFmode);
15901   temp = standard_80387_constant_rtx (6); /* fldl2t */
15902   emit_move_insn (operands[3], temp);
15903   emit_move_insn (operands[8], CONST1_RTX (XFmode));  /* fld1 */
15906 (define_expand "exp10df2"
15907   [(set (match_dup 2)
15908         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15909    (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15910    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15911    (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15912    (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15913    (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
15914    (parallel [(set (match_dup 10)
15915                    (unspec:XF [(match_dup 9) (match_dup 5)]
15916                               UNSPEC_FSCALE_FRACT))
15917               (set (match_dup 11)
15918                    (unspec:XF [(match_dup 9) (match_dup 5)]
15919                               UNSPEC_FSCALE_EXP))])
15920    (set (match_operand:DF 0 "register_operand" "")
15921         (float_truncate:DF (match_dup 10)))]
15922   "TARGET_USE_FANCY_MATH_387
15923    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15924    && flag_unsafe_math_optimizations"
15926   rtx temp;
15927   int i;
15929   for (i=2; i<12; i++)
15930     operands[i] = gen_reg_rtx (XFmode);
15931   temp = standard_80387_constant_rtx (6); /* fldl2t */
15932   emit_move_insn (operands[3], temp);
15933   emit_move_insn (operands[8], CONST1_RTX (XFmode));  /* fld1 */
15936 (define_expand "exp10xf2"
15937   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
15938                                (match_dup 2)))
15939    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
15940    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
15941    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
15942    (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
15943    (parallel [(set (match_operand:XF 0 "register_operand" "")
15944                    (unspec:XF [(match_dup 8) (match_dup 4)]
15945                               UNSPEC_FSCALE_FRACT))
15946               (set (match_dup 9)
15947                    (unspec:XF [(match_dup 8) (match_dup 4)]
15948                               UNSPEC_FSCALE_EXP))])]
15949   "TARGET_USE_FANCY_MATH_387
15950    && flag_unsafe_math_optimizations"
15952   rtx temp;
15953   int i;
15955   for (i=2; i<10; i++)
15956     operands[i] = gen_reg_rtx (XFmode);
15957   temp = standard_80387_constant_rtx (6); /* fldl2t */
15958   emit_move_insn (operands[2], temp);
15959   emit_move_insn (operands[7], CONST1_RTX (XFmode));  /* fld1 */
15962 (define_expand "exp2sf2"
15963   [(set (match_dup 2)
15964         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15965    (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
15966    (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
15967    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
15968    (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
15969    (parallel [(set (match_dup 8)
15970                    (unspec:XF [(match_dup 7) (match_dup 3)]
15971                               UNSPEC_FSCALE_FRACT))
15972               (set (match_dup 9)
15973                    (unspec:XF [(match_dup 7) (match_dup 3)]
15974                               UNSPEC_FSCALE_EXP))])
15975    (set (match_operand:SF 0 "register_operand" "")
15976         (float_truncate:SF (match_dup 8)))]
15977   "TARGET_USE_FANCY_MATH_387
15978    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15979    && flag_unsafe_math_optimizations"
15981   int i;
15983   for (i=2; i<10; i++)
15984     operands[i] = gen_reg_rtx (XFmode);
15985   emit_move_insn (operands[6], CONST1_RTX (XFmode));  /* fld1 */
15988 (define_expand "exp2df2"
15989   [(set (match_dup 2)
15990         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15991    (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
15992    (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
15993    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
15994    (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
15995    (parallel [(set (match_dup 8)
15996                    (unspec:XF [(match_dup 7) (match_dup 3)]
15997                               UNSPEC_FSCALE_FRACT))
15998               (set (match_dup 9)
15999                    (unspec:XF [(match_dup 7) (match_dup 3)]
16000                               UNSPEC_FSCALE_EXP))])
16001    (set (match_operand:DF 0 "register_operand" "")
16002         (float_truncate:DF (match_dup 8)))]
16003   "TARGET_USE_FANCY_MATH_387
16004    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16005    && flag_unsafe_math_optimizations"
16007   int i;
16009   for (i=2; i<10; i++)
16010     operands[i] = gen_reg_rtx (XFmode);
16011   emit_move_insn (operands[6], CONST1_RTX (XFmode));  /* fld1 */
16014 (define_expand "exp2xf2"
16015   [(set (match_dup 2) (match_operand:XF 1 "register_operand" ""))
16016    (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
16017    (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
16018    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
16019    (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
16020    (parallel [(set (match_operand:XF 0 "register_operand" "")
16021                    (unspec:XF [(match_dup 7) (match_dup 3)]
16022                               UNSPEC_FSCALE_FRACT))
16023               (set (match_dup 8)
16024                    (unspec:XF [(match_dup 7) (match_dup 3)]
16025                               UNSPEC_FSCALE_EXP))])]
16026   "TARGET_USE_FANCY_MATH_387
16027    && flag_unsafe_math_optimizations"
16029   int i;
16031   for (i=2; i<9; i++)
16032     operands[i] = gen_reg_rtx (XFmode);
16033   emit_move_insn (operands[6], CONST1_RTX (XFmode));  /* fld1 */
16036 (define_expand "expm1df2"
16037   [(set (match_dup 2)
16038         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16039    (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16040    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16041    (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16042    (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16043    (parallel [(set (match_dup 8)
16044                    (unspec:XF [(match_dup 7) (match_dup 5)]
16045                               UNSPEC_FSCALE_FRACT))
16046                    (set (match_dup 9)
16047                    (unspec:XF [(match_dup 7) (match_dup 5)]
16048                               UNSPEC_FSCALE_EXP))])
16049    (parallel [(set (match_dup 11)
16050                    (unspec:XF [(match_dup 10) (match_dup 9)]
16051                               UNSPEC_FSCALE_FRACT))
16052               (set (match_dup 12)
16053                    (unspec:XF [(match_dup 10) (match_dup 9)]
16054                               UNSPEC_FSCALE_EXP))])
16055    (set (match_dup 13) (minus:XF (match_dup 11) (match_dup 10)))
16056    (set (match_dup 14) (plus:XF (match_dup 13) (match_dup 8)))
16057    (set (match_operand:DF 0 "register_operand" "")
16058         (float_truncate:DF (match_dup 14)))]
16059   "TARGET_USE_FANCY_MATH_387
16060    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16061    && flag_unsafe_math_optimizations"
16063   rtx temp;
16064   int i;
16066   for (i=2; i<15; i++)
16067     operands[i] = gen_reg_rtx (XFmode);
16068   temp = standard_80387_constant_rtx (5); /* fldl2e */
16069   emit_move_insn (operands[3], temp);
16070   emit_move_insn (operands[10], CONST1_RTX (XFmode));  /* fld1 */
16073 (define_expand "expm1sf2"
16074   [(set (match_dup 2)
16075         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16076    (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16077    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16078    (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16079    (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16080    (parallel [(set (match_dup 8)
16081                    (unspec:XF [(match_dup 7) (match_dup 5)]
16082                               UNSPEC_FSCALE_FRACT))
16083                    (set (match_dup 9)
16084                    (unspec:XF [(match_dup 7) (match_dup 5)]
16085                               UNSPEC_FSCALE_EXP))])
16086    (parallel [(set (match_dup 11)
16087                    (unspec:XF [(match_dup 10) (match_dup 9)]
16088                               UNSPEC_FSCALE_FRACT))
16089               (set (match_dup 12)
16090                    (unspec:XF [(match_dup 10) (match_dup 9)]
16091                               UNSPEC_FSCALE_EXP))])
16092    (set (match_dup 13) (minus:XF (match_dup 11) (match_dup 10)))
16093    (set (match_dup 14) (plus:XF (match_dup 13) (match_dup 8)))
16094    (set (match_operand:SF 0 "register_operand" "")
16095         (float_truncate:SF (match_dup 14)))]
16096   "TARGET_USE_FANCY_MATH_387
16097    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16098    && flag_unsafe_math_optimizations"
16100   rtx temp;
16101   int i;
16103   for (i=2; i<15; i++)
16104     operands[i] = gen_reg_rtx (XFmode);
16105   temp = standard_80387_constant_rtx (5); /* fldl2e */
16106   emit_move_insn (operands[3], temp);
16107   emit_move_insn (operands[10], CONST1_RTX (XFmode));  /* fld1 */
16110 (define_expand "expm1xf2"
16111   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
16112                                (match_dup 2)))
16113    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
16114    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
16115    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
16116    (parallel [(set (match_dup 7)
16117                    (unspec:XF [(match_dup 6) (match_dup 4)]
16118                               UNSPEC_FSCALE_FRACT))
16119                    (set (match_dup 8)
16120                    (unspec:XF [(match_dup 6) (match_dup 4)]
16121                               UNSPEC_FSCALE_EXP))])
16122    (parallel [(set (match_dup 10)
16123                    (unspec:XF [(match_dup 9) (match_dup 8)]
16124                               UNSPEC_FSCALE_FRACT))
16125               (set (match_dup 11)
16126                    (unspec:XF [(match_dup 9) (match_dup 8)]
16127                               UNSPEC_FSCALE_EXP))])
16128    (set (match_dup 12) (minus:XF (match_dup 10) (match_dup 9)))
16129    (set (match_operand:XF 0 "register_operand" "")
16130         (plus:XF (match_dup 12) (match_dup 7)))]
16131   "TARGET_USE_FANCY_MATH_387
16132    && flag_unsafe_math_optimizations"
16134   rtx temp;
16135   int i;
16137   for (i=2; i<13; i++)
16138     operands[i] = gen_reg_rtx (XFmode);
16139   temp = standard_80387_constant_rtx (5); /* fldl2e */
16140   emit_move_insn (operands[2], temp);
16141   emit_move_insn (operands[9], CONST1_RTX (XFmode));  /* fld1 */
16144 (define_expand "ldexpdf3"
16145   [(set (match_dup 3)
16146         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16147    (set (match_dup 4)
16148         (float:XF (match_operand:SI 2 "register_operand" "")))
16149    (parallel [(set (match_dup 5)
16150                    (unspec:XF [(match_dup 3) (match_dup 4)]
16151                               UNSPEC_FSCALE_FRACT))
16152               (set (match_dup 6)
16153                    (unspec:XF [(match_dup 3) (match_dup 4)]
16154                               UNSPEC_FSCALE_EXP))])
16155    (set (match_operand:DF 0 "register_operand" "")
16156         (float_truncate:DF (match_dup 5)))]
16157   "TARGET_USE_FANCY_MATH_387
16158    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16159    && flag_unsafe_math_optimizations"
16161   int i;
16163   for (i=3; i<7; i++)
16164     operands[i] = gen_reg_rtx (XFmode);
16167 (define_expand "ldexpsf3"
16168   [(set (match_dup 3)
16169         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16170    (set (match_dup 4)
16171         (float:XF (match_operand:SI 2 "register_operand" "")))
16172    (parallel [(set (match_dup 5)
16173                    (unspec:XF [(match_dup 3) (match_dup 4)]
16174                               UNSPEC_FSCALE_FRACT))
16175               (set (match_dup 6)
16176                    (unspec:XF [(match_dup 3) (match_dup 4)]
16177                               UNSPEC_FSCALE_EXP))])
16178    (set (match_operand:SF 0 "register_operand" "")
16179         (float_truncate:SF (match_dup 5)))]
16180   "TARGET_USE_FANCY_MATH_387
16181    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16182    && flag_unsafe_math_optimizations"
16184   int i;
16186   for (i=3; i<7; i++)
16187     operands[i] = gen_reg_rtx (XFmode);
16190 (define_expand "ldexpxf3"
16191   [(set (match_dup 3)
16192         (float:XF (match_operand:SI 2 "register_operand" "")))
16193    (parallel [(set (match_operand:XF 0 " register_operand" "")
16194                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
16195                                (match_dup 3)]
16196                               UNSPEC_FSCALE_FRACT))
16197               (set (match_dup 4)
16198                    (unspec:XF [(match_dup 1) (match_dup 3)]
16199                               UNSPEC_FSCALE_EXP))])]
16200   "TARGET_USE_FANCY_MATH_387
16201    && flag_unsafe_math_optimizations"
16203   int i;
16205   for (i=3; i<5; i++)
16206     operands[i] = gen_reg_rtx (XFmode);
16210 (define_insn "frndintxf2"
16211   [(set (match_operand:XF 0 "register_operand" "=f")
16212         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16213          UNSPEC_FRNDINT))]
16214   "TARGET_USE_FANCY_MATH_387
16215    && flag_unsafe_math_optimizations"
16216   "frndint"
16217   [(set_attr "type" "fpspc")
16218    (set_attr "mode" "XF")])
16220 (define_expand "rintdf2"
16221   [(use (match_operand:DF 0 "register_operand" ""))
16222    (use (match_operand:DF 1 "register_operand" ""))]
16223   "TARGET_USE_FANCY_MATH_387
16224    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16225    && flag_unsafe_math_optimizations"
16227   rtx op0 = gen_reg_rtx (XFmode);
16228   rtx op1 = gen_reg_rtx (XFmode);
16230   emit_insn (gen_extenddfxf2 (op1, operands[1]));
16231   emit_insn (gen_frndintxf2 (op0, op1));
16233   emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16234   DONE;
16237 (define_expand "rintsf2"
16238   [(use (match_operand:SF 0 "register_operand" ""))
16239    (use (match_operand:SF 1 "register_operand" ""))]
16240   "TARGET_USE_FANCY_MATH_387
16241    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16242    && flag_unsafe_math_optimizations"
16244   rtx op0 = gen_reg_rtx (XFmode);
16245   rtx op1 = gen_reg_rtx (XFmode);
16247   emit_insn (gen_extendsfxf2 (op1, operands[1]));
16248   emit_insn (gen_frndintxf2 (op0, op1));
16250   emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16251   DONE;
16254 (define_expand "rintxf2"
16255   [(use (match_operand:XF 0 "register_operand" ""))
16256    (use (match_operand:XF 1 "register_operand" ""))]
16257   "TARGET_USE_FANCY_MATH_387
16258    && flag_unsafe_math_optimizations"
16260   emit_insn (gen_frndintxf2 (operands[0], operands[1]));
16261   DONE;
16264 (define_insn "fistdi2"
16265   [(set (match_operand:DI 0 "memory_operand" "=m")
16266         (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
16267          UNSPEC_FIST))
16268    (clobber (match_scratch:XF 2 "=&1f"))]
16269   "TARGET_USE_FANCY_MATH_387
16270    && flag_unsafe_math_optimizations"
16271   "* return output_fix_trunc (insn, operands, 0);"
16272   [(set_attr "type" "fpspc")
16273    (set_attr "mode" "DI")])
16275 (define_insn "fistdi2_with_temp"
16276   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
16277         (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
16278          UNSPEC_FIST))
16279    (clobber (match_operand:DI 2 "memory_operand" "=m,m"))
16280    (clobber (match_scratch:XF 3 "=&1f,&1f"))]
16281   "TARGET_USE_FANCY_MATH_387
16282    && flag_unsafe_math_optimizations"
16283   "#"
16284   [(set_attr "type" "fpspc")
16285    (set_attr "mode" "DI")])
16287 (define_split 
16288   [(set (match_operand:DI 0 "register_operand" "")
16289         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16290          UNSPEC_FIST))
16291    (clobber (match_operand:DI 2 "memory_operand" ""))
16292    (clobber (match_scratch 3 ""))]
16293   "reload_completed"
16294   [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
16295               (clobber (match_dup 3))])
16296    (set (match_dup 0) (match_dup 2))]
16297   "")
16299 (define_split 
16300   [(set (match_operand:DI 0 "memory_operand" "")
16301         (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16302          UNSPEC_FIST))
16303    (clobber (match_operand:DI 2 "memory_operand" ""))
16304    (clobber (match_scratch 3 ""))]
16305   "reload_completed"
16306   [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
16307               (clobber (match_dup 3))])]
16308   "")
16310 (define_insn "fist<mode>2"
16311   [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
16312         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16313          UNSPEC_FIST))]
16314   "TARGET_USE_FANCY_MATH_387
16315    && flag_unsafe_math_optimizations"
16316   "* return output_fix_trunc (insn, operands, 0);"
16317   [(set_attr "type" "fpspc")
16318    (set_attr "mode" "<MODE>")])
16320 (define_insn "fist<mode>2_with_temp"
16321   [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
16322         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
16323          UNSPEC_FIST))
16324    (clobber (match_operand:X87MODEI12 2 "memory_operand" "=m,m"))]
16325   "TARGET_USE_FANCY_MATH_387
16326    && flag_unsafe_math_optimizations"
16327   "#"
16328   [(set_attr "type" "fpspc")
16329    (set_attr "mode" "<MODE>")])
16331 (define_split 
16332   [(set (match_operand:X87MODEI12 0 "register_operand" "")
16333         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16334          UNSPEC_FIST))
16335    (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
16336   "reload_completed"
16337   [(set (match_dup 2) (unspec:X87MODEI12 [(match_dup 1)]
16338                        UNSPEC_FIST))
16339    (set (match_dup 0) (match_dup 2))]
16340   "")
16342 (define_split 
16343   [(set (match_operand:X87MODEI12 0 "memory_operand" "")
16344         (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16345          UNSPEC_FIST))
16346    (clobber (match_scratch 2 ""))]
16347   "reload_completed"
16348   [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
16349                        UNSPEC_FIST))]
16350   "")
16352 (define_expand "lrint<mode>2"
16353   [(use (match_operand:X87MODEI 0 "nonimmediate_operand" ""))
16354    (use (match_operand:XF 1 "register_operand" ""))]
16355   "TARGET_USE_FANCY_MATH_387
16356    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16357    && flag_unsafe_math_optimizations"
16359   if (memory_operand (operands[0], VOIDmode))
16360     emit_insn (gen_fist<mode>2 (operands[0], operands[1]));
16361   else
16362     {
16363       operands[2] = assign_386_stack_local (<MODE>mode, 0);
16364       emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1],
16365                                             operands[2]));
16366     }
16367   DONE;
16370 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16371 (define_insn_and_split "frndintxf2_floor"
16372   [(set (match_operand:XF 0 "register_operand" "=f")
16373         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16374          UNSPEC_FRNDINT_FLOOR))
16375    (clobber (reg:CC FLAGS_REG))]
16376   "TARGET_USE_FANCY_MATH_387
16377    && flag_unsafe_math_optimizations
16378    && !(reload_completed || reload_in_progress)"
16379   "#"
16380   "&& 1"
16381   [(const_int 0)]
16383   ix86_optimize_mode_switching = 1;
16385   operands[2] = assign_386_stack_local (HImode, 1);
16386   operands[3] = assign_386_stack_local (HImode, 2);
16388   emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1],
16389                                         operands[2], operands[3]));
16390   DONE;
16392   [(set_attr "type" "frndint")
16393    (set_attr "i387_cw" "floor")
16394    (set_attr "mode" "XF")])
16396 (define_insn "frndintxf2_floor_i387"
16397   [(set (match_operand:XF 0 "register_operand" "=f")
16398         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16399          UNSPEC_FRNDINT_FLOOR))
16400    (use (match_operand:HI 2 "memory_operand" "m"))
16401    (use (match_operand:HI 3 "memory_operand" "m"))]
16402   "TARGET_USE_FANCY_MATH_387
16403    && flag_unsafe_math_optimizations"
16404   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
16405   [(set_attr "type" "frndint")
16406    (set_attr "i387_cw" "floor")
16407    (set_attr "mode" "XF")])
16409 (define_expand "floorxf2"
16410   [(use (match_operand:XF 0 "register_operand" ""))
16411    (use (match_operand:XF 1 "register_operand" ""))]
16412   "TARGET_USE_FANCY_MATH_387
16413    && flag_unsafe_math_optimizations"
16415   emit_insn (gen_frndintxf2_floor (operands[0], operands[1]));
16416   DONE;
16419 (define_expand "floordf2"
16420   [(use (match_operand:DF 0 "register_operand" ""))
16421    (use (match_operand:DF 1 "register_operand" ""))]
16422   "TARGET_USE_FANCY_MATH_387
16423    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16424    && flag_unsafe_math_optimizations"
16426   rtx op0 = gen_reg_rtx (XFmode);
16427   rtx op1 = gen_reg_rtx (XFmode);
16429   emit_insn (gen_extenddfxf2 (op1, operands[1]));
16430   emit_insn (gen_frndintxf2_floor (op0, op1));
16432   emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16433   DONE;
16436 (define_expand "floorsf2"
16437   [(use (match_operand:SF 0 "register_operand" ""))
16438    (use (match_operand:SF 1 "register_operand" ""))]
16439   "TARGET_USE_FANCY_MATH_387
16440    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16441    && flag_unsafe_math_optimizations"
16443   rtx op0 = gen_reg_rtx (XFmode);
16444   rtx op1 = gen_reg_rtx (XFmode);
16446   emit_insn (gen_extendsfxf2 (op1, operands[1]));
16447   emit_insn (gen_frndintxf2_floor (op0, op1));
16449   emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16450   DONE;
16453 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16454 (define_insn_and_split "frndintxf2_ceil"
16455   [(set (match_operand:XF 0 "register_operand" "=f")
16456         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16457          UNSPEC_FRNDINT_CEIL))
16458    (clobber (reg:CC FLAGS_REG))]
16459   "TARGET_USE_FANCY_MATH_387
16460    && flag_unsafe_math_optimizations
16461    && !(reload_completed || reload_in_progress)"
16462   "#"
16463   "&& 1"
16464   [(const_int 0)]
16466   ix86_optimize_mode_switching = 1;
16468   operands[2] = assign_386_stack_local (HImode, 1);
16469   operands[3] = assign_386_stack_local (HImode, 2);
16471   emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1],
16472                                        operands[2], operands[3]));
16473   DONE;
16475   [(set_attr "type" "frndint")
16476    (set_attr "i387_cw" "ceil")
16477    (set_attr "mode" "XF")])
16479 (define_insn "frndintxf2_ceil_i387"
16480   [(set (match_operand:XF 0 "register_operand" "=f")
16481         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16482          UNSPEC_FRNDINT_CEIL))
16483    (use (match_operand:HI 2 "memory_operand" "m"))
16484    (use (match_operand:HI 3 "memory_operand" "m"))]
16485   "TARGET_USE_FANCY_MATH_387
16486    && flag_unsafe_math_optimizations"
16487   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
16488   [(set_attr "type" "frndint")
16489    (set_attr "i387_cw" "ceil")
16490    (set_attr "mode" "XF")])
16492 (define_expand "ceilxf2"
16493   [(use (match_operand:XF 0 "register_operand" ""))
16494    (use (match_operand:XF 1 "register_operand" ""))]
16495   "TARGET_USE_FANCY_MATH_387
16496    && flag_unsafe_math_optimizations"
16498   emit_insn (gen_frndintxf2_ceil (operands[0], operands[1]));
16499   DONE;
16502 (define_expand "ceildf2"
16503   [(use (match_operand:DF 0 "register_operand" ""))
16504    (use (match_operand:DF 1 "register_operand" ""))]
16505   "TARGET_USE_FANCY_MATH_387
16506    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16507    && flag_unsafe_math_optimizations"
16509   rtx op0 = gen_reg_rtx (XFmode);
16510   rtx op1 = gen_reg_rtx (XFmode);
16512   emit_insn (gen_extenddfxf2 (op1, operands[1]));
16513   emit_insn (gen_frndintxf2_ceil (op0, op1));
16515   emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16516   DONE;
16519 (define_expand "ceilsf2"
16520   [(use (match_operand:SF 0 "register_operand" ""))
16521    (use (match_operand:SF 1 "register_operand" ""))]
16522   "TARGET_USE_FANCY_MATH_387
16523    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16524    && flag_unsafe_math_optimizations"
16526   rtx op0 = gen_reg_rtx (XFmode);
16527   rtx op1 = gen_reg_rtx (XFmode);
16529   emit_insn (gen_extendsfxf2 (op1, operands[1]));
16530   emit_insn (gen_frndintxf2_ceil (op0, op1));
16532   emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16533   DONE;
16536 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16537 (define_insn_and_split "frndintxf2_trunc"
16538   [(set (match_operand:XF 0 "register_operand" "=f")
16539         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16540          UNSPEC_FRNDINT_TRUNC))
16541    (clobber (reg:CC FLAGS_REG))]
16542   "TARGET_USE_FANCY_MATH_387
16543    && flag_unsafe_math_optimizations
16544    && !(reload_completed || reload_in_progress)"
16545   "#"
16546   "&& 1"
16547   [(const_int 0)]
16549   ix86_optimize_mode_switching = 1;
16551   operands[2] = assign_386_stack_local (HImode, 1);
16552   operands[3] = assign_386_stack_local (HImode, 2);
16554   emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1],
16555                                         operands[2], operands[3]));
16556   DONE;
16558   [(set_attr "type" "frndint")
16559    (set_attr "i387_cw" "trunc")
16560    (set_attr "mode" "XF")])
16562 (define_insn "frndintxf2_trunc_i387"
16563   [(set (match_operand:XF 0 "register_operand" "=f")
16564         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16565          UNSPEC_FRNDINT_TRUNC))
16566    (use (match_operand:HI 2 "memory_operand" "m"))
16567    (use (match_operand:HI 3 "memory_operand" "m"))]
16568   "TARGET_USE_FANCY_MATH_387
16569    && flag_unsafe_math_optimizations"
16570   "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
16571   [(set_attr "type" "frndint")
16572    (set_attr "i387_cw" "trunc")
16573    (set_attr "mode" "XF")])
16575 (define_expand "btruncxf2"
16576   [(use (match_operand:XF 0 "register_operand" ""))
16577    (use (match_operand:XF 1 "register_operand" ""))]
16578   "TARGET_USE_FANCY_MATH_387
16579    && flag_unsafe_math_optimizations"
16581   emit_insn (gen_frndintxf2_trunc (operands[0], operands[1]));
16582   DONE;
16585 (define_expand "btruncdf2"
16586   [(use (match_operand:DF 0 "register_operand" ""))
16587    (use (match_operand:DF 1 "register_operand" ""))]
16588   "TARGET_USE_FANCY_MATH_387
16589    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16590    && flag_unsafe_math_optimizations"
16592   rtx op0 = gen_reg_rtx (XFmode);
16593   rtx op1 = gen_reg_rtx (XFmode);
16595   emit_insn (gen_extenddfxf2 (op1, operands[1]));
16596   emit_insn (gen_frndintxf2_trunc (op0, op1));
16598   emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16599   DONE;
16602 (define_expand "btruncsf2"
16603   [(use (match_operand:SF 0 "register_operand" ""))
16604    (use (match_operand:SF 1 "register_operand" ""))]
16605   "TARGET_USE_FANCY_MATH_387
16606    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16607    && flag_unsafe_math_optimizations"
16609   rtx op0 = gen_reg_rtx (XFmode);
16610   rtx op1 = gen_reg_rtx (XFmode);
16612   emit_insn (gen_extendsfxf2 (op1, operands[1]));
16613   emit_insn (gen_frndintxf2_trunc (op0, op1));
16615   emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16616   DONE;
16619 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16620 (define_insn_and_split "frndintxf2_mask_pm"
16621   [(set (match_operand:XF 0 "register_operand" "=f")
16622         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16623          UNSPEC_FRNDINT_MASK_PM))
16624    (clobber (reg:CC FLAGS_REG))]
16625   "TARGET_USE_FANCY_MATH_387
16626    && flag_unsafe_math_optimizations
16627    && !(reload_completed || reload_in_progress)"
16628   "#"
16629   "&& 1"
16630   [(const_int 0)]
16632   ix86_optimize_mode_switching = 1;
16634   operands[2] = assign_386_stack_local (HImode, 1);
16635   operands[3] = assign_386_stack_local (HImode, 2);
16637   emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1],
16638                                           operands[2], operands[3]));
16639   DONE;
16641   [(set_attr "type" "frndint")
16642    (set_attr "i387_cw" "mask_pm")
16643    (set_attr "mode" "XF")])
16645 (define_insn "frndintxf2_mask_pm_i387"
16646   [(set (match_operand:XF 0 "register_operand" "=f")
16647         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16648          UNSPEC_FRNDINT_MASK_PM))
16649    (use (match_operand:HI 2 "memory_operand" "m"))
16650    (use (match_operand:HI 3 "memory_operand" "m"))]
16651   "TARGET_USE_FANCY_MATH_387
16652    && flag_unsafe_math_optimizations"
16653   "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2"
16654   [(set_attr "type" "frndint")
16655    (set_attr "i387_cw" "mask_pm")
16656    (set_attr "mode" "XF")])
16658 (define_expand "nearbyintxf2"
16659   [(use (match_operand:XF 0 "register_operand" ""))
16660    (use (match_operand:XF 1 "register_operand" ""))]
16661   "TARGET_USE_FANCY_MATH_387
16662    && flag_unsafe_math_optimizations"
16664   emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1]));
16666   DONE;
16669 (define_expand "nearbyintdf2"
16670   [(use (match_operand:DF 0 "register_operand" ""))
16671    (use (match_operand:DF 1 "register_operand" ""))]
16672   "TARGET_USE_FANCY_MATH_387
16673    && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16674    && flag_unsafe_math_optimizations"
16676   rtx op0 = gen_reg_rtx (XFmode);
16677   rtx op1 = gen_reg_rtx (XFmode);
16679   emit_insn (gen_extenddfxf2 (op1, operands[1]));
16680   emit_insn (gen_frndintxf2_mask_pm (op0, op1));
16682   emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16683   DONE;
16686 (define_expand "nearbyintsf2"
16687   [(use (match_operand:SF 0 "register_operand" ""))
16688    (use (match_operand:SF 1 "register_operand" ""))]
16689   "TARGET_USE_FANCY_MATH_387
16690    && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16691    && flag_unsafe_math_optimizations"
16693   rtx op0 = gen_reg_rtx (XFmode);
16694   rtx op1 = gen_reg_rtx (XFmode);
16696   emit_insn (gen_extendsfxf2 (op1, operands[1]));
16697   emit_insn (gen_frndintxf2_mask_pm (op0, op1));
16699   emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16700   DONE;
16704 ;; Block operation instructions
16706 (define_insn "cld"
16707  [(set (reg:SI DIRFLAG_REG) (const_int 0))]
16708  ""
16709  "cld"
16710   [(set_attr "type" "cld")])
16712 (define_expand "movmemsi"
16713   [(use (match_operand:BLK 0 "memory_operand" ""))
16714    (use (match_operand:BLK 1 "memory_operand" ""))
16715    (use (match_operand:SI 2 "nonmemory_operand" ""))
16716    (use (match_operand:SI 3 "const_int_operand" ""))]
16717   "! optimize_size"
16719  if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3]))
16720    DONE;
16721  else
16722    FAIL;
16725 (define_expand "movmemdi"
16726   [(use (match_operand:BLK 0 "memory_operand" ""))
16727    (use (match_operand:BLK 1 "memory_operand" ""))
16728    (use (match_operand:DI 2 "nonmemory_operand" ""))
16729    (use (match_operand:DI 3 "const_int_operand" ""))]
16730   "TARGET_64BIT"
16732  if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3]))
16733    DONE;
16734  else
16735    FAIL;
16738 ;; Most CPUs don't like single string operations
16739 ;; Handle this case here to simplify previous expander.
16741 (define_expand "strmov"
16742   [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
16743    (set (match_operand 1 "memory_operand" "") (match_dup 4))
16744    (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
16745               (clobber (reg:CC FLAGS_REG))])
16746    (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
16747               (clobber (reg:CC FLAGS_REG))])]
16748   ""
16750   rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
16752   /* If .md ever supports :P for Pmode, these can be directly
16753      in the pattern above.  */
16754   operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
16755   operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
16757   if (TARGET_SINGLE_STRINGOP || optimize_size)
16758     {
16759       emit_insn (gen_strmov_singleop (operands[0], operands[1],
16760                                       operands[2], operands[3],
16761                                       operands[5], operands[6]));
16762       DONE;
16763     }
16765   operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
16768 (define_expand "strmov_singleop"
16769   [(parallel [(set (match_operand 1 "memory_operand" "")
16770                    (match_operand 3 "memory_operand" ""))
16771               (set (match_operand 0 "register_operand" "")
16772                    (match_operand 4 "" ""))
16773               (set (match_operand 2 "register_operand" "")
16774                    (match_operand 5 "" ""))
16775               (use (reg:SI DIRFLAG_REG))])]
16776   "TARGET_SINGLE_STRINGOP || optimize_size"
16777   "")
16779 (define_insn "*strmovdi_rex_1"
16780   [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
16781         (mem:DI (match_operand:DI 3 "register_operand" "1")))
16782    (set (match_operand:DI 0 "register_operand" "=D")
16783         (plus:DI (match_dup 2)
16784                  (const_int 8)))
16785    (set (match_operand:DI 1 "register_operand" "=S")
16786         (plus:DI (match_dup 3)
16787                  (const_int 8)))
16788    (use (reg:SI DIRFLAG_REG))]
16789   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
16790   "movsq"
16791   [(set_attr "type" "str")
16792    (set_attr "mode" "DI")
16793    (set_attr "memory" "both")])
16795 (define_insn "*strmovsi_1"
16796   [(set (mem:SI (match_operand:SI 2 "register_operand" "0"))
16797         (mem:SI (match_operand:SI 3 "register_operand" "1")))
16798    (set (match_operand:SI 0 "register_operand" "=D")
16799         (plus:SI (match_dup 2)
16800                  (const_int 4)))
16801    (set (match_operand:SI 1 "register_operand" "=S")
16802         (plus:SI (match_dup 3)
16803                  (const_int 4)))
16804    (use (reg:SI DIRFLAG_REG))]
16805   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
16806   "{movsl|movsd}"
16807   [(set_attr "type" "str")
16808    (set_attr "mode" "SI")
16809    (set_attr "memory" "both")])
16811 (define_insn "*strmovsi_rex_1"
16812   [(set (mem:SI (match_operand:DI 2 "register_operand" "0"))
16813         (mem:SI (match_operand:DI 3 "register_operand" "1")))
16814    (set (match_operand:DI 0 "register_operand" "=D")
16815         (plus:DI (match_dup 2)
16816                  (const_int 4)))
16817    (set (match_operand:DI 1 "register_operand" "=S")
16818         (plus:DI (match_dup 3)
16819                  (const_int 4)))
16820    (use (reg:SI DIRFLAG_REG))]
16821   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
16822   "{movsl|movsd}"
16823   [(set_attr "type" "str")
16824    (set_attr "mode" "SI")
16825    (set_attr "memory" "both")])
16827 (define_insn "*strmovhi_1"
16828   [(set (mem:HI (match_operand:SI 2 "register_operand" "0"))
16829         (mem:HI (match_operand:SI 3 "register_operand" "1")))
16830    (set (match_operand:SI 0 "register_operand" "=D")
16831         (plus:SI (match_dup 2)
16832                  (const_int 2)))
16833    (set (match_operand:SI 1 "register_operand" "=S")
16834         (plus:SI (match_dup 3)
16835                  (const_int 2)))
16836    (use (reg:SI DIRFLAG_REG))]
16837   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
16838   "movsw"
16839   [(set_attr "type" "str")
16840    (set_attr "memory" "both")
16841    (set_attr "mode" "HI")])
16843 (define_insn "*strmovhi_rex_1"
16844   [(set (mem:HI (match_operand:DI 2 "register_operand" "0"))
16845         (mem:HI (match_operand:DI 3 "register_operand" "1")))
16846    (set (match_operand:DI 0 "register_operand" "=D")
16847         (plus:DI (match_dup 2)
16848                  (const_int 2)))
16849    (set (match_operand:DI 1 "register_operand" "=S")
16850         (plus:DI (match_dup 3)
16851                  (const_int 2)))
16852    (use (reg:SI DIRFLAG_REG))]
16853   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
16854   "movsw"
16855   [(set_attr "type" "str")
16856    (set_attr "memory" "both")
16857    (set_attr "mode" "HI")])
16859 (define_insn "*strmovqi_1"
16860   [(set (mem:QI (match_operand:SI 2 "register_operand" "0"))
16861         (mem:QI (match_operand:SI 3 "register_operand" "1")))
16862    (set (match_operand:SI 0 "register_operand" "=D")
16863         (plus:SI (match_dup 2)
16864                  (const_int 1)))
16865    (set (match_operand:SI 1 "register_operand" "=S")
16866         (plus:SI (match_dup 3)
16867                  (const_int 1)))
16868    (use (reg:SI DIRFLAG_REG))]
16869   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
16870   "movsb"
16871   [(set_attr "type" "str")
16872    (set_attr "memory" "both")
16873    (set_attr "mode" "QI")])
16875 (define_insn "*strmovqi_rex_1"
16876   [(set (mem:QI (match_operand:DI 2 "register_operand" "0"))
16877         (mem:QI (match_operand:DI 3 "register_operand" "1")))
16878    (set (match_operand:DI 0 "register_operand" "=D")
16879         (plus:DI (match_dup 2)
16880                  (const_int 1)))
16881    (set (match_operand:DI 1 "register_operand" "=S")
16882         (plus:DI (match_dup 3)
16883                  (const_int 1)))
16884    (use (reg:SI DIRFLAG_REG))]
16885   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
16886   "movsb"
16887   [(set_attr "type" "str")
16888    (set_attr "memory" "both")
16889    (set_attr "mode" "QI")])
16891 (define_expand "rep_mov"
16892   [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
16893               (set (match_operand 0 "register_operand" "")
16894                    (match_operand 5 "" ""))
16895               (set (match_operand 2 "register_operand" "")
16896                    (match_operand 6 "" ""))
16897               (set (match_operand 1 "memory_operand" "")
16898                    (match_operand 3 "memory_operand" ""))
16899               (use (match_dup 4))
16900               (use (reg:SI DIRFLAG_REG))])]
16901   ""
16902   "")
16904 (define_insn "*rep_movdi_rex64"
16905   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
16906    (set (match_operand:DI 0 "register_operand" "=D") 
16907         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
16908                             (const_int 3))
16909                  (match_operand:DI 3 "register_operand" "0")))
16910    (set (match_operand:DI 1 "register_operand" "=S") 
16911         (plus:DI (ashift:DI (match_dup 5) (const_int 3))
16912                  (match_operand:DI 4 "register_operand" "1")))
16913    (set (mem:BLK (match_dup 3))
16914         (mem:BLK (match_dup 4)))
16915    (use (match_dup 5))
16916    (use (reg:SI DIRFLAG_REG))]
16917   "TARGET_64BIT"
16918   "{rep\;movsq|rep movsq}"
16919   [(set_attr "type" "str")
16920    (set_attr "prefix_rep" "1")
16921    (set_attr "memory" "both")
16922    (set_attr "mode" "DI")])
16924 (define_insn "*rep_movsi"
16925   [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
16926    (set (match_operand:SI 0 "register_operand" "=D") 
16927         (plus:SI (ashift:SI (match_operand:SI 5 "register_operand" "2")
16928                             (const_int 2))
16929                  (match_operand:SI 3 "register_operand" "0")))
16930    (set (match_operand:SI 1 "register_operand" "=S") 
16931         (plus:SI (ashift:SI (match_dup 5) (const_int 2))
16932                  (match_operand:SI 4 "register_operand" "1")))
16933    (set (mem:BLK (match_dup 3))
16934         (mem:BLK (match_dup 4)))
16935    (use (match_dup 5))
16936    (use (reg:SI DIRFLAG_REG))]
16937   "!TARGET_64BIT"
16938   "{rep\;movsl|rep movsd}"
16939   [(set_attr "type" "str")
16940    (set_attr "prefix_rep" "1")
16941    (set_attr "memory" "both")
16942    (set_attr "mode" "SI")])
16944 (define_insn "*rep_movsi_rex64"
16945   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
16946    (set (match_operand:DI 0 "register_operand" "=D") 
16947         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
16948                             (const_int 2))
16949                  (match_operand:DI 3 "register_operand" "0")))
16950    (set (match_operand:DI 1 "register_operand" "=S") 
16951         (plus:DI (ashift:DI (match_dup 5) (const_int 2))
16952                  (match_operand:DI 4 "register_operand" "1")))
16953    (set (mem:BLK (match_dup 3))
16954         (mem:BLK (match_dup 4)))
16955    (use (match_dup 5))
16956    (use (reg:SI DIRFLAG_REG))]
16957   "TARGET_64BIT"
16958   "{rep\;movsl|rep movsd}"
16959   [(set_attr "type" "str")
16960    (set_attr "prefix_rep" "1")
16961    (set_attr "memory" "both")
16962    (set_attr "mode" "SI")])
16964 (define_insn "*rep_movqi"
16965   [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
16966    (set (match_operand:SI 0 "register_operand" "=D") 
16967         (plus:SI (match_operand:SI 3 "register_operand" "0")
16968                  (match_operand:SI 5 "register_operand" "2")))
16969    (set (match_operand:SI 1 "register_operand" "=S") 
16970         (plus:SI (match_operand:SI 4 "register_operand" "1") (match_dup 5)))
16971    (set (mem:BLK (match_dup 3))
16972         (mem:BLK (match_dup 4)))
16973    (use (match_dup 5))
16974    (use (reg:SI DIRFLAG_REG))]
16975   "!TARGET_64BIT"
16976   "{rep\;movsb|rep movsb}"
16977   [(set_attr "type" "str")
16978    (set_attr "prefix_rep" "1")
16979    (set_attr "memory" "both")
16980    (set_attr "mode" "SI")])
16982 (define_insn "*rep_movqi_rex64"
16983   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
16984    (set (match_operand:DI 0 "register_operand" "=D") 
16985         (plus:DI (match_operand:DI 3 "register_operand" "0")
16986                  (match_operand:DI 5 "register_operand" "2")))
16987    (set (match_operand:DI 1 "register_operand" "=S") 
16988         (plus:DI (match_operand:DI 4 "register_operand" "1") (match_dup 5)))
16989    (set (mem:BLK (match_dup 3))
16990         (mem:BLK (match_dup 4)))
16991    (use (match_dup 5))
16992    (use (reg:SI DIRFLAG_REG))]
16993   "TARGET_64BIT"
16994   "{rep\;movsb|rep movsb}"
16995   [(set_attr "type" "str")
16996    (set_attr "prefix_rep" "1")
16997    (set_attr "memory" "both")
16998    (set_attr "mode" "SI")])
17000 (define_expand "clrmemsi"
17001    [(use (match_operand:BLK 0 "memory_operand" ""))
17002     (use (match_operand:SI 1 "nonmemory_operand" ""))
17003     (use (match_operand 2 "const_int_operand" ""))]
17004   ""
17006  if (ix86_expand_clrmem (operands[0], operands[1], operands[2]))
17007    DONE;
17008  else
17009    FAIL;
17012 (define_expand "clrmemdi"
17013    [(use (match_operand:BLK 0 "memory_operand" ""))
17014     (use (match_operand:DI 1 "nonmemory_operand" ""))
17015     (use (match_operand 2 "const_int_operand" ""))]
17016   "TARGET_64BIT"
17018  if (ix86_expand_clrmem (operands[0], operands[1], operands[2]))
17019    DONE;
17020  else
17021    FAIL;
17024 ;; Most CPUs don't like single string operations
17025 ;; Handle this case here to simplify previous expander.
17027 (define_expand "strset"
17028   [(set (match_operand 1 "memory_operand" "")
17029         (match_operand 2 "register_operand" ""))
17030    (parallel [(set (match_operand 0 "register_operand" "")
17031                    (match_dup 3))
17032               (clobber (reg:CC FLAGS_REG))])]
17033   ""
17035   if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
17036     operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
17038   /* If .md ever supports :P for Pmode, this can be directly
17039      in the pattern above.  */
17040   operands[3] = gen_rtx_PLUS (Pmode, operands[0],
17041                               GEN_INT (GET_MODE_SIZE (GET_MODE
17042                                                       (operands[2]))));
17043   if (TARGET_SINGLE_STRINGOP || optimize_size)
17044     {
17045       emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
17046                                       operands[3]));
17047       DONE;
17048     }
17051 (define_expand "strset_singleop"
17052   [(parallel [(set (match_operand 1 "memory_operand" "")
17053                    (match_operand 2 "register_operand" ""))
17054               (set (match_operand 0 "register_operand" "")
17055                    (match_operand 3 "" ""))
17056               (use (reg:SI DIRFLAG_REG))])]
17057   "TARGET_SINGLE_STRINGOP || optimize_size"
17058   "")
17060 (define_insn "*strsetdi_rex_1"
17061   [(set (mem:DI (match_operand:DI 1 "register_operand" "0"))
17062         (match_operand:DI 2 "register_operand" "a"))
17063    (set (match_operand:DI 0 "register_operand" "=D")
17064         (plus:DI (match_dup 1)
17065                  (const_int 8)))
17066    (use (reg:SI DIRFLAG_REG))]
17067   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17068   "stosq"
17069   [(set_attr "type" "str")
17070    (set_attr "memory" "store")
17071    (set_attr "mode" "DI")])
17073 (define_insn "*strsetsi_1"
17074   [(set (mem:SI (match_operand:SI 1 "register_operand" "0"))
17075         (match_operand:SI 2 "register_operand" "a"))
17076    (set (match_operand:SI 0 "register_operand" "=D")
17077         (plus:SI (match_dup 1)
17078                  (const_int 4)))
17079    (use (reg:SI DIRFLAG_REG))]
17080   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17081   "{stosl|stosd}"
17082   [(set_attr "type" "str")
17083    (set_attr "memory" "store")
17084    (set_attr "mode" "SI")])
17086 (define_insn "*strsetsi_rex_1"
17087   [(set (mem:SI (match_operand:DI 1 "register_operand" "0"))
17088         (match_operand:SI 2 "register_operand" "a"))
17089    (set (match_operand:DI 0 "register_operand" "=D")
17090         (plus:DI (match_dup 1)
17091                  (const_int 4)))
17092    (use (reg:SI DIRFLAG_REG))]
17093   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17094   "{stosl|stosd}"
17095   [(set_attr "type" "str")
17096    (set_attr "memory" "store")
17097    (set_attr "mode" "SI")])
17099 (define_insn "*strsethi_1"
17100   [(set (mem:HI (match_operand:SI 1 "register_operand" "0"))
17101         (match_operand:HI 2 "register_operand" "a"))
17102    (set (match_operand:SI 0 "register_operand" "=D")
17103         (plus:SI (match_dup 1)
17104                  (const_int 2)))
17105    (use (reg:SI DIRFLAG_REG))]
17106   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17107   "stosw"
17108   [(set_attr "type" "str")
17109    (set_attr "memory" "store")
17110    (set_attr "mode" "HI")])
17112 (define_insn "*strsethi_rex_1"
17113   [(set (mem:HI (match_operand:DI 1 "register_operand" "0"))
17114         (match_operand:HI 2 "register_operand" "a"))
17115    (set (match_operand:DI 0 "register_operand" "=D")
17116         (plus:DI (match_dup 1)
17117                  (const_int 2)))
17118    (use (reg:SI DIRFLAG_REG))]
17119   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17120   "stosw"
17121   [(set_attr "type" "str")
17122    (set_attr "memory" "store")
17123    (set_attr "mode" "HI")])
17125 (define_insn "*strsetqi_1"
17126   [(set (mem:QI (match_operand:SI 1 "register_operand" "0"))
17127         (match_operand:QI 2 "register_operand" "a"))
17128    (set (match_operand:SI 0 "register_operand" "=D")
17129         (plus:SI (match_dup 1)
17130                  (const_int 1)))
17131    (use (reg:SI DIRFLAG_REG))]
17132   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17133   "stosb"
17134   [(set_attr "type" "str")
17135    (set_attr "memory" "store")
17136    (set_attr "mode" "QI")])
17138 (define_insn "*strsetqi_rex_1"
17139   [(set (mem:QI (match_operand:DI 1 "register_operand" "0"))
17140         (match_operand:QI 2 "register_operand" "a"))
17141    (set (match_operand:DI 0 "register_operand" "=D")
17142         (plus:DI (match_dup 1)
17143                  (const_int 1)))
17144    (use (reg:SI DIRFLAG_REG))]
17145   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17146   "stosb"
17147   [(set_attr "type" "str")
17148    (set_attr "memory" "store")
17149    (set_attr "mode" "QI")])
17151 (define_expand "rep_stos"
17152   [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
17153               (set (match_operand 0 "register_operand" "")
17154                    (match_operand 4 "" ""))
17155               (set (match_operand 2 "memory_operand" "") (const_int 0))
17156               (use (match_operand 3 "register_operand" ""))
17157               (use (match_dup 1))
17158               (use (reg:SI DIRFLAG_REG))])]
17159   ""
17160   "")
17162 (define_insn "*rep_stosdi_rex64"
17163   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17164    (set (match_operand:DI 0 "register_operand" "=D") 
17165         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
17166                             (const_int 3))
17167                  (match_operand:DI 3 "register_operand" "0")))
17168    (set (mem:BLK (match_dup 3))
17169         (const_int 0))
17170    (use (match_operand:DI 2 "register_operand" "a"))
17171    (use (match_dup 4))
17172    (use (reg:SI DIRFLAG_REG))]
17173   "TARGET_64BIT"
17174   "{rep\;stosq|rep stosq}"
17175   [(set_attr "type" "str")
17176    (set_attr "prefix_rep" "1")
17177    (set_attr "memory" "store")
17178    (set_attr "mode" "DI")])
17180 (define_insn "*rep_stossi"
17181   [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
17182    (set (match_operand:SI 0 "register_operand" "=D") 
17183         (plus:SI (ashift:SI (match_operand:SI 4 "register_operand" "1")
17184                             (const_int 2))
17185                  (match_operand:SI 3 "register_operand" "0")))
17186    (set (mem:BLK (match_dup 3))
17187         (const_int 0))
17188    (use (match_operand:SI 2 "register_operand" "a"))
17189    (use (match_dup 4))
17190    (use (reg:SI DIRFLAG_REG))]
17191   "!TARGET_64BIT"
17192   "{rep\;stosl|rep stosd}"
17193   [(set_attr "type" "str")
17194    (set_attr "prefix_rep" "1")
17195    (set_attr "memory" "store")
17196    (set_attr "mode" "SI")])
17198 (define_insn "*rep_stossi_rex64"
17199   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17200    (set (match_operand:DI 0 "register_operand" "=D") 
17201         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
17202                             (const_int 2))
17203                  (match_operand:DI 3 "register_operand" "0")))
17204    (set (mem:BLK (match_dup 3))
17205         (const_int 0))
17206    (use (match_operand:SI 2 "register_operand" "a"))
17207    (use (match_dup 4))
17208    (use (reg:SI DIRFLAG_REG))]
17209   "TARGET_64BIT"
17210   "{rep\;stosl|rep stosd}"
17211   [(set_attr "type" "str")
17212    (set_attr "prefix_rep" "1")
17213    (set_attr "memory" "store")
17214    (set_attr "mode" "SI")])
17216 (define_insn "*rep_stosqi"
17217   [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
17218    (set (match_operand:SI 0 "register_operand" "=D") 
17219         (plus:SI (match_operand:SI 3 "register_operand" "0")
17220                  (match_operand:SI 4 "register_operand" "1")))
17221    (set (mem:BLK (match_dup 3))
17222         (const_int 0))
17223    (use (match_operand:QI 2 "register_operand" "a"))
17224    (use (match_dup 4))
17225    (use (reg:SI DIRFLAG_REG))]
17226   "!TARGET_64BIT"
17227   "{rep\;stosb|rep stosb}"
17228   [(set_attr "type" "str")
17229    (set_attr "prefix_rep" "1")
17230    (set_attr "memory" "store")
17231    (set_attr "mode" "QI")])
17233 (define_insn "*rep_stosqi_rex64"
17234   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17235    (set (match_operand:DI 0 "register_operand" "=D") 
17236         (plus:DI (match_operand:DI 3 "register_operand" "0")
17237                  (match_operand:DI 4 "register_operand" "1")))
17238    (set (mem:BLK (match_dup 3))
17239         (const_int 0))
17240    (use (match_operand:QI 2 "register_operand" "a"))
17241    (use (match_dup 4))
17242    (use (reg:SI DIRFLAG_REG))]
17243   "TARGET_64BIT"
17244   "{rep\;stosb|rep stosb}"
17245   [(set_attr "type" "str")
17246    (set_attr "prefix_rep" "1")
17247    (set_attr "memory" "store")
17248    (set_attr "mode" "QI")])
17250 (define_expand "cmpstrsi"
17251   [(set (match_operand:SI 0 "register_operand" "")
17252         (compare:SI (match_operand:BLK 1 "general_operand" "")
17253                     (match_operand:BLK 2 "general_operand" "")))
17254    (use (match_operand 3 "general_operand" ""))
17255    (use (match_operand 4 "immediate_operand" ""))]
17256   "! optimize_size || TARGET_INLINE_ALL_STRINGOPS"
17258   rtx addr1, addr2, out, outlow, count, countreg, align;
17260   /* Can't use this if the user has appropriated esi or edi.  */
17261   if (global_regs[4] || global_regs[5])
17262     FAIL;
17264   out = operands[0];
17265   if (GET_CODE (out) != REG)
17266     out = gen_reg_rtx (SImode);
17268   addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
17269   addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
17270   if (addr1 != XEXP (operands[1], 0))
17271     operands[1] = replace_equiv_address_nv (operands[1], addr1);
17272   if (addr2 != XEXP (operands[2], 0))
17273     operands[2] = replace_equiv_address_nv (operands[2], addr2);
17275   count = operands[3];
17276   countreg = ix86_zero_extend_to_Pmode (count);
17278   /* %%% Iff we are testing strict equality, we can use known alignment
17279      to good advantage.  This may be possible with combine, particularly
17280      once cc0 is dead.  */
17281   align = operands[4];
17283   emit_insn (gen_cld ());
17284   if (GET_CODE (count) == CONST_INT)
17285     {
17286       if (INTVAL (count) == 0)
17287         {
17288           emit_move_insn (operands[0], const0_rtx);
17289           DONE;
17290         }
17291       emit_insn (gen_cmpstrqi_nz_1 (addr1, addr2, countreg, align,
17292                                     operands[1], operands[2]));
17293     }
17294   else
17295     {
17296       if (TARGET_64BIT)
17297         emit_insn (gen_cmpdi_1_rex64 (countreg, countreg));
17298       else
17299         emit_insn (gen_cmpsi_1 (countreg, countreg));
17300       emit_insn (gen_cmpstrqi_1 (addr1, addr2, countreg, align,
17301                                  operands[1], operands[2]));
17302     }
17304   outlow = gen_lowpart (QImode, out);
17305   emit_insn (gen_cmpintqi (outlow));
17306   emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
17308   if (operands[0] != out)
17309     emit_move_insn (operands[0], out);
17311   DONE;
17314 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
17316 (define_expand "cmpintqi"
17317   [(set (match_dup 1)
17318         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
17319    (set (match_dup 2)
17320         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
17321    (parallel [(set (match_operand:QI 0 "register_operand" "")
17322                    (minus:QI (match_dup 1)
17323                              (match_dup 2)))
17324               (clobber (reg:CC FLAGS_REG))])]
17325   ""
17326   "operands[1] = gen_reg_rtx (QImode);
17327    operands[2] = gen_reg_rtx (QImode);")
17329 ;; memcmp recognizers.  The `cmpsb' opcode does nothing if the count is
17330 ;; zero.  Emit extra code to make sure that a zero-length compare is EQ.
17332 (define_expand "cmpstrqi_nz_1"
17333   [(parallel [(set (reg:CC FLAGS_REG)
17334                    (compare:CC (match_operand 4 "memory_operand" "")
17335                                (match_operand 5 "memory_operand" "")))
17336               (use (match_operand 2 "register_operand" ""))
17337               (use (match_operand:SI 3 "immediate_operand" ""))
17338               (use (reg:SI DIRFLAG_REG))
17339               (clobber (match_operand 0 "register_operand" ""))
17340               (clobber (match_operand 1 "register_operand" ""))
17341               (clobber (match_dup 2))])]
17342   ""
17343   "")
17345 (define_insn "*cmpstrqi_nz_1"
17346   [(set (reg:CC FLAGS_REG)
17347         (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
17348                     (mem:BLK (match_operand:SI 5 "register_operand" "1"))))
17349    (use (match_operand:SI 6 "register_operand" "2"))
17350    (use (match_operand:SI 3 "immediate_operand" "i"))
17351    (use (reg:SI DIRFLAG_REG))
17352    (clobber (match_operand:SI 0 "register_operand" "=S"))
17353    (clobber (match_operand:SI 1 "register_operand" "=D"))
17354    (clobber (match_operand:SI 2 "register_operand" "=c"))]
17355   "!TARGET_64BIT"
17356   "repz{\;| }cmpsb"
17357   [(set_attr "type" "str")
17358    (set_attr "mode" "QI")
17359    (set_attr "prefix_rep" "1")])
17361 (define_insn "*cmpstrqi_nz_rex_1"
17362   [(set (reg:CC FLAGS_REG)
17363         (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
17364                     (mem:BLK (match_operand:DI 5 "register_operand" "1"))))
17365    (use (match_operand:DI 6 "register_operand" "2"))
17366    (use (match_operand:SI 3 "immediate_operand" "i"))
17367    (use (reg:SI DIRFLAG_REG))
17368    (clobber (match_operand:DI 0 "register_operand" "=S"))
17369    (clobber (match_operand:DI 1 "register_operand" "=D"))
17370    (clobber (match_operand:DI 2 "register_operand" "=c"))]
17371   "TARGET_64BIT"
17372   "repz{\;| }cmpsb"
17373   [(set_attr "type" "str")
17374    (set_attr "mode" "QI")
17375    (set_attr "prefix_rep" "1")])
17377 ;; The same, but the count is not known to not be zero.
17379 (define_expand "cmpstrqi_1"
17380   [(parallel [(set (reg:CC FLAGS_REG)
17381                 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
17382                                      (const_int 0))
17383                   (compare:CC (match_operand 4 "memory_operand" "")
17384                               (match_operand 5 "memory_operand" ""))
17385                   (const_int 0)))
17386               (use (match_operand:SI 3 "immediate_operand" ""))
17387               (use (reg:CC FLAGS_REG))
17388               (use (reg:SI DIRFLAG_REG))
17389               (clobber (match_operand 0 "register_operand" ""))
17390               (clobber (match_operand 1 "register_operand" ""))
17391               (clobber (match_dup 2))])]
17392   ""
17393   "")
17395 (define_insn "*cmpstrqi_1"
17396   [(set (reg:CC FLAGS_REG)
17397         (if_then_else:CC (ne (match_operand:SI 6 "register_operand" "2")
17398                              (const_int 0))
17399           (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
17400                       (mem:BLK (match_operand:SI 5 "register_operand" "1")))
17401           (const_int 0)))
17402    (use (match_operand:SI 3 "immediate_operand" "i"))
17403    (use (reg:CC FLAGS_REG))
17404    (use (reg:SI DIRFLAG_REG))
17405    (clobber (match_operand:SI 0 "register_operand" "=S"))
17406    (clobber (match_operand:SI 1 "register_operand" "=D"))
17407    (clobber (match_operand:SI 2 "register_operand" "=c"))]
17408   "!TARGET_64BIT"
17409   "repz{\;| }cmpsb"
17410   [(set_attr "type" "str")
17411    (set_attr "mode" "QI")
17412    (set_attr "prefix_rep" "1")])
17414 (define_insn "*cmpstrqi_rex_1"
17415   [(set (reg:CC FLAGS_REG)
17416         (if_then_else:CC (ne (match_operand:DI 6 "register_operand" "2")
17417                              (const_int 0))
17418           (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
17419                       (mem:BLK (match_operand:DI 5 "register_operand" "1")))
17420           (const_int 0)))
17421    (use (match_operand:SI 3 "immediate_operand" "i"))
17422    (use (reg:CC FLAGS_REG))
17423    (use (reg:SI DIRFLAG_REG))
17424    (clobber (match_operand:DI 0 "register_operand" "=S"))
17425    (clobber (match_operand:DI 1 "register_operand" "=D"))
17426    (clobber (match_operand:DI 2 "register_operand" "=c"))]
17427   "TARGET_64BIT"
17428   "repz{\;| }cmpsb"
17429   [(set_attr "type" "str")
17430    (set_attr "mode" "QI")
17431    (set_attr "prefix_rep" "1")])
17433 (define_expand "strlensi"
17434   [(set (match_operand:SI 0 "register_operand" "")
17435         (unspec:SI [(match_operand:BLK 1 "general_operand" "")
17436                     (match_operand:QI 2 "immediate_operand" "")
17437                     (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
17438   ""
17440  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
17441    DONE;
17442  else
17443    FAIL;
17446 (define_expand "strlendi"
17447   [(set (match_operand:DI 0 "register_operand" "")
17448         (unspec:DI [(match_operand:BLK 1 "general_operand" "")
17449                     (match_operand:QI 2 "immediate_operand" "")
17450                     (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
17451   ""
17453  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
17454    DONE;
17455  else
17456    FAIL;
17459 (define_expand "strlenqi_1"
17460   [(parallel [(set (match_operand 0 "register_operand" "") (match_operand 2 "" ""))
17461               (use (reg:SI DIRFLAG_REG))
17462               (clobber (match_operand 1 "register_operand" ""))
17463               (clobber (reg:CC FLAGS_REG))])]
17464   ""
17465   "")
17467 (define_insn "*strlenqi_1"
17468   [(set (match_operand:SI 0 "register_operand" "=&c")
17469         (unspec:SI [(mem:BLK (match_operand:SI 5 "register_operand" "1"))
17470                     (match_operand:QI 2 "register_operand" "a")
17471                     (match_operand:SI 3 "immediate_operand" "i")
17472                     (match_operand:SI 4 "register_operand" "0")] UNSPEC_SCAS))
17473    (use (reg:SI DIRFLAG_REG))
17474    (clobber (match_operand:SI 1 "register_operand" "=D"))
17475    (clobber (reg:CC FLAGS_REG))]
17476   "!TARGET_64BIT"
17477   "repnz{\;| }scasb"
17478   [(set_attr "type" "str")
17479    (set_attr "mode" "QI")
17480    (set_attr "prefix_rep" "1")])
17482 (define_insn "*strlenqi_rex_1"
17483   [(set (match_operand:DI 0 "register_operand" "=&c")
17484         (unspec:DI [(mem:BLK (match_operand:DI 5 "register_operand" "1"))
17485                     (match_operand:QI 2 "register_operand" "a")
17486                     (match_operand:DI 3 "immediate_operand" "i")
17487                     (match_operand:DI 4 "register_operand" "0")] UNSPEC_SCAS))
17488    (use (reg:SI DIRFLAG_REG))
17489    (clobber (match_operand:DI 1 "register_operand" "=D"))
17490    (clobber (reg:CC FLAGS_REG))]
17491   "TARGET_64BIT"
17492   "repnz{\;| }scasb"
17493   [(set_attr "type" "str")
17494    (set_attr "mode" "QI")
17495    (set_attr "prefix_rep" "1")])
17497 ;; Peephole optimizations to clean up after cmpstr*.  This should be
17498 ;; handled in combine, but it is not currently up to the task.
17499 ;; When used for their truth value, the cmpstr* expanders generate
17500 ;; code like this:
17502 ;;   repz cmpsb
17503 ;;   seta       %al
17504 ;;   setb       %dl
17505 ;;   cmpb       %al, %dl
17506 ;;   jcc        label
17508 ;; The intermediate three instructions are unnecessary.
17510 ;; This one handles cmpstr*_nz_1...
17511 (define_peephole2
17512   [(parallel[
17513      (set (reg:CC FLAGS_REG)
17514           (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
17515                       (mem:BLK (match_operand 5 "register_operand" ""))))
17516      (use (match_operand 6 "register_operand" ""))
17517      (use (match_operand:SI 3 "immediate_operand" ""))
17518      (use (reg:SI DIRFLAG_REG))
17519      (clobber (match_operand 0 "register_operand" ""))
17520      (clobber (match_operand 1 "register_operand" ""))
17521      (clobber (match_operand 2 "register_operand" ""))])
17522    (set (match_operand:QI 7 "register_operand" "")
17523         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
17524    (set (match_operand:QI 8 "register_operand" "")
17525         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
17526    (set (reg FLAGS_REG)
17527         (compare (match_dup 7) (match_dup 8)))
17528   ]
17529   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
17530   [(parallel[
17531      (set (reg:CC FLAGS_REG)
17532           (compare:CC (mem:BLK (match_dup 4))
17533                       (mem:BLK (match_dup 5))))
17534      (use (match_dup 6))
17535      (use (match_dup 3))
17536      (use (reg:SI DIRFLAG_REG))
17537      (clobber (match_dup 0))
17538      (clobber (match_dup 1))
17539      (clobber (match_dup 2))])]
17540   "")
17542 ;; ...and this one handles cmpstr*_1.
17543 (define_peephole2
17544   [(parallel[
17545      (set (reg:CC FLAGS_REG)
17546           (if_then_else:CC (ne (match_operand 6 "register_operand" "")
17547                                (const_int 0))
17548             (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
17549                         (mem:BLK (match_operand 5 "register_operand" "")))
17550             (const_int 0)))
17551      (use (match_operand:SI 3 "immediate_operand" ""))
17552      (use (reg:CC FLAGS_REG))
17553      (use (reg:SI DIRFLAG_REG))
17554      (clobber (match_operand 0 "register_operand" ""))
17555      (clobber (match_operand 1 "register_operand" ""))
17556      (clobber (match_operand 2 "register_operand" ""))])
17557    (set (match_operand:QI 7 "register_operand" "")
17558         (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
17559    (set (match_operand:QI 8 "register_operand" "")
17560         (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
17561    (set (reg FLAGS_REG)
17562         (compare (match_dup 7) (match_dup 8)))
17563   ]
17564   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
17565   [(parallel[
17566      (set (reg:CC FLAGS_REG)
17567           (if_then_else:CC (ne (match_dup 6)
17568                                (const_int 0))
17569             (compare:CC (mem:BLK (match_dup 4))
17570                         (mem:BLK (match_dup 5)))
17571             (const_int 0)))
17572      (use (match_dup 3))
17573      (use (reg:CC FLAGS_REG))
17574      (use (reg:SI DIRFLAG_REG))
17575      (clobber (match_dup 0))
17576      (clobber (match_dup 1))
17577      (clobber (match_dup 2))])]
17578   "")
17582 ;; Conditional move instructions.
17584 (define_expand "movdicc"
17585   [(set (match_operand:DI 0 "register_operand" "")
17586         (if_then_else:DI (match_operand 1 "comparison_operator" "")
17587                          (match_operand:DI 2 "general_operand" "")
17588                          (match_operand:DI 3 "general_operand" "")))]
17589   "TARGET_64BIT"
17590   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
17592 (define_insn "x86_movdicc_0_m1_rex64"
17593   [(set (match_operand:DI 0 "register_operand" "=r")
17594         (if_then_else:DI (match_operand 1 "ix86_carry_flag_operator" "")
17595           (const_int -1)
17596           (const_int 0)))
17597    (clobber (reg:CC FLAGS_REG))]
17598   "TARGET_64BIT"
17599   "sbb{q}\t%0, %0"
17600   ; Since we don't have the proper number of operands for an alu insn,
17601   ; fill in all the blanks.
17602   [(set_attr "type" "alu")
17603    (set_attr "pent_pair" "pu")
17604    (set_attr "memory" "none")
17605    (set_attr "imm_disp" "false")
17606    (set_attr "mode" "DI")
17607    (set_attr "length_immediate" "0")])
17609 (define_insn "*movdicc_c_rex64"
17610   [(set (match_operand:DI 0 "register_operand" "=r,r")
17611         (if_then_else:DI (match_operator 1 "ix86_comparison_operator" 
17612                                 [(reg FLAGS_REG) (const_int 0)])
17613                       (match_operand:DI 2 "nonimmediate_operand" "rm,0")
17614                       (match_operand:DI 3 "nonimmediate_operand" "0,rm")))]
17615   "TARGET_64BIT && TARGET_CMOVE
17616    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17617   "@
17618    cmov%O2%C1\t{%2, %0|%0, %2}
17619    cmov%O2%c1\t{%3, %0|%0, %3}"
17620   [(set_attr "type" "icmov")
17621    (set_attr "mode" "DI")])
17623 (define_expand "movsicc"
17624   [(set (match_operand:SI 0 "register_operand" "")
17625         (if_then_else:SI (match_operand 1 "comparison_operator" "")
17626                          (match_operand:SI 2 "general_operand" "")
17627                          (match_operand:SI 3 "general_operand" "")))]
17628   ""
17629   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
17631 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
17632 ;; the register first winds up with `sbbl $0,reg', which is also weird.
17633 ;; So just document what we're doing explicitly.
17635 (define_insn "x86_movsicc_0_m1"
17636   [(set (match_operand:SI 0 "register_operand" "=r")
17637         (if_then_else:SI (match_operand 1 "ix86_carry_flag_operator" "")
17638           (const_int -1)
17639           (const_int 0)))
17640    (clobber (reg:CC FLAGS_REG))]
17641   ""
17642   "sbb{l}\t%0, %0"
17643   ; Since we don't have the proper number of operands for an alu insn,
17644   ; fill in all the blanks.
17645   [(set_attr "type" "alu")
17646    (set_attr "pent_pair" "pu")
17647    (set_attr "memory" "none")
17648    (set_attr "imm_disp" "false")
17649    (set_attr "mode" "SI")
17650    (set_attr "length_immediate" "0")])
17652 (define_insn "*movsicc_noc"
17653   [(set (match_operand:SI 0 "register_operand" "=r,r")
17654         (if_then_else:SI (match_operator 1 "ix86_comparison_operator" 
17655                                 [(reg FLAGS_REG) (const_int 0)])
17656                       (match_operand:SI 2 "nonimmediate_operand" "rm,0")
17657                       (match_operand:SI 3 "nonimmediate_operand" "0,rm")))]
17658   "TARGET_CMOVE
17659    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17660   "@
17661    cmov%O2%C1\t{%2, %0|%0, %2}
17662    cmov%O2%c1\t{%3, %0|%0, %3}"
17663   [(set_attr "type" "icmov")
17664    (set_attr "mode" "SI")])
17666 (define_expand "movhicc"
17667   [(set (match_operand:HI 0 "register_operand" "")
17668         (if_then_else:HI (match_operand 1 "comparison_operator" "")
17669                          (match_operand:HI 2 "general_operand" "")
17670                          (match_operand:HI 3 "general_operand" "")))]
17671   "TARGET_HIMODE_MATH"
17672   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
17674 (define_insn "*movhicc_noc"
17675   [(set (match_operand:HI 0 "register_operand" "=r,r")
17676         (if_then_else:HI (match_operator 1 "ix86_comparison_operator" 
17677                                 [(reg FLAGS_REG) (const_int 0)])
17678                       (match_operand:HI 2 "nonimmediate_operand" "rm,0")
17679                       (match_operand:HI 3 "nonimmediate_operand" "0,rm")))]
17680   "TARGET_CMOVE
17681    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17682   "@
17683    cmov%O2%C1\t{%2, %0|%0, %2}
17684    cmov%O2%c1\t{%3, %0|%0, %3}"
17685   [(set_attr "type" "icmov")
17686    (set_attr "mode" "HI")])
17688 (define_expand "movqicc"
17689   [(set (match_operand:QI 0 "register_operand" "")
17690         (if_then_else:QI (match_operand 1 "comparison_operator" "")
17691                          (match_operand:QI 2 "general_operand" "")
17692                          (match_operand:QI 3 "general_operand" "")))]
17693   "TARGET_QIMODE_MATH"
17694   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
17696 (define_insn_and_split "*movqicc_noc"
17697   [(set (match_operand:QI 0 "register_operand" "=r,r")
17698         (if_then_else:QI (match_operator 1 "ix86_comparison_operator" 
17699                                 [(match_operand 4 "flags_reg_operand" "")
17700                                  (const_int 0)])
17701                       (match_operand:QI 2 "register_operand" "r,0")
17702                       (match_operand:QI 3 "register_operand" "0,r")))]
17703   "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
17704   "#"
17705   "&& reload_completed"
17706   [(set (match_dup 0)
17707         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
17708                       (match_dup 2)
17709                       (match_dup 3)))]
17710   "operands[0] = gen_lowpart (SImode, operands[0]);
17711    operands[2] = gen_lowpart (SImode, operands[2]);
17712    operands[3] = gen_lowpart (SImode, operands[3]);"
17713   [(set_attr "type" "icmov")
17714    (set_attr "mode" "SI")])
17716 (define_expand "movsfcc"
17717   [(set (match_operand:SF 0 "register_operand" "")
17718         (if_then_else:SF (match_operand 1 "comparison_operator" "")
17719                          (match_operand:SF 2 "register_operand" "")
17720                          (match_operand:SF 3 "register_operand" "")))]
17721   "(TARGET_80387 && TARGET_CMOVE) || TARGET_SSE_MATH"
17722   "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
17724 ;; These versions of min/max are aware of the instruction's behavior
17725 ;; wrt -0.0 and NaN inputs.  If we don't care about either, then we
17726 ;; should have used the smin/smax expanders in the first place.
17727 (define_insn "*movsfcc_1_sse_min"
17728   [(set (match_operand:SF 0 "register_operand" "=x")
17729         (if_then_else:SF
17730           (lt:SF (match_operand:SF 1 "register_operand" "0")
17731                  (match_operand:SF 2 "nonimmediate_operand" "xm"))
17732           (match_dup 1)
17733           (match_dup 2)))]
17734   "TARGET_SSE_MATH"
17735   "minss\t{%2, %0|%0, %2}"
17736   [(set_attr "type" "sseadd")
17737    (set_attr "mode" "SF")])
17739 (define_insn "*movsfcc_1_sse_max"
17740   [(set (match_operand:SF 0 "register_operand" "=x")
17741         (if_then_else:SF
17742           (lt:SF (match_operand:SF 2 "nonimmediate_operand" "xm")
17743                  (match_operand:SF 1 "nonimmediate_operand" "0"))
17744           (match_dup 1)
17745           (match_dup 2)))]
17746   "TARGET_SSE_MATH"
17747   "maxss\t{%2, %0|%0, %2}"
17748   [(set_attr "type" "sseadd")
17749    (set_attr "mode" "SF")])
17751 (define_insn_and_split "*movsfcc_1_sse"
17752   [(set (match_operand:SF 0 "register_operand" "=x,x,x")
17753         (if_then_else:SF
17754           (match_operator:SF 4 "sse_comparison_operator"
17755             [(match_operand:SF 5 "register_operand" "0,0,0")
17756              (match_operand:SF 6 "nonimmediate_operand" "xm,xm,xm")])
17757           (match_operand:SF 2 "reg_or_0_operand" "C,x,x")
17758           (match_operand:SF 3 "reg_or_0_operand" "x,C,x")))
17759    (clobber (match_scratch:V4SF 1 "=&x,&x,&x"))]
17760   "TARGET_SSE_MATH"
17761   "#"
17762   "&& reload_completed"
17763   [(const_int 0)]
17765   ix86_split_sse_movcc (operands);
17766   DONE;
17769 (define_insn "*movsfcc_1_387"
17770   [(set (match_operand:SF 0 "register_operand" "=f#r,f#r,r#f,r#f")
17771         (if_then_else:SF (match_operator 1 "fcmov_comparison_operator" 
17772                                 [(reg FLAGS_REG) (const_int 0)])
17773                       (match_operand:SF 2 "nonimmediate_operand" "f#r,0,rm#f,0")
17774                       (match_operand:SF 3 "nonimmediate_operand" "0,f#r,0,rm#f")))]
17775   "TARGET_80387 && TARGET_CMOVE
17776    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17777   "@
17778    fcmov%F1\t{%2, %0|%0, %2}
17779    fcmov%f1\t{%3, %0|%0, %3}
17780    cmov%O2%C1\t{%2, %0|%0, %2}
17781    cmov%O2%c1\t{%3, %0|%0, %3}"
17782   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
17783    (set_attr "mode" "SF,SF,SI,SI")])
17785 (define_expand "movdfcc"
17786   [(set (match_operand:DF 0 "register_operand" "")
17787         (if_then_else:DF (match_operand 1 "comparison_operator" "")
17788                          (match_operand:DF 2 "register_operand" "")
17789                          (match_operand:DF 3 "register_operand" "")))]
17790   "(TARGET_80387 && TARGET_CMOVE) || (TARGET_SSE2 && TARGET_SSE_MATH)"
17791   "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
17793 ;; These versions of min/max are aware of the instruction's behavior
17794 ;; wrt -0.0 and NaN inputs.  If we don't care about either, then we
17795 ;; should have used the smin/smax expanders in the first place.
17796 (define_insn "*movdfcc_1_sse_min"
17797   [(set (match_operand:DF 0 "register_operand" "=x")
17798         (if_then_else:DF
17799           (lt:DF (match_operand:DF 1 "register_operand" "0")
17800                  (match_operand:DF 2 "nonimmediate_operand" "xm"))
17801           (match_dup 1)
17802           (match_dup 2)))]
17803   "TARGET_SSE2 && TARGET_SSE_MATH"
17804   "minsd\t{%2, %0|%0, %2}"
17805   [(set_attr "type" "sseadd")
17806    (set_attr "mode" "DF")])
17808 (define_insn "*movdfcc_1_sse_max"
17809   [(set (match_operand:DF 0 "register_operand" "=x")
17810         (if_then_else:DF
17811           (lt:DF (match_operand:DF 2 "nonimmediate_operand" "xm")
17812                  (match_operand:DF 1 "nonimmediate_operand" "0"))
17813           (match_dup 1)
17814           (match_dup 2)))]
17815   "TARGET_SSE2 && TARGET_SSE_MATH"
17816   "maxsd\t{%2, %0|%0, %2}"
17817   [(set_attr "type" "sseadd")
17818    (set_attr "mode" "DF")])
17820 (define_insn_and_split "*movdfcc_1_sse"
17821   [(set (match_operand:DF 0 "register_operand" "=x,x,x")
17822         (if_then_else:DF
17823           (match_operator:DF 4 "sse_comparison_operator"
17824             [(match_operand:DF 5 "register_operand" "0,0,0")
17825              (match_operand:DF 6 "nonimmediate_operand" "xm,xm,xm")])
17826           (match_operand:DF 2 "reg_or_0_operand" "C,x,x")
17827           (match_operand:DF 3 "reg_or_0_operand" "x,C,x")))
17828    (clobber (match_scratch:V2DF 1 "=&x,&x,&x"))]
17829   "TARGET_SSE2 && TARGET_SSE_MATH"
17830   "#"
17831   "&& reload_completed"
17832   [(const_int 0)]
17834   ix86_split_sse_movcc (operands);
17835   DONE;
17838 (define_insn "*movdfcc_1"
17839   [(set (match_operand:DF 0 "register_operand" "=f#r,f#r,&r#f,&r#f")
17840         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator" 
17841                                 [(reg FLAGS_REG) (const_int 0)])
17842                       (match_operand:DF 2 "nonimmediate_operand" "f#r,0,rm#f,0")
17843                       (match_operand:DF 3 "nonimmediate_operand" "0,f#r,0,rm#f")))]
17844   "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
17845    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17846   "@
17847    fcmov%F1\t{%2, %0|%0, %2}
17848    fcmov%f1\t{%3, %0|%0, %3}
17849    #
17850    #"
17851   [(set_attr "type" "fcmov,fcmov,multi,multi")
17852    (set_attr "mode" "DF")])
17854 (define_insn "*movdfcc_1_rex64"
17855   [(set (match_operand:DF 0 "register_operand" "=f#r,f#r,r#f,r#f")
17856         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator" 
17857                                 [(reg FLAGS_REG) (const_int 0)])
17858                       (match_operand:DF 2 "nonimmediate_operand" "f#r,0#r,rm#f,0#f")
17859                       (match_operand:DF 3 "nonimmediate_operand" "0#r,f#r,0#f,rm#f")))]
17860   "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
17861    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17862   "@
17863    fcmov%F1\t{%2, %0|%0, %2}
17864    fcmov%f1\t{%3, %0|%0, %3}
17865    cmov%O2%C1\t{%2, %0|%0, %2}
17866    cmov%O2%c1\t{%3, %0|%0, %3}"
17867   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
17868    (set_attr "mode" "DF")])
17870 (define_split
17871   [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand" "")
17872         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator" 
17873                                 [(match_operand 4 "flags_reg_operand" "")
17874                                  (const_int 0)])
17875                       (match_operand:DF 2 "nonimmediate_operand" "")
17876                       (match_operand:DF 3 "nonimmediate_operand" "")))]
17877   "!TARGET_64BIT && reload_completed"
17878   [(set (match_dup 2)
17879         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
17880                       (match_dup 5)
17881                       (match_dup 7)))
17882    (set (match_dup 3)
17883         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
17884                       (match_dup 6)
17885                       (match_dup 8)))]
17886   "split_di (operands+2, 1, operands+5, operands+6);
17887    split_di (operands+3, 1, operands+7, operands+8);
17888    split_di (operands, 1, operands+2, operands+3);")
17890 (define_expand "movxfcc"
17891   [(set (match_operand:XF 0 "register_operand" "")
17892         (if_then_else:XF (match_operand 1 "comparison_operator" "")
17893                          (match_operand:XF 2 "register_operand" "")
17894                          (match_operand:XF 3 "register_operand" "")))]
17895   "TARGET_80387 && TARGET_CMOVE"
17896   "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
17898 (define_insn "*movxfcc_1"
17899   [(set (match_operand:XF 0 "register_operand" "=f,f")
17900         (if_then_else:XF (match_operator 1 "fcmov_comparison_operator" 
17901                                 [(reg FLAGS_REG) (const_int 0)])
17902                       (match_operand:XF 2 "register_operand" "f,0")
17903                       (match_operand:XF 3 "register_operand" "0,f")))]
17904   "TARGET_80387 && TARGET_CMOVE"
17905   "@
17906    fcmov%F1\t{%2, %0|%0, %2}
17907    fcmov%f1\t{%3, %0|%0, %3}"
17908   [(set_attr "type" "fcmov")
17909    (set_attr "mode" "XF")])
17911 ;; These versions of the min/max patterns are intentionally ignorant of
17912 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
17913 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
17914 ;; are undefined in this condition, we're certain this is correct.
17916 (define_insn "sminsf3"
17917   [(set (match_operand:SF 0 "register_operand" "=x")
17918         (smin:SF (match_operand:SF 1 "nonimmediate_operand" "%0")
17919                  (match_operand:SF 2 "nonimmediate_operand" "xm")))]
17920   "TARGET_SSE_MATH"
17921   "minss\t{%2, %0|%0, %2}"
17922   [(set_attr "type" "sseadd")
17923    (set_attr "mode" "SF")])
17925 (define_insn "smaxsf3"
17926   [(set (match_operand:SF 0 "register_operand" "=x")
17927         (smax:SF (match_operand:SF 1 "nonimmediate_operand" "%0")
17928                  (match_operand:SF 2 "nonimmediate_operand" "xm")))]
17929   "TARGET_SSE_MATH"
17930   "maxss\t{%2, %0|%0, %2}"
17931   [(set_attr "type" "sseadd")
17932    (set_attr "mode" "SF")])
17934 (define_insn "smindf3"
17935   [(set (match_operand:DF 0 "register_operand" "=x")
17936         (smin:DF (match_operand:DF 1 "nonimmediate_operand" "%0")
17937                  (match_operand:DF 2 "nonimmediate_operand" "xm")))]
17938   "TARGET_SSE2 && TARGET_SSE_MATH"
17939   "minsd\t{%2, %0|%0, %2}"
17940   [(set_attr "type" "sseadd")
17941    (set_attr "mode" "DF")])
17943 (define_insn "smaxdf3"
17944   [(set (match_operand:DF 0 "register_operand" "=x")
17945         (smax:DF (match_operand:DF 1 "nonimmediate_operand" "%0")
17946                  (match_operand:DF 2 "nonimmediate_operand" "xm")))]
17947   "TARGET_SSE2 && TARGET_SSE_MATH"
17948   "maxsd\t{%2, %0|%0, %2}"
17949   [(set_attr "type" "sseadd")
17950    (set_attr "mode" "DF")])
17952 ;; Conditional addition patterns
17953 (define_expand "addqicc"
17954   [(match_operand:QI 0 "register_operand" "")
17955    (match_operand 1 "comparison_operator" "")
17956    (match_operand:QI 2 "register_operand" "")
17957    (match_operand:QI 3 "const_int_operand" "")]
17958   ""
17959   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
17961 (define_expand "addhicc"
17962   [(match_operand:HI 0 "register_operand" "")
17963    (match_operand 1 "comparison_operator" "")
17964    (match_operand:HI 2 "register_operand" "")
17965    (match_operand:HI 3 "const_int_operand" "")]
17966   ""
17967   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
17969 (define_expand "addsicc"
17970   [(match_operand:SI 0 "register_operand" "")
17971    (match_operand 1 "comparison_operator" "")
17972    (match_operand:SI 2 "register_operand" "")
17973    (match_operand:SI 3 "const_int_operand" "")]
17974   ""
17975   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
17977 (define_expand "adddicc"
17978   [(match_operand:DI 0 "register_operand" "")
17979    (match_operand 1 "comparison_operator" "")
17980    (match_operand:DI 2 "register_operand" "")
17981    (match_operand:DI 3 "const_int_operand" "")]
17982   "TARGET_64BIT"
17983   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
17986 ;; Misc patterns (?)
17988 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
17989 ;; Otherwise there will be nothing to keep
17990 ;; 
17991 ;; [(set (reg ebp) (reg esp))]
17992 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
17993 ;;  (clobber (eflags)]
17994 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
17996 ;; in proper program order.
17997 (define_insn "pro_epilogue_adjust_stack_1"
17998   [(set (match_operand:SI 0 "register_operand" "=r,r")
17999         (plus:SI (match_operand:SI 1 "register_operand" "0,r")
18000                  (match_operand:SI 2 "immediate_operand" "i,i")))
18001    (clobber (reg:CC FLAGS_REG))
18002    (clobber (mem:BLK (scratch)))]
18003   "!TARGET_64BIT"
18005   switch (get_attr_type (insn))
18006     {
18007     case TYPE_IMOV:
18008       return "mov{l}\t{%1, %0|%0, %1}";
18010     case TYPE_ALU:
18011       if (GET_CODE (operands[2]) == CONST_INT
18012           && (INTVAL (operands[2]) == 128
18013               || (INTVAL (operands[2]) < 0
18014                   && INTVAL (operands[2]) != -128)))
18015         {
18016           operands[2] = GEN_INT (-INTVAL (operands[2]));
18017           return "sub{l}\t{%2, %0|%0, %2}";
18018         }
18019       return "add{l}\t{%2, %0|%0, %2}";
18021     case TYPE_LEA:
18022       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
18023       return "lea{l}\t{%a2, %0|%0, %a2}";
18025     default:
18026       abort ();
18027     }
18029   [(set (attr "type")
18030         (cond [(eq_attr "alternative" "0")
18031                  (const_string "alu")
18032                (match_operand:SI 2 "const0_operand" "")
18033                  (const_string "imov")
18034               ]
18035               (const_string "lea")))
18036    (set_attr "mode" "SI")])
18038 (define_insn "pro_epilogue_adjust_stack_rex64"
18039   [(set (match_operand:DI 0 "register_operand" "=r,r")
18040         (plus:DI (match_operand:DI 1 "register_operand" "0,r")
18041                  (match_operand:DI 2 "x86_64_immediate_operand" "e,e")))
18042    (clobber (reg:CC FLAGS_REG))
18043    (clobber (mem:BLK (scratch)))]
18044   "TARGET_64BIT"
18046   switch (get_attr_type (insn))
18047     {
18048     case TYPE_IMOV:
18049       return "mov{q}\t{%1, %0|%0, %1}";
18051     case TYPE_ALU:
18052       if (GET_CODE (operands[2]) == CONST_INT
18053           /* Avoid overflows.  */
18054           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
18055           && (INTVAL (operands[2]) == 128
18056               || (INTVAL (operands[2]) < 0
18057                   && INTVAL (operands[2]) != -128)))
18058         {
18059           operands[2] = GEN_INT (-INTVAL (operands[2]));
18060           return "sub{q}\t{%2, %0|%0, %2}";
18061         }
18062       return "add{q}\t{%2, %0|%0, %2}";
18064     case TYPE_LEA:
18065       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
18066       return "lea{q}\t{%a2, %0|%0, %a2}";
18068     default:
18069       abort ();
18070     }
18072   [(set (attr "type")
18073         (cond [(eq_attr "alternative" "0")
18074                  (const_string "alu")
18075                (match_operand:DI 2 "const0_operand" "")
18076                  (const_string "imov")
18077               ]
18078               (const_string "lea")))
18079    (set_attr "mode" "DI")])
18081 (define_insn "pro_epilogue_adjust_stack_rex64_2"
18082   [(set (match_operand:DI 0 "register_operand" "=r,r")
18083         (plus:DI (match_operand:DI 1 "register_operand" "0,r")
18084                  (match_operand:DI 3 "immediate_operand" "i,i")))
18085    (use (match_operand:DI 2 "register_operand" "r,r"))
18086    (clobber (reg:CC FLAGS_REG))
18087    (clobber (mem:BLK (scratch)))]
18088   "TARGET_64BIT"
18090   switch (get_attr_type (insn))
18091     {
18092     case TYPE_ALU:
18093       return "add{q}\t{%2, %0|%0, %2}";
18095     case TYPE_LEA:
18096       operands[2] = gen_rtx_PLUS (DImode, operands[1], operands[2]);
18097       return "lea{q}\t{%a2, %0|%0, %a2}";
18099     default:
18100       abort ();
18101     }
18103   [(set_attr "type" "alu,lea")
18104    (set_attr "mode" "DI")])
18106 (define_expand "allocate_stack_worker"
18107   [(match_operand:SI 0 "register_operand" "")]
18108   "TARGET_STACK_PROBE"
18110   if (reload_completed)
18111     {
18112       if (TARGET_64BIT)
18113         emit_insn (gen_allocate_stack_worker_rex64_postreload (operands[0]));
18114       else
18115         emit_insn (gen_allocate_stack_worker_postreload (operands[0]));
18116     }
18117   else
18118     {
18119       if (TARGET_64BIT)
18120         emit_insn (gen_allocate_stack_worker_rex64 (operands[0]));
18121       else
18122         emit_insn (gen_allocate_stack_worker_1 (operands[0]));
18123     }
18124   DONE;
18127 (define_insn "allocate_stack_worker_1"
18128   [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")]
18129     UNSPECV_STACK_PROBE)
18130    (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0)))
18131    (clobber (match_scratch:SI 1 "=0"))
18132    (clobber (reg:CC FLAGS_REG))]
18133   "!TARGET_64BIT && TARGET_STACK_PROBE"
18134   "call\t__alloca"
18135   [(set_attr "type" "multi")
18136    (set_attr "length" "5")])
18138 (define_expand "allocate_stack_worker_postreload"
18139   [(parallel [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")]
18140                                     UNSPECV_STACK_PROBE)
18141               (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0)))
18142               (clobber (match_dup 0))
18143               (clobber (reg:CC FLAGS_REG))])]
18144   ""
18145   "")
18147 (define_insn "allocate_stack_worker_rex64"
18148   [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")]
18149     UNSPECV_STACK_PROBE)
18150    (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0)))
18151    (clobber (match_scratch:DI 1 "=0"))
18152    (clobber (reg:CC FLAGS_REG))]
18153   "TARGET_64BIT && TARGET_STACK_PROBE"
18154   "call\t__alloca"
18155   [(set_attr "type" "multi")
18156    (set_attr "length" "5")])
18158 (define_expand "allocate_stack_worker_rex64_postreload"
18159   [(parallel [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")]
18160                                     UNSPECV_STACK_PROBE)
18161               (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0)))
18162               (clobber (match_dup 0))
18163               (clobber (reg:CC FLAGS_REG))])]
18164   ""
18165   "")
18167 (define_expand "allocate_stack"
18168   [(parallel [(set (match_operand:SI 0 "register_operand" "=r")
18169                    (minus:SI (reg:SI SP_REG)
18170                              (match_operand:SI 1 "general_operand" "")))
18171               (clobber (reg:CC FLAGS_REG))])
18172    (parallel [(set (reg:SI SP_REG)
18173                    (minus:SI (reg:SI SP_REG) (match_dup 1)))
18174               (clobber (reg:CC FLAGS_REG))])]
18175   "TARGET_STACK_PROBE"
18177 #ifdef CHECK_STACK_LIMIT
18178   if (GET_CODE (operands[1]) == CONST_INT
18179       && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
18180     emit_insn (gen_subsi3 (stack_pointer_rtx, stack_pointer_rtx,
18181                            operands[1]));
18182   else 
18183 #endif
18184     emit_insn (gen_allocate_stack_worker (copy_to_mode_reg (SImode,
18185                                                             operands[1])));
18187   emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
18188   DONE;
18191 (define_expand "builtin_setjmp_receiver"
18192   [(label_ref (match_operand 0 "" ""))]
18193   "!TARGET_64BIT && flag_pic"
18195   emit_insn (gen_set_got (pic_offset_table_rtx));
18196   DONE;
18199 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
18201 (define_split
18202   [(set (match_operand 0 "register_operand" "")
18203         (match_operator 3 "promotable_binary_operator"
18204            [(match_operand 1 "register_operand" "")
18205             (match_operand 2 "aligned_operand" "")]))
18206    (clobber (reg:CC FLAGS_REG))]
18207   "! TARGET_PARTIAL_REG_STALL && reload_completed
18208    && ((GET_MODE (operands[0]) == HImode 
18209         && ((!optimize_size && !TARGET_FAST_PREFIX)
18210             || GET_CODE (operands[2]) != CONST_INT
18211             || CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')))
18212        || (GET_MODE (operands[0]) == QImode 
18213            && (TARGET_PROMOTE_QImode || optimize_size)))"
18214   [(parallel [(set (match_dup 0)
18215                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
18216               (clobber (reg:CC FLAGS_REG))])]
18217   "operands[0] = gen_lowpart (SImode, operands[0]);
18218    operands[1] = gen_lowpart (SImode, operands[1]);
18219    if (GET_CODE (operands[3]) != ASHIFT)
18220      operands[2] = gen_lowpart (SImode, operands[2]);
18221    PUT_MODE (operands[3], SImode);")
18223 ; Promote the QImode tests, as i386 has encoding of the AND
18224 ; instruction with 32-bit sign-extended immediate and thus the
18225 ; instruction size is unchanged, except in the %eax case for
18226 ; which it is increased by one byte, hence the ! optimize_size.
18227 (define_split
18228   [(set (match_operand 0 "flags_reg_operand" "")
18229         (match_operator 2 "compare_operator"
18230           [(and (match_operand 3 "aligned_operand" "")
18231                 (match_operand 4 "const_int_operand" ""))
18232            (const_int 0)]))
18233    (set (match_operand 1 "register_operand" "")
18234         (and (match_dup 3) (match_dup 4)))]
18235   "! TARGET_PARTIAL_REG_STALL && reload_completed
18236    /* Ensure that the operand will remain sign-extended immediate.  */
18237    && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)
18238    && ! optimize_size
18239    && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
18240        || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))"
18241   [(parallel [(set (match_dup 0)
18242                    (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
18243                                     (const_int 0)]))
18244               (set (match_dup 1)
18245                    (and:SI (match_dup 3) (match_dup 4)))])]
18247   operands[4]
18248     = gen_int_mode (INTVAL (operands[4])
18249                     & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
18250   operands[1] = gen_lowpart (SImode, operands[1]);
18251   operands[3] = gen_lowpart (SImode, operands[3]);
18254 ; Don't promote the QImode tests, as i386 doesn't have encoding of
18255 ; the TEST instruction with 32-bit sign-extended immediate and thus
18256 ; the instruction size would at least double, which is not what we
18257 ; want even with ! optimize_size.
18258 (define_split
18259   [(set (match_operand 0 "flags_reg_operand" "")
18260         (match_operator 1 "compare_operator"
18261           [(and (match_operand:HI 2 "aligned_operand" "")
18262                 (match_operand:HI 3 "const_int_operand" ""))
18263            (const_int 0)]))]
18264   "! TARGET_PARTIAL_REG_STALL && reload_completed
18265    /* Ensure that the operand will remain sign-extended immediate.  */
18266    && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)
18267    && ! TARGET_FAST_PREFIX
18268    && ! optimize_size"
18269   [(set (match_dup 0)
18270         (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
18271                          (const_int 0)]))]
18273   operands[3]
18274     = gen_int_mode (INTVAL (operands[3])
18275                     & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
18276   operands[2] = gen_lowpart (SImode, operands[2]);
18279 (define_split
18280   [(set (match_operand 0 "register_operand" "")
18281         (neg (match_operand 1 "register_operand" "")))
18282    (clobber (reg:CC FLAGS_REG))]
18283   "! TARGET_PARTIAL_REG_STALL && reload_completed
18284    && (GET_MODE (operands[0]) == HImode
18285        || (GET_MODE (operands[0]) == QImode 
18286            && (TARGET_PROMOTE_QImode || optimize_size)))"
18287   [(parallel [(set (match_dup 0)
18288                    (neg:SI (match_dup 1)))
18289               (clobber (reg:CC FLAGS_REG))])]
18290   "operands[0] = gen_lowpart (SImode, operands[0]);
18291    operands[1] = gen_lowpart (SImode, operands[1]);")
18293 (define_split
18294   [(set (match_operand 0 "register_operand" "")
18295         (not (match_operand 1 "register_operand" "")))]
18296   "! TARGET_PARTIAL_REG_STALL && reload_completed
18297    && (GET_MODE (operands[0]) == HImode
18298        || (GET_MODE (operands[0]) == QImode 
18299            && (TARGET_PROMOTE_QImode || optimize_size)))"
18300   [(set (match_dup 0)
18301         (not:SI (match_dup 1)))]
18302   "operands[0] = gen_lowpart (SImode, operands[0]);
18303    operands[1] = gen_lowpart (SImode, operands[1]);")
18305 (define_split 
18306   [(set (match_operand 0 "register_operand" "")
18307         (if_then_else (match_operator 1 "comparison_operator" 
18308                                 [(reg FLAGS_REG) (const_int 0)])
18309                       (match_operand 2 "register_operand" "")
18310                       (match_operand 3 "register_operand" "")))]
18311   "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE
18312    && (GET_MODE (operands[0]) == HImode
18313        || (GET_MODE (operands[0]) == QImode 
18314            && (TARGET_PROMOTE_QImode || optimize_size)))"
18315   [(set (match_dup 0)
18316         (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
18317   "operands[0] = gen_lowpart (SImode, operands[0]);
18318    operands[2] = gen_lowpart (SImode, operands[2]);
18319    operands[3] = gen_lowpart (SImode, operands[3]);")
18320                         
18322 ;; RTL Peephole optimizations, run before sched2.  These primarily look to
18323 ;; transform a complex memory operation into two memory to register operations.
18325 ;; Don't push memory operands
18326 (define_peephole2
18327   [(set (match_operand:SI 0 "push_operand" "")
18328         (match_operand:SI 1 "memory_operand" ""))
18329    (match_scratch:SI 2 "r")]
18330   "! optimize_size && ! TARGET_PUSH_MEMORY"
18331   [(set (match_dup 2) (match_dup 1))
18332    (set (match_dup 0) (match_dup 2))]
18333   "")
18335 (define_peephole2
18336   [(set (match_operand:DI 0 "push_operand" "")
18337         (match_operand:DI 1 "memory_operand" ""))
18338    (match_scratch:DI 2 "r")]
18339   "! optimize_size && ! TARGET_PUSH_MEMORY"
18340   [(set (match_dup 2) (match_dup 1))
18341    (set (match_dup 0) (match_dup 2))]
18342   "")
18344 ;; We need to handle SFmode only, because DFmode and XFmode is split to
18345 ;; SImode pushes.
18346 (define_peephole2
18347   [(set (match_operand:SF 0 "push_operand" "")
18348         (match_operand:SF 1 "memory_operand" ""))
18349    (match_scratch:SF 2 "r")]
18350   "! optimize_size && ! TARGET_PUSH_MEMORY"
18351   [(set (match_dup 2) (match_dup 1))
18352    (set (match_dup 0) (match_dup 2))]
18353   "")
18355 (define_peephole2
18356   [(set (match_operand:HI 0 "push_operand" "")
18357         (match_operand:HI 1 "memory_operand" ""))
18358    (match_scratch:HI 2 "r")]
18359   "! optimize_size && ! TARGET_PUSH_MEMORY"
18360   [(set (match_dup 2) (match_dup 1))
18361    (set (match_dup 0) (match_dup 2))]
18362   "")
18364 (define_peephole2
18365   [(set (match_operand:QI 0 "push_operand" "")
18366         (match_operand:QI 1 "memory_operand" ""))
18367    (match_scratch:QI 2 "q")]
18368   "! optimize_size && ! TARGET_PUSH_MEMORY"
18369   [(set (match_dup 2) (match_dup 1))
18370    (set (match_dup 0) (match_dup 2))]
18371   "")
18373 ;; Don't move an immediate directly to memory when the instruction
18374 ;; gets too big.
18375 (define_peephole2
18376   [(match_scratch:SI 1 "r")
18377    (set (match_operand:SI 0 "memory_operand" "")
18378         (const_int 0))]
18379   "! optimize_size
18380    && ! TARGET_USE_MOV0
18381    && TARGET_SPLIT_LONG_MOVES
18382    && get_attr_length (insn) >= ix86_cost->large_insn
18383    && peep2_regno_dead_p (0, FLAGS_REG)"
18384   [(parallel [(set (match_dup 1) (const_int 0))
18385               (clobber (reg:CC FLAGS_REG))])
18386    (set (match_dup 0) (match_dup 1))]
18387   "")
18389 (define_peephole2
18390   [(match_scratch:HI 1 "r")
18391    (set (match_operand:HI 0 "memory_operand" "")
18392         (const_int 0))]
18393   "! optimize_size
18394    && ! TARGET_USE_MOV0
18395    && TARGET_SPLIT_LONG_MOVES
18396    && get_attr_length (insn) >= ix86_cost->large_insn
18397    && peep2_regno_dead_p (0, FLAGS_REG)"
18398   [(parallel [(set (match_dup 2) (const_int 0))
18399               (clobber (reg:CC FLAGS_REG))])
18400    (set (match_dup 0) (match_dup 1))]
18401   "operands[2] = gen_lowpart (SImode, operands[1]);")
18403 (define_peephole2
18404   [(match_scratch:QI 1 "q")
18405    (set (match_operand:QI 0 "memory_operand" "")
18406         (const_int 0))]
18407   "! optimize_size
18408    && ! TARGET_USE_MOV0
18409    && TARGET_SPLIT_LONG_MOVES
18410    && get_attr_length (insn) >= ix86_cost->large_insn
18411    && peep2_regno_dead_p (0, FLAGS_REG)"
18412   [(parallel [(set (match_dup 2) (const_int 0))
18413               (clobber (reg:CC FLAGS_REG))])
18414    (set (match_dup 0) (match_dup 1))]
18415   "operands[2] = gen_lowpart (SImode, operands[1]);")
18417 (define_peephole2
18418   [(match_scratch:SI 2 "r")
18419    (set (match_operand:SI 0 "memory_operand" "")
18420         (match_operand:SI 1 "immediate_operand" ""))]
18421   "! optimize_size
18422    && get_attr_length (insn) >= ix86_cost->large_insn
18423    && TARGET_SPLIT_LONG_MOVES"
18424   [(set (match_dup 2) (match_dup 1))
18425    (set (match_dup 0) (match_dup 2))]
18426   "")
18428 (define_peephole2
18429   [(match_scratch:HI 2 "r")
18430    (set (match_operand:HI 0 "memory_operand" "")
18431         (match_operand:HI 1 "immediate_operand" ""))]
18432   "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
18433   && TARGET_SPLIT_LONG_MOVES"
18434   [(set (match_dup 2) (match_dup 1))
18435    (set (match_dup 0) (match_dup 2))]
18436   "")
18438 (define_peephole2
18439   [(match_scratch:QI 2 "q")
18440    (set (match_operand:QI 0 "memory_operand" "")
18441         (match_operand:QI 1 "immediate_operand" ""))]
18442   "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
18443   && TARGET_SPLIT_LONG_MOVES"
18444   [(set (match_dup 2) (match_dup 1))
18445    (set (match_dup 0) (match_dup 2))]
18446   "")
18448 ;; Don't compare memory with zero, load and use a test instead.
18449 (define_peephole2
18450   [(set (match_operand 0 "flags_reg_operand" "")
18451         (match_operator 1 "compare_operator"
18452           [(match_operand:SI 2 "memory_operand" "")
18453            (const_int 0)]))
18454    (match_scratch:SI 3 "r")]
18455   "ix86_match_ccmode (insn, CCNOmode) && ! optimize_size"
18456   [(set (match_dup 3) (match_dup 2))
18457    (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))]
18458   "")
18460 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer. 
18461 ;; Don't split NOTs with a displacement operand, because resulting XOR
18462 ;; will not be pairable anyway.
18464 ;; On AMD K6, NOT is vector decoded with memory operand that cannot be
18465 ;; represented using a modRM byte.  The XOR replacement is long decoded,
18466 ;; so this split helps here as well.
18468 ;; Note: Can't do this as a regular split because we can't get proper
18469 ;; lifetime information then.
18471 (define_peephole2
18472   [(set (match_operand:SI 0 "nonimmediate_operand" "")
18473         (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
18474   "!optimize_size
18475    && peep2_regno_dead_p (0, FLAGS_REG)
18476    && ((TARGET_PENTIUM 
18477         && (GET_CODE (operands[0]) != MEM
18478             || !memory_displacement_operand (operands[0], SImode)))
18479        || (TARGET_K6 && long_memory_operand (operands[0], SImode)))"
18480   [(parallel [(set (match_dup 0)
18481                    (xor:SI (match_dup 1) (const_int -1)))
18482               (clobber (reg:CC FLAGS_REG))])]
18483   "")
18485 (define_peephole2
18486   [(set (match_operand:HI 0 "nonimmediate_operand" "")
18487         (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
18488   "!optimize_size
18489    && peep2_regno_dead_p (0, FLAGS_REG)
18490    && ((TARGET_PENTIUM 
18491         && (GET_CODE (operands[0]) != MEM
18492             || !memory_displacement_operand (operands[0], HImode)))
18493        || (TARGET_K6 && long_memory_operand (operands[0], HImode)))"
18494   [(parallel [(set (match_dup 0)
18495                    (xor:HI (match_dup 1) (const_int -1)))
18496               (clobber (reg:CC FLAGS_REG))])]
18497   "")
18499 (define_peephole2
18500   [(set (match_operand:QI 0 "nonimmediate_operand" "")
18501         (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
18502   "!optimize_size
18503    && peep2_regno_dead_p (0, FLAGS_REG)
18504    && ((TARGET_PENTIUM 
18505         && (GET_CODE (operands[0]) != MEM
18506             || !memory_displacement_operand (operands[0], QImode)))
18507        || (TARGET_K6 && long_memory_operand (operands[0], QImode)))"
18508   [(parallel [(set (match_dup 0)
18509                    (xor:QI (match_dup 1) (const_int -1)))
18510               (clobber (reg:CC FLAGS_REG))])]
18511   "")
18513 ;; Non pairable "test imm, reg" instructions can be translated to
18514 ;; "and imm, reg" if reg dies.  The "and" form is also shorter (one
18515 ;; byte opcode instead of two, have a short form for byte operands),
18516 ;; so do it for other CPUs as well.  Given that the value was dead,
18517 ;; this should not create any new dependencies.  Pass on the sub-word
18518 ;; versions if we're concerned about partial register stalls.
18520 (define_peephole2
18521   [(set (match_operand 0 "flags_reg_operand" "")
18522         (match_operator 1 "compare_operator"
18523           [(and:SI (match_operand:SI 2 "register_operand" "")
18524                    (match_operand:SI 3 "immediate_operand" ""))
18525            (const_int 0)]))]
18526   "ix86_match_ccmode (insn, CCNOmode)
18527    && (true_regnum (operands[2]) != 0
18528        || (GET_CODE (operands[3]) == CONST_INT
18529            && CONST_OK_FOR_LETTER_P (INTVAL (operands[3]), 'K')))
18530    && peep2_reg_dead_p (1, operands[2])"
18531   [(parallel
18532      [(set (match_dup 0)
18533            (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
18534                             (const_int 0)]))
18535       (set (match_dup 2)
18536            (and:SI (match_dup 2) (match_dup 3)))])]
18537   "")
18539 ;; We don't need to handle HImode case, because it will be promoted to SImode
18540 ;; on ! TARGET_PARTIAL_REG_STALL
18542 (define_peephole2
18543   [(set (match_operand 0 "flags_reg_operand" "")
18544         (match_operator 1 "compare_operator"
18545           [(and:QI (match_operand:QI 2 "register_operand" "")
18546                    (match_operand:QI 3 "immediate_operand" ""))
18547            (const_int 0)]))]
18548   "! TARGET_PARTIAL_REG_STALL
18549    && ix86_match_ccmode (insn, CCNOmode)
18550    && true_regnum (operands[2]) != 0
18551    && peep2_reg_dead_p (1, operands[2])"
18552   [(parallel
18553      [(set (match_dup 0)
18554            (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
18555                             (const_int 0)]))
18556       (set (match_dup 2)
18557            (and:QI (match_dup 2) (match_dup 3)))])]
18558   "")
18560 (define_peephole2
18561   [(set (match_operand 0 "flags_reg_operand" "")
18562         (match_operator 1 "compare_operator"
18563           [(and:SI
18564              (zero_extract:SI
18565                (match_operand 2 "ext_register_operand" "")
18566                (const_int 8)
18567                (const_int 8))
18568              (match_operand 3 "const_int_operand" ""))
18569            (const_int 0)]))]
18570   "! TARGET_PARTIAL_REG_STALL
18571    && ix86_match_ccmode (insn, CCNOmode)
18572    && true_regnum (operands[2]) != 0
18573    && peep2_reg_dead_p (1, operands[2])"
18574   [(parallel [(set (match_dup 0)
18575                    (match_op_dup 1
18576                      [(and:SI
18577                         (zero_extract:SI
18578                           (match_dup 2)
18579                           (const_int 8)
18580                           (const_int 8))
18581                         (match_dup 3))
18582                       (const_int 0)]))
18583               (set (zero_extract:SI (match_dup 2)
18584                                     (const_int 8)
18585                                     (const_int 8))
18586                    (and:SI 
18587                      (zero_extract:SI
18588                        (match_dup 2)
18589                        (const_int 8)
18590                        (const_int 8))
18591                      (match_dup 3)))])]
18592   "")
18594 ;; Don't do logical operations with memory inputs.
18595 (define_peephole2
18596   [(match_scratch:SI 2 "r")
18597    (parallel [(set (match_operand:SI 0 "register_operand" "")
18598                    (match_operator:SI 3 "arith_or_logical_operator"
18599                      [(match_dup 0)
18600                       (match_operand:SI 1 "memory_operand" "")]))
18601               (clobber (reg:CC FLAGS_REG))])]
18602   "! optimize_size && ! TARGET_READ_MODIFY"
18603   [(set (match_dup 2) (match_dup 1))
18604    (parallel [(set (match_dup 0)
18605                    (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
18606               (clobber (reg:CC FLAGS_REG))])]
18607   "")
18609 (define_peephole2
18610   [(match_scratch:SI 2 "r")
18611    (parallel [(set (match_operand:SI 0 "register_operand" "")
18612                    (match_operator:SI 3 "arith_or_logical_operator"
18613                      [(match_operand:SI 1 "memory_operand" "")
18614                       (match_dup 0)]))
18615               (clobber (reg:CC FLAGS_REG))])]
18616   "! optimize_size && ! TARGET_READ_MODIFY"
18617   [(set (match_dup 2) (match_dup 1))
18618    (parallel [(set (match_dup 0)
18619                    (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
18620               (clobber (reg:CC FLAGS_REG))])]
18621   "")
18623 ; Don't do logical operations with memory outputs
18625 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
18626 ; instruction into two 1-uop insns plus a 2-uop insn.  That last has
18627 ; the same decoder scheduling characteristics as the original.
18629 (define_peephole2
18630   [(match_scratch:SI 2 "r")
18631    (parallel [(set (match_operand:SI 0 "memory_operand" "")
18632                    (match_operator:SI 3 "arith_or_logical_operator"
18633                      [(match_dup 0)
18634                       (match_operand:SI 1 "nonmemory_operand" "")]))
18635               (clobber (reg:CC FLAGS_REG))])]
18636   "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
18637   [(set (match_dup 2) (match_dup 0))
18638    (parallel [(set (match_dup 2)
18639                    (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
18640               (clobber (reg:CC FLAGS_REG))])
18641    (set (match_dup 0) (match_dup 2))]
18642   "")
18644 (define_peephole2
18645   [(match_scratch:SI 2 "r")
18646    (parallel [(set (match_operand:SI 0 "memory_operand" "")
18647                    (match_operator:SI 3 "arith_or_logical_operator"
18648                      [(match_operand:SI 1 "nonmemory_operand" "")
18649                       (match_dup 0)]))
18650               (clobber (reg:CC FLAGS_REG))])]
18651   "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
18652   [(set (match_dup 2) (match_dup 0))
18653    (parallel [(set (match_dup 2)
18654                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
18655               (clobber (reg:CC FLAGS_REG))])
18656    (set (match_dup 0) (match_dup 2))]
18657   "")
18659 ;; Attempt to always use XOR for zeroing registers.
18660 (define_peephole2
18661   [(set (match_operand 0 "register_operand" "")
18662         (match_operand 1 "const0_operand" ""))]
18663   "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD
18664    && (! TARGET_USE_MOV0 || optimize_size)
18665    && GENERAL_REG_P (operands[0])
18666    && peep2_regno_dead_p (0, FLAGS_REG)"
18667   [(parallel [(set (match_dup 0) (const_int 0))
18668               (clobber (reg:CC FLAGS_REG))])]
18670   operands[0] = gen_lowpart (word_mode, operands[0]);
18673 (define_peephole2
18674   [(set (strict_low_part (match_operand 0 "register_operand" ""))
18675         (const_int 0))]
18676   "(GET_MODE (operands[0]) == QImode
18677     || GET_MODE (operands[0]) == HImode)
18678    && (! TARGET_USE_MOV0 || optimize_size)
18679    && peep2_regno_dead_p (0, FLAGS_REG)"
18680   [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
18681               (clobber (reg:CC FLAGS_REG))])])
18683 ;; For HI and SI modes, or $-1,reg is smaller than mov $-1,reg.
18684 (define_peephole2
18685   [(set (match_operand 0 "register_operand" "")
18686         (const_int -1))]
18687   "(GET_MODE (operands[0]) == HImode
18688     || GET_MODE (operands[0]) == SImode 
18689     || (GET_MODE (operands[0]) == DImode && TARGET_64BIT))
18690    && (optimize_size || TARGET_PENTIUM)
18691    && peep2_regno_dead_p (0, FLAGS_REG)"
18692   [(parallel [(set (match_dup 0) (const_int -1))
18693               (clobber (reg:CC FLAGS_REG))])]
18694   "operands[0] = gen_lowpart (GET_MODE (operands[0]) == DImode ? DImode : SImode,
18695                               operands[0]);")
18697 ;; Attempt to convert simple leas to adds. These can be created by
18698 ;; move expanders.
18699 (define_peephole2
18700   [(set (match_operand:SI 0 "register_operand" "")
18701         (plus:SI (match_dup 0)
18702                  (match_operand:SI 1 "nonmemory_operand" "")))]
18703   "peep2_regno_dead_p (0, FLAGS_REG)"
18704   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
18705               (clobber (reg:CC FLAGS_REG))])]
18706   "")
18708 (define_peephole2
18709   [(set (match_operand:SI 0 "register_operand" "")
18710         (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
18711                             (match_operand:DI 2 "nonmemory_operand" "")) 0))]
18712   "peep2_regno_dead_p (0, FLAGS_REG) && REGNO (operands[0]) == REGNO (operands[1])"
18713   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
18714               (clobber (reg:CC FLAGS_REG))])]
18715   "operands[2] = gen_lowpart (SImode, operands[2]);")
18717 (define_peephole2
18718   [(set (match_operand:DI 0 "register_operand" "")
18719         (plus:DI (match_dup 0)
18720                  (match_operand:DI 1 "x86_64_general_operand" "")))]
18721   "peep2_regno_dead_p (0, FLAGS_REG)"
18722   [(parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
18723               (clobber (reg:CC FLAGS_REG))])]
18724   "")
18726 (define_peephole2
18727   [(set (match_operand:SI 0 "register_operand" "")
18728         (mult:SI (match_dup 0)
18729                  (match_operand:SI 1 "const_int_operand" "")))]
18730   "exact_log2 (INTVAL (operands[1])) >= 0
18731    && peep2_regno_dead_p (0, FLAGS_REG)"
18732   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
18733               (clobber (reg:CC FLAGS_REG))])]
18734   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
18736 (define_peephole2
18737   [(set (match_operand:DI 0 "register_operand" "")
18738         (mult:DI (match_dup 0)
18739                  (match_operand:DI 1 "const_int_operand" "")))]
18740   "exact_log2 (INTVAL (operands[1])) >= 0
18741    && peep2_regno_dead_p (0, FLAGS_REG)"
18742   [(parallel [(set (match_dup 0) (ashift:DI (match_dup 0) (match_dup 2)))
18743               (clobber (reg:CC FLAGS_REG))])]
18744   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
18746 (define_peephole2
18747   [(set (match_operand:SI 0 "register_operand" "")
18748         (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
18749                    (match_operand:DI 2 "const_int_operand" "")) 0))]
18750   "exact_log2 (INTVAL (operands[2])) >= 0
18751    && REGNO (operands[0]) == REGNO (operands[1])
18752    && peep2_regno_dead_p (0, FLAGS_REG)"
18753   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
18754               (clobber (reg:CC FLAGS_REG))])]
18755   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
18757 ;; The ESP adjustments can be done by the push and pop instructions.  Resulting
18758 ;; code is shorter, since push is only 1 byte, while add imm, %esp 3 bytes.  On
18759 ;; many CPUs it is also faster, since special hardware to avoid esp
18760 ;; dependencies is present.
18762 ;; While some of these conversions may be done using splitters, we use peepholes
18763 ;; in order to allow combine_stack_adjustments pass to see nonobfuscated RTL.
18765 ;; Convert prologue esp subtractions to push.
18766 ;; We need register to push.  In order to keep verify_flow_info happy we have
18767 ;; two choices
18768 ;; - use scratch and clobber it in order to avoid dependencies
18769 ;; - use already live register
18770 ;; We can't use the second way right now, since there is no reliable way how to
18771 ;; verify that given register is live.  First choice will also most likely in
18772 ;; fewer dependencies.  On the place of esp adjustments it is very likely that
18773 ;; call clobbered registers are dead.  We may want to use base pointer as an
18774 ;; alternative when no register is available later.
18776 (define_peephole2
18777   [(match_scratch:SI 0 "r")
18778    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
18779               (clobber (reg:CC FLAGS_REG))
18780               (clobber (mem:BLK (scratch)))])]
18781   "optimize_size || !TARGET_SUB_ESP_4"
18782   [(clobber (match_dup 0))
18783    (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
18784               (clobber (mem:BLK (scratch)))])])
18786 (define_peephole2
18787   [(match_scratch:SI 0 "r")
18788    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
18789               (clobber (reg:CC FLAGS_REG))
18790               (clobber (mem:BLK (scratch)))])]
18791   "optimize_size || !TARGET_SUB_ESP_8"
18792   [(clobber (match_dup 0))
18793    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
18794    (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
18795               (clobber (mem:BLK (scratch)))])])
18797 ;; Convert esp subtractions to push.
18798 (define_peephole2
18799   [(match_scratch:SI 0 "r")
18800    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
18801               (clobber (reg:CC FLAGS_REG))])]
18802   "optimize_size || !TARGET_SUB_ESP_4"
18803   [(clobber (match_dup 0))
18804    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
18806 (define_peephole2
18807   [(match_scratch:SI 0 "r")
18808    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
18809               (clobber (reg:CC FLAGS_REG))])]
18810   "optimize_size || !TARGET_SUB_ESP_8"
18811   [(clobber (match_dup 0))
18812    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
18813    (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
18815 ;; Convert epilogue deallocator to pop.
18816 (define_peephole2
18817   [(match_scratch:SI 0 "r")
18818    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
18819               (clobber (reg:CC FLAGS_REG))
18820               (clobber (mem:BLK (scratch)))])]
18821   "optimize_size || !TARGET_ADD_ESP_4"
18822   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
18823               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
18824               (clobber (mem:BLK (scratch)))])]
18825   "")
18827 ;; Two pops case is tricky, since pop causes dependency on destination register.
18828 ;; We use two registers if available.
18829 (define_peephole2
18830   [(match_scratch:SI 0 "r")
18831    (match_scratch:SI 1 "r")
18832    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
18833               (clobber (reg:CC FLAGS_REG))
18834               (clobber (mem:BLK (scratch)))])]
18835   "optimize_size || !TARGET_ADD_ESP_8"
18836   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
18837               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
18838               (clobber (mem:BLK (scratch)))])
18839    (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
18840               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
18841   "")
18843 (define_peephole2
18844   [(match_scratch:SI 0 "r")
18845    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
18846               (clobber (reg:CC FLAGS_REG))
18847               (clobber (mem:BLK (scratch)))])]
18848   "optimize_size"
18849   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
18850               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
18851               (clobber (mem:BLK (scratch)))])
18852    (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
18853               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
18854   "")
18856 ;; Convert esp additions to pop.
18857 (define_peephole2
18858   [(match_scratch:SI 0 "r")
18859    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
18860               (clobber (reg:CC FLAGS_REG))])]
18861   ""
18862   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
18863               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
18864   "")
18866 ;; Two pops case is tricky, since pop causes dependency on destination register.
18867 ;; We use two registers if available.
18868 (define_peephole2
18869   [(match_scratch:SI 0 "r")
18870    (match_scratch:SI 1 "r")
18871    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
18872               (clobber (reg:CC FLAGS_REG))])]
18873   ""
18874   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
18875               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
18876    (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
18877               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
18878   "")
18880 (define_peephole2
18881   [(match_scratch:SI 0 "r")
18882    (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
18883               (clobber (reg:CC FLAGS_REG))])]
18884   "optimize_size"
18885   [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
18886               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
18887    (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
18888               (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
18889   "")
18891 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
18892 ;; required and register dies.  Similarly for 128 to plus -128.
18893 (define_peephole2
18894   [(set (match_operand 0 "flags_reg_operand" "")
18895         (match_operator 1 "compare_operator"
18896           [(match_operand 2 "register_operand" "")
18897            (match_operand 3 "const_int_operand" "")]))]
18898   "(INTVAL (operands[3]) == -1
18899     || INTVAL (operands[3]) == 1
18900     || INTVAL (operands[3]) == 128)
18901    && ix86_match_ccmode (insn, CCGCmode)
18902    && peep2_reg_dead_p (1, operands[2])"
18903   [(parallel [(set (match_dup 0)
18904                    (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
18905               (clobber (match_dup 2))])]
18906   "")
18908 (define_peephole2
18909   [(match_scratch:DI 0 "r")
18910    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
18911               (clobber (reg:CC FLAGS_REG))
18912               (clobber (mem:BLK (scratch)))])]
18913   "optimize_size || !TARGET_SUB_ESP_4"
18914   [(clobber (match_dup 0))
18915    (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
18916               (clobber (mem:BLK (scratch)))])])
18918 (define_peephole2
18919   [(match_scratch:DI 0 "r")
18920    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
18921               (clobber (reg:CC FLAGS_REG))
18922               (clobber (mem:BLK (scratch)))])]
18923   "optimize_size || !TARGET_SUB_ESP_8"
18924   [(clobber (match_dup 0))
18925    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
18926    (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
18927               (clobber (mem:BLK (scratch)))])])
18929 ;; Convert esp subtractions to push.
18930 (define_peephole2
18931   [(match_scratch:DI 0 "r")
18932    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
18933               (clobber (reg:CC FLAGS_REG))])]
18934   "optimize_size || !TARGET_SUB_ESP_4"
18935   [(clobber (match_dup 0))
18936    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
18938 (define_peephole2
18939   [(match_scratch:DI 0 "r")
18940    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
18941               (clobber (reg:CC FLAGS_REG))])]
18942   "optimize_size || !TARGET_SUB_ESP_8"
18943   [(clobber (match_dup 0))
18944    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
18945    (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
18947 ;; Convert epilogue deallocator to pop.
18948 (define_peephole2
18949   [(match_scratch:DI 0 "r")
18950    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
18951               (clobber (reg:CC FLAGS_REG))
18952               (clobber (mem:BLK (scratch)))])]
18953   "optimize_size || !TARGET_ADD_ESP_4"
18954   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
18955               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
18956               (clobber (mem:BLK (scratch)))])]
18957   "")
18959 ;; Two pops case is tricky, since pop causes dependency on destination register.
18960 ;; We use two registers if available.
18961 (define_peephole2
18962   [(match_scratch:DI 0 "r")
18963    (match_scratch:DI 1 "r")
18964    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
18965               (clobber (reg:CC FLAGS_REG))
18966               (clobber (mem:BLK (scratch)))])]
18967   "optimize_size || !TARGET_ADD_ESP_8"
18968   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
18969               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
18970               (clobber (mem:BLK (scratch)))])
18971    (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
18972               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
18973   "")
18975 (define_peephole2
18976   [(match_scratch:DI 0 "r")
18977    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
18978               (clobber (reg:CC FLAGS_REG))
18979               (clobber (mem:BLK (scratch)))])]
18980   "optimize_size"
18981   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
18982               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
18983               (clobber (mem:BLK (scratch)))])
18984    (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
18985               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
18986   "")
18988 ;; Convert esp additions to pop.
18989 (define_peephole2
18990   [(match_scratch:DI 0 "r")
18991    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
18992               (clobber (reg:CC FLAGS_REG))])]
18993   ""
18994   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
18995               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
18996   "")
18998 ;; Two pops case is tricky, since pop causes dependency on destination register.
18999 ;; We use two registers if available.
19000 (define_peephole2
19001   [(match_scratch:DI 0 "r")
19002    (match_scratch:DI 1 "r")
19003    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19004               (clobber (reg:CC FLAGS_REG))])]
19005   ""
19006   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19007               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
19008    (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
19009               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19010   "")
19012 (define_peephole2
19013   [(match_scratch:DI 0 "r")
19014    (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19015               (clobber (reg:CC FLAGS_REG))])]
19016   "optimize_size"
19017   [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19018               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
19019    (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19020               (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19021   "")
19023 ;; Convert imul by three, five and nine into lea
19024 (define_peephole2
19025   [(parallel
19026     [(set (match_operand:SI 0 "register_operand" "")
19027           (mult:SI (match_operand:SI 1 "register_operand" "")
19028                    (match_operand:SI 2 "const_int_operand" "")))
19029      (clobber (reg:CC FLAGS_REG))])]
19030   "INTVAL (operands[2]) == 3
19031    || INTVAL (operands[2]) == 5
19032    || INTVAL (operands[2]) == 9"
19033   [(set (match_dup 0)
19034         (plus:SI (mult:SI (match_dup 1) (match_dup 2))
19035                  (match_dup 1)))]
19036   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19038 (define_peephole2
19039   [(parallel
19040     [(set (match_operand:SI 0 "register_operand" "")
19041           (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
19042                    (match_operand:SI 2 "const_int_operand" "")))
19043      (clobber (reg:CC FLAGS_REG))])]
19044   "!optimize_size 
19045    && (INTVAL (operands[2]) == 3
19046        || INTVAL (operands[2]) == 5
19047        || INTVAL (operands[2]) == 9)"
19048   [(set (match_dup 0) (match_dup 1))
19049    (set (match_dup 0)
19050         (plus:SI (mult:SI (match_dup 0) (match_dup 2))
19051                  (match_dup 0)))]
19052   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19054 (define_peephole2
19055   [(parallel
19056     [(set (match_operand:DI 0 "register_operand" "")
19057           (mult:DI (match_operand:DI 1 "register_operand" "")
19058                    (match_operand:DI 2 "const_int_operand" "")))
19059      (clobber (reg:CC FLAGS_REG))])]
19060   "TARGET_64BIT
19061    && (INTVAL (operands[2]) == 3
19062        || INTVAL (operands[2]) == 5
19063        || INTVAL (operands[2]) == 9)"
19064   [(set (match_dup 0)
19065         (plus:DI (mult:DI (match_dup 1) (match_dup 2))
19066                  (match_dup 1)))]
19067   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19069 (define_peephole2
19070   [(parallel
19071     [(set (match_operand:DI 0 "register_operand" "")
19072           (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
19073                    (match_operand:DI 2 "const_int_operand" "")))
19074      (clobber (reg:CC FLAGS_REG))])]
19075   "TARGET_64BIT
19076    && !optimize_size 
19077    && (INTVAL (operands[2]) == 3
19078        || INTVAL (operands[2]) == 5
19079        || INTVAL (operands[2]) == 9)"
19080   [(set (match_dup 0) (match_dup 1))
19081    (set (match_dup 0)
19082         (plus:DI (mult:DI (match_dup 0) (match_dup 2))
19083                  (match_dup 0)))]
19084   { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19086 ;; Imul $32bit_imm, mem, reg is vector decoded, while
19087 ;; imul $32bit_imm, reg, reg is direct decoded.
19088 (define_peephole2
19089   [(match_scratch:DI 3 "r")
19090    (parallel [(set (match_operand:DI 0 "register_operand" "")
19091                    (mult:DI (match_operand:DI 1 "memory_operand" "")
19092                             (match_operand:DI 2 "immediate_operand" "")))
19093               (clobber (reg:CC FLAGS_REG))])]
19094   "TARGET_K8 && !optimize_size
19095    && (GET_CODE (operands[2]) != CONST_INT
19096        || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19097   [(set (match_dup 3) (match_dup 1))
19098    (parallel [(set (match_dup 0) (mult:DI (match_dup 3) (match_dup 2)))
19099               (clobber (reg:CC FLAGS_REG))])]
19102 (define_peephole2
19103   [(match_scratch:SI 3 "r")
19104    (parallel [(set (match_operand:SI 0 "register_operand" "")
19105                    (mult:SI (match_operand:SI 1 "memory_operand" "")
19106                             (match_operand:SI 2 "immediate_operand" "")))
19107               (clobber (reg:CC FLAGS_REG))])]
19108   "TARGET_K8 && !optimize_size
19109    && (GET_CODE (operands[2]) != CONST_INT
19110        || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19111   [(set (match_dup 3) (match_dup 1))
19112    (parallel [(set (match_dup 0) (mult:SI (match_dup 3) (match_dup 2)))
19113               (clobber (reg:CC FLAGS_REG))])]
19116 (define_peephole2
19117   [(match_scratch:SI 3 "r")
19118    (parallel [(set (match_operand:DI 0 "register_operand" "")
19119                    (zero_extend:DI
19120                      (mult:SI (match_operand:SI 1 "memory_operand" "")
19121                               (match_operand:SI 2 "immediate_operand" ""))))
19122               (clobber (reg:CC FLAGS_REG))])]
19123   "TARGET_K8 && !optimize_size
19124    && (GET_CODE (operands[2]) != CONST_INT
19125        || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19126   [(set (match_dup 3) (match_dup 1))
19127    (parallel [(set (match_dup 0) (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
19128               (clobber (reg:CC FLAGS_REG))])]
19131 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
19132 ;; Convert it into imul reg, reg
19133 ;; It would be better to force assembler to encode instruction using long
19134 ;; immediate, but there is apparently no way to do so.
19135 (define_peephole2
19136   [(parallel [(set (match_operand:DI 0 "register_operand" "")
19137                    (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
19138                             (match_operand:DI 2 "const_int_operand" "")))
19139               (clobber (reg:CC FLAGS_REG))])
19140    (match_scratch:DI 3 "r")]
19141   "TARGET_K8 && !optimize_size
19142    && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')"
19143   [(set (match_dup 3) (match_dup 2))
19144    (parallel [(set (match_dup 0) (mult:DI (match_dup 0) (match_dup 3)))
19145               (clobber (reg:CC FLAGS_REG))])]
19147   if (!rtx_equal_p (operands[0], operands[1]))
19148     emit_move_insn (operands[0], operands[1]);
19151 (define_peephole2
19152   [(parallel [(set (match_operand:SI 0 "register_operand" "")
19153                    (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
19154                             (match_operand:SI 2 "const_int_operand" "")))
19155               (clobber (reg:CC FLAGS_REG))])
19156    (match_scratch:SI 3 "r")]
19157   "TARGET_K8 && !optimize_size
19158    && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')"
19159   [(set (match_dup 3) (match_dup 2))
19160    (parallel [(set (match_dup 0) (mult:SI (match_dup 0) (match_dup 3)))
19161               (clobber (reg:CC FLAGS_REG))])]
19163   if (!rtx_equal_p (operands[0], operands[1]))
19164     emit_move_insn (operands[0], operands[1]);
19167 (define_peephole2
19168   [(parallel [(set (match_operand:HI 0 "register_operand" "")
19169                    (mult:HI (match_operand:HI 1 "nonimmediate_operand" "")
19170                             (match_operand:HI 2 "immediate_operand" "")))
19171               (clobber (reg:CC FLAGS_REG))])
19172    (match_scratch:HI 3 "r")]
19173   "TARGET_K8 && !optimize_size"
19174   [(set (match_dup 3) (match_dup 2))
19175    (parallel [(set (match_dup 0) (mult:HI (match_dup 0) (match_dup 3)))
19176               (clobber (reg:CC FLAGS_REG))])]
19178   if (!rtx_equal_p (operands[0], operands[1]))
19179     emit_move_insn (operands[0], operands[1]);
19182 ;; Call-value patterns last so that the wildcard operand does not
19183 ;; disrupt insn-recog's switch tables.
19185 (define_insn "*call_value_pop_0"
19186   [(set (match_operand 0 "" "")
19187         (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
19188               (match_operand:SI 2 "" "")))
19189    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
19190                             (match_operand:SI 3 "immediate_operand" "")))]
19191   "!TARGET_64BIT"
19193   if (SIBLING_CALL_P (insn))
19194     return "jmp\t%P1";
19195   else
19196     return "call\t%P1";
19198   [(set_attr "type" "callv")])
19200 (define_insn "*call_value_pop_1"
19201   [(set (match_operand 0 "" "")
19202         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
19203               (match_operand:SI 2 "" "")))
19204    (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
19205                             (match_operand:SI 3 "immediate_operand" "i")))]
19206   "!TARGET_64BIT"
19208   if (constant_call_address_operand (operands[1], Pmode))
19209     {
19210       if (SIBLING_CALL_P (insn))
19211         return "jmp\t%P1";
19212       else
19213         return "call\t%P1";
19214     }
19215   if (SIBLING_CALL_P (insn))
19216     return "jmp\t%A1";
19217   else
19218     return "call\t%A1";
19220   [(set_attr "type" "callv")])
19222 (define_insn "*call_value_0"
19223   [(set (match_operand 0 "" "")
19224         (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
19225               (match_operand:SI 2 "" "")))]
19226   "!TARGET_64BIT"
19228   if (SIBLING_CALL_P (insn))
19229     return "jmp\t%P1";
19230   else
19231     return "call\t%P1";
19233   [(set_attr "type" "callv")])
19235 (define_insn "*call_value_0_rex64"
19236   [(set (match_operand 0 "" "")
19237         (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
19238               (match_operand:DI 2 "const_int_operand" "")))]
19239   "TARGET_64BIT"
19241   if (SIBLING_CALL_P (insn))
19242     return "jmp\t%P1";
19243   else
19244     return "call\t%P1";
19246   [(set_attr "type" "callv")])
19248 (define_insn "*call_value_1"
19249   [(set (match_operand 0 "" "")
19250         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
19251               (match_operand:SI 2 "" "")))]
19252   "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
19254   if (constant_call_address_operand (operands[1], Pmode))
19255     return "call\t%P1";
19256   return "call\t%A1";
19258   [(set_attr "type" "callv")])
19260 (define_insn "*sibcall_value_1"
19261   [(set (match_operand 0 "" "")
19262         (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "s,c,d,a"))
19263               (match_operand:SI 2 "" "")))]
19264   "SIBLING_CALL_P (insn) && !TARGET_64BIT"
19266   if (constant_call_address_operand (operands[1], Pmode))
19267     return "jmp\t%P1";
19268   return "jmp\t%A1";
19270   [(set_attr "type" "callv")])
19272 (define_insn "*call_value_1_rex64"
19273   [(set (match_operand 0 "" "")
19274         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rsm"))
19275               (match_operand:DI 2 "" "")))]
19276   "!SIBLING_CALL_P (insn) && TARGET_64BIT"
19278   if (constant_call_address_operand (operands[1], Pmode))
19279     return "call\t%P1";
19280   return "call\t%A1";
19282   [(set_attr "type" "callv")])
19284 (define_insn "*sibcall_value_1_rex64"
19285   [(set (match_operand 0 "" "")
19286         (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
19287               (match_operand:DI 2 "" "")))]
19288   "SIBLING_CALL_P (insn) && TARGET_64BIT"
19289   "jmp\t%P1"
19290   [(set_attr "type" "callv")])
19292 (define_insn "*sibcall_value_1_rex64_v"
19293   [(set (match_operand 0 "" "")
19294         (call (mem:QI (reg:DI 40))
19295               (match_operand:DI 1 "" "")))]
19296   "SIBLING_CALL_P (insn) && TARGET_64BIT"
19297   "jmp\t*%%r11"
19298   [(set_attr "type" "callv")])
19300 (define_insn "trap"
19301   [(trap_if (const_int 1) (const_int 5))]
19302   ""
19303   "int\t$5")
19305 ;;; ix86 doesn't have conditional trap instructions, but we fake them
19306 ;;; for the sake of bounds checking.  By emitting bounds checks as
19307 ;;; conditional traps rather than as conditional jumps around
19308 ;;; unconditional traps we avoid introducing spurious basic-block
19309 ;;; boundaries and facilitate elimination of redundant checks.  In
19310 ;;; honor of the too-inflexible-for-BPs `bound' instruction, we use
19311 ;;; interrupt 5.
19312 ;;; 
19313 ;;; FIXME: Static branch prediction rules for ix86 are such that
19314 ;;; forward conditional branches predict as untaken.  As implemented
19315 ;;; below, pseudo conditional traps violate that rule.  We should use
19316 ;;; .pushsection/.popsection to place all of the `int 5's in a special
19317 ;;; section loaded at the end of the text segment and branch forward
19318 ;;; there on bounds-failure, and then jump back immediately (in case
19319 ;;; the system chooses to ignore bounds violations, or to report
19320 ;;; violations and continue execution).
19322 (define_expand "conditional_trap"
19323   [(trap_if (match_operator 0 "comparison_operator"
19324              [(match_dup 2) (const_int 0)])
19325             (match_operand 1 "const_int_operand" ""))]
19326   ""
19328   emit_insn (gen_rtx_TRAP_IF (VOIDmode,
19329                               ix86_expand_compare (GET_CODE (operands[0]),
19330                                                    NULL, NULL),
19331                               operands[1]));
19332   DONE;
19335 (define_insn "*conditional_trap_1"
19336   [(trap_if (match_operator 0 "comparison_operator"
19337              [(reg FLAGS_REG) (const_int 0)])
19338             (match_operand 1 "const_int_operand" ""))]
19339   ""
19341   operands[2] = gen_label_rtx ();
19342   output_asm_insn ("j%c0\t%l2\; int\t%1", operands);
19343   (*targetm.asm_out.internal_label) (asm_out_file, "L",
19344                              CODE_LABEL_NUMBER (operands[2]));
19345   RET;
19348 (define_expand "sse_prologue_save"
19349   [(parallel [(set (match_operand:BLK 0 "" "")
19350                    (unspec:BLK [(reg:DI 21)
19351                                 (reg:DI 22)
19352                                 (reg:DI 23)
19353                                 (reg:DI 24)
19354                                 (reg:DI 25)
19355                                 (reg:DI 26)
19356                                 (reg:DI 27)
19357                                 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
19358               (use (match_operand:DI 1 "register_operand" ""))
19359               (use (match_operand:DI 2 "immediate_operand" ""))
19360               (use (label_ref:DI (match_operand 3 "" "")))])]
19361   "TARGET_64BIT"
19362   "")
19364 (define_insn "*sse_prologue_save_insn"
19365   [(set (mem:BLK (plus:DI (match_operand:DI 0 "register_operand" "R")
19366                           (match_operand:DI 4 "const_int_operand" "n")))
19367         (unspec:BLK [(reg:DI 21)
19368                      (reg:DI 22)
19369                      (reg:DI 23)
19370                      (reg:DI 24)
19371                      (reg:DI 25)
19372                      (reg:DI 26)
19373                      (reg:DI 27)
19374                      (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
19375    (use (match_operand:DI 1 "register_operand" "r"))
19376    (use (match_operand:DI 2 "const_int_operand" "i"))
19377    (use (label_ref:DI (match_operand 3 "" "X")))]
19378   "TARGET_64BIT
19379    && INTVAL (operands[4]) + SSE_REGPARM_MAX * 16 - 16 < 128
19380    && INTVAL (operands[4]) + INTVAL (operands[2]) * 16 >= -128"
19381   "*
19383   int i;
19384   operands[0] = gen_rtx_MEM (Pmode,
19385                              gen_rtx_PLUS (Pmode, operands[0], operands[4]));
19386   output_asm_insn (\"jmp\\t%A1\", operands);
19387   for (i = SSE_REGPARM_MAX - 1; i >= INTVAL (operands[2]); i--)
19388     {
19389       operands[4] = adjust_address (operands[0], DImode, i*16);
19390       operands[5] = gen_rtx_REG (TImode, SSE_REGNO (i));
19391       PUT_MODE (operands[4], TImode);
19392       if (GET_CODE (XEXP (operands[0], 0)) != PLUS)
19393         output_asm_insn (\"rex\", operands);
19394       output_asm_insn (\"movaps\\t{%5, %4|%4, %5}\", operands);
19395     }
19396   (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
19397                              CODE_LABEL_NUMBER (operands[3]));
19398   RET;
19400   "
19401   [(set_attr "type" "other")
19402    (set_attr "length_immediate" "0")
19403    (set_attr "length_address" "0")
19404    (set_attr "length" "135")
19405    (set_attr "memory" "store")
19406    (set_attr "modrm" "0")
19407    (set_attr "mode" "DI")])
19409 (define_expand "prefetch"
19410   [(prefetch (match_operand 0 "address_operand" "")
19411              (match_operand:SI 1 "const_int_operand" "")
19412              (match_operand:SI 2 "const_int_operand" ""))]
19413   "TARGET_PREFETCH_SSE || TARGET_3DNOW"
19415   int rw = INTVAL (operands[1]);
19416   int locality = INTVAL (operands[2]);
19418   if (rw != 0 && rw != 1)
19419     abort ();
19420   if (locality < 0 || locality > 3)
19421     abort ();
19422   if (GET_MODE (operands[0]) != Pmode && GET_MODE (operands[0]) != VOIDmode)
19423     abort ();
19425   /* Use 3dNOW prefetch in case we are asking for write prefetch not
19426      supported by SSE counterpart or the SSE prefetch is not available
19427      (K6 machines).  Otherwise use SSE prefetch as it allows specifying
19428      of locality.  */
19429   if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
19430     operands[2] = GEN_INT (3);
19431   else
19432     operands[1] = const0_rtx;
19435 (define_insn "*prefetch_sse"
19436   [(prefetch (match_operand:SI 0 "address_operand" "p")
19437              (const_int 0)
19438              (match_operand:SI 1 "const_int_operand" ""))]
19439   "TARGET_PREFETCH_SSE && !TARGET_64BIT"
19441   static const char * const patterns[4] = {
19442    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
19443   };
19445   int locality = INTVAL (operands[1]);
19446   if (locality < 0 || locality > 3)
19447     abort ();
19449   return patterns[locality];  
19451   [(set_attr "type" "sse")
19452    (set_attr "memory" "none")])
19454 (define_insn "*prefetch_sse_rex"
19455   [(prefetch (match_operand:DI 0 "address_operand" "p")
19456              (const_int 0)
19457              (match_operand:SI 1 "const_int_operand" ""))]
19458   "TARGET_PREFETCH_SSE && TARGET_64BIT"
19460   static const char * const patterns[4] = {
19461    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
19462   };
19464   int locality = INTVAL (operands[1]);
19465   if (locality < 0 || locality > 3)
19466     abort ();
19468   return patterns[locality];  
19470   [(set_attr "type" "sse")
19471    (set_attr "memory" "none")])
19473 (define_insn "*prefetch_3dnow"
19474   [(prefetch (match_operand:SI 0 "address_operand" "p")
19475              (match_operand:SI 1 "const_int_operand" "n")
19476              (const_int 3))]
19477   "TARGET_3DNOW && !TARGET_64BIT"
19479   if (INTVAL (operands[1]) == 0)
19480     return "prefetch\t%a0";
19481   else
19482     return "prefetchw\t%a0";
19484   [(set_attr "type" "mmx")
19485    (set_attr "memory" "none")])
19487 (define_insn "*prefetch_3dnow_rex"
19488   [(prefetch (match_operand:DI 0 "address_operand" "p")
19489              (match_operand:SI 1 "const_int_operand" "n")
19490              (const_int 3))]
19491   "TARGET_3DNOW && TARGET_64BIT"
19493   if (INTVAL (operands[1]) == 0)
19494     return "prefetch\t%a0";
19495   else
19496     return "prefetchw\t%a0";
19498   [(set_attr "type" "mmx")
19499    (set_attr "memory" "none")])
19501 (include "sse.md")
19502 (include "mmx.md")