Merge branch 'master' of ssh://crater.dragonflybsd.org/repository/git/dragonfly
[dragonfly.git] / contrib / gcc-3.4 / gcc / config / i386 / i386.md
1 ;; GCC machine description for IA-32 and x86-64.
2 ;; Copyright (C) 1988, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
3 ;; 2001, 2002, 2003, 2004
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.
14 ;;
15 ;; GCC is distributed in the hope that it will be useful,
16 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18 ;; GNU General Public License for more details.
19 ;;
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GCC; see the file COPYING.  If not, write to
22 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
23 ;; Boston, MA 02111-1307, USA.  */
24 ;;
25 ;; The original PO technology requires these to be ordered by speed,
26 ;; so that assigner will pick the fastest.
27 ;;
28 ;; See file "rtl.def" for documentation on define_insn, match_*, et. al.
29 ;;
30 ;; Macro REG_CLASS_FROM_LETTER in file i386.h defines the register
31 ;; constraint letters.
32 ;;
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.
43 ;;
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.
50
51 ;; UNSPEC usage:
52
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)
64
65    ; Prologue support
66    (UNSPEC_STACK_ALLOC          11)
67    (UNSPEC_SET_GOT              12)
68    (UNSPEC_SSE_PROLOGUE_SAVE    13)
69
70    ; TLS support
71    (UNSPEC_TP                   15)
72    (UNSPEC_TLS_GD               16)
73    (UNSPEC_TLS_LD_BASE          17)
74
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)
84
85    ; For SSE/MMX support:
86    (UNSPEC_FIX                  30)
87    (UNSPEC_MASKMOV              32)
88    (UNSPEC_MOVMSK               33)
89    (UNSPEC_MOVNT                34)
90    (UNSPEC_MOVA                 38)
91    (UNSPEC_MOVU                 39)
92    (UNSPEC_SHUFFLE              41)
93    (UNSPEC_RCP                  42)
94    (UNSPEC_RSQRT                43)
95    (UNSPEC_SFENCE               44)
96    (UNSPEC_NOP                  45)     ; prevents combiner cleverness
97    (UNSPEC_PAVGUSB              49)
98    (UNSPEC_PFRCP                50)
99    (UNSPEC_PFRCPIT1             51)
100    (UNSPEC_PFRCPIT2             52)
101    (UNSPEC_PFRSQRT              53)
102    (UNSPEC_PFRSQIT1             54)
103    (UNSPEC_PSHUFLW              55)
104    (UNSPEC_PSHUFHW              56)
105    (UNSPEC_MFENCE               59)
106    (UNSPEC_LFENCE               60)
107    (UNSPEC_PSADBW               61)
108    (UNSPEC_ADDSUB               71)
109    (UNSPEC_HADD                 72)
110    (UNSPEC_HSUB                 73)
111    (UNSPEC_MOVSHDUP             74)
112    (UNSPEC_MOVSLDUP             75)
113    (UNSPEC_LDQQU                76)
114    (UNSPEC_MOVDDUP              77)
115
116    ; x87 Floating point
117    (UNSPEC_FPATAN               65)
118    (UNSPEC_FYL2X                66)
119    (UNSPEC_FSCALE               67)
120    (UNSPEC_FRNDINT              68)
121    (UNSPEC_F2XM1                69)
122
123    ; REP instruction
124    (UNSPEC_REP                  75)
125   ])
126
127 (define_constants
128   [(UNSPECV_BLOCKAGE            0)
129    (UNSPECV_STACK_PROBE         10)
130    (UNSPECV_EH_RETURN           13)
131    (UNSPECV_EMMS                31)
132    (UNSPECV_LDMXCSR             37)
133    (UNSPECV_STMXCSR             40)
134    (UNSPECV_FEMMS               46)
135    (UNSPECV_CLFLUSH             57)
136    (UNSPECV_ALIGN               68)
137    (UNSPECV_MONITOR             69)
138    (UNSPECV_MWAIT               70)
139   ])
140
141 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
142 ;; from i386.c.
143
144 ;; In C guard expressions, put expressions which may be compile-time
145 ;; constants first.  This allows for better optimization.  For
146 ;; example, write "TARGET_64BIT && reload_completed", not
147 ;; "reload_completed && TARGET_64BIT".
148
149 \f
150 ;; Processor type.  This attribute must exactly match the processor_type
151 ;; enumeration in i386.h.
152 (define_attr "cpu" "i386,i486,pentium,pentiumpro,k6,athlon,pentium4,k8"
153   (const (symbol_ref "ix86_tune")))
154
155 ;; A basic instruction type.  Refinements due to arguments to be
156 ;; provided in other attributes.
157 (define_attr "type"
158   "other,multi,
159    alu,alu1,negnot,imov,imovx,lea,
160    incdec,ishift,ishift1,rotate,rotate1,imul,idiv,
161    icmp,test,ibr,setcc,icmov,
162    push,pop,call,callv,leave,
163    str,cld,
164    fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,
165    sselog,sseiadd,sseishft,sseimul,
166    sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv,
167    mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft"
168   (const_string "other"))
169
170 ;; Main data type used by the insn
171 (define_attr "mode"
172   "unknown,none,QI,HI,SI,DI,SF,DF,XF,TI,V4SF,V2DF,V2SF"
173   (const_string "unknown"))
174
175 ;; The CPU unit operations uses.
176 (define_attr "unit" "integer,i387,sse,mmx,unknown"
177   (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp")
178            (const_string "i387")
179          (eq_attr "type" "sselog,sseiadd,sseishft,sseimul,
180                           sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv")
181            (const_string "sse")
182          (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft")
183            (const_string "mmx")
184          (eq_attr "type" "other")
185            (const_string "unknown")]
186          (const_string "integer")))
187
188 ;; The (bounding maximum) length of an instruction immediate.
189 (define_attr "length_immediate" ""
190   (cond [(eq_attr "type" "incdec,setcc,icmov,str,cld,lea,other,multi,idiv,leave")
191            (const_int 0)
192          (eq_attr "unit" "i387,sse,mmx")
193            (const_int 0)
194          (eq_attr "type" "alu,alu1,negnot,imovx,ishift,rotate,ishift1,rotate1,
195                           imul,icmp,push,pop")
196            (symbol_ref "ix86_attr_length_immediate_default(insn,1)")
197          (eq_attr "type" "imov,test")
198            (symbol_ref "ix86_attr_length_immediate_default(insn,0)")
199          (eq_attr "type" "call")
200            (if_then_else (match_operand 0 "constant_call_address_operand" "")
201              (const_int 4)
202              (const_int 0))
203          (eq_attr "type" "callv")
204            (if_then_else (match_operand 1 "constant_call_address_operand" "")
205              (const_int 4)
206              (const_int 0))
207          ;; We don't know the size before shorten_branches.  Expect
208          ;; the instruction to fit for better scheduling.
209          (eq_attr "type" "ibr")
210            (const_int 1)
211          ]
212          (symbol_ref "/* Update immediate_length and other attributes! */
213                       abort(),1")))
214
215 ;; The (bounding maximum) length of an instruction address.
216 (define_attr "length_address" ""
217   (cond [(eq_attr "type" "str,cld,other,multi,fxch")
218            (const_int 0)
219          (and (eq_attr "type" "call")
220               (match_operand 0 "constant_call_address_operand" ""))
221              (const_int 0)
222          (and (eq_attr "type" "callv")
223               (match_operand 1 "constant_call_address_operand" ""))
224              (const_int 0)
225          ]
226          (symbol_ref "ix86_attr_length_address_default (insn)")))
227
228 ;; Set when length prefix is used.
229 (define_attr "prefix_data16" ""
230   (if_then_else (ior (eq_attr "mode" "HI")
231                      (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF")))
232     (const_int 1)
233     (const_int 0)))
234
235 ;; Set when string REP prefix is used.
236 (define_attr "prefix_rep" "" 
237   (if_then_else (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF"))
238     (const_int 1)
239     (const_int 0)))
240
241 ;; Set when 0f opcode prefix is used.
242 (define_attr "prefix_0f" ""
243   (if_then_else 
244     (ior (eq_attr "type" "imovx,setcc,icmov")
245          (eq_attr "unit" "sse,mmx"))
246     (const_int 1)
247     (const_int 0)))
248
249 ;; Set when 0f opcode prefix is used.
250 (define_attr "prefix_rex" ""
251   (cond [(and (eq_attr "mode" "DI")
252               (eq_attr "type" "!push,pop,call,callv,leave,ibr"))
253            (const_int 1)
254          (and (eq_attr "mode" "QI")
255               (ne (symbol_ref "x86_extended_QIreg_mentioned_p (insn)")
256                   (const_int 0)))
257            (const_int 1)
258          (ne (symbol_ref "x86_extended_reg_mentioned_p (insn)")
259              (const_int 0))
260            (const_int 1)
261         ]
262         (const_int 0)))
263
264 ;; Set when modrm byte is used.
265 (define_attr "modrm" ""
266   (cond [(eq_attr "type" "str,cld,leave")
267            (const_int 0)
268          (eq_attr "unit" "i387")
269            (const_int 0)
270          (and (eq_attr "type" "incdec")
271               (ior (match_operand:SI 1 "register_operand" "")
272                    (match_operand:HI 1 "register_operand" "")))
273            (const_int 0)
274          (and (eq_attr "type" "push")
275               (not (match_operand 1 "memory_operand" "")))
276            (const_int 0)
277          (and (eq_attr "type" "pop")
278               (not (match_operand 0 "memory_operand" "")))
279            (const_int 0)
280          (and (eq_attr "type" "imov")
281               (and (match_operand 0 "register_operand" "")
282                    (match_operand 1 "immediate_operand" "")))
283            (const_int 0)
284          (and (eq_attr "type" "call")
285               (match_operand 0 "constant_call_address_operand" ""))
286              (const_int 0)
287          (and (eq_attr "type" "callv")
288               (match_operand 1 "constant_call_address_operand" ""))
289              (const_int 0)
290          ]
291          (const_int 1)))
292
293 ;; The (bounding maximum) length of an instruction in bytes.
294 ;; ??? fistp is in fact fldcw/fistp/fldcw sequence.  Later we may want
295 ;; to split it and compute proper length as for other insns.
296 (define_attr "length" ""
297   (cond [(eq_attr "type" "other,multi,fistp")
298            (const_int 16)
299          (eq_attr "type" "fcmp")
300            (const_int 4)
301          (eq_attr "unit" "i387")
302            (plus (const_int 2)
303                  (plus (attr "prefix_data16")
304                        (attr "length_address")))]
305          (plus (plus (attr "modrm")
306                      (plus (attr "prefix_0f")
307                            (plus (attr "prefix_rex")
308                                  (const_int 1))))
309                (plus (attr "prefix_rep")
310                      (plus (attr "prefix_data16")
311                            (plus (attr "length_immediate")
312                                  (attr "length_address")))))))
313
314 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
315 ;; `store' if there is a simple memory reference therein, or `unknown'
316 ;; if the instruction is complex.
317
318 (define_attr "memory" "none,load,store,both,unknown"
319   (cond [(eq_attr "type" "other,multi,str")
320            (const_string "unknown")
321          (eq_attr "type" "lea,fcmov,fpspc,cld")
322            (const_string "none")
323          (eq_attr "type" "fistp,leave")
324            (const_string "both")
325          (eq_attr "type" "push")
326            (if_then_else (match_operand 1 "memory_operand" "")
327              (const_string "both")
328              (const_string "store"))
329          (eq_attr "type" "pop")
330            (if_then_else (match_operand 0 "memory_operand" "")
331              (const_string "both")
332              (const_string "load"))
333          (eq_attr "type" "setcc")
334            (if_then_else (match_operand 0 "memory_operand" "")
335              (const_string "store")
336              (const_string "none"))
337          (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp")
338            (if_then_else (ior (match_operand 0 "memory_operand" "")
339                               (match_operand 1 "memory_operand" ""))
340              (const_string "load")
341              (const_string "none"))
342          (eq_attr "type" "ibr")
343            (if_then_else (match_operand 0 "memory_operand" "")
344              (const_string "load")
345              (const_string "none"))
346          (eq_attr "type" "call")
347            (if_then_else (match_operand 0 "constant_call_address_operand" "")
348              (const_string "none")
349              (const_string "load"))
350          (eq_attr "type" "callv")
351            (if_then_else (match_operand 1 "constant_call_address_operand" "")
352              (const_string "none")
353              (const_string "load"))
354          (and (eq_attr "type" "alu1,negnot,ishift1")
355               (match_operand 1 "memory_operand" ""))
356            (const_string "both")
357          (and (match_operand 0 "memory_operand" "")
358               (match_operand 1 "memory_operand" ""))
359            (const_string "both")
360          (match_operand 0 "memory_operand" "")
361            (const_string "store")
362          (match_operand 1 "memory_operand" "")
363            (const_string "load")
364          (and (eq_attr "type"
365                  "!alu1,negnot,ishift1,
366                    imov,imovx,icmp,test,
367                    fmov,fcmp,fsgn,
368                    sse,ssemov,ssecmp,ssecomi,ssecvt,sseicvt,
369                    mmx,mmxmov,mmxcmp,mmxcvt")
370               (match_operand 2 "memory_operand" ""))
371            (const_string "load")
372          (and (eq_attr "type" "icmov")
373               (match_operand 3 "memory_operand" ""))
374            (const_string "load")
375         ]
376         (const_string "none")))
377
378 ;; Indicates if an instruction has both an immediate and a displacement.
379
380 (define_attr "imm_disp" "false,true,unknown"
381   (cond [(eq_attr "type" "other,multi")
382            (const_string "unknown")
383          (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1")
384               (and (match_operand 0 "memory_displacement_operand" "")
385                    (match_operand 1 "immediate_operand" "")))
386            (const_string "true")
387          (and (eq_attr "type" "alu,ishift,rotate,imul,idiv")
388               (and (match_operand 0 "memory_displacement_operand" "")
389                    (match_operand 2 "immediate_operand" "")))
390            (const_string "true")
391         ]
392         (const_string "false")))
393
394 ;; Indicates if an FP operation has an integer source.
395
396 (define_attr "fp_int_src" "false,true"
397   (const_string "false"))
398
399 ;; Describe a user's asm statement.
400 (define_asm_attributes
401   [(set_attr "length" "128")
402    (set_attr "type" "multi")])
403 \f
404 (include "pentium.md")
405 (include "ppro.md")
406 (include "k6.md")
407 (include "athlon.md")
408 \f
409 ;; Compare instructions.
410
411 ;; All compare insns have expanders that save the operands away without
412 ;; actually generating RTL.  The bCOND or sCOND (emitted immediately
413 ;; after the cmp) will actually emit the cmpM.
414
415 (define_expand "cmpdi"
416   [(set (reg:CC 17)
417         (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
418                     (match_operand:DI 1 "x86_64_general_operand" "")))]
419   ""
420 {
421   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
422     operands[0] = force_reg (DImode, operands[0]);
423   ix86_compare_op0 = operands[0];
424   ix86_compare_op1 = operands[1];
425   DONE;
426 })
427
428 (define_expand "cmpsi"
429   [(set (reg:CC 17)
430         (compare:CC (match_operand:SI 0 "cmpsi_operand" "")
431                     (match_operand:SI 1 "general_operand" "")))]
432   ""
433 {
434   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
435     operands[0] = force_reg (SImode, operands[0]);
436   ix86_compare_op0 = operands[0];
437   ix86_compare_op1 = operands[1];
438   DONE;
439 })
440
441 (define_expand "cmphi"
442   [(set (reg:CC 17)
443         (compare:CC (match_operand:HI 0 "nonimmediate_operand" "")
444                     (match_operand:HI 1 "general_operand" "")))]
445   ""
446 {
447   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
448     operands[0] = force_reg (HImode, operands[0]);
449   ix86_compare_op0 = operands[0];
450   ix86_compare_op1 = operands[1];
451   DONE;
452 })
453
454 (define_expand "cmpqi"
455   [(set (reg:CC 17)
456         (compare:CC (match_operand:QI 0 "nonimmediate_operand" "")
457                     (match_operand:QI 1 "general_operand" "")))]
458   "TARGET_QIMODE_MATH"
459 {
460   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
461     operands[0] = force_reg (QImode, operands[0]);
462   ix86_compare_op0 = operands[0];
463   ix86_compare_op1 = operands[1];
464   DONE;
465 })
466
467 (define_insn "cmpdi_ccno_1_rex64"
468   [(set (reg 17)
469         (compare (match_operand:DI 0 "nonimmediate_operand" "r,?mr")
470                  (match_operand:DI 1 "const0_operand" "n,n")))]
471   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
472   "@
473    test{q}\t{%0, %0|%0, %0}
474    cmp{q}\t{%1, %0|%0, %1}"
475   [(set_attr "type" "test,icmp")
476    (set_attr "length_immediate" "0,1")
477    (set_attr "mode" "DI")])
478
479 (define_insn "*cmpdi_minus_1_rex64"
480   [(set (reg 17)
481         (compare (minus:DI (match_operand:DI 0 "nonimmediate_operand" "rm,r")
482                            (match_operand:DI 1 "x86_64_general_operand" "re,mr"))
483                  (const_int 0)))]
484   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)"
485   "cmp{q}\t{%1, %0|%0, %1}"
486   [(set_attr "type" "icmp")
487    (set_attr "mode" "DI")])
488
489 (define_expand "cmpdi_1_rex64"
490   [(set (reg:CC 17)
491         (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
492                     (match_operand:DI 1 "general_operand" "")))]
493   "TARGET_64BIT"
494   "")
495
496 (define_insn "cmpdi_1_insn_rex64"
497   [(set (reg 17)
498         (compare (match_operand:DI 0 "nonimmediate_operand" "mr,r")
499                  (match_operand:DI 1 "x86_64_general_operand" "re,mr")))]
500   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
501   "cmp{q}\t{%1, %0|%0, %1}"
502   [(set_attr "type" "icmp")
503    (set_attr "mode" "DI")])
504
505
506 (define_insn "*cmpsi_ccno_1"
507   [(set (reg 17)
508         (compare (match_operand:SI 0 "nonimmediate_operand" "r,?mr")
509                  (match_operand:SI 1 "const0_operand" "n,n")))]
510   "ix86_match_ccmode (insn, CCNOmode)"
511   "@
512    test{l}\t{%0, %0|%0, %0}
513    cmp{l}\t{%1, %0|%0, %1}"
514   [(set_attr "type" "test,icmp")
515    (set_attr "length_immediate" "0,1")
516    (set_attr "mode" "SI")])
517
518 (define_insn "*cmpsi_minus_1"
519   [(set (reg 17)
520         (compare (minus:SI (match_operand:SI 0 "nonimmediate_operand" "rm,r")
521                            (match_operand:SI 1 "general_operand" "ri,mr"))
522                  (const_int 0)))]
523   "ix86_match_ccmode (insn, CCGOCmode)"
524   "cmp{l}\t{%1, %0|%0, %1}"
525   [(set_attr "type" "icmp")
526    (set_attr "mode" "SI")])
527
528 (define_expand "cmpsi_1"
529   [(set (reg:CC 17)
530         (compare:CC (match_operand:SI 0 "nonimmediate_operand" "rm,r")
531                     (match_operand:SI 1 "general_operand" "ri,mr")))]
532   ""
533   "")
534
535 (define_insn "*cmpsi_1_insn"
536   [(set (reg 17)
537         (compare (match_operand:SI 0 "nonimmediate_operand" "rm,r")
538                  (match_operand:SI 1 "general_operand" "ri,mr")))]
539   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
540     && ix86_match_ccmode (insn, CCmode)"
541   "cmp{l}\t{%1, %0|%0, %1}"
542   [(set_attr "type" "icmp")
543    (set_attr "mode" "SI")])
544
545 (define_insn "*cmphi_ccno_1"
546   [(set (reg 17)
547         (compare (match_operand:HI 0 "nonimmediate_operand" "r,?mr")
548                  (match_operand:HI 1 "const0_operand" "n,n")))]
549   "ix86_match_ccmode (insn, CCNOmode)"
550   "@
551    test{w}\t{%0, %0|%0, %0}
552    cmp{w}\t{%1, %0|%0, %1}"
553   [(set_attr "type" "test,icmp")
554    (set_attr "length_immediate" "0,1")
555    (set_attr "mode" "HI")])
556
557 (define_insn "*cmphi_minus_1"
558   [(set (reg 17)
559         (compare (minus:HI (match_operand:HI 0 "nonimmediate_operand" "rm,r")
560                            (match_operand:HI 1 "general_operand" "ri,mr"))
561                  (const_int 0)))]
562   "ix86_match_ccmode (insn, CCGOCmode)"
563   "cmp{w}\t{%1, %0|%0, %1}"
564   [(set_attr "type" "icmp")
565    (set_attr "mode" "HI")])
566
567 (define_insn "*cmphi_1"
568   [(set (reg 17)
569         (compare (match_operand:HI 0 "nonimmediate_operand" "rm,r")
570                  (match_operand:HI 1 "general_operand" "ri,mr")))]
571   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
572    && ix86_match_ccmode (insn, CCmode)"
573   "cmp{w}\t{%1, %0|%0, %1}"
574   [(set_attr "type" "icmp")
575    (set_attr "mode" "HI")])
576
577 (define_insn "*cmpqi_ccno_1"
578   [(set (reg 17)
579         (compare (match_operand:QI 0 "nonimmediate_operand" "q,?mq")
580                  (match_operand:QI 1 "const0_operand" "n,n")))]
581   "ix86_match_ccmode (insn, CCNOmode)"
582   "@
583    test{b}\t{%0, %0|%0, %0}
584    cmp{b}\t{$0, %0|%0, 0}"
585   [(set_attr "type" "test,icmp")
586    (set_attr "length_immediate" "0,1")
587    (set_attr "mode" "QI")])
588
589 (define_insn "*cmpqi_1"
590   [(set (reg 17)
591         (compare (match_operand:QI 0 "nonimmediate_operand" "qm,q")
592                  (match_operand:QI 1 "general_operand" "qi,mq")))]
593   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
594     && ix86_match_ccmode (insn, CCmode)"
595   "cmp{b}\t{%1, %0|%0, %1}"
596   [(set_attr "type" "icmp")
597    (set_attr "mode" "QI")])
598
599 (define_insn "*cmpqi_minus_1"
600   [(set (reg 17)
601         (compare (minus:QI (match_operand:QI 0 "nonimmediate_operand" "qm,q")
602                            (match_operand:QI 1 "general_operand" "qi,mq"))
603                  (const_int 0)))]
604   "ix86_match_ccmode (insn, CCGOCmode)"
605   "cmp{b}\t{%1, %0|%0, %1}"
606   [(set_attr "type" "icmp")
607    (set_attr "mode" "QI")])
608
609 (define_insn "*cmpqi_ext_1"
610   [(set (reg 17)
611         (compare
612           (match_operand:QI 0 "general_operand" "Qm")
613           (subreg:QI
614             (zero_extract:SI
615               (match_operand 1 "ext_register_operand" "Q")
616               (const_int 8)
617               (const_int 8)) 0)))]
618   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
619   "cmp{b}\t{%h1, %0|%0, %h1}"
620   [(set_attr "type" "icmp")
621    (set_attr "mode" "QI")])
622
623 (define_insn "*cmpqi_ext_1_rex64"
624   [(set (reg 17)
625         (compare
626           (match_operand:QI 0 "register_operand" "Q")
627           (subreg:QI
628             (zero_extract:SI
629               (match_operand 1 "ext_register_operand" "Q")
630               (const_int 8)
631               (const_int 8)) 0)))]
632   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
633   "cmp{b}\t{%h1, %0|%0, %h1}"
634   [(set_attr "type" "icmp")
635    (set_attr "mode" "QI")])
636
637 (define_insn "*cmpqi_ext_2"
638   [(set (reg 17)
639         (compare
640           (subreg:QI
641             (zero_extract:SI
642               (match_operand 0 "ext_register_operand" "Q")
643               (const_int 8)
644               (const_int 8)) 0)
645           (match_operand:QI 1 "const0_operand" "n")))]
646   "ix86_match_ccmode (insn, CCNOmode)"
647   "test{b}\t%h0, %h0"
648   [(set_attr "type" "test")
649    (set_attr "length_immediate" "0")
650    (set_attr "mode" "QI")])
651
652 (define_expand "cmpqi_ext_3"
653   [(set (reg:CC 17)
654         (compare:CC
655           (subreg:QI
656             (zero_extract:SI
657               (match_operand 0 "ext_register_operand" "")
658               (const_int 8)
659               (const_int 8)) 0)
660           (match_operand:QI 1 "general_operand" "")))]
661   ""
662   "")
663
664 (define_insn "cmpqi_ext_3_insn"
665   [(set (reg 17)
666         (compare
667           (subreg:QI
668             (zero_extract:SI
669               (match_operand 0 "ext_register_operand" "Q")
670               (const_int 8)
671               (const_int 8)) 0)
672           (match_operand:QI 1 "general_operand" "Qmn")))]
673   "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
674   "cmp{b}\t{%1, %h0|%h0, %1}"
675   [(set_attr "type" "icmp")
676    (set_attr "mode" "QI")])
677
678 (define_insn "cmpqi_ext_3_insn_rex64"
679   [(set (reg 17)
680         (compare
681           (subreg:QI
682             (zero_extract:SI
683               (match_operand 0 "ext_register_operand" "Q")
684               (const_int 8)
685               (const_int 8)) 0)
686           (match_operand:QI 1 "nonmemory_operand" "Qn")))]
687   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
688   "cmp{b}\t{%1, %h0|%h0, %1}"
689   [(set_attr "type" "icmp")
690    (set_attr "mode" "QI")])
691
692 (define_insn "*cmpqi_ext_4"
693   [(set (reg 17)
694         (compare
695           (subreg:QI
696             (zero_extract:SI
697               (match_operand 0 "ext_register_operand" "Q")
698               (const_int 8)
699               (const_int 8)) 0)
700           (subreg:QI
701             (zero_extract:SI
702               (match_operand 1 "ext_register_operand" "Q")
703               (const_int 8)
704               (const_int 8)) 0)))]
705   "ix86_match_ccmode (insn, CCmode)"
706   "cmp{b}\t{%h1, %h0|%h0, %h1}"
707   [(set_attr "type" "icmp")
708    (set_attr "mode" "QI")])
709
710 ;; These implement float point compares.
711 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
712 ;; which would allow mix and match FP modes on the compares.  Which is what
713 ;; the old patterns did, but with many more of them.
714
715 (define_expand "cmpxf"
716   [(set (reg:CC 17)
717         (compare:CC (match_operand:XF 0 "cmp_fp_expander_operand" "")
718                     (match_operand:XF 1 "cmp_fp_expander_operand" "")))]
719   "TARGET_80387"
720 {
721   ix86_compare_op0 = operands[0];
722   ix86_compare_op1 = operands[1];
723   DONE;
724 })
725
726 (define_expand "cmpdf"
727   [(set (reg:CC 17)
728         (compare:CC (match_operand:DF 0 "cmp_fp_expander_operand" "")
729                     (match_operand:DF 1 "cmp_fp_expander_operand" "")))]
730   "TARGET_80387 || TARGET_SSE2"
731 {
732   ix86_compare_op0 = operands[0];
733   ix86_compare_op1 = operands[1];
734   DONE;
735 })
736
737 (define_expand "cmpsf"
738   [(set (reg:CC 17)
739         (compare:CC (match_operand:SF 0 "cmp_fp_expander_operand" "")
740                     (match_operand:SF 1 "cmp_fp_expander_operand" "")))]
741   "TARGET_80387 || TARGET_SSE"
742 {
743   ix86_compare_op0 = operands[0];
744   ix86_compare_op1 = operands[1];
745   DONE;
746 })
747
748 ;; FP compares, step 1:
749 ;; Set the FP condition codes.
750 ;;
751 ;; CCFPmode     compare with exceptions
752 ;; CCFPUmode    compare with no exceptions
753
754 ;; %%% It is an unfortunate fact that ftst has no non-popping variant,
755 ;; and that fp moves clobber the condition codes, and that there is
756 ;; currently no way to describe this fact to reg-stack.  So there are
757 ;; no splitters yet for this.
758
759 ;; %%% YIKES!  This scheme does not retain a strong connection between 
760 ;; the real compare and the ultimate cc0 user, so CC_REVERSE does not
761 ;; work!  Only allow tos/mem with tos in op 0.
762 ;;
763 ;; Hmm, of course, this is what the actual _hardware_ does.  Perhaps
764 ;; things aren't as bad as they sound...
765
766 (define_insn "*cmpfp_0"
767   [(set (match_operand:HI 0 "register_operand" "=a")
768         (unspec:HI
769           [(compare:CCFP (match_operand 1 "register_operand" "f")
770                          (match_operand 2 "const0_operand" "X"))]
771           UNSPEC_FNSTSW))]
772   "TARGET_80387
773    && FLOAT_MODE_P (GET_MODE (operands[1]))
774    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
775 {
776   if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
777     return "ftst\;fnstsw\t%0\;fstp\t%y0";
778   else
779     return "ftst\;fnstsw\t%0";
780 }
781   [(set_attr "type" "multi")
782    (set (attr "mode")
783      (cond [(match_operand:SF 1 "" "")
784               (const_string "SF")
785             (match_operand:DF 1 "" "")
786               (const_string "DF")
787            ]
788            (const_string "XF")))])
789
790 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
791 ;; used to manage the reg stack popping would not be preserved.
792
793 (define_insn "*cmpfp_2_sf"
794   [(set (reg:CCFP 18)
795         (compare:CCFP
796           (match_operand:SF 0 "register_operand" "f")
797           (match_operand:SF 1 "nonimmediate_operand" "fm")))]
798   "TARGET_80387"
799   "* return output_fp_compare (insn, operands, 0, 0);"
800   [(set_attr "type" "fcmp")
801    (set_attr "mode" "SF")])
802
803 (define_insn "*cmpfp_2_sf_1"
804   [(set (match_operand:HI 0 "register_operand" "=a")
805         (unspec:HI
806           [(compare:CCFP
807              (match_operand:SF 1 "register_operand" "f")
808              (match_operand:SF 2 "nonimmediate_operand" "fm"))]
809           UNSPEC_FNSTSW))]
810   "TARGET_80387"
811   "* return output_fp_compare (insn, operands, 2, 0);"
812   [(set_attr "type" "fcmp")
813    (set_attr "mode" "SF")])
814
815 (define_insn "*cmpfp_2_df"
816   [(set (reg:CCFP 18)
817         (compare:CCFP
818           (match_operand:DF 0 "register_operand" "f")
819           (match_operand:DF 1 "nonimmediate_operand" "fm")))]
820   "TARGET_80387"
821   "* return output_fp_compare (insn, operands, 0, 0);"
822   [(set_attr "type" "fcmp")
823    (set_attr "mode" "DF")])
824
825 (define_insn "*cmpfp_2_df_1"
826   [(set (match_operand:HI 0 "register_operand" "=a")
827         (unspec:HI
828           [(compare:CCFP
829              (match_operand:DF 1 "register_operand" "f")
830              (match_operand:DF 2 "nonimmediate_operand" "fm"))]
831           UNSPEC_FNSTSW))]
832   "TARGET_80387"
833   "* return output_fp_compare (insn, operands, 2, 0);"
834   [(set_attr "type" "multi")
835    (set_attr "mode" "DF")])
836
837 (define_insn "*cmpfp_2_xf"
838   [(set (reg:CCFP 18)
839         (compare:CCFP
840           (match_operand:XF 0 "register_operand" "f")
841           (match_operand:XF 1 "register_operand" "f")))]
842   "TARGET_80387"
843   "* return output_fp_compare (insn, operands, 0, 0);"
844   [(set_attr "type" "fcmp")
845    (set_attr "mode" "XF")])
846
847 (define_insn "*cmpfp_2_xf_1"
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 "register_operand" "f"))]
853           UNSPEC_FNSTSW))]
854   "TARGET_80387"
855   "* return output_fp_compare (insn, operands, 2, 0);"
856   [(set_attr "type" "multi")
857    (set_attr "mode" "XF")])
858
859 (define_insn "*cmpfp_2u"
860   [(set (reg:CCFPU 18)
861         (compare:CCFPU
862           (match_operand 0 "register_operand" "f")
863           (match_operand 1 "register_operand" "f")))]
864   "TARGET_80387
865    && FLOAT_MODE_P (GET_MODE (operands[0]))
866    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
867   "* return output_fp_compare (insn, operands, 0, 1);"
868   [(set_attr "type" "fcmp")
869    (set (attr "mode")
870      (cond [(match_operand:SF 1 "" "")
871               (const_string "SF")
872             (match_operand:DF 1 "" "")
873               (const_string "DF")
874            ]
875            (const_string "XF")))])
876
877 (define_insn "*cmpfp_2u_1"
878   [(set (match_operand:HI 0 "register_operand" "=a")
879         (unspec:HI
880           [(compare:CCFPU
881              (match_operand 1 "register_operand" "f")
882              (match_operand 2 "register_operand" "f"))]
883           UNSPEC_FNSTSW))]
884   "TARGET_80387
885    && FLOAT_MODE_P (GET_MODE (operands[1]))
886    && GET_MODE (operands[1]) == GET_MODE (operands[2])"
887   "* return output_fp_compare (insn, operands, 2, 1);"
888   [(set_attr "type" "multi")
889    (set (attr "mode")
890      (cond [(match_operand:SF 1 "" "")
891               (const_string "SF")
892             (match_operand:DF 1 "" "")
893               (const_string "DF")
894            ]
895            (const_string "XF")))])
896
897 ;; Patterns to match the SImode-in-memory ficom instructions.
898 ;;
899 ;; %%% Play games with accepting gp registers, as otherwise we have to
900 ;; force them to memory during rtl generation, which is no good.  We
901 ;; can get rid of this once we teach reload to do memory input reloads 
902 ;; via pushes.
903
904 (define_insn "*ficom_1"
905   [(set (reg:CCFP 18)
906         (compare:CCFP
907           (match_operand 0 "register_operand" "f,f")
908           (float (match_operand:SI 1 "nonimmediate_operand" "m,?r"))))]
909   "0 && TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[0]))
910    && GET_MODE (XEXP (SET_SRC (PATTERN (insn)), 1)) == GET_MODE (operands[0])"
911   "#")
912
913 ;; Split the not-really-implemented gp register case into a
914 ;; push-op-pop sequence.
915 ;;
916 ;; %%% This is most efficient, but am I gonna get in trouble
917 ;; for separating cc0_setter and cc0_user?
918
919 (define_split
920   [(set (reg:CCFP 18)
921         (compare:CCFP
922           (match_operand:SF 0 "register_operand" "")
923           (float (match_operand:SI 1 "register_operand" ""))))]
924   "0 && TARGET_80387 && reload_completed"
925   [(set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 1))
926    (set (reg:CCFP 18) (compare:CCFP (match_dup 0) (match_dup 2)))
927    (parallel [(set (match_dup 1) (mem:SI (reg:SI 7)))
928               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
929   "operands[2] = gen_rtx_MEM (Pmode, stack_pointer_rtx);
930    operands[2] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[2]);")
931
932 ;; FP compares, step 2
933 ;; Move the fpsw to ax.
934
935 (define_insn "*x86_fnstsw_1"
936   [(set (match_operand:HI 0 "register_operand" "=a")
937         (unspec:HI [(reg 18)] UNSPEC_FNSTSW))]
938   "TARGET_80387"
939   "fnstsw\t%0"
940   [(set_attr "length" "2")
941    (set_attr "mode" "SI")
942    (set_attr "unit" "i387")
943    (set_attr "ppro_uops" "few")])
944
945 ;; FP compares, step 3
946 ;; Get ax into flags, general case.
947
948 (define_insn "x86_sahf_1"
949   [(set (reg:CC 17)
950         (unspec:CC [(match_operand:HI 0 "register_operand" "a")] UNSPEC_SAHF))]
951   "!TARGET_64BIT"
952   "sahf"
953   [(set_attr "length" "1")
954    (set_attr "athlon_decode" "vector")
955    (set_attr "mode" "SI")
956    (set_attr "ppro_uops" "one")])
957
958 ;; Pentium Pro can do steps 1 through 3 in one go.
959
960 (define_insn "*cmpfp_i"
961   [(set (reg:CCFP 17)
962         (compare:CCFP (match_operand 0 "register_operand" "f")
963                       (match_operand 1 "register_operand" "f")))]
964   "TARGET_80387 && TARGET_CMOVE
965    && !SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
966    && FLOAT_MODE_P (GET_MODE (operands[0]))
967    && GET_MODE (operands[0]) == GET_MODE (operands[0])"
968   "* return output_fp_compare (insn, operands, 1, 0);"
969   [(set_attr "type" "fcmp")
970    (set (attr "mode")
971      (cond [(match_operand:SF 1 "" "")
972               (const_string "SF")
973             (match_operand:DF 1 "" "")
974               (const_string "DF")
975            ]
976            (const_string "XF")))
977    (set_attr "athlon_decode" "vector")])
978
979 (define_insn "*cmpfp_i_sse"
980   [(set (reg:CCFP 17)
981         (compare:CCFP (match_operand 0 "register_operand" "f#x,x#f")
982                       (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
983   "TARGET_80387
984    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
985    && GET_MODE (operands[0]) == GET_MODE (operands[0])"
986   "* return output_fp_compare (insn, operands, 1, 0);"
987   [(set_attr "type" "fcmp,ssecomi")
988    (set (attr "mode")
989      (if_then_else (match_operand:SF 1 "" "")
990         (const_string "SF")
991         (const_string "DF")))
992    (set_attr "athlon_decode" "vector")])
993
994 (define_insn "*cmpfp_i_sse_only"
995   [(set (reg:CCFP 17)
996         (compare:CCFP (match_operand 0 "register_operand" "x")
997                       (match_operand 1 "nonimmediate_operand" "xm")))]
998   "SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
999    && GET_MODE (operands[0]) == GET_MODE (operands[0])"
1000   "* return output_fp_compare (insn, operands, 1, 0);"
1001   [(set_attr "type" "ssecomi")
1002    (set (attr "mode")
1003      (if_then_else (match_operand:SF 1 "" "")
1004         (const_string "SF")
1005         (const_string "DF")))
1006    (set_attr "athlon_decode" "vector")])
1007
1008 (define_insn "*cmpfp_iu"
1009   [(set (reg:CCFPU 17)
1010         (compare:CCFPU (match_operand 0 "register_operand" "f")
1011                        (match_operand 1 "register_operand" "f")))]
1012   "TARGET_80387 && TARGET_CMOVE
1013    && !SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1014    && FLOAT_MODE_P (GET_MODE (operands[0]))
1015    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1016   "* return output_fp_compare (insn, operands, 1, 1);"
1017   [(set_attr "type" "fcmp")
1018    (set (attr "mode")
1019      (cond [(match_operand:SF 1 "" "")
1020               (const_string "SF")
1021             (match_operand:DF 1 "" "")
1022               (const_string "DF")
1023            ]
1024            (const_string "XF")))
1025    (set_attr "athlon_decode" "vector")])
1026
1027 (define_insn "*cmpfp_iu_sse"
1028   [(set (reg:CCFPU 17)
1029         (compare:CCFPU (match_operand 0 "register_operand" "f#x,x#f")
1030                        (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
1031   "TARGET_80387
1032    && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1033    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1034   "* return output_fp_compare (insn, operands, 1, 1);"
1035   [(set_attr "type" "fcmp,ssecomi")
1036    (set (attr "mode")
1037      (if_then_else (match_operand:SF 1 "" "")
1038         (const_string "SF")
1039         (const_string "DF")))
1040    (set_attr "athlon_decode" "vector")])
1041
1042 (define_insn "*cmpfp_iu_sse_only"
1043   [(set (reg:CCFPU 17)
1044         (compare:CCFPU (match_operand 0 "register_operand" "x")
1045                        (match_operand 1 "nonimmediate_operand" "xm")))]
1046   "SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1047    && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1048   "* return output_fp_compare (insn, operands, 1, 1);"
1049   [(set_attr "type" "ssecomi")
1050    (set (attr "mode")
1051      (if_then_else (match_operand:SF 1 "" "")
1052         (const_string "SF")
1053         (const_string "DF")))
1054    (set_attr "athlon_decode" "vector")])
1055 \f
1056 ;; Move instructions.
1057
1058 ;; General case of fullword move.
1059
1060 (define_expand "movsi"
1061   [(set (match_operand:SI 0 "nonimmediate_operand" "")
1062         (match_operand:SI 1 "general_operand" ""))]
1063   ""
1064   "ix86_expand_move (SImode, operands); DONE;")
1065
1066 ;; Push/pop instructions.  They are separate since autoinc/dec is not a
1067 ;; general_operand.
1068 ;;
1069 ;; %%% We don't use a post-inc memory reference because x86 is not a 
1070 ;; general AUTO_INC_DEC host, which impacts how it is treated in flow.
1071 ;; Changing this impacts compiler performance on other non-AUTO_INC_DEC
1072 ;; targets without our curiosities, and it is just as easy to represent
1073 ;; this differently.
1074
1075 (define_insn "*pushsi2"
1076   [(set (match_operand:SI 0 "push_operand" "=<")
1077         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1078   "!TARGET_64BIT"
1079   "push{l}\t%1"
1080   [(set_attr "type" "push")
1081    (set_attr "mode" "SI")])
1082
1083 ;; For 64BIT abi we always round up to 8 bytes.
1084 (define_insn "*pushsi2_rex64"
1085   [(set (match_operand:SI 0 "push_operand" "=X")
1086         (match_operand:SI 1 "nonmemory_no_elim_operand" "ri"))]
1087   "TARGET_64BIT"
1088   "push{q}\t%q1"
1089   [(set_attr "type" "push")
1090    (set_attr "mode" "SI")])
1091
1092 (define_insn "*pushsi2_prologue"
1093   [(set (match_operand:SI 0 "push_operand" "=<")
1094         (match_operand:SI 1 "general_no_elim_operand" "ri*m"))
1095    (clobber (mem:BLK (scratch)))]
1096   "!TARGET_64BIT"
1097   "push{l}\t%1"
1098   [(set_attr "type" "push")
1099    (set_attr "mode" "SI")])
1100
1101 (define_insn "*popsi1_epilogue"
1102   [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1103         (mem:SI (reg:SI 7)))
1104    (set (reg:SI 7)
1105         (plus:SI (reg:SI 7) (const_int 4)))
1106    (clobber (mem:BLK (scratch)))]
1107   "!TARGET_64BIT"
1108   "pop{l}\t%0"
1109   [(set_attr "type" "pop")
1110    (set_attr "mode" "SI")])
1111
1112 (define_insn "popsi1"
1113   [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1114         (mem:SI (reg:SI 7)))
1115    (set (reg:SI 7)
1116         (plus:SI (reg:SI 7) (const_int 4)))]
1117   "!TARGET_64BIT"
1118   "pop{l}\t%0"
1119   [(set_attr "type" "pop")
1120    (set_attr "mode" "SI")])
1121
1122 (define_insn "*movsi_xor"
1123   [(set (match_operand:SI 0 "register_operand" "=r")
1124         (match_operand:SI 1 "const0_operand" "i"))
1125    (clobber (reg:CC 17))]
1126   "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1127   "xor{l}\t{%0, %0|%0, %0}"
1128   [(set_attr "type" "alu1")
1129    (set_attr "mode" "SI")
1130    (set_attr "length_immediate" "0")])
1131  
1132 (define_insn "*movsi_or"
1133   [(set (match_operand:SI 0 "register_operand" "=r")
1134         (match_operand:SI 1 "immediate_operand" "i"))
1135    (clobber (reg:CC 17))]
1136   "reload_completed
1137    && operands[1] == constm1_rtx
1138    && (TARGET_PENTIUM || optimize_size)"
1139 {
1140   operands[1] = constm1_rtx;
1141   return "or{l}\t{%1, %0|%0, %1}";
1142 }
1143   [(set_attr "type" "alu1")
1144    (set_attr "mode" "SI")
1145    (set_attr "length_immediate" "1")])
1146
1147 (define_insn "*movsi_1"
1148   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,m,!*y,!rm,!*y,!*Y,!rm,!*Y")
1149         (match_operand:SI 1 "general_operand" "rinm,rin,*y,*y,rm,*Y,*Y,rm"))]
1150   "(TARGET_INTER_UNIT_MOVES || optimize_size)
1151    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1152 {
1153   switch (get_attr_type (insn))
1154     {
1155     case TYPE_SSEMOV:
1156       if (get_attr_mode (insn) == MODE_TI)
1157         return "movdqa\t{%1, %0|%0, %1}";
1158       return "movd\t{%1, %0|%0, %1}";
1159
1160     case TYPE_MMXMOV:
1161       if (get_attr_mode (insn) == MODE_DI)
1162         return "movq\t{%1, %0|%0, %1}";
1163       return "movd\t{%1, %0|%0, %1}";
1164
1165     case TYPE_LEA:
1166       return "lea{l}\t{%1, %0|%0, %1}";
1167
1168     default:
1169       if (flag_pic && !LEGITIMATE_PIC_OPERAND_P (operands[1]))
1170         abort();
1171       return "mov{l}\t{%1, %0|%0, %1}";
1172     }
1173 }
1174   [(set (attr "type")
1175      (cond [(eq_attr "alternative" "2,3,4")
1176               (const_string "mmxmov")
1177             (eq_attr "alternative" "5,6,7")
1178               (const_string "ssemov")
1179             (and (ne (symbol_ref "flag_pic") (const_int 0))
1180                  (match_operand:SI 1 "symbolic_operand" ""))
1181               (const_string "lea")
1182            ]
1183            (const_string "imov")))
1184    (set_attr "mode" "SI,SI,DI,SI,SI,TI,SI,SI")])
1185
1186 (define_insn "*movsi_1_nointernunit"
1187   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,m,!*y,!m,!*y,!*Y,!m,!*Y")
1188         (match_operand:SI 1 "general_operand" "rinm,rin,*y,*y,m,*Y,*Y,m"))]
1189   "(!TARGET_INTER_UNIT_MOVES && !optimize_size)
1190    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1191 {
1192   switch (get_attr_type (insn))
1193     {
1194     case TYPE_SSEMOV:
1195       if (get_attr_mode (insn) == MODE_TI)
1196         return "movdqa\t{%1, %0|%0, %1}";
1197       return "movd\t{%1, %0|%0, %1}";
1198
1199     case TYPE_MMXMOV:
1200       if (get_attr_mode (insn) == MODE_DI)
1201         return "movq\t{%1, %0|%0, %1}";
1202       return "movd\t{%1, %0|%0, %1}";
1203
1204     case TYPE_LEA:
1205       return "lea{l}\t{%1, %0|%0, %1}";
1206
1207     default:
1208       if (flag_pic && !LEGITIMATE_PIC_OPERAND_P (operands[1]))
1209         abort();
1210       return "mov{l}\t{%1, %0|%0, %1}";
1211     }
1212 }
1213   [(set (attr "type")
1214      (cond [(eq_attr "alternative" "2,3,4")
1215               (const_string "mmxmov")
1216             (eq_attr "alternative" "5,6,7")
1217               (const_string "ssemov")
1218             (and (ne (symbol_ref "flag_pic") (const_int 0))
1219                  (match_operand:SI 1 "symbolic_operand" ""))
1220               (const_string "lea")
1221            ]
1222            (const_string "imov")))
1223    (set_attr "mode" "SI,SI,DI,SI,SI,TI,SI,SI")])
1224
1225 ;; Stores and loads of ax to arbitrary constant address.
1226 ;; We fake an second form of instruction to force reload to load address
1227 ;; into register when rax is not available
1228 (define_insn "*movabssi_1_rex64"
1229   [(set (mem:SI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1230         (match_operand:SI 1 "nonmemory_operand" "a,er"))]
1231   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1232   "@
1233    movabs{l}\t{%1, %P0|%P0, %1}
1234    mov{l}\t{%1, %a0|%a0, %1}"
1235   [(set_attr "type" "imov")
1236    (set_attr "modrm" "0,*")
1237    (set_attr "length_address" "8,0")
1238    (set_attr "length_immediate" "0,*")
1239    (set_attr "memory" "store")
1240    (set_attr "mode" "SI")])
1241
1242 (define_insn "*movabssi_2_rex64"
1243   [(set (match_operand:SI 0 "register_operand" "=a,r")
1244         (mem:SI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1245   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1246   "@
1247    movabs{l}\t{%P1, %0|%0, %P1}
1248    mov{l}\t{%a1, %0|%0, %a1}"
1249   [(set_attr "type" "imov")
1250    (set_attr "modrm" "0,*")
1251    (set_attr "length_address" "8,0")
1252    (set_attr "length_immediate" "0")
1253    (set_attr "memory" "load")
1254    (set_attr "mode" "SI")])
1255
1256 (define_insn "*swapsi"
1257   [(set (match_operand:SI 0 "register_operand" "+r")
1258         (match_operand:SI 1 "register_operand" "+r"))
1259    (set (match_dup 1)
1260         (match_dup 0))]
1261   ""
1262   "xchg{l}\t%1, %0"
1263   [(set_attr "type" "imov")
1264    (set_attr "mode" "SI")
1265    (set_attr "pent_pair" "np")
1266    (set_attr "athlon_decode" "vector")
1267    (set_attr "ppro_uops" "few")])
1268
1269 (define_expand "movhi"
1270   [(set (match_operand:HI 0 "nonimmediate_operand" "")
1271         (match_operand:HI 1 "general_operand" ""))]
1272   ""
1273   "ix86_expand_move (HImode, operands); DONE;")
1274
1275 (define_insn "*pushhi2"
1276   [(set (match_operand:HI 0 "push_operand" "=<,<")
1277         (match_operand:HI 1 "general_no_elim_operand" "n,r*m"))]
1278   "!TARGET_64BIT"
1279   "@
1280    push{w}\t{|WORD PTR }%1
1281    push{w}\t%1"
1282   [(set_attr "type" "push")
1283    (set_attr "mode" "HI")])
1284
1285 ;; For 64BIT abi we always round up to 8 bytes.
1286 (define_insn "*pushhi2_rex64"
1287   [(set (match_operand:HI 0 "push_operand" "=X")
1288         (match_operand:HI 1 "nonmemory_no_elim_operand" "ri"))]
1289   "TARGET_64BIT"
1290   "push{q}\t%q1"
1291   [(set_attr "type" "push")
1292    (set_attr "mode" "QI")])
1293
1294 (define_insn "*movhi_1"
1295   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
1296         (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
1297   "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1298 {
1299   switch (get_attr_type (insn))
1300     {
1301     case TYPE_IMOVX:
1302       /* movzwl is faster than movw on p2 due to partial word stalls,
1303          though not as fast as an aligned movl.  */
1304       return "movz{wl|x}\t{%1, %k0|%k0, %1}";
1305     default:
1306       if (get_attr_mode (insn) == MODE_SI)
1307         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1308       else
1309         return "mov{w}\t{%1, %0|%0, %1}";
1310     }
1311 }
1312   [(set (attr "type")
1313      (cond [(and (eq_attr "alternative" "0")
1314                  (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1315                           (const_int 0))
1316                       (eq (symbol_ref "TARGET_HIMODE_MATH")
1317                           (const_int 0))))
1318               (const_string "imov")
1319             (and (eq_attr "alternative" "1,2")
1320                  (match_operand:HI 1 "aligned_operand" ""))
1321               (const_string "imov")
1322             (and (ne (symbol_ref "TARGET_MOVX")
1323                      (const_int 0))
1324                  (eq_attr "alternative" "0,2"))
1325               (const_string "imovx")
1326            ]
1327            (const_string "imov")))
1328     (set (attr "mode")
1329       (cond [(eq_attr "type" "imovx")
1330                (const_string "SI")
1331              (and (eq_attr "alternative" "1,2")
1332                   (match_operand:HI 1 "aligned_operand" ""))
1333                (const_string "SI")
1334              (and (eq_attr "alternative" "0")
1335                   (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1336                            (const_int 0))
1337                        (eq (symbol_ref "TARGET_HIMODE_MATH")
1338                            (const_int 0))))
1339                (const_string "SI")
1340             ]
1341             (const_string "HI")))])
1342
1343 ;; Stores and loads of ax to arbitrary constant address.
1344 ;; We fake an second form of instruction to force reload to load address
1345 ;; into register when rax is not available
1346 (define_insn "*movabshi_1_rex64"
1347   [(set (mem:HI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1348         (match_operand:HI 1 "nonmemory_operand" "a,er"))]
1349   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1350   "@
1351    movabs{w}\t{%1, %P0|%P0, %1}
1352    mov{w}\t{%1, %a0|%a0, %1}"
1353   [(set_attr "type" "imov")
1354    (set_attr "modrm" "0,*")
1355    (set_attr "length_address" "8,0")
1356    (set_attr "length_immediate" "0,*")
1357    (set_attr "memory" "store")
1358    (set_attr "mode" "HI")])
1359
1360 (define_insn "*movabshi_2_rex64"
1361   [(set (match_operand:HI 0 "register_operand" "=a,r")
1362         (mem:HI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1363   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1364   "@
1365    movabs{w}\t{%P1, %0|%0, %P1}
1366    mov{w}\t{%a1, %0|%0, %a1}"
1367   [(set_attr "type" "imov")
1368    (set_attr "modrm" "0,*")
1369    (set_attr "length_address" "8,0")
1370    (set_attr "length_immediate" "0")
1371    (set_attr "memory" "load")
1372    (set_attr "mode" "HI")])
1373
1374 (define_insn "*swaphi_1"
1375   [(set (match_operand:HI 0 "register_operand" "+r")
1376         (match_operand:HI 1 "register_operand" "+r"))
1377    (set (match_dup 1)
1378         (match_dup 0))]
1379   "!TARGET_PARTIAL_REG_STALL || optimize_size"
1380   "xchg{l}\t%k1, %k0"
1381   [(set_attr "type" "imov")
1382    (set_attr "mode" "SI")
1383    (set_attr "pent_pair" "np")
1384    (set_attr "athlon_decode" "vector")
1385    (set_attr "ppro_uops" "few")])
1386
1387 (define_insn "*swaphi_2"
1388   [(set (match_operand:HI 0 "register_operand" "+r")
1389         (match_operand:HI 1 "register_operand" "+r"))
1390    (set (match_dup 1)
1391         (match_dup 0))]
1392   "TARGET_PARTIAL_REG_STALL"
1393   "xchg{w}\t%1, %0"
1394   [(set_attr "type" "imov")
1395    (set_attr "mode" "HI")
1396    (set_attr "pent_pair" "np")
1397    (set_attr "athlon_decode" "vector")
1398    (set_attr "ppro_uops" "few")])
1399
1400 (define_expand "movstricthi"
1401   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" ""))
1402         (match_operand:HI 1 "general_operand" ""))]
1403   "! TARGET_PARTIAL_REG_STALL || optimize_size"
1404 {
1405   /* Don't generate memory->memory moves, go through a register */
1406   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1407     operands[1] = force_reg (HImode, operands[1]);
1408 })
1409
1410 (define_insn "*movstricthi_1"
1411   [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+rm,r"))
1412         (match_operand:HI 1 "general_operand" "rn,m"))]
1413   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1414    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1415   "mov{w}\t{%1, %0|%0, %1}"
1416   [(set_attr "type" "imov")
1417    (set_attr "mode" "HI")])
1418
1419 (define_insn "*movstricthi_xor"
1420   [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
1421         (match_operand:HI 1 "const0_operand" "i"))
1422    (clobber (reg:CC 17))]
1423   "reload_completed
1424    && ((!TARGET_USE_MOV0 && !TARGET_PARTIAL_REG_STALL) || optimize_size)"
1425   "xor{w}\t{%0, %0|%0, %0}"
1426   [(set_attr "type" "alu1")
1427    (set_attr "mode" "HI")
1428    (set_attr "length_immediate" "0")])
1429
1430 (define_expand "movqi"
1431   [(set (match_operand:QI 0 "nonimmediate_operand" "")
1432         (match_operand:QI 1 "general_operand" ""))]
1433   ""
1434   "ix86_expand_move (QImode, operands); DONE;")
1435
1436 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1437 ;; "push a byte".  But actually we use pushw, which has the effect
1438 ;; of rounding the amount pushed up to a halfword.
1439
1440 (define_insn "*pushqi2"
1441   [(set (match_operand:QI 0 "push_operand" "=X,X")
1442         (match_operand:QI 1 "nonmemory_no_elim_operand" "n,r"))]
1443   "!TARGET_64BIT"
1444   "@
1445    push{w}\t{|word ptr }%1
1446    push{w}\t%w1"
1447   [(set_attr "type" "push")
1448    (set_attr "mode" "HI")])
1449
1450 ;; For 64BIT abi we always round up to 8 bytes.
1451 (define_insn "*pushqi2_rex64"
1452   [(set (match_operand:QI 0 "push_operand" "=X")
1453         (match_operand:QI 1 "nonmemory_no_elim_operand" "qi"))]
1454   "TARGET_64BIT"
1455   "push{q}\t%q1"
1456   [(set_attr "type" "push")
1457    (set_attr "mode" "QI")])
1458
1459 ;; Situation is quite tricky about when to choose full sized (SImode) move
1460 ;; over QImode moves.  For Q_REG -> Q_REG move we use full size only for
1461 ;; partial register dependency machines (such as AMD Athlon), where QImode
1462 ;; moves issue extra dependency and for partial register stalls machines
1463 ;; that don't use QImode patterns (and QImode move cause stall on the next
1464 ;; instruction).
1465 ;;
1466 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
1467 ;; register stall machines with, where we use QImode instructions, since
1468 ;; partial register stall can be caused there.  Then we use movzx.
1469 (define_insn "*movqi_1"
1470   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
1471         (match_operand:QI 1 "general_operand"      " q,qn,qm,q,rn,qm,qn"))]
1472   "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1473 {
1474   switch (get_attr_type (insn))
1475     {
1476     case TYPE_IMOVX:
1477       if (!ANY_QI_REG_P (operands[1]) && GET_CODE (operands[1]) != MEM)
1478         abort ();
1479       return "movz{bl|x}\t{%1, %k0|%k0, %1}";
1480     default:
1481       if (get_attr_mode (insn) == MODE_SI)
1482         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1483       else
1484         return "mov{b}\t{%1, %0|%0, %1}";
1485     }
1486 }
1487   [(set (attr "type")
1488      (cond [(and (eq_attr "alternative" "3")
1489                  (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1490                           (const_int 0))
1491                       (eq (symbol_ref "TARGET_QIMODE_MATH")
1492                           (const_int 0))))
1493               (const_string "imov")
1494             (eq_attr "alternative" "3,5")
1495               (const_string "imovx")
1496             (and (ne (symbol_ref "TARGET_MOVX")
1497                      (const_int 0))
1498                  (eq_attr "alternative" "2"))
1499               (const_string "imovx")
1500            ]
1501            (const_string "imov")))
1502    (set (attr "mode")
1503       (cond [(eq_attr "alternative" "3,4,5")
1504                (const_string "SI")
1505              (eq_attr "alternative" "6")
1506                (const_string "QI")
1507              (eq_attr "type" "imovx")
1508                (const_string "SI")
1509              (and (eq_attr "type" "imov")
1510                   (and (eq_attr "alternative" "0,1,2")
1511                        (ne (symbol_ref "TARGET_PARTIAL_REG_DEPENDENCY")
1512                            (const_int 0))))
1513                (const_string "SI")
1514              ;; Avoid partial register stalls when not using QImode arithmetic
1515              (and (eq_attr "type" "imov")
1516                   (and (eq_attr "alternative" "0,1,2")
1517                        (and (ne (symbol_ref "TARGET_PARTIAL_REG_STALL")
1518                                 (const_int 0))
1519                             (eq (symbol_ref "TARGET_QIMODE_MATH")
1520                                 (const_int 0)))))
1521                (const_string "SI")
1522            ]
1523            (const_string "QI")))])
1524
1525 (define_expand "reload_outqi"
1526   [(parallel [(match_operand:QI 0 "" "=m")
1527               (match_operand:QI 1 "register_operand" "r")
1528               (match_operand:QI 2 "register_operand" "=&q")])]
1529   ""
1530 {
1531   rtx op0, op1, op2;
1532   op0 = operands[0]; op1 = operands[1]; op2 = operands[2];
1533
1534   if (reg_overlap_mentioned_p (op2, op0))
1535     abort ();
1536   if (! q_regs_operand (op1, QImode))
1537     {
1538       emit_insn (gen_movqi (op2, op1));
1539       op1 = op2;
1540     }
1541   emit_insn (gen_movqi (op0, op1));
1542   DONE;
1543 })
1544
1545 (define_insn "*swapqi_1"
1546   [(set (match_operand:QI 0 "register_operand" "+r")
1547         (match_operand:QI 1 "register_operand" "+r"))
1548    (set (match_dup 1)
1549         (match_dup 0))]
1550   "!TARGET_PARTIAL_REG_STALL || optimize_size"
1551   "xchg{l}\t%k1, %k0"
1552   [(set_attr "type" "imov")
1553    (set_attr "mode" "SI")
1554    (set_attr "pent_pair" "np")
1555    (set_attr "athlon_decode" "vector")
1556    (set_attr "ppro_uops" "few")])
1557
1558 (define_insn "*swapqi_2"
1559   [(set (match_operand:QI 0 "register_operand" "+q")
1560         (match_operand:QI 1 "register_operand" "+q"))
1561    (set (match_dup 1)
1562         (match_dup 0))]
1563   "TARGET_PARTIAL_REG_STALL"
1564   "xchg{b}\t%1, %0"
1565   [(set_attr "type" "imov")
1566    (set_attr "mode" "QI")
1567    (set_attr "pent_pair" "np")
1568    (set_attr "athlon_decode" "vector")
1569    (set_attr "ppro_uops" "few")])
1570
1571 (define_expand "movstrictqi"
1572   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
1573         (match_operand:QI 1 "general_operand" ""))]
1574   "! TARGET_PARTIAL_REG_STALL || optimize_size"
1575 {
1576   /* Don't generate memory->memory moves, go through a register.  */
1577   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1578     operands[1] = force_reg (QImode, operands[1]);
1579 })
1580
1581 (define_insn "*movstrictqi_1"
1582   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
1583         (match_operand:QI 1 "general_operand" "*qn,m"))]
1584   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1585    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1586   "mov{b}\t{%1, %0|%0, %1}"
1587   [(set_attr "type" "imov")
1588    (set_attr "mode" "QI")])
1589
1590 (define_insn "*movstrictqi_xor"
1591   [(set (strict_low_part (match_operand:QI 0 "q_regs_operand" "+q"))
1592         (match_operand:QI 1 "const0_operand" "i"))
1593    (clobber (reg:CC 17))]
1594   "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1595   "xor{b}\t{%0, %0|%0, %0}"
1596   [(set_attr "type" "alu1")
1597    (set_attr "mode" "QI")
1598    (set_attr "length_immediate" "0")])
1599
1600 (define_insn "*movsi_extv_1"
1601   [(set (match_operand:SI 0 "register_operand" "=R")
1602         (sign_extract:SI (match_operand 1 "ext_register_operand" "Q")
1603                          (const_int 8)
1604                          (const_int 8)))]
1605   ""
1606   "movs{bl|x}\t{%h1, %0|%0, %h1}"
1607   [(set_attr "type" "imovx")
1608    (set_attr "mode" "SI")])
1609
1610 (define_insn "*movhi_extv_1"
1611   [(set (match_operand:HI 0 "register_operand" "=R")
1612         (sign_extract:HI (match_operand 1 "ext_register_operand" "Q")
1613                          (const_int 8)
1614                          (const_int 8)))]
1615   ""
1616   "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
1617   [(set_attr "type" "imovx")
1618    (set_attr "mode" "SI")])
1619
1620 (define_insn "*movqi_extv_1"
1621   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
1622         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1623                          (const_int 8)
1624                          (const_int 8)))]
1625   "!TARGET_64BIT"
1626 {
1627   switch (get_attr_type (insn))
1628     {
1629     case TYPE_IMOVX:
1630       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1631     default:
1632       return "mov{b}\t{%h1, %0|%0, %h1}";
1633     }
1634 }
1635   [(set (attr "type")
1636      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1637                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1638                              (ne (symbol_ref "TARGET_MOVX")
1639                                  (const_int 0))))
1640         (const_string "imovx")
1641         (const_string "imov")))
1642    (set (attr "mode")
1643      (if_then_else (eq_attr "type" "imovx")
1644         (const_string "SI")
1645         (const_string "QI")))])
1646
1647 (define_insn "*movqi_extv_1_rex64"
1648   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1649         (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1650                          (const_int 8)
1651                          (const_int 8)))]
1652   "TARGET_64BIT"
1653 {
1654   switch (get_attr_type (insn))
1655     {
1656     case TYPE_IMOVX:
1657       return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1658     default:
1659       return "mov{b}\t{%h1, %0|%0, %h1}";
1660     }
1661 }
1662   [(set (attr "type")
1663      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1664                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1665                              (ne (symbol_ref "TARGET_MOVX")
1666                                  (const_int 0))))
1667         (const_string "imovx")
1668         (const_string "imov")))
1669    (set (attr "mode")
1670      (if_then_else (eq_attr "type" "imovx")
1671         (const_string "SI")
1672         (const_string "QI")))])
1673
1674 ;; Stores and loads of ax to arbitrary constant address.
1675 ;; We fake an second form of instruction to force reload to load address
1676 ;; into register when rax is not available
1677 (define_insn "*movabsqi_1_rex64"
1678   [(set (mem:QI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1679         (match_operand:QI 1 "nonmemory_operand" "a,er"))]
1680   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1681   "@
1682    movabs{b}\t{%1, %P0|%P0, %1}
1683    mov{b}\t{%1, %a0|%a0, %1}"
1684   [(set_attr "type" "imov")
1685    (set_attr "modrm" "0,*")
1686    (set_attr "length_address" "8,0")
1687    (set_attr "length_immediate" "0,*")
1688    (set_attr "memory" "store")
1689    (set_attr "mode" "QI")])
1690
1691 (define_insn "*movabsqi_2_rex64"
1692   [(set (match_operand:QI 0 "register_operand" "=a,r")
1693         (mem:QI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1694   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1695   "@
1696    movabs{b}\t{%P1, %0|%0, %P1}
1697    mov{b}\t{%a1, %0|%0, %a1}"
1698   [(set_attr "type" "imov")
1699    (set_attr "modrm" "0,*")
1700    (set_attr "length_address" "8,0")
1701    (set_attr "length_immediate" "0")
1702    (set_attr "memory" "load")
1703    (set_attr "mode" "QI")])
1704
1705 (define_insn "*movsi_extzv_1"
1706   [(set (match_operand:SI 0 "register_operand" "=R")
1707         (zero_extract:SI (match_operand 1 "ext_register_operand" "Q")
1708                          (const_int 8)
1709                          (const_int 8)))]
1710   ""
1711   "movz{bl|x}\t{%h1, %0|%0, %h1}"
1712   [(set_attr "type" "imovx")
1713    (set_attr "mode" "SI")])
1714
1715 (define_insn "*movqi_extzv_2"
1716   [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
1717         (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1718                                     (const_int 8)
1719                                     (const_int 8)) 0))]
1720   "!TARGET_64BIT"
1721 {
1722   switch (get_attr_type (insn))
1723     {
1724     case TYPE_IMOVX:
1725       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1726     default:
1727       return "mov{b}\t{%h1, %0|%0, %h1}";
1728     }
1729 }
1730   [(set (attr "type")
1731      (if_then_else (and (match_operand:QI 0 "register_operand" "")
1732                         (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1733                              (ne (symbol_ref "TARGET_MOVX")
1734                                  (const_int 0))))
1735         (const_string "imovx")
1736         (const_string "imov")))
1737    (set (attr "mode")
1738      (if_then_else (eq_attr "type" "imovx")
1739         (const_string "SI")
1740         (const_string "QI")))])
1741
1742 (define_insn "*movqi_extzv_2_rex64"
1743   [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1744         (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1745                                     (const_int 8)
1746                                     (const_int 8)) 0))]
1747   "TARGET_64BIT"
1748 {
1749   switch (get_attr_type (insn))
1750     {
1751     case TYPE_IMOVX:
1752       return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1753     default:
1754       return "mov{b}\t{%h1, %0|%0, %h1}";
1755     }
1756 }
1757   [(set (attr "type")
1758      (if_then_else (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1759                         (ne (symbol_ref "TARGET_MOVX")
1760                             (const_int 0)))
1761         (const_string "imovx")
1762         (const_string "imov")))
1763    (set (attr "mode")
1764      (if_then_else (eq_attr "type" "imovx")
1765         (const_string "SI")
1766         (const_string "QI")))])
1767
1768 (define_insn "movsi_insv_1"
1769   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
1770                          (const_int 8)
1771                          (const_int 8))
1772         (match_operand:SI 1 "general_operand" "Qmn"))]
1773   "!TARGET_64BIT"
1774   "mov{b}\t{%b1, %h0|%h0, %b1}"
1775   [(set_attr "type" "imov")
1776    (set_attr "mode" "QI")])
1777
1778 (define_insn "movdi_insv_1_rex64"
1779   [(set (zero_extract:DI (match_operand 0 "ext_register_operand" "+Q")
1780                          (const_int 8)
1781                          (const_int 8))
1782         (match_operand:DI 1 "nonmemory_operand" "Qn"))]
1783   "TARGET_64BIT"
1784   "mov{b}\t{%b1, %h0|%h0, %b1}"
1785   [(set_attr "type" "imov")
1786    (set_attr "mode" "QI")])
1787
1788 (define_insn "*movqi_insv_2"
1789   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
1790                          (const_int 8)
1791                          (const_int 8))
1792         (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
1793                      (const_int 8)))]
1794   ""
1795   "mov{b}\t{%h1, %h0|%h0, %h1}"
1796   [(set_attr "type" "imov")
1797    (set_attr "mode" "QI")])
1798
1799 (define_expand "movdi"
1800   [(set (match_operand:DI 0 "nonimmediate_operand" "")
1801         (match_operand:DI 1 "general_operand" ""))]
1802   ""
1803   "ix86_expand_move (DImode, operands); DONE;")
1804
1805 (define_insn "*pushdi"
1806   [(set (match_operand:DI 0 "push_operand" "=<")
1807         (match_operand:DI 1 "general_no_elim_operand" "riF*m"))]
1808   "!TARGET_64BIT"
1809   "#")
1810
1811 (define_insn "pushdi2_rex64"
1812   [(set (match_operand:DI 0 "push_operand" "=<,!<")
1813         (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
1814   "TARGET_64BIT"
1815   "@
1816    push{q}\t%1
1817    #"
1818   [(set_attr "type" "push,multi")
1819    (set_attr "mode" "DI")])
1820
1821 ;; Convert impossible pushes of immediate to existing instructions.
1822 ;; First try to get scratch register and go through it.  In case this
1823 ;; fails, push sign extended lower part first and then overwrite
1824 ;; upper part by 32bit move.
1825 (define_peephole2
1826   [(match_scratch:DI 2 "r")
1827    (set (match_operand:DI 0 "push_operand" "")
1828         (match_operand:DI 1 "immediate_operand" ""))]
1829   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1830    && !x86_64_immediate_operand (operands[1], DImode)"
1831   [(set (match_dup 2) (match_dup 1))
1832    (set (match_dup 0) (match_dup 2))]
1833   "")
1834
1835 ;; We need to define this as both peepholer and splitter for case
1836 ;; peephole2 pass is not run.
1837 (define_peephole2
1838   [(set (match_operand:DI 0 "push_operand" "")
1839         (match_operand:DI 1 "immediate_operand" ""))]
1840   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1841    && !x86_64_immediate_operand (operands[1], DImode) && 1"
1842   [(set (match_dup 0) (match_dup 1))
1843    (set (match_dup 2) (match_dup 3))]
1844   "split_di (operands + 1, 1, operands + 2, operands + 3);
1845    operands[1] = gen_lowpart (DImode, operands[2]);
1846    operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1847                                                     GEN_INT (4)));
1848   ")
1849
1850 (define_split
1851   [(set (match_operand:DI 0 "push_operand" "")
1852         (match_operand:DI 1 "immediate_operand" ""))]
1853   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
1854                    ? flow2_completed : reload_completed)
1855    && !symbolic_operand (operands[1], DImode)
1856    && !x86_64_immediate_operand (operands[1], DImode)"
1857   [(set (match_dup 0) (match_dup 1))
1858    (set (match_dup 2) (match_dup 3))]
1859   "split_di (operands + 1, 1, operands + 2, operands + 3);
1860    operands[1] = gen_lowpart (DImode, operands[2]);
1861    operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1862                                                     GEN_INT (4)));
1863   ")
1864
1865 (define_insn "*pushdi2_prologue_rex64"
1866   [(set (match_operand:DI 0 "push_operand" "=<")
1867         (match_operand:DI 1 "general_no_elim_operand" "re*m"))
1868    (clobber (mem:BLK (scratch)))]
1869   "TARGET_64BIT"
1870   "push{q}\t%1"
1871   [(set_attr "type" "push")
1872    (set_attr "mode" "DI")])
1873
1874 (define_insn "*popdi1_epilogue_rex64"
1875   [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
1876         (mem:DI (reg:DI 7)))
1877    (set (reg:DI 7)
1878         (plus:DI (reg:DI 7) (const_int 8)))
1879    (clobber (mem:BLK (scratch)))]
1880   "TARGET_64BIT"
1881   "pop{q}\t%0"
1882   [(set_attr "type" "pop")
1883    (set_attr "mode" "DI")])
1884
1885 (define_insn "popdi1"
1886   [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
1887         (mem:DI (reg:DI 7)))
1888    (set (reg:DI 7)
1889         (plus:DI (reg:DI 7) (const_int 8)))]
1890   "TARGET_64BIT"
1891   "pop{q}\t%0"
1892   [(set_attr "type" "pop")
1893    (set_attr "mode" "DI")])
1894
1895 (define_insn "*movdi_xor_rex64"
1896   [(set (match_operand:DI 0 "register_operand" "=r")
1897         (match_operand:DI 1 "const0_operand" "i"))
1898    (clobber (reg:CC 17))]
1899   "TARGET_64BIT && (!TARGET_USE_MOV0 || optimize_size)
1900    && reload_completed"
1901   "xor{l}\t{%k0, %k0|%k0, %k0}"
1902   [(set_attr "type" "alu1")
1903    (set_attr "mode" "SI")
1904    (set_attr "length_immediate" "0")])
1905
1906 (define_insn "*movdi_or_rex64"
1907   [(set (match_operand:DI 0 "register_operand" "=r")
1908         (match_operand:DI 1 "const_int_operand" "i"))
1909    (clobber (reg:CC 17))]
1910   "TARGET_64BIT && (TARGET_PENTIUM || optimize_size)
1911    && reload_completed
1912    && operands[1] == constm1_rtx"
1913 {
1914   operands[1] = constm1_rtx;
1915   return "or{q}\t{%1, %0|%0, %1}";
1916 }
1917   [(set_attr "type" "alu1")
1918    (set_attr "mode" "DI")
1919    (set_attr "length_immediate" "1")])
1920
1921 (define_insn "*movdi_2"
1922   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,!m*y,!*y,!m,!*Y,!*Y")
1923         (match_operand:DI 1 "general_operand" "riFo,riF,*y,m,*Y,*Y,m"))]
1924   "!TARGET_64BIT
1925    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1926   "@
1927    #
1928    #
1929    movq\t{%1, %0|%0, %1}
1930    movq\t{%1, %0|%0, %1}
1931    movq\t{%1, %0|%0, %1}
1932    movdqa\t{%1, %0|%0, %1}
1933    movq\t{%1, %0|%0, %1}"
1934   [(set_attr "type" "*,*,mmx,mmx,ssemov,ssemov,ssemov")
1935    (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI")])
1936
1937 (define_split
1938   [(set (match_operand:DI 0 "push_operand" "")
1939         (match_operand:DI 1 "general_operand" ""))]
1940   "!TARGET_64BIT && reload_completed
1941    && (! MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
1942   [(const_int 0)]
1943   "ix86_split_long_move (operands); DONE;")
1944
1945 ;; %%% This multiword shite has got to go.
1946 (define_split
1947   [(set (match_operand:DI 0 "nonimmediate_operand" "")
1948         (match_operand:DI 1 "general_operand" ""))]
1949   "!TARGET_64BIT && reload_completed
1950    && (!MMX_REG_P (operands[0]) && !SSE_REG_P (operands[0]))
1951    && (!MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
1952   [(const_int 0)]
1953   "ix86_split_long_move (operands); DONE;")
1954
1955 (define_insn "*movdi_1_rex64"
1956   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,r,mr,!mr,!*y,!rm,!*y,!*Y,!rm,!*Y")
1957         (match_operand:DI 1 "general_operand" "Z,rem,i,re,n,*y,*y,rm,*Y,*Y,rm"))]
1958   "TARGET_64BIT
1959    && (TARGET_INTER_UNIT_MOVES || optimize_size)
1960    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1961 {
1962   switch (get_attr_type (insn))
1963     {
1964     case TYPE_SSEMOV:
1965       if (get_attr_mode (insn) == MODE_TI)
1966           return "movdqa\t{%1, %0|%0, %1}";
1967       /* FALLTHRU */
1968     case TYPE_MMXMOV:
1969       /* Moves from and into integer register is done using movd opcode with
1970          REX prefix.  */
1971       if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
1972           return "movd\t{%1, %0|%0, %1}";
1973       return "movq\t{%1, %0|%0, %1}";
1974     case TYPE_MULTI:
1975       return "#";
1976     case TYPE_LEA:
1977       return "lea{q}\t{%a1, %0|%0, %a1}";
1978     default:
1979       if (flag_pic && !LEGITIMATE_PIC_OPERAND_P (operands[1]))
1980         abort ();
1981       if (get_attr_mode (insn) == MODE_SI)
1982         return "mov{l}\t{%k1, %k0|%k0, %k1}";
1983       else if (which_alternative == 2)
1984         return "movabs{q}\t{%1, %0|%0, %1}";
1985       else
1986         return "mov{q}\t{%1, %0|%0, %1}";
1987     }
1988 }
1989   [(set (attr "type")
1990      (cond [(eq_attr "alternative" "5,6,7")
1991               (const_string "mmxmov")
1992             (eq_attr "alternative" "8,9,10")
1993               (const_string "ssemov")
1994             (eq_attr "alternative" "4")
1995               (const_string "multi")
1996             (and (ne (symbol_ref "flag_pic") (const_int 0))
1997                  (match_operand:DI 1 "symbolic_operand" ""))
1998               (const_string "lea")
1999            ]
2000            (const_string "imov")))
2001    (set_attr "modrm" "*,0,0,*,*,*,*,*,*,*,*")
2002    (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*,*,*")
2003    (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,TI,DI,DI")])
2004
2005 (define_insn "*movdi_1_rex64_nointerunit"
2006   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,r,mr,!mr,!*y,!m,!*y,!*Y,!m,!*Y")
2007         (match_operand:DI 1 "general_operand" "Z,rem,i,re,n,*y,*y,m,*Y,*Y,m"))]
2008   "TARGET_64BIT
2009    && (!TARGET_INTER_UNIT_MOVES && !optimize_size)
2010    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2011 {
2012   switch (get_attr_type (insn))
2013     {
2014     case TYPE_SSEMOV:
2015       if (get_attr_mode (insn) == MODE_TI)
2016           return "movdqa\t{%1, %0|%0, %1}";
2017       /* FALLTHRU */
2018     case TYPE_MMXMOV:
2019       return "movq\t{%1, %0|%0, %1}";
2020     case TYPE_MULTI:
2021       return "#";
2022     case TYPE_LEA:
2023       return "lea{q}\t{%a1, %0|%0, %a1}";
2024     default:
2025       if (flag_pic && !LEGITIMATE_PIC_OPERAND_P (operands[1]))
2026         abort ();
2027       if (get_attr_mode (insn) == MODE_SI)
2028         return "mov{l}\t{%k1, %k0|%k0, %k1}";
2029       else if (which_alternative == 2)
2030         return "movabs{q}\t{%1, %0|%0, %1}";
2031       else
2032         return "mov{q}\t{%1, %0|%0, %1}";
2033     }
2034 }
2035   [(set (attr "type")
2036      (cond [(eq_attr "alternative" "5,6,7")
2037               (const_string "mmxmov")
2038             (eq_attr "alternative" "8,9,10")
2039               (const_string "ssemov")
2040             (eq_attr "alternative" "4")
2041               (const_string "multi")
2042             (and (ne (symbol_ref "flag_pic") (const_int 0))
2043                  (match_operand:DI 1 "symbolic_operand" ""))
2044               (const_string "lea")
2045            ]
2046            (const_string "imov")))
2047    (set_attr "modrm" "*,0,0,*,*,*,*,*,*,*,*")
2048    (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*,*,*")
2049    (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,TI,DI,DI")])
2050
2051 ;; Stores and loads of ax to arbitrary constant address.
2052 ;; We fake an second form of instruction to force reload to load address
2053 ;; into register when rax is not available
2054 (define_insn "*movabsdi_1_rex64"
2055   [(set (mem:DI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2056         (match_operand:DI 1 "nonmemory_operand" "a,er"))]
2057   "TARGET_64BIT && ix86_check_movabs (insn, 0)"
2058   "@
2059    movabs{q}\t{%1, %P0|%P0, %1}
2060    mov{q}\t{%1, %a0|%a0, %1}"
2061   [(set_attr "type" "imov")
2062    (set_attr "modrm" "0,*")
2063    (set_attr "length_address" "8,0")
2064    (set_attr "length_immediate" "0,*")
2065    (set_attr "memory" "store")
2066    (set_attr "mode" "DI")])
2067
2068 (define_insn "*movabsdi_2_rex64"
2069   [(set (match_operand:DI 0 "register_operand" "=a,r")
2070         (mem:DI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2071   "TARGET_64BIT && ix86_check_movabs (insn, 1)"
2072   "@
2073    movabs{q}\t{%P1, %0|%0, %P1}
2074    mov{q}\t{%a1, %0|%0, %a1}"
2075   [(set_attr "type" "imov")
2076    (set_attr "modrm" "0,*")
2077    (set_attr "length_address" "8,0")
2078    (set_attr "length_immediate" "0")
2079    (set_attr "memory" "load")
2080    (set_attr "mode" "DI")])
2081
2082 ;; Convert impossible stores of immediate to existing instructions.
2083 ;; First try to get scratch register and go through it.  In case this
2084 ;; fails, move by 32bit parts.
2085 (define_peephole2
2086   [(match_scratch:DI 2 "r")
2087    (set (match_operand:DI 0 "memory_operand" "")
2088         (match_operand:DI 1 "immediate_operand" ""))]
2089   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2090    && !x86_64_immediate_operand (operands[1], DImode)"
2091   [(set (match_dup 2) (match_dup 1))
2092    (set (match_dup 0) (match_dup 2))]
2093   "")
2094
2095 ;; We need to define this as both peepholer and splitter for case
2096 ;; peephole2 pass is not run.
2097 (define_peephole2
2098   [(set (match_operand:DI 0 "memory_operand" "")
2099         (match_operand:DI 1 "immediate_operand" ""))]
2100   "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2101    && !x86_64_immediate_operand (operands[1], DImode) && 1"
2102   [(set (match_dup 2) (match_dup 3))
2103    (set (match_dup 4) (match_dup 5))]
2104   "split_di (operands, 2, operands + 2, operands + 4);")
2105
2106 (define_split
2107   [(set (match_operand:DI 0 "memory_operand" "")
2108         (match_operand:DI 1 "immediate_operand" ""))]
2109   "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2110                    ? flow2_completed : reload_completed)
2111    && !symbolic_operand (operands[1], DImode)
2112    && !x86_64_immediate_operand (operands[1], DImode)"
2113   [(set (match_dup 2) (match_dup 3))
2114    (set (match_dup 4) (match_dup 5))]
2115   "split_di (operands, 2, operands + 2, operands + 4);")
2116
2117 (define_insn "*swapdi_rex64"
2118   [(set (match_operand:DI 0 "register_operand" "+r")
2119         (match_operand:DI 1 "register_operand" "+r"))
2120    (set (match_dup 1)
2121         (match_dup 0))]
2122   "TARGET_64BIT"
2123   "xchg{q}\t%1, %0"
2124   [(set_attr "type" "imov")
2125    (set_attr "mode" "DI")
2126    (set_attr "pent_pair" "np")
2127    (set_attr "athlon_decode" "vector")
2128    (set_attr "ppro_uops" "few")])
2129
2130 (define_expand "movsf"
2131   [(set (match_operand:SF 0 "nonimmediate_operand" "")
2132         (match_operand:SF 1 "general_operand" ""))]
2133   ""
2134   "ix86_expand_move (SFmode, operands); DONE;")
2135
2136 (define_insn "*pushsf"
2137   [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2138         (match_operand:SF 1 "general_no_elim_operand" "f#rx,rFm#fx,x#rf"))]
2139   "!TARGET_64BIT"
2140 {
2141   switch (which_alternative)
2142     {
2143     case 1:
2144       return "push{l}\t%1";
2145
2146     default:
2147       /* This insn should be already split before reg-stack.  */
2148       abort ();
2149     }
2150 }
2151   [(set_attr "type" "multi,push,multi")
2152    (set_attr "mode" "SF,SI,SF")])
2153
2154 (define_insn "*pushsf_rex64"
2155   [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2156         (match_operand:SF 1 "nonmemory_no_elim_operand" "f#rx,rF#fx,x#rf"))]
2157   "TARGET_64BIT"
2158 {
2159   switch (which_alternative)
2160     {
2161     case 1:
2162       return "push{q}\t%q1";
2163
2164     default:
2165       /* This insn should be already split before reg-stack.  */
2166       abort ();
2167     }
2168 }
2169   [(set_attr "type" "multi,push,multi")
2170    (set_attr "mode" "SF,DI,SF")])
2171
2172 (define_split
2173   [(set (match_operand:SF 0 "push_operand" "")
2174         (match_operand:SF 1 "memory_operand" ""))]
2175   "reload_completed
2176    && GET_CODE (operands[1]) == MEM
2177    && constant_pool_reference_p (operands[1])"
2178   [(set (match_dup 0)
2179         (match_dup 1))]
2180   "operands[1] = avoid_constant_pool_reference (operands[1]);")
2181
2182
2183 ;; %%% Kill this when call knows how to work this out.
2184 (define_split
2185   [(set (match_operand:SF 0 "push_operand" "")
2186         (match_operand:SF 1 "any_fp_register_operand" ""))]
2187   "!TARGET_64BIT"
2188   [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -4)))
2189    (set (mem:SF (reg:SI 7)) (match_dup 1))])
2190
2191 (define_split
2192   [(set (match_operand:SF 0 "push_operand" "")
2193         (match_operand:SF 1 "any_fp_register_operand" ""))]
2194   "TARGET_64BIT"
2195   [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -8)))
2196    (set (mem:SF (reg:DI 7)) (match_dup 1))])
2197
2198 (define_insn "*movsf_1"
2199   [(set (match_operand:SF 0 "nonimmediate_operand" "=f#xr,m,f#xr,r#xf,m,x#rf,x#rf,x#rf,m,!*y,!rm,!*y")
2200         (match_operand:SF 1 "general_operand" "fm#rx,f#rx,G,rmF#fx,Fr#fx,C,x,xm#rf,x#rf,rm,*y,*y"))]
2201   "(TARGET_INTER_UNIT_MOVES || optimize_size)
2202    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2203    && (reload_in_progress || reload_completed
2204        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2205        || GET_CODE (operands[1]) != CONST_DOUBLE
2206        || memory_operand (operands[0], SFmode))" 
2207 {
2208   switch (which_alternative)
2209     {
2210     case 0:
2211       if (REG_P (operands[1])
2212           && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2213         return "fstp\t%y0";
2214       else if (STACK_TOP_P (operands[0]))
2215         return "fld%z1\t%y1";
2216       else
2217         return "fst\t%y0";
2218
2219     case 1:
2220       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2221         return "fstp%z0\t%y0";
2222       else
2223         return "fst%z0\t%y0";
2224
2225     case 2:
2226       return standard_80387_constant_opcode (operands[1]);
2227
2228     case 3:
2229     case 4:
2230       return "mov{l}\t{%1, %0|%0, %1}";
2231     case 5:
2232       if (get_attr_mode (insn) == MODE_TI)
2233         return "pxor\t%0, %0";
2234       else
2235         return "xorps\t%0, %0";
2236     case 6:
2237       if (get_attr_mode (insn) == MODE_V4SF)
2238         return "movaps\t{%1, %0|%0, %1}";
2239       else
2240         return "movss\t{%1, %0|%0, %1}";
2241     case 7:
2242     case 8:
2243       return "movss\t{%1, %0|%0, %1}";
2244
2245     case 9:
2246     case 10:
2247       return "movd\t{%1, %0|%0, %1}";
2248
2249     case 11:
2250       return "movq\t{%1, %0|%0, %1}";
2251
2252     default:
2253       abort();
2254     }
2255 }
2256   [(set_attr "type" "fmov,fmov,fmov,imov,imov,ssemov,ssemov,ssemov,ssemov,mmxmov,mmxmov,mmxmov")
2257    (set (attr "mode")
2258         (cond [(eq_attr "alternative" "3,4,9,10")
2259                  (const_string "SI")
2260                (eq_attr "alternative" "5")
2261                  (if_then_else
2262                    (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2263                                  (const_int 0))
2264                              (ne (symbol_ref "TARGET_SSE2")
2265                                  (const_int 0)))
2266                         (eq (symbol_ref "optimize_size")
2267                             (const_int 0)))
2268                    (const_string "TI")
2269                    (const_string "V4SF"))
2270                /* For architectures resolving dependencies on
2271                   whole SSE registers use APS move to break dependency
2272                   chains, otherwise use short move to avoid extra work. 
2273
2274                   Do the same for architectures resolving dependencies on
2275                   the parts.  While in DF mode it is better to always handle
2276                   just register parts, the SF mode is different due to lack
2277                   of instructions to load just part of the register.  It is
2278                   better to maintain the whole registers in single format
2279                   to avoid problems on using packed logical operations.  */
2280                (eq_attr "alternative" "6")
2281                  (if_then_else
2282                    (ior (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2283                             (const_int 0))
2284                         (ne (symbol_ref "TARGET_SSE_PARTIAL_REGS")
2285                             (const_int 0)))
2286                    (const_string "V4SF")
2287                    (const_string "SF"))
2288                (eq_attr "alternative" "11")
2289                  (const_string "DI")]
2290                (const_string "SF")))])
2291
2292 (define_insn "*movsf_1_nointerunit"
2293   [(set (match_operand:SF 0 "nonimmediate_operand" "=f#xr,m,f#xr,r#xf,m,x#rf,x#rf,x#rf,m,!*y,!m,!*y")
2294         (match_operand:SF 1 "general_operand" "fm#rx,f#rx,G,rmF#fx,Fr#fx,C,x,xm#rf,x#rf,m,*y,*y"))]
2295   "(!TARGET_INTER_UNIT_MOVES && !optimize_size)
2296    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2297    && (reload_in_progress || reload_completed
2298        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2299        || GET_CODE (operands[1]) != CONST_DOUBLE
2300        || memory_operand (operands[0], SFmode))" 
2301 {
2302   switch (which_alternative)
2303     {
2304     case 0:
2305       if (REG_P (operands[1])
2306           && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2307         {
2308           if (REGNO (operands[0]) == FIRST_STACK_REG
2309               && TARGET_USE_FFREEP)
2310             return "ffreep\t%y0";
2311           return "fstp\t%y0";
2312         }
2313       else if (STACK_TOP_P (operands[0]))
2314         return "fld%z1\t%y1";
2315       else
2316         return "fst\t%y0";
2317
2318     case 1:
2319       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2320         return "fstp%z0\t%y0";
2321       else
2322         return "fst%z0\t%y0";
2323
2324     case 2:
2325       return standard_80387_constant_opcode (operands[1]);
2326
2327     case 3:
2328     case 4:
2329       return "mov{l}\t{%1, %0|%0, %1}";
2330     case 5:
2331       if (get_attr_mode (insn) == MODE_TI)
2332         return "pxor\t%0, %0";
2333       else
2334         return "xorps\t%0, %0";
2335     case 6:
2336       if (get_attr_mode (insn) == MODE_V4SF)
2337         return "movaps\t{%1, %0|%0, %1}";
2338       else
2339         return "movss\t{%1, %0|%0, %1}";
2340     case 7:
2341     case 8:
2342       return "movss\t{%1, %0|%0, %1}";
2343
2344     case 9:
2345     case 10:
2346       return "movd\t{%1, %0|%0, %1}";
2347
2348     case 11:
2349       return "movq\t{%1, %0|%0, %1}";
2350
2351     default:
2352       abort();
2353     }
2354 }
2355   [(set_attr "type" "fmov,fmov,fmov,imov,imov,ssemov,ssemov,ssemov,ssemov,mmxmov,mmxmov,mmxmov")
2356    (set (attr "mode")
2357         (cond [(eq_attr "alternative" "3,4,9,10")
2358                  (const_string "SI")
2359                (eq_attr "alternative" "5")
2360                  (if_then_else
2361                    (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2362                                  (const_int 0))
2363                              (ne (symbol_ref "TARGET_SSE2")
2364                                  (const_int 0)))
2365                         (eq (symbol_ref "optimize_size")
2366                             (const_int 0)))
2367                    (const_string "TI")
2368                    (const_string "V4SF"))
2369                /* For architectures resolving dependencies on
2370                   whole SSE registers use APS move to break dependency
2371                   chains, otherwise use short move to avoid extra work. 
2372
2373                   Do the same for architectures resolving dependencies on
2374                   the parts.  While in DF mode it is better to always handle
2375                   just register parts, the SF mode is different due to lack
2376                   of instructions to load just part of the register.  It is
2377                   better to maintain the whole registers in single format
2378                   to avoid problems on using packed logical operations.  */
2379                (eq_attr "alternative" "6")
2380                  (if_then_else
2381                    (ior (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2382                             (const_int 0))
2383                         (ne (symbol_ref "TARGET_SSE_PARTIAL_REGS")
2384                             (const_int 0)))
2385                    (const_string "V4SF")
2386                    (const_string "SF"))
2387                (eq_attr "alternative" "11")
2388                  (const_string "DI")]
2389                (const_string "SF")))])
2390
2391 (define_insn "*swapsf"
2392   [(set (match_operand:SF 0 "register_operand" "+f")
2393         (match_operand:SF 1 "register_operand" "+f"))
2394    (set (match_dup 1)
2395         (match_dup 0))]
2396   "reload_completed || !TARGET_SSE"
2397 {
2398   if (STACK_TOP_P (operands[0]))
2399     return "fxch\t%1";
2400   else
2401     return "fxch\t%0";
2402 }
2403   [(set_attr "type" "fxch")
2404    (set_attr "mode" "SF")])
2405
2406 (define_expand "movdf"
2407   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2408         (match_operand:DF 1 "general_operand" ""))]
2409   ""
2410   "ix86_expand_move (DFmode, operands); DONE;")
2411
2412 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2413 ;; Size of pushdf using integer instructions is 2+2*memory operand size
2414 ;; On the average, pushdf using integers can be still shorter.  Allow this
2415 ;; pattern for optimize_size too.
2416
2417 (define_insn "*pushdf_nointeger"
2418   [(set (match_operand:DF 0 "push_operand" "=<,<,<,<")
2419         (match_operand:DF 1 "general_no_elim_operand" "f#Y,Fo#fY,*r#fY,Y#f"))]
2420   "!TARGET_64BIT && !TARGET_INTEGER_DFMODE_MOVES"
2421 {
2422   /* This insn should be already split before reg-stack.  */
2423   abort ();
2424 }
2425   [(set_attr "type" "multi")
2426    (set_attr "mode" "DF,SI,SI,DF")])
2427
2428 (define_insn "*pushdf_integer"
2429   [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2430         (match_operand:DF 1 "general_no_elim_operand" "f#rY,rFo#fY,Y#rf"))]
2431   "TARGET_64BIT || TARGET_INTEGER_DFMODE_MOVES"
2432 {
2433   /* This insn should be already split before reg-stack.  */
2434   abort ();
2435 }
2436   [(set_attr "type" "multi")
2437    (set_attr "mode" "DF,SI,DF")])
2438
2439 ;; %%% Kill this when call knows how to work this out.
2440 (define_split
2441   [(set (match_operand:DF 0 "push_operand" "")
2442         (match_operand:DF 1 "any_fp_register_operand" ""))]
2443   "!TARGET_64BIT && reload_completed"
2444   [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
2445    (set (mem:DF (reg:SI 7)) (match_dup 1))]
2446   "")
2447
2448 (define_split
2449   [(set (match_operand:DF 0 "push_operand" "")
2450         (match_operand:DF 1 "any_fp_register_operand" ""))]
2451   "TARGET_64BIT && reload_completed"
2452   [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -8)))
2453    (set (mem:DF (reg:DI 7)) (match_dup 1))]
2454   "")
2455
2456 (define_split
2457   [(set (match_operand:DF 0 "push_operand" "")
2458         (match_operand:DF 1 "general_operand" ""))]
2459   "reload_completed"
2460   [(const_int 0)]
2461   "ix86_split_long_move (operands); DONE;")
2462
2463 ;; Moving is usually shorter when only FP registers are used. This separate
2464 ;; movdf pattern avoids the use of integer registers for FP operations
2465 ;; when optimizing for size.
2466
2467 (define_insn "*movdf_nointeger"
2468   [(set (match_operand:DF 0 "nonimmediate_operand" "=f#Y,m,f#Y,*r,o,Y#f,Y#f,Y#f,m")
2469         (match_operand:DF 1 "general_operand" "fm#Y,f#Y,G,*roF,F*r,C,Y#f,YHm#f,Y#f"))]
2470   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2471    && ((optimize_size || !TARGET_INTEGER_DFMODE_MOVES) && !TARGET_64BIT)
2472    && (reload_in_progress || reload_completed
2473        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2474        || GET_CODE (operands[1]) != CONST_DOUBLE
2475        || memory_operand (operands[0], DFmode))" 
2476 {
2477   switch (which_alternative)
2478     {
2479     case 0:
2480       if (REG_P (operands[1])
2481           && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2482         {
2483           if (REGNO (operands[0]) == FIRST_STACK_REG
2484               && TARGET_USE_FFREEP)
2485             return "ffreep\t%y0";
2486           return "fstp\t%y0";
2487         }
2488       else if (STACK_TOP_P (operands[0]))
2489         return "fld%z1\t%y1";
2490       else
2491         return "fst\t%y0";
2492
2493     case 1:
2494       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2495         return "fstp%z0\t%y0";
2496       else
2497         return "fst%z0\t%y0";
2498
2499     case 2:
2500       return standard_80387_constant_opcode (operands[1]);
2501
2502     case 3:
2503     case 4:
2504       return "#";
2505     case 5:
2506       switch (get_attr_mode (insn))
2507         {
2508         case MODE_V4SF:
2509           return "xorps\t%0, %0";
2510         case MODE_V2DF:
2511           return "xorpd\t%0, %0";
2512         case MODE_TI:
2513           return "pxor\t%0, %0";
2514         default:
2515           abort ();
2516         }
2517     case 6:
2518       switch (get_attr_mode (insn))
2519         {
2520         case MODE_V4SF:
2521           return "movaps\t{%1, %0|%0, %1}";
2522         case MODE_V2DF:
2523           return "movapd\t{%1, %0|%0, %1}";
2524         case MODE_DF:
2525           return "movsd\t{%1, %0|%0, %1}";
2526         default:
2527           abort ();
2528         }
2529     case 7:
2530       if (get_attr_mode (insn) == MODE_V2DF)
2531         return "movlpd\t{%1, %0|%0, %1}";
2532       else
2533         return "movsd\t{%1, %0|%0, %1}";
2534     case 8:
2535       return "movsd\t{%1, %0|%0, %1}";
2536
2537     default:
2538       abort();
2539     }
2540 }
2541   [(set_attr "type" "fmov,fmov,fmov,multi,multi,ssemov,ssemov,ssemov,ssemov")
2542    (set (attr "mode")
2543         (cond [(eq_attr "alternative" "3,4")
2544                  (const_string "SI")
2545                /* xorps is one byte shorter.  */
2546                (eq_attr "alternative" "5")
2547                  (cond [(ne (symbol_ref "optimize_size")
2548                             (const_int 0))
2549                           (const_string "V4SF")
2550                         (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2551                             (const_int 0))
2552                           (const_string "TI")]
2553                        (const_string "V2DF"))
2554                /* For architectures resolving dependencies on
2555                   whole SSE registers use APD move to break dependency
2556                   chains, otherwise use short move to avoid extra work.
2557
2558                   movaps encodes one byte shorter.  */
2559                (eq_attr "alternative" "6")
2560                  (cond
2561                   [(ne (symbol_ref "optimize_size")
2562                        (const_int 0))
2563                      (const_string "V4SF")
2564                    (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2565                        (const_int 0))
2566                      (const_string "V2DF")]
2567                    (const_string "DF"))
2568                /* For architectures resolving dependencies on register
2569                   parts we may avoid extra work to zero out upper part
2570                   of register.  */
2571                (eq_attr "alternative" "7")
2572                  (if_then_else
2573                    (ne (symbol_ref "TARGET_SSE_PARTIAL_REGS")
2574                        (const_int 0))
2575                    (const_string "V2DF")
2576                    (const_string "DF"))]
2577                (const_string "DF")))])
2578
2579 (define_insn "*movdf_integer"
2580   [(set (match_operand:DF 0 "nonimmediate_operand" "=f#Yr,m,f#Yr,r#Yf,o,Y#rf,Y#rf,Y#rf,m")
2581         (match_operand:DF 1 "general_operand" "fm#Yr,f#Yr,G,roF#Yf,Fr#Yf,C,Y#rf,Ym#rf,Y#rf"))]
2582   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2583    && ((!optimize_size && TARGET_INTEGER_DFMODE_MOVES) || TARGET_64BIT)
2584    && (reload_in_progress || reload_completed
2585        || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2586        || GET_CODE (operands[1]) != CONST_DOUBLE
2587        || memory_operand (operands[0], DFmode))" 
2588 {
2589   switch (which_alternative)
2590     {
2591     case 0:
2592       if (REG_P (operands[1])
2593           && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2594         {
2595           if (REGNO (operands[0]) == FIRST_STACK_REG
2596               && TARGET_USE_FFREEP)
2597             return "ffreep\t%y0";
2598           return "fstp\t%y0";
2599         }
2600       else if (STACK_TOP_P (operands[0]))
2601         return "fld%z1\t%y1";
2602       else
2603         return "fst\t%y0";
2604
2605     case 1:
2606       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2607         return "fstp%z0\t%y0";
2608       else
2609         return "fst%z0\t%y0";
2610
2611     case 2:
2612       return standard_80387_constant_opcode (operands[1]);
2613
2614     case 3:
2615     case 4:
2616       return "#";
2617
2618     case 5:
2619       switch (get_attr_mode (insn))
2620         {
2621         case MODE_V4SF:
2622           return "xorps\t%0, %0";
2623         case MODE_V2DF:
2624           return "xorpd\t%0, %0";
2625         case MODE_TI:
2626           return "pxor\t%0, %0";
2627         default:
2628           abort ();
2629         }
2630     case 6:
2631       switch (get_attr_mode (insn))
2632         {
2633         case MODE_V4SF:
2634           return "movaps\t{%1, %0|%0, %1}";
2635         case MODE_V2DF:
2636           return "movapd\t{%1, %0|%0, %1}";
2637         case MODE_DF:
2638           return "movsd\t{%1, %0|%0, %1}";
2639         default:
2640           abort ();
2641         }
2642     case 7:
2643       if (get_attr_mode (insn) == MODE_V2DF)
2644         return "movlpd\t{%1, %0|%0, %1}";
2645       else
2646         return "movsd\t{%1, %0|%0, %1}";
2647     case 8:
2648       return "movsd\t{%1, %0|%0, %1}";
2649
2650     default:
2651       abort();
2652     }
2653 }
2654   [(set_attr "type" "fmov,fmov,fmov,multi,multi,ssemov,ssemov,ssemov,ssemov")
2655    (set (attr "mode")
2656         (cond [(eq_attr "alternative" "3,4")
2657                  (const_string "SI")
2658                /* xorps is one byte shorter.  */
2659                (eq_attr "alternative" "5")
2660                  (cond [(ne (symbol_ref "optimize_size")
2661                             (const_int 0))
2662                           (const_string "V4SF")
2663                         (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2664                             (const_int 0))
2665                           (const_string "TI")]
2666                        (const_string "V2DF"))
2667                /* For architectures resolving dependencies on
2668                   whole SSE registers use APD move to break dependency
2669                   chains, otherwise use short move to avoid extra work.  
2670
2671                   movaps encodes one byte shorter.  */
2672                (eq_attr "alternative" "6")
2673                  (cond
2674                   [(ne (symbol_ref "optimize_size")
2675                        (const_int 0))
2676                      (const_string "V4SF")
2677                    (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2678                        (const_int 0))
2679                      (const_string "V2DF")]
2680                    (const_string "DF"))
2681                /* For architectures resolving dependencies on register
2682                   parts we may avoid extra work to zero out upper part
2683                   of register.  */
2684                (eq_attr "alternative" "7")
2685                  (if_then_else
2686                    (ne (symbol_ref "TARGET_SSE_PARTIAL_REGS")
2687                        (const_int 0))
2688                    (const_string "V2DF")
2689                    (const_string "DF"))]
2690                (const_string "DF")))])
2691
2692 (define_split
2693   [(set (match_operand:DF 0 "nonimmediate_operand" "")
2694         (match_operand:DF 1 "general_operand" ""))]
2695   "reload_completed
2696    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2697    && ! (ANY_FP_REG_P (operands[0]) || 
2698          (GET_CODE (operands[0]) == SUBREG
2699           && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2700    && ! (ANY_FP_REG_P (operands[1]) || 
2701          (GET_CODE (operands[1]) == SUBREG
2702           && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2703   [(const_int 0)]
2704   "ix86_split_long_move (operands); DONE;")
2705
2706 (define_insn "*swapdf"
2707   [(set (match_operand:DF 0 "register_operand" "+f")
2708         (match_operand:DF 1 "register_operand" "+f"))
2709    (set (match_dup 1)
2710         (match_dup 0))]
2711   "reload_completed || !TARGET_SSE2"
2712 {
2713   if (STACK_TOP_P (operands[0]))
2714     return "fxch\t%1";
2715   else
2716     return "fxch\t%0";
2717 }
2718   [(set_attr "type" "fxch")
2719    (set_attr "mode" "DF")])
2720
2721 (define_expand "movxf"
2722   [(set (match_operand:XF 0 "nonimmediate_operand" "")
2723         (match_operand:XF 1 "general_operand" ""))]
2724   ""
2725   "ix86_expand_move (XFmode, operands); DONE;")
2726
2727 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2728 ;; Size of pushdf using integer instructions is 3+3*memory operand size
2729 ;; Pushing using integer instructions is longer except for constants
2730 ;; and direct memory references.
2731 ;; (assuming that any given constant is pushed only once, but this ought to be
2732 ;;  handled elsewhere).
2733
2734 (define_insn "*pushxf_nointeger"
2735   [(set (match_operand:XF 0 "push_operand" "=X,X,X")
2736         (match_operand:XF 1 "general_no_elim_operand" "f,Fo,*r"))]
2737   "optimize_size"
2738 {
2739   /* This insn should be already split before reg-stack.  */
2740   abort ();
2741 }
2742   [(set_attr "type" "multi")
2743    (set_attr "mode" "XF,SI,SI")])
2744
2745 (define_insn "*pushxf_integer"
2746   [(set (match_operand:XF 0 "push_operand" "=<,<")
2747         (match_operand:XF 1 "general_no_elim_operand" "f#r,ro#f"))]
2748   "!optimize_size"
2749 {
2750   /* This insn should be already split before reg-stack.  */
2751   abort ();
2752 }
2753   [(set_attr "type" "multi")
2754    (set_attr "mode" "XF,SI")])
2755
2756 (define_split
2757   [(set (match_operand 0 "push_operand" "")
2758         (match_operand 1 "general_operand" ""))]
2759   "reload_completed
2760    && (GET_MODE (operands[0]) == XFmode
2761        || GET_MODE (operands[0]) == DFmode)
2762    && !ANY_FP_REG_P (operands[1])"
2763   [(const_int 0)]
2764   "ix86_split_long_move (operands); DONE;")
2765
2766 (define_split
2767   [(set (match_operand:XF 0 "push_operand" "")
2768         (match_operand:XF 1 "any_fp_register_operand" ""))]
2769   "!TARGET_64BIT"
2770   [(set (reg:SI 7) (plus:SI (reg:SI 7) (match_dup 2)))
2771    (set (mem:XF (reg:SI 7)) (match_dup 1))]
2772   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
2773
2774 (define_split
2775   [(set (match_operand:XF 0 "push_operand" "")
2776         (match_operand:XF 1 "any_fp_register_operand" ""))]
2777   "TARGET_64BIT"
2778   [(set (reg:DI 7) (plus:DI (reg:DI 7) (match_dup 2)))
2779    (set (mem:XF (reg:DI 7)) (match_dup 1))]
2780   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
2781
2782 ;; Do not use integer registers when optimizing for size
2783 (define_insn "*movxf_nointeger"
2784   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,*r,o")
2785         (match_operand:XF 1 "general_operand" "fm,f,G,*roF,F*r"))]
2786   "optimize_size
2787    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2788    && (reload_in_progress || reload_completed
2789        || GET_CODE (operands[1]) != CONST_DOUBLE
2790        || memory_operand (operands[0], XFmode))" 
2791 {
2792   switch (which_alternative)
2793     {
2794     case 0:
2795       if (REG_P (operands[1])
2796           && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2797         {
2798           if (REGNO (operands[0]) == FIRST_STACK_REG
2799               && TARGET_USE_FFREEP)
2800             return "ffreep\t%y0";
2801           return "fstp\t%y0";
2802         }
2803       else if (STACK_TOP_P (operands[0]))
2804         return "fld%z1\t%y1";
2805       else
2806         return "fst\t%y0";
2807
2808     case 1:
2809       /* There is no non-popping store to memory for XFmode.  So if
2810          we need one, follow the store with a load.  */
2811       if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2812         return "fstp%z0\t%y0\;fld%z0\t%y0";
2813       else
2814         return "fstp%z0\t%y0";
2815
2816     case 2:
2817       return standard_80387_constant_opcode (operands[1]);
2818
2819     case 3: case 4:
2820       return "#";
2821     }
2822   abort();
2823 }
2824   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2825    (set_attr "mode" "XF,XF,XF,SI,SI")])
2826
2827 (define_insn "*movxf_integer"
2828   [(set (match_operand:XF 0 "nonimmediate_operand" "=f#r,m,f#r,r#f,o")
2829         (match_operand:XF 1 "general_operand" "fm#r,f#r,G,roF#f,Fr#f"))]
2830   "!optimize_size
2831    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2832    && (reload_in_progress || reload_completed
2833        || GET_CODE (operands[1]) != CONST_DOUBLE
2834        || memory_operand (operands[0], XFmode))" 
2835 {
2836   switch (which_alternative)
2837     {
2838     case 0:
2839       if (REG_P (operands[1])
2840           && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2841         {
2842           if (REGNO (operands[0]) == FIRST_STACK_REG
2843               && TARGET_USE_FFREEP)
2844             return "ffreep\t%y0";
2845           return "fstp\t%y0";
2846         }
2847       else if (STACK_TOP_P (operands[0]))
2848         return "fld%z1\t%y1";
2849       else
2850         return "fst\t%y0";
2851
2852     case 1:
2853       /* There is no non-popping store to memory for XFmode.  So if
2854          we need one, follow the store with a load.  */
2855       if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2856         return "fstp%z0\t%y0\;fld%z0\t%y0";
2857       else
2858         return "fstp%z0\t%y0";
2859
2860     case 2:
2861       return standard_80387_constant_opcode (operands[1]);
2862
2863     case 3: case 4:
2864       return "#";
2865     }
2866   abort();
2867 }
2868   [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2869    (set_attr "mode" "XF,XF,XF,SI,SI")])
2870
2871 (define_split
2872   [(set (match_operand 0 "nonimmediate_operand" "")
2873         (match_operand 1 "general_operand" ""))]
2874   "reload_completed
2875    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2876    && GET_MODE (operands[0]) == XFmode
2877    && ! (ANY_FP_REG_P (operands[0]) || 
2878          (GET_CODE (operands[0]) == SUBREG
2879           && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2880    && ! (ANY_FP_REG_P (operands[1]) || 
2881          (GET_CODE (operands[1]) == SUBREG
2882           && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2883   [(const_int 0)]
2884   "ix86_split_long_move (operands); DONE;")
2885
2886 (define_split
2887   [(set (match_operand 0 "register_operand" "")
2888         (match_operand 1 "memory_operand" ""))]
2889   "reload_completed
2890    && GET_CODE (operands[1]) == MEM
2891    && (GET_MODE (operands[0]) == XFmode
2892        || GET_MODE (operands[0]) == SFmode || GET_MODE (operands[0]) == DFmode)
2893    && constant_pool_reference_p (operands[1])"
2894   [(set (match_dup 0) (match_dup 1))]
2895 {
2896   rtx c = avoid_constant_pool_reference (operands[1]);
2897   rtx r = operands[0];
2898
2899   if (GET_CODE (r) == SUBREG)
2900     r = SUBREG_REG (r);
2901
2902   if (SSE_REG_P (r))
2903     {
2904       if (!standard_sse_constant_p (c))
2905         FAIL;
2906     }
2907   else if (FP_REG_P (r))
2908     {
2909       if (!standard_80387_constant_p (c))
2910         FAIL;
2911     }
2912   else if (MMX_REG_P (r))
2913     FAIL;
2914
2915   operands[1] = c;
2916 })
2917
2918 (define_insn "swapxf"
2919   [(set (match_operand:XF 0 "register_operand" "+f")
2920         (match_operand:XF 1 "register_operand" "+f"))
2921    (set (match_dup 1)
2922         (match_dup 0))]
2923   ""
2924 {
2925   if (STACK_TOP_P (operands[0]))
2926     return "fxch\t%1";
2927   else
2928     return "fxch\t%0";
2929 }
2930   [(set_attr "type" "fxch")
2931    (set_attr "mode" "XF")])
2932 \f
2933 ;; Zero extension instructions
2934
2935 (define_expand "zero_extendhisi2"
2936   [(set (match_operand:SI 0 "register_operand" "")
2937      (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
2938   ""
2939 {
2940   if (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
2941     {
2942       operands[1] = force_reg (HImode, operands[1]);
2943       emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
2944       DONE;
2945     }
2946 })
2947
2948 (define_insn "zero_extendhisi2_and"
2949   [(set (match_operand:SI 0 "register_operand" "=r")
2950      (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
2951    (clobber (reg:CC 17))]
2952   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
2953   "#"
2954   [(set_attr "type" "alu1")
2955    (set_attr "mode" "SI")])
2956
2957 (define_split
2958   [(set (match_operand:SI 0 "register_operand" "")
2959         (zero_extend:SI (match_operand:HI 1 "register_operand" "")))
2960    (clobber (reg:CC 17))]
2961   "reload_completed && TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
2962   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
2963               (clobber (reg:CC 17))])]
2964   "")
2965
2966 (define_insn "*zero_extendhisi2_movzwl"
2967   [(set (match_operand:SI 0 "register_operand" "=r")
2968      (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
2969   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
2970   "movz{wl|x}\t{%1, %0|%0, %1}"
2971   [(set_attr "type" "imovx")
2972    (set_attr "mode" "SI")])
2973
2974 (define_expand "zero_extendqihi2"
2975   [(parallel
2976     [(set (match_operand:HI 0 "register_operand" "")
2977        (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
2978      (clobber (reg:CC 17))])]
2979   ""
2980   "")
2981
2982 (define_insn "*zero_extendqihi2_and"
2983   [(set (match_operand:HI 0 "register_operand" "=r,?&q")
2984      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
2985    (clobber (reg:CC 17))]
2986   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
2987   "#"
2988   [(set_attr "type" "alu1")
2989    (set_attr "mode" "HI")])
2990
2991 (define_insn "*zero_extendqihi2_movzbw_and"
2992   [(set (match_operand:HI 0 "register_operand" "=r,r")
2993      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
2994    (clobber (reg:CC 17))]
2995   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
2996   "#"
2997   [(set_attr "type" "imovx,alu1")
2998    (set_attr "mode" "HI")])
2999
3000 (define_insn "*zero_extendqihi2_movzbw"
3001   [(set (match_operand:HI 0 "register_operand" "=r")
3002      (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3003   "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3004   "movz{bw|x}\t{%1, %0|%0, %1}"
3005   [(set_attr "type" "imovx")
3006    (set_attr "mode" "HI")])
3007
3008 ;; For the movzbw case strip only the clobber
3009 (define_split
3010   [(set (match_operand:HI 0 "register_operand" "")
3011         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3012    (clobber (reg:CC 17))]
3013   "reload_completed 
3014    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3015    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3016   [(set (match_operand:HI 0 "register_operand" "")
3017         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))])
3018
3019 ;; When source and destination does not overlap, clear destination
3020 ;; first and then do the movb
3021 (define_split
3022   [(set (match_operand:HI 0 "register_operand" "")
3023         (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3024    (clobber (reg:CC 17))]
3025   "reload_completed
3026    && ANY_QI_REG_P (operands[0])
3027    && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3028    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3029   [(set (match_dup 0) (const_int 0))
3030    (set (strict_low_part (match_dup 2)) (match_dup 1))]
3031   "operands[2] = gen_lowpart (QImode, operands[0]);")
3032
3033 ;; Rest is handled by single and.
3034 (define_split
3035   [(set (match_operand:HI 0 "register_operand" "")
3036         (zero_extend:HI (match_operand:QI 1 "register_operand" "")))
3037    (clobber (reg:CC 17))]
3038   "reload_completed
3039    && true_regnum (operands[0]) == true_regnum (operands[1])"
3040   [(parallel [(set (match_dup 0) (and:HI (match_dup 0) (const_int 255)))
3041               (clobber (reg:CC 17))])]
3042   "")
3043
3044 (define_expand "zero_extendqisi2"
3045   [(parallel
3046     [(set (match_operand:SI 0 "register_operand" "")
3047        (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3048      (clobber (reg:CC 17))])]
3049   ""
3050   "")
3051
3052 (define_insn "*zero_extendqisi2_and"
3053   [(set (match_operand:SI 0 "register_operand" "=r,?&q")
3054      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3055    (clobber (reg:CC 17))]
3056   "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3057   "#"
3058   [(set_attr "type" "alu1")
3059    (set_attr "mode" "SI")])
3060
3061 (define_insn "*zero_extendqisi2_movzbw_and"
3062   [(set (match_operand:SI 0 "register_operand" "=r,r")
3063      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3064    (clobber (reg:CC 17))]
3065   "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3066   "#"
3067   [(set_attr "type" "imovx,alu1")
3068    (set_attr "mode" "SI")])
3069
3070 (define_insn "*zero_extendqisi2_movzbw"
3071   [(set (match_operand:SI 0 "register_operand" "=r")
3072      (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3073   "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3074   "movz{bl|x}\t{%1, %0|%0, %1}"
3075   [(set_attr "type" "imovx")
3076    (set_attr "mode" "SI")])
3077
3078 ;; For the movzbl case strip only the clobber
3079 (define_split
3080   [(set (match_operand:SI 0 "register_operand" "")
3081         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3082    (clobber (reg:CC 17))]
3083   "reload_completed 
3084    && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3085    && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3086   [(set (match_dup 0)
3087         (zero_extend:SI (match_dup 1)))])
3088
3089 ;; When source and destination does not overlap, clear destination
3090 ;; first and then do the movb
3091 (define_split
3092   [(set (match_operand:SI 0 "register_operand" "")
3093         (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3094    (clobber (reg:CC 17))]
3095   "reload_completed
3096    && ANY_QI_REG_P (operands[0])
3097    && (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM)
3098    && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3099    && !reg_overlap_mentioned_p (operands[0], operands[1])"
3100   [(set (match_dup 0) (const_int 0))
3101    (set (strict_low_part (match_dup 2)) (match_dup 1))]
3102   "operands[2] = gen_lowpart (QImode, operands[0]);")
3103
3104 ;; Rest is handled by single and.
3105 (define_split
3106   [(set (match_operand:SI 0 "register_operand" "")
3107         (zero_extend:SI (match_operand:QI 1 "register_operand" "")))
3108    (clobber (reg:CC 17))]
3109   "reload_completed
3110    && true_regnum (operands[0]) == true_regnum (operands[1])"
3111   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 255)))
3112               (clobber (reg:CC 17))])]
3113   "")
3114
3115 ;; %%% Kill me once multi-word ops are sane.
3116 (define_expand "zero_extendsidi2"
3117   [(set (match_operand:DI 0 "register_operand" "=r")
3118      (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm")))]
3119   ""
3120   "if (!TARGET_64BIT)
3121      {
3122        emit_insn (gen_zero_extendsidi2_32 (operands[0], operands[1]));
3123        DONE;
3124      }
3125   ")
3126
3127 (define_insn "zero_extendsidi2_32"
3128   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?*o,!?y,!?Y")
3129         (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "0,rm,r,m,m")))
3130    (clobber (reg:CC 17))]
3131   "!TARGET_64BIT && !TARGET_INTER_UNIT_MOVES"
3132   "@
3133    #
3134    #
3135    #
3136    movd\t{%1, %0|%0, %1}
3137    movd\t{%1, %0|%0, %1}"
3138   [(set_attr "mode" "SI,SI,SI,DI,TI")
3139    (set_attr "type" "multi,multi,multi,mmxmov,ssemov")])
3140
3141 (define_insn "*zero_extendsidi2_32_1"
3142   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?*o,!?y,!?Y")
3143         (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "0,rm,r,rm,rm")))
3144    (clobber (reg:CC 17))]
3145   "!TARGET_64BIT && TARGET_INTER_UNIT_MOVES"
3146   "@
3147    #
3148    #
3149    #
3150    movd\t{%1, %0|%0, %1}
3151    movd\t{%1, %0|%0, %1}"
3152   [(set_attr "mode" "SI,SI,SI,DI,TI")
3153    (set_attr "type" "multi,multi,multi,mmxmov,ssemov")])
3154
3155 (define_insn "zero_extendsidi2_rex64"
3156   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,!?y,!?Y")
3157      (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm,0,m,m")))]
3158   "TARGET_64BIT && !TARGET_INTER_UNIT_MOVES"
3159   "@
3160    mov\t{%k1, %k0|%k0, %k1}
3161    #
3162    movd\t{%1, %0|%0, %1}
3163    movd\t{%1, %0|%0, %1}"
3164   [(set_attr "type" "imovx,imov,mmxmov,ssemov")
3165    (set_attr "mode" "SI,DI,DI,TI")])
3166
3167 (define_insn "*zero_extendsidi2_rex64_1"
3168   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,!?y,!*?")
3169      (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm,0,rm,rm")))]
3170   "TARGET_64BIT && TARGET_INTER_UNIT_MOVES"
3171   "@
3172    mov\t{%k1, %k0|%k0, %k1}
3173    #
3174    movd\t{%1, %0|%0, %1}
3175    movd\t{%1, %0|%0, %1}"
3176   [(set_attr "type" "imovx,imov,mmxmov,ssemov")
3177    (set_attr "mode" "SI,DI,SI,SI")])
3178
3179 (define_split
3180   [(set (match_operand:DI 0 "memory_operand" "")
3181      (zero_extend:DI (match_dup 0)))]
3182   "TARGET_64BIT"
3183   [(set (match_dup 4) (const_int 0))]
3184   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3185
3186 (define_split 
3187   [(set (match_operand:DI 0 "register_operand" "")
3188         (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3189    (clobber (reg:CC 17))]
3190   "!TARGET_64BIT && reload_completed
3191    && true_regnum (operands[0]) == true_regnum (operands[1])"
3192   [(set (match_dup 4) (const_int 0))]
3193   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3194
3195 (define_split 
3196   [(set (match_operand:DI 0 "nonimmediate_operand" "")
3197         (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3198    (clobber (reg:CC 17))]
3199   "!TARGET_64BIT && reload_completed
3200    && !SSE_REG_P (operands[0]) && !MMX_REG_P (operands[0])"
3201   [(set (match_dup 3) (match_dup 1))
3202    (set (match_dup 4) (const_int 0))]
3203   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3204
3205 (define_insn "zero_extendhidi2"
3206   [(set (match_operand:DI 0 "register_operand" "=r,r")
3207      (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "r,m")))]
3208   "TARGET_64BIT"
3209   "@
3210    movz{wl|x}\t{%1, %k0|%k0, %1} 
3211    movz{wq|x}\t{%1, %0|%0, %1}"
3212   [(set_attr "type" "imovx")
3213    (set_attr "mode" "SI,DI")])
3214
3215 (define_insn "zero_extendqidi2"
3216   [(set (match_operand:DI 0 "register_operand" "=r,r")
3217      (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "Q,m")))]
3218   "TARGET_64BIT"
3219   "@
3220    movz{bl|x}\t{%1, %k0|%k0, %1} 
3221    movz{bq|x}\t{%1, %0|%0, %1}"
3222   [(set_attr "type" "imovx")
3223    (set_attr "mode" "SI,DI")])
3224 \f
3225 ;; Sign extension instructions
3226
3227 (define_expand "extendsidi2"
3228   [(parallel [(set (match_operand:DI 0 "register_operand" "")
3229                    (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3230               (clobber (reg:CC 17))
3231               (clobber (match_scratch:SI 2 ""))])]
3232   ""
3233 {
3234   if (TARGET_64BIT)
3235     {
3236       emit_insn (gen_extendsidi2_rex64 (operands[0], operands[1]));
3237       DONE;
3238     }
3239 })
3240
3241 (define_insn "*extendsidi2_1"
3242   [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3243         (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3244    (clobber (reg:CC 17))
3245    (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3246   "!TARGET_64BIT"
3247   "#")
3248
3249 (define_insn "extendsidi2_rex64"
3250   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3251         (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3252   "TARGET_64BIT"
3253   "@
3254    {cltq|cdqe}
3255    movs{lq|x}\t{%1,%0|%0, %1}"
3256   [(set_attr "type" "imovx")
3257    (set_attr "mode" "DI")
3258    (set_attr "prefix_0f" "0")
3259    (set_attr "modrm" "0,1")])
3260
3261 (define_insn "extendhidi2"
3262   [(set (match_operand:DI 0 "register_operand" "=r")
3263         (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3264   "TARGET_64BIT"
3265   "movs{wq|x}\t{%1,%0|%0, %1}"
3266   [(set_attr "type" "imovx")
3267    (set_attr "mode" "DI")])
3268
3269 (define_insn "extendqidi2"
3270   [(set (match_operand:DI 0 "register_operand" "=r")
3271         (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3272   "TARGET_64BIT"
3273   "movs{bq|x}\t{%1,%0|%0, %1}"
3274    [(set_attr "type" "imovx")
3275     (set_attr "mode" "DI")])
3276
3277 ;; Extend to memory case when source register does die.
3278 (define_split 
3279   [(set (match_operand:DI 0 "memory_operand" "")
3280         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3281    (clobber (reg:CC 17))
3282    (clobber (match_operand:SI 2 "register_operand" ""))]
3283   "(reload_completed
3284     && dead_or_set_p (insn, operands[1])
3285     && !reg_mentioned_p (operands[1], operands[0]))"
3286   [(set (match_dup 3) (match_dup 1))
3287    (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3288               (clobber (reg:CC 17))])
3289    (set (match_dup 4) (match_dup 1))]
3290   "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3291
3292 ;; Extend to memory case when source register does not die.
3293 (define_split 
3294   [(set (match_operand:DI 0 "memory_operand" "")
3295         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3296    (clobber (reg:CC 17))
3297    (clobber (match_operand:SI 2 "register_operand" ""))]
3298   "reload_completed"
3299   [(const_int 0)]
3300 {
3301   split_di (&operands[0], 1, &operands[3], &operands[4]);
3302
3303   emit_move_insn (operands[3], operands[1]);
3304
3305   /* Generate a cltd if possible and doing so it profitable.  */
3306   if (true_regnum (operands[1]) == 0
3307       && true_regnum (operands[2]) == 1
3308       && (optimize_size || TARGET_USE_CLTD))
3309     {
3310       emit_insn (gen_ashrsi3_31 (operands[2], operands[1], GEN_INT (31)));
3311     }
3312   else
3313     {
3314       emit_move_insn (operands[2], operands[1]);
3315       emit_insn (gen_ashrsi3_31 (operands[2], operands[2], GEN_INT (31)));
3316     }
3317   emit_move_insn (operands[4], operands[2]);
3318   DONE;
3319 })
3320
3321 ;; Extend to register case.  Optimize case where source and destination
3322 ;; registers match and cases where we can use cltd.
3323 (define_split 
3324   [(set (match_operand:DI 0 "register_operand" "")
3325         (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3326    (clobber (reg:CC 17))
3327    (clobber (match_scratch:SI 2 ""))]
3328   "reload_completed"
3329   [(const_int 0)]
3330 {
3331   split_di (&operands[0], 1, &operands[3], &operands[4]);
3332
3333   if (true_regnum (operands[3]) != true_regnum (operands[1]))
3334     emit_move_insn (operands[3], operands[1]);
3335
3336   /* Generate a cltd if possible and doing so it profitable.  */
3337   if (true_regnum (operands[3]) == 0
3338       && (optimize_size || TARGET_USE_CLTD))
3339     {
3340       emit_insn (gen_ashrsi3_31 (operands[4], operands[3], GEN_INT (31)));
3341       DONE;
3342     }
3343
3344   if (true_regnum (operands[4]) != true_regnum (operands[1]))
3345     emit_move_insn (operands[4], operands[1]);
3346
3347   emit_insn (gen_ashrsi3_31 (operands[4], operands[4], GEN_INT (31)));
3348   DONE;
3349 })
3350
3351 (define_insn "extendhisi2"
3352   [(set (match_operand:SI 0 "register_operand" "=*a,r")
3353         (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3354   ""
3355 {
3356   switch (get_attr_prefix_0f (insn))
3357     {
3358     case 0:
3359       return "{cwtl|cwde}";
3360     default:
3361       return "movs{wl|x}\t{%1,%0|%0, %1}";
3362     }
3363 }
3364   [(set_attr "type" "imovx")
3365    (set_attr "mode" "SI")
3366    (set (attr "prefix_0f")
3367      ;; movsx is short decodable while cwtl is vector decoded.
3368      (if_then_else (and (eq_attr "cpu" "!k6")
3369                         (eq_attr "alternative" "0"))
3370         (const_string "0")
3371         (const_string "1")))
3372    (set (attr "modrm")
3373      (if_then_else (eq_attr "prefix_0f" "0")
3374         (const_string "0")
3375         (const_string "1")))])
3376
3377 (define_insn "*extendhisi2_zext"
3378   [(set (match_operand:DI 0 "register_operand" "=*a,r")
3379         (zero_extend:DI
3380           (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3381   "TARGET_64BIT"
3382 {
3383   switch (get_attr_prefix_0f (insn))
3384     {
3385     case 0:
3386       return "{cwtl|cwde}";
3387     default:
3388       return "movs{wl|x}\t{%1,%k0|%k0, %1}";
3389     }
3390 }
3391   [(set_attr "type" "imovx")
3392    (set_attr "mode" "SI")
3393    (set (attr "prefix_0f")
3394      ;; movsx is short decodable while cwtl is vector decoded.
3395      (if_then_else (and (eq_attr "cpu" "!k6")
3396                         (eq_attr "alternative" "0"))
3397         (const_string "0")
3398         (const_string "1")))
3399    (set (attr "modrm")
3400      (if_then_else (eq_attr "prefix_0f" "0")
3401         (const_string "0")
3402         (const_string "1")))])
3403
3404 (define_insn "extendqihi2"
3405   [(set (match_operand:HI 0 "register_operand" "=*a,r")
3406         (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3407   ""
3408 {
3409   switch (get_attr_prefix_0f (insn))
3410     {
3411     case 0:
3412       return "{cbtw|cbw}";
3413     default:
3414       return "movs{bw|x}\t{%1,%0|%0, %1}";
3415     }
3416 }
3417   [(set_attr "type" "imovx")
3418    (set_attr "mode" "HI")
3419    (set (attr "prefix_0f")
3420      ;; movsx is short decodable while cwtl is vector decoded.
3421      (if_then_else (and (eq_attr "cpu" "!k6")
3422                         (eq_attr "alternative" "0"))
3423         (const_string "0")
3424         (const_string "1")))
3425    (set (attr "modrm")
3426      (if_then_else (eq_attr "prefix_0f" "0")
3427         (const_string "0")
3428         (const_string "1")))])
3429
3430 (define_insn "extendqisi2"
3431   [(set (match_operand:SI 0 "register_operand" "=r")
3432         (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3433   ""
3434   "movs{bl|x}\t{%1,%0|%0, %1}"
3435    [(set_attr "type" "imovx")
3436     (set_attr "mode" "SI")])
3437
3438 (define_insn "*extendqisi2_zext"
3439   [(set (match_operand:DI 0 "register_operand" "=r")
3440         (zero_extend:DI
3441           (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3442   "TARGET_64BIT"
3443   "movs{bl|x}\t{%1,%k0|%k0, %1}"
3444    [(set_attr "type" "imovx")
3445     (set_attr "mode" "SI")])
3446 \f
3447 ;; Conversions between float and double.
3448
3449 ;; These are all no-ops in the model used for the 80387.  So just
3450 ;; emit moves.
3451
3452 ;; %%% Kill these when call knows how to work out a DFmode push earlier. 
3453 (define_insn "*dummy_extendsfdf2"
3454   [(set (match_operand:DF 0 "push_operand" "=<")
3455         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fY")))]
3456   "0"
3457   "#")
3458
3459 (define_split
3460   [(set (match_operand:DF 0 "push_operand" "")
3461         (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3462   "!TARGET_64BIT"
3463   [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
3464    (set (mem:DF (reg:SI 7)) (float_extend:DF (match_dup 1)))])
3465
3466 (define_split
3467   [(set (match_operand:DF 0 "push_operand" "")
3468         (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3469   "TARGET_64BIT"
3470   [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -8)))
3471    (set (mem:DF (reg:DI 7)) (float_extend:DF (match_dup 1)))])
3472
3473 (define_insn "*dummy_extendsfxf2"
3474   [(set (match_operand:XF 0 "push_operand" "=<")
3475         (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "f")))]
3476   "0"
3477   "#")
3478
3479 (define_split
3480   [(set (match_operand:XF 0 "push_operand" "")
3481         (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3482   ""
3483   [(set (reg:SI 7) (plus:SI (reg:SI 7) (match_dup 2)))
3484    (set (mem:XF (reg:SI 7)) (float_extend:XF (match_dup 1)))]
3485   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3486
3487 (define_split
3488   [(set (match_operand:XF 0 "push_operand" "")
3489         (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3490   "TARGET_64BIT"
3491   [(set (reg:DI 7) (plus:DI (reg:DI 7) (match_dup 2)))
3492    (set (mem:DF (reg:DI 7)) (float_extend:XF (match_dup 1)))]
3493   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3494
3495 (define_split
3496   [(set (match_operand:XF 0 "push_operand" "")
3497         (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3498   ""
3499   [(set (reg:SI 7) (plus:SI (reg:SI 7) (match_dup 2)))
3500    (set (mem:DF (reg:SI 7)) (float_extend:XF (match_dup 1)))]
3501   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3502
3503 (define_split
3504   [(set (match_operand:XF 0 "push_operand" "")
3505         (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3506   "TARGET_64BIT"
3507   [(set (reg:DI 7) (plus:DI (reg:DI 7) (match_dup 2)))
3508    (set (mem:XF (reg:DI 7)) (float_extend:XF (match_dup 1)))]
3509   "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3510
3511 (define_expand "extendsfdf2"
3512   [(set (match_operand:DF 0 "nonimmediate_operand" "")
3513         (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
3514   "TARGET_80387 || TARGET_SSE2"
3515 {
3516   /* ??? Needed for compress_float_constant since all fp constants
3517      are LEGITIMATE_CONSTANT_P.  */
3518   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3519     operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3520   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3521     operands[1] = force_reg (SFmode, operands[1]);
3522 })
3523
3524 (define_insn "*extendsfdf2_1"
3525   [(set (match_operand:DF 0 "nonimmediate_operand" "=f#Y,mf#Y,Y#f")
3526         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm#Y,f#Y,mY#f")))]
3527   "(TARGET_80387 || TARGET_SSE2)
3528    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3529 {
3530   switch (which_alternative)
3531     {
3532     case 0:
3533       if (REG_P (operands[1])
3534           && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3535         return "fstp\t%y0";
3536       else if (STACK_TOP_P (operands[0]))
3537         return "fld%z1\t%y1";
3538       else
3539         return "fst\t%y0";
3540
3541     case 1:
3542       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3543         return "fstp%z0\t%y0";
3544
3545       else
3546         return "fst%z0\t%y0";
3547     case 2:
3548       return "cvtss2sd\t{%1, %0|%0, %1}";
3549
3550     default:
3551       abort ();
3552     }
3553 }
3554   [(set_attr "type" "fmov,fmov,ssecvt")
3555    (set_attr "mode" "SF,XF,DF")])
3556
3557 (define_insn "*extendsfdf2_1_sse_only"
3558   [(set (match_operand:DF 0 "register_operand" "=Y")
3559         (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "mY")))]
3560   "!TARGET_80387 && TARGET_SSE2
3561    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3562   "cvtss2sd\t{%1, %0|%0, %1}"
3563   [(set_attr "type" "ssecvt")
3564    (set_attr "mode" "DF")])
3565
3566 (define_expand "extendsfxf2"
3567   [(set (match_operand:XF 0 "nonimmediate_operand" "")
3568         (float_extend:XF (match_operand:SF 1 "general_operand" "")))]
3569   "TARGET_80387"
3570 {
3571   /* ??? Needed for compress_float_constant since all fp constants
3572      are LEGITIMATE_CONSTANT_P.  */
3573   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3574     operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3575   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3576     operands[1] = force_reg (SFmode, operands[1]);
3577 })
3578
3579 (define_insn "*extendsfxf2_1"
3580   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3581         (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3582   "TARGET_80387
3583    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3584 {
3585   switch (which_alternative)
3586     {
3587     case 0:
3588       if (REG_P (operands[1])
3589           && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3590         return "fstp\t%y0";
3591       else if (STACK_TOP_P (operands[0]))
3592         return "fld%z1\t%y1";
3593       else
3594         return "fst\t%y0";
3595
3596     case 1:
3597       /* There is no non-popping store to memory for XFmode.  So if
3598          we need one, follow the store with a load.  */
3599       if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3600         return "fstp%z0\t%y0\n\tfld%z0\t%y0";
3601       else
3602         return "fstp%z0\t%y0";
3603
3604     default:
3605       abort ();
3606     }
3607 }
3608   [(set_attr "type" "fmov")
3609    (set_attr "mode" "SF,XF")])
3610
3611 (define_expand "extenddfxf2"
3612   [(set (match_operand:XF 0 "nonimmediate_operand" "")
3613         (float_extend:XF (match_operand:DF 1 "general_operand" "")))]
3614   "TARGET_80387"
3615 {
3616   /* ??? Needed for compress_float_constant since all fp constants
3617      are LEGITIMATE_CONSTANT_P.  */
3618   if (GET_CODE (operands[1]) == CONST_DOUBLE)
3619     operands[1] = validize_mem (force_const_mem (DFmode, operands[1]));
3620   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3621     operands[1] = force_reg (DFmode, operands[1]);
3622 })
3623
3624 (define_insn "*extenddfxf2_1"
3625   [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3626         (float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "fm,f")))]
3627   "TARGET_80387
3628    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3629 {
3630   switch (which_alternative)
3631     {
3632     case 0:
3633       if (REG_P (operands[1])
3634           && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3635         return "fstp\t%y0";
3636       else if (STACK_TOP_P (operands[0]))
3637         return "fld%z1\t%y1";
3638       else
3639         return "fst\t%y0";
3640
3641     case 1:
3642       /* There is no non-popping store to memory for XFmode.  So if
3643          we need one, follow the store with a load.  */
3644       if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3645         return "fstp%z0\t%y0\n\tfld%z0\t%y0";
3646       else
3647         return "fstp%z0\t%y0";
3648
3649     default:
3650       abort ();
3651     }
3652 }
3653   [(set_attr "type" "fmov")
3654    (set_attr "mode" "DF,XF")])
3655
3656 ;; %%% This seems bad bad news.
3657 ;; This cannot output into an f-reg because there is no way to be sure
3658 ;; of truncating in that case.  Otherwise this is just like a simple move
3659 ;; insn.  So we pretend we can output to a reg in order to get better
3660 ;; register preferencing, but we really use a stack slot.
3661
3662 (define_expand "truncdfsf2"
3663   [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
3664                    (float_truncate:SF
3665                     (match_operand:DF 1 "register_operand" "")))
3666               (clobber (match_dup 2))])]
3667   "TARGET_80387 || TARGET_SSE2"
3668   "
3669    if (TARGET_80387)
3670      operands[2] = assign_386_stack_local (SFmode, 0);
3671    else
3672      {
3673         emit_insn (gen_truncdfsf2_sse_only (operands[0], operands[1]));
3674         DONE;
3675      }
3676 ")
3677
3678 (define_insn "*truncdfsf2_1"
3679   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f#rx,?r#fx,?x#rf")
3680         (float_truncate:SF
3681          (match_operand:DF 1 "register_operand" "f,f,f,f")))
3682    (clobber (match_operand:SF 2 "memory_operand" "=X,m,m,m"))]
3683   "TARGET_80387 && !TARGET_SSE2"
3684 {
3685   switch (which_alternative)
3686     {
3687     case 0:
3688       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3689         return "fstp%z0\t%y0";
3690       else
3691         return "fst%z0\t%y0";
3692     default:
3693       abort ();
3694     }
3695 }
3696   [(set_attr "type" "fmov,multi,multi,multi")
3697    (set_attr "mode" "SF,SF,SF,SF")])
3698
3699 (define_insn "*truncdfsf2_1_sse"
3700   [(set (match_operand:SF 0 "nonimmediate_operand" "=*!m#fxr,?f#xr,?r#fx,?x#fr,Y#fr")
3701         (float_truncate:SF
3702          (match_operand:DF 1 "nonimmediate_operand" "f#Y,f#Y,f#Y,f#Y,mY#f")))
3703    (clobber (match_operand:SF 2 "memory_operand" "=X,m,m,m,X"))]
3704   "TARGET_80387 && TARGET_SSE2 && !TARGET_SSE_PARTIAL_REGS_FOR_CVTSD2SS"
3705 {
3706   switch (which_alternative)
3707     {
3708     case 0:
3709       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3710         return "fstp%z0\t%y0";
3711       else
3712         return "fst%z0\t%y0";
3713     case 4:
3714       return "#";
3715     default:
3716       abort ();
3717     }
3718 }
3719   [(set_attr "type" "fmov,multi,multi,multi,ssecvt")
3720    (set_attr "mode" "SF,SF,SF,SF,DF")])
3721
3722 (define_insn "*truncdfsf2_1_sse_nooverlap"
3723   [(set (match_operand:SF 0 "nonimmediate_operand" "=*!m,?f#rx,?r#fx,?x#rf,&Y")
3724         (float_truncate:SF
3725          (match_operand:DF 1 "nonimmediate_operand" "f#Y,f#Y,f#Y,f#Y,mY#f")))
3726    (clobber (match_operand:SF 2 "memory_operand" "=X,m,m,m,X"))]
3727   "TARGET_80387 && TARGET_SSE2 && TARGET_SSE_PARTIAL_REGS_FOR_CVTSD2SS"
3728 {
3729   switch (which_alternative)
3730     {
3731     case 0:
3732       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3733         return "fstp%z0\t%y0";
3734       else
3735         return "fst%z0\t%y0";
3736     case 4:
3737       return "#";
3738     default:
3739       abort ();
3740     }
3741 }
3742   [(set_attr "type" "fmov,multi,multi,multi,ssecvt")
3743    (set_attr "mode" "SF,SF,SF,SF,DF")])
3744
3745 (define_insn "*truncdfsf2_2"
3746   [(set (match_operand:SF 0 "nonimmediate_operand" "=Y,Y,!m")
3747         (float_truncate:SF
3748          (match_operand:DF 1 "nonimmediate_operand" "Y,mY,f#Y")))]
3749   "TARGET_80387 && TARGET_SSE2 && !TARGET_SSE_PARTIAL_REGS_FOR_CVTSD2SS
3750    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3751 {
3752   switch (which_alternative)
3753     {
3754     case 0:
3755     case 1:
3756       return "cvtsd2ss\t{%1, %0|%0, %1}";
3757     case 2:
3758       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3759         return "fstp%z0\t%y0";
3760       else
3761         return "fst%z0\t%y0";
3762     default:
3763       abort ();
3764     }
3765 }
3766   [(set_attr "type" "ssecvt,ssecvt,fmov")
3767    (set_attr "athlon_decode" "vector,double,*")
3768    (set_attr "mode" "SF,SF,SF")])
3769
3770 (define_insn "*truncdfsf2_2_nooverlap"
3771   [(set (match_operand:SF 0 "nonimmediate_operand" "=&Y,!m")
3772         (float_truncate:SF
3773          (match_operand:DF 1 "nonimmediate_operand" "mY,f")))]
3774   "TARGET_80387 && TARGET_SSE2 && TARGET_SSE_PARTIAL_REGS_FOR_CVTSD2SS
3775    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3776 {
3777   switch (which_alternative)
3778     {
3779     case 0:
3780       return "#";
3781     case 1:
3782       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3783         return "fstp%z0\t%y0";
3784       else
3785         return "fst%z0\t%y0";
3786     default:
3787       abort ();
3788     }
3789 }
3790   [(set_attr "type" "ssecvt,fmov")
3791    (set_attr "mode" "DF,SF")])
3792
3793 (define_insn "*truncdfsf2_3"
3794   [(set (match_operand:SF 0 "memory_operand" "=m")
3795         (float_truncate:SF
3796          (match_operand:DF 1 "register_operand" "f")))]
3797   "TARGET_80387"
3798 {
3799   if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3800     return "fstp%z0\t%y0";
3801   else
3802     return "fst%z0\t%y0";
3803 }
3804   [(set_attr "type" "fmov")
3805    (set_attr "mode" "SF")])
3806
3807 (define_insn "truncdfsf2_sse_only"
3808   [(set (match_operand:SF 0 "register_operand" "=Y,Y")
3809         (float_truncate:SF
3810          (match_operand:DF 1 "nonimmediate_operand" "Y,mY")))]
3811   "!TARGET_80387 && TARGET_SSE2 && !TARGET_SSE_PARTIAL_REGS_FOR_CVTSD2SS"
3812   "cvtsd2ss\t{%1, %0|%0, %1}"
3813   [(set_attr "type" "ssecvt")
3814    (set_attr "athlon_decode" "vector,double")
3815    (set_attr "mode" "SF")])
3816
3817 (define_insn "*truncdfsf2_sse_only_nooverlap"
3818   [(set (match_operand:SF 0 "register_operand" "=&Y")
3819         (float_truncate:SF
3820          (match_operand:DF 1 "nonimmediate_operand" "mY")))]
3821   "!TARGET_80387 && TARGET_SSE2 && TARGET_SSE_PARTIAL_REGS_FOR_CVTSD2SS"
3822   "#"
3823   [(set_attr "type" "ssecvt")
3824    (set_attr "mode" "DF")])
3825
3826 (define_split
3827   [(set (match_operand:SF 0 "memory_operand" "")
3828         (float_truncate:SF
3829          (match_operand:DF 1 "register_operand" "")))
3830    (clobber (match_operand:SF 2 "memory_operand" ""))]
3831   "TARGET_80387"
3832   [(set (match_dup 0) (float_truncate:SF (match_dup 1)))]
3833   "")
3834
3835 ; Avoid possible reformatting penalty on the destination by first
3836 ; zeroing it out
3837 (define_split
3838   [(set (match_operand:SF 0 "register_operand" "")
3839         (float_truncate:SF
3840          (match_operand:DF 1 "nonimmediate_operand" "")))
3841    (clobber (match_operand 2 "" ""))]
3842   "TARGET_80387 && reload_completed
3843    && SSE_REG_P (operands[0])
3844    && !STACK_REG_P (operands[1])"
3845   [(const_int 0)]
3846 {
3847   rtx src, dest;
3848   if (!TARGET_SSE_PARTIAL_REGS_FOR_CVTSD2SS)
3849     emit_insn (gen_truncdfsf2_sse_only (operands[0], operands[1]));
3850   else
3851     {
3852       dest = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
3853       src = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
3854       /* simplify_gen_subreg refuses to widen memory references.  */
3855       if (GET_CODE (src) == SUBREG)
3856         alter_subreg (&src);
3857       if (reg_overlap_mentioned_p (operands[0], operands[1]))
3858         abort ();
3859       emit_insn (gen_sse_clrv4sf (dest, CONST0_RTX (V4SFmode)));
3860       emit_insn (gen_cvtsd2ss (dest, dest, src));
3861     }
3862   DONE;
3863 })
3864
3865 (define_split
3866   [(set (match_operand:SF 0 "register_operand" "")
3867         (float_truncate:SF
3868          (match_operand:DF 1 "nonimmediate_operand" "")))]
3869   "TARGET_80387 && reload_completed
3870    && SSE_REG_P (operands[0]) && TARGET_SSE_PARTIAL_REGS_FOR_CVTSD2SS"
3871   [(const_int 0)]
3872 {
3873   rtx src, dest;
3874   dest = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
3875   src = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
3876   /* simplify_gen_subreg refuses to widen memory references.  */
3877   if (GET_CODE (src) == SUBREG)
3878     alter_subreg (&src);
3879   if (reg_overlap_mentioned_p (operands[0], operands[1]))
3880     abort ();
3881   emit_insn (gen_sse_clrv4sf (dest, CONST0_RTX (V4SFmode)));
3882   emit_insn (gen_cvtsd2ss (dest, dest, src));
3883   DONE;
3884 })
3885
3886 (define_split
3887   [(set (match_operand:SF 0 "register_operand" "")
3888         (float_truncate:SF
3889          (match_operand:DF 1 "fp_register_operand" "")))
3890    (clobber (match_operand:SF 2 "memory_operand" ""))]
3891   "TARGET_80387 && reload_completed"
3892   [(set (match_dup 2) (float_truncate:SF (match_dup 1)))
3893    (set (match_dup 0) (match_dup 2))]
3894   "")
3895
3896 (define_expand "truncxfsf2"
3897   [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
3898                    (float_truncate:SF
3899                     (match_operand:XF 1 "register_operand" "")))
3900               (clobber (match_dup 2))])]
3901   "TARGET_80387"
3902   "operands[2] = assign_386_stack_local (SFmode, 0);")
3903
3904 (define_insn "*truncxfsf2_1"
3905   [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f#rx,?r#fx,?x#rf")
3906         (float_truncate:SF
3907          (match_operand:XF 1 "register_operand" "f,f,f,f")))
3908    (clobber (match_operand:SF 2 "memory_operand" "=X,m,m,m"))]
3909   "TARGET_80387"
3910 {
3911   switch (which_alternative)
3912     {
3913     case 0:
3914       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3915         return "fstp%z0\t%y0";
3916       else
3917         return "fst%z0\t%y0";
3918     default:
3919       abort();
3920     }
3921 }
3922   [(set_attr "type" "fmov,multi,multi,multi")
3923    (set_attr "mode" "SF")])
3924
3925 (define_insn "*truncxfsf2_2"
3926   [(set (match_operand:SF 0 "memory_operand" "=m")
3927         (float_truncate:SF
3928          (match_operand:XF 1 "register_operand" "f")))]
3929   "TARGET_80387"
3930 {
3931   if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3932     return "fstp%z0\t%y0";
3933   else
3934     return "fst%z0\t%y0";
3935 }
3936   [(set_attr "type" "fmov")
3937    (set_attr "mode" "SF")])
3938
3939 (define_split
3940   [(set (match_operand:SF 0 "memory_operand" "")
3941         (float_truncate:SF
3942          (match_operand:XF 1 "register_operand" "")))
3943    (clobber (match_operand:SF 2 "memory_operand" ""))]
3944   "TARGET_80387"
3945   [(set (match_dup 0) (float_truncate:SF (match_dup 1)))]
3946   "")
3947
3948 (define_split
3949   [(set (match_operand:SF 0 "register_operand" "")
3950         (float_truncate:SF
3951          (match_operand:XF 1 "register_operand" "")))
3952    (clobber (match_operand:SF 2 "memory_operand" ""))]
3953   "TARGET_80387 && reload_completed"
3954   [(set (match_dup 2) (float_truncate:SF (match_dup 1)))
3955    (set (match_dup 0) (match_dup 2))]
3956   "")
3957
3958 (define_expand "truncxfdf2"
3959   [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
3960                    (float_truncate:DF
3961                     (match_operand:XF 1 "register_operand" "")))
3962               (clobber (match_dup 2))])]
3963   "TARGET_80387"
3964   "operands[2] = assign_386_stack_local (DFmode, 0);")
3965
3966 (define_insn "*truncxfdf2_1"
3967   [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f#rY,?r#fY,?Y#rf")
3968         (float_truncate:DF
3969          (match_operand:XF 1 "register_operand" "f,f,f,f")))
3970    (clobber (match_operand:DF 2 "memory_operand" "=X,m,m,m"))]
3971   "TARGET_80387"
3972 {
3973   switch (which_alternative)
3974     {
3975     case 0:
3976       if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3977         return "fstp%z0\t%y0";
3978       else
3979         return "fst%z0\t%y0";
3980     default:
3981       abort();
3982     }
3983   abort ();
3984 }
3985   [(set_attr "type" "fmov,multi,multi,multi")
3986    (set_attr "mode" "DF")])
3987
3988 (define_insn "*truncxfdf2_2"
3989   [(set (match_operand:DF 0 "memory_operand" "=m")
3990         (float_truncate:DF
3991           (match_operand:XF 1 "register_operand" "f")))]
3992   "TARGET_80387"
3993 {
3994   if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3995     return "fstp%z0\t%y0";
3996   else
3997     return "fst%z0\t%y0";
3998 }
3999   [(set_attr "type" "fmov")
4000    (set_attr "mode" "DF")])
4001
4002 (define_split
4003   [(set (match_operand:DF 0 "memory_operand" "")
4004         (float_truncate:DF
4005          (match_operand:XF 1 "register_operand" "")))
4006    (clobber (match_operand:DF 2 "memory_operand" ""))]
4007   "TARGET_80387"
4008   [(set (match_dup 0) (float_truncate:DF (match_dup 1)))]
4009   "")
4010
4011 (define_split
4012   [(set (match_operand:DF 0 "register_operand" "")
4013         (float_truncate:DF
4014          (match_operand:XF 1 "register_operand" "")))
4015    (clobber (match_operand:DF 2 "memory_operand" ""))]
4016   "TARGET_80387 && reload_completed"
4017   [(set (match_dup 2) (float_truncate:DF (match_dup 1)))
4018    (set (match_dup 0) (match_dup 2))]
4019   "")
4020
4021 \f
4022 ;; %%% Break up all these bad boys.
4023
4024 ;; Signed conversion to DImode.
4025
4026 (define_expand "fix_truncxfdi2"
4027   [(set (match_operand:DI 0 "nonimmediate_operand" "")
4028         (fix:DI (match_operand:XF 1 "register_operand" "")))]
4029   "TARGET_80387"
4030   "")
4031
4032 (define_expand "fix_truncdfdi2"
4033   [(set (match_operand:DI 0 "nonimmediate_operand" "")
4034         (fix:DI (match_operand:DF 1 "register_operand" "")))]
4035   "TARGET_80387 || (TARGET_SSE2 && TARGET_64BIT)"
4036 {
4037   if (TARGET_64BIT && TARGET_SSE2)
4038    {
4039      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4040      emit_insn (gen_fix_truncdfdi_sse (out, operands[1]));
4041      if (out != operands[0])
4042         emit_move_insn (operands[0], out);
4043      DONE;
4044    }
4045 })
4046
4047 (define_expand "fix_truncsfdi2"
4048   [(set (match_operand:DI 0 "nonimmediate_operand" "")
4049         (fix:DI (match_operand:SF 1 "register_operand" "")))]
4050   "TARGET_80387 || (TARGET_SSE && TARGET_64BIT)"
4051 {
4052   if (TARGET_SSE && TARGET_64BIT)
4053    {
4054      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4055      emit_insn (gen_fix_truncsfdi_sse (out, operands[1]));
4056      if (out != operands[0])
4057         emit_move_insn (operands[0], out);
4058      DONE;
4059    }
4060 })
4061
4062 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4063 ;; of the machinery.
4064 (define_insn_and_split "*fix_truncdi_1"
4065   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4066         (fix:DI (match_operand 1 "register_operand" "f,f")))]
4067   "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4068    && !reload_completed && !reload_in_progress
4069    && (!SSE_FLOAT_MODE_P (GET_MODE (operands[1])) || !TARGET_64BIT)"
4070   "#"
4071   "&& 1"
4072   [(const_int 0)]
4073 {
4074   ix86_optimize_mode_switching = 1;
4075   operands[2] = assign_386_stack_local (HImode, 1);
4076   operands[3] = assign_386_stack_local (HImode, 2);
4077   if (memory_operand (operands[0], VOIDmode))
4078     emit_insn (gen_fix_truncdi_memory (operands[0], operands[1],
4079                                        operands[2], operands[3]));
4080   else
4081     {
4082       operands[4] = assign_386_stack_local (DImode, 0);
4083       emit_insn (gen_fix_truncdi_nomemory (operands[0], operands[1],
4084                                            operands[2], operands[3],
4085                                            operands[4]));
4086     }
4087   DONE;
4088 }
4089   [(set_attr "type" "fistp")
4090    (set_attr "mode" "DI")])
4091
4092 (define_insn "fix_truncdi_nomemory"
4093   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4094         (fix:DI (match_operand 1 "register_operand" "f,f")))
4095    (use (match_operand:HI 2 "memory_operand" "m,m"))
4096    (use (match_operand:HI 3 "memory_operand" "m,m"))
4097    (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
4098    (clobber (match_scratch:DF 5 "=&1f,&1f"))]
4099   "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4100    && (!SSE_FLOAT_MODE_P (GET_MODE (operands[1])) || !TARGET_64BIT)"
4101   "#"
4102   [(set_attr "type" "fistp")
4103    (set_attr "mode" "DI")])
4104
4105 (define_insn "fix_truncdi_memory"
4106   [(set (match_operand:DI 0 "memory_operand" "=m")
4107         (fix:DI (match_operand 1 "register_operand" "f")))
4108    (use (match_operand:HI 2 "memory_operand" "m"))
4109    (use (match_operand:HI 3 "memory_operand" "m"))
4110    (clobber (match_scratch:DF 4 "=&1f"))]
4111   "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4112    && (!SSE_FLOAT_MODE_P (GET_MODE (operands[1])) || !TARGET_64BIT)"
4113   "* operands[5] = operands[4]; return output_fix_trunc (insn, operands);"
4114   [(set_attr "type" "fistp")
4115    (set_attr "mode" "DI")])
4116
4117 (define_split 
4118   [(set (match_operand:DI 0 "register_operand" "")
4119         (fix:DI (match_operand 1 "register_operand" "")))
4120    (use (match_operand:HI 2 "memory_operand" ""))
4121    (use (match_operand:HI 3 "memory_operand" ""))
4122    (clobber (match_operand:DI 4 "memory_operand" ""))
4123    (clobber (match_scratch 5 ""))]
4124   "reload_completed"
4125   [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
4126               (use (match_dup 2))
4127               (use (match_dup 3))
4128               (clobber (match_dup 5))])
4129    (set (match_dup 0) (match_dup 4))]
4130   "")
4131
4132 (define_split 
4133   [(set (match_operand:DI 0 "memory_operand" "")
4134         (fix:DI (match_operand 1 "register_operand" "")))
4135    (use (match_operand:HI 2 "memory_operand" ""))
4136    (use (match_operand:HI 3 "memory_operand" ""))
4137    (clobber (match_operand:DI 4 "memory_operand" ""))
4138    (clobber (match_scratch 5 ""))]
4139   "reload_completed"
4140   [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
4141               (use (match_dup 2))
4142               (use (match_dup 3))
4143               (clobber (match_dup 5))])]
4144   "")
4145
4146 ;; When SSE available, it is always faster to use it!
4147 (define_insn "fix_truncsfdi_sse"
4148   [(set (match_operand:DI 0 "register_operand" "=r,r")
4149         (fix:DI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))]
4150   "TARGET_64BIT && TARGET_SSE"
4151   "cvttss2si{q}\t{%1, %0|%0, %1}"
4152   [(set_attr "type" "sseicvt")
4153    (set_attr "mode" "SF")
4154    (set_attr "athlon_decode" "double,vector")])
4155
4156 ;; Avoid vector decoded form of the instruction.
4157 (define_peephole2
4158   [(match_scratch:SF 2 "x")
4159    (set (match_operand:DI 0 "register_operand" "")
4160         (fix:DI (match_operand:SF 1 "memory_operand" "")))]
4161   "TARGET_K8 && !optimize_size"
4162   [(set (match_dup 2) (match_dup 1))
4163    (set (match_dup 0) (fix:DI (match_dup 2)))]
4164   "")
4165
4166 (define_insn "fix_truncdfdi_sse"
4167   [(set (match_operand:DI 0 "register_operand" "=r,r")
4168         (fix:DI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))]
4169   "TARGET_64BIT && TARGET_SSE2"
4170   "cvttsd2si{q}\t{%1, %0|%0, %1}"
4171   [(set_attr "type" "sseicvt,sseicvt")
4172    (set_attr "mode" "DF")
4173    (set_attr "athlon_decode" "double,vector")])
4174
4175 ;; Avoid vector decoded form of the instruction.
4176 (define_peephole2
4177   [(match_scratch:DF 2 "Y")
4178    (set (match_operand:DI 0 "register_operand" "")
4179         (fix:DI (match_operand:DF 1 "memory_operand" "")))]
4180   "TARGET_K8 && !optimize_size"
4181   [(set (match_dup 2) (match_dup 1))
4182    (set (match_dup 0) (fix:DI (match_dup 2)))]
4183   "")
4184
4185 ;; Signed conversion to SImode.
4186
4187 (define_expand "fix_truncxfsi2"
4188   [(set (match_operand:SI 0 "nonimmediate_operand" "")
4189         (fix:SI (match_operand:XF 1 "register_operand" "")))]
4190   "TARGET_80387"
4191   "")
4192
4193 (define_expand "fix_truncdfsi2"
4194   [(set (match_operand:SI 0 "nonimmediate_operand" "")
4195         (fix:SI (match_operand:DF 1 "register_operand" "")))]
4196   "TARGET_80387 || TARGET_SSE2"
4197 {
4198   if (TARGET_SSE2)
4199    {
4200      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4201      emit_insn (gen_fix_truncdfsi_sse (out, operands[1]));
4202      if (out != operands[0])
4203         emit_move_insn (operands[0], out);
4204      DONE;
4205    }
4206 })
4207
4208 (define_expand "fix_truncsfsi2"
4209   [(set (match_operand:SI 0 "nonimmediate_operand" "")
4210         (fix:SI (match_operand:SF 1 "register_operand" "")))]
4211   "TARGET_80387 || TARGET_SSE"
4212 {
4213   if (TARGET_SSE)
4214    {
4215      rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4216      emit_insn (gen_fix_truncsfsi_sse (out, operands[1]));
4217      if (out != operands[0])
4218         emit_move_insn (operands[0], out);
4219      DONE;
4220    }
4221 })
4222
4223 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4224 ;; of the machinery.
4225 (define_insn_and_split "*fix_truncsi_1"
4226   [(set (match_operand:SI 0 "nonimmediate_operand" "=m,?r")
4227         (fix:SI (match_operand 1 "register_operand" "f,f")))]
4228   "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4229    && !reload_completed && !reload_in_progress
4230    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4231   "#"
4232   "&& 1"
4233   [(const_int 0)]
4234 {
4235   ix86_optimize_mode_switching = 1;
4236   operands[2] = assign_386_stack_local (HImode, 1);
4237   operands[3] = assign_386_stack_local (HImode, 2);
4238   if (memory_operand (operands[0], VOIDmode))
4239     emit_insn (gen_fix_truncsi_memory (operands[0], operands[1],
4240                                        operands[2], operands[3]));
4241   else
4242     {
4243       operands[4] = assign_386_stack_local (SImode, 0);
4244       emit_insn (gen_fix_truncsi_nomemory (operands[0], operands[1],
4245                                            operands[2], operands[3],
4246                                            operands[4]));
4247     }
4248   DONE;
4249 }
4250   [(set_attr "type" "fistp")
4251    (set_attr "mode" "SI")])
4252
4253 (define_insn "fix_truncsi_nomemory"
4254   [(set (match_operand:SI 0 "nonimmediate_operand" "=m,?r")
4255         (fix:SI (match_operand 1 "register_operand" "f,f")))
4256    (use (match_operand:HI 2 "memory_operand" "m,m"))
4257    (use (match_operand:HI 3 "memory_operand" "m,m"))
4258    (clobber (match_operand:SI 4 "memory_operand" "=m,m"))]
4259   "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4260    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4261   "#"
4262   [(set_attr "type" "fistp")
4263    (set_attr "mode" "SI")])
4264
4265 (define_insn "fix_truncsi_memory"
4266   [(set (match_operand:SI 0 "memory_operand" "=m")
4267         (fix:SI (match_operand 1 "register_operand" "f")))
4268    (use (match_operand:HI 2 "memory_operand" "m"))
4269    (use (match_operand:HI 3 "memory_operand" "m"))]
4270   "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4271    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4272   "* return output_fix_trunc (insn, operands);"
4273   [(set_attr "type" "fistp")
4274    (set_attr "mode" "SI")])
4275
4276 ;; When SSE available, it is always faster to use it!
4277 (define_insn "fix_truncsfsi_sse"
4278   [(set (match_operand:SI 0 "register_operand" "=r,r")
4279         (fix:SI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))]
4280   "TARGET_SSE"
4281   "cvttss2si\t{%1, %0|%0, %1}"
4282   [(set_attr "type" "sseicvt")
4283    (set_attr "mode" "DF")
4284    (set_attr "athlon_decode" "double,vector")])
4285
4286 ;; Avoid vector decoded form of the instruction.
4287 (define_peephole2
4288   [(match_scratch:SF 2 "x")
4289    (set (match_operand:SI 0 "register_operand" "")
4290         (fix:SI (match_operand:SF 1 "memory_operand" "")))]
4291   "TARGET_K8 && !optimize_size"
4292   [(set (match_dup 2) (match_dup 1))
4293    (set (match_dup 0) (fix:SI (match_dup 2)))]
4294   "")
4295
4296 (define_insn "fix_truncdfsi_sse"
4297   [(set (match_operand:SI 0 "register_operand" "=r,r")
4298         (fix:SI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))]
4299   "TARGET_SSE2"
4300   "cvttsd2si\t{%1, %0|%0, %1}"
4301   [(set_attr "type" "sseicvt")
4302    (set_attr "mode" "DF")
4303    (set_attr "athlon_decode" "double,vector")])
4304
4305 ;; Avoid vector decoded form of the instruction.
4306 (define_peephole2
4307   [(match_scratch:DF 2 "Y")
4308    (set (match_operand:SI 0 "register_operand" "")
4309         (fix:SI (match_operand:DF 1 "memory_operand" "")))]
4310   "TARGET_K8 && !optimize_size"
4311   [(set (match_dup 2) (match_dup 1))
4312    (set (match_dup 0) (fix:SI (match_dup 2)))]
4313   "")
4314
4315 (define_split 
4316   [(set (match_operand:SI 0 "register_operand" "")
4317         (fix:SI (match_operand 1 "register_operand" "")))
4318    (use (match_operand:HI 2 "memory_operand" ""))
4319    (use (match_operand:HI 3 "memory_operand" ""))
4320    (clobber (match_operand:SI 4 "memory_operand" ""))]
4321   "reload_completed"
4322   [(parallel [(set (match_dup 4) (fix:SI (match_dup 1)))
4323               (use (match_dup 2))
4324               (use (match_dup 3))])
4325    (set (match_dup 0) (match_dup 4))]
4326   "")
4327
4328 (define_split 
4329   [(set (match_operand:SI 0 "memory_operand" "")
4330         (fix:SI (match_operand 1 "register_operand" "")))
4331    (use (match_operand:HI 2 "memory_operand" ""))
4332    (use (match_operand:HI 3 "memory_operand" ""))
4333    (clobber (match_operand:SI 4 "memory_operand" ""))]
4334   "reload_completed"
4335   [(parallel [(set (match_dup 0) (fix:SI (match_dup 1)))
4336               (use (match_dup 2))
4337               (use (match_dup 3))])]
4338   "")
4339
4340 ;; Signed conversion to HImode.
4341
4342 (define_expand "fix_truncxfhi2"
4343   [(set (match_operand:HI 0 "nonimmediate_operand" "")
4344         (fix:HI (match_operand:XF 1 "register_operand" "")))]
4345   "TARGET_80387"
4346   "")
4347
4348 (define_expand "fix_truncdfhi2"
4349   [(set (match_operand:HI 0 "nonimmediate_operand" "")
4350         (fix:HI (match_operand:DF 1 "register_operand" "")))]
4351   "TARGET_80387 && !TARGET_SSE2"
4352   "")
4353
4354 (define_expand "fix_truncsfhi2"
4355   [(set (match_operand:HI 0 "nonimmediate_operand" "")
4356         (fix:HI (match_operand:SF 1 "register_operand" "")))]
4357   "TARGET_80387 && !TARGET_SSE"
4358   "")
4359
4360 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4361 ;; of the machinery.
4362 (define_insn_and_split "*fix_trunchi_1"
4363   [(set (match_operand:HI 0 "nonimmediate_operand" "=m,?r")
4364         (fix:HI (match_operand 1 "register_operand" "f,f")))]
4365   "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4366    && !reload_completed && !reload_in_progress
4367    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4368   "#"
4369   ""
4370   [(const_int 0)]
4371 {
4372   ix86_optimize_mode_switching = 1;
4373   operands[2] = assign_386_stack_local (HImode, 1);
4374   operands[3] = assign_386_stack_local (HImode, 2);
4375   if (memory_operand (operands[0], VOIDmode))
4376     emit_insn (gen_fix_trunchi_memory (operands[0], operands[1],
4377                                        operands[2], operands[3]));
4378   else
4379     {
4380       operands[4] = assign_386_stack_local (HImode, 0);
4381       emit_insn (gen_fix_trunchi_nomemory (operands[0], operands[1],
4382                                            operands[2], operands[3],
4383                                            operands[4]));
4384     }
4385   DONE;
4386 }
4387   [(set_attr "type" "fistp")
4388    (set_attr "mode" "HI")])
4389
4390 (define_insn "fix_trunchi_nomemory"
4391   [(set (match_operand:HI 0 "nonimmediate_operand" "=m,?r")
4392         (fix:HI (match_operand 1 "register_operand" "f,f")))
4393    (use (match_operand:HI 2 "memory_operand" "m,m"))
4394    (use (match_operand:HI 3 "memory_operand" "m,m"))
4395    (clobber (match_operand:HI 4 "memory_operand" "=m,m"))]
4396   "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4397    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4398   "#"
4399   [(set_attr "type" "fistp")
4400    (set_attr "mode" "HI")])
4401
4402 (define_insn "fix_trunchi_memory"
4403   [(set (match_operand:HI 0 "memory_operand" "=m")
4404         (fix:HI (match_operand 1 "register_operand" "f")))
4405    (use (match_operand:HI 2 "memory_operand" "m"))
4406    (use (match_operand:HI 3 "memory_operand" "m"))]
4407   "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4408    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4409   "* return output_fix_trunc (insn, operands);"
4410   [(set_attr "type" "fistp")
4411    (set_attr "mode" "HI")])
4412
4413 (define_split 
4414   [(set (match_operand:HI 0 "memory_operand" "")
4415         (fix:HI (match_operand 1 "register_operand" "")))
4416    (use (match_operand:HI 2 "memory_operand" ""))
4417    (use (match_operand:HI 3 "memory_operand" ""))
4418    (clobber (match_operand:HI 4 "memory_operand" ""))]
4419   "reload_completed"
4420   [(parallel [(set (match_dup 0) (fix:HI (match_dup 1)))
4421               (use (match_dup 2))
4422               (use (match_dup 3))])]
4423   "")
4424
4425 (define_split 
4426   [(set (match_operand:HI 0 "register_operand" "")
4427         (fix:HI (match_operand 1 "register_operand" "")))
4428    (use (match_operand:HI 2 "memory_operand" ""))
4429    (use (match_operand:HI 3 "memory_operand" ""))
4430    (clobber (match_operand:HI 4 "memory_operand" ""))]
4431   "reload_completed"
4432   [(parallel [(set (match_dup 4) (fix:HI (match_dup 1)))
4433               (use (match_dup 2))
4434               (use (match_dup 3))
4435               (clobber (match_dup 4))])
4436    (set (match_dup 0) (match_dup 4))]
4437   "")
4438
4439 ;; %% Not used yet.
4440 (define_insn "x86_fnstcw_1"
4441   [(set (match_operand:HI 0 "memory_operand" "=m")
4442         (unspec:HI [(reg:HI 18)] UNSPEC_FSTCW))]
4443   "TARGET_80387"
4444   "fnstcw\t%0"
4445   [(set_attr "length" "2")
4446    (set_attr "mode" "HI")
4447    (set_attr "unit" "i387")
4448    (set_attr "ppro_uops" "few")])
4449
4450 (define_insn "x86_fldcw_1"
4451   [(set (reg:HI 18)
4452         (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
4453   "TARGET_80387"
4454   "fldcw\t%0"
4455   [(set_attr "length" "2")
4456    (set_attr "mode" "HI")
4457    (set_attr "unit" "i387")
4458    (set_attr "athlon_decode" "vector")
4459    (set_attr "ppro_uops" "few")])
4460 \f
4461 ;; Conversion between fixed point and floating point.
4462
4463 ;; Even though we only accept memory inputs, the backend _really_
4464 ;; wants to be able to do this between registers.
4465
4466 (define_expand "floathisf2"
4467   [(set (match_operand:SF 0 "register_operand" "")
4468         (float:SF (match_operand:HI 1 "nonimmediate_operand" "")))]
4469   "TARGET_SSE || TARGET_80387"
4470 {
4471   if (TARGET_SSE && TARGET_SSE_MATH)
4472     {
4473       emit_insn (gen_floatsisf2 (operands[0],
4474                                  convert_to_mode (SImode, operands[1], 0)));
4475       DONE;
4476     }
4477 })
4478
4479 (define_insn "*floathisf2_1"
4480   [(set (match_operand:SF 0 "register_operand" "=f,f")
4481         (float:SF (match_operand:HI 1 "nonimmediate_operand" "m,r")))]
4482   "TARGET_80387 && (!TARGET_SSE || !TARGET_SSE_MATH)"
4483   "@
4484    fild%z1\t%1
4485    #"
4486   [(set_attr "type" "fmov,multi")
4487    (set_attr "mode" "SF")
4488    (set_attr "fp_int_src" "true")])
4489
4490 (define_expand "floatsisf2"
4491   [(set (match_operand:SF 0 "register_operand" "")
4492         (float:SF (match_operand:SI 1 "nonimmediate_operand" "")))]
4493   "TARGET_SSE || TARGET_80387"
4494   "")
4495
4496 (define_insn "*floatsisf2_i387"
4497   [(set (match_operand:SF 0 "register_operand" "=f#x,?f#x,x#f,x#f")
4498         (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))]
4499   "TARGET_80387 && (!TARGET_SSE || TARGET_MIX_SSE_I387)"
4500   "@
4501    fild%z1\t%1
4502    #
4503    cvtsi2ss\t{%1, %0|%0, %1}
4504    cvtsi2ss\t{%1, %0|%0, %1}"
4505   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4506    (set_attr "mode" "SF")
4507    (set_attr "athlon_decode" "*,*,vector,double")
4508    (set_attr "fp_int_src" "true")])
4509
4510 (define_insn "*floatsisf2_sse"
4511   [(set (match_operand:SF 0 "register_operand" "=x,x")
4512         (float:SF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))]
4513   "TARGET_SSE"
4514   "cvtsi2ss\t{%1, %0|%0, %1}"
4515   [(set_attr "type" "sseicvt")
4516    (set_attr "mode" "SF")
4517    (set_attr "athlon_decode" "vector,double")
4518    (set_attr "fp_int_src" "true")])
4519
4520 ; Avoid possible reformatting penalty on the destination by first
4521 ; zeroing it out
4522 (define_split
4523   [(set (match_operand:SF 0 "register_operand" "")
4524         (float:SF (match_operand:SI 1 "nonimmediate_operand" "")))]
4525   "TARGET_80387 && reload_completed && TARGET_SSE_PARTIAL_REGS
4526    && SSE_REG_P (operands[0])"
4527   [(const_int 0)]
4528 {
4529   rtx dest;
4530   dest = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
4531   emit_insn (gen_sse_clrv4sf (dest, CONST0_RTX (V4SFmode)));
4532   emit_insn (gen_cvtsi2ss (dest, dest, operands[1]));
4533   DONE;
4534 })
4535
4536 (define_expand "floatdisf2"
4537   [(set (match_operand:SF 0 "register_operand" "")
4538         (float:SF (match_operand:DI 1 "nonimmediate_operand" "")))]
4539   "(TARGET_64BIT && TARGET_SSE) || TARGET_80387"
4540   "")
4541
4542 (define_insn "*floatdisf2_i387_only"
4543   [(set (match_operand:SF 0 "register_operand" "=f,?f")
4544         (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,r")))]
4545   "TARGET_80387 && (!TARGET_SSE || !TARGET_64BIT || TARGET_MIX_SSE_I387)"
4546   "@
4547    fild%z1\t%1
4548    #"
4549   [(set_attr "type" "fmov,multi")
4550    (set_attr "mode" "SF")
4551    (set_attr "fp_int_src" "true")])
4552
4553 (define_insn "*floatdisf2_i387"
4554   [(set (match_operand:SF 0 "register_operand" "=f#x,?f#x,x#f,x#f")
4555         (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))]
4556   "TARGET_64BIT && TARGET_80387 && (!TARGET_SSE || TARGET_MIX_SSE_I387)"
4557   "@
4558    fild%z1\t%1
4559    #
4560    cvtsi2ss{q}\t{%1, %0|%0, %1}
4561    cvtsi2ss{q}\t{%1, %0|%0, %1}"
4562   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4563    (set_attr "mode" "SF")
4564    (set_attr "athlon_decode" "*,*,vector,double")
4565    (set_attr "fp_int_src" "true")])
4566
4567 (define_insn "*floatdisf2_sse"
4568   [(set (match_operand:SF 0 "register_operand" "=x,x")
4569         (float:SF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))]
4570   "TARGET_64BIT && TARGET_SSE"
4571   "cvtsi2ss{q}\t{%1, %0|%0, %1}"
4572   [(set_attr "type" "sseicvt")
4573    (set_attr "mode" "SF")
4574    (set_attr "athlon_decode" "vector,double")
4575    (set_attr "fp_int_src" "true")])
4576
4577 ; Avoid possible reformatting penalty on the destination by first
4578 ; zeroing it out
4579 (define_split
4580   [(set (match_operand:SF 0 "register_operand" "")
4581         (float:SF (match_operand:DI 1 "nonimmediate_operand" "")))]
4582   "TARGET_80387 && reload_completed && TARGET_SSE_PARTIAL_REGS
4583    && SSE_REG_P (operands[0])"
4584   [(const_int 0)]
4585 {
4586   rtx dest;
4587   dest = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
4588   emit_insn (gen_sse_clrv4sf (dest, CONST0_RTX (V4SFmode)));
4589   emit_insn (gen_cvtsi2ssq (dest, dest, operands[1]));
4590   DONE;
4591 })
4592
4593 (define_expand "floathidf2"
4594   [(set (match_operand:DF 0 "register_operand" "")
4595         (float:DF (match_operand:HI 1 "nonimmediate_operand" "")))]
4596   "TARGET_SSE2 || TARGET_80387"
4597 {
4598   if (TARGET_SSE && TARGET_SSE_MATH)
4599     {
4600       emit_insn (gen_floatsidf2 (operands[0],
4601                                  convert_to_mode (SImode, operands[1], 0)));
4602       DONE;
4603     }
4604 })
4605
4606 (define_insn "*floathidf2_1"
4607   [(set (match_operand:DF 0 "register_operand" "=f,f")
4608         (float:DF (match_operand:HI 1 "nonimmediate_operand" "m,r")))]
4609   "TARGET_80387 && (!TARGET_SSE2 || !TARGET_SSE_MATH)"
4610   "@
4611    fild%z1\t%1
4612    #"
4613   [(set_attr "type" "fmov,multi")
4614    (set_attr "mode" "DF")
4615    (set_attr "fp_int_src" "true")])
4616
4617 (define_expand "floatsidf2"
4618   [(set (match_operand:DF 0 "register_operand" "")
4619         (float:DF (match_operand:SI 1 "nonimmediate_operand" "")))]
4620   "TARGET_80387 || TARGET_SSE2"
4621   "")
4622
4623 (define_insn "*floatsidf2_i387"
4624   [(set (match_operand:DF 0 "register_operand" "=f#Y,?f#Y,Y#f,Y#f")
4625         (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))]
4626   "TARGET_80387 && (!TARGET_SSE2 || TARGET_MIX_SSE_I387)"
4627   "@
4628    fild%z1\t%1
4629    #
4630    cvtsi2sd\t{%1, %0|%0, %1}
4631    cvtsi2sd\t{%1, %0|%0, %1}"
4632   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4633    (set_attr "mode" "DF")
4634    (set_attr "athlon_decode" "*,*,double,direct")
4635    (set_attr "fp_int_src" "true")])
4636
4637 (define_insn "*floatsidf2_sse"
4638   [(set (match_operand:DF 0 "register_operand" "=Y,Y")
4639         (float:DF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))]
4640   "TARGET_SSE2"
4641   "cvtsi2sd\t{%1, %0|%0, %1}"
4642   [(set_attr "type" "sseicvt")
4643    (set_attr "mode" "DF")
4644    (set_attr "athlon_decode" "double,direct")
4645    (set_attr "fp_int_src" "true")])
4646
4647 (define_expand "floatdidf2"
4648   [(set (match_operand:DF 0 "register_operand" "")
4649         (float:DF (match_operand:DI 1 "nonimmediate_operand" "")))]
4650   "(TARGET_64BIT && TARGET_SSE2) || TARGET_80387"
4651   "")
4652
4653 (define_insn "*floatdidf2_i387_only"
4654   [(set (match_operand:DF 0 "register_operand" "=f,?f")
4655         (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,r")))]
4656   "TARGET_80387 && (!TARGET_SSE2 || !TARGET_64BIT)"
4657   "@
4658    fild%z1\t%1
4659    #"
4660   [(set_attr "type" "fmov,multi")
4661    (set_attr "mode" "DF")
4662    (set_attr "fp_int_src" "true")])
4663
4664 (define_insn "*floatdidf2_i387"
4665   [(set (match_operand:DF 0 "register_operand" "=f#Y,?f#Y,Y#f,Y#f")
4666         (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))]
4667   "TARGET_64BIT && TARGET_80387 && (!TARGET_SSE2 || TARGET_MIX_SSE_I387)"
4668   "@
4669    fild%z1\t%1
4670    #
4671    cvtsi2sd{q}\t{%1, %0|%0, %1}
4672    cvtsi2sd{q}\t{%1, %0|%0, %1}"
4673   [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4674    (set_attr "mode" "DF")
4675    (set_attr "athlon_decode" "*,*,double,direct")
4676    (set_attr "fp_int_src" "true")])
4677
4678 (define_insn "*floatdidf2_sse"
4679   [(set (match_operand:DF 0 "register_operand" "=Y,Y")
4680         (float:DF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))]
4681   "TARGET_SSE2"
4682   "cvtsi2sd{q}\t{%1, %0|%0, %1}"
4683   [(set_attr "type" "sseicvt")
4684    (set_attr "mode" "DF")
4685    (set_attr "athlon_decode" "double,direct")
4686    (set_attr "fp_int_src" "true")])
4687
4688 (define_insn "floathixf2"
4689   [(set (match_operand:XF 0 "register_operand" "=f,f")
4690         (float:XF (match_operand:HI 1 "nonimmediate_operand" "m,r")))]
4691   "TARGET_80387"
4692   "@
4693    fild%z1\t%1
4694    #"
4695   [(set_attr "type" "fmov,multi")
4696    (set_attr "mode" "XF")
4697    (set_attr "fp_int_src" "true")])
4698
4699 (define_insn "floatsixf2"
4700   [(set (match_operand:XF 0 "register_operand" "=f,f")
4701         (float:XF (match_operand:SI 1 "nonimmediate_operand" "m,r")))]
4702   "TARGET_80387"
4703   "@
4704    fild%z1\t%1
4705    #"
4706   [(set_attr "type" "fmov,multi")
4707    (set_attr "mode" "XF")
4708    (set_attr "fp_int_src" "true")])
4709
4710 (define_insn "floatdixf2"
4711   [(set (match_operand:XF 0 "register_operand" "=f,f")
4712         (float:XF (match_operand:DI 1 "nonimmediate_operand" "m,r")))]
4713   "TARGET_80387"
4714   "@
4715    fild%z1\t%1
4716    #"
4717   [(set_attr "type" "fmov,multi")
4718    (set_attr "mode" "XF")
4719    (set_attr "fp_int_src" "true")])
4720
4721 ;; %%% Kill these when reload knows how to do it.
4722 (define_split
4723   [(set (match_operand 0 "fp_register_operand" "")
4724         (float (match_operand 1 "register_operand" "")))]
4725   "reload_completed && FLOAT_MODE_P (GET_MODE (operands[0]))"
4726   [(const_int 0)]
4727 {
4728   operands[2] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
4729   operands[2] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[2]);
4730   emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[2]));
4731   ix86_free_from_memory (GET_MODE (operands[1]));
4732   DONE;
4733 })
4734
4735 (define_expand "floatunssisf2"
4736   [(use (match_operand:SF 0 "register_operand" ""))
4737    (use (match_operand:SI 1 "register_operand" ""))]
4738   "TARGET_SSE && TARGET_SSE_MATH && !TARGET_64BIT"
4739   "x86_emit_floatuns (operands); DONE;")
4740
4741 (define_expand "floatunsdisf2"
4742   [(use (match_operand:SF 0 "register_operand" ""))
4743    (use (match_operand:DI 1 "register_operand" ""))]
4744   "TARGET_SSE && TARGET_SSE_MATH && TARGET_64BIT"
4745   "x86_emit_floatuns (operands); DONE;")
4746
4747 (define_expand "floatunsdidf2"
4748   [(use (match_operand:DF 0 "register_operand" ""))
4749    (use (match_operand:DI 1 "register_operand" ""))]
4750   "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_64BIT"
4751   "x86_emit_floatuns (operands); DONE;")
4752 \f
4753 ;; SSE extract/set expanders
4754
4755 (define_expand "vec_setv2df"
4756   [(match_operand:V2DF 0 "register_operand" "")
4757    (match_operand:DF 1 "register_operand" "")
4758    (match_operand 2 "const_int_operand" "")]
4759   "TARGET_SSE2"
4760 {
4761   switch (INTVAL (operands[2]))
4762     {
4763     case 0:
4764       emit_insn (gen_sse2_movsd (operands[0], operands[0],
4765                                  simplify_gen_subreg (V2DFmode, operands[1],
4766                                                       DFmode, 0)));
4767       break;
4768     case 1:
4769       {
4770         rtx op1 = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
4771
4772         emit_insn (gen_sse2_unpcklpd (operands[0], operands[0], op1));
4773       }
4774       break;
4775     default:
4776       abort ();
4777     }
4778   DONE;
4779 })
4780
4781 (define_expand "vec_extractv2df"
4782   [(match_operand:DF 0 "register_operand" "")
4783    (match_operand:V2DF 1 "register_operand" "")
4784    (match_operand 2 "const_int_operand" "")]
4785   "TARGET_SSE2"
4786 {
4787   switch (INTVAL (operands[2]))
4788     {
4789     case 0:
4790       emit_move_insn (operands[0], gen_lowpart (DFmode, operands[1]));
4791       break;
4792     case 1:
4793       {
4794         rtx dest = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
4795
4796         emit_insn (gen_sse2_unpckhpd (dest, operands[1], operands[1]));
4797       }
4798       break;
4799     default:
4800       abort ();
4801     }
4802   DONE;
4803 })
4804
4805 (define_expand "vec_initv2df"
4806   [(match_operand:V2DF 0 "register_operand" "")
4807    (match_operand 1 "" "")]
4808   "TARGET_SSE2"
4809 {
4810   ix86_expand_vector_init (operands[0], operands[1]);
4811   DONE;
4812 })
4813
4814 (define_expand "vec_setv4sf"
4815   [(match_operand:V4SF 0 "register_operand" "")
4816    (match_operand:SF 1 "register_operand" "")
4817    (match_operand 2 "const_int_operand" "")]
4818   "TARGET_SSE"
4819 {
4820   switch (INTVAL (operands[2]))
4821     {
4822     case 0:
4823       emit_insn (gen_sse_movss (operands[0], operands[0],
4824                                 simplify_gen_subreg (V4SFmode, operands[1],
4825                                                      SFmode, 0)));
4826       break;
4827     case 1:
4828       {
4829         rtx op1 = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
4830         rtx tmp = gen_reg_rtx (V4SFmode);
4831  
4832         emit_move_insn (tmp, operands[0]);
4833         emit_insn (gen_sse_unpcklps (operands[0], operands[0], operands[0]));
4834         emit_insn (gen_sse_movss (operands[0], operands[0], op1));
4835         emit_insn (gen_sse_shufps (operands[0], operands[0], tmp,
4836                                    GEN_INT (1 + (0<<2) + (2<<4) + (3<<6))));
4837       }
4838     case 2:
4839       {
4840         rtx op1 = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
4841         rtx tmp = gen_reg_rtx (V4SFmode);
4842
4843         emit_move_insn (tmp, operands[0]);
4844         emit_insn (gen_sse_movss (tmp, tmp, op1));
4845         emit_insn (gen_sse_shufps (operands[0], operands[0], tmp,
4846                                    GEN_INT (0 + (1<<2) + (0<<4) + (3<<6))));
4847       }
4848       break;
4849     case 3:
4850       {
4851         rtx op1 = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
4852         rtx tmp = gen_reg_rtx (V4SFmode);
4853
4854         emit_move_insn (tmp, operands[0]);
4855         emit_insn (gen_sse_movss (tmp, tmp, op1));
4856         emit_insn (gen_sse_shufps (operands[0], operands[0], tmp,
4857                                    GEN_INT (0 + (1<<2) + (2<<4) + (0<<6))));
4858       }
4859       break;
4860     default:
4861       abort ();
4862     }
4863   DONE;
4864 })
4865
4866 (define_expand "vec_extractv4sf"
4867   [(match_operand:SF 0 "register_operand" "")
4868    (match_operand:V4SF 1 "register_operand" "")
4869    (match_operand 2 "const_int_operand" "")]
4870   "TARGET_SSE"
4871 {
4872   switch (INTVAL (operands[2]))
4873     {
4874     case 0:
4875       emit_move_insn (operands[0], gen_lowpart (SFmode, operands[1]));
4876       break;
4877     case 1:
4878       {
4879         rtx op0 = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
4880         rtx tmp = gen_reg_rtx (V4SFmode);
4881  
4882         emit_move_insn (tmp, operands[1]);
4883         emit_insn (gen_sse_shufps (op0, tmp, tmp,
4884                                    GEN_INT (1)));
4885       }
4886     case 2:
4887       {
4888         rtx op0 = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
4889         rtx tmp = gen_reg_rtx (V4SFmode);
4890  
4891         emit_move_insn (tmp, operands[1]);
4892         emit_insn (gen_sse_unpckhps (op0, tmp, tmp));
4893       }
4894     case 3:
4895       {
4896         rtx op0 = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
4897         rtx tmp = gen_reg_rtx (V4SFmode);
4898  
4899         emit_move_insn (tmp, operands[1]);
4900         emit_insn (gen_sse_shufps (op0, tmp, tmp,
4901                                    GEN_INT (3)));
4902       }
4903     default:
4904       abort ();
4905     }
4906   DONE;
4907 })
4908
4909 (define_expand "vec_initv4sf"
4910   [(match_operand:V4SF 0 "register_operand" "")
4911    (match_operand 1 "" "")]
4912   "TARGET_SSE"
4913 {
4914   ix86_expand_vector_init (operands[0], operands[1]);
4915   DONE;
4916 })
4917 \f
4918 ;; Add instructions
4919
4920 ;; %%% splits for addsidi3
4921 ;  [(set (match_operand:DI 0 "nonimmediate_operand" "")
4922 ;       (plus:DI (match_operand:DI 1 "general_operand" "")
4923 ;                (zero_extend:DI (match_operand:SI 2 "general_operand" ""))))]
4924
4925 (define_expand "adddi3"
4926   [(set (match_operand:DI 0 "nonimmediate_operand" "")
4927         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4928                  (match_operand:DI 2 "x86_64_general_operand" "")))
4929    (clobber (reg:CC 17))]
4930   ""
4931   "ix86_expand_binary_operator (PLUS, DImode, operands); DONE;")
4932
4933 (define_insn "*adddi3_1"
4934   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
4935         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
4936                  (match_operand:DI 2 "general_operand" "roiF,riF")))
4937    (clobber (reg:CC 17))]
4938   "!TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4939   "#")
4940
4941 (define_split
4942   [(set (match_operand:DI 0 "nonimmediate_operand" "")
4943         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4944                  (match_operand:DI 2 "general_operand" "")))
4945    (clobber (reg:CC 17))]
4946   "!TARGET_64BIT && reload_completed"
4947   [(parallel [(set (reg:CC 17) (unspec:CC [(match_dup 1) (match_dup 2)]
4948                                           UNSPEC_ADD_CARRY))
4949               (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))])
4950    (parallel [(set (match_dup 3)
4951                    (plus:SI (plus:SI (ltu:SI (reg:CC 17) (const_int 0))
4952                                      (match_dup 4))
4953                             (match_dup 5)))
4954               (clobber (reg:CC 17))])]
4955   "split_di (operands+0, 1, operands+0, operands+3);
4956    split_di (operands+1, 1, operands+1, operands+4);
4957    split_di (operands+2, 1, operands+2, operands+5);")
4958
4959 (define_insn "adddi3_carry_rex64"
4960   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
4961           (plus:DI (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
4962                             (match_operand:DI 1 "nonimmediate_operand" "%0,0"))
4963                    (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
4964    (clobber (reg:CC 17))]
4965   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4966   "adc{q}\t{%2, %0|%0, %2}"
4967   [(set_attr "type" "alu")
4968    (set_attr "pent_pair" "pu")
4969    (set_attr "mode" "DI")
4970    (set_attr "ppro_uops" "few")])
4971
4972 (define_insn "*adddi3_cc_rex64"
4973   [(set (reg:CC 17)
4974         (unspec:CC [(match_operand:DI 1 "nonimmediate_operand" "%0,0")
4975                     (match_operand:DI 2 "x86_64_general_operand" "re,rm")]
4976                    UNSPEC_ADD_CARRY))
4977    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
4978         (plus:DI (match_dup 1) (match_dup 2)))]
4979   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4980   "add{q}\t{%2, %0|%0, %2}"
4981   [(set_attr "type" "alu")
4982    (set_attr "mode" "DI")])
4983
4984 (define_insn "addqi3_carry"
4985   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
4986           (plus:QI (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
4987                             (match_operand:QI 1 "nonimmediate_operand" "%0,0"))
4988                    (match_operand:QI 2 "general_operand" "qi,qm")))
4989    (clobber (reg:CC 17))]
4990   "ix86_binary_operator_ok (PLUS, QImode, operands)"
4991   "adc{b}\t{%2, %0|%0, %2}"
4992   [(set_attr "type" "alu")
4993    (set_attr "pent_pair" "pu")
4994    (set_attr "mode" "QI")
4995    (set_attr "ppro_uops" "few")])
4996
4997 (define_insn "addhi3_carry"
4998   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
4999           (plus:HI (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
5000                             (match_operand:HI 1 "nonimmediate_operand" "%0,0"))
5001                    (match_operand:HI 2 "general_operand" "ri,rm")))
5002    (clobber (reg:CC 17))]
5003   "ix86_binary_operator_ok (PLUS, HImode, operands)"
5004   "adc{w}\t{%2, %0|%0, %2}"
5005   [(set_attr "type" "alu")
5006    (set_attr "pent_pair" "pu")
5007    (set_attr "mode" "HI")
5008    (set_attr "ppro_uops" "few")])
5009
5010 (define_insn "addsi3_carry"
5011   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
5012           (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
5013                             (match_operand:SI 1 "nonimmediate_operand" "%0,0"))
5014                    (match_operand:SI 2 "general_operand" "ri,rm")))
5015    (clobber (reg:CC 17))]
5016   "ix86_binary_operator_ok (PLUS, SImode, operands)"
5017   "adc{l}\t{%2, %0|%0, %2}"
5018   [(set_attr "type" "alu")
5019    (set_attr "pent_pair" "pu")
5020    (set_attr "mode" "SI")
5021    (set_attr "ppro_uops" "few")])
5022
5023 (define_insn "*addsi3_carry_zext"
5024   [(set (match_operand:DI 0 "register_operand" "=r")
5025           (zero_extend:DI 
5026             (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
5027                               (match_operand:SI 1 "nonimmediate_operand" "%0"))
5028                      (match_operand:SI 2 "general_operand" "rim"))))
5029    (clobber (reg:CC 17))]
5030   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5031   "adc{l}\t{%2, %k0|%k0, %2}"
5032   [(set_attr "type" "alu")
5033    (set_attr "pent_pair" "pu")
5034    (set_attr "mode" "SI")
5035    (set_attr "ppro_uops" "few")])
5036
5037 (define_insn "*addsi3_cc"
5038   [(set (reg:CC 17)
5039         (unspec:CC [(match_operand:SI 1 "nonimmediate_operand" "%0,0")
5040                     (match_operand:SI 2 "general_operand" "ri,rm")]
5041                    UNSPEC_ADD_CARRY))
5042    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
5043         (plus:SI (match_dup 1) (match_dup 2)))]
5044   "ix86_binary_operator_ok (PLUS, SImode, operands)"
5045   "add{l}\t{%2, %0|%0, %2}"
5046   [(set_attr "type" "alu")
5047    (set_attr "mode" "SI")])
5048
5049 (define_insn "addqi3_cc"
5050   [(set (reg:CC 17)
5051         (unspec:CC [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
5052                     (match_operand:QI 2 "general_operand" "qi,qm")]
5053                    UNSPEC_ADD_CARRY))
5054    (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
5055         (plus:QI (match_dup 1) (match_dup 2)))]
5056   "ix86_binary_operator_ok (PLUS, QImode, operands)"
5057   "add{b}\t{%2, %0|%0, %2}"
5058   [(set_attr "type" "alu")
5059    (set_attr "mode" "QI")])
5060
5061 (define_expand "addsi3"
5062   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
5063                    (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
5064                             (match_operand:SI 2 "general_operand" "")))
5065               (clobber (reg:CC 17))])]
5066   ""
5067   "ix86_expand_binary_operator (PLUS, SImode, operands); DONE;")
5068
5069 (define_insn "*lea_1"
5070   [(set (match_operand:SI 0 "register_operand" "=r")
5071         (match_operand:SI 1 "no_seg_address_operand" "p"))]
5072   "!TARGET_64BIT"
5073   "lea{l}\t{%a1, %0|%0, %a1}"
5074   [(set_attr "type" "lea")
5075    (set_attr "mode" "SI")])
5076
5077 (define_insn "*lea_1_rex64"
5078   [(set (match_operand:SI 0 "register_operand" "=r")
5079         (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0))]
5080   "TARGET_64BIT"
5081   "lea{l}\t{%a1, %0|%0, %a1}"
5082   [(set_attr "type" "lea")
5083    (set_attr "mode" "SI")])
5084
5085 (define_insn "*lea_1_zext"
5086   [(set (match_operand:DI 0 "register_operand" "=r")
5087         (zero_extend:DI
5088          (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0)))]
5089   "TARGET_64BIT"
5090   "lea{l}\t{%a1, %k0|%k0, %a1}"
5091   [(set_attr "type" "lea")
5092    (set_attr "mode" "SI")])
5093
5094 (define_insn "*lea_2_rex64"
5095   [(set (match_operand:DI 0 "register_operand" "=r")
5096         (match_operand:DI 1 "no_seg_address_operand" "p"))]
5097   "TARGET_64BIT"
5098   "lea{q}\t{%a1, %0|%0, %a1}"
5099   [(set_attr "type" "lea")
5100    (set_attr "mode" "DI")])
5101
5102 ;; The lea patterns for non-Pmodes needs to be matched by several
5103 ;; insns converted to real lea by splitters.
5104
5105 (define_insn_and_split "*lea_general_1"
5106   [(set (match_operand 0 "register_operand" "=r")
5107         (plus (plus (match_operand 1 "index_register_operand" "r")
5108                     (match_operand 2 "register_operand" "r"))
5109               (match_operand 3 "immediate_operand" "i")))]
5110   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5111     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5112    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5113    && GET_MODE (operands[0]) == GET_MODE (operands[1])
5114    && GET_MODE (operands[0]) == GET_MODE (operands[2])
5115    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
5116        || GET_MODE (operands[3]) == VOIDmode)"
5117   "#"
5118   "&& reload_completed"
5119   [(const_int 0)]
5120 {
5121   rtx pat;
5122   operands[0] = gen_lowpart (SImode, operands[0]);
5123   operands[1] = gen_lowpart (Pmode, operands[1]);
5124   operands[2] = gen_lowpart (Pmode, operands[2]);
5125   operands[3] = gen_lowpart (Pmode, operands[3]);
5126   pat = gen_rtx_PLUS (Pmode, gen_rtx_PLUS (Pmode, operands[1], operands[2]),
5127                       operands[3]);
5128   if (Pmode != SImode)
5129     pat = gen_rtx_SUBREG (SImode, pat, 0);
5130   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5131   DONE;
5132 }
5133   [(set_attr "type" "lea")
5134    (set_attr "mode" "SI")])
5135
5136 (define_insn_and_split "*lea_general_1_zext"
5137   [(set (match_operand:DI 0 "register_operand" "=r")
5138         (zero_extend:DI
5139           (plus:SI (plus:SI (match_operand:SI 1 "index_register_operand" "r")
5140                             (match_operand:SI 2 "register_operand" "r"))
5141                    (match_operand:SI 3 "immediate_operand" "i"))))]
5142   "TARGET_64BIT"
5143   "#"
5144   "&& reload_completed"
5145   [(set (match_dup 0)
5146         (zero_extend:DI (subreg:SI (plus:DI (plus:DI (match_dup 1)
5147                                                      (match_dup 2))
5148                                             (match_dup 3)) 0)))]
5149 {
5150   operands[1] = gen_lowpart (Pmode, operands[1]);
5151   operands[2] = gen_lowpart (Pmode, operands[2]);
5152   operands[3] = gen_lowpart (Pmode, operands[3]);
5153 }
5154   [(set_attr "type" "lea")
5155    (set_attr "mode" "SI")])
5156
5157 (define_insn_and_split "*lea_general_2"
5158   [(set (match_operand 0 "register_operand" "=r")
5159         (plus (mult (match_operand 1 "index_register_operand" "r")
5160                     (match_operand 2 "const248_operand" "i"))
5161               (match_operand 3 "nonmemory_operand" "ri")))]
5162   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5163     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5164    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5165    && GET_MODE (operands[0]) == GET_MODE (operands[1])
5166    && (GET_MODE (operands[0]) == GET_MODE (operands[3])
5167        || GET_MODE (operands[3]) == VOIDmode)"
5168   "#"
5169   "&& reload_completed"
5170   [(const_int 0)]
5171 {
5172   rtx pat;
5173   operands[0] = gen_lowpart (SImode, operands[0]);
5174   operands[1] = gen_lowpart (Pmode, operands[1]);
5175   operands[3] = gen_lowpart (Pmode, operands[3]);
5176   pat = gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], operands[2]),
5177                       operands[3]);
5178   if (Pmode != SImode)
5179     pat = gen_rtx_SUBREG (SImode, pat, 0);
5180   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5181   DONE;
5182 }
5183   [(set_attr "type" "lea")
5184    (set_attr "mode" "SI")])
5185
5186 (define_insn_and_split "*lea_general_2_zext"
5187   [(set (match_operand:DI 0 "register_operand" "=r")
5188         (zero_extend:DI
5189           (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "r")
5190                             (match_operand:SI 2 "const248_operand" "n"))
5191                    (match_operand:SI 3 "nonmemory_operand" "ri"))))]
5192   "TARGET_64BIT"
5193   "#"
5194   "&& reload_completed"
5195   [(set (match_dup 0)
5196         (zero_extend:DI (subreg:SI (plus:DI (mult:DI (match_dup 1)
5197                                                      (match_dup 2))
5198                                             (match_dup 3)) 0)))]
5199 {
5200   operands[1] = gen_lowpart (Pmode, operands[1]);
5201   operands[3] = gen_lowpart (Pmode, operands[3]);
5202 }
5203   [(set_attr "type" "lea")
5204    (set_attr "mode" "SI")])
5205
5206 (define_insn_and_split "*lea_general_3"
5207   [(set (match_operand 0 "register_operand" "=r")
5208         (plus (plus (mult (match_operand 1 "index_register_operand" "r")
5209                           (match_operand 2 "const248_operand" "i"))
5210                     (match_operand 3 "register_operand" "r"))
5211               (match_operand 4 "immediate_operand" "i")))]
5212   "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5213     || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5214    && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5215    && GET_MODE (operands[0]) == GET_MODE (operands[1])
5216    && GET_MODE (operands[0]) == GET_MODE (operands[3])"
5217   "#"
5218   "&& reload_completed"
5219   [(const_int 0)]
5220 {
5221   rtx pat;
5222   operands[0] = gen_lowpart (SImode, operands[0]);
5223   operands[1] = gen_lowpart (Pmode, operands[1]);
5224   operands[3] = gen_lowpart (Pmode, operands[3]);
5225   operands[4] = gen_lowpart (Pmode, operands[4]);
5226   pat = gen_rtx_PLUS (Pmode,
5227                       gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1],
5228                                                          operands[2]),
5229                                     operands[3]),
5230                       operands[4]);
5231   if (Pmode != SImode)
5232     pat = gen_rtx_SUBREG (SImode, pat, 0);
5233   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5234   DONE;
5235 }
5236   [(set_attr "type" "lea")
5237    (set_attr "mode" "SI")])
5238
5239 (define_insn_and_split "*lea_general_3_zext"
5240   [(set (match_operand:DI 0 "register_operand" "=r")
5241         (zero_extend:DI
5242           (plus:SI (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "r")
5243                                      (match_operand:SI 2 "const248_operand" "n"))
5244                             (match_operand:SI 3 "register_operand" "r"))
5245                    (match_operand:SI 4 "immediate_operand" "i"))))]
5246   "TARGET_64BIT"
5247   "#"
5248   "&& reload_completed"
5249   [(set (match_dup 0)
5250         (zero_extend:DI (subreg:SI (plus:DI (plus:DI (mult:DI (match_dup 1)
5251                                                               (match_dup 2))
5252                                                      (match_dup 3))
5253                                             (match_dup 4)) 0)))]
5254 {
5255   operands[1] = gen_lowpart (Pmode, operands[1]);
5256   operands[3] = gen_lowpart (Pmode, operands[3]);
5257   operands[4] = gen_lowpart (Pmode, operands[4]);
5258 }
5259   [(set_attr "type" "lea")
5260    (set_attr "mode" "SI")])
5261
5262 (define_insn "*adddi_1_rex64"
5263   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r")
5264         (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,r")
5265                  (match_operand:DI 2 "x86_64_general_operand" "rme,re,re")))
5266    (clobber (reg:CC 17))]
5267   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5268 {
5269   switch (get_attr_type (insn))
5270     {
5271     case TYPE_LEA:
5272       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5273       return "lea{q}\t{%a2, %0|%0, %a2}";
5274
5275     case TYPE_INCDEC:
5276       if (! rtx_equal_p (operands[0], operands[1]))
5277         abort ();
5278       if (operands[2] == const1_rtx)
5279         return "inc{q}\t%0";
5280       else if (operands[2] == constm1_rtx)
5281         return "dec{q}\t%0";
5282       else
5283         abort ();
5284
5285     default:
5286       if (! rtx_equal_p (operands[0], operands[1]))
5287         abort ();
5288
5289       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5290          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5291       if (GET_CODE (operands[2]) == CONST_INT
5292           /* Avoid overflows.  */
5293           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5294           && (INTVAL (operands[2]) == 128
5295               || (INTVAL (operands[2]) < 0
5296                   && INTVAL (operands[2]) != -128)))
5297         {
5298           operands[2] = GEN_INT (-INTVAL (operands[2]));
5299           return "sub{q}\t{%2, %0|%0, %2}";
5300         }
5301       return "add{q}\t{%2, %0|%0, %2}";
5302     }
5303 }
5304   [(set (attr "type")
5305      (cond [(eq_attr "alternative" "2")
5306               (const_string "lea")
5307             ; Current assemblers are broken and do not allow @GOTOFF in
5308             ; ought but a memory context.
5309             (match_operand:DI 2 "pic_symbolic_operand" "")
5310               (const_string "lea")
5311             (match_operand:DI 2 "incdec_operand" "")
5312               (const_string "incdec")
5313            ]
5314            (const_string "alu")))
5315    (set_attr "mode" "DI")])
5316
5317 ;; Convert lea to the lea pattern to avoid flags dependency.
5318 (define_split
5319   [(set (match_operand:DI 0 "register_operand" "")
5320         (plus:DI (match_operand:DI 1 "register_operand" "")
5321                  (match_operand:DI 2 "x86_64_nonmemory_operand" "")))
5322    (clobber (reg:CC 17))]
5323   "TARGET_64BIT && reload_completed
5324    && true_regnum (operands[0]) != true_regnum (operands[1])"
5325   [(set (match_dup 0)
5326         (plus:DI (match_dup 1)
5327                  (match_dup 2)))]
5328   "")
5329
5330 (define_insn "*adddi_2_rex64"
5331   [(set (reg 17)
5332         (compare
5333           (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5334                    (match_operand:DI 2 "x86_64_general_operand" "rme,re"))
5335           (const_int 0)))                       
5336    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
5337         (plus:DI (match_dup 1) (match_dup 2)))]
5338   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5339    && ix86_binary_operator_ok (PLUS, DImode, operands)
5340    /* Current assemblers are broken and do not allow @GOTOFF in
5341       ought but a memory context.  */
5342    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5343 {
5344   switch (get_attr_type (insn))
5345     {
5346     case TYPE_INCDEC:
5347       if (! rtx_equal_p (operands[0], operands[1]))
5348         abort ();
5349       if (operands[2] == const1_rtx)
5350         return "inc{q}\t%0";
5351       else if (operands[2] == constm1_rtx)
5352         return "dec{q}\t%0";
5353       else
5354         abort ();
5355
5356     default:
5357       if (! rtx_equal_p (operands[0], operands[1]))
5358         abort ();
5359       /* ???? We ought to handle there the 32bit case too
5360          - do we need new constraint?  */
5361       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5362          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5363       if (GET_CODE (operands[2]) == CONST_INT
5364           /* Avoid overflows.  */
5365           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5366           && (INTVAL (operands[2]) == 128
5367               || (INTVAL (operands[2]) < 0
5368                   && INTVAL (operands[2]) != -128)))
5369         {
5370           operands[2] = GEN_INT (-INTVAL (operands[2]));
5371           return "sub{q}\t{%2, %0|%0, %2}";
5372         }
5373       return "add{q}\t{%2, %0|%0, %2}";
5374     }
5375 }
5376   [(set (attr "type")
5377      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5378         (const_string "incdec")
5379         (const_string "alu")))
5380    (set_attr "mode" "DI")])
5381
5382 (define_insn "*adddi_3_rex64"
5383   [(set (reg 17)
5384         (compare (neg:DI (match_operand:DI 2 "x86_64_general_operand" "rme"))
5385                  (match_operand:DI 1 "x86_64_general_operand" "%0")))
5386    (clobber (match_scratch:DI 0 "=r"))]
5387   "TARGET_64BIT
5388    && ix86_match_ccmode (insn, CCZmode)
5389    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5390    /* Current assemblers are broken and do not allow @GOTOFF in
5391       ought but a memory context.  */
5392    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5393 {
5394   switch (get_attr_type (insn))
5395     {
5396     case TYPE_INCDEC:
5397       if (! rtx_equal_p (operands[0], operands[1]))
5398         abort ();
5399       if (operands[2] == const1_rtx)
5400         return "inc{q}\t%0";
5401       else if (operands[2] == constm1_rtx)
5402         return "dec{q}\t%0";
5403       else
5404         abort ();
5405
5406     default:
5407       if (! rtx_equal_p (operands[0], operands[1]))
5408         abort ();
5409       /* ???? We ought to handle there the 32bit case too
5410          - do we need new constraint?  */
5411       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5412          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5413       if (GET_CODE (operands[2]) == CONST_INT
5414           /* Avoid overflows.  */
5415           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5416           && (INTVAL (operands[2]) == 128
5417               || (INTVAL (operands[2]) < 0
5418                   && INTVAL (operands[2]) != -128)))
5419         {
5420           operands[2] = GEN_INT (-INTVAL (operands[2]));
5421           return "sub{q}\t{%2, %0|%0, %2}";
5422         }
5423       return "add{q}\t{%2, %0|%0, %2}";
5424     }
5425 }
5426   [(set (attr "type")
5427      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5428         (const_string "incdec")
5429         (const_string "alu")))
5430    (set_attr "mode" "DI")])
5431
5432 ; For comparisons against 1, -1 and 128, we may generate better code
5433 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
5434 ; is matched then.  We can't accept general immediate, because for
5435 ; case of overflows,  the result is messed up.
5436 ; This pattern also don't hold of 0x8000000000000000, since the value overflows
5437 ; when negated.
5438 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5439 ; only for comparisons not depending on it.
5440 (define_insn "*adddi_4_rex64"
5441   [(set (reg 17)
5442         (compare (match_operand:DI 1 "nonimmediate_operand" "0")
5443                  (match_operand:DI 2 "x86_64_immediate_operand" "e")))
5444    (clobber (match_scratch:DI 0 "=rm"))]
5445   "TARGET_64BIT
5446    &&  ix86_match_ccmode (insn, CCGCmode)"
5447 {
5448   switch (get_attr_type (insn))
5449     {
5450     case TYPE_INCDEC:
5451       if (operands[2] == constm1_rtx)
5452         return "inc{q}\t%0";
5453       else if (operands[2] == const1_rtx)
5454         return "dec{q}\t%0";
5455       else
5456         abort();
5457
5458     default:
5459       if (! rtx_equal_p (operands[0], operands[1]))
5460         abort ();
5461       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5462          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5463       if ((INTVAL (operands[2]) == -128
5464            || (INTVAL (operands[2]) > 0
5465                && INTVAL (operands[2]) != 128))
5466           /* Avoid overflows.  */
5467           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))))
5468         return "sub{q}\t{%2, %0|%0, %2}";
5469       operands[2] = GEN_INT (-INTVAL (operands[2]));
5470       return "add{q}\t{%2, %0|%0, %2}";
5471     }
5472 }
5473   [(set (attr "type")
5474      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5475         (const_string "incdec")
5476         (const_string "alu")))
5477    (set_attr "mode" "DI")])
5478
5479 (define_insn "*adddi_5_rex64"
5480   [(set (reg 17)
5481         (compare
5482           (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5483                    (match_operand:DI 2 "x86_64_general_operand" "rme"))
5484           (const_int 0)))                       
5485    (clobber (match_scratch:DI 0 "=r"))]
5486   "TARGET_64BIT
5487    && ix86_match_ccmode (insn, CCGOCmode)
5488    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5489    /* Current assemblers are broken and do not allow @GOTOFF in
5490       ought but a memory context.  */
5491    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5492 {
5493   switch (get_attr_type (insn))
5494     {
5495     case TYPE_INCDEC:
5496       if (! rtx_equal_p (operands[0], operands[1]))
5497         abort ();
5498       if (operands[2] == const1_rtx)
5499         return "inc{q}\t%0";
5500       else if (operands[2] == constm1_rtx)
5501         return "dec{q}\t%0";
5502       else
5503         abort();
5504
5505     default:
5506       if (! rtx_equal_p (operands[0], operands[1]))
5507         abort ();
5508       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5509          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5510       if (GET_CODE (operands[2]) == CONST_INT
5511           /* Avoid overflows.  */
5512           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5513           && (INTVAL (operands[2]) == 128
5514               || (INTVAL (operands[2]) < 0
5515                   && INTVAL (operands[2]) != -128)))
5516         {
5517           operands[2] = GEN_INT (-INTVAL (operands[2]));
5518           return "sub{q}\t{%2, %0|%0, %2}";
5519         }
5520       return "add{q}\t{%2, %0|%0, %2}";
5521     }
5522 }
5523   [(set (attr "type")
5524      (if_then_else (match_operand:DI 2 "incdec_operand" "")
5525         (const_string "incdec")
5526         (const_string "alu")))
5527    (set_attr "mode" "DI")])
5528
5529
5530 (define_insn "*addsi_1"
5531   [(set (match_operand:SI 0 "nonimmediate_operand" "=r,rm,r")
5532         (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,r")
5533                  (match_operand:SI 2 "general_operand" "rmni,rni,rni")))
5534    (clobber (reg:CC 17))]
5535   "ix86_binary_operator_ok (PLUS, SImode, operands)"
5536 {
5537   switch (get_attr_type (insn))
5538     {
5539     case TYPE_LEA:
5540       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5541       return "lea{l}\t{%a2, %0|%0, %a2}";
5542
5543     case TYPE_INCDEC:
5544       if (! rtx_equal_p (operands[0], operands[1]))
5545         abort ();
5546       if (operands[2] == const1_rtx)
5547         return "inc{l}\t%0";
5548       else if (operands[2] == constm1_rtx)
5549         return "dec{l}\t%0";
5550       else
5551         abort();
5552
5553     default:
5554       if (! rtx_equal_p (operands[0], operands[1]))
5555         abort ();
5556
5557       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5558          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5559       if (GET_CODE (operands[2]) == CONST_INT
5560           && (INTVAL (operands[2]) == 128
5561               || (INTVAL (operands[2]) < 0
5562                   && INTVAL (operands[2]) != -128)))
5563         {
5564           operands[2] = GEN_INT (-INTVAL (operands[2]));
5565           return "sub{l}\t{%2, %0|%0, %2}";
5566         }
5567       return "add{l}\t{%2, %0|%0, %2}";
5568     }
5569 }
5570   [(set (attr "type")
5571      (cond [(eq_attr "alternative" "2")
5572               (const_string "lea")
5573             ; Current assemblers are broken and do not allow @GOTOFF in
5574             ; ought but a memory context.
5575             (match_operand:SI 2 "pic_symbolic_operand" "")
5576               (const_string "lea")
5577             (match_operand:SI 2 "incdec_operand" "")
5578               (const_string "incdec")
5579            ]
5580            (const_string "alu")))
5581    (set_attr "mode" "SI")])
5582
5583 ;; Convert lea to the lea pattern to avoid flags dependency.
5584 (define_split
5585   [(set (match_operand 0 "register_operand" "")
5586         (plus (match_operand 1 "register_operand" "")
5587               (match_operand 2 "nonmemory_operand" "")))
5588    (clobber (reg:CC 17))]
5589   "reload_completed
5590    && true_regnum (operands[0]) != true_regnum (operands[1])"
5591   [(const_int 0)]
5592 {
5593   rtx pat;
5594   /* In -fPIC mode the constructs like (const (unspec [symbol_ref]))
5595      may confuse gen_lowpart.  */
5596   if (GET_MODE (operands[0]) != Pmode)
5597     {
5598       operands[1] = gen_lowpart (Pmode, operands[1]);
5599       operands[2] = gen_lowpart (Pmode, operands[2]);
5600     }
5601   operands[0] = gen_lowpart (SImode, operands[0]);
5602   pat = gen_rtx_PLUS (Pmode, operands[1], operands[2]);
5603   if (Pmode != SImode)
5604     pat = gen_rtx_SUBREG (SImode, pat, 0);
5605   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5606   DONE;
5607 })
5608
5609 ;; It may seem that nonimmediate operand is proper one for operand 1.
5610 ;; The addsi_1 pattern allows nonimmediate operand at that place and
5611 ;; we take care in ix86_binary_operator_ok to not allow two memory
5612 ;; operands so proper swapping will be done in reload.  This allow
5613 ;; patterns constructed from addsi_1 to match.
5614 (define_insn "addsi_1_zext"
5615   [(set (match_operand:DI 0 "register_operand" "=r,r")
5616         (zero_extend:DI
5617           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r")
5618                    (match_operand:SI 2 "general_operand" "rmni,rni"))))
5619    (clobber (reg:CC 17))]
5620   "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5621 {
5622   switch (get_attr_type (insn))
5623     {
5624     case TYPE_LEA:
5625       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5626       return "lea{l}\t{%a2, %k0|%k0, %a2}";
5627
5628     case TYPE_INCDEC:
5629       if (operands[2] == const1_rtx)
5630         return "inc{l}\t%k0";
5631       else if (operands[2] == constm1_rtx)
5632         return "dec{l}\t%k0";
5633       else
5634         abort();
5635
5636     default:
5637       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5638          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5639       if (GET_CODE (operands[2]) == CONST_INT
5640           && (INTVAL (operands[2]) == 128
5641               || (INTVAL (operands[2]) < 0
5642                   && INTVAL (operands[2]) != -128)))
5643         {
5644           operands[2] = GEN_INT (-INTVAL (operands[2]));
5645           return "sub{l}\t{%2, %k0|%k0, %2}";
5646         }
5647       return "add{l}\t{%2, %k0|%k0, %2}";
5648     }
5649 }
5650   [(set (attr "type")
5651      (cond [(eq_attr "alternative" "1")
5652               (const_string "lea")
5653             ; Current assemblers are broken and do not allow @GOTOFF in
5654             ; ought but a memory context.
5655             (match_operand:SI 2 "pic_symbolic_operand" "")
5656               (const_string "lea")
5657             (match_operand:SI 2 "incdec_operand" "")
5658               (const_string "incdec")
5659            ]
5660            (const_string "alu")))
5661    (set_attr "mode" "SI")])
5662
5663 ;; Convert lea to the lea pattern to avoid flags dependency.
5664 (define_split
5665   [(set (match_operand:DI 0 "register_operand" "")
5666         (zero_extend:DI
5667           (plus:SI (match_operand:SI 1 "register_operand" "")
5668                    (match_operand:SI 2 "nonmemory_operand" ""))))
5669    (clobber (reg:CC 17))]
5670   "TARGET_64BIT && reload_completed
5671    && true_regnum (operands[0]) != true_regnum (operands[1])"
5672   [(set (match_dup 0)
5673         (zero_extend:DI (subreg:SI (plus:DI (match_dup 1) (match_dup 2)) 0)))]
5674 {
5675   operands[1] = gen_lowpart (Pmode, operands[1]);
5676   operands[2] = gen_lowpart (Pmode, operands[2]);
5677 })
5678
5679 (define_insn "*addsi_2"
5680   [(set (reg 17)
5681         (compare
5682           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
5683                    (match_operand:SI 2 "general_operand" "rmni,rni"))
5684           (const_int 0)))                       
5685    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
5686         (plus:SI (match_dup 1) (match_dup 2)))]
5687   "ix86_match_ccmode (insn, CCGOCmode)
5688    && ix86_binary_operator_ok (PLUS, SImode, operands)
5689    /* Current assemblers are broken and do not allow @GOTOFF in
5690       ought but a memory context.  */
5691    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5692 {
5693   switch (get_attr_type (insn))
5694     {
5695     case TYPE_INCDEC:
5696       if (! rtx_equal_p (operands[0], operands[1]))
5697         abort ();
5698       if (operands[2] == const1_rtx)
5699         return "inc{l}\t%0";
5700       else if (operands[2] == constm1_rtx)
5701         return "dec{l}\t%0";
5702       else
5703         abort();
5704
5705     default:
5706       if (! rtx_equal_p (operands[0], operands[1]))
5707         abort ();
5708       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5709          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5710       if (GET_CODE (operands[2]) == CONST_INT
5711           && (INTVAL (operands[2]) == 128
5712               || (INTVAL (operands[2]) < 0
5713                   && INTVAL (operands[2]) != -128)))
5714         {
5715           operands[2] = GEN_INT (-INTVAL (operands[2]));
5716           return "sub{l}\t{%2, %0|%0, %2}";
5717         }
5718       return "add{l}\t{%2, %0|%0, %2}";
5719     }
5720 }
5721   [(set (attr "type")
5722      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5723         (const_string "incdec")
5724         (const_string "alu")))
5725    (set_attr "mode" "SI")])
5726
5727 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5728 (define_insn "*addsi_2_zext"
5729   [(set (reg 17)
5730         (compare
5731           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5732                    (match_operand:SI 2 "general_operand" "rmni"))
5733           (const_int 0)))                       
5734    (set (match_operand:DI 0 "register_operand" "=r")
5735         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5736   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5737    && ix86_binary_operator_ok (PLUS, SImode, operands)
5738    /* Current assemblers are broken and do not allow @GOTOFF in
5739       ought but a memory context.  */
5740    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5741 {
5742   switch (get_attr_type (insn))
5743     {
5744     case TYPE_INCDEC:
5745       if (operands[2] == const1_rtx)
5746         return "inc{l}\t%k0";
5747       else if (operands[2] == constm1_rtx)
5748         return "dec{l}\t%k0";
5749       else
5750         abort();
5751
5752     default:
5753       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5754          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5755       if (GET_CODE (operands[2]) == CONST_INT
5756           && (INTVAL (operands[2]) == 128
5757               || (INTVAL (operands[2]) < 0
5758                   && INTVAL (operands[2]) != -128)))
5759         {
5760           operands[2] = GEN_INT (-INTVAL (operands[2]));
5761           return "sub{l}\t{%2, %k0|%k0, %2}";
5762         }
5763       return "add{l}\t{%2, %k0|%k0, %2}";
5764     }
5765 }
5766   [(set (attr "type")
5767      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5768         (const_string "incdec")
5769         (const_string "alu")))
5770    (set_attr "mode" "SI")])
5771
5772 (define_insn "*addsi_3"
5773   [(set (reg 17)
5774         (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5775                  (match_operand:SI 1 "nonimmediate_operand" "%0")))
5776    (clobber (match_scratch:SI 0 "=r"))]
5777   "ix86_match_ccmode (insn, CCZmode)
5778    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5779    /* Current assemblers are broken and do not allow @GOTOFF in
5780       ought but a memory context.  */
5781    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5782 {
5783   switch (get_attr_type (insn))
5784     {
5785     case TYPE_INCDEC:
5786       if (! rtx_equal_p (operands[0], operands[1]))
5787         abort ();
5788       if (operands[2] == const1_rtx)
5789         return "inc{l}\t%0";
5790       else if (operands[2] == constm1_rtx)
5791         return "dec{l}\t%0";
5792       else
5793         abort();
5794
5795     default:
5796       if (! rtx_equal_p (operands[0], operands[1]))
5797         abort ();
5798       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5799          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5800       if (GET_CODE (operands[2]) == CONST_INT
5801           && (INTVAL (operands[2]) == 128
5802               || (INTVAL (operands[2]) < 0
5803                   && INTVAL (operands[2]) != -128)))
5804         {
5805           operands[2] = GEN_INT (-INTVAL (operands[2]));
5806           return "sub{l}\t{%2, %0|%0, %2}";
5807         }
5808       return "add{l}\t{%2, %0|%0, %2}";
5809     }
5810 }
5811   [(set (attr "type")
5812      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5813         (const_string "incdec")
5814         (const_string "alu")))
5815    (set_attr "mode" "SI")])
5816
5817 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5818 (define_insn "*addsi_3_zext"
5819   [(set (reg 17)
5820         (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5821                  (match_operand:SI 1 "nonimmediate_operand" "%0")))
5822    (set (match_operand:DI 0 "register_operand" "=r")
5823         (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5824   "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
5825    && ix86_binary_operator_ok (PLUS, SImode, operands)
5826    /* Current assemblers are broken and do not allow @GOTOFF in
5827       ought but a memory context.  */
5828    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5829 {
5830   switch (get_attr_type (insn))
5831     {
5832     case TYPE_INCDEC:
5833       if (operands[2] == const1_rtx)
5834         return "inc{l}\t%k0";
5835       else if (operands[2] == constm1_rtx)
5836         return "dec{l}\t%k0";
5837       else
5838         abort();
5839
5840     default:
5841       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5842          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5843       if (GET_CODE (operands[2]) == CONST_INT
5844           && (INTVAL (operands[2]) == 128
5845               || (INTVAL (operands[2]) < 0
5846                   && INTVAL (operands[2]) != -128)))
5847         {
5848           operands[2] = GEN_INT (-INTVAL (operands[2]));
5849           return "sub{l}\t{%2, %k0|%k0, %2}";
5850         }
5851       return "add{l}\t{%2, %k0|%k0, %2}";
5852     }
5853 }
5854   [(set (attr "type")
5855      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5856         (const_string "incdec")
5857         (const_string "alu")))
5858    (set_attr "mode" "SI")])
5859
5860 ; For comparisons against 1, -1 and 128, we may generate better code
5861 ; by converting cmp to add, inc or dec as done by peephole2.  This pattern
5862 ; is matched then.  We can't accept general immediate, because for
5863 ; case of overflows,  the result is messed up.
5864 ; This pattern also don't hold of 0x80000000, since the value overflows
5865 ; when negated.
5866 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5867 ; only for comparisons not depending on it.
5868 (define_insn "*addsi_4"
5869   [(set (reg 17)
5870         (compare (match_operand:SI 1 "nonimmediate_operand" "0")
5871                  (match_operand:SI 2 "const_int_operand" "n")))
5872    (clobber (match_scratch:SI 0 "=rm"))]
5873   "ix86_match_ccmode (insn, CCGCmode)
5874    && (INTVAL (operands[2]) & 0xffffffff) != 0x80000000"
5875 {
5876   switch (get_attr_type (insn))
5877     {
5878     case TYPE_INCDEC:
5879       if (operands[2] == constm1_rtx)
5880         return "inc{l}\t%0";
5881       else if (operands[2] == const1_rtx)
5882         return "dec{l}\t%0";
5883       else
5884         abort();
5885
5886     default:
5887       if (! rtx_equal_p (operands[0], operands[1]))
5888         abort ();
5889       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5890          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5891       if ((INTVAL (operands[2]) == -128
5892            || (INTVAL (operands[2]) > 0
5893                && INTVAL (operands[2]) != 128)))
5894         return "sub{l}\t{%2, %0|%0, %2}";
5895       operands[2] = GEN_INT (-INTVAL (operands[2]));
5896       return "add{l}\t{%2, %0|%0, %2}";
5897     }
5898 }
5899   [(set (attr "type")
5900      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5901         (const_string "incdec")
5902         (const_string "alu")))
5903    (set_attr "mode" "SI")])
5904
5905 (define_insn "*addsi_5"
5906   [(set (reg 17)
5907         (compare
5908           (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5909                    (match_operand:SI 2 "general_operand" "rmni"))
5910           (const_int 0)))                       
5911    (clobber (match_scratch:SI 0 "=r"))]
5912   "ix86_match_ccmode (insn, CCGOCmode)
5913    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5914    /* Current assemblers are broken and do not allow @GOTOFF in
5915       ought but a memory context.  */
5916    && ! pic_symbolic_operand (operands[2], VOIDmode)"
5917 {
5918   switch (get_attr_type (insn))
5919     {
5920     case TYPE_INCDEC:
5921       if (! rtx_equal_p (operands[0], operands[1]))
5922         abort ();
5923       if (operands[2] == const1_rtx)
5924         return "inc{l}\t%0";
5925       else if (operands[2] == constm1_rtx)
5926         return "dec{l}\t%0";
5927       else
5928         abort();
5929
5930     default:
5931       if (! rtx_equal_p (operands[0], operands[1]))
5932         abort ();
5933       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5934          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5935       if (GET_CODE (operands[2]) == CONST_INT
5936           && (INTVAL (operands[2]) == 128
5937               || (INTVAL (operands[2]) < 0
5938                   && INTVAL (operands[2]) != -128)))
5939         {
5940           operands[2] = GEN_INT (-INTVAL (operands[2]));
5941           return "sub{l}\t{%2, %0|%0, %2}";
5942         }
5943       return "add{l}\t{%2, %0|%0, %2}";
5944     }
5945 }
5946   [(set (attr "type")
5947      (if_then_else (match_operand:SI 2 "incdec_operand" "")
5948         (const_string "incdec")
5949         (const_string "alu")))
5950    (set_attr "mode" "SI")])
5951
5952 (define_expand "addhi3"
5953   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
5954                    (plus:HI (match_operand:HI 1 "nonimmediate_operand" "")
5955                             (match_operand:HI 2 "general_operand" "")))
5956               (clobber (reg:CC 17))])]
5957   "TARGET_HIMODE_MATH"
5958   "ix86_expand_binary_operator (PLUS, HImode, operands); DONE;")
5959
5960 ;; %%% After Dave's SUBREG_BYTE stuff goes in, re-enable incb %ah
5961 ;; type optimizations enabled by define-splits.  This is not important
5962 ;; for PII, and in fact harmful because of partial register stalls.
5963
5964 (define_insn "*addhi_1_lea"
5965   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
5966         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r")
5967                  (match_operand:HI 2 "general_operand" "ri,rm,rni")))
5968    (clobber (reg:CC 17))]
5969   "!TARGET_PARTIAL_REG_STALL
5970    && ix86_binary_operator_ok (PLUS, HImode, operands)"
5971 {
5972   switch (get_attr_type (insn))
5973     {
5974     case TYPE_LEA:
5975       return "#";
5976     case TYPE_INCDEC:
5977       if (operands[2] == const1_rtx)
5978         return "inc{w}\t%0";
5979       else if (operands[2] == constm1_rtx)
5980         return "dec{w}\t%0";
5981       abort();
5982
5983     default:
5984       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5985          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
5986       if (GET_CODE (operands[2]) == CONST_INT
5987           && (INTVAL (operands[2]) == 128
5988               || (INTVAL (operands[2]) < 0
5989                   && INTVAL (operands[2]) != -128)))
5990         {
5991           operands[2] = GEN_INT (-INTVAL (operands[2]));
5992           return "sub{w}\t{%2, %0|%0, %2}";
5993         }
5994       return "add{w}\t{%2, %0|%0, %2}";
5995     }
5996 }
5997   [(set (attr "type")
5998      (if_then_else (eq_attr "alternative" "2")
5999         (const_string "lea")
6000         (if_then_else (match_operand:HI 2 "incdec_operand" "")
6001            (const_string "incdec")
6002            (const_string "alu"))))
6003    (set_attr "mode" "HI,HI,SI")])
6004
6005 (define_insn "*addhi_1"
6006   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6007         (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
6008                  (match_operand:HI 2 "general_operand" "ri,rm")))
6009    (clobber (reg:CC 17))]
6010   "TARGET_PARTIAL_REG_STALL
6011    && ix86_binary_operator_ok (PLUS, HImode, operands)"
6012 {
6013   switch (get_attr_type (insn))
6014     {
6015     case TYPE_INCDEC:
6016       if (operands[2] == const1_rtx)
6017         return "inc{w}\t%0";
6018       else if (operands[2] == constm1_rtx)
6019         return "dec{w}\t%0";
6020       abort();
6021
6022     default:
6023       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6024          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6025       if (GET_CODE (operands[2]) == CONST_INT
6026           && (INTVAL (operands[2]) == 128
6027               || (INTVAL (operands[2]) < 0
6028                   && INTVAL (operands[2]) != -128)))
6029         {
6030           operands[2] = GEN_INT (-INTVAL (operands[2]));
6031           return "sub{w}\t{%2, %0|%0, %2}";
6032         }
6033       return "add{w}\t{%2, %0|%0, %2}";
6034     }
6035 }
6036   [(set (attr "type")
6037      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6038         (const_string "incdec")
6039         (const_string "alu")))
6040    (set_attr "mode" "HI")])
6041
6042 (define_insn "*addhi_2"
6043   [(set (reg 17)
6044         (compare
6045           (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
6046                    (match_operand:HI 2 "general_operand" "rmni,rni"))
6047           (const_int 0)))                       
6048    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
6049         (plus:HI (match_dup 1) (match_dup 2)))]
6050   "ix86_match_ccmode (insn, CCGOCmode)
6051    && ix86_binary_operator_ok (PLUS, HImode, operands)"
6052 {
6053   switch (get_attr_type (insn))
6054     {
6055     case TYPE_INCDEC:
6056       if (operands[2] == const1_rtx)
6057         return "inc{w}\t%0";
6058       else if (operands[2] == constm1_rtx)
6059         return "dec{w}\t%0";
6060       abort();
6061
6062     default:
6063       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6064          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6065       if (GET_CODE (operands[2]) == CONST_INT
6066           && (INTVAL (operands[2]) == 128
6067               || (INTVAL (operands[2]) < 0
6068                   && INTVAL (operands[2]) != -128)))
6069         {
6070           operands[2] = GEN_INT (-INTVAL (operands[2]));
6071           return "sub{w}\t{%2, %0|%0, %2}";
6072         }
6073       return "add{w}\t{%2, %0|%0, %2}";
6074     }
6075 }
6076   [(set (attr "type")
6077      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6078         (const_string "incdec")
6079         (const_string "alu")))
6080    (set_attr "mode" "HI")])
6081
6082 (define_insn "*addhi_3"
6083   [(set (reg 17)
6084         (compare (neg:HI (match_operand:HI 2 "general_operand" "rmni"))
6085                  (match_operand:HI 1 "nonimmediate_operand" "%0")))
6086    (clobber (match_scratch:HI 0 "=r"))]
6087   "ix86_match_ccmode (insn, CCZmode)
6088    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6089 {
6090   switch (get_attr_type (insn))
6091     {
6092     case TYPE_INCDEC:
6093       if (operands[2] == const1_rtx)
6094         return "inc{w}\t%0";
6095       else if (operands[2] == constm1_rtx)
6096         return "dec{w}\t%0";
6097       abort();
6098
6099     default:
6100       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6101          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6102       if (GET_CODE (operands[2]) == CONST_INT
6103           && (INTVAL (operands[2]) == 128
6104               || (INTVAL (operands[2]) < 0
6105                   && INTVAL (operands[2]) != -128)))
6106         {
6107           operands[2] = GEN_INT (-INTVAL (operands[2]));
6108           return "sub{w}\t{%2, %0|%0, %2}";
6109         }
6110       return "add{w}\t{%2, %0|%0, %2}";
6111     }
6112 }
6113   [(set (attr "type")
6114      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6115         (const_string "incdec")
6116         (const_string "alu")))
6117    (set_attr "mode" "HI")])
6118
6119 ; See comments above addsi_3_imm for details.
6120 (define_insn "*addhi_4"
6121   [(set (reg 17)
6122         (compare (match_operand:HI 1 "nonimmediate_operand" "0")
6123                  (match_operand:HI 2 "const_int_operand" "n")))
6124    (clobber (match_scratch:HI 0 "=rm"))]
6125   "ix86_match_ccmode (insn, CCGCmode)
6126    && (INTVAL (operands[2]) & 0xffff) != 0x8000"
6127 {
6128   switch (get_attr_type (insn))
6129     {
6130     case TYPE_INCDEC:
6131       if (operands[2] == constm1_rtx)
6132         return "inc{w}\t%0";
6133       else if (operands[2] == const1_rtx)
6134         return "dec{w}\t%0";
6135       else
6136         abort();
6137
6138     default:
6139       if (! rtx_equal_p (operands[0], operands[1]))
6140         abort ();
6141       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6142          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6143       if ((INTVAL (operands[2]) == -128
6144            || (INTVAL (operands[2]) > 0
6145                && INTVAL (operands[2]) != 128)))
6146         return "sub{w}\t{%2, %0|%0, %2}";
6147       operands[2] = GEN_INT (-INTVAL (operands[2]));
6148       return "add{w}\t{%2, %0|%0, %2}";
6149     }
6150 }
6151   [(set (attr "type")
6152      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6153         (const_string "incdec")
6154         (const_string "alu")))
6155    (set_attr "mode" "SI")])
6156
6157
6158 (define_insn "*addhi_5"
6159   [(set (reg 17)
6160         (compare
6161           (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
6162                    (match_operand:HI 2 "general_operand" "rmni"))
6163           (const_int 0)))                       
6164    (clobber (match_scratch:HI 0 "=r"))]
6165   "ix86_match_ccmode (insn, CCGOCmode)
6166    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6167 {
6168   switch (get_attr_type (insn))
6169     {
6170     case TYPE_INCDEC:
6171       if (operands[2] == const1_rtx)
6172         return "inc{w}\t%0";
6173       else if (operands[2] == constm1_rtx)
6174         return "dec{w}\t%0";
6175       abort();
6176
6177     default:
6178       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6179          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6180       if (GET_CODE (operands[2]) == CONST_INT
6181           && (INTVAL (operands[2]) == 128
6182               || (INTVAL (operands[2]) < 0
6183                   && INTVAL (operands[2]) != -128)))
6184         {
6185           operands[2] = GEN_INT (-INTVAL (operands[2]));
6186           return "sub{w}\t{%2, %0|%0, %2}";
6187         }
6188       return "add{w}\t{%2, %0|%0, %2}";
6189     }
6190 }
6191   [(set (attr "type")
6192      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6193         (const_string "incdec")
6194         (const_string "alu")))
6195    (set_attr "mode" "HI")])
6196
6197 (define_expand "addqi3"
6198   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6199                    (plus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6200                             (match_operand:QI 2 "general_operand" "")))
6201               (clobber (reg:CC 17))])]
6202   "TARGET_QIMODE_MATH"
6203   "ix86_expand_binary_operator (PLUS, QImode, operands); DONE;")
6204
6205 ;; %%% Potential partial reg stall on alternative 2.  What to do?
6206 (define_insn "*addqi_1_lea"
6207   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r,r")
6208         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,r")
6209                  (match_operand:QI 2 "general_operand" "qn,qmn,rn,rn")))
6210    (clobber (reg:CC 17))]
6211   "!TARGET_PARTIAL_REG_STALL
6212    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6213 {
6214   int widen = (which_alternative == 2);
6215   switch (get_attr_type (insn))
6216     {
6217     case TYPE_LEA:
6218       return "#";
6219     case TYPE_INCDEC:
6220       if (operands[2] == const1_rtx)
6221         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6222       else if (operands[2] == constm1_rtx)
6223         return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6224       abort();
6225
6226     default:
6227       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6228          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6229       if (GET_CODE (operands[2]) == CONST_INT
6230           && (INTVAL (operands[2]) == 128
6231               || (INTVAL (operands[2]) < 0
6232                   && INTVAL (operands[2]) != -128)))
6233         {
6234           operands[2] = GEN_INT (-INTVAL (operands[2]));
6235           if (widen)
6236             return "sub{l}\t{%2, %k0|%k0, %2}";
6237           else
6238             return "sub{b}\t{%2, %0|%0, %2}";
6239         }
6240       if (widen)
6241         return "add{l}\t{%k2, %k0|%k0, %k2}";
6242       else
6243         return "add{b}\t{%2, %0|%0, %2}";
6244     }
6245 }
6246   [(set (attr "type")
6247      (if_then_else (eq_attr "alternative" "3")
6248         (const_string "lea")
6249         (if_then_else (match_operand:QI 2 "incdec_operand" "")
6250            (const_string "incdec")
6251            (const_string "alu"))))
6252    (set_attr "mode" "QI,QI,SI,SI")])
6253
6254 (define_insn "*addqi_1"
6255   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
6256         (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
6257                  (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
6258    (clobber (reg:CC 17))]
6259   "TARGET_PARTIAL_REG_STALL
6260    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6261 {
6262   int widen = (which_alternative == 2);
6263   switch (get_attr_type (insn))
6264     {
6265     case TYPE_INCDEC:
6266       if (operands[2] == const1_rtx)
6267         return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6268       else if (operands[2] == constm1_rtx)
6269         return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6270       abort();
6271
6272     default:
6273       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6274          Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
6275       if (GET_CODE (operands[2]) == CONST_INT
6276           && (INTVAL (operands[2]) == 128
6277               || (INTVAL (operands[2]) < 0
6278                   && INTVAL (operands[2]) != -128)))
6279         {
6280           operands[2] = GEN_INT (-INTVAL (operands[2]));
6281           if (widen)
6282             return "sub{l}\t{%2, %k0|%k0, %2}";
6283           else
6284             return "sub{b}\t{%2, %0|%0, %2}";
6285         }
6286       if (widen)
6287         return "add{l}\t{%k2, %k0|%k0, %k2}";
6288       else
6289         return "add{b}\t{%2, %0|%0, %2}";
6290     }
6291 }
6292   [(set (attr "type")
6293      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6294         (const_string "incdec")
6295         (const_string "alu")))
6296    (set_attr "mode" "QI,QI,SI")])
6297
6298 (define_insn "*addqi_1_slp"
6299   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6300         (plus:QI (match_dup 0)
6301                  (match_operand:QI 1 "general_operand" "qn,qnm")))
6302    (clobber (reg:CC 17))]
6303   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6304    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
6305 {
6306   switch (get_attr_type (insn))
6307     {
6308     case TYPE_INCDEC:
6309       if (operands[1] == const1_rtx)
6310         return "inc{b}\t%0";
6311       else if (operands[1] == constm1_rtx)
6312         return "dec{b}\t%0";
6313       abort();
6314
6315     default:
6316       /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.  */
6317       if (GET_CODE (operands[1]) == CONST_INT
6318           && INTVAL (operands[1]) < 0)
6319         {
6320           operands[1] = GEN_INT (-INTVAL (operands[1]));
6321           return "sub{b}\t{%1, %0|%0, %1}";
6322         }
6323       return "add{b}\t{%1, %0|%0, %1}";
6324     }
6325 }
6326   [(set (attr "type")
6327      (if_then_else (match_operand:QI 1 "incdec_operand" "")
6328         (const_string "incdec")
6329         (const_string "alu1")))
6330    (set (attr "memory")
6331      (if_then_else (match_operand 1 "memory_operand" "")
6332         (const_string "load")
6333         (const_string "none")))
6334    (set_attr "mode" "QI")])
6335
6336 (define_insn "*addqi_2"
6337   [(set (reg 17)
6338         (compare
6339           (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
6340                    (match_operand:QI 2 "general_operand" "qmni,qni"))
6341           (const_int 0)))
6342    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
6343         (plus:QI (match_dup 1) (match_dup 2)))]
6344   "ix86_match_ccmode (insn, CCGOCmode)
6345    && ix86_binary_operator_ok (PLUS, QImode, operands)"
6346 {
6347   switch (get_attr_type (insn))
6348     {
6349     case TYPE_INCDEC:
6350       if (operands[2] == const1_rtx)
6351         return "inc{b}\t%0";
6352       else if (operands[2] == constm1_rtx
6353                || (GET_CODE (operands[2]) == CONST_INT
6354                    && INTVAL (operands[2]) == 255))
6355         return "dec{b}\t%0";
6356       abort();
6357
6358     default:
6359       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
6360       if (GET_CODE (operands[2]) == CONST_INT
6361           && INTVAL (operands[2]) < 0)
6362         {
6363           operands[2] = GEN_INT (-INTVAL (operands[2]));
6364           return "sub{b}\t{%2, %0|%0, %2}";
6365         }
6366       return "add{b}\t{%2, %0|%0, %2}";
6367     }
6368 }
6369   [(set (attr "type")
6370      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6371         (const_string "incdec")
6372         (const_string "alu")))
6373    (set_attr "mode" "QI")])
6374
6375 (define_insn "*addqi_3"
6376   [(set (reg 17)
6377         (compare (neg:QI (match_operand:QI 2 "general_operand" "qmni"))
6378                  (match_operand:QI 1 "nonimmediate_operand" "%0")))
6379    (clobber (match_scratch:QI 0 "=q"))]
6380   "ix86_match_ccmode (insn, CCZmode)
6381    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6382 {
6383   switch (get_attr_type (insn))
6384     {
6385     case TYPE_INCDEC:
6386       if (operands[2] == const1_rtx)
6387         return "inc{b}\t%0";
6388       else if (operands[2] == constm1_rtx
6389                || (GET_CODE (operands[2]) == CONST_INT
6390                    && INTVAL (operands[2]) == 255))
6391         return "dec{b}\t%0";
6392       abort();
6393
6394     default:
6395       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
6396       if (GET_CODE (operands[2]) == CONST_INT
6397           && INTVAL (operands[2]) < 0)
6398         {
6399           operands[2] = GEN_INT (-INTVAL (operands[2]));
6400           return "sub{b}\t{%2, %0|%0, %2}";
6401         }
6402       return "add{b}\t{%2, %0|%0, %2}";
6403     }
6404 }
6405   [(set (attr "type")
6406      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6407         (const_string "incdec")
6408         (const_string "alu")))
6409    (set_attr "mode" "QI")])
6410
6411 ; See comments above addsi_3_imm for details.
6412 (define_insn "*addqi_4"
6413   [(set (reg 17)
6414         (compare (match_operand:QI 1 "nonimmediate_operand" "0")
6415                  (match_operand:QI 2 "const_int_operand" "n")))
6416    (clobber (match_scratch:QI 0 "=qm"))]
6417   "ix86_match_ccmode (insn, CCGCmode)
6418    && (INTVAL (operands[2]) & 0xff) != 0x80"
6419 {
6420   switch (get_attr_type (insn))
6421     {
6422     case TYPE_INCDEC:
6423       if (operands[2] == constm1_rtx
6424           || (GET_CODE (operands[2]) == CONST_INT
6425               && INTVAL (operands[2]) == 255))
6426         return "inc{b}\t%0";
6427       else if (operands[2] == const1_rtx)
6428         return "dec{b}\t%0";
6429       else
6430         abort();
6431
6432     default:
6433       if (! rtx_equal_p (operands[0], operands[1]))
6434         abort ();
6435       if (INTVAL (operands[2]) < 0)
6436         {
6437           operands[2] = GEN_INT (-INTVAL (operands[2]));
6438           return "add{b}\t{%2, %0|%0, %2}";
6439         }
6440       return "sub{b}\t{%2, %0|%0, %2}";
6441     }
6442 }
6443   [(set (attr "type")
6444      (if_then_else (match_operand:HI 2 "incdec_operand" "")
6445         (const_string "incdec")
6446         (const_string "alu")))
6447    (set_attr "mode" "QI")])
6448
6449
6450 (define_insn "*addqi_5"
6451   [(set (reg 17)
6452         (compare
6453           (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6454                    (match_operand:QI 2 "general_operand" "qmni"))
6455           (const_int 0)))
6456    (clobber (match_scratch:QI 0 "=q"))]
6457   "ix86_match_ccmode (insn, CCGOCmode)
6458    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6459 {
6460   switch (get_attr_type (insn))
6461     {
6462     case TYPE_INCDEC:
6463       if (operands[2] == const1_rtx)
6464         return "inc{b}\t%0";
6465       else if (operands[2] == constm1_rtx
6466                || (GET_CODE (operands[2]) == CONST_INT
6467                    && INTVAL (operands[2]) == 255))
6468         return "dec{b}\t%0";
6469       abort();
6470
6471     default:
6472       /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'.  */
6473       if (GET_CODE (operands[2]) == CONST_INT
6474           && INTVAL (operands[2]) < 0)
6475         {
6476           operands[2] = GEN_INT (-INTVAL (operands[2]));
6477           return "sub{b}\t{%2, %0|%0, %2}";
6478         }
6479       return "add{b}\t{%2, %0|%0, %2}";
6480     }
6481 }
6482   [(set (attr "type")
6483      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6484         (const_string "incdec")
6485         (const_string "alu")))
6486    (set_attr "mode" "QI")])
6487
6488
6489 (define_insn "addqi_ext_1"
6490   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6491                          (const_int 8)
6492                          (const_int 8))
6493         (plus:SI
6494           (zero_extract:SI
6495             (match_operand 1 "ext_register_operand" "0")
6496             (const_int 8)
6497             (const_int 8))
6498           (match_operand:QI 2 "general_operand" "Qmn")))
6499    (clobber (reg:CC 17))]
6500   "!TARGET_64BIT"
6501 {
6502   switch (get_attr_type (insn))
6503     {
6504     case TYPE_INCDEC:
6505       if (operands[2] == const1_rtx)
6506         return "inc{b}\t%h0";
6507       else if (operands[2] == constm1_rtx
6508                || (GET_CODE (operands[2]) == CONST_INT
6509                    && INTVAL (operands[2]) == 255))
6510         return "dec{b}\t%h0";
6511       abort();
6512
6513     default:
6514       return "add{b}\t{%2, %h0|%h0, %2}";
6515     }
6516 }
6517   [(set (attr "type")
6518      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6519         (const_string "incdec")
6520         (const_string "alu")))
6521    (set_attr "mode" "QI")])
6522
6523 (define_insn "*addqi_ext_1_rex64"
6524   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6525                          (const_int 8)
6526                          (const_int 8))
6527         (plus:SI
6528           (zero_extract:SI
6529             (match_operand 1 "ext_register_operand" "0")
6530             (const_int 8)
6531             (const_int 8))
6532           (match_operand:QI 2 "nonmemory_operand" "Qn")))
6533    (clobber (reg:CC 17))]
6534   "TARGET_64BIT"
6535 {
6536   switch (get_attr_type (insn))
6537     {
6538     case TYPE_INCDEC:
6539       if (operands[2] == const1_rtx)
6540         return "inc{b}\t%h0";
6541       else if (operands[2] == constm1_rtx
6542                || (GET_CODE (operands[2]) == CONST_INT
6543                    && INTVAL (operands[2]) == 255))
6544         return "dec{b}\t%h0";
6545       abort();
6546
6547     default:
6548       return "add{b}\t{%2, %h0|%h0, %2}";
6549     }
6550 }
6551   [(set (attr "type")
6552      (if_then_else (match_operand:QI 2 "incdec_operand" "")
6553         (const_string "incdec")
6554         (const_string "alu")))
6555    (set_attr "mode" "QI")])
6556
6557 (define_insn "*addqi_ext_2"
6558   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6559                          (const_int 8)
6560                          (const_int 8))
6561         (plus:SI
6562           (zero_extract:SI
6563             (match_operand 1 "ext_register_operand" "%0")
6564             (const_int 8)
6565             (const_int 8))
6566           (zero_extract:SI
6567             (match_operand 2 "ext_register_operand" "Q")
6568             (const_int 8)
6569             (const_int 8))))
6570    (clobber (reg:CC 17))]
6571   ""
6572   "add{b}\t{%h2, %h0|%h0, %h2}"
6573   [(set_attr "type" "alu")
6574    (set_attr "mode" "QI")])
6575
6576 ;; The patterns that match these are at the end of this file.
6577
6578 (define_expand "addxf3"
6579   [(set (match_operand:XF 0 "register_operand" "")
6580         (plus:XF (match_operand:XF 1 "register_operand" "")
6581                  (match_operand:XF 2 "register_operand" "")))]
6582   "TARGET_80387"
6583   "")
6584
6585 (define_expand "adddf3"
6586   [(set (match_operand:DF 0 "register_operand" "")
6587         (plus:DF (match_operand:DF 1 "register_operand" "")
6588                  (match_operand:DF 2 "nonimmediate_operand" "")))]
6589   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
6590   "")
6591
6592 (define_expand "addsf3"
6593   [(set (match_operand:SF 0 "register_operand" "")
6594         (plus:SF (match_operand:SF 1 "register_operand" "")
6595                  (match_operand:SF 2 "nonimmediate_operand" "")))]
6596   "TARGET_80387 || TARGET_SSE_MATH"
6597   "")
6598 \f
6599 ;; Subtract instructions
6600
6601 ;; %%% splits for subsidi3
6602
6603 (define_expand "subdi3"
6604   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
6605                    (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6606                              (match_operand:DI 2 "x86_64_general_operand" "")))
6607               (clobber (reg:CC 17))])]
6608   ""
6609   "ix86_expand_binary_operator (MINUS, DImode, operands); DONE;")
6610
6611 (define_insn "*subdi3_1"
6612   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
6613         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6614                   (match_operand:DI 2 "general_operand" "roiF,riF")))
6615    (clobber (reg:CC 17))]
6616   "!TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6617   "#")
6618
6619 (define_split
6620   [(set (match_operand:DI 0 "nonimmediate_operand" "")
6621         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6622                   (match_operand:DI 2 "general_operand" "")))
6623    (clobber (reg:CC 17))]
6624   "!TARGET_64BIT && reload_completed"
6625   [(parallel [(set (reg:CC 17) (compare:CC (match_dup 1) (match_dup 2)))
6626               (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 2)))])
6627    (parallel [(set (match_dup 3)
6628                    (minus:SI (match_dup 4)
6629                              (plus:SI (ltu:SI (reg:CC 17) (const_int 0))
6630                                       (match_dup 5))))
6631               (clobber (reg:CC 17))])]
6632   "split_di (operands+0, 1, operands+0, operands+3);
6633    split_di (operands+1, 1, operands+1, operands+4);
6634    split_di (operands+2, 1, operands+2, operands+5);")
6635
6636 (define_insn "subdi3_carry_rex64"
6637   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6638           (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6639             (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
6640                (match_operand:DI 2 "x86_64_general_operand" "re,rm"))))
6641    (clobber (reg:CC 17))]
6642   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6643   "sbb{q}\t{%2, %0|%0, %2}"
6644   [(set_attr "type" "alu")
6645    (set_attr "pent_pair" "pu")
6646    (set_attr "ppro_uops" "few")
6647    (set_attr "mode" "DI")])
6648
6649 (define_insn "*subdi_1_rex64"
6650   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6651         (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6652                   (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6653    (clobber (reg:CC 17))]
6654   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6655   "sub{q}\t{%2, %0|%0, %2}"
6656   [(set_attr "type" "alu")
6657    (set_attr "mode" "DI")])
6658
6659 (define_insn "*subdi_2_rex64"
6660   [(set (reg 17)
6661         (compare
6662           (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6663                     (match_operand:DI 2 "x86_64_general_operand" "re,rm"))
6664           (const_int 0)))
6665    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6666         (minus:DI (match_dup 1) (match_dup 2)))]
6667   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6668    && ix86_binary_operator_ok (MINUS, DImode, operands)"
6669   "sub{q}\t{%2, %0|%0, %2}"
6670   [(set_attr "type" "alu")
6671    (set_attr "mode" "DI")])
6672
6673 (define_insn "*subdi_3_rex63"
6674   [(set (reg 17)
6675         (compare (match_operand:DI 1 "nonimmediate_operand" "0,0")
6676                  (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6677    (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6678         (minus:DI (match_dup 1) (match_dup 2)))]
6679   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6680    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6681   "sub{q}\t{%2, %0|%0, %2}"
6682   [(set_attr "type" "alu")
6683    (set_attr "mode" "DI")])
6684
6685 (define_insn "subqi3_carry"
6686   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6687           (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6688             (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
6689                (match_operand:QI 2 "general_operand" "qi,qm"))))
6690    (clobber (reg:CC 17))]
6691   "ix86_binary_operator_ok (MINUS, QImode, operands)"
6692   "sbb{b}\t{%2, %0|%0, %2}"
6693   [(set_attr "type" "alu")
6694    (set_attr "pent_pair" "pu")
6695    (set_attr "ppro_uops" "few")
6696    (set_attr "mode" "QI")])
6697
6698 (define_insn "subhi3_carry"
6699   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6700           (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6701             (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
6702                (match_operand:HI 2 "general_operand" "ri,rm"))))
6703    (clobber (reg:CC 17))]
6704   "ix86_binary_operator_ok (MINUS, HImode, operands)"
6705   "sbb{w}\t{%2, %0|%0, %2}"
6706   [(set_attr "type" "alu")
6707    (set_attr "pent_pair" "pu")
6708    (set_attr "ppro_uops" "few")
6709    (set_attr "mode" "HI")])
6710
6711 (define_insn "subsi3_carry"
6712   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6713           (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6714             (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6715                (match_operand:SI 2 "general_operand" "ri,rm"))))
6716    (clobber (reg:CC 17))]
6717   "ix86_binary_operator_ok (MINUS, SImode, operands)"
6718   "sbb{l}\t{%2, %0|%0, %2}"
6719   [(set_attr "type" "alu")
6720    (set_attr "pent_pair" "pu")
6721    (set_attr "ppro_uops" "few")
6722    (set_attr "mode" "SI")])
6723
6724 (define_insn "subsi3_carry_zext"
6725   [(set (match_operand:DI 0 "register_operand" "=rm,r")
6726           (zero_extend:DI
6727             (minus:SI (match_operand:SI 1 "register_operand" "0,0")
6728               (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6729                  (match_operand:SI 2 "general_operand" "ri,rm")))))
6730    (clobber (reg:CC 17))]
6731   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6732   "sbb{l}\t{%2, %k0|%k0, %2}"
6733   [(set_attr "type" "alu")
6734    (set_attr "pent_pair" "pu")
6735    (set_attr "ppro_uops" "few")
6736    (set_attr "mode" "SI")])
6737
6738 (define_expand "subsi3"
6739   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
6740                    (minus:SI (match_operand:SI 1 "nonimmediate_operand" "")
6741                              (match_operand:SI 2 "general_operand" "")))
6742               (clobber (reg:CC 17))])]
6743   ""
6744   "ix86_expand_binary_operator (MINUS, SImode, operands); DONE;")
6745
6746 (define_insn "*subsi_1"
6747   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6748         (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6749                   (match_operand:SI 2 "general_operand" "ri,rm")))
6750    (clobber (reg:CC 17))]
6751   "ix86_binary_operator_ok (MINUS, SImode, operands)"
6752   "sub{l}\t{%2, %0|%0, %2}"
6753   [(set_attr "type" "alu")
6754    (set_attr "mode" "SI")])
6755
6756 (define_insn "*subsi_1_zext"
6757   [(set (match_operand:DI 0 "register_operand" "=r")
6758         (zero_extend:DI
6759           (minus:SI (match_operand:SI 1 "register_operand" "0")
6760                     (match_operand:SI 2 "general_operand" "rim"))))
6761    (clobber (reg:CC 17))]
6762   "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6763   "sub{l}\t{%2, %k0|%k0, %2}"
6764   [(set_attr "type" "alu")
6765    (set_attr "mode" "SI")])
6766
6767 (define_insn "*subsi_2"
6768   [(set (reg 17)
6769         (compare
6770           (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6771                     (match_operand:SI 2 "general_operand" "ri,rm"))
6772           (const_int 0)))
6773    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6774         (minus:SI (match_dup 1) (match_dup 2)))]
6775   "ix86_match_ccmode (insn, CCGOCmode)
6776    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6777   "sub{l}\t{%2, %0|%0, %2}"
6778   [(set_attr "type" "alu")
6779    (set_attr "mode" "SI")])
6780
6781 (define_insn "*subsi_2_zext"
6782   [(set (reg 17)
6783         (compare
6784           (minus:SI (match_operand:SI 1 "register_operand" "0")
6785                     (match_operand:SI 2 "general_operand" "rim"))
6786           (const_int 0)))
6787    (set (match_operand:DI 0 "register_operand" "=r")
6788         (zero_extend:DI
6789           (minus:SI (match_dup 1)
6790                     (match_dup 2))))]
6791   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6792    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6793   "sub{l}\t{%2, %k0|%k0, %2}"
6794   [(set_attr "type" "alu")
6795    (set_attr "mode" "SI")])
6796
6797 (define_insn "*subsi_3"
6798   [(set (reg 17)
6799         (compare (match_operand:SI 1 "nonimmediate_operand" "0,0")
6800                  (match_operand:SI 2 "general_operand" "ri,rm")))
6801    (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6802         (minus:SI (match_dup 1) (match_dup 2)))]
6803   "ix86_match_ccmode (insn, CCmode)
6804    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6805   "sub{l}\t{%2, %0|%0, %2}"
6806   [(set_attr "type" "alu")
6807    (set_attr "mode" "SI")])
6808
6809 (define_insn "*subsi_3_zext"
6810   [(set (reg 17)
6811         (compare (match_operand:SI 1 "register_operand" "0")
6812                  (match_operand:SI 2 "general_operand" "rim")))
6813    (set (match_operand:DI 0 "register_operand" "=r")
6814         (zero_extend:DI
6815           (minus:SI (match_dup 1)
6816                     (match_dup 2))))]
6817   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6818    && ix86_binary_operator_ok (MINUS, SImode, operands)"
6819   "sub{q}\t{%2, %0|%0, %2}"
6820   [(set_attr "type" "alu")
6821    (set_attr "mode" "DI")])
6822
6823 (define_expand "subhi3"
6824   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
6825                    (minus:HI (match_operand:HI 1 "nonimmediate_operand" "")
6826                              (match_operand:HI 2 "general_operand" "")))
6827               (clobber (reg:CC 17))])]
6828   "TARGET_HIMODE_MATH"
6829   "ix86_expand_binary_operator (MINUS, HImode, operands); DONE;")
6830
6831 (define_insn "*subhi_1"
6832   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6833         (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6834                   (match_operand:HI 2 "general_operand" "ri,rm")))
6835    (clobber (reg:CC 17))]
6836   "ix86_binary_operator_ok (MINUS, HImode, operands)"
6837   "sub{w}\t{%2, %0|%0, %2}"
6838   [(set_attr "type" "alu")
6839    (set_attr "mode" "HI")])
6840
6841 (define_insn "*subhi_2"
6842   [(set (reg 17)
6843         (compare
6844           (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6845                     (match_operand:HI 2 "general_operand" "ri,rm"))
6846           (const_int 0)))
6847    (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6848         (minus:HI (match_dup 1) (match_dup 2)))]
6849   "ix86_match_ccmode (insn, CCGOCmode)
6850    && ix86_binary_operator_ok (MINUS, HImode, operands)"
6851   "sub{w}\t{%2, %0|%0, %2}"
6852   [(set_attr "type" "alu")
6853    (set_attr "mode" "HI")])
6854
6855 (define_insn "*subhi_3"
6856   [(set (reg 17)
6857         (compare (match_operand:HI 1 "nonimmediate_operand" "0,0")
6858                  (match_operand:HI 2 "general_operand" "ri,rm")))
6859    (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6860         (minus:HI (match_dup 1) (match_dup 2)))]
6861   "ix86_match_ccmode (insn, CCmode)
6862    && ix86_binary_operator_ok (MINUS, HImode, operands)"
6863   "sub{w}\t{%2, %0|%0, %2}"
6864   [(set_attr "type" "alu")
6865    (set_attr "mode" "HI")])
6866
6867 (define_expand "subqi3"
6868   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6869                    (minus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6870                              (match_operand:QI 2 "general_operand" "")))
6871               (clobber (reg:CC 17))])]
6872   "TARGET_QIMODE_MATH"
6873   "ix86_expand_binary_operator (MINUS, QImode, operands); DONE;")
6874
6875 (define_insn "*subqi_1"
6876   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6877         (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6878                   (match_operand:QI 2 "general_operand" "qn,qmn")))
6879    (clobber (reg:CC 17))]
6880   "ix86_binary_operator_ok (MINUS, QImode, operands)"
6881   "sub{b}\t{%2, %0|%0, %2}"
6882   [(set_attr "type" "alu")
6883    (set_attr "mode" "QI")])
6884
6885 (define_insn "*subqi_1_slp"
6886   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6887         (minus:QI (match_dup 0)
6888                   (match_operand:QI 1 "general_operand" "qn,qmn")))
6889    (clobber (reg:CC 17))]
6890   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6891    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
6892   "sub{b}\t{%1, %0|%0, %1}"
6893   [(set_attr "type" "alu1")
6894    (set_attr "mode" "QI")])
6895
6896 (define_insn "*subqi_2"
6897   [(set (reg 17)
6898         (compare
6899           (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6900                     (match_operand:QI 2 "general_operand" "qi,qm"))
6901           (const_int 0)))
6902    (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6903         (minus:HI (match_dup 1) (match_dup 2)))]
6904   "ix86_match_ccmode (insn, CCGOCmode)
6905    && ix86_binary_operator_ok (MINUS, QImode, operands)"
6906   "sub{b}\t{%2, %0|%0, %2}"
6907   [(set_attr "type" "alu")
6908    (set_attr "mode" "QI")])
6909
6910 (define_insn "*subqi_3"
6911   [(set (reg 17)
6912         (compare (match_operand:QI 1 "nonimmediate_operand" "0,0")
6913                  (match_operand:QI 2 "general_operand" "qi,qm")))
6914    (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6915         (minus:HI (match_dup 1) (match_dup 2)))]
6916   "ix86_match_ccmode (insn, CCmode)
6917    && ix86_binary_operator_ok (MINUS, QImode, operands)"
6918   "sub{b}\t{%2, %0|%0, %2}"
6919   [(set_attr "type" "alu")
6920    (set_attr "mode" "QI")])
6921
6922 ;; The patterns that match these are at the end of this file.
6923
6924 (define_expand "subxf3"
6925   [(set (match_operand:XF 0 "register_operand" "")
6926         (minus:XF (match_operand:XF 1 "register_operand" "")
6927                   (match_operand:XF 2 "register_operand" "")))]
6928   "TARGET_80387"
6929   "")
6930
6931 (define_expand "subdf3"
6932   [(set (match_operand:DF 0 "register_operand" "")
6933         (minus:DF (match_operand:DF 1 "register_operand" "")
6934                   (match_operand:DF 2 "nonimmediate_operand" "")))]
6935   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
6936   "")
6937
6938 (define_expand "subsf3"
6939   [(set (match_operand:SF 0 "register_operand" "")
6940         (minus:SF (match_operand:SF 1 "register_operand" "")
6941                   (match_operand:SF 2 "nonimmediate_operand" "")))]
6942   "TARGET_80387 || TARGET_SSE_MATH"
6943   "")
6944 \f
6945 ;; Multiply instructions
6946
6947 (define_expand "muldi3"
6948   [(parallel [(set (match_operand:DI 0 "register_operand" "")
6949                    (mult:DI (match_operand:DI 1 "register_operand" "")
6950                             (match_operand:DI 2 "x86_64_general_operand" "")))
6951               (clobber (reg:CC 17))])]
6952   "TARGET_64BIT"
6953   "")
6954
6955 (define_insn "*muldi3_1_rex64"
6956   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6957         (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%rm,rm,0")
6958                  (match_operand:DI 2 "x86_64_general_operand" "K,e,mr")))
6959    (clobber (reg:CC 17))]
6960   "TARGET_64BIT
6961    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6962   "@
6963    imul{q}\t{%2, %1, %0|%0, %1, %2}
6964    imul{q}\t{%2, %1, %0|%0, %1, %2}
6965    imul{q}\t{%2, %0|%0, %2}"
6966   [(set_attr "type" "imul")
6967    (set_attr "prefix_0f" "0,0,1")
6968    (set (attr "athlon_decode")
6969         (cond [(eq_attr "cpu" "athlon")
6970                   (const_string "vector")
6971                (eq_attr "alternative" "1")
6972                   (const_string "vector")
6973                (and (eq_attr "alternative" "2")
6974                     (match_operand 1 "memory_operand" ""))
6975                   (const_string "vector")]
6976               (const_string "direct")))
6977    (set_attr "mode" "DI")])
6978
6979 (define_expand "mulsi3"
6980   [(parallel [(set (match_operand:SI 0 "register_operand" "")
6981                    (mult:SI (match_operand:SI 1 "register_operand" "")
6982                             (match_operand:SI 2 "general_operand" "")))
6983               (clobber (reg:CC 17))])]
6984   ""
6985   "")
6986
6987 (define_insn "*mulsi3_1"
6988   [(set (match_operand:SI 0 "register_operand" "=r,r,r")
6989         (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6990                  (match_operand:SI 2 "general_operand" "K,i,mr")))
6991    (clobber (reg:CC 17))]
6992   "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6993   "@
6994    imul{l}\t{%2, %1, %0|%0, %1, %2}
6995    imul{l}\t{%2, %1, %0|%0, %1, %2}
6996    imul{l}\t{%2, %0|%0, %2}"
6997   [(set_attr "type" "imul")
6998    (set_attr "prefix_0f" "0,0,1")
6999    (set (attr "athlon_decode")
7000         (cond [(eq_attr "cpu" "athlon")
7001                   (const_string "vector")
7002                (eq_attr "alternative" "1")
7003                   (const_string "vector")
7004                (and (eq_attr "alternative" "2")
7005                     (match_operand 1 "memory_operand" ""))
7006                   (const_string "vector")]
7007               (const_string "direct")))
7008    (set_attr "mode" "SI")])
7009
7010 (define_insn "*mulsi3_1_zext"
7011   [(set (match_operand:DI 0 "register_operand" "=r,r,r")
7012         (zero_extend:DI
7013           (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
7014                    (match_operand:SI 2 "general_operand" "K,i,mr"))))
7015    (clobber (reg:CC 17))]
7016   "TARGET_64BIT
7017    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7018   "@
7019    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
7020    imul{l}\t{%2, %1, %k0|%k0, %1, %2}
7021    imul{l}\t{%2, %k0|%k0, %2}"
7022   [(set_attr "type" "imul")
7023    (set_attr "prefix_0f" "0,0,1")
7024    (set (attr "athlon_decode")
7025         (cond [(eq_attr "cpu" "athlon")
7026                   (const_string "vector")
7027                (eq_attr "alternative" "1")
7028                   (const_string "vector")
7029                (and (eq_attr "alternative" "2")
7030                     (match_operand 1 "memory_operand" ""))
7031                   (const_string "vector")]
7032               (const_string "direct")))
7033    (set_attr "mode" "SI")])
7034
7035 (define_expand "mulhi3"
7036   [(parallel [(set (match_operand:HI 0 "register_operand" "")
7037                    (mult:HI (match_operand:HI 1 "register_operand" "")
7038                             (match_operand:HI 2 "general_operand" "")))
7039               (clobber (reg:CC 17))])]
7040   "TARGET_HIMODE_MATH"
7041   "")
7042
7043 (define_insn "*mulhi3_1"
7044   [(set (match_operand:HI 0 "register_operand" "=r,r,r")
7045         (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
7046                  (match_operand:HI 2 "general_operand" "K,i,mr")))
7047    (clobber (reg:CC 17))]
7048   "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7049   "@
7050    imul{w}\t{%2, %1, %0|%0, %1, %2}
7051    imul{w}\t{%2, %1, %0|%0, %1, %2}
7052    imul{w}\t{%2, %0|%0, %2}"
7053   [(set_attr "type" "imul")
7054    (set_attr "prefix_0f" "0,0,1")
7055    (set (attr "athlon_decode")
7056         (cond [(eq_attr "cpu" "athlon")
7057                   (const_string "vector")
7058                (eq_attr "alternative" "1,2")
7059                   (const_string "vector")]
7060               (const_string "direct")))
7061    (set_attr "mode" "HI")])
7062
7063 (define_expand "mulqi3"
7064   [(parallel [(set (match_operand:QI 0 "register_operand" "")
7065                    (mult:QI (match_operand:QI 1 "nonimmediate_operand" "")
7066                             (match_operand:QI 2 "register_operand" "")))
7067               (clobber (reg:CC 17))])]
7068   "TARGET_QIMODE_MATH"
7069   "")
7070
7071 (define_insn "*mulqi3_1"
7072   [(set (match_operand:QI 0 "register_operand" "=a")
7073         (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
7074                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
7075    (clobber (reg:CC 17))]
7076   "TARGET_QIMODE_MATH
7077    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7078   "mul{b}\t%2"
7079   [(set_attr "type" "imul")
7080    (set_attr "length_immediate" "0")
7081    (set (attr "athlon_decode")
7082      (if_then_else (eq_attr "cpu" "athlon")
7083         (const_string "vector")
7084         (const_string "direct")))
7085    (set_attr "mode" "QI")])
7086
7087 (define_expand "umulqihi3"
7088   [(parallel [(set (match_operand:HI 0 "register_operand" "")
7089                    (mult:HI (zero_extend:HI
7090                               (match_operand:QI 1 "nonimmediate_operand" ""))
7091                             (zero_extend:HI
7092                               (match_operand:QI 2 "register_operand" ""))))
7093               (clobber (reg:CC 17))])]
7094   "TARGET_QIMODE_MATH"
7095   "")
7096
7097 (define_insn "*umulqihi3_1"
7098   [(set (match_operand:HI 0 "register_operand" "=a")
7099         (mult:HI (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
7100                  (zero_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
7101    (clobber (reg:CC 17))]
7102   "TARGET_QIMODE_MATH
7103    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7104   "mul{b}\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 "direct")))
7111    (set_attr "mode" "QI")])
7112
7113 (define_expand "mulqihi3"
7114   [(parallel [(set (match_operand:HI 0 "register_operand" "")
7115                    (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))
7116                             (sign_extend:HI (match_operand:QI 2 "register_operand" ""))))
7117               (clobber (reg:CC 17))])]
7118   "TARGET_QIMODE_MATH"
7119   "")
7120
7121 (define_insn "*mulqihi3_insn"
7122   [(set (match_operand:HI 0 "register_operand" "=a")
7123         (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
7124                  (sign_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
7125    (clobber (reg:CC 17))]
7126   "TARGET_QIMODE_MATH
7127    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7128   "imul{b}\t%2"
7129   [(set_attr "type" "imul")
7130    (set_attr "length_immediate" "0")
7131    (set (attr "athlon_decode")
7132      (if_then_else (eq_attr "cpu" "athlon")
7133         (const_string "vector")
7134         (const_string "direct")))
7135    (set_attr "mode" "QI")])
7136
7137 (define_expand "umulditi3"
7138   [(parallel [(set (match_operand:TI 0 "register_operand" "")
7139                    (mult:TI (zero_extend:TI
7140                               (match_operand:DI 1 "nonimmediate_operand" ""))
7141                             (zero_extend:TI
7142                               (match_operand:DI 2 "register_operand" ""))))
7143               (clobber (reg:CC 17))])]
7144   "TARGET_64BIT"
7145   "")
7146
7147 (define_insn "*umulditi3_insn"
7148   [(set (match_operand:TI 0 "register_operand" "=A")
7149         (mult:TI (zero_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
7150                  (zero_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
7151    (clobber (reg:CC 17))]
7152   "TARGET_64BIT
7153    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7154   "mul{q}\t%2"
7155   [(set_attr "type" "imul")
7156    (set_attr "ppro_uops" "few")
7157    (set_attr "length_immediate" "0")
7158    (set (attr "athlon_decode")
7159      (if_then_else (eq_attr "cpu" "athlon")
7160         (const_string "vector")
7161         (const_string "double")))
7162    (set_attr "mode" "DI")])
7163
7164 ;; We can't use this pattern in 64bit mode, since it results in two separate 32bit registers
7165 (define_expand "umulsidi3"
7166   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7167                    (mult:DI (zero_extend:DI
7168                               (match_operand:SI 1 "nonimmediate_operand" ""))
7169                             (zero_extend:DI
7170                               (match_operand:SI 2 "register_operand" ""))))
7171               (clobber (reg:CC 17))])]
7172   "!TARGET_64BIT"
7173   "")
7174
7175 (define_insn "*umulsidi3_insn"
7176   [(set (match_operand:DI 0 "register_operand" "=A")
7177         (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7178                  (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7179    (clobber (reg:CC 17))]
7180   "!TARGET_64BIT
7181    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7182   "mul{l}\t%2"
7183   [(set_attr "type" "imul")
7184    (set_attr "ppro_uops" "few")
7185    (set_attr "length_immediate" "0")
7186    (set (attr "athlon_decode")
7187      (if_then_else (eq_attr "cpu" "athlon")
7188         (const_string "vector")
7189         (const_string "double")))
7190    (set_attr "mode" "SI")])
7191
7192 (define_expand "mulditi3"
7193   [(parallel [(set (match_operand:TI 0 "register_operand" "")
7194                    (mult:TI (sign_extend:TI
7195                               (match_operand:DI 1 "nonimmediate_operand" ""))
7196                             (sign_extend:TI
7197                               (match_operand:DI 2 "register_operand" ""))))
7198               (clobber (reg:CC 17))])]
7199   "TARGET_64BIT"
7200   "")
7201
7202 (define_insn "*mulditi3_insn"
7203   [(set (match_operand:TI 0 "register_operand" "=A")
7204         (mult:TI (sign_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
7205                  (sign_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
7206    (clobber (reg:CC 17))]
7207   "TARGET_64BIT
7208    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7209   "imul{q}\t%2"
7210   [(set_attr "type" "imul")
7211    (set_attr "length_immediate" "0")
7212    (set (attr "athlon_decode")
7213      (if_then_else (eq_attr "cpu" "athlon")
7214         (const_string "vector")
7215         (const_string "double")))
7216    (set_attr "mode" "DI")])
7217
7218 (define_expand "mulsidi3"
7219   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7220                    (mult:DI (sign_extend:DI
7221                               (match_operand:SI 1 "nonimmediate_operand" ""))
7222                             (sign_extend:DI
7223                               (match_operand:SI 2 "register_operand" ""))))
7224               (clobber (reg:CC 17))])]
7225   "!TARGET_64BIT"
7226   "")
7227
7228 (define_insn "*mulsidi3_insn"
7229   [(set (match_operand:DI 0 "register_operand" "=A")
7230         (mult:DI (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7231                  (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7232    (clobber (reg:CC 17))]
7233   "!TARGET_64BIT
7234    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7235   "imul{l}\t%2"
7236   [(set_attr "type" "imul")
7237    (set_attr "length_immediate" "0")
7238    (set (attr "athlon_decode")
7239      (if_then_else (eq_attr "cpu" "athlon")
7240         (const_string "vector")
7241         (const_string "double")))
7242    (set_attr "mode" "SI")])
7243
7244 (define_expand "umuldi3_highpart"
7245   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7246                    (truncate:DI
7247                      (lshiftrt:TI
7248                        (mult:TI (zero_extend:TI
7249                                   (match_operand:DI 1 "nonimmediate_operand" ""))
7250                                 (zero_extend:TI
7251                                   (match_operand:DI 2 "register_operand" "")))
7252                        (const_int 64))))
7253               (clobber (match_scratch:DI 3 ""))
7254               (clobber (reg:CC 17))])]
7255   "TARGET_64BIT"
7256   "")
7257
7258 (define_insn "*umuldi3_highpart_rex64"
7259   [(set (match_operand:DI 0 "register_operand" "=d")
7260         (truncate:DI
7261           (lshiftrt:TI
7262             (mult:TI (zero_extend:TI
7263                        (match_operand:DI 1 "nonimmediate_operand" "%a"))
7264                      (zero_extend:TI
7265                        (match_operand:DI 2 "nonimmediate_operand" "rm")))
7266             (const_int 64))))
7267    (clobber (match_scratch:DI 3 "=1"))
7268    (clobber (reg:CC 17))]
7269   "TARGET_64BIT
7270    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7271   "mul{q}\t%2"
7272   [(set_attr "type" "imul")
7273    (set_attr "ppro_uops" "few")
7274    (set_attr "length_immediate" "0")
7275    (set (attr "athlon_decode")
7276      (if_then_else (eq_attr "cpu" "athlon")
7277         (const_string "vector")
7278         (const_string "double")))
7279    (set_attr "mode" "DI")])
7280
7281 (define_expand "umulsi3_highpart"
7282   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7283                    (truncate:SI
7284                      (lshiftrt:DI
7285                        (mult:DI (zero_extend:DI
7286                                   (match_operand:SI 1 "nonimmediate_operand" ""))
7287                                 (zero_extend:DI
7288                                   (match_operand:SI 2 "register_operand" "")))
7289                        (const_int 32))))
7290               (clobber (match_scratch:SI 3 ""))
7291               (clobber (reg:CC 17))])]
7292   ""
7293   "")
7294
7295 (define_insn "*umulsi3_highpart_insn"
7296   [(set (match_operand:SI 0 "register_operand" "=d")
7297         (truncate:SI
7298           (lshiftrt:DI
7299             (mult:DI (zero_extend:DI
7300                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7301                      (zero_extend:DI
7302                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7303             (const_int 32))))
7304    (clobber (match_scratch:SI 3 "=1"))
7305    (clobber (reg:CC 17))]
7306   "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7307   "mul{l}\t%2"
7308   [(set_attr "type" "imul")
7309    (set_attr "ppro_uops" "few")
7310    (set_attr "length_immediate" "0")
7311    (set (attr "athlon_decode")
7312      (if_then_else (eq_attr "cpu" "athlon")
7313         (const_string "vector")
7314         (const_string "double")))
7315    (set_attr "mode" "SI")])
7316
7317 (define_insn "*umulsi3_highpart_zext"
7318   [(set (match_operand:DI 0 "register_operand" "=d")
7319         (zero_extend:DI (truncate:SI
7320           (lshiftrt:DI
7321             (mult:DI (zero_extend:DI
7322                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7323                      (zero_extend:DI
7324                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7325             (const_int 32)))))
7326    (clobber (match_scratch:SI 3 "=1"))
7327    (clobber (reg:CC 17))]
7328   "TARGET_64BIT
7329    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7330   "mul{l}\t%2"
7331   [(set_attr "type" "imul")
7332    (set_attr "ppro_uops" "few")
7333    (set_attr "length_immediate" "0")
7334    (set (attr "athlon_decode")
7335      (if_then_else (eq_attr "cpu" "athlon")
7336         (const_string "vector")
7337         (const_string "double")))
7338    (set_attr "mode" "SI")])
7339
7340 (define_expand "smuldi3_highpart"
7341   [(parallel [(set (match_operand:DI 0 "register_operand" "=d")
7342                    (truncate:DI
7343                      (lshiftrt:TI
7344                        (mult:TI (sign_extend:TI
7345                                   (match_operand:DI 1 "nonimmediate_operand" ""))
7346                                 (sign_extend:TI
7347                                   (match_operand:DI 2 "register_operand" "")))
7348                        (const_int 64))))
7349               (clobber (match_scratch:DI 3 ""))
7350               (clobber (reg:CC 17))])]
7351   "TARGET_64BIT"
7352   "")
7353
7354 (define_insn "*smuldi3_highpart_rex64"
7355   [(set (match_operand:DI 0 "register_operand" "=d")
7356         (truncate:DI
7357           (lshiftrt:TI
7358             (mult:TI (sign_extend:TI
7359                        (match_operand:DI 1 "nonimmediate_operand" "%a"))
7360                      (sign_extend:TI
7361                        (match_operand:DI 2 "nonimmediate_operand" "rm")))
7362             (const_int 64))))
7363    (clobber (match_scratch:DI 3 "=1"))
7364    (clobber (reg:CC 17))]
7365   "TARGET_64BIT
7366    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7367   "imul{q}\t%2"
7368   [(set_attr "type" "imul")
7369    (set_attr "ppro_uops" "few")
7370    (set (attr "athlon_decode")
7371      (if_then_else (eq_attr "cpu" "athlon")
7372         (const_string "vector")
7373         (const_string "double")))
7374    (set_attr "mode" "DI")])
7375
7376 (define_expand "smulsi3_highpart"
7377   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7378                    (truncate:SI
7379                      (lshiftrt:DI
7380                        (mult:DI (sign_extend:DI
7381                                   (match_operand:SI 1 "nonimmediate_operand" ""))
7382                                 (sign_extend:DI
7383                                   (match_operand:SI 2 "register_operand" "")))
7384                        (const_int 32))))
7385               (clobber (match_scratch:SI 3 ""))
7386               (clobber (reg:CC 17))])]
7387   ""
7388   "")
7389
7390 (define_insn "*smulsi3_highpart_insn"
7391   [(set (match_operand:SI 0 "register_operand" "=d")
7392         (truncate:SI
7393           (lshiftrt:DI
7394             (mult:DI (sign_extend:DI
7395                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7396                      (sign_extend:DI
7397                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7398             (const_int 32))))
7399    (clobber (match_scratch:SI 3 "=1"))
7400    (clobber (reg:CC 17))]
7401   "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7402   "imul{l}\t%2"
7403   [(set_attr "type" "imul")
7404    (set_attr "ppro_uops" "few")
7405    (set (attr "athlon_decode")
7406      (if_then_else (eq_attr "cpu" "athlon")
7407         (const_string "vector")
7408         (const_string "double")))
7409    (set_attr "mode" "SI")])
7410
7411 (define_insn "*smulsi3_highpart_zext"
7412   [(set (match_operand:DI 0 "register_operand" "=d")
7413         (zero_extend:DI (truncate:SI
7414           (lshiftrt:DI
7415             (mult:DI (sign_extend:DI
7416                        (match_operand:SI 1 "nonimmediate_operand" "%a"))
7417                      (sign_extend:DI
7418                        (match_operand:SI 2 "nonimmediate_operand" "rm")))
7419             (const_int 32)))))
7420    (clobber (match_scratch:SI 3 "=1"))
7421    (clobber (reg:CC 17))]
7422   "TARGET_64BIT
7423    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7424   "imul{l}\t%2"
7425   [(set_attr "type" "imul")
7426    (set_attr "ppro_uops" "few")
7427    (set (attr "athlon_decode")
7428      (if_then_else (eq_attr "cpu" "athlon")
7429         (const_string "vector")
7430         (const_string "double")))
7431    (set_attr "mode" "SI")])
7432
7433 ;; The patterns that match these are at the end of this file.
7434
7435 (define_expand "mulxf3"
7436   [(set (match_operand:XF 0 "register_operand" "")
7437         (mult:XF (match_operand:XF 1 "register_operand" "")
7438                  (match_operand:XF 2 "register_operand" "")))]
7439   "TARGET_80387"
7440   "")
7441
7442 (define_expand "muldf3"
7443   [(set (match_operand:DF 0 "register_operand" "")
7444         (mult:DF (match_operand:DF 1 "register_operand" "")
7445                  (match_operand:DF 2 "nonimmediate_operand" "")))]
7446   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
7447   "")
7448
7449 (define_expand "mulsf3"
7450   [(set (match_operand:SF 0 "register_operand" "")
7451         (mult:SF (match_operand:SF 1 "register_operand" "")
7452                  (match_operand:SF 2 "nonimmediate_operand" "")))]
7453   "TARGET_80387 || TARGET_SSE_MATH"
7454   "")
7455 \f
7456 ;; Divide instructions
7457
7458 (define_insn "divqi3"
7459   [(set (match_operand:QI 0 "register_operand" "=a")
7460         (div:QI (match_operand:HI 1 "register_operand" "0")
7461                 (match_operand:QI 2 "nonimmediate_operand" "qm")))
7462    (clobber (reg:CC 17))]
7463   "TARGET_QIMODE_MATH"
7464   "idiv{b}\t%2"
7465   [(set_attr "type" "idiv")
7466    (set_attr "mode" "QI")
7467    (set_attr "ppro_uops" "few")])
7468
7469 (define_insn "udivqi3"
7470   [(set (match_operand:QI 0 "register_operand" "=a")
7471         (udiv:QI (match_operand:HI 1 "register_operand" "0")
7472                  (match_operand:QI 2 "nonimmediate_operand" "qm")))
7473    (clobber (reg:CC 17))]
7474   "TARGET_QIMODE_MATH"
7475   "div{b}\t%2"
7476   [(set_attr "type" "idiv")
7477    (set_attr "mode" "QI")
7478    (set_attr "ppro_uops" "few")])
7479
7480 ;; The patterns that match these are at the end of this file.
7481
7482 (define_expand "divxf3"
7483   [(set (match_operand:XF 0 "register_operand" "")
7484         (div:XF (match_operand:XF 1 "register_operand" "")
7485                 (match_operand:XF 2 "register_operand" "")))]
7486   "TARGET_80387"
7487   "")
7488
7489 (define_expand "divdf3"
7490   [(set (match_operand:DF 0 "register_operand" "")
7491         (div:DF (match_operand:DF 1 "register_operand" "")
7492                 (match_operand:DF 2 "nonimmediate_operand" "")))]
7493    "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
7494    "")
7495  
7496 (define_expand "divsf3"
7497   [(set (match_operand:SF 0 "register_operand" "")
7498         (div:SF (match_operand:SF 1 "register_operand" "")
7499                 (match_operand:SF 2 "nonimmediate_operand" "")))]
7500   "TARGET_80387 || TARGET_SSE_MATH"
7501   "")
7502 \f
7503 ;; Remainder instructions.
7504
7505 (define_expand "divmoddi4"
7506   [(parallel [(set (match_operand:DI 0 "register_operand" "")
7507                    (div:DI (match_operand:DI 1 "register_operand" "")
7508                            (match_operand:DI 2 "nonimmediate_operand" "")))
7509               (set (match_operand:DI 3 "register_operand" "")
7510                    (mod:DI (match_dup 1) (match_dup 2)))
7511               (clobber (reg:CC 17))])]
7512   "TARGET_64BIT"
7513   "")
7514
7515 ;; Allow to come the parameter in eax or edx to avoid extra moves.
7516 ;; Penalize eax case slightly because it results in worse scheduling
7517 ;; of code.
7518 (define_insn "*divmoddi4_nocltd_rex64"
7519   [(set (match_operand:DI 0 "register_operand" "=&a,?a")
7520         (div:DI (match_operand:DI 2 "register_operand" "1,0")
7521                 (match_operand:DI 3 "nonimmediate_operand" "rm,rm")))
7522    (set (match_operand:DI 1 "register_operand" "=&d,&d")
7523         (mod:DI (match_dup 2) (match_dup 3)))
7524    (clobber (reg:CC 17))]
7525   "TARGET_64BIT && !optimize_size && !TARGET_USE_CLTD"
7526   "#"
7527   [(set_attr "type" "multi")])
7528
7529 (define_insn "*divmoddi4_cltd_rex64"
7530   [(set (match_operand:DI 0 "register_operand" "=a")
7531         (div:DI (match_operand:DI 2 "register_operand" "a")
7532                 (match_operand:DI 3 "nonimmediate_operand" "rm")))
7533    (set (match_operand:DI 1 "register_operand" "=&d")
7534         (mod:DI (match_dup 2) (match_dup 3)))
7535    (clobber (reg:CC 17))]
7536   "TARGET_64BIT && (optimize_size || TARGET_USE_CLTD)"
7537   "#"
7538   [(set_attr "type" "multi")])
7539
7540 (define_insn "*divmoddi_noext_rex64"
7541   [(set (match_operand:DI 0 "register_operand" "=a")
7542         (div:DI (match_operand:DI 1 "register_operand" "0")
7543                 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7544    (set (match_operand:DI 3 "register_operand" "=d")
7545         (mod:DI (match_dup 1) (match_dup 2)))
7546    (use (match_operand:DI 4 "register_operand" "3"))
7547    (clobber (reg:CC 17))]
7548   "TARGET_64BIT"
7549   "idiv{q}\t%2"
7550   [(set_attr "type" "idiv")
7551    (set_attr "mode" "DI")
7552    (set_attr "ppro_uops" "few")])
7553
7554 (define_split
7555   [(set (match_operand:DI 0 "register_operand" "")
7556         (div:DI (match_operand:DI 1 "register_operand" "")
7557                 (match_operand:DI 2 "nonimmediate_operand" "")))
7558    (set (match_operand:DI 3 "register_operand" "")
7559         (mod:DI (match_dup 1) (match_dup 2)))
7560    (clobber (reg:CC 17))]
7561   "TARGET_64BIT && reload_completed"
7562   [(parallel [(set (match_dup 3)
7563                    (ashiftrt:DI (match_dup 4) (const_int 63)))
7564               (clobber (reg:CC 17))])
7565    (parallel [(set (match_dup 0)
7566                    (div:DI (reg:DI 0) (match_dup 2)))
7567               (set (match_dup 3)
7568                    (mod:DI (reg:DI 0) (match_dup 2)))
7569               (use (match_dup 3))
7570               (clobber (reg:CC 17))])]
7571 {
7572   /* Avoid use of cltd in favor of a mov+shift.  */
7573   if (!TARGET_USE_CLTD && !optimize_size)
7574     {
7575       if (true_regnum (operands[1]))
7576         emit_move_insn (operands[0], operands[1]);
7577       else
7578         emit_move_insn (operands[3], operands[1]);
7579       operands[4] = operands[3];
7580     }
7581   else
7582     {
7583       if (true_regnum (operands[1]))
7584         abort();
7585       operands[4] = operands[1];
7586     }
7587 })
7588
7589
7590 (define_expand "divmodsi4"
7591   [(parallel [(set (match_operand:SI 0 "register_operand" "")
7592                    (div:SI (match_operand:SI 1 "register_operand" "")
7593                            (match_operand:SI 2 "nonimmediate_operand" "")))
7594               (set (match_operand:SI 3 "register_operand" "")
7595                    (mod:SI (match_dup 1) (match_dup 2)))
7596               (clobber (reg:CC 17))])]
7597   ""
7598   "")
7599
7600 ;; Allow to come the parameter in eax or edx to avoid extra moves.
7601 ;; Penalize eax case slightly because it results in worse scheduling
7602 ;; of code.
7603 (define_insn "*divmodsi4_nocltd"
7604   [(set (match_operand:SI 0 "register_operand" "=&a,?a")
7605         (div:SI (match_operand:SI 2 "register_operand" "1,0")
7606                 (match_operand:SI 3 "nonimmediate_operand" "rm,rm")))
7607    (set (match_operand:SI 1 "register_operand" "=&d,&d")
7608         (mod:SI (match_dup 2) (match_dup 3)))
7609    (clobber (reg:CC 17))]
7610   "!optimize_size && !TARGET_USE_CLTD"
7611   "#"
7612   [(set_attr "type" "multi")])
7613
7614 (define_insn "*divmodsi4_cltd"
7615   [(set (match_operand:SI 0 "register_operand" "=a")
7616         (div:SI (match_operand:SI 2 "register_operand" "a")
7617                 (match_operand:SI 3 "nonimmediate_operand" "rm")))
7618    (set (match_operand:SI 1 "register_operand" "=&d")
7619         (mod:SI (match_dup 2) (match_dup 3)))
7620    (clobber (reg:CC 17))]
7621   "optimize_size || TARGET_USE_CLTD"
7622   "#"
7623   [(set_attr "type" "multi")])
7624
7625 (define_insn "*divmodsi_noext"
7626   [(set (match_operand:SI 0 "register_operand" "=a")
7627         (div:SI (match_operand:SI 1 "register_operand" "0")
7628                 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7629    (set (match_operand:SI 3 "register_operand" "=d")
7630         (mod:SI (match_dup 1) (match_dup 2)))
7631    (use (match_operand:SI 4 "register_operand" "3"))
7632    (clobber (reg:CC 17))]
7633   ""
7634   "idiv{l}\t%2"
7635   [(set_attr "type" "idiv")
7636    (set_attr "mode" "SI")
7637    (set_attr "ppro_uops" "few")])
7638
7639 (define_split
7640   [(set (match_operand:SI 0 "register_operand" "")
7641         (div:SI (match_operand:SI 1 "register_operand" "")
7642                 (match_operand:SI 2 "nonimmediate_operand" "")))
7643    (set (match_operand:SI 3 "register_operand" "")
7644         (mod:SI (match_dup 1) (match_dup 2)))
7645    (clobber (reg:CC 17))]
7646   "reload_completed"
7647   [(parallel [(set (match_dup 3)
7648                    (ashiftrt:SI (match_dup 4) (const_int 31)))
7649               (clobber (reg:CC 17))])
7650    (parallel [(set (match_dup 0)
7651                    (div:SI (reg:SI 0) (match_dup 2)))
7652               (set (match_dup 3)
7653                    (mod:SI (reg:SI 0) (match_dup 2)))
7654               (use (match_dup 3))
7655               (clobber (reg:CC 17))])]
7656 {
7657   /* Avoid use of cltd in favor of a mov+shift.  */
7658   if (!TARGET_USE_CLTD && !optimize_size)
7659     {
7660       if (true_regnum (operands[1]))
7661         emit_move_insn (operands[0], operands[1]);
7662       else
7663         emit_move_insn (operands[3], operands[1]);
7664       operands[4] = operands[3];
7665     }
7666   else
7667     {
7668       if (true_regnum (operands[1]))
7669         abort();
7670       operands[4] = operands[1];
7671     }
7672 })
7673 ;; %%% Split me.
7674 (define_insn "divmodhi4"
7675   [(set (match_operand:HI 0 "register_operand" "=a")
7676         (div:HI (match_operand:HI 1 "register_operand" "0")
7677                 (match_operand:HI 2 "nonimmediate_operand" "rm")))
7678    (set (match_operand:HI 3 "register_operand" "=&d")
7679         (mod:HI (match_dup 1) (match_dup 2)))
7680    (clobber (reg:CC 17))]
7681   "TARGET_HIMODE_MATH"
7682   "cwtd\;idiv{w}\t%2"
7683   [(set_attr "type" "multi")
7684    (set_attr "length_immediate" "0")
7685    (set_attr "mode" "SI")])
7686
7687 (define_insn "udivmoddi4"
7688   [(set (match_operand:DI 0 "register_operand" "=a")
7689         (udiv:DI (match_operand:DI 1 "register_operand" "0")
7690                  (match_operand:DI 2 "nonimmediate_operand" "rm")))
7691    (set (match_operand:DI 3 "register_operand" "=&d")
7692         (umod:DI (match_dup 1) (match_dup 2)))
7693    (clobber (reg:CC 17))]
7694   "TARGET_64BIT"
7695   "xor{q}\t%3, %3\;div{q}\t%2"
7696   [(set_attr "type" "multi")
7697    (set_attr "length_immediate" "0")
7698    (set_attr "mode" "DI")])
7699
7700 (define_insn "*udivmoddi4_noext"
7701   [(set (match_operand:DI 0 "register_operand" "=a")
7702         (udiv:DI (match_operand:DI 1 "register_operand" "0")
7703                  (match_operand:DI 2 "nonimmediate_operand" "rm")))
7704    (set (match_operand:DI 3 "register_operand" "=d")
7705         (umod:DI (match_dup 1) (match_dup 2)))
7706    (use (match_dup 3))
7707    (clobber (reg:CC 17))]
7708   "TARGET_64BIT"
7709   "div{q}\t%2"
7710   [(set_attr "type" "idiv")
7711    (set_attr "ppro_uops" "few")
7712    (set_attr "mode" "DI")])
7713
7714 (define_split
7715   [(set (match_operand:DI 0 "register_operand" "")
7716         (udiv:DI (match_operand:DI 1 "register_operand" "")
7717                  (match_operand:DI 2 "nonimmediate_operand" "")))
7718    (set (match_operand:DI 3 "register_operand" "")
7719         (umod:DI (match_dup 1) (match_dup 2)))
7720    (clobber (reg:CC 17))]
7721   "TARGET_64BIT && reload_completed"
7722   [(set (match_dup 3) (const_int 0))
7723    (parallel [(set (match_dup 0)
7724                    (udiv:DI (match_dup 1) (match_dup 2)))
7725               (set (match_dup 3)
7726                    (umod:DI (match_dup 1) (match_dup 2)))
7727               (use (match_dup 3))
7728               (clobber (reg:CC 17))])]
7729   "")
7730
7731 (define_insn "udivmodsi4"
7732   [(set (match_operand:SI 0 "register_operand" "=a")
7733         (udiv:SI (match_operand:SI 1 "register_operand" "0")
7734                  (match_operand:SI 2 "nonimmediate_operand" "rm")))
7735    (set (match_operand:SI 3 "register_operand" "=&d")
7736         (umod:SI (match_dup 1) (match_dup 2)))
7737    (clobber (reg:CC 17))]
7738   ""
7739   "xor{l}\t%3, %3\;div{l}\t%2"
7740   [(set_attr "type" "multi")
7741    (set_attr "length_immediate" "0")
7742    (set_attr "mode" "SI")])
7743
7744 (define_insn "*udivmodsi4_noext"
7745   [(set (match_operand:SI 0 "register_operand" "=a")
7746         (udiv:SI (match_operand:SI 1 "register_operand" "0")
7747                  (match_operand:SI 2 "nonimmediate_operand" "rm")))
7748    (set (match_operand:SI 3 "register_operand" "=d")
7749         (umod:SI (match_dup 1) (match_dup 2)))
7750    (use (match_dup 3))
7751    (clobber (reg:CC 17))]
7752   ""
7753   "div{l}\t%2"
7754   [(set_attr "type" "idiv")
7755    (set_attr "ppro_uops" "few")
7756    (set_attr "mode" "SI")])
7757
7758 (define_split
7759   [(set (match_operand:SI 0 "register_operand" "")
7760         (udiv:SI (match_operand:SI 1 "register_operand" "")
7761                  (match_operand:SI 2 "nonimmediate_operand" "")))
7762    (set (match_operand:SI 3 "register_operand" "")
7763         (umod:SI (match_dup 1) (match_dup 2)))
7764    (clobber (reg:CC 17))]
7765   "reload_completed"
7766   [(set (match_dup 3) (const_int 0))
7767    (parallel [(set (match_dup 0)
7768                    (udiv:SI (match_dup 1) (match_dup 2)))
7769               (set (match_dup 3)
7770                    (umod:SI (match_dup 1) (match_dup 2)))
7771               (use (match_dup 3))
7772               (clobber (reg:CC 17))])]
7773   "")
7774
7775 (define_expand "udivmodhi4"
7776   [(set (match_dup 4) (const_int 0))
7777    (parallel [(set (match_operand:HI 0 "register_operand" "")
7778                    (udiv:HI (match_operand:HI 1 "register_operand" "")
7779                             (match_operand:HI 2 "nonimmediate_operand" "")))
7780               (set (match_operand:HI 3 "register_operand" "")
7781                    (umod:HI (match_dup 1) (match_dup 2)))
7782               (use (match_dup 4))
7783               (clobber (reg:CC 17))])]
7784   "TARGET_HIMODE_MATH"
7785   "operands[4] = gen_reg_rtx (HImode);")
7786
7787 (define_insn "*udivmodhi_noext"
7788   [(set (match_operand:HI 0 "register_operand" "=a")
7789         (udiv:HI (match_operand:HI 1 "register_operand" "0")
7790                  (match_operand:HI 2 "nonimmediate_operand" "rm")))
7791    (set (match_operand:HI 3 "register_operand" "=d")
7792         (umod:HI (match_dup 1) (match_dup 2)))
7793    (use (match_operand:HI 4 "register_operand" "3"))
7794    (clobber (reg:CC 17))]
7795   ""
7796   "div{w}\t%2"
7797   [(set_attr "type" "idiv")
7798    (set_attr "mode" "HI")
7799    (set_attr "ppro_uops" "few")])
7800
7801 ;; We can not use div/idiv for double division, because it causes
7802 ;; "division by zero" on the overflow and that's not what we expect
7803 ;; from truncate.  Because true (non truncating) double division is
7804 ;; never generated, we can't create this insn anyway.
7805 ;
7806 ;(define_insn ""
7807 ;  [(set (match_operand:SI 0 "register_operand" "=a")
7808 ;       (truncate:SI
7809 ;         (udiv:DI (match_operand:DI 1 "register_operand" "A")
7810 ;                  (zero_extend:DI
7811 ;                    (match_operand:SI 2 "nonimmediate_operand" "rm")))))
7812 ;   (set (match_operand:SI 3 "register_operand" "=d")
7813 ;       (truncate:SI
7814 ;         (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
7815 ;   (clobber (reg:CC 17))]
7816 ;  ""
7817 ;  "div{l}\t{%2, %0|%0, %2}"
7818 ;  [(set_attr "type" "idiv")
7819 ;   (set_attr "ppro_uops" "few")])
7820 \f
7821 ;;- Logical AND instructions
7822
7823 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
7824 ;; Note that this excludes ah.
7825
7826 (define_insn "*testdi_1_rex64"
7827   [(set (reg 17)
7828         (compare
7829           (and:DI (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
7830                   (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
7831           (const_int 0)))]
7832   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7833    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7834   "@
7835    test{l}\t{%k1, %k0|%k0, %k1} 
7836    test{l}\t{%k1, %k0|%k0, %k1} 
7837    test{q}\t{%1, %0|%0, %1} 
7838    test{q}\t{%1, %0|%0, %1} 
7839    test{q}\t{%1, %0|%0, %1}"
7840   [(set_attr "type" "test")
7841    (set_attr "modrm" "0,1,0,1,1")
7842    (set_attr "mode" "SI,SI,DI,DI,DI")
7843    (set_attr "pent_pair" "uv,np,uv,np,uv")])
7844
7845 (define_insn "testsi_1"
7846   [(set (reg 17)
7847         (compare
7848           (and:SI (match_operand:SI 0 "nonimmediate_operand" "%!*a,r,rm")
7849                   (match_operand:SI 1 "general_operand" "in,in,rin"))
7850           (const_int 0)))]
7851   "ix86_match_ccmode (insn, CCNOmode)
7852    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7853   "test{l}\t{%1, %0|%0, %1}"
7854   [(set_attr "type" "test")
7855    (set_attr "modrm" "0,1,1")
7856    (set_attr "mode" "SI")
7857    (set_attr "pent_pair" "uv,np,uv")])
7858
7859 (define_expand "testsi_ccno_1"
7860   [(set (reg:CCNO 17)
7861         (compare:CCNO
7862           (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
7863                   (match_operand:SI 1 "nonmemory_operand" ""))
7864           (const_int 0)))]
7865   ""
7866   "")
7867
7868 (define_insn "*testhi_1"
7869   [(set (reg 17)
7870         (compare (and:HI (match_operand:HI 0 "nonimmediate_operand" "%!*a,r,rm")
7871                          (match_operand:HI 1 "general_operand" "n,n,rn"))
7872                  (const_int 0)))]
7873   "ix86_match_ccmode (insn, CCNOmode)
7874    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7875   "test{w}\t{%1, %0|%0, %1}"
7876   [(set_attr "type" "test")
7877    (set_attr "modrm" "0,1,1")
7878    (set_attr "mode" "HI")
7879    (set_attr "pent_pair" "uv,np,uv")])
7880
7881 (define_expand "testqi_ccz_1"
7882   [(set (reg:CCZ 17)
7883         (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
7884                              (match_operand:QI 1 "nonmemory_operand" ""))
7885                  (const_int 0)))]
7886   ""
7887   "")
7888
7889 (define_insn "*testqi_1_maybe_si"
7890   [(set (reg 17)
7891         (compare
7892           (and:QI
7893             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
7894             (match_operand:QI 1 "general_operand" "n,n,qn,n"))
7895           (const_int 0)))]
7896   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
7897    && ix86_match_ccmode (insn,
7898                          GET_CODE (operands[1]) == CONST_INT
7899                          && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
7900 {
7901   if (which_alternative == 3)
7902     {
7903       if (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) < 0)
7904         operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
7905       return "test{l}\t{%1, %k0|%k0, %1}";
7906     }
7907   return "test{b}\t{%1, %0|%0, %1}";
7908 }
7909   [(set_attr "type" "test")
7910    (set_attr "modrm" "0,1,1,1")
7911    (set_attr "mode" "QI,QI,QI,SI")
7912    (set_attr "pent_pair" "uv,np,uv,np")])
7913
7914 (define_insn "*testqi_1"
7915   [(set (reg 17)
7916         (compare
7917           (and:QI
7918             (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm")
7919             (match_operand:QI 1 "general_operand" "n,n,qn"))
7920           (const_int 0)))]
7921   "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
7922    && ix86_match_ccmode (insn, CCNOmode)"
7923   "test{b}\t{%1, %0|%0, %1}"
7924   [(set_attr "type" "test")
7925    (set_attr "modrm" "0,1,1")
7926    (set_attr "mode" "QI")
7927    (set_attr "pent_pair" "uv,np,uv")])
7928
7929 (define_expand "testqi_ext_ccno_0"
7930   [(set (reg:CCNO 17)
7931         (compare:CCNO
7932           (and:SI
7933             (zero_extract:SI
7934               (match_operand 0 "ext_register_operand" "")
7935               (const_int 8)
7936               (const_int 8))
7937             (match_operand 1 "const_int_operand" ""))
7938           (const_int 0)))]
7939   ""
7940   "")
7941
7942 (define_insn "*testqi_ext_0"
7943   [(set (reg 17)
7944         (compare
7945           (and:SI
7946             (zero_extract:SI
7947               (match_operand 0 "ext_register_operand" "Q")
7948               (const_int 8)
7949               (const_int 8))
7950             (match_operand 1 "const_int_operand" "n"))
7951           (const_int 0)))]
7952   "ix86_match_ccmode (insn, CCNOmode)"
7953   "test{b}\t{%1, %h0|%h0, %1}"
7954   [(set_attr "type" "test")
7955    (set_attr "mode" "QI")
7956    (set_attr "length_immediate" "1")
7957    (set_attr "pent_pair" "np")])
7958
7959 (define_insn "*testqi_ext_1"
7960   [(set (reg 17)
7961         (compare
7962           (and:SI
7963             (zero_extract:SI
7964               (match_operand 0 "ext_register_operand" "Q")
7965               (const_int 8)
7966               (const_int 8))
7967             (zero_extend:SI
7968               (match_operand:QI 1 "general_operand" "Qm")))
7969           (const_int 0)))]
7970   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7971    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7972   "test{b}\t{%1, %h0|%h0, %1}"
7973   [(set_attr "type" "test")
7974    (set_attr "mode" "QI")])
7975
7976 (define_insn "*testqi_ext_1_rex64"
7977   [(set (reg 17)
7978         (compare
7979           (and:SI
7980             (zero_extract:SI
7981               (match_operand 0 "ext_register_operand" "Q")
7982               (const_int 8)
7983               (const_int 8))
7984             (zero_extend:SI
7985               (match_operand:QI 1 "register_operand" "Q")))
7986           (const_int 0)))]
7987   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7988   "test{b}\t{%1, %h0|%h0, %1}"
7989   [(set_attr "type" "test")
7990    (set_attr "mode" "QI")])
7991
7992 (define_insn "*testqi_ext_2"
7993   [(set (reg 17)
7994         (compare
7995           (and:SI
7996             (zero_extract:SI
7997               (match_operand 0 "ext_register_operand" "Q")
7998               (const_int 8)
7999               (const_int 8))
8000             (zero_extract:SI
8001               (match_operand 1 "ext_register_operand" "Q")
8002               (const_int 8)
8003               (const_int 8)))
8004           (const_int 0)))]
8005   "ix86_match_ccmode (insn, CCNOmode)"
8006   "test{b}\t{%h1, %h0|%h0, %h1}"
8007   [(set_attr "type" "test")
8008    (set_attr "mode" "QI")])
8009
8010 ;; Combine likes to form bit extractions for some tests.  Humor it.
8011 (define_insn "*testqi_ext_3"
8012   [(set (reg 17)
8013         (compare (zero_extract:SI
8014                    (match_operand 0 "nonimmediate_operand" "rm")
8015                    (match_operand:SI 1 "const_int_operand" "")
8016                    (match_operand:SI 2 "const_int_operand" ""))
8017                  (const_int 0)))]
8018   "ix86_match_ccmode (insn, CCNOmode)
8019    && (GET_MODE (operands[0]) == SImode
8020        || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
8021        || GET_MODE (operands[0]) == HImode
8022        || GET_MODE (operands[0]) == QImode)"
8023   "#")
8024
8025 (define_insn "*testqi_ext_3_rex64"
8026   [(set (reg 17)
8027         (compare (zero_extract:DI
8028                    (match_operand 0 "nonimmediate_operand" "rm")
8029                    (match_operand:DI 1 "const_int_operand" "")
8030                    (match_operand:DI 2 "const_int_operand" ""))
8031                  (const_int 0)))]
8032   "TARGET_64BIT
8033    && ix86_match_ccmode (insn, CCNOmode)
8034    /* The code below cannot deal with constants outside HOST_WIDE_INT.  */
8035    && INTVAL (operands[1]) + INTVAL (operands[2]) < HOST_BITS_PER_WIDE_INT
8036    /* Ensure that resulting mask is zero or sign extended operand.  */
8037    && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
8038        || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
8039            && INTVAL (operands[1]) > 32))
8040    && (GET_MODE (operands[0]) == SImode
8041        || GET_MODE (operands[0]) == DImode
8042        || GET_MODE (operands[0]) == HImode
8043        || GET_MODE (operands[0]) == QImode)"
8044   "#")
8045
8046 (define_split
8047   [(set (match_operand 0 "flags_reg_operand" "")
8048         (match_operator 1 "compare_operator"
8049           [(zero_extract
8050              (match_operand 2 "nonimmediate_operand" "")
8051              (match_operand 3 "const_int_operand" "")
8052              (match_operand 4 "const_int_operand" ""))
8053            (const_int 0)]))]
8054   "ix86_match_ccmode (insn, CCNOmode)"
8055   [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
8056 {
8057   rtx val = operands[2];
8058   HOST_WIDE_INT len = INTVAL (operands[3]);
8059   HOST_WIDE_INT pos = INTVAL (operands[4]);
8060   HOST_WIDE_INT mask;
8061   enum machine_mode mode, submode;
8062
8063   mode = GET_MODE (val);
8064   if (GET_CODE (val) == MEM)
8065     {
8066       /* ??? Combine likes to put non-volatile mem extractions in QImode
8067          no matter the size of the test.  So find a mode that works.  */
8068       if (! MEM_VOLATILE_P (val))
8069         {
8070           mode = smallest_mode_for_size (pos + len, MODE_INT);
8071           val = adjust_address (val, mode, 0);
8072         }
8073     }
8074   else if (GET_CODE (val) == SUBREG
8075            && (submode = GET_MODE (SUBREG_REG (val)),
8076                GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
8077            && pos + len <= GET_MODE_BITSIZE (submode))
8078     {
8079       /* Narrow a paradoxical subreg to prevent partial register stalls.  */
8080       mode = submode;
8081       val = SUBREG_REG (val);
8082     }
8083   else if (mode == HImode && pos + len <= 8)
8084     {
8085       /* Small HImode tests can be converted to QImode.  */
8086       mode = QImode;
8087       val = gen_lowpart (QImode, val);
8088     }
8089
8090   mask  = ((HOST_WIDE_INT)1 << (pos + len)) - 1;
8091   mask &= ~(((HOST_WIDE_INT)1 << pos) - 1);
8092
8093   operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
8094 })
8095
8096 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
8097 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
8098 ;; this is relatively important trick.
8099 ;; Do the conversion only post-reload to avoid limiting of the register class
8100 ;; to QI regs.
8101 (define_split
8102   [(set (match_operand 0 "flags_reg_operand" "")
8103         (match_operator 1 "compare_operator"
8104           [(and (match_operand 2 "register_operand" "")
8105                 (match_operand 3 "const_int_operand" ""))
8106            (const_int 0)]))]
8107    "reload_completed
8108     && QI_REG_P (operands[2])
8109     && GET_MODE (operands[2]) != QImode
8110     && ((ix86_match_ccmode (insn, CCZmode)
8111          && !(INTVAL (operands[3]) & ~(255 << 8)))
8112         || (ix86_match_ccmode (insn, CCNOmode)
8113             && !(INTVAL (operands[3]) & ~(127 << 8))))"
8114   [(set (match_dup 0)
8115         (match_op_dup 1
8116           [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
8117                    (match_dup 3))
8118            (const_int 0)]))]
8119   "operands[2] = gen_lowpart (SImode, operands[2]);
8120    operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);")
8121
8122 (define_split
8123   [(set (match_operand 0 "flags_reg_operand" "")
8124         (match_operator 1 "compare_operator"
8125           [(and (match_operand 2 "nonimmediate_operand" "")
8126                 (match_operand 3 "const_int_operand" ""))
8127            (const_int 0)]))]
8128    "reload_completed
8129     && GET_MODE (operands[2]) != QImode
8130     && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
8131     && ((ix86_match_ccmode (insn, CCZmode)
8132          && !(INTVAL (operands[3]) & ~255))
8133         || (ix86_match_ccmode (insn, CCNOmode)
8134             && !(INTVAL (operands[3]) & ~127)))"
8135   [(set (match_dup 0)
8136         (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
8137                          (const_int 0)]))]
8138   "operands[2] = gen_lowpart (QImode, operands[2]);
8139    operands[3] = gen_lowpart (QImode, operands[3]);")
8140
8141
8142 ;; %%% This used to optimize known byte-wide and operations to memory,
8143 ;; and sometimes to QImode registers.  If this is considered useful,
8144 ;; it should be done with splitters.
8145
8146 (define_expand "anddi3"
8147   [(set (match_operand:DI 0 "nonimmediate_operand" "")
8148         (and:DI (match_operand:DI 1 "nonimmediate_operand" "")
8149                 (match_operand:DI 2 "x86_64_szext_general_operand" "")))
8150    (clobber (reg:CC 17))]
8151   "TARGET_64BIT"
8152   "ix86_expand_binary_operator (AND, DImode, operands); DONE;")
8153
8154 (define_insn "*anddi_1_rex64"
8155   [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
8156         (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
8157                 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
8158    (clobber (reg:CC 17))]
8159   "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
8160 {
8161   switch (get_attr_type (insn))
8162     {
8163     case TYPE_IMOVX:
8164       {
8165         enum machine_mode mode;
8166
8167         if (GET_CODE (operands[2]) != CONST_INT)
8168           abort ();
8169         if (INTVAL (operands[2]) == 0xff)
8170           mode = QImode;
8171         else if (INTVAL (operands[2]) == 0xffff)
8172           mode = HImode;
8173         else
8174           abort ();
8175         
8176         operands[1] = gen_lowpart (mode, operands[1]);
8177         if (mode == QImode)
8178           return "movz{bq|x}\t{%1,%0|%0, %1}";
8179         else
8180           return "movz{wq|x}\t{%1,%0|%0, %1}";
8181       }
8182
8183     default:
8184       if (! rtx_equal_p (operands[0], operands[1]))
8185         abort ();
8186       if (get_attr_mode (insn) == MODE_SI)
8187         return "and{l}\t{%k2, %k0|%k0, %k2}";
8188       else
8189         return "and{q}\t{%2, %0|%0, %2}";
8190     }
8191 }
8192   [(set_attr "type" "alu,alu,alu,imovx")
8193    (set_attr "length_immediate" "*,*,*,0")
8194    (set_attr "mode" "SI,DI,DI,DI")])
8195
8196 (define_insn "*anddi_2"
8197   [(set (reg 17)
8198         (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
8199                          (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
8200                  (const_int 0)))
8201    (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
8202         (and:DI (match_dup 1) (match_dup 2)))]
8203   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8204    && ix86_binary_operator_ok (AND, DImode, operands)"
8205   "@
8206    and{l}\t{%k2, %k0|%k0, %k2} 
8207    and{q}\t{%2, %0|%0, %2} 
8208    and{q}\t{%2, %0|%0, %2}"
8209   [(set_attr "type" "alu")
8210    (set_attr "mode" "SI,DI,DI")])
8211
8212 (define_expand "andsi3"
8213   [(set (match_operand:SI 0 "nonimmediate_operand" "")
8214         (and:SI (match_operand:SI 1 "nonimmediate_operand" "")
8215                 (match_operand:SI 2 "general_operand" "")))
8216    (clobber (reg:CC 17))]
8217   ""
8218   "ix86_expand_binary_operator (AND, SImode, operands); DONE;")
8219
8220 (define_insn "*andsi_1"
8221   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
8222         (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
8223                 (match_operand:SI 2 "general_operand" "ri,rm,L")))
8224    (clobber (reg:CC 17))]
8225   "ix86_binary_operator_ok (AND, SImode, operands)"
8226 {
8227   switch (get_attr_type (insn))
8228     {
8229     case TYPE_IMOVX:
8230       {
8231         enum machine_mode mode;
8232
8233         if (GET_CODE (operands[2]) != CONST_INT)
8234           abort ();
8235         if (INTVAL (operands[2]) == 0xff)
8236           mode = QImode;
8237         else if (INTVAL (operands[2]) == 0xffff)
8238           mode = HImode;
8239         else
8240           abort ();
8241         
8242         operands[1] = gen_lowpart (mode, operands[1]);
8243         if (mode == QImode)
8244           return "movz{bl|x}\t{%1,%0|%0, %1}";
8245         else
8246           return "movz{wl|x}\t{%1,%0|%0, %1}";
8247       }
8248
8249     default:
8250       if (! rtx_equal_p (operands[0], operands[1]))
8251         abort ();
8252       return "and{l}\t{%2, %0|%0, %2}";
8253     }
8254 }
8255   [(set_attr "type" "alu,alu,imovx")
8256    (set_attr "length_immediate" "*,*,0")
8257    (set_attr "mode" "SI")])
8258
8259 (define_split
8260   [(set (match_operand 0 "register_operand" "")
8261         (and (match_dup 0)
8262              (const_int -65536)))
8263    (clobber (reg:CC 17))]
8264   "optimize_size || (TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)"
8265   [(set (strict_low_part (match_dup 1)) (const_int 0))]
8266   "operands[1] = gen_lowpart (HImode, operands[0]);")
8267
8268 (define_split
8269   [(set (match_operand 0 "ext_register_operand" "")
8270         (and (match_dup 0)
8271              (const_int -256)))
8272    (clobber (reg:CC 17))]
8273   "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8274   [(set (strict_low_part (match_dup 1)) (const_int 0))]
8275   "operands[1] = gen_lowpart (QImode, operands[0]);")
8276
8277 (define_split
8278   [(set (match_operand 0 "ext_register_operand" "")
8279         (and (match_dup 0)
8280              (const_int -65281)))
8281    (clobber (reg:CC 17))]
8282   "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8283   [(parallel [(set (zero_extract:SI (match_dup 0)
8284                                     (const_int 8)
8285                                     (const_int 8))
8286                    (xor:SI 
8287                      (zero_extract:SI (match_dup 0)
8288                                       (const_int 8)
8289                                       (const_int 8))
8290                      (zero_extract:SI (match_dup 0)
8291                                       (const_int 8)
8292                                       (const_int 8))))
8293               (clobber (reg:CC 17))])]
8294   "operands[0] = gen_lowpart (SImode, operands[0]);")
8295
8296 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8297 (define_insn "*andsi_1_zext"
8298   [(set (match_operand:DI 0 "register_operand" "=r")
8299         (zero_extend:DI
8300           (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8301                   (match_operand:SI 2 "general_operand" "rim"))))
8302    (clobber (reg:CC 17))]
8303   "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
8304   "and{l}\t{%2, %k0|%k0, %2}"
8305   [(set_attr "type" "alu")
8306    (set_attr "mode" "SI")])
8307
8308 (define_insn "*andsi_2"
8309   [(set (reg 17)
8310         (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8311                          (match_operand:SI 2 "general_operand" "rim,ri"))
8312                  (const_int 0)))
8313    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8314         (and:SI (match_dup 1) (match_dup 2)))]
8315   "ix86_match_ccmode (insn, CCNOmode)
8316    && ix86_binary_operator_ok (AND, SImode, operands)"
8317   "and{l}\t{%2, %0|%0, %2}"
8318   [(set_attr "type" "alu")
8319    (set_attr "mode" "SI")])
8320
8321 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8322 (define_insn "*andsi_2_zext"
8323   [(set (reg 17)
8324         (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8325                          (match_operand:SI 2 "general_operand" "rim"))
8326                  (const_int 0)))
8327    (set (match_operand:DI 0 "register_operand" "=r")
8328         (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
8329   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8330    && ix86_binary_operator_ok (AND, SImode, operands)"
8331   "and{l}\t{%2, %k0|%k0, %2}"
8332   [(set_attr "type" "alu")
8333    (set_attr "mode" "SI")])
8334
8335 (define_expand "andhi3"
8336   [(set (match_operand:HI 0 "nonimmediate_operand" "")
8337         (and:HI (match_operand:HI 1 "nonimmediate_operand" "")
8338                 (match_operand:HI 2 "general_operand" "")))
8339    (clobber (reg:CC 17))]
8340   "TARGET_HIMODE_MATH"
8341   "ix86_expand_binary_operator (AND, HImode, operands); DONE;")
8342
8343 (define_insn "*andhi_1"
8344   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
8345         (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
8346                 (match_operand:HI 2 "general_operand" "ri,rm,L")))
8347    (clobber (reg:CC 17))]
8348   "ix86_binary_operator_ok (AND, HImode, operands)"
8349 {
8350   switch (get_attr_type (insn))
8351     {
8352     case TYPE_IMOVX:
8353       if (GET_CODE (operands[2]) != CONST_INT)
8354         abort ();
8355       if (INTVAL (operands[2]) == 0xff)
8356         return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
8357       abort ();
8358
8359     default:
8360       if (! rtx_equal_p (operands[0], operands[1]))
8361         abort ();
8362
8363       return "and{w}\t{%2, %0|%0, %2}";
8364     }
8365 }
8366   [(set_attr "type" "alu,alu,imovx")
8367    (set_attr "length_immediate" "*,*,0")
8368    (set_attr "mode" "HI,HI,SI")])
8369
8370 (define_insn "*andhi_2"
8371   [(set (reg 17)
8372         (compare (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8373                          (match_operand:HI 2 "general_operand" "rim,ri"))
8374                  (const_int 0)))
8375    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8376         (and:HI (match_dup 1) (match_dup 2)))]
8377   "ix86_match_ccmode (insn, CCNOmode)
8378    && ix86_binary_operator_ok (AND, HImode, operands)"
8379   "and{w}\t{%2, %0|%0, %2}"
8380   [(set_attr "type" "alu")
8381    (set_attr "mode" "HI")])
8382
8383 (define_expand "andqi3"
8384   [(set (match_operand:QI 0 "nonimmediate_operand" "")
8385         (and:QI (match_operand:QI 1 "nonimmediate_operand" "")
8386                 (match_operand:QI 2 "general_operand" "")))
8387    (clobber (reg:CC 17))]
8388   "TARGET_QIMODE_MATH"
8389   "ix86_expand_binary_operator (AND, QImode, operands); DONE;")
8390
8391 ;; %%% Potential partial reg stall on alternative 2.  What to do?
8392 (define_insn "*andqi_1"
8393   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
8394         (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8395                 (match_operand:QI 2 "general_operand" "qi,qmi,ri")))
8396    (clobber (reg:CC 17))]
8397   "ix86_binary_operator_ok (AND, QImode, operands)"
8398   "@
8399    and{b}\t{%2, %0|%0, %2}
8400    and{b}\t{%2, %0|%0, %2}
8401    and{l}\t{%k2, %k0|%k0, %k2}"
8402   [(set_attr "type" "alu")
8403    (set_attr "mode" "QI,QI,SI")])
8404
8405 (define_insn "*andqi_1_slp"
8406   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
8407         (and:QI (match_dup 0)
8408                 (match_operand:QI 1 "general_operand" "qi,qmi")))
8409    (clobber (reg:CC 17))]
8410   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8411    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8412   "and{b}\t{%1, %0|%0, %1}"
8413   [(set_attr "type" "alu1")
8414    (set_attr "mode" "QI")])
8415
8416 (define_insn "*andqi_2_maybe_si"
8417   [(set (reg 17)
8418         (compare (and:QI
8419                       (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8420                       (match_operand:QI 2 "general_operand" "qim,qi,i"))
8421                  (const_int 0)))
8422    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
8423         (and:QI (match_dup 1) (match_dup 2)))]
8424   "ix86_binary_operator_ok (AND, QImode, operands)
8425    && ix86_match_ccmode (insn,
8426                          GET_CODE (operands[2]) == CONST_INT
8427                          && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
8428 {
8429   if (which_alternative == 2)
8430     {
8431       if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
8432         operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
8433       return "and{l}\t{%2, %k0|%k0, %2}";
8434     }
8435   return "and{b}\t{%2, %0|%0, %2}";
8436 }
8437   [(set_attr "type" "alu")
8438    (set_attr "mode" "QI,QI,SI")])
8439
8440 (define_insn "*andqi_2"
8441   [(set (reg 17)
8442         (compare (and:QI
8443                    (match_operand:QI 1 "nonimmediate_operand" "%0,0")
8444                    (match_operand:QI 2 "general_operand" "qim,qi"))
8445                  (const_int 0)))
8446    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
8447         (and:QI (match_dup 1) (match_dup 2)))]
8448   "ix86_match_ccmode (insn, CCNOmode)
8449    && ix86_binary_operator_ok (AND, QImode, operands)"
8450   "and{b}\t{%2, %0|%0, %2}"
8451   [(set_attr "type" "alu")
8452    (set_attr "mode" "QI")])
8453
8454 (define_insn "*andqi_2_slp"
8455   [(set (reg 17)
8456         (compare (and:QI
8457                    (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8458                    (match_operand:QI 1 "nonimmediate_operand" "qmi,qi"))
8459                  (const_int 0)))
8460    (set (strict_low_part (match_dup 0))
8461         (and:QI (match_dup 0) (match_dup 1)))]
8462   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8463    && ix86_match_ccmode (insn, CCNOmode)
8464    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8465   "and{b}\t{%1, %0|%0, %1}"
8466   [(set_attr "type" "alu1")
8467    (set_attr "mode" "QI")])
8468
8469 ;; ??? A bug in recog prevents it from recognizing a const_int as an
8470 ;; operand to zero_extend in andqi_ext_1.  It was checking explicitly
8471 ;; for a QImode operand, which of course failed.
8472
8473 (define_insn "andqi_ext_0"
8474   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8475                          (const_int 8)
8476                          (const_int 8))
8477         (and:SI 
8478           (zero_extract:SI
8479             (match_operand 1 "ext_register_operand" "0")
8480             (const_int 8)
8481             (const_int 8))
8482           (match_operand 2 "const_int_operand" "n")))
8483    (clobber (reg:CC 17))]
8484   ""
8485   "and{b}\t{%2, %h0|%h0, %2}"
8486   [(set_attr "type" "alu")
8487    (set_attr "length_immediate" "1")
8488    (set_attr "mode" "QI")])
8489
8490 ;; Generated by peephole translating test to and.  This shows up
8491 ;; often in fp comparisons.
8492
8493 (define_insn "*andqi_ext_0_cc"
8494   [(set (reg 17)
8495         (compare
8496           (and:SI
8497             (zero_extract:SI
8498               (match_operand 1 "ext_register_operand" "0")
8499               (const_int 8)
8500               (const_int 8))
8501             (match_operand 2 "const_int_operand" "n"))
8502           (const_int 0)))
8503    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8504                          (const_int 8)
8505                          (const_int 8))
8506         (and:SI 
8507           (zero_extract:SI
8508             (match_dup 1)
8509             (const_int 8)
8510             (const_int 8))
8511           (match_dup 2)))]
8512   "ix86_match_ccmode (insn, CCNOmode)"
8513   "and{b}\t{%2, %h0|%h0, %2}"
8514   [(set_attr "type" "alu")
8515    (set_attr "length_immediate" "1")
8516    (set_attr "mode" "QI")])
8517
8518 (define_insn "*andqi_ext_1"
8519   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8520                          (const_int 8)
8521                          (const_int 8))
8522         (and:SI 
8523           (zero_extract:SI
8524             (match_operand 1 "ext_register_operand" "0")
8525             (const_int 8)
8526             (const_int 8))
8527           (zero_extend:SI
8528             (match_operand:QI 2 "general_operand" "Qm"))))
8529    (clobber (reg:CC 17))]
8530   "!TARGET_64BIT"
8531   "and{b}\t{%2, %h0|%h0, %2}"
8532   [(set_attr "type" "alu")
8533    (set_attr "length_immediate" "0")
8534    (set_attr "mode" "QI")])
8535
8536 (define_insn "*andqi_ext_1_rex64"
8537   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8538                          (const_int 8)
8539                          (const_int 8))
8540         (and:SI 
8541           (zero_extract:SI
8542             (match_operand 1 "ext_register_operand" "0")
8543             (const_int 8)
8544             (const_int 8))
8545           (zero_extend:SI
8546             (match_operand 2 "ext_register_operand" "Q"))))
8547    (clobber (reg:CC 17))]
8548   "TARGET_64BIT"
8549   "and{b}\t{%2, %h0|%h0, %2}"
8550   [(set_attr "type" "alu")
8551    (set_attr "length_immediate" "0")
8552    (set_attr "mode" "QI")])
8553
8554 (define_insn "*andqi_ext_2"
8555   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8556                          (const_int 8)
8557                          (const_int 8))
8558         (and:SI
8559           (zero_extract:SI
8560             (match_operand 1 "ext_register_operand" "%0")
8561             (const_int 8)
8562             (const_int 8))
8563           (zero_extract:SI
8564             (match_operand 2 "ext_register_operand" "Q")
8565             (const_int 8)
8566             (const_int 8))))
8567    (clobber (reg:CC 17))]
8568   ""
8569   "and{b}\t{%h2, %h0|%h0, %h2}"
8570   [(set_attr "type" "alu")
8571    (set_attr "length_immediate" "0")
8572    (set_attr "mode" "QI")])
8573
8574 ;; Convert wide AND instructions with immediate operand to shorter QImode
8575 ;; equivalents when possible.
8576 ;; Don't do the splitting with memory operands, since it introduces risk
8577 ;; of memory mismatch stalls.  We may want to do the splitting for optimizing
8578 ;; for size, but that can (should?) be handled by generic code instead.
8579 (define_split
8580   [(set (match_operand 0 "register_operand" "")
8581         (and (match_operand 1 "register_operand" "")
8582              (match_operand 2 "const_int_operand" "")))
8583    (clobber (reg:CC 17))]
8584    "reload_completed
8585     && QI_REG_P (operands[0])
8586     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8587     && !(~INTVAL (operands[2]) & ~(255 << 8))
8588     && GET_MODE (operands[0]) != QImode"
8589   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8590                    (and:SI (zero_extract:SI (match_dup 1)
8591                                             (const_int 8) (const_int 8))
8592                            (match_dup 2)))
8593               (clobber (reg:CC 17))])]
8594   "operands[0] = gen_lowpart (SImode, operands[0]);
8595    operands[1] = gen_lowpart (SImode, operands[1]);
8596    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8597
8598 ;; Since AND can be encoded with sign extended immediate, this is only
8599 ;; profitable when 7th bit is not set.
8600 (define_split
8601   [(set (match_operand 0 "register_operand" "")
8602         (and (match_operand 1 "general_operand" "")
8603              (match_operand 2 "const_int_operand" "")))
8604    (clobber (reg:CC 17))]
8605    "reload_completed
8606     && ANY_QI_REG_P (operands[0])
8607     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8608     && !(~INTVAL (operands[2]) & ~255)
8609     && !(INTVAL (operands[2]) & 128)
8610     && GET_MODE (operands[0]) != QImode"
8611   [(parallel [(set (strict_low_part (match_dup 0))
8612                    (and:QI (match_dup 1)
8613                            (match_dup 2)))
8614               (clobber (reg:CC 17))])]
8615   "operands[0] = gen_lowpart (QImode, operands[0]);
8616    operands[1] = gen_lowpart (QImode, operands[1]);
8617    operands[2] = gen_lowpart (QImode, operands[2]);")
8618 \f
8619 ;; Logical inclusive OR instructions
8620
8621 ;; %%% This used to optimize known byte-wide and operations to memory.
8622 ;; If this is considered useful, it should be done with splitters.
8623
8624 (define_expand "iordi3"
8625   [(set (match_operand:DI 0 "nonimmediate_operand" "")
8626         (ior:DI (match_operand:DI 1 "nonimmediate_operand" "")
8627                 (match_operand:DI 2 "x86_64_general_operand" "")))
8628    (clobber (reg:CC 17))]
8629   "TARGET_64BIT"
8630   "ix86_expand_binary_operator (IOR, DImode, operands); DONE;")
8631
8632 (define_insn "*iordi_1_rex64"
8633   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
8634         (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8635                 (match_operand:DI 2 "x86_64_general_operand" "re,rme")))
8636    (clobber (reg:CC 17))]
8637   "TARGET_64BIT
8638    && ix86_binary_operator_ok (IOR, DImode, operands)"
8639   "or{q}\t{%2, %0|%0, %2}"
8640   [(set_attr "type" "alu")
8641    (set_attr "mode" "DI")])
8642
8643 (define_insn "*iordi_2_rex64"
8644   [(set (reg 17)
8645         (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8646                          (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
8647                  (const_int 0)))
8648    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
8649         (ior:DI (match_dup 1) (match_dup 2)))]
8650   "TARGET_64BIT
8651    && ix86_match_ccmode (insn, CCNOmode)
8652    && ix86_binary_operator_ok (IOR, DImode, operands)"
8653   "or{q}\t{%2, %0|%0, %2}"
8654   [(set_attr "type" "alu")
8655    (set_attr "mode" "DI")])
8656
8657 (define_insn "*iordi_3_rex64"
8658   [(set (reg 17)
8659         (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
8660                          (match_operand:DI 2 "x86_64_general_operand" "rem"))
8661                  (const_int 0)))
8662    (clobber (match_scratch:DI 0 "=r"))]
8663   "TARGET_64BIT
8664    && ix86_match_ccmode (insn, CCNOmode)
8665    && ix86_binary_operator_ok (IOR, DImode, operands)"
8666   "or{q}\t{%2, %0|%0, %2}"
8667   [(set_attr "type" "alu")
8668    (set_attr "mode" "DI")])
8669
8670
8671 (define_expand "iorsi3"
8672   [(set (match_operand:SI 0 "nonimmediate_operand" "")
8673         (ior:SI (match_operand:SI 1 "nonimmediate_operand" "")
8674                 (match_operand:SI 2 "general_operand" "")))
8675    (clobber (reg:CC 17))]
8676   ""
8677   "ix86_expand_binary_operator (IOR, SImode, operands); DONE;")
8678
8679 (define_insn "*iorsi_1"
8680   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
8681         (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8682                 (match_operand:SI 2 "general_operand" "ri,rmi")))
8683    (clobber (reg:CC 17))]
8684   "ix86_binary_operator_ok (IOR, SImode, operands)"
8685   "or{l}\t{%2, %0|%0, %2}"
8686   [(set_attr "type" "alu")
8687    (set_attr "mode" "SI")])
8688
8689 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8690 (define_insn "*iorsi_1_zext"
8691   [(set (match_operand:DI 0 "register_operand" "=rm")
8692         (zero_extend:DI
8693           (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8694                   (match_operand:SI 2 "general_operand" "rim"))))
8695    (clobber (reg:CC 17))]
8696   "TARGET_64BIT && ix86_binary_operator_ok (IOR, SImode, operands)"
8697   "or{l}\t{%2, %k0|%k0, %2}"
8698   [(set_attr "type" "alu")
8699    (set_attr "mode" "SI")])
8700
8701 (define_insn "*iorsi_1_zext_imm"
8702   [(set (match_operand:DI 0 "register_operand" "=rm")
8703         (ior:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8704                 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8705    (clobber (reg:CC 17))]
8706   "TARGET_64BIT"
8707   "or{l}\t{%2, %k0|%k0, %2}"
8708   [(set_attr "type" "alu")
8709    (set_attr "mode" "SI")])
8710
8711 (define_insn "*iorsi_2"
8712   [(set (reg 17)
8713         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8714                          (match_operand:SI 2 "general_operand" "rim,ri"))
8715                  (const_int 0)))
8716    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8717         (ior:SI (match_dup 1) (match_dup 2)))]
8718   "ix86_match_ccmode (insn, CCNOmode)
8719    && ix86_binary_operator_ok (IOR, SImode, operands)"
8720   "or{l}\t{%2, %0|%0, %2}"
8721   [(set_attr "type" "alu")
8722    (set_attr "mode" "SI")])
8723
8724 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8725 ;; ??? Special case for immediate operand is missing - it is tricky.
8726 (define_insn "*iorsi_2_zext"
8727   [(set (reg 17)
8728         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8729                          (match_operand:SI 2 "general_operand" "rim"))
8730                  (const_int 0)))
8731    (set (match_operand:DI 0 "register_operand" "=r")
8732         (zero_extend:DI (ior:SI (match_dup 1) (match_dup 2))))]
8733   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8734    && ix86_binary_operator_ok (IOR, SImode, operands)"
8735   "or{l}\t{%2, %k0|%k0, %2}"
8736   [(set_attr "type" "alu")
8737    (set_attr "mode" "SI")])
8738
8739 (define_insn "*iorsi_2_zext_imm"
8740   [(set (reg 17)
8741         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8742                          (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
8743                  (const_int 0)))
8744    (set (match_operand:DI 0 "register_operand" "=r")
8745         (ior:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8746   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8747    && ix86_binary_operator_ok (IOR, SImode, operands)"
8748   "or{l}\t{%2, %k0|%k0, %2}"
8749   [(set_attr "type" "alu")
8750    (set_attr "mode" "SI")])
8751
8752 (define_insn "*iorsi_3"
8753   [(set (reg 17)
8754         (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8755                          (match_operand:SI 2 "general_operand" "rim"))
8756                  (const_int 0)))
8757    (clobber (match_scratch:SI 0 "=r"))]
8758   "ix86_match_ccmode (insn, CCNOmode)
8759    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8760   "or{l}\t{%2, %0|%0, %2}"
8761   [(set_attr "type" "alu")
8762    (set_attr "mode" "SI")])
8763
8764 (define_expand "iorhi3"
8765   [(set (match_operand:HI 0 "nonimmediate_operand" "")
8766         (ior:HI (match_operand:HI 1 "nonimmediate_operand" "")
8767                 (match_operand:HI 2 "general_operand" "")))
8768    (clobber (reg:CC 17))]
8769   "TARGET_HIMODE_MATH"
8770   "ix86_expand_binary_operator (IOR, HImode, operands); DONE;")
8771
8772 (define_insn "*iorhi_1"
8773   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
8774         (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8775                 (match_operand:HI 2 "general_operand" "rmi,ri")))
8776    (clobber (reg:CC 17))]
8777   "ix86_binary_operator_ok (IOR, HImode, operands)"
8778   "or{w}\t{%2, %0|%0, %2}"
8779   [(set_attr "type" "alu")
8780    (set_attr "mode" "HI")])
8781
8782 (define_insn "*iorhi_2"
8783   [(set (reg 17)
8784         (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8785                          (match_operand:HI 2 "general_operand" "rim,ri"))
8786                  (const_int 0)))
8787    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8788         (ior:HI (match_dup 1) (match_dup 2)))]
8789   "ix86_match_ccmode (insn, CCNOmode)
8790    && ix86_binary_operator_ok (IOR, HImode, operands)"
8791   "or{w}\t{%2, %0|%0, %2}"
8792   [(set_attr "type" "alu")
8793    (set_attr "mode" "HI")])
8794
8795 (define_insn "*iorhi_3"
8796   [(set (reg 17)
8797         (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
8798                          (match_operand:HI 2 "general_operand" "rim"))
8799                  (const_int 0)))
8800    (clobber (match_scratch:HI 0 "=r"))]
8801   "ix86_match_ccmode (insn, CCNOmode)
8802    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8803   "or{w}\t{%2, %0|%0, %2}"
8804   [(set_attr "type" "alu")
8805    (set_attr "mode" "HI")])
8806
8807 (define_expand "iorqi3"
8808   [(set (match_operand:QI 0 "nonimmediate_operand" "")
8809         (ior:QI (match_operand:QI 1 "nonimmediate_operand" "")
8810                 (match_operand:QI 2 "general_operand" "")))
8811    (clobber (reg:CC 17))]
8812   "TARGET_QIMODE_MATH"
8813   "ix86_expand_binary_operator (IOR, QImode, operands); DONE;")
8814
8815 ;; %%% Potential partial reg stall on alternative 2.  What to do?
8816 (define_insn "*iorqi_1"
8817   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
8818         (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8819                 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
8820    (clobber (reg:CC 17))]
8821   "ix86_binary_operator_ok (IOR, QImode, operands)"
8822   "@
8823    or{b}\t{%2, %0|%0, %2}
8824    or{b}\t{%2, %0|%0, %2}
8825    or{l}\t{%k2, %k0|%k0, %k2}"
8826   [(set_attr "type" "alu")
8827    (set_attr "mode" "QI,QI,SI")])
8828
8829 (define_insn "*iorqi_1_slp"
8830   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
8831         (ior:QI (match_dup 0)
8832                 (match_operand:QI 1 "general_operand" "qmi,qi")))
8833    (clobber (reg:CC 17))]
8834   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8835    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8836   "or{b}\t{%1, %0|%0, %1}"
8837   [(set_attr "type" "alu1")
8838    (set_attr "mode" "QI")])
8839
8840 (define_insn "*iorqi_2"
8841   [(set (reg 17)
8842         (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
8843                          (match_operand:QI 2 "general_operand" "qim,qi"))
8844                  (const_int 0)))
8845    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
8846         (ior:QI (match_dup 1) (match_dup 2)))]
8847   "ix86_match_ccmode (insn, CCNOmode)
8848    && ix86_binary_operator_ok (IOR, QImode, operands)"
8849   "or{b}\t{%2, %0|%0, %2}"
8850   [(set_attr "type" "alu")
8851    (set_attr "mode" "QI")])
8852
8853 (define_insn "*iorqi_2_slp"
8854   [(set (reg 17)
8855         (compare (ior:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8856                          (match_operand:QI 1 "general_operand" "qim,qi"))
8857                  (const_int 0)))
8858    (set (strict_low_part (match_dup 0))
8859         (ior:QI (match_dup 0) (match_dup 1)))]
8860   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8861    && ix86_match_ccmode (insn, CCNOmode)
8862    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8863   "or{b}\t{%1, %0|%0, %1}"
8864   [(set_attr "type" "alu1")
8865    (set_attr "mode" "QI")])
8866
8867 (define_insn "*iorqi_3"
8868   [(set (reg 17)
8869         (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
8870                          (match_operand:QI 2 "general_operand" "qim"))
8871                  (const_int 0)))
8872    (clobber (match_scratch:QI 0 "=q"))]
8873   "ix86_match_ccmode (insn, CCNOmode)
8874    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8875   "or{b}\t{%2, %0|%0, %2}"
8876   [(set_attr "type" "alu")
8877    (set_attr "mode" "QI")])
8878
8879 (define_insn "iorqi_ext_0"
8880   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8881                          (const_int 8)
8882                          (const_int 8))
8883         (ior:SI 
8884           (zero_extract:SI
8885             (match_operand 1 "ext_register_operand" "0")
8886             (const_int 8)
8887             (const_int 8))
8888           (match_operand 2 "const_int_operand" "n")))
8889    (clobber (reg:CC 17))]
8890   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8891   "or{b}\t{%2, %h0|%h0, %2}"
8892   [(set_attr "type" "alu")
8893    (set_attr "length_immediate" "1")
8894    (set_attr "mode" "QI")])
8895
8896 (define_insn "*iorqi_ext_1"
8897   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8898                          (const_int 8)
8899                          (const_int 8))
8900         (ior:SI 
8901           (zero_extract:SI
8902             (match_operand 1 "ext_register_operand" "0")
8903             (const_int 8)
8904             (const_int 8))
8905           (zero_extend:SI
8906             (match_operand:QI 2 "general_operand" "Qm"))))
8907    (clobber (reg:CC 17))]
8908   "!TARGET_64BIT
8909    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
8910   "or{b}\t{%2, %h0|%h0, %2}"
8911   [(set_attr "type" "alu")
8912    (set_attr "length_immediate" "0")
8913    (set_attr "mode" "QI")])
8914
8915 (define_insn "*iorqi_ext_1_rex64"
8916   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8917                          (const_int 8)
8918                          (const_int 8))
8919         (ior:SI 
8920           (zero_extract:SI
8921             (match_operand 1 "ext_register_operand" "0")
8922             (const_int 8)
8923             (const_int 8))
8924           (zero_extend:SI
8925             (match_operand 2 "ext_register_operand" "Q"))))
8926    (clobber (reg:CC 17))]
8927   "TARGET_64BIT
8928    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
8929   "or{b}\t{%2, %h0|%h0, %2}"
8930   [(set_attr "type" "alu")
8931    (set_attr "length_immediate" "0")
8932    (set_attr "mode" "QI")])
8933
8934 (define_insn "*iorqi_ext_2"
8935   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8936                          (const_int 8)
8937                          (const_int 8))
8938         (ior:SI 
8939           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
8940                            (const_int 8)
8941                            (const_int 8))
8942           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
8943                            (const_int 8)
8944                            (const_int 8))))
8945    (clobber (reg:CC 17))]
8946   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8947   "ior{b}\t{%h2, %h0|%h0, %h2}"
8948   [(set_attr "type" "alu")
8949    (set_attr "length_immediate" "0")
8950    (set_attr "mode" "QI")])
8951
8952 (define_split
8953   [(set (match_operand 0 "register_operand" "")
8954         (ior (match_operand 1 "register_operand" "")
8955              (match_operand 2 "const_int_operand" "")))
8956    (clobber (reg:CC 17))]
8957    "reload_completed
8958     && QI_REG_P (operands[0])
8959     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8960     && !(INTVAL (operands[2]) & ~(255 << 8))
8961     && GET_MODE (operands[0]) != QImode"
8962   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8963                    (ior:SI (zero_extract:SI (match_dup 1)
8964                                             (const_int 8) (const_int 8))
8965                            (match_dup 2)))
8966               (clobber (reg:CC 17))])]
8967   "operands[0] = gen_lowpart (SImode, operands[0]);
8968    operands[1] = gen_lowpart (SImode, operands[1]);
8969    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8970
8971 ;; Since OR can be encoded with sign extended immediate, this is only
8972 ;; profitable when 7th bit is set.
8973 (define_split
8974   [(set (match_operand 0 "register_operand" "")
8975         (ior (match_operand 1 "general_operand" "")
8976              (match_operand 2 "const_int_operand" "")))
8977    (clobber (reg:CC 17))]
8978    "reload_completed
8979     && ANY_QI_REG_P (operands[0])
8980     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8981     && !(INTVAL (operands[2]) & ~255)
8982     && (INTVAL (operands[2]) & 128)
8983     && GET_MODE (operands[0]) != QImode"
8984   [(parallel [(set (strict_low_part (match_dup 0))
8985                    (ior:QI (match_dup 1)
8986                            (match_dup 2)))
8987               (clobber (reg:CC 17))])]
8988   "operands[0] = gen_lowpart (QImode, operands[0]);
8989    operands[1] = gen_lowpart (QImode, operands[1]);
8990    operands[2] = gen_lowpart (QImode, operands[2]);")
8991 \f
8992 ;; Logical XOR instructions
8993
8994 ;; %%% This used to optimize known byte-wide and operations to memory.
8995 ;; If this is considered useful, it should be done with splitters.
8996
8997 (define_expand "xordi3"
8998   [(set (match_operand:DI 0 "nonimmediate_operand" "")
8999         (xor:DI (match_operand:DI 1 "nonimmediate_operand" "")
9000                 (match_operand:DI 2 "x86_64_general_operand" "")))
9001    (clobber (reg:CC 17))]
9002   "TARGET_64BIT"
9003   "ix86_expand_binary_operator (XOR, DImode, operands); DONE;")
9004
9005 (define_insn "*xordi_1_rex64"
9006   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
9007         (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9008                 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
9009    (clobber (reg:CC 17))]
9010   "TARGET_64BIT
9011    && ix86_binary_operator_ok (XOR, DImode, operands)"
9012   "@
9013    xor{q}\t{%2, %0|%0, %2} 
9014    xor{q}\t{%2, %0|%0, %2}"
9015   [(set_attr "type" "alu")
9016    (set_attr "mode" "DI,DI")])
9017
9018 (define_insn "*xordi_2_rex64"
9019   [(set (reg 17)
9020         (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
9021                          (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
9022                  (const_int 0)))
9023    (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
9024         (xor:DI (match_dup 1) (match_dup 2)))]
9025   "TARGET_64BIT
9026    && ix86_match_ccmode (insn, CCNOmode)
9027    && ix86_binary_operator_ok (XOR, DImode, operands)"
9028   "@
9029    xor{q}\t{%2, %0|%0, %2} 
9030    xor{q}\t{%2, %0|%0, %2}"
9031   [(set_attr "type" "alu")
9032    (set_attr "mode" "DI,DI")])
9033
9034 (define_insn "*xordi_3_rex64"
9035   [(set (reg 17)
9036         (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
9037                          (match_operand:DI 2 "x86_64_general_operand" "rem"))
9038                  (const_int 0)))
9039    (clobber (match_scratch:DI 0 "=r"))]
9040   "TARGET_64BIT
9041    && ix86_match_ccmode (insn, CCNOmode)
9042    && ix86_binary_operator_ok (XOR, DImode, operands)"
9043   "xor{q}\t{%2, %0|%0, %2}"
9044   [(set_attr "type" "alu")
9045    (set_attr "mode" "DI")])
9046
9047 (define_expand "xorsi3"
9048   [(set (match_operand:SI 0 "nonimmediate_operand" "")
9049         (xor:SI (match_operand:SI 1 "nonimmediate_operand" "")
9050                 (match_operand:SI 2 "general_operand" "")))
9051    (clobber (reg:CC 17))]
9052   ""
9053   "ix86_expand_binary_operator (XOR, SImode, operands); DONE;")
9054
9055 (define_insn "*xorsi_1"
9056   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
9057         (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9058                 (match_operand:SI 2 "general_operand" "ri,rm")))
9059    (clobber (reg:CC 17))]
9060   "ix86_binary_operator_ok (XOR, SImode, operands)"
9061   "xor{l}\t{%2, %0|%0, %2}"
9062   [(set_attr "type" "alu")
9063    (set_attr "mode" "SI")])
9064
9065 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9066 ;; Add speccase for immediates
9067 (define_insn "*xorsi_1_zext"
9068   [(set (match_operand:DI 0 "register_operand" "=r")
9069         (zero_extend:DI
9070           (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9071                   (match_operand:SI 2 "general_operand" "rim"))))
9072    (clobber (reg:CC 17))]
9073   "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
9074   "xor{l}\t{%2, %k0|%k0, %2}"
9075   [(set_attr "type" "alu")
9076    (set_attr "mode" "SI")])
9077
9078 (define_insn "*xorsi_1_zext_imm"
9079   [(set (match_operand:DI 0 "register_operand" "=r")
9080         (xor:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
9081                 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
9082    (clobber (reg:CC 17))]
9083   "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
9084   "xor{l}\t{%2, %k0|%k0, %2}"
9085   [(set_attr "type" "alu")
9086    (set_attr "mode" "SI")])
9087
9088 (define_insn "*xorsi_2"
9089   [(set (reg 17)
9090         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
9091                          (match_operand:SI 2 "general_operand" "rim,ri"))
9092                  (const_int 0)))
9093    (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
9094         (xor:SI (match_dup 1) (match_dup 2)))]
9095   "ix86_match_ccmode (insn, CCNOmode)
9096    && ix86_binary_operator_ok (XOR, SImode, operands)"
9097   "xor{l}\t{%2, %0|%0, %2}"
9098   [(set_attr "type" "alu")
9099    (set_attr "mode" "SI")])
9100
9101 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
9102 ;; ??? Special case for immediate operand is missing - it is tricky.
9103 (define_insn "*xorsi_2_zext"
9104   [(set (reg 17)
9105         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9106                          (match_operand:SI 2 "general_operand" "rim"))
9107                  (const_int 0)))
9108    (set (match_operand:DI 0 "register_operand" "=r")
9109         (zero_extend:DI (xor:SI (match_dup 1) (match_dup 2))))]
9110   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9111    && ix86_binary_operator_ok (XOR, SImode, operands)"
9112   "xor{l}\t{%2, %k0|%k0, %2}"
9113   [(set_attr "type" "alu")
9114    (set_attr "mode" "SI")])
9115
9116 (define_insn "*xorsi_2_zext_imm"
9117   [(set (reg 17)
9118         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9119                          (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
9120                  (const_int 0)))
9121    (set (match_operand:DI 0 "register_operand" "=r")
9122         (xor:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
9123   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9124    && ix86_binary_operator_ok (XOR, SImode, operands)"
9125   "xor{l}\t{%2, %k0|%k0, %2}"
9126   [(set_attr "type" "alu")
9127    (set_attr "mode" "SI")])
9128
9129 (define_insn "*xorsi_3"
9130   [(set (reg 17)
9131         (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
9132                          (match_operand:SI 2 "general_operand" "rim"))
9133                  (const_int 0)))
9134    (clobber (match_scratch:SI 0 "=r"))]
9135   "ix86_match_ccmode (insn, CCNOmode)
9136    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
9137   "xor{l}\t{%2, %0|%0, %2}"
9138   [(set_attr "type" "alu")
9139    (set_attr "mode" "SI")])
9140
9141 (define_expand "xorhi3"
9142   [(set (match_operand:HI 0 "nonimmediate_operand" "")
9143         (xor:HI (match_operand:HI 1 "nonimmediate_operand" "")
9144                 (match_operand:HI 2 "general_operand" "")))
9145    (clobber (reg:CC 17))]
9146   "TARGET_HIMODE_MATH"
9147   "ix86_expand_binary_operator (XOR, HImode, operands); DONE;")
9148
9149 (define_insn "*xorhi_1"
9150   [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
9151         (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9152                 (match_operand:HI 2 "general_operand" "rmi,ri")))
9153    (clobber (reg:CC 17))]
9154   "ix86_binary_operator_ok (XOR, HImode, operands)"
9155   "xor{w}\t{%2, %0|%0, %2}"
9156   [(set_attr "type" "alu")
9157    (set_attr "mode" "HI")])
9158
9159 (define_insn "*xorhi_2"
9160   [(set (reg 17)
9161         (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9162                          (match_operand:HI 2 "general_operand" "rim,ri"))
9163                  (const_int 0)))
9164    (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
9165         (xor:HI (match_dup 1) (match_dup 2)))]
9166   "ix86_match_ccmode (insn, CCNOmode)
9167    && ix86_binary_operator_ok (XOR, HImode, operands)"
9168   "xor{w}\t{%2, %0|%0, %2}"
9169   [(set_attr "type" "alu")
9170    (set_attr "mode" "HI")])
9171
9172 (define_insn "*xorhi_3"
9173   [(set (reg 17)
9174         (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
9175                          (match_operand:HI 2 "general_operand" "rim"))
9176                  (const_int 0)))
9177    (clobber (match_scratch:HI 0 "=r"))]
9178   "ix86_match_ccmode (insn, CCNOmode)
9179    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
9180   "xor{w}\t{%2, %0|%0, %2}"
9181   [(set_attr "type" "alu")
9182    (set_attr "mode" "HI")])
9183
9184 (define_expand "xorqi3"
9185   [(set (match_operand:QI 0 "nonimmediate_operand" "")
9186         (xor:QI (match_operand:QI 1 "nonimmediate_operand" "")
9187                 (match_operand:QI 2 "general_operand" "")))
9188    (clobber (reg:CC 17))]
9189   "TARGET_QIMODE_MATH"
9190   "ix86_expand_binary_operator (XOR, QImode, operands); DONE;")
9191
9192 ;; %%% Potential partial reg stall on alternative 2.  What to do?
9193 (define_insn "*xorqi_1"
9194   [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
9195         (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9196                 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
9197    (clobber (reg:CC 17))]
9198   "ix86_binary_operator_ok (XOR, QImode, operands)"
9199   "@
9200    xor{b}\t{%2, %0|%0, %2}
9201    xor{b}\t{%2, %0|%0, %2}
9202    xor{l}\t{%k2, %k0|%k0, %k2}"
9203   [(set_attr "type" "alu")
9204    (set_attr "mode" "QI,QI,SI")])
9205
9206 (define_insn "*xorqi_1_slp"
9207   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
9208         (xor:QI (match_dup 0)
9209                 (match_operand:QI 1 "general_operand" "qi,qmi")))
9210    (clobber (reg:CC 17))]
9211   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9212    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
9213   "xor{b}\t{%1, %0|%0, %1}"
9214   [(set_attr "type" "alu1")
9215    (set_attr "mode" "QI")])
9216
9217 (define_insn "xorqi_ext_0"
9218   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9219                          (const_int 8)
9220                          (const_int 8))
9221         (xor:SI 
9222           (zero_extract:SI
9223             (match_operand 1 "ext_register_operand" "0")
9224             (const_int 8)
9225             (const_int 8))
9226           (match_operand 2 "const_int_operand" "n")))
9227    (clobber (reg:CC 17))]
9228   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9229   "xor{b}\t{%2, %h0|%h0, %2}"
9230   [(set_attr "type" "alu")
9231    (set_attr "length_immediate" "1")
9232    (set_attr "mode" "QI")])
9233
9234 (define_insn "*xorqi_ext_1"
9235   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9236                          (const_int 8)
9237                          (const_int 8))
9238         (xor:SI 
9239           (zero_extract:SI
9240             (match_operand 1 "ext_register_operand" "0")
9241             (const_int 8)
9242             (const_int 8))
9243           (zero_extend:SI
9244             (match_operand:QI 2 "general_operand" "Qm"))))
9245    (clobber (reg:CC 17))]
9246   "!TARGET_64BIT
9247    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9248   "xor{b}\t{%2, %h0|%h0, %2}"
9249   [(set_attr "type" "alu")
9250    (set_attr "length_immediate" "0")
9251    (set_attr "mode" "QI")])
9252
9253 (define_insn "*xorqi_ext_1_rex64"
9254   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9255                          (const_int 8)
9256                          (const_int 8))
9257         (xor:SI 
9258           (zero_extract:SI
9259             (match_operand 1 "ext_register_operand" "0")
9260             (const_int 8)
9261             (const_int 8))
9262           (zero_extend:SI
9263             (match_operand 2 "ext_register_operand" "Q"))))
9264    (clobber (reg:CC 17))]
9265   "TARGET_64BIT
9266    && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9267   "xor{b}\t{%2, %h0|%h0, %2}"
9268   [(set_attr "type" "alu")
9269    (set_attr "length_immediate" "0")
9270    (set_attr "mode" "QI")])
9271
9272 (define_insn "*xorqi_ext_2"
9273   [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9274                          (const_int 8)
9275                          (const_int 8))
9276         (xor:SI 
9277           (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
9278                            (const_int 8)
9279                            (const_int 8))
9280           (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
9281                            (const_int 8)
9282                            (const_int 8))))
9283    (clobber (reg:CC 17))]
9284   "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9285   "xor{b}\t{%h2, %h0|%h0, %h2}"
9286   [(set_attr "type" "alu")
9287    (set_attr "length_immediate" "0")
9288    (set_attr "mode" "QI")])
9289
9290 (define_insn "*xorqi_cc_1"
9291   [(set (reg 17)
9292         (compare
9293           (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9294                   (match_operand:QI 2 "general_operand" "qim,qi"))
9295           (const_int 0)))
9296    (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9297         (xor:QI (match_dup 1) (match_dup 2)))]
9298   "ix86_match_ccmode (insn, CCNOmode)
9299    && ix86_binary_operator_ok (XOR, QImode, operands)"
9300   "xor{b}\t{%2, %0|%0, %2}"
9301   [(set_attr "type" "alu")
9302    (set_attr "mode" "QI")])
9303
9304 (define_insn "*xorqi_2_slp"
9305   [(set (reg 17)
9306         (compare (xor:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9307                          (match_operand:QI 1 "general_operand" "qim,qi"))
9308                  (const_int 0)))
9309    (set (strict_low_part (match_dup 0))
9310         (xor:QI (match_dup 0) (match_dup 1)))]
9311   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9312    && ix86_match_ccmode (insn, CCNOmode)
9313    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
9314   "xor{b}\t{%1, %0|%0, %1}"
9315   [(set_attr "type" "alu1")
9316    (set_attr "mode" "QI")])
9317
9318 (define_insn "*xorqi_cc_2"
9319   [(set (reg 17)
9320         (compare
9321           (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
9322                   (match_operand:QI 2 "general_operand" "qim"))
9323           (const_int 0)))
9324    (clobber (match_scratch:QI 0 "=q"))]
9325   "ix86_match_ccmode (insn, CCNOmode)
9326    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
9327   "xor{b}\t{%2, %0|%0, %2}"
9328   [(set_attr "type" "alu")
9329    (set_attr "mode" "QI")])
9330
9331 (define_insn "*xorqi_cc_ext_1"
9332   [(set (reg 17)
9333         (compare
9334           (xor:SI
9335             (zero_extract:SI
9336               (match_operand 1 "ext_register_operand" "0")
9337               (const_int 8)
9338               (const_int 8))
9339             (match_operand:QI 2 "general_operand" "qmn"))
9340           (const_int 0)))
9341    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
9342                          (const_int 8)
9343                          (const_int 8))
9344         (xor:SI 
9345           (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9346           (match_dup 2)))]
9347   "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9348   "xor{b}\t{%2, %h0|%h0, %2}"
9349   [(set_attr "type" "alu")
9350    (set_attr "mode" "QI")])
9351
9352 (define_insn "*xorqi_cc_ext_1_rex64"
9353   [(set (reg 17)
9354         (compare
9355           (xor:SI
9356             (zero_extract:SI
9357               (match_operand 1 "ext_register_operand" "0")
9358               (const_int 8)
9359               (const_int 8))
9360             (match_operand:QI 2 "nonmemory_operand" "Qn"))
9361           (const_int 0)))
9362    (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9363                          (const_int 8)
9364                          (const_int 8))
9365         (xor:SI 
9366           (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9367           (match_dup 2)))]
9368   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9369   "xor{b}\t{%2, %h0|%h0, %2}"
9370   [(set_attr "type" "alu")
9371    (set_attr "mode" "QI")])
9372
9373 (define_expand "xorqi_cc_ext_1"
9374   [(parallel [
9375      (set (reg:CCNO 17)
9376           (compare:CCNO
9377             (xor:SI
9378               (zero_extract:SI
9379                 (match_operand 1 "ext_register_operand" "")
9380                 (const_int 8)
9381                 (const_int 8))
9382               (match_operand:QI 2 "general_operand" ""))
9383             (const_int 0)))
9384      (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
9385                            (const_int 8)
9386                            (const_int 8))
9387           (xor:SI 
9388             (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9389             (match_dup 2)))])]
9390   ""
9391   "")
9392
9393 (define_split
9394   [(set (match_operand 0 "register_operand" "")
9395         (xor (match_operand 1 "register_operand" "")
9396              (match_operand 2 "const_int_operand" "")))
9397    (clobber (reg:CC 17))]
9398    "reload_completed
9399     && QI_REG_P (operands[0])
9400     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9401     && !(INTVAL (operands[2]) & ~(255 << 8))
9402     && GET_MODE (operands[0]) != QImode"
9403   [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9404                    (xor:SI (zero_extract:SI (match_dup 1)
9405                                             (const_int 8) (const_int 8))
9406                            (match_dup 2)))
9407               (clobber (reg:CC 17))])]
9408   "operands[0] = gen_lowpart (SImode, operands[0]);
9409    operands[1] = gen_lowpart (SImode, operands[1]);
9410    operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9411
9412 ;; Since XOR can be encoded with sign extended immediate, this is only
9413 ;; profitable when 7th bit is set.
9414 (define_split
9415   [(set (match_operand 0 "register_operand" "")
9416         (xor (match_operand 1 "general_operand" "")
9417              (match_operand 2 "const_int_operand" "")))
9418    (clobber (reg:CC 17))]
9419    "reload_completed
9420     && ANY_QI_REG_P (operands[0])
9421     && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9422     && !(INTVAL (operands[2]) & ~255)
9423     && (INTVAL (operands[2]) & 128)
9424     && GET_MODE (operands[0]) != QImode"
9425   [(parallel [(set (strict_low_part (match_dup 0))
9426                    (xor:QI (match_dup 1)
9427                            (match_dup 2)))
9428               (clobber (reg:CC 17))])]
9429   "operands[0] = gen_lowpart (QImode, operands[0]);
9430    operands[1] = gen_lowpart (QImode, operands[1]);
9431    operands[2] = gen_lowpart (QImode, operands[2]);")
9432 \f
9433 ;; Negation instructions
9434
9435 (define_expand "negdi2"
9436   [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
9437                    (neg:DI (match_operand:DI 1 "nonimmediate_operand" "")))
9438               (clobber (reg:CC 17))])]
9439   ""
9440   "ix86_expand_unary_operator (NEG, DImode, operands); DONE;")
9441
9442 (define_insn "*negdi2_1"
9443   [(set (match_operand:DI 0 "nonimmediate_operand" "=ro")
9444         (neg:DI (match_operand:DI 1 "general_operand" "0")))
9445    (clobber (reg:CC 17))]
9446   "!TARGET_64BIT
9447    && ix86_unary_operator_ok (NEG, DImode, operands)"
9448   "#")
9449
9450 (define_split
9451   [(set (match_operand:DI 0 "nonimmediate_operand" "")
9452         (neg:DI (match_operand:DI 1 "general_operand" "")))
9453    (clobber (reg:CC 17))]
9454   "!TARGET_64BIT && reload_completed"
9455   [(parallel
9456     [(set (reg:CCZ 17)
9457           (compare:CCZ (neg:SI (match_dup 2)) (const_int 0)))
9458      (set (match_dup 0) (neg:SI (match_dup 2)))])
9459    (parallel
9460     [(set (match_dup 1)
9461           (plus:SI (plus:SI (ltu:SI (reg:CC 17) (const_int 0))
9462                             (match_dup 3))
9463                    (const_int 0)))
9464      (clobber (reg:CC 17))])
9465    (parallel
9466     [(set (match_dup 1)
9467           (neg:SI (match_dup 1)))
9468      (clobber (reg:CC 17))])]
9469   "split_di (operands+1, 1, operands+2, operands+3);
9470    split_di (operands+0, 1, operands+0, operands+1);")
9471
9472 (define_insn "*negdi2_1_rex64"
9473   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9474         (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0")))
9475    (clobber (reg:CC 17))]
9476   "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
9477   "neg{q}\t%0"
9478   [(set_attr "type" "negnot")
9479    (set_attr "mode" "DI")])
9480
9481 ;; The problem with neg is that it does not perform (compare x 0),
9482 ;; it really performs (compare 0 x), which leaves us with the zero
9483 ;; flag being the only useful item.
9484
9485 (define_insn "*negdi2_cmpz_rex64"
9486   [(set (reg:CCZ 17)
9487         (compare:CCZ (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
9488                      (const_int 0)))
9489    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9490         (neg:DI (match_dup 1)))]
9491   "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
9492   "neg{q}\t%0"
9493   [(set_attr "type" "negnot")
9494    (set_attr "mode" "DI")])
9495
9496
9497 (define_expand "negsi2"
9498   [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
9499                    (neg:SI (match_operand:SI 1 "nonimmediate_operand" "")))
9500               (clobber (reg:CC 17))])]
9501   ""
9502   "ix86_expand_unary_operator (NEG, SImode, operands); DONE;")
9503
9504 (define_insn "*negsi2_1"
9505   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9506         (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0")))
9507    (clobber (reg:CC 17))]
9508   "ix86_unary_operator_ok (NEG, SImode, operands)"
9509   "neg{l}\t%0"
9510   [(set_attr "type" "negnot")
9511    (set_attr "mode" "SI")])
9512
9513 ;; Combine is quite creative about this pattern.
9514 (define_insn "*negsi2_1_zext"
9515   [(set (match_operand:DI 0 "register_operand" "=r")
9516         (lshiftrt:DI (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
9517                                         (const_int 32)))
9518                      (const_int 32)))
9519    (clobber (reg:CC 17))]
9520   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
9521   "neg{l}\t%k0"
9522   [(set_attr "type" "negnot")
9523    (set_attr "mode" "SI")])
9524
9525 ;; The problem with neg is that it does not perform (compare x 0),
9526 ;; it really performs (compare 0 x), which leaves us with the zero
9527 ;; flag being the only useful item.
9528
9529 (define_insn "*negsi2_cmpz"
9530   [(set (reg:CCZ 17)
9531         (compare:CCZ (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
9532                      (const_int 0)))
9533    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9534         (neg:SI (match_dup 1)))]
9535   "ix86_unary_operator_ok (NEG, SImode, operands)"
9536   "neg{l}\t%0"
9537   [(set_attr "type" "negnot")
9538    (set_attr "mode" "SI")])
9539
9540 (define_insn "*negsi2_cmpz_zext"
9541   [(set (reg:CCZ 17)
9542         (compare:CCZ (lshiftrt:DI
9543                        (neg:DI (ashift:DI
9544                                  (match_operand:DI 1 "register_operand" "0")
9545                                  (const_int 32)))
9546                        (const_int 32))
9547                      (const_int 0)))
9548    (set (match_operand:DI 0 "register_operand" "=r")
9549         (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
9550                                         (const_int 32)))
9551                      (const_int 32)))]
9552   "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
9553   "neg{l}\t%k0"
9554   [(set_attr "type" "negnot")
9555    (set_attr "mode" "SI")])
9556
9557 (define_expand "neghi2"
9558   [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
9559                    (neg:HI (match_operand:HI 1 "nonimmediate_operand" "")))
9560               (clobber (reg:CC 17))])]
9561   "TARGET_HIMODE_MATH"
9562   "ix86_expand_unary_operator (NEG, HImode, operands); DONE;")
9563
9564 (define_insn "*neghi2_1"
9565   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9566         (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0")))
9567    (clobber (reg:CC 17))]
9568   "ix86_unary_operator_ok (NEG, HImode, operands)"
9569   "neg{w}\t%0"
9570   [(set_attr "type" "negnot")
9571    (set_attr "mode" "HI")])
9572
9573 (define_insn "*neghi2_cmpz"
9574   [(set (reg:CCZ 17)
9575         (compare:CCZ (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
9576                      (const_int 0)))
9577    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9578         (neg:HI (match_dup 1)))]
9579   "ix86_unary_operator_ok (NEG, HImode, operands)"
9580   "neg{w}\t%0"
9581   [(set_attr "type" "negnot")
9582    (set_attr "mode" "HI")])
9583
9584 (define_expand "negqi2"
9585   [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
9586                    (neg:QI (match_operand:QI 1 "nonimmediate_operand" "")))
9587               (clobber (reg:CC 17))])]
9588   "TARGET_QIMODE_MATH"
9589   "ix86_expand_unary_operator (NEG, QImode, operands); DONE;")
9590
9591 (define_insn "*negqi2_1"
9592   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9593         (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0")))
9594    (clobber (reg:CC 17))]
9595   "ix86_unary_operator_ok (NEG, QImode, operands)"
9596   "neg{b}\t%0"
9597   [(set_attr "type" "negnot")
9598    (set_attr "mode" "QI")])
9599
9600 (define_insn "*negqi2_cmpz"
9601   [(set (reg:CCZ 17)
9602         (compare:CCZ (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
9603                      (const_int 0)))
9604    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9605         (neg:QI (match_dup 1)))]
9606   "ix86_unary_operator_ok (NEG, QImode, operands)"
9607   "neg{b}\t%0"
9608   [(set_attr "type" "negnot")
9609    (set_attr "mode" "QI")])
9610
9611 ;; Changing of sign for FP values is doable using integer unit too.
9612
9613 (define_expand "negsf2"
9614   [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
9615                    (neg:SF (match_operand:SF 1 "nonimmediate_operand" "")))
9616               (clobber (reg:CC 17))])]
9617   "TARGET_80387 || TARGET_SSE_MATH"
9618   "if (TARGET_SSE_MATH)
9619      {
9620        /* In case operand is in memory,  we will not use SSE.  */
9621        if (memory_operand (operands[0], VOIDmode)
9622            && rtx_equal_p (operands[0], operands[1]))
9623          emit_insn (gen_negsf2_memory (operands[0], operands[1]));
9624        else
9625         {
9626           /* Using SSE is tricky, since we need bitwise negation of -0
9627              in register.  */
9628           rtx reg = gen_reg_rtx (SFmode);
9629           rtx dest = operands[0];
9630           rtx imm = gen_lowpart (SFmode, gen_int_mode (0x80000000, SImode));
9631
9632           operands[1] = force_reg (SFmode, operands[1]);
9633           operands[0] = force_reg (SFmode, operands[0]);
9634           reg = force_reg (V4SFmode,
9635                            gen_rtx_CONST_VECTOR (V4SFmode,
9636                              gen_rtvec (4, imm, CONST0_RTX (SFmode),
9637                                         CONST0_RTX (SFmode),
9638                                         CONST0_RTX (SFmode))));
9639           emit_insn (gen_negsf2_ifs (operands[0], operands[1], reg));
9640           if (dest != operands[0])
9641             emit_move_insn (dest, operands[0]);
9642         }
9643        DONE;
9644      }
9645    ix86_expand_unary_operator (NEG, SFmode, operands); DONE;")
9646
9647 (define_insn "negsf2_memory"
9648   [(set (match_operand:SF 0 "memory_operand" "=m")
9649         (neg:SF (match_operand:SF 1 "memory_operand" "0")))
9650    (clobber (reg:CC 17))]
9651   "ix86_unary_operator_ok (NEG, SFmode, operands)"
9652   "#")
9653
9654 (define_insn "negsf2_ifs"
9655   [(set (match_operand:SF 0 "nonimmediate_operand" "=x#fr,x#fr,f#xr,rm#xf")
9656         (neg:SF (match_operand:SF 1 "nonimmediate_operand" "0,x#fr,0,0")))
9657    (use (match_operand:V4SF 2 "nonimmediate_operand" "xm,0,xm*r,xm*r"))
9658    (clobber (reg:CC 17))]
9659   "TARGET_SSE
9660    && (reload_in_progress || reload_completed
9661        || (register_operand (operands[0], VOIDmode)
9662            && register_operand (operands[1], VOIDmode)))"
9663   "#")
9664
9665 (define_split
9666   [(set (match_operand:SF 0 "memory_operand" "")
9667         (neg:SF (match_operand:SF 1 "memory_operand" "")))
9668    (use (match_operand:SF 2 "" ""))
9669    (clobber (reg:CC 17))]
9670   ""
9671   [(parallel [(set (match_dup 0)
9672                    (neg:SF (match_dup 1)))
9673               (clobber (reg:CC 17))])])
9674
9675 (define_split
9676   [(set (match_operand:SF 0 "register_operand" "")
9677         (neg:SF (match_operand:SF 1 "register_operand" "")))
9678    (use (match_operand:V4SF 2 "" ""))
9679    (clobber (reg:CC 17))]
9680   "reload_completed && !SSE_REG_P (operands[0])"
9681   [(parallel [(set (match_dup 0)
9682                    (neg:SF (match_dup 1)))
9683               (clobber (reg:CC 17))])])
9684
9685 (define_split
9686   [(set (match_operand:SF 0 "register_operand" "")
9687         (neg:SF (match_operand:SF 1 "register_operand" "")))
9688    (use (match_operand:V4SF 2 "nonimmediate_operand" ""))
9689    (clobber (reg:CC 17))]
9690   "reload_completed && SSE_REG_P (operands[0])"
9691   [(set (match_dup 0)
9692         (xor:V4SF (match_dup 1)
9693                   (match_dup 2)))]
9694 {
9695   operands[0] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
9696   operands[1] = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
9697   if (operands_match_p (operands[0], operands[2]))
9698     {
9699       rtx tmp;
9700       tmp = operands[1];
9701       operands[1] = operands[2];
9702       operands[2] = tmp;
9703     }
9704 })
9705
9706
9707 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
9708 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
9709 ;; to itself.
9710 (define_insn "*negsf2_if"
9711   [(set (match_operand:SF 0 "nonimmediate_operand" "=f#r,rm#f")
9712         (neg:SF (match_operand:SF 1 "nonimmediate_operand" "0,0")))
9713    (clobber (reg:CC 17))]
9714   "TARGET_80387
9715    && ix86_unary_operator_ok (NEG, SFmode, operands)"
9716   "#")
9717
9718 (define_split
9719   [(set (match_operand:SF 0 "fp_register_operand" "")
9720         (neg:SF (match_operand:SF 1 "register_operand" "")))
9721    (clobber (reg:CC 17))]
9722   "TARGET_80387 && reload_completed"
9723   [(set (match_dup 0)
9724         (neg:SF (match_dup 1)))]
9725   "")
9726
9727 (define_split
9728   [(set (match_operand:SF 0 "register_and_not_fp_reg_operand" "")
9729         (neg:SF (match_operand:SF 1 "register_operand" "")))
9730    (clobber (reg:CC 17))]
9731   "TARGET_80387 && reload_completed"
9732   [(parallel [(set (match_dup 0) (xor:SI (match_dup 0) (match_dup 1)))
9733               (clobber (reg:CC 17))])]
9734   "operands[1] = gen_int_mode (0x80000000, SImode);
9735    operands[0] = gen_lowpart (SImode, operands[0]);")
9736
9737 (define_split
9738   [(set (match_operand 0 "memory_operand" "")
9739         (neg (match_operand 1 "memory_operand" "")))
9740    (clobber (reg:CC 17))]
9741   "TARGET_80387 && reload_completed && FLOAT_MODE_P (GET_MODE (operands[0]))"
9742   [(parallel [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
9743               (clobber (reg:CC 17))])]
9744 {
9745   int size = GET_MODE_SIZE (GET_MODE (operands[1]));
9746
9747   if (GET_MODE (operands[1]) == XFmode)
9748     size = 10;
9749   operands[0] = adjust_address (operands[0], QImode, size - 1);
9750   operands[1] = gen_int_mode (0x80, QImode);
9751 })
9752
9753 (define_expand "negdf2"
9754   [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
9755                    (neg:DF (match_operand:DF 1 "nonimmediate_operand" "")))
9756               (clobber (reg:CC 17))])]
9757   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
9758   "if (TARGET_SSE2 && TARGET_SSE_MATH)
9759      {
9760        /* In case operand is in memory,  we will not use SSE.  */
9761        if (memory_operand (operands[0], VOIDmode)
9762            && rtx_equal_p (operands[0], operands[1]))
9763          emit_insn (gen_negdf2_memory (operands[0], operands[1]));
9764        else
9765         {
9766           /* Using SSE is tricky, since we need bitwise negation of -0
9767              in register.  */
9768           rtx reg;
9769 #if HOST_BITS_PER_WIDE_INT >= 64
9770           rtx imm = gen_int_mode (((HOST_WIDE_INT)1) << 63, DImode);
9771 #else
9772           rtx imm = immed_double_const (0, 0x80000000, DImode);
9773 #endif
9774           rtx dest = operands[0];
9775
9776           operands[1] = force_reg (DFmode, operands[1]);
9777           operands[0] = force_reg (DFmode, operands[0]);
9778           imm = gen_lowpart (DFmode, imm);
9779           reg = force_reg (V2DFmode,
9780                            gen_rtx_CONST_VECTOR (V2DFmode,
9781                              gen_rtvec (2, imm, CONST0_RTX (DFmode))));
9782           emit_insn (gen_negdf2_ifs (operands[0], operands[1], reg));
9783           if (dest != operands[0])
9784             emit_move_insn (dest, operands[0]);
9785         }
9786        DONE;
9787      }
9788    ix86_expand_unary_operator (NEG, DFmode, operands); DONE;")
9789
9790 (define_insn "negdf2_memory"
9791   [(set (match_operand:DF 0 "memory_operand" "=m")
9792         (neg:DF (match_operand:DF 1 "memory_operand" "0")))
9793    (clobber (reg:CC 17))]
9794   "ix86_unary_operator_ok (NEG, DFmode, operands)"
9795   "#")
9796
9797 (define_insn "negdf2_ifs"
9798   [(set (match_operand:DF 0 "nonimmediate_operand" "=Y#fr,Y#fr,f#Yr,rm#Yf")
9799         (neg:DF (match_operand:DF 1 "nonimmediate_operand" "0,Y#fr,0,0")))
9800    (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym,0,Ym*r,Ym*r"))
9801    (clobber (reg:CC 17))]
9802   "!TARGET_64BIT && TARGET_SSE2
9803    && (reload_in_progress || reload_completed
9804        || (register_operand (operands[0], VOIDmode)
9805            && register_operand (operands[1], VOIDmode)))"
9806   "#")
9807
9808 (define_insn "*negdf2_ifs_rex64"
9809   [(set (match_operand:DF 0 "nonimmediate_operand" "=Y#f,Y#f,fm#Y")
9810         (neg:DF (match_operand:DF 1 "nonimmediate_operand" "0,Y#fr,0")))
9811    (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym,0,Ym*r"))
9812    (clobber (reg:CC 17))]
9813   "TARGET_64BIT && TARGET_SSE2
9814    && (reload_in_progress || reload_completed
9815        || (register_operand (operands[0], VOIDmode)
9816            && register_operand (operands[1], VOIDmode)))"
9817   "#")
9818
9819 (define_split
9820   [(set (match_operand:DF 0 "memory_operand" "")
9821         (neg:DF (match_operand:DF 1 "memory_operand" "")))
9822    (use (match_operand:V2DF 2 "" ""))
9823    (clobber (reg:CC 17))]
9824   ""
9825   [(parallel [(set (match_dup 0)
9826                    (neg:DF (match_dup 1)))
9827               (clobber (reg:CC 17))])])
9828
9829 (define_split
9830   [(set (match_operand:DF 0 "register_operand" "")
9831         (neg:DF (match_operand:DF 1 "register_operand" "")))
9832    (use (match_operand:V2DF 2 "" ""))
9833    (clobber (reg:CC 17))]
9834   "reload_completed && !SSE_REG_P (operands[0])
9835    && (!TARGET_64BIT || FP_REG_P (operands[0]))"
9836   [(parallel [(set (match_dup 0)
9837                    (neg:DF (match_dup 1)))
9838               (clobber (reg:CC 17))])])
9839
9840 (define_split
9841   [(set (match_operand:DF 0 "register_operand" "")
9842         (neg:DF (match_operand:DF 1 "register_operand" "")))
9843    (use (match_operand:V2DF 2 "" ""))
9844    (clobber (reg:CC 17))]
9845   "TARGET_64BIT && reload_completed && GENERAL_REG_P (operands[0])"
9846   [(parallel [(set (match_dup 0)
9847                    (xor:DI (match_dup 1) (match_dup 2)))
9848               (clobber (reg:CC 17))])]
9849    "operands[0] = gen_lowpart (DImode, operands[0]);
9850     operands[1] = gen_lowpart (DImode, operands[1]);
9851     operands[2] = gen_lowpart (DImode, operands[2]);")
9852
9853 (define_split
9854   [(set (match_operand:DF 0 "register_operand" "")
9855         (neg:DF (match_operand:DF 1 "register_operand" "")))
9856    (use (match_operand:V2DF 2 "nonimmediate_operand" ""))
9857    (clobber (reg:CC 17))]
9858   "reload_completed && SSE_REG_P (operands[0])"
9859   [(set (match_dup 0)
9860         (xor:V2DF (match_dup 1)
9861                   (match_dup 2)))]
9862 {
9863   operands[0] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
9864   operands[1] = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
9865   /* Avoid possible reformatting on the operands.  */
9866   if (TARGET_SSE_PARTIAL_REGS && !optimize_size)
9867     emit_insn (gen_sse2_unpcklpd (operands[0], operands[0], operands[0]));
9868   if (operands_match_p (operands[0], operands[2]))
9869     {
9870       rtx tmp;
9871       tmp = operands[1];
9872       operands[1] = operands[2];
9873       operands[2] = tmp;
9874     }
9875 })
9876
9877 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
9878 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
9879 ;; to itself.
9880 (define_insn "*negdf2_if"
9881   [(set (match_operand:DF 0 "nonimmediate_operand" "=f#r,rm#f")
9882         (neg:DF (match_operand:DF 1 "nonimmediate_operand" "0,0")))
9883    (clobber (reg:CC 17))]
9884   "!TARGET_64BIT && TARGET_80387
9885    && ix86_unary_operator_ok (NEG, DFmode, operands)"
9886   "#")
9887
9888 ;; FIXME: We should to allow integer registers here.  Problem is that
9889 ;; we need another scratch register to get constant from.
9890 ;; Forcing constant to mem if no register available in peep2 should be
9891 ;; safe even for PIC mode, because of RIP relative addressing.
9892 (define_insn "*negdf2_if_rex64"
9893   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,mf")
9894         (neg:DF (match_operand:DF 1 "nonimmediate_operand" "0,0")))
9895    (clobber (reg:CC 17))]
9896   "TARGET_64BIT && TARGET_80387
9897    && ix86_unary_operator_ok (NEG, DFmode, operands)"
9898   "#")
9899
9900 (define_split
9901   [(set (match_operand:DF 0 "fp_register_operand" "")
9902         (neg:DF (match_operand:DF 1 "register_operand" "")))
9903    (clobber (reg:CC 17))]
9904   "TARGET_80387 && reload_completed"
9905   [(set (match_dup 0)
9906         (neg:DF (match_dup 1)))]
9907   "")
9908
9909 (define_split
9910   [(set (match_operand:DF 0 "register_and_not_fp_reg_operand" "")
9911         (neg:DF (match_operand:DF 1 "register_operand" "")))
9912    (clobber (reg:CC 17))]
9913   "!TARGET_64BIT && TARGET_80387 && reload_completed"
9914   [(parallel [(set (match_dup 3) (xor:SI (match_dup 3) (match_dup 4)))
9915               (clobber (reg:CC 17))])]
9916   "operands[4] = gen_int_mode (0x80000000, SImode);
9917    split_di (operands+0, 1, operands+2, operands+3);")
9918
9919 (define_expand "negxf2"
9920   [(parallel [(set (match_operand:XF 0 "nonimmediate_operand" "")
9921                    (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))
9922               (clobber (reg:CC 17))])]
9923   "TARGET_80387"
9924   "ix86_expand_unary_operator (NEG, XFmode, operands); DONE;")
9925
9926 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
9927 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
9928 ;; to itself.
9929 (define_insn "*negxf2_if"
9930   [(set (match_operand:XF 0 "nonimmediate_operand" "=f#r,rm#f")
9931         (neg:XF (match_operand:XF 1 "nonimmediate_operand" "0,0")))
9932    (clobber (reg:CC 17))]
9933   "TARGET_80387
9934    && ix86_unary_operator_ok (NEG, XFmode, operands)"
9935   "#")
9936
9937 (define_split
9938   [(set (match_operand:XF 0 "fp_register_operand" "")
9939         (neg:XF (match_operand:XF 1 "register_operand" "")))
9940    (clobber (reg:CC 17))]
9941   "TARGET_80387 && reload_completed"
9942   [(set (match_dup 0)
9943         (neg:XF (match_dup 1)))]
9944   "")
9945
9946 (define_split
9947   [(set (match_operand:XF 0 "register_and_not_fp_reg_operand" "")
9948         (neg:XF (match_operand:XF 1 "register_operand" "")))
9949    (clobber (reg:CC 17))]
9950   "TARGET_80387 && reload_completed"
9951   [(parallel [(set (match_dup 0) (xor:SI (match_dup 0) (match_dup 1)))
9952               (clobber (reg:CC 17))])]
9953   "operands[1] = GEN_INT (0x8000);
9954    operands[0] = gen_rtx_REG (SImode,
9955                               true_regnum (operands[0]) + (TARGET_64BIT ? 1 : 2));")
9956
9957 ;; Conditionalize these after reload. If they matches before reload, we 
9958 ;; lose the clobber and ability to use integer instructions.
9959
9960 (define_insn "*negsf2_1"
9961   [(set (match_operand:SF 0 "register_operand" "=f")
9962         (neg:SF (match_operand:SF 1 "register_operand" "0")))]
9963   "TARGET_80387 && reload_completed"
9964   "fchs"
9965   [(set_attr "type" "fsgn")
9966    (set_attr "mode" "SF")
9967    (set_attr "ppro_uops" "few")])
9968
9969 (define_insn "*negdf2_1"
9970   [(set (match_operand:DF 0 "register_operand" "=f")
9971         (neg:DF (match_operand:DF 1 "register_operand" "0")))]
9972   "TARGET_80387 && reload_completed"
9973   "fchs"
9974   [(set_attr "type" "fsgn")
9975    (set_attr "mode" "DF")
9976    (set_attr "ppro_uops" "few")])
9977
9978 (define_insn "*negextendsfdf2"
9979   [(set (match_operand:DF 0 "register_operand" "=f")
9980         (neg:DF (float_extend:DF
9981                   (match_operand:SF 1 "register_operand" "0"))))]
9982   "TARGET_80387"
9983   "fchs"
9984   [(set_attr "type" "fsgn")
9985    (set_attr "mode" "DF")
9986    (set_attr "ppro_uops" "few")])
9987
9988 (define_insn "*negxf2_1"
9989   [(set (match_operand:XF 0 "register_operand" "=f")
9990         (neg:XF (match_operand:XF 1 "register_operand" "0")))]
9991   "TARGET_80387 && reload_completed"
9992   "fchs"
9993   [(set_attr "type" "fsgn")
9994    (set_attr "mode" "XF")
9995    (set_attr "ppro_uops" "few")])
9996
9997 (define_insn "*negextenddfxf2"
9998   [(set (match_operand:XF 0 "register_operand" "=f")
9999         (neg:XF (float_extend:XF
10000                   (match_operand:DF 1 "register_operand" "0"))))]
10001   "TARGET_80387"
10002   "fchs"
10003   [(set_attr "type" "fsgn")
10004    (set_attr "mode" "XF")
10005    (set_attr "ppro_uops" "few")])
10006
10007 (define_insn "*negextendsfxf2"
10008   [(set (match_operand:XF 0 "register_operand" "=f")
10009         (neg:XF (float_extend:XF
10010                   (match_operand:SF 1 "register_operand" "0"))))]
10011   "TARGET_80387"
10012   "fchs"
10013   [(set_attr "type" "fsgn")
10014    (set_attr "mode" "XF")
10015    (set_attr "ppro_uops" "few")])
10016 \f
10017 ;; Absolute value instructions
10018
10019 (define_expand "abssf2"
10020   [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
10021                    (neg:SF (match_operand:SF 1 "nonimmediate_operand" "")))
10022               (clobber (reg:CC 17))])]
10023   "TARGET_80387 || TARGET_SSE_MATH"
10024   "if (TARGET_SSE_MATH)
10025      {
10026        /* In case operand is in memory,  we will not use SSE.  */
10027        if (memory_operand (operands[0], VOIDmode)
10028            && rtx_equal_p (operands[0], operands[1]))
10029          emit_insn (gen_abssf2_memory (operands[0], operands[1]));
10030        else
10031         {
10032           /* Using SSE is tricky, since we need bitwise negation of -0
10033              in register.  */
10034           rtx reg = gen_reg_rtx (V4SFmode);
10035           rtx dest = operands[0];
10036           rtx imm;
10037
10038           operands[1] = force_reg (SFmode, operands[1]);
10039           operands[0] = force_reg (SFmode, operands[0]);
10040           imm = gen_lowpart (SFmode, gen_int_mode(~0x80000000, SImode));
10041           reg = force_reg (V4SFmode,
10042                            gen_rtx_CONST_VECTOR (V4SFmode,
10043                            gen_rtvec (4, imm, CONST0_RTX (SFmode),
10044                                       CONST0_RTX (SFmode),
10045                                       CONST0_RTX (SFmode))));
10046           emit_insn (gen_abssf2_ifs (operands[0], operands[1], reg));
10047           if (dest != operands[0])
10048             emit_move_insn (dest, operands[0]);
10049         }
10050        DONE;
10051      }
10052    ix86_expand_unary_operator (ABS, SFmode, operands); DONE;")
10053
10054 (define_insn "abssf2_memory"
10055   [(set (match_operand:SF 0 "memory_operand" "=m")
10056         (abs:SF (match_operand:SF 1 "memory_operand" "0")))
10057    (clobber (reg:CC 17))]
10058   "ix86_unary_operator_ok (ABS, SFmode, operands)"
10059   "#")
10060
10061 (define_insn "abssf2_ifs"
10062   [(set (match_operand:SF 0 "nonimmediate_operand" "=x#fr,x#fr,f#xr,rm#xf")
10063         (abs:SF (match_operand:SF 1 "nonimmediate_operand" "0,x#fr,0,0")))
10064    (use (match_operand:V4SF 2 "nonimmediate_operand" "xm,0,xm*r,xm*r"))
10065    (clobber (reg:CC 17))]
10066   "TARGET_SSE
10067    && (reload_in_progress || reload_completed
10068        || (register_operand (operands[0], VOIDmode)
10069             && register_operand (operands[1], VOIDmode)))"
10070   "#")
10071
10072 (define_split
10073   [(set (match_operand:SF 0 "memory_operand" "")
10074         (abs:SF (match_operand:SF 1 "memory_operand" "")))
10075    (use (match_operand:V4SF 2 "" ""))
10076    (clobber (reg:CC 17))]
10077   ""
10078   [(parallel [(set (match_dup 0)
10079                    (abs:SF (match_dup 1)))
10080               (clobber (reg:CC 17))])])
10081
10082 (define_split
10083   [(set (match_operand:SF 0 "register_operand" "")
10084         (abs:SF (match_operand:SF 1 "register_operand" "")))
10085    (use (match_operand:V4SF 2 "" ""))
10086    (clobber (reg:CC 17))]
10087   "reload_completed && !SSE_REG_P (operands[0])"
10088   [(parallel [(set (match_dup 0)
10089                    (abs:SF (match_dup 1)))
10090               (clobber (reg:CC 17))])])
10091
10092 (define_split
10093   [(set (match_operand:SF 0 "register_operand" "")
10094         (abs:SF (match_operand:SF 1 "register_operand" "")))
10095    (use (match_operand:V4SF 2 "nonimmediate_operand" ""))
10096    (clobber (reg:CC 17))]
10097   "reload_completed && SSE_REG_P (operands[0])"
10098   [(set (match_dup 0)
10099         (and:V4SF (match_dup 1)
10100                   (match_dup 2)))]
10101 {
10102   operands[0] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
10103   operands[1] = simplify_gen_subreg (V4SFmode, operands[1], SFmode, 0);
10104   if (operands_match_p (operands[0], operands[2]))
10105     {
10106       rtx tmp;
10107       tmp = operands[1];
10108       operands[1] = operands[2];
10109       operands[2] = tmp;
10110     }
10111 })
10112
10113 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
10114 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
10115 ;; to itself.
10116 (define_insn "*abssf2_if"
10117   [(set (match_operand:SF 0 "nonimmediate_operand" "=f#r,rm#f")
10118         (abs:SF (match_operand:SF 1 "nonimmediate_operand" "0,0")))
10119    (clobber (reg:CC 17))]
10120   "TARGET_80387 && ix86_unary_operator_ok (ABS, SFmode, operands)"
10121   "#")
10122
10123 (define_split
10124   [(set (match_operand:SF 0 "fp_register_operand" "")
10125         (abs:SF (match_operand:SF 1 "register_operand" "")))
10126    (clobber (reg:CC 17))]
10127   "TARGET_80387 && reload_completed"
10128   [(set (match_dup 0)
10129         (abs:SF (match_dup 1)))]
10130   "")
10131
10132 (define_split
10133   [(set (match_operand:SF 0 "register_and_not_fp_reg_operand" "")
10134         (abs:SF (match_operand:SF 1 "register_operand" "")))
10135    (clobber (reg:CC 17))]
10136   "TARGET_80387 && reload_completed"
10137   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (match_dup 1)))
10138               (clobber (reg:CC 17))])]
10139   "operands[1] = gen_int_mode (~0x80000000, SImode);
10140    operands[0] = gen_lowpart (SImode, operands[0]);")
10141
10142 (define_split
10143   [(set (match_operand 0 "memory_operand" "")
10144         (abs (match_operand 1 "memory_operand" "")))
10145    (clobber (reg:CC 17))]
10146   "TARGET_80387 && reload_completed && FLOAT_MODE_P (GET_MODE (operands[0]))"
10147   [(parallel [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
10148               (clobber (reg:CC 17))])]
10149 {
10150   int size = GET_MODE_SIZE (GET_MODE (operands[1]));
10151
10152   if (GET_MODE (operands[1]) == XFmode)
10153     size = 10;
10154   operands[0] = adjust_address (operands[0], QImode, size - 1);
10155   operands[1] = gen_int_mode (~0x80, QImode);
10156 })
10157
10158 (define_expand "absdf2"
10159   [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
10160                    (neg:DF (match_operand:DF 1 "nonimmediate_operand" "")))
10161               (clobber (reg:CC 17))])]
10162   "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
10163   "if (TARGET_SSE2 && TARGET_SSE_MATH)
10164      {
10165        /* In case operand is in memory,  we will not use SSE.  */
10166        if (memory_operand (operands[0], VOIDmode)
10167            && rtx_equal_p (operands[0], operands[1]))
10168          emit_insn (gen_absdf2_memory (operands[0], operands[1]));
10169        else
10170         {
10171           /* Using SSE is tricky, since we need bitwise negation of -0
10172              in register.  */
10173           rtx reg = gen_reg_rtx (V2DFmode);
10174 #if HOST_BITS_PER_WIDE_INT >= 64
10175           rtx imm = gen_int_mode (~(((HOST_WIDE_INT)1) << 63), DImode);
10176 #else
10177           rtx imm = immed_double_const (~0, ~0x80000000, DImode);
10178 #endif
10179           rtx dest = operands[0];
10180
10181           operands[1] = force_reg (DFmode, operands[1]);
10182           operands[0] = force_reg (DFmode, operands[0]);
10183
10184           /* Produce LONG_DOUBLE with the proper immediate argument.  */
10185           imm = gen_lowpart (DFmode, imm);
10186           reg = force_reg (V2DFmode,
10187                            gen_rtx_CONST_VECTOR (V2DFmode,
10188                            gen_rtvec (2, imm, CONST0_RTX (DFmode))));
10189           emit_insn (gen_absdf2_ifs (operands[0], operands[1], reg));
10190           if (dest != operands[0])
10191             emit_move_insn (dest, operands[0]);
10192         }
10193        DONE;
10194      }
10195    ix86_expand_unary_operator (ABS, DFmode, operands); DONE;")
10196
10197 (define_insn "absdf2_memory"
10198   [(set (match_operand:DF 0 "memory_operand" "=m")
10199         (abs:DF (match_operand:DF 1 "memory_operand" "0")))
10200    (clobber (reg:CC 17))]
10201   "ix86_unary_operator_ok (ABS, DFmode, operands)"
10202   "#")
10203
10204 (define_insn "absdf2_ifs"
10205   [(set (match_operand:DF 0 "nonimmediate_operand" "=Y#fr,Y#fr,mf#Yr,mr#Yf")
10206         (abs:DF (match_operand:DF 1 "nonimmediate_operand" "0,Y#fr,0,0")))
10207    (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym,0,Ym*r,Ym*r"))
10208    (clobber (reg:CC 17))]
10209   "!TARGET_64BIT && TARGET_SSE2
10210    && (reload_in_progress || reload_completed
10211        || (register_operand (operands[0], VOIDmode)
10212            && register_operand (operands[1], VOIDmode)))"
10213   "#")
10214
10215 (define_insn "*absdf2_ifs_rex64"
10216   [(set (match_operand:DF 0 "nonimmediate_operand" "=Y#fr,Y#fr,mf#Yr")
10217         (abs:DF (match_operand:DF 1 "nonimmediate_operand" "0,Y#fr,0")))
10218    (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym,0,Ym*r"))
10219    (clobber (reg:CC 17))]
10220   "TARGET_64BIT && TARGET_SSE2
10221    && (reload_in_progress || reload_completed
10222        || (register_operand (operands[0], VOIDmode)
10223            && register_operand (operands[1], VOIDmode)))"
10224   "#")
10225
10226 (define_split
10227   [(set (match_operand:DF 0 "memory_operand" "")
10228         (abs:DF (match_operand:DF 1 "memory_operand" "")))
10229    (use (match_operand:V2DF 2 "" ""))
10230    (clobber (reg:CC 17))]
10231   ""
10232   [(parallel [(set (match_dup 0)
10233                    (abs:DF (match_dup 1)))
10234               (clobber (reg:CC 17))])])
10235
10236 (define_split
10237   [(set (match_operand:DF 0 "register_operand" "")
10238         (abs:DF (match_operand:DF 1 "register_operand" "")))
10239    (use (match_operand:V2DF 2 "" ""))
10240    (clobber (reg:CC 17))]
10241   "reload_completed && !SSE_REG_P (operands[0])"
10242   [(parallel [(set (match_dup 0)
10243                    (abs:DF (match_dup 1)))
10244               (clobber (reg:CC 17))])])
10245
10246 (define_split
10247   [(set (match_operand:DF 0 "register_operand" "")
10248         (abs:DF (match_operand:DF 1 "register_operand" "")))
10249    (use (match_operand:V2DF 2 "nonimmediate_operand" ""))
10250    (clobber (reg:CC 17))]
10251   "reload_completed && SSE_REG_P (operands[0])"
10252   [(set (match_dup 0)
10253         (and:V2DF (match_dup 1)
10254                   (match_dup 2)))]
10255 {
10256   operands[0] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
10257   operands[1] = simplify_gen_subreg (V2DFmode, operands[1], DFmode, 0);
10258   /* Avoid possible reformatting on the operands.  */
10259   if (TARGET_SSE_PARTIAL_REGS && !optimize_size)
10260     emit_insn (gen_sse2_unpcklpd (operands[0], operands[0], operands[0]));
10261   if (operands_match_p (operands[0], operands[2]))
10262     {
10263       rtx tmp;
10264       tmp = operands[1];
10265       operands[1] = operands[2];
10266       operands[2] = tmp;
10267     }
10268 })
10269
10270
10271 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
10272 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
10273 ;; to itself.
10274 (define_insn "*absdf2_if"
10275   [(set (match_operand:DF 0 "nonimmediate_operand" "=f#r,rm#f")
10276         (abs:DF (match_operand:DF 1 "nonimmediate_operand" "0,0")))
10277    (clobber (reg:CC 17))]
10278   "!TARGET_64BIT && TARGET_80387
10279    && ix86_unary_operator_ok (ABS, DFmode, operands)"
10280   "#")
10281
10282 ;; FIXME: We should to allow integer registers here.  Problem is that
10283 ;; we need another scratch register to get constant from.
10284 ;; Forcing constant to mem if no register available in peep2 should be
10285 ;; safe even for PIC mode, because of RIP relative addressing.
10286 (define_insn "*absdf2_if_rex64"
10287   [(set (match_operand:DF 0 "nonimmediate_operand" "=f,mf")
10288         (abs:DF (match_operand:DF 1 "nonimmediate_operand" "0,0")))
10289    (clobber (reg:CC 17))]
10290   "TARGET_64BIT && TARGET_80387
10291    && ix86_unary_operator_ok (ABS, DFmode, operands)"
10292   "#")
10293
10294 (define_split
10295   [(set (match_operand:DF 0 "fp_register_operand" "")
10296         (abs:DF (match_operand:DF 1 "register_operand" "")))
10297    (clobber (reg:CC 17))]
10298   "TARGET_80387 && reload_completed"
10299   [(set (match_dup 0)
10300         (abs:DF (match_dup 1)))]
10301   "")
10302
10303 (define_split
10304   [(set (match_operand:DF 0 "register_and_not_fp_reg_operand" "")
10305         (abs:DF (match_operand:DF 1 "register_operand" "")))
10306    (clobber (reg:CC 17))]
10307   "!TARGET_64BIT && TARGET_80387 && reload_completed"
10308   [(parallel [(set (match_dup 3) (and:SI (match_dup 3) (match_dup 4)))
10309               (clobber (reg:CC 17))])]
10310   "operands[4] = gen_int_mode (~0x80000000, SImode);
10311    split_di (operands+0, 1, operands+2, operands+3);")
10312
10313 (define_expand "absxf2"
10314   [(parallel [(set (match_operand:XF 0 "nonimmediate_operand" "")
10315                    (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))
10316               (clobber (reg:CC 17))])]
10317   "TARGET_80387"
10318   "ix86_expand_unary_operator (ABS, XFmode, operands); DONE;")
10319
10320 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
10321 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
10322 ;; to itself.
10323 (define_insn "*absxf2_if"
10324   [(set (match_operand:XF 0 "nonimmediate_operand" "=f#r,rm#f")
10325         (abs:XF (match_operand:XF 1 "nonimmediate_operand" "0,0")))
10326    (clobber (reg:CC 17))]
10327   "TARGET_80387
10328    && ix86_unary_operator_ok (ABS, XFmode, operands)"
10329   "#")
10330
10331 (define_split
10332   [(set (match_operand:XF 0 "fp_register_operand" "")
10333         (abs:XF (match_operand:XF 1 "register_operand" "")))
10334    (clobber (reg:CC 17))]
10335   "TARGET_80387 && reload_completed"
10336   [(set (match_dup 0)
10337         (abs:XF (match_dup 1)))]
10338   "")
10339
10340 (define_split
10341   [(set (match_operand:XF 0 "register_and_not_fp_reg_operand" "")
10342         (abs:XF (match_operand:XF 1 "register_operand" "")))
10343    (clobber (reg:CC 17))]
10344   "TARGET_80387 && reload_completed"
10345   [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (match_dup 1)))
10346               (clobber (reg:CC 17))])]
10347   "operands[1] = GEN_INT (~0x8000);
10348    operands[0] = gen_rtx_REG (SImode,
10349                               true_regnum (operands[0]) + (TARGET_64BIT ? 1 : 2));")
10350
10351 (define_insn "*abssf2_1"
10352   [(set (match_operand:SF 0 "register_operand" "=f")
10353         (abs:SF (match_operand:SF 1 "register_operand" "0")))]
10354   "TARGET_80387 && reload_completed"
10355   "fabs"
10356   [(set_attr "type" "fsgn")
10357    (set_attr "mode" "SF")])
10358
10359 (define_insn "*absdf2_1"
10360   [(set (match_operand:DF 0 "register_operand" "=f")
10361         (abs:DF (match_operand:DF 1 "register_operand" "0")))]
10362   "TARGET_80387 && reload_completed"
10363   "fabs"
10364   [(set_attr "type" "fsgn")
10365    (set_attr "mode" "DF")])
10366
10367 (define_insn "*absextendsfdf2"
10368   [(set (match_operand:DF 0 "register_operand" "=f")
10369         (abs:DF (float_extend:DF
10370                   (match_operand:SF 1 "register_operand" "0"))))]
10371   "TARGET_80387"
10372   "fabs"
10373   [(set_attr "type" "fsgn")
10374    (set_attr "mode" "DF")])
10375
10376 (define_insn "*absxf2_1"
10377   [(set (match_operand:XF 0 "register_operand" "=f")
10378         (abs:XF (match_operand:XF 1 "register_operand" "0")))]
10379   "TARGET_80387 && reload_completed"
10380   "fabs"
10381   [(set_attr "type" "fsgn")
10382    (set_attr "mode" "DF")])
10383
10384 (define_insn "*absextenddfxf2"
10385   [(set (match_operand:XF 0 "register_operand" "=f")
10386         (abs:XF (float_extend:XF
10387           (match_operand:DF 1 "register_operand" "0"))))]
10388   "TARGET_80387"
10389   "fabs"
10390   [(set_attr "type" "fsgn")
10391    (set_attr "mode" "XF")])
10392
10393 (define_insn "*absextendsfxf2"
10394   [(set (match_operand:XF 0 "register_operand" "=f")
10395         (abs:XF (float_extend:XF
10396           (match_operand:SF 1 "register_operand" "0"))))]
10397   "TARGET_80387"
10398   "fabs"
10399   [(set_attr "type" "fsgn")
10400    (set_attr "mode" "XF")])
10401 \f
10402 ;; One complement instructions
10403
10404 (define_expand "one_cmpldi2"
10405   [(set (match_operand:DI 0 "nonimmediate_operand" "")
10406         (not:DI (match_operand:DI 1 "nonimmediate_operand" "")))]
10407   "TARGET_64BIT"
10408   "ix86_expand_unary_operator (NOT, DImode, operands); DONE;")
10409
10410 (define_insn "*one_cmpldi2_1_rex64"
10411   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10412         (not:DI (match_operand:DI 1 "nonimmediate_operand" "0")))]
10413   "TARGET_64BIT && ix86_unary_operator_ok (NOT, DImode, operands)"
10414   "not{q}\t%0"
10415   [(set_attr "type" "negnot")
10416    (set_attr "mode" "DI")])
10417
10418 (define_insn "*one_cmpldi2_2_rex64"
10419   [(set (reg 17)
10420         (compare (not:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
10421                  (const_int 0)))
10422    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10423         (not:DI (match_dup 1)))]
10424   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10425    && ix86_unary_operator_ok (NOT, DImode, operands)"
10426   "#"
10427   [(set_attr "type" "alu1")
10428    (set_attr "mode" "DI")])
10429
10430 (define_split
10431   [(set (match_operand 0 "flags_reg_operand" "")
10432         (match_operator 2 "compare_operator"
10433           [(not:DI (match_operand:DI 3 "nonimmediate_operand" ""))
10434            (const_int 0)]))
10435    (set (match_operand:DI 1 "nonimmediate_operand" "")
10436         (not:DI (match_dup 3)))]
10437   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
10438   [(parallel [(set (match_dup 0)
10439                    (match_op_dup 2
10440                      [(xor:DI (match_dup 3) (const_int -1))
10441                       (const_int 0)]))
10442               (set (match_dup 1)
10443                    (xor:DI (match_dup 3) (const_int -1)))])]
10444   "")
10445
10446 (define_expand "one_cmplsi2"
10447   [(set (match_operand:SI 0 "nonimmediate_operand" "")
10448         (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
10449   ""
10450   "ix86_expand_unary_operator (NOT, SImode, operands); DONE;")
10451
10452 (define_insn "*one_cmplsi2_1"
10453   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10454         (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))]
10455   "ix86_unary_operator_ok (NOT, SImode, operands)"
10456   "not{l}\t%0"
10457   [(set_attr "type" "negnot")
10458    (set_attr "mode" "SI")])
10459
10460 ;; ??? Currently never generated - xor is used instead.
10461 (define_insn "*one_cmplsi2_1_zext"
10462   [(set (match_operand:DI 0 "register_operand" "=r")
10463         (zero_extend:DI (not:SI (match_operand:SI 1 "register_operand" "0"))))]
10464   "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
10465   "not{l}\t%k0"
10466   [(set_attr "type" "negnot")
10467    (set_attr "mode" "SI")])
10468
10469 (define_insn "*one_cmplsi2_2"
10470   [(set (reg 17)
10471         (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
10472                  (const_int 0)))
10473    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10474         (not:SI (match_dup 1)))]
10475   "ix86_match_ccmode (insn, CCNOmode)
10476    && ix86_unary_operator_ok (NOT, SImode, operands)"
10477   "#"
10478   [(set_attr "type" "alu1")
10479    (set_attr "mode" "SI")])
10480
10481 (define_split
10482   [(set (match_operand 0 "flags_reg_operand" "")
10483         (match_operator 2 "compare_operator"
10484           [(not:SI (match_operand:SI 3 "nonimmediate_operand" ""))
10485            (const_int 0)]))
10486    (set (match_operand:SI 1 "nonimmediate_operand" "")
10487         (not:SI (match_dup 3)))]
10488   "ix86_match_ccmode (insn, CCNOmode)"
10489   [(parallel [(set (match_dup 0)
10490                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
10491                                     (const_int 0)]))
10492               (set (match_dup 1)
10493                    (xor:SI (match_dup 3) (const_int -1)))])]
10494   "")
10495
10496 ;; ??? Currently never generated - xor is used instead.
10497 (define_insn "*one_cmplsi2_2_zext"
10498   [(set (reg 17)
10499         (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
10500                  (const_int 0)))
10501    (set (match_operand:DI 0 "register_operand" "=r")
10502         (zero_extend:DI (not:SI (match_dup 1))))]
10503   "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10504    && ix86_unary_operator_ok (NOT, SImode, operands)"
10505   "#"
10506   [(set_attr "type" "alu1")
10507    (set_attr "mode" "SI")])
10508
10509 (define_split
10510   [(set (match_operand 0 "flags_reg_operand" "")
10511         (match_operator 2 "compare_operator"
10512           [(not:SI (match_operand:SI 3 "register_operand" ""))
10513            (const_int 0)]))
10514    (set (match_operand:DI 1 "register_operand" "")
10515         (zero_extend:DI (not:SI (match_dup 3))))]
10516   "ix86_match_ccmode (insn, CCNOmode)"
10517   [(parallel [(set (match_dup 0)
10518                    (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
10519                                     (const_int 0)]))
10520               (set (match_dup 1)
10521                    (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])]
10522   "")
10523
10524 (define_expand "one_cmplhi2"
10525   [(set (match_operand:HI 0 "nonimmediate_operand" "")
10526         (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
10527   "TARGET_HIMODE_MATH"
10528   "ix86_expand_unary_operator (NOT, HImode, operands); DONE;")
10529
10530 (define_insn "*one_cmplhi2_1"
10531   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10532         (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))]
10533   "ix86_unary_operator_ok (NOT, HImode, operands)"
10534   "not{w}\t%0"
10535   [(set_attr "type" "negnot")
10536    (set_attr "mode" "HI")])
10537
10538 (define_insn "*one_cmplhi2_2"
10539   [(set (reg 17)
10540         (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
10541                  (const_int 0)))
10542    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10543         (not:HI (match_dup 1)))]
10544   "ix86_match_ccmode (insn, CCNOmode)
10545    && ix86_unary_operator_ok (NEG, HImode, operands)"
10546   "#"
10547   [(set_attr "type" "alu1")
10548    (set_attr "mode" "HI")])
10549
10550 (define_split
10551   [(set (match_operand 0 "flags_reg_operand" "")
10552         (match_operator 2 "compare_operator"
10553           [(not:HI (match_operand:HI 3 "nonimmediate_operand" ""))
10554            (const_int 0)]))
10555    (set (match_operand:HI 1 "nonimmediate_operand" "")
10556         (not:HI (match_dup 3)))]
10557   "ix86_match_ccmode (insn, CCNOmode)"
10558   [(parallel [(set (match_dup 0)
10559                    (match_op_dup 2 [(xor:HI (match_dup 3) (const_int -1))
10560                                     (const_int 0)]))
10561               (set (match_dup 1)
10562                    (xor:HI (match_dup 3) (const_int -1)))])]
10563   "")
10564
10565 ;; %%% Potential partial reg stall on alternative 1.  What to do?
10566 (define_expand "one_cmplqi2"
10567   [(set (match_operand:QI 0 "nonimmediate_operand" "")
10568         (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
10569   "TARGET_QIMODE_MATH"
10570   "ix86_expand_unary_operator (NOT, QImode, operands); DONE;")
10571
10572 (define_insn "*one_cmplqi2_1"
10573   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10574         (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
10575   "ix86_unary_operator_ok (NOT, QImode, operands)"
10576   "@
10577    not{b}\t%0
10578    not{l}\t%k0"
10579   [(set_attr "type" "negnot")
10580    (set_attr "mode" "QI,SI")])
10581
10582 (define_insn "*one_cmplqi2_2"
10583   [(set (reg 17)
10584         (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
10585                  (const_int 0)))
10586    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10587         (not:QI (match_dup 1)))]
10588   "ix86_match_ccmode (insn, CCNOmode)
10589    && ix86_unary_operator_ok (NOT, QImode, operands)"
10590   "#"
10591   [(set_attr "type" "alu1")
10592    (set_attr "mode" "QI")])
10593
10594 (define_split
10595   [(set (match_operand 0 "flags_reg_operand" "")
10596         (match_operator 2 "compare_operator"
10597           [(not:QI (match_operand:QI 3 "nonimmediate_operand" ""))
10598            (const_int 0)]))
10599    (set (match_operand:QI 1 "nonimmediate_operand" "")
10600         (not:QI (match_dup 3)))]
10601   "ix86_match_ccmode (insn, CCNOmode)"
10602   [(parallel [(set (match_dup 0)
10603                    (match_op_dup 2 [(xor:QI (match_dup 3) (const_int -1))
10604                                     (const_int 0)]))
10605               (set (match_dup 1)
10606                    (xor:QI (match_dup 3) (const_int -1)))])]
10607   "")
10608 \f
10609 ;; Arithmetic shift instructions
10610
10611 ;; DImode shifts are implemented using the i386 "shift double" opcode,
10612 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem".  If the shift count
10613 ;; is variable, then the count is in %cl and the "imm" operand is dropped
10614 ;; from the assembler input.
10615 ;;
10616 ;; This instruction shifts the target reg/mem as usual, but instead of
10617 ;; shifting in zeros, bits are shifted in from reg operand.  If the insn
10618 ;; is a left shift double, bits are taken from the high order bits of
10619 ;; reg, else if the insn is a shift right double, bits are taken from the
10620 ;; low order bits of reg.  So if %eax is "1234" and %edx is "5678",
10621 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
10622 ;;
10623 ;; Since sh[lr]d does not change the `reg' operand, that is done
10624 ;; separately, making all shifts emit pairs of shift double and normal
10625 ;; shift.  Since sh[lr]d does not shift more than 31 bits, and we wish to
10626 ;; support a 63 bit shift, each shift where the count is in a reg expands
10627 ;; to a pair of shifts, a branch, a shift by 32 and a label.
10628 ;;
10629 ;; If the shift count is a constant, we need never emit more than one
10630 ;; shift pair, instead using moves and sign extension for counts greater
10631 ;; than 31.
10632
10633 (define_expand "ashldi3"
10634   [(parallel [(set (match_operand:DI 0 "shiftdi_operand" "")
10635                    (ashift:DI (match_operand:DI 1 "shiftdi_operand" "")
10636                               (match_operand:QI 2 "nonmemory_operand" "")))
10637               (clobber (reg:CC 17))])]
10638   ""
10639 {
10640   if (!TARGET_64BIT && TARGET_CMOVE && ! immediate_operand (operands[2], QImode))
10641     {
10642       emit_insn (gen_ashldi3_1 (operands[0], operands[1], operands[2]));
10643       DONE;
10644     }
10645   ix86_expand_binary_operator (ASHIFT, DImode, operands);
10646   DONE;
10647 })
10648
10649 (define_insn "*ashldi3_1_rex64"
10650   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
10651         (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0,r")
10652                    (match_operand:QI 2 "nonmemory_operand" "cJ,M")))
10653    (clobber (reg:CC 17))]
10654   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10655 {
10656   switch (get_attr_type (insn))
10657     {
10658     case TYPE_ALU:
10659       if (operands[2] != const1_rtx)
10660         abort ();
10661       if (!rtx_equal_p (operands[0], operands[1]))
10662         abort ();
10663       return "add{q}\t{%0, %0|%0, %0}";
10664
10665     case TYPE_LEA:
10666       if (GET_CODE (operands[2]) != CONST_INT
10667           || (unsigned HOST_WIDE_INT) INTVAL (operands[2]) > 3)
10668         abort ();
10669       operands[1] = gen_rtx_MULT (DImode, operands[1],
10670                                   GEN_INT (1 << INTVAL (operands[2])));
10671       return "lea{q}\t{%a1, %0|%0, %a1}";
10672
10673     default:
10674       if (REG_P (operands[2]))
10675         return "sal{q}\t{%b2, %0|%0, %b2}";
10676       else if (GET_CODE (operands[2]) == CONST_INT
10677                && INTVAL (operands[2]) == 1
10678                && (TARGET_SHIFT1 || optimize_size))
10679         return "sal{q}\t%0";
10680       else
10681         return "sal{q}\t{%2, %0|%0, %2}";
10682     }
10683 }
10684   [(set (attr "type")
10685      (cond [(eq_attr "alternative" "1")
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" "DI")])
10695
10696 ;; Convert lea to the lea pattern to avoid flags dependency.
10697 (define_split
10698   [(set (match_operand:DI 0 "register_operand" "")
10699         (ashift:DI (match_operand:DI 1 "register_operand" "")
10700                    (match_operand:QI 2 "immediate_operand" "")))
10701    (clobber (reg:CC 17))]
10702   "TARGET_64BIT && reload_completed
10703    && true_regnum (operands[0]) != true_regnum (operands[1])"
10704   [(set (match_dup 0)
10705         (mult:DI (match_dup 1)
10706                  (match_dup 2)))]
10707   "operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);")
10708
10709 ;; This pattern can't accept a variable shift count, since shifts by
10710 ;; zero don't affect the flags.  We assume that shifts by constant
10711 ;; zero are optimized away.
10712 (define_insn "*ashldi3_cmp_rex64"
10713   [(set (reg 17)
10714         (compare
10715           (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10716                      (match_operand:QI 2 "immediate_operand" "e"))
10717           (const_int 0)))
10718    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10719         (ashift:DI (match_dup 1) (match_dup 2)))]
10720   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10721    && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10722 {
10723   switch (get_attr_type (insn))
10724     {
10725     case TYPE_ALU:
10726       if (operands[2] != const1_rtx)
10727         abort ();
10728       return "add{q}\t{%0, %0|%0, %0}";
10729
10730     default:
10731       if (REG_P (operands[2]))
10732         return "sal{q}\t{%b2, %0|%0, %b2}";
10733       else if (GET_CODE (operands[2]) == CONST_INT
10734                && INTVAL (operands[2]) == 1
10735                && (TARGET_SHIFT1 || optimize_size))
10736         return "sal{q}\t%0";
10737       else
10738         return "sal{q}\t{%2, %0|%0, %2}";
10739     }
10740 }
10741   [(set (attr "type")
10742      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10743                           (const_int 0))
10744                       (match_operand 0 "register_operand" ""))
10745                  (match_operand 2 "const1_operand" ""))
10746               (const_string "alu")
10747            ]
10748            (const_string "ishift")))
10749    (set_attr "mode" "DI")])
10750
10751 (define_insn "ashldi3_1"
10752   [(set (match_operand:DI 0 "register_operand" "=r")
10753         (ashift:DI (match_operand:DI 1 "register_operand" "0")
10754                    (match_operand:QI 2 "nonmemory_operand" "Jc")))
10755    (clobber (match_scratch:SI 3 "=&r"))
10756    (clobber (reg:CC 17))]
10757   "!TARGET_64BIT && TARGET_CMOVE"
10758   "#"
10759   [(set_attr "type" "multi")])
10760
10761 (define_insn "*ashldi3_2"
10762   [(set (match_operand:DI 0 "register_operand" "=r")
10763         (ashift:DI (match_operand:DI 1 "register_operand" "0")
10764                    (match_operand:QI 2 "nonmemory_operand" "Jc")))
10765    (clobber (reg:CC 17))]
10766   "!TARGET_64BIT"
10767   "#"
10768   [(set_attr "type" "multi")])
10769
10770 (define_split
10771   [(set (match_operand:DI 0 "register_operand" "")
10772         (ashift:DI (match_operand:DI 1 "register_operand" "")
10773                    (match_operand:QI 2 "nonmemory_operand" "")))
10774    (clobber (match_scratch:SI 3 ""))
10775    (clobber (reg:CC 17))]
10776   "!TARGET_64BIT && TARGET_CMOVE && reload_completed"
10777   [(const_int 0)]
10778   "ix86_split_ashldi (operands, operands[3]); DONE;")
10779
10780 (define_split
10781   [(set (match_operand:DI 0 "register_operand" "")
10782         (ashift:DI (match_operand:DI 1 "register_operand" "")
10783                    (match_operand:QI 2 "nonmemory_operand" "")))
10784    (clobber (reg:CC 17))]
10785   "!TARGET_64BIT && reload_completed"
10786   [(const_int 0)]
10787   "ix86_split_ashldi (operands, NULL_RTX); DONE;")
10788
10789 (define_insn "x86_shld_1"
10790   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
10791         (ior:SI (ashift:SI (match_dup 0)
10792                   (match_operand:QI 2 "nonmemory_operand" "I,c"))
10793                 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
10794                   (minus:QI (const_int 32) (match_dup 2)))))
10795    (clobber (reg:CC 17))]
10796   ""
10797   "@
10798    shld{l}\t{%2, %1, %0|%0, %1, %2}
10799    shld{l}\t{%s2%1, %0|%0, %1, %2}"
10800   [(set_attr "type" "ishift")
10801    (set_attr "prefix_0f" "1")
10802    (set_attr "mode" "SI")
10803    (set_attr "pent_pair" "np")
10804    (set_attr "athlon_decode" "vector")
10805    (set_attr "ppro_uops" "few")])
10806
10807 (define_expand "x86_shift_adj_1"
10808   [(set (reg:CCZ 17)
10809         (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
10810                              (const_int 32))
10811                      (const_int 0)))
10812    (set (match_operand:SI 0 "register_operand" "")
10813         (if_then_else:SI (ne (reg:CCZ 17) (const_int 0))
10814                          (match_operand:SI 1 "register_operand" "")
10815                          (match_dup 0)))
10816    (set (match_dup 1)
10817         (if_then_else:SI (ne (reg:CCZ 17) (const_int 0))
10818                          (match_operand:SI 3 "register_operand" "r")
10819                          (match_dup 1)))]
10820   "TARGET_CMOVE"
10821   "")
10822
10823 (define_expand "x86_shift_adj_2"
10824   [(use (match_operand:SI 0 "register_operand" ""))
10825    (use (match_operand:SI 1 "register_operand" ""))
10826    (use (match_operand:QI 2 "register_operand" ""))]
10827   ""
10828 {
10829   rtx label = gen_label_rtx ();
10830   rtx tmp;
10831
10832   emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
10833
10834   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
10835   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
10836   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
10837                               gen_rtx_LABEL_REF (VOIDmode, label),
10838                               pc_rtx);
10839   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
10840   JUMP_LABEL (tmp) = label;
10841
10842   emit_move_insn (operands[0], operands[1]);
10843   emit_move_insn (operands[1], const0_rtx);
10844
10845   emit_label (label);
10846   LABEL_NUSES (label) = 1;
10847
10848   DONE;
10849 })
10850
10851 (define_expand "ashlsi3"
10852   [(set (match_operand:SI 0 "nonimmediate_operand" "")
10853         (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
10854                    (match_operand:QI 2 "nonmemory_operand" "")))
10855    (clobber (reg:CC 17))]
10856   ""
10857   "ix86_expand_binary_operator (ASHIFT, SImode, operands); DONE;")
10858
10859 (define_insn "*ashlsi3_1"
10860   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
10861         (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,r")
10862                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
10863    (clobber (reg:CC 17))]
10864   "ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10865 {
10866   switch (get_attr_type (insn))
10867     {
10868     case TYPE_ALU:
10869       if (operands[2] != const1_rtx)
10870         abort ();
10871       if (!rtx_equal_p (operands[0], operands[1]))
10872         abort ();
10873       return "add{l}\t{%0, %0|%0, %0}";
10874
10875     case TYPE_LEA:
10876       return "#";
10877
10878     default:
10879       if (REG_P (operands[2]))
10880         return "sal{l}\t{%b2, %0|%0, %b2}";
10881       else if (GET_CODE (operands[2]) == CONST_INT
10882                && INTVAL (operands[2]) == 1
10883                && (TARGET_SHIFT1 || optimize_size))
10884         return "sal{l}\t%0";
10885       else
10886         return "sal{l}\t{%2, %0|%0, %2}";
10887     }
10888 }
10889   [(set (attr "type")
10890      (cond [(eq_attr "alternative" "1")
10891               (const_string "lea")
10892             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10893                           (const_int 0))
10894                       (match_operand 0 "register_operand" ""))
10895                  (match_operand 2 "const1_operand" ""))
10896               (const_string "alu")
10897            ]
10898            (const_string "ishift")))
10899    (set_attr "mode" "SI")])
10900
10901 ;; Convert lea to the lea pattern to avoid flags dependency.
10902 (define_split
10903   [(set (match_operand 0 "register_operand" "")
10904         (ashift (match_operand 1 "index_register_operand" "")
10905                 (match_operand:QI 2 "const_int_operand" "")))
10906    (clobber (reg:CC 17))]
10907   "reload_completed
10908    && true_regnum (operands[0]) != true_regnum (operands[1])"
10909   [(const_int 0)]
10910 {
10911   rtx pat;
10912   operands[0] = gen_lowpart (SImode, operands[0]);
10913   operands[1] = gen_lowpart (Pmode, operands[1]);
10914   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
10915   pat = gen_rtx_MULT (Pmode, operands[1], operands[2]);
10916   if (Pmode != SImode)
10917     pat = gen_rtx_SUBREG (SImode, pat, 0);
10918   emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
10919   DONE;
10920 })
10921
10922 ;; Rare case of shifting RSP is handled by generating move and shift
10923 (define_split
10924   [(set (match_operand 0 "register_operand" "")
10925         (ashift (match_operand 1 "register_operand" "")
10926                 (match_operand:QI 2 "const_int_operand" "")))
10927    (clobber (reg:CC 17))]
10928   "reload_completed
10929    && true_regnum (operands[0]) != true_regnum (operands[1])"
10930   [(const_int 0)]
10931 {
10932   rtx pat, clob;
10933   emit_move_insn (operands[1], operands[0]);
10934   pat = gen_rtx_SET (VOIDmode, operands[0],
10935                      gen_rtx_ASHIFT (GET_MODE (operands[0]),
10936                                      operands[0], operands[2]));
10937   clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
10938   emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, pat, clob)));
10939   DONE;
10940 })
10941
10942 (define_insn "*ashlsi3_1_zext"
10943   [(set (match_operand:DI 0 "register_operand" "=r,r")
10944         (zero_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "0,r")
10945                         (match_operand:QI 2 "nonmemory_operand" "cI,M"))))
10946    (clobber (reg:CC 17))]
10947   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10948 {
10949   switch (get_attr_type (insn))
10950     {
10951     case TYPE_ALU:
10952       if (operands[2] != const1_rtx)
10953         abort ();
10954       return "add{l}\t{%k0, %k0|%k0, %k0}";
10955
10956     case TYPE_LEA:
10957       return "#";
10958
10959     default:
10960       if (REG_P (operands[2]))
10961         return "sal{l}\t{%b2, %k0|%k0, %b2}";
10962       else if (GET_CODE (operands[2]) == CONST_INT
10963                && INTVAL (operands[2]) == 1
10964                && (TARGET_SHIFT1 || optimize_size))
10965         return "sal{l}\t%k0";
10966       else
10967         return "sal{l}\t{%2, %k0|%k0, %2}";
10968     }
10969 }
10970   [(set (attr "type")
10971      (cond [(eq_attr "alternative" "1")
10972               (const_string "lea")
10973             (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10974                      (const_int 0))
10975                  (match_operand 2 "const1_operand" ""))
10976               (const_string "alu")
10977            ]
10978            (const_string "ishift")))
10979    (set_attr "mode" "SI")])
10980
10981 ;; Convert lea to the lea pattern to avoid flags dependency.
10982 (define_split
10983   [(set (match_operand:DI 0 "register_operand" "")
10984         (zero_extend:DI (ashift (match_operand 1 "register_operand" "")
10985                                 (match_operand:QI 2 "const_int_operand" ""))))
10986    (clobber (reg:CC 17))]
10987   "TARGET_64BIT && reload_completed
10988    && true_regnum (operands[0]) != true_regnum (operands[1])"
10989   [(set (match_dup 0) (zero_extend:DI
10990                         (subreg:SI (mult:SI (match_dup 1)
10991                                             (match_dup 2)) 0)))]
10992 {
10993   operands[1] = gen_lowpart (Pmode, operands[1]);
10994   operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
10995 })
10996
10997 ;; This pattern can't accept a variable shift count, since shifts by
10998 ;; zero don't affect the flags.  We assume that shifts by constant
10999 ;; zero are optimized away.
11000 (define_insn "*ashlsi3_cmp"
11001   [(set (reg 17)
11002         (compare
11003           (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11004                      (match_operand:QI 2 "const_int_1_31_operand" "I"))
11005           (const_int 0)))
11006    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11007         (ashift:SI (match_dup 1) (match_dup 2)))]
11008   "ix86_match_ccmode (insn, CCGOCmode)
11009    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11010 {
11011   switch (get_attr_type (insn))
11012     {
11013     case TYPE_ALU:
11014       if (operands[2] != const1_rtx)
11015         abort ();
11016       return "add{l}\t{%0, %0|%0, %0}";
11017
11018     default:
11019       if (REG_P (operands[2]))
11020         return "sal{l}\t{%b2, %0|%0, %b2}";
11021       else if (GET_CODE (operands[2]) == CONST_INT
11022                && INTVAL (operands[2]) == 1
11023                && (TARGET_SHIFT1 || optimize_size))
11024         return "sal{l}\t%0";
11025       else
11026         return "sal{l}\t{%2, %0|%0, %2}";
11027     }
11028 }
11029   [(set (attr "type")
11030      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11031                           (const_int 0))
11032                       (match_operand 0 "register_operand" ""))
11033                  (match_operand 2 "const1_operand" ""))
11034               (const_string "alu")
11035            ]
11036            (const_string "ishift")))
11037    (set_attr "mode" "SI")])
11038
11039 (define_insn "*ashlsi3_cmp_zext"
11040   [(set (reg 17)
11041         (compare
11042           (ashift:SI (match_operand:SI 1 "register_operand" "0")
11043                      (match_operand:QI 2 "const_int_1_31_operand" "I"))
11044           (const_int 0)))
11045    (set (match_operand:DI 0 "register_operand" "=r")
11046         (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
11047   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11048    && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
11049 {
11050   switch (get_attr_type (insn))
11051     {
11052     case TYPE_ALU:
11053       if (operands[2] != const1_rtx)
11054         abort ();
11055       return "add{l}\t{%k0, %k0|%k0, %k0}";
11056
11057     default:
11058       if (REG_P (operands[2]))
11059         return "sal{l}\t{%b2, %k0|%k0, %b2}";
11060       else if (GET_CODE (operands[2]) == CONST_INT
11061                && INTVAL (operands[2]) == 1
11062                && (TARGET_SHIFT1 || optimize_size))
11063         return "sal{l}\t%k0";
11064       else
11065         return "sal{l}\t{%2, %k0|%k0, %2}";
11066     }
11067 }
11068   [(set (attr "type")
11069      (cond [(and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11070                      (const_int 0))
11071                  (match_operand 2 "const1_operand" ""))
11072               (const_string "alu")
11073            ]
11074            (const_string "ishift")))
11075    (set_attr "mode" "SI")])
11076
11077 (define_expand "ashlhi3"
11078   [(set (match_operand:HI 0 "nonimmediate_operand" "")
11079         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "")
11080                    (match_operand:QI 2 "nonmemory_operand" "")))
11081    (clobber (reg:CC 17))]
11082   "TARGET_HIMODE_MATH"
11083   "ix86_expand_binary_operator (ASHIFT, HImode, operands); DONE;")
11084
11085 (define_insn "*ashlhi3_1_lea"
11086   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
11087         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,r")
11088                    (match_operand:QI 2 "nonmemory_operand" "cI,M")))
11089    (clobber (reg:CC 17))]
11090   "!TARGET_PARTIAL_REG_STALL
11091    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11092 {
11093   switch (get_attr_type (insn))
11094     {
11095     case TYPE_LEA:
11096       return "#";
11097     case TYPE_ALU:
11098       if (operands[2] != const1_rtx)
11099         abort ();
11100       return "add{w}\t{%0, %0|%0, %0}";
11101
11102     default:
11103       if (REG_P (operands[2]))
11104         return "sal{w}\t{%b2, %0|%0, %b2}";
11105       else if (GET_CODE (operands[2]) == CONST_INT
11106                && INTVAL (operands[2]) == 1
11107                && (TARGET_SHIFT1 || optimize_size))
11108         return "sal{w}\t%0";
11109       else
11110         return "sal{w}\t{%2, %0|%0, %2}";
11111     }
11112 }
11113   [(set (attr "type")
11114      (cond [(eq_attr "alternative" "1")
11115               (const_string "lea")
11116             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11117                           (const_int 0))
11118                       (match_operand 0 "register_operand" ""))
11119                  (match_operand 2 "const1_operand" ""))
11120               (const_string "alu")
11121            ]
11122            (const_string "ishift")))
11123    (set_attr "mode" "HI,SI")])
11124
11125 (define_insn "*ashlhi3_1"
11126   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11127         (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11128                    (match_operand:QI 2 "nonmemory_operand" "cI")))
11129    (clobber (reg:CC 17))]
11130   "TARGET_PARTIAL_REG_STALL
11131    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11132 {
11133   switch (get_attr_type (insn))
11134     {
11135     case TYPE_ALU:
11136       if (operands[2] != const1_rtx)
11137         abort ();
11138       return "add{w}\t{%0, %0|%0, %0}";
11139
11140     default:
11141       if (REG_P (operands[2]))
11142         return "sal{w}\t{%b2, %0|%0, %b2}";
11143       else if (GET_CODE (operands[2]) == CONST_INT
11144                && INTVAL (operands[2]) == 1
11145                && (TARGET_SHIFT1 || optimize_size))
11146         return "sal{w}\t%0";
11147       else
11148         return "sal{w}\t{%2, %0|%0, %2}";
11149     }
11150 }
11151   [(set (attr "type")
11152      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11153                           (const_int 0))
11154                       (match_operand 0 "register_operand" ""))
11155                  (match_operand 2 "const1_operand" ""))
11156               (const_string "alu")
11157            ]
11158            (const_string "ishift")))
11159    (set_attr "mode" "HI")])
11160
11161 ;; This pattern can't accept a variable shift count, since shifts by
11162 ;; zero don't affect the flags.  We assume that shifts by constant
11163 ;; zero are optimized away.
11164 (define_insn "*ashlhi3_cmp"
11165   [(set (reg 17)
11166         (compare
11167           (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11168                      (match_operand:QI 2 "const_int_1_31_operand" "I"))
11169           (const_int 0)))
11170    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11171         (ashift:HI (match_dup 1) (match_dup 2)))]
11172   "ix86_match_ccmode (insn, CCGOCmode)
11173    && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
11174 {
11175   switch (get_attr_type (insn))
11176     {
11177     case TYPE_ALU:
11178       if (operands[2] != const1_rtx)
11179         abort ();
11180       return "add{w}\t{%0, %0|%0, %0}";
11181
11182     default:
11183       if (REG_P (operands[2]))
11184         return "sal{w}\t{%b2, %0|%0, %b2}";
11185       else if (GET_CODE (operands[2]) == CONST_INT
11186                && INTVAL (operands[2]) == 1
11187                && (TARGET_SHIFT1 || optimize_size))
11188         return "sal{w}\t%0";
11189       else
11190         return "sal{w}\t{%2, %0|%0, %2}";
11191     }
11192 }
11193   [(set (attr "type")
11194      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11195                           (const_int 0))
11196                       (match_operand 0 "register_operand" ""))
11197                  (match_operand 2 "const1_operand" ""))
11198               (const_string "alu")
11199            ]
11200            (const_string "ishift")))
11201    (set_attr "mode" "HI")])
11202
11203 (define_expand "ashlqi3"
11204   [(set (match_operand:QI 0 "nonimmediate_operand" "")
11205         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "")
11206                    (match_operand:QI 2 "nonmemory_operand" "")))
11207    (clobber (reg:CC 17))]
11208   "TARGET_QIMODE_MATH"
11209   "ix86_expand_binary_operator (ASHIFT, QImode, operands); DONE;")
11210
11211 ;; %%% Potential partial reg stall on alternative 2.  What to do?
11212
11213 (define_insn "*ashlqi3_1_lea"
11214   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r")
11215         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,r")
11216                    (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
11217    (clobber (reg:CC 17))]
11218   "!TARGET_PARTIAL_REG_STALL
11219    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11220 {
11221   switch (get_attr_type (insn))
11222     {
11223     case TYPE_LEA:
11224       return "#";
11225     case TYPE_ALU:
11226       if (operands[2] != const1_rtx)
11227         abort ();
11228       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
11229         return "add{l}\t{%k0, %k0|%k0, %k0}";
11230       else
11231         return "add{b}\t{%0, %0|%0, %0}";
11232
11233     default:
11234       if (REG_P (operands[2]))
11235         {
11236           if (get_attr_mode (insn) == MODE_SI)
11237             return "sal{l}\t{%b2, %k0|%k0, %b2}";
11238           else
11239             return "sal{b}\t{%b2, %0|%0, %b2}";
11240         }
11241       else if (GET_CODE (operands[2]) == CONST_INT
11242                && INTVAL (operands[2]) == 1
11243                && (TARGET_SHIFT1 || optimize_size))
11244         {
11245           if (get_attr_mode (insn) == MODE_SI)
11246             return "sal{l}\t%0";
11247           else
11248             return "sal{b}\t%0";
11249         }
11250       else
11251         {
11252           if (get_attr_mode (insn) == MODE_SI)
11253             return "sal{l}\t{%2, %k0|%k0, %2}";
11254           else
11255             return "sal{b}\t{%2, %0|%0, %2}";
11256         }
11257     }
11258 }
11259   [(set (attr "type")
11260      (cond [(eq_attr "alternative" "2")
11261               (const_string "lea")
11262             (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11263                           (const_int 0))
11264                       (match_operand 0 "register_operand" ""))
11265                  (match_operand 2 "const1_operand" ""))
11266               (const_string "alu")
11267            ]
11268            (const_string "ishift")))
11269    (set_attr "mode" "QI,SI,SI")])
11270
11271 (define_insn "*ashlqi3_1"
11272   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
11273         (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11274                    (match_operand:QI 2 "nonmemory_operand" "cI,cI")))
11275    (clobber (reg:CC 17))]
11276   "TARGET_PARTIAL_REG_STALL
11277    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11278 {
11279   switch (get_attr_type (insn))
11280     {
11281     case TYPE_ALU:
11282       if (operands[2] != const1_rtx)
11283         abort ();
11284       if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
11285         return "add{l}\t{%k0, %k0|%k0, %k0}";
11286       else
11287         return "add{b}\t{%0, %0|%0, %0}";
11288
11289     default:
11290       if (REG_P (operands[2]))
11291         {
11292           if (get_attr_mode (insn) == MODE_SI)
11293             return "sal{l}\t{%b2, %k0|%k0, %b2}";
11294           else
11295             return "sal{b}\t{%b2, %0|%0, %b2}";
11296         }
11297       else if (GET_CODE (operands[2]) == CONST_INT
11298                && INTVAL (operands[2]) == 1
11299                && (TARGET_SHIFT1 || optimize_size))
11300         {
11301           if (get_attr_mode (insn) == MODE_SI)
11302             return "sal{l}\t%0";
11303           else
11304             return "sal{b}\t%0";
11305         }
11306       else
11307         {
11308           if (get_attr_mode (insn) == MODE_SI)
11309             return "sal{l}\t{%2, %k0|%k0, %2}";
11310           else
11311             return "sal{b}\t{%2, %0|%0, %2}";
11312         }
11313     }
11314 }
11315   [(set (attr "type")
11316      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11317                           (const_int 0))
11318                       (match_operand 0 "register_operand" ""))
11319                  (match_operand 2 "const1_operand" ""))
11320               (const_string "alu")
11321            ]
11322            (const_string "ishift")))
11323    (set_attr "mode" "QI,SI")])
11324
11325 ;; This pattern can't accept a variable shift count, since shifts by
11326 ;; zero don't affect the flags.  We assume that shifts by constant
11327 ;; zero are optimized away.
11328 (define_insn "*ashlqi3_cmp"
11329   [(set (reg 17)
11330         (compare
11331           (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11332                      (match_operand:QI 2 "const_int_1_31_operand" "I"))
11333           (const_int 0)))
11334    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11335         (ashift:QI (match_dup 1) (match_dup 2)))]
11336   "ix86_match_ccmode (insn, CCGOCmode)
11337    && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
11338 {
11339   switch (get_attr_type (insn))
11340     {
11341     case TYPE_ALU:
11342       if (operands[2] != const1_rtx)
11343         abort ();
11344       return "add{b}\t{%0, %0|%0, %0}";
11345
11346     default:
11347       if (REG_P (operands[2]))
11348         return "sal{b}\t{%b2, %0|%0, %b2}";
11349       else if (GET_CODE (operands[2]) == CONST_INT
11350                && INTVAL (operands[2]) == 1
11351                && (TARGET_SHIFT1 || optimize_size))
11352         return "sal{b}\t%0";
11353       else
11354         return "sal{b}\t{%2, %0|%0, %2}";
11355     }
11356 }
11357   [(set (attr "type")
11358      (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
11359                           (const_int 0))
11360                       (match_operand 0 "register_operand" ""))
11361                  (match_operand 2 "const1_operand" ""))
11362               (const_string "alu")
11363            ]
11364            (const_string "ishift")))
11365    (set_attr "mode" "QI")])
11366
11367 ;; See comment above `ashldi3' about how this works.
11368
11369 (define_expand "ashrdi3"
11370   [(parallel [(set (match_operand:DI 0 "shiftdi_operand" "")
11371                    (ashiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
11372                                 (match_operand:QI 2 "nonmemory_operand" "")))
11373               (clobber (reg:CC 17))])]
11374   ""
11375 {
11376   if (!TARGET_64BIT && TARGET_CMOVE && ! immediate_operand (operands[2], QImode))
11377     {
11378       emit_insn (gen_ashrdi3_1 (operands[0], operands[1], operands[2]));
11379       DONE;
11380     }
11381   ix86_expand_binary_operator (ASHIFTRT, DImode, operands);
11382   DONE;
11383 })
11384
11385 (define_insn "ashrdi3_63_rex64"
11386   [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
11387         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
11388                      (match_operand:DI 2 "const_int_operand" "i,i")))
11389    (clobber (reg:CC 17))]
11390   "TARGET_64BIT && INTVAL (operands[2]) == 63 && (TARGET_USE_CLTD || optimize_size)
11391    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11392   "@
11393    {cqto|cqo}
11394    sar{q}\t{%2, %0|%0, %2}"
11395   [(set_attr "type" "imovx,ishift")
11396    (set_attr "prefix_0f" "0,*")
11397    (set_attr "length_immediate" "0,*")
11398    (set_attr "modrm" "0,1")
11399    (set_attr "mode" "DI")])
11400
11401 (define_insn "*ashrdi3_1_one_bit_rex64"
11402   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11403         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11404                      (match_operand:QI 2 "const1_operand" "")))
11405    (clobber (reg:CC 17))]
11406   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)
11407    && (TARGET_SHIFT1 || optimize_size)"
11408   "sar{q}\t%0"
11409   [(set_attr "type" "ishift")
11410    (set (attr "length") 
11411      (if_then_else (match_operand:DI 0 "register_operand" "") 
11412         (const_string "2")
11413         (const_string "*")))])
11414
11415 (define_insn "*ashrdi3_1_rex64"
11416   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11417         (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11418                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
11419    (clobber (reg:CC 17))]
11420   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11421   "@
11422    sar{q}\t{%2, %0|%0, %2}
11423    sar{q}\t{%b2, %0|%0, %b2}"
11424   [(set_attr "type" "ishift")
11425    (set_attr "mode" "DI")])
11426
11427 ;; This pattern can't accept a variable shift count, since shifts by
11428 ;; zero don't affect the flags.  We assume that shifts by constant
11429 ;; zero are optimized away.
11430 (define_insn "*ashrdi3_one_bit_cmp_rex64"
11431   [(set (reg 17)
11432         (compare
11433           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11434                        (match_operand:QI 2 "const1_operand" ""))
11435           (const_int 0)))
11436    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11437         (ashiftrt:DI (match_dup 1) (match_dup 2)))]
11438   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11439    && (TARGET_SHIFT1 || optimize_size)
11440    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11441   "sar{q}\t%0"
11442   [(set_attr "type" "ishift")
11443    (set (attr "length") 
11444      (if_then_else (match_operand:DI 0 "register_operand" "") 
11445         (const_string "2")
11446         (const_string "*")))])
11447
11448 ;; This pattern can't accept a variable shift count, since shifts by
11449 ;; zero don't affect the flags.  We assume that shifts by constant
11450 ;; zero are optimized away.
11451 (define_insn "*ashrdi3_cmp_rex64"
11452   [(set (reg 17)
11453         (compare
11454           (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11455                        (match_operand:QI 2 "const_int_operand" "n"))
11456           (const_int 0)))
11457    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11458         (ashiftrt:DI (match_dup 1) (match_dup 2)))]
11459   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11460    && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11461   "sar{q}\t{%2, %0|%0, %2}"
11462   [(set_attr "type" "ishift")
11463    (set_attr "mode" "DI")])
11464
11465
11466 (define_insn "ashrdi3_1"
11467   [(set (match_operand:DI 0 "register_operand" "=r")
11468         (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
11469                      (match_operand:QI 2 "nonmemory_operand" "Jc")))
11470    (clobber (match_scratch:SI 3 "=&r"))
11471    (clobber (reg:CC 17))]
11472   "!TARGET_64BIT && TARGET_CMOVE"
11473   "#"
11474   [(set_attr "type" "multi")])
11475
11476 (define_insn "*ashrdi3_2"
11477   [(set (match_operand:DI 0 "register_operand" "=r")
11478         (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
11479                      (match_operand:QI 2 "nonmemory_operand" "Jc")))
11480    (clobber (reg:CC 17))]
11481   "!TARGET_64BIT"
11482   "#"
11483   [(set_attr "type" "multi")])
11484
11485 (define_split
11486   [(set (match_operand:DI 0 "register_operand" "")
11487         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
11488                      (match_operand:QI 2 "nonmemory_operand" "")))
11489    (clobber (match_scratch:SI 3 ""))
11490    (clobber (reg:CC 17))]
11491   "!TARGET_64BIT && TARGET_CMOVE && reload_completed"
11492   [(const_int 0)]
11493   "ix86_split_ashrdi (operands, operands[3]); DONE;")
11494
11495 (define_split
11496   [(set (match_operand:DI 0 "register_operand" "")
11497         (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
11498                      (match_operand:QI 2 "nonmemory_operand" "")))
11499    (clobber (reg:CC 17))]
11500   "!TARGET_64BIT && reload_completed"
11501   [(const_int 0)]
11502   "ix86_split_ashrdi (operands, NULL_RTX); DONE;")
11503
11504 (define_insn "x86_shrd_1"
11505   [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
11506         (ior:SI (ashiftrt:SI (match_dup 0)
11507                   (match_operand:QI 2 "nonmemory_operand" "I,c"))
11508                 (ashift:SI (match_operand:SI 1 "register_operand" "r,r")
11509                   (minus:QI (const_int 32) (match_dup 2)))))
11510    (clobber (reg:CC 17))]
11511   ""
11512   "@
11513    shrd{l}\t{%2, %1, %0|%0, %1, %2}
11514    shrd{l}\t{%s2%1, %0|%0, %1, %2}"
11515   [(set_attr "type" "ishift")
11516    (set_attr "prefix_0f" "1")
11517    (set_attr "pent_pair" "np")
11518    (set_attr "ppro_uops" "few")
11519    (set_attr "mode" "SI")])
11520
11521 (define_expand "x86_shift_adj_3"
11522   [(use (match_operand:SI 0 "register_operand" ""))
11523    (use (match_operand:SI 1 "register_operand" ""))
11524    (use (match_operand:QI 2 "register_operand" ""))]
11525   ""
11526 {
11527   rtx label = gen_label_rtx ();
11528   rtx tmp;
11529
11530   emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
11531
11532   tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
11533   tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
11534   tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
11535                               gen_rtx_LABEL_REF (VOIDmode, label),
11536                               pc_rtx);
11537   tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
11538   JUMP_LABEL (tmp) = label;
11539
11540   emit_move_insn (operands[0], operands[1]);
11541   emit_insn (gen_ashrsi3_31 (operands[1], operands[1], GEN_INT (31)));
11542
11543   emit_label (label);
11544   LABEL_NUSES (label) = 1;
11545
11546   DONE;
11547 })
11548
11549 (define_insn "ashrsi3_31"
11550   [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
11551         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
11552                      (match_operand:SI 2 "const_int_operand" "i,i")))
11553    (clobber (reg:CC 17))]
11554   "INTVAL (operands[2]) == 31 && (TARGET_USE_CLTD || optimize_size)
11555    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11556   "@
11557    {cltd|cdq}
11558    sar{l}\t{%2, %0|%0, %2}"
11559   [(set_attr "type" "imovx,ishift")
11560    (set_attr "prefix_0f" "0,*")
11561    (set_attr "length_immediate" "0,*")
11562    (set_attr "modrm" "0,1")
11563    (set_attr "mode" "SI")])
11564
11565 (define_insn "*ashrsi3_31_zext"
11566   [(set (match_operand:DI 0 "register_operand" "=*d,r")
11567         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
11568                                      (match_operand:SI 2 "const_int_operand" "i,i"))))
11569    (clobber (reg:CC 17))]
11570   "TARGET_64BIT && (TARGET_USE_CLTD || optimize_size)
11571    && INTVAL (operands[2]) == 31
11572    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11573   "@
11574    {cltd|cdq}
11575    sar{l}\t{%2, %k0|%k0, %2}"
11576   [(set_attr "type" "imovx,ishift")
11577    (set_attr "prefix_0f" "0,*")
11578    (set_attr "length_immediate" "0,*")
11579    (set_attr "modrm" "0,1")
11580    (set_attr "mode" "SI")])
11581
11582 (define_expand "ashrsi3"
11583   [(set (match_operand:SI 0 "nonimmediate_operand" "")
11584         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
11585                      (match_operand:QI 2 "nonmemory_operand" "")))
11586    (clobber (reg:CC 17))]
11587   ""
11588   "ix86_expand_binary_operator (ASHIFTRT, SImode, operands); DONE;")
11589
11590 (define_insn "*ashrsi3_1_one_bit"
11591   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11592         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11593                      (match_operand:QI 2 "const1_operand" "")))
11594    (clobber (reg:CC 17))]
11595   "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
11596    && (TARGET_SHIFT1 || optimize_size)"
11597   "sar{l}\t%0"
11598   [(set_attr "type" "ishift")
11599    (set (attr "length") 
11600      (if_then_else (match_operand:SI 0 "register_operand" "") 
11601         (const_string "2")
11602         (const_string "*")))])
11603
11604 (define_insn "*ashrsi3_1_one_bit_zext"
11605   [(set (match_operand:DI 0 "register_operand" "=r")
11606         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11607                                      (match_operand:QI 2 "const1_operand" ""))))
11608    (clobber (reg:CC 17))]
11609   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
11610    && (TARGET_SHIFT1 || optimize_size)"
11611   "sar{l}\t%k0"
11612   [(set_attr "type" "ishift")
11613    (set_attr "length" "2")])
11614
11615 (define_insn "*ashrsi3_1"
11616   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11617         (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11618                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
11619    (clobber (reg:CC 17))]
11620   "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11621   "@
11622    sar{l}\t{%2, %0|%0, %2}
11623    sar{l}\t{%b2, %0|%0, %b2}"
11624   [(set_attr "type" "ishift")
11625    (set_attr "mode" "SI")])
11626
11627 (define_insn "*ashrsi3_1_zext"
11628   [(set (match_operand:DI 0 "register_operand" "=r,r")
11629         (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0")
11630                                      (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11631    (clobber (reg:CC 17))]
11632   "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11633   "@
11634    sar{l}\t{%2, %k0|%k0, %2}
11635    sar{l}\t{%b2, %k0|%k0, %b2}"
11636   [(set_attr "type" "ishift")
11637    (set_attr "mode" "SI")])
11638
11639 ;; This pattern can't accept a variable shift count, since shifts by
11640 ;; zero don't affect the flags.  We assume that shifts by constant
11641 ;; zero are optimized away.
11642 (define_insn "*ashrsi3_one_bit_cmp"
11643   [(set (reg 17)
11644         (compare
11645           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11646                        (match_operand:QI 2 "const1_operand" ""))
11647           (const_int 0)))
11648    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11649         (ashiftrt:SI (match_dup 1) (match_dup 2)))]
11650   "ix86_match_ccmode (insn, CCGOCmode)
11651    && (TARGET_SHIFT1 || optimize_size)
11652    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11653   "sar{l}\t%0"
11654   [(set_attr "type" "ishift")
11655    (set (attr "length") 
11656      (if_then_else (match_operand:SI 0 "register_operand" "") 
11657         (const_string "2")
11658         (const_string "*")))])
11659
11660 (define_insn "*ashrsi3_one_bit_cmp_zext"
11661   [(set (reg 17)
11662         (compare
11663           (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11664                        (match_operand:QI 2 "const1_operand" ""))
11665           (const_int 0)))
11666    (set (match_operand:DI 0 "register_operand" "=r")
11667         (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
11668   "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
11669    && (TARGET_SHIFT1 || optimize_size)
11670    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11671   "sar{l}\t%k0"
11672   [(set_attr "type" "ishift")
11673    (set_attr "length" "2")])
11674
11675 ;; This pattern can't accept a variable shift count, since shifts by
11676 ;; zero don't affect the flags.  We assume that shifts by constant
11677 ;; zero are optimized away.
11678 (define_insn "*ashrsi3_cmp"
11679   [(set (reg 17)
11680         (compare
11681           (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11682                        (match_operand:QI 2 "const_int_1_31_operand" "I"))
11683           (const_int 0)))
11684    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11685         (ashiftrt:SI (match_dup 1) (match_dup 2)))]
11686   "ix86_match_ccmode (insn, CCGOCmode)
11687    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11688   "sar{l}\t{%2, %0|%0, %2}"
11689   [(set_attr "type" "ishift")
11690    (set_attr "mode" "SI")])
11691
11692 (define_insn "*ashrsi3_cmp_zext"
11693   [(set (reg 17)
11694         (compare
11695           (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11696                        (match_operand:QI 2 "const_int_1_31_operand" "I"))
11697           (const_int 0)))
11698    (set (match_operand:DI 0 "register_operand" "=r")
11699         (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
11700   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11701    && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11702   "sar{l}\t{%2, %k0|%k0, %2}"
11703   [(set_attr "type" "ishift")
11704    (set_attr "mode" "SI")])
11705
11706 (define_expand "ashrhi3"
11707   [(set (match_operand:HI 0 "nonimmediate_operand" "")
11708         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
11709                      (match_operand:QI 2 "nonmemory_operand" "")))
11710    (clobber (reg:CC 17))]
11711   "TARGET_HIMODE_MATH"
11712   "ix86_expand_binary_operator (ASHIFTRT, HImode, operands); DONE;")
11713
11714 (define_insn "*ashrhi3_1_one_bit"
11715   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11716         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11717                      (match_operand:QI 2 "const1_operand" "")))
11718    (clobber (reg:CC 17))]
11719   "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)
11720    && (TARGET_SHIFT1 || optimize_size)"
11721   "sar{w}\t%0"
11722   [(set_attr "type" "ishift")
11723    (set (attr "length") 
11724      (if_then_else (match_operand 0 "register_operand" "") 
11725         (const_string "2")
11726         (const_string "*")))])
11727
11728 (define_insn "*ashrhi3_1"
11729   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11730         (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11731                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
11732    (clobber (reg:CC 17))]
11733   "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11734   "@
11735    sar{w}\t{%2, %0|%0, %2}
11736    sar{w}\t{%b2, %0|%0, %b2}"
11737   [(set_attr "type" "ishift")
11738    (set_attr "mode" "HI")])
11739
11740 ;; This pattern can't accept a variable shift count, since shifts by
11741 ;; zero don't affect the flags.  We assume that shifts by constant
11742 ;; zero are optimized away.
11743 (define_insn "*ashrhi3_one_bit_cmp"
11744   [(set (reg 17)
11745         (compare
11746           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11747                        (match_operand:QI 2 "const1_operand" ""))
11748           (const_int 0)))
11749    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11750         (ashiftrt:HI (match_dup 1) (match_dup 2)))]
11751   "ix86_match_ccmode (insn, CCGOCmode)
11752    && (TARGET_SHIFT1 || optimize_size)
11753    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11754   "sar{w}\t%0"
11755   [(set_attr "type" "ishift")
11756    (set (attr "length") 
11757      (if_then_else (match_operand 0 "register_operand" "") 
11758         (const_string "2")
11759         (const_string "*")))])
11760
11761 ;; This pattern can't accept a variable shift count, since shifts by
11762 ;; zero don't affect the flags.  We assume that shifts by constant
11763 ;; zero are optimized away.
11764 (define_insn "*ashrhi3_cmp"
11765   [(set (reg 17)
11766         (compare
11767           (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11768                        (match_operand:QI 2 "const_int_1_31_operand" "I"))
11769           (const_int 0)))
11770    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11771         (ashiftrt:HI (match_dup 1) (match_dup 2)))]
11772   "ix86_match_ccmode (insn, CCGOCmode)
11773    && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11774   "sar{w}\t{%2, %0|%0, %2}"
11775   [(set_attr "type" "ishift")
11776    (set_attr "mode" "HI")])
11777
11778 (define_expand "ashrqi3"
11779   [(set (match_operand:QI 0 "nonimmediate_operand" "")
11780         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
11781                      (match_operand:QI 2 "nonmemory_operand" "")))
11782    (clobber (reg:CC 17))]
11783   "TARGET_QIMODE_MATH"
11784   "ix86_expand_binary_operator (ASHIFTRT, QImode, operands); DONE;")
11785
11786 (define_insn "*ashrqi3_1_one_bit"
11787   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11788         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11789                      (match_operand:QI 2 "const1_operand" "")))
11790    (clobber (reg:CC 17))]
11791   "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
11792    && (TARGET_SHIFT1 || optimize_size)"
11793   "sar{b}\t%0"
11794   [(set_attr "type" "ishift")
11795    (set (attr "length") 
11796      (if_then_else (match_operand 0 "register_operand" "") 
11797         (const_string "2")
11798         (const_string "*")))])
11799
11800 (define_insn "*ashrqi3_1_one_bit_slp"
11801   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11802         (ashiftrt:QI (match_dup 0)
11803                      (match_operand:QI 1 "const1_operand" "")))
11804    (clobber (reg:CC 17))]
11805   "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
11806    && (! TARGET_PARTIAL_REG_STALL || optimize_size)
11807    && (TARGET_SHIFT1 || optimize_size)"
11808   "sar{b}\t%0"
11809   [(set_attr "type" "ishift1")
11810    (set (attr "length") 
11811      (if_then_else (match_operand 0 "register_operand" "") 
11812         (const_string "2")
11813         (const_string "*")))])
11814
11815 (define_insn "*ashrqi3_1"
11816   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11817         (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11818                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
11819    (clobber (reg:CC 17))]
11820   "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11821   "@
11822    sar{b}\t{%2, %0|%0, %2}
11823    sar{b}\t{%b2, %0|%0, %b2}"
11824   [(set_attr "type" "ishift")
11825    (set_attr "mode" "QI")])
11826
11827 (define_insn "*ashrqi3_1_slp"
11828   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11829         (ashiftrt:QI (match_dup 0)
11830                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
11831    (clobber (reg:CC 17))]
11832   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11833    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11834   "@
11835    sar{b}\t{%1, %0|%0, %1}
11836    sar{b}\t{%b1, %0|%0, %b1}"
11837   [(set_attr "type" "ishift1")
11838    (set_attr "mode" "QI")])
11839
11840 ;; This pattern can't accept a variable shift count, since shifts by
11841 ;; zero don't affect the flags.  We assume that shifts by constant
11842 ;; zero are optimized away.
11843 (define_insn "*ashrqi3_one_bit_cmp"
11844   [(set (reg 17)
11845         (compare
11846           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11847                        (match_operand:QI 2 "const1_operand" "I"))
11848           (const_int 0)))
11849    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11850         (ashiftrt:QI (match_dup 1) (match_dup 2)))]
11851   "ix86_match_ccmode (insn, CCGOCmode)
11852    && (TARGET_SHIFT1 || optimize_size)
11853    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11854   "sar{b}\t%0"
11855   [(set_attr "type" "ishift")
11856    (set (attr "length") 
11857      (if_then_else (match_operand 0 "register_operand" "") 
11858         (const_string "2")
11859         (const_string "*")))])
11860
11861 ;; This pattern can't accept a variable shift count, since shifts by
11862 ;; zero don't affect the flags.  We assume that shifts by constant
11863 ;; zero are optimized away.
11864 (define_insn "*ashrqi3_cmp"
11865   [(set (reg 17)
11866         (compare
11867           (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11868                        (match_operand:QI 2 "const_int_1_31_operand" "I"))
11869           (const_int 0)))
11870    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11871         (ashiftrt:QI (match_dup 1) (match_dup 2)))]
11872   "ix86_match_ccmode (insn, CCGOCmode)
11873    && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11874   "sar{b}\t{%2, %0|%0, %2}"
11875   [(set_attr "type" "ishift")
11876    (set_attr "mode" "QI")])
11877 \f
11878 ;; Logical shift instructions
11879
11880 ;; See comment above `ashldi3' about how this works.
11881
11882 (define_expand "lshrdi3"
11883   [(parallel [(set (match_operand:DI 0 "shiftdi_operand" "")
11884                    (lshiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
11885                                 (match_operand:QI 2 "nonmemory_operand" "")))
11886               (clobber (reg:CC 17))])]
11887   ""
11888 {
11889   if (!TARGET_64BIT && TARGET_CMOVE && ! immediate_operand (operands[2], QImode))
11890     {
11891       emit_insn (gen_lshrdi3_1 (operands[0], operands[1], operands[2]));
11892       DONE;
11893     }
11894   ix86_expand_binary_operator (LSHIFTRT, DImode, operands);
11895   DONE;
11896 })
11897
11898 (define_insn "*lshrdi3_1_one_bit_rex64"
11899   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11900         (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11901                      (match_operand:QI 2 "const1_operand" "")))
11902    (clobber (reg:CC 17))]
11903   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11904    && (TARGET_SHIFT1 || optimize_size)"
11905   "shr{q}\t%0"
11906   [(set_attr "type" "ishift")
11907    (set (attr "length") 
11908      (if_then_else (match_operand:DI 0 "register_operand" "") 
11909         (const_string "2")
11910         (const_string "*")))])
11911
11912 (define_insn "*lshrdi3_1_rex64"
11913   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11914         (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11915                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
11916    (clobber (reg:CC 17))]
11917   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11918   "@
11919    shr{q}\t{%2, %0|%0, %2}
11920    shr{q}\t{%b2, %0|%0, %b2}"
11921   [(set_attr "type" "ishift")
11922    (set_attr "mode" "DI")])
11923
11924 ;; This pattern can't accept a variable shift count, since shifts by
11925 ;; zero don't affect the flags.  We assume that shifts by constant
11926 ;; zero are optimized away.
11927 (define_insn "*lshrdi3_cmp_one_bit_rex64"
11928   [(set (reg 17)
11929         (compare
11930           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11931                        (match_operand:QI 2 "const1_operand" ""))
11932           (const_int 0)))
11933    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11934         (lshiftrt:DI (match_dup 1) (match_dup 2)))]
11935   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11936    && (TARGET_SHIFT1 || optimize_size)
11937    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11938   "shr{q}\t%0"
11939   [(set_attr "type" "ishift")
11940    (set (attr "length") 
11941      (if_then_else (match_operand:DI 0 "register_operand" "") 
11942         (const_string "2")
11943         (const_string "*")))])
11944
11945 ;; This pattern can't accept a variable shift count, since shifts by
11946 ;; zero don't affect the flags.  We assume that shifts by constant
11947 ;; zero are optimized away.
11948 (define_insn "*lshrdi3_cmp_rex64"
11949   [(set (reg 17)
11950         (compare
11951           (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11952                        (match_operand:QI 2 "const_int_operand" "e"))
11953           (const_int 0)))
11954    (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11955         (lshiftrt:DI (match_dup 1) (match_dup 2)))]
11956   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11957    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11958   "shr{q}\t{%2, %0|%0, %2}"
11959   [(set_attr "type" "ishift")
11960    (set_attr "mode" "DI")])
11961
11962 (define_insn "lshrdi3_1"
11963   [(set (match_operand:DI 0 "register_operand" "=r")
11964         (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
11965                      (match_operand:QI 2 "nonmemory_operand" "Jc")))
11966    (clobber (match_scratch:SI 3 "=&r"))
11967    (clobber (reg:CC 17))]
11968   "!TARGET_64BIT && TARGET_CMOVE"
11969   "#"
11970   [(set_attr "type" "multi")])
11971
11972 (define_insn "*lshrdi3_2"
11973   [(set (match_operand:DI 0 "register_operand" "=r")
11974         (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
11975                      (match_operand:QI 2 "nonmemory_operand" "Jc")))
11976    (clobber (reg:CC 17))]
11977   "!TARGET_64BIT"
11978   "#"
11979   [(set_attr "type" "multi")])
11980
11981 (define_split 
11982   [(set (match_operand:DI 0 "register_operand" "")
11983         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
11984                      (match_operand:QI 2 "nonmemory_operand" "")))
11985    (clobber (match_scratch:SI 3 ""))
11986    (clobber (reg:CC 17))]
11987   "!TARGET_64BIT && TARGET_CMOVE && reload_completed"
11988   [(const_int 0)]
11989   "ix86_split_lshrdi (operands, operands[3]); DONE;")
11990
11991 (define_split 
11992   [(set (match_operand:DI 0 "register_operand" "")
11993         (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
11994                      (match_operand:QI 2 "nonmemory_operand" "")))
11995    (clobber (reg:CC 17))]
11996   "!TARGET_64BIT && reload_completed"
11997   [(const_int 0)]
11998   "ix86_split_lshrdi (operands, NULL_RTX); DONE;")
11999
12000 (define_expand "lshrsi3"
12001   [(set (match_operand:SI 0 "nonimmediate_operand" "")
12002         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
12003                      (match_operand:QI 2 "nonmemory_operand" "")))
12004    (clobber (reg:CC 17))]
12005   ""
12006   "ix86_expand_binary_operator (LSHIFTRT, SImode, operands); DONE;")
12007
12008 (define_insn "*lshrsi3_1_one_bit"
12009   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12010         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12011                      (match_operand:QI 2 "const1_operand" "")))
12012    (clobber (reg:CC 17))]
12013   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
12014    && (TARGET_SHIFT1 || optimize_size)"
12015   "shr{l}\t%0"
12016   [(set_attr "type" "ishift")
12017    (set (attr "length") 
12018      (if_then_else (match_operand:SI 0 "register_operand" "") 
12019         (const_string "2")
12020         (const_string "*")))])
12021
12022 (define_insn "*lshrsi3_1_one_bit_zext"
12023   [(set (match_operand:DI 0 "register_operand" "=r")
12024         (lshiftrt:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "0"))
12025                      (match_operand:QI 2 "const1_operand" "")))
12026    (clobber (reg:CC 17))]
12027   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
12028    && (TARGET_SHIFT1 || optimize_size)"
12029   "shr{l}\t%k0"
12030   [(set_attr "type" "ishift")
12031    (set_attr "length" "2")])
12032
12033 (define_insn "*lshrsi3_1"
12034   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12035         (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12036                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12037    (clobber (reg:CC 17))]
12038   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12039   "@
12040    shr{l}\t{%2, %0|%0, %2}
12041    shr{l}\t{%b2, %0|%0, %b2}"
12042   [(set_attr "type" "ishift")
12043    (set_attr "mode" "SI")])
12044
12045 (define_insn "*lshrsi3_1_zext"
12046   [(set (match_operand:DI 0 "register_operand" "=r,r")
12047         (zero_extend:DI
12048           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12049                        (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12050    (clobber (reg:CC 17))]
12051   "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12052   "@
12053    shr{l}\t{%2, %k0|%k0, %2}
12054    shr{l}\t{%b2, %k0|%k0, %b2}"
12055   [(set_attr "type" "ishift")
12056    (set_attr "mode" "SI")])
12057
12058 ;; This pattern can't accept a variable shift count, since shifts by
12059 ;; zero don't affect the flags.  We assume that shifts by constant
12060 ;; zero are optimized away.
12061 (define_insn "*lshrsi3_one_bit_cmp"
12062   [(set (reg 17)
12063         (compare
12064           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12065                        (match_operand:QI 2 "const1_operand" ""))
12066           (const_int 0)))
12067    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12068         (lshiftrt:SI (match_dup 1) (match_dup 2)))]
12069   "ix86_match_ccmode (insn, CCGOCmode)
12070    && (TARGET_SHIFT1 || optimize_size)
12071    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12072   "shr{l}\t%0"
12073   [(set_attr "type" "ishift")
12074    (set (attr "length") 
12075      (if_then_else (match_operand:SI 0 "register_operand" "") 
12076         (const_string "2")
12077         (const_string "*")))])
12078
12079 (define_insn "*lshrsi3_cmp_one_bit_zext"
12080   [(set (reg 17)
12081         (compare
12082           (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
12083                        (match_operand:QI 2 "const1_operand" ""))
12084           (const_int 0)))
12085    (set (match_operand:DI 0 "register_operand" "=r")
12086         (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
12087   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
12088    && (TARGET_SHIFT1 || optimize_size)
12089    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12090   "shr{l}\t%k0"
12091   [(set_attr "type" "ishift")
12092    (set_attr "length" "2")])
12093
12094 ;; This pattern can't accept a variable shift count, since shifts by
12095 ;; zero don't affect the flags.  We assume that shifts by constant
12096 ;; zero are optimized away.
12097 (define_insn "*lshrsi3_cmp"
12098   [(set (reg 17)
12099         (compare
12100           (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12101                        (match_operand:QI 2 "const_int_1_31_operand" "I"))
12102           (const_int 0)))
12103    (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12104         (lshiftrt:SI (match_dup 1) (match_dup 2)))]
12105   "ix86_match_ccmode (insn, CCGOCmode)
12106    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12107   "shr{l}\t{%2, %0|%0, %2}"
12108   [(set_attr "type" "ishift")
12109    (set_attr "mode" "SI")])
12110
12111 (define_insn "*lshrsi3_cmp_zext"
12112   [(set (reg 17)
12113         (compare
12114           (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
12115                        (match_operand:QI 2 "const_int_1_31_operand" "I"))
12116           (const_int 0)))
12117    (set (match_operand:DI 0 "register_operand" "=r")
12118         (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
12119   "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
12120    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12121   "shr{l}\t{%2, %k0|%k0, %2}"
12122   [(set_attr "type" "ishift")
12123    (set_attr "mode" "SI")])
12124
12125 (define_expand "lshrhi3"
12126   [(set (match_operand:HI 0 "nonimmediate_operand" "")
12127         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
12128                      (match_operand:QI 2 "nonmemory_operand" "")))
12129    (clobber (reg:CC 17))]
12130   "TARGET_HIMODE_MATH"
12131   "ix86_expand_binary_operator (LSHIFTRT, HImode, operands); DONE;")
12132
12133 (define_insn "*lshrhi3_1_one_bit"
12134   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12135         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12136                      (match_operand:QI 2 "const1_operand" "")))
12137    (clobber (reg:CC 17))]
12138   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
12139    && (TARGET_SHIFT1 || optimize_size)"
12140   "shr{w}\t%0"
12141   [(set_attr "type" "ishift")
12142    (set (attr "length") 
12143      (if_then_else (match_operand 0 "register_operand" "") 
12144         (const_string "2")
12145         (const_string "*")))])
12146
12147 (define_insn "*lshrhi3_1"
12148   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12149         (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12150                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12151    (clobber (reg:CC 17))]
12152   "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12153   "@
12154    shr{w}\t{%2, %0|%0, %2}
12155    shr{w}\t{%b2, %0|%0, %b2}"
12156   [(set_attr "type" "ishift")
12157    (set_attr "mode" "HI")])
12158
12159 ;; This pattern can't accept a variable shift count, since shifts by
12160 ;; zero don't affect the flags.  We assume that shifts by constant
12161 ;; zero are optimized away.
12162 (define_insn "*lshrhi3_one_bit_cmp"
12163   [(set (reg 17)
12164         (compare
12165           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12166                        (match_operand:QI 2 "const1_operand" ""))
12167           (const_int 0)))
12168    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12169         (lshiftrt:HI (match_dup 1) (match_dup 2)))]
12170   "ix86_match_ccmode (insn, CCGOCmode)
12171    && (TARGET_SHIFT1 || optimize_size)
12172    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12173   "shr{w}\t%0"
12174   [(set_attr "type" "ishift")
12175    (set (attr "length") 
12176      (if_then_else (match_operand:SI 0 "register_operand" "") 
12177         (const_string "2")
12178         (const_string "*")))])
12179
12180 ;; This pattern can't accept a variable shift count, since shifts by
12181 ;; zero don't affect the flags.  We assume that shifts by constant
12182 ;; zero are optimized away.
12183 (define_insn "*lshrhi3_cmp"
12184   [(set (reg 17)
12185         (compare
12186           (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12187                        (match_operand:QI 2 "const_int_1_31_operand" "I"))
12188           (const_int 0)))
12189    (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12190         (lshiftrt:HI (match_dup 1) (match_dup 2)))]
12191   "ix86_match_ccmode (insn, CCGOCmode)
12192    && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
12193   "shr{w}\t{%2, %0|%0, %2}"
12194   [(set_attr "type" "ishift")
12195    (set_attr "mode" "HI")])
12196
12197 (define_expand "lshrqi3"
12198   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12199         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
12200                      (match_operand:QI 2 "nonmemory_operand" "")))
12201    (clobber (reg:CC 17))]
12202   "TARGET_QIMODE_MATH"
12203   "ix86_expand_binary_operator (LSHIFTRT, QImode, operands); DONE;")
12204
12205 (define_insn "*lshrqi3_1_one_bit"
12206   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12207         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12208                      (match_operand:QI 2 "const1_operand" "")))
12209    (clobber (reg:CC 17))]
12210   "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)
12211    && (TARGET_SHIFT1 || optimize_size)"
12212   "shr{b}\t%0"
12213   [(set_attr "type" "ishift")
12214    (set (attr "length") 
12215      (if_then_else (match_operand 0 "register_operand" "") 
12216         (const_string "2")
12217         (const_string "*")))])
12218
12219 (define_insn "*lshrqi3_1_one_bit_slp"
12220   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12221         (lshiftrt:QI (match_dup 0)
12222                      (match_operand:QI 1 "const1_operand" "")))
12223    (clobber (reg:CC 17))]
12224   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12225    && (TARGET_SHIFT1 || optimize_size)"
12226   "shr{b}\t%0"
12227   [(set_attr "type" "ishift1")
12228    (set (attr "length") 
12229      (if_then_else (match_operand 0 "register_operand" "") 
12230         (const_string "2")
12231         (const_string "*")))])
12232
12233 (define_insn "*lshrqi3_1"
12234   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12235         (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12236                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12237    (clobber (reg:CC 17))]
12238   "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
12239   "@
12240    shr{b}\t{%2, %0|%0, %2}
12241    shr{b}\t{%b2, %0|%0, %b2}"
12242   [(set_attr "type" "ishift")
12243    (set_attr "mode" "QI")])
12244
12245 (define_insn "*lshrqi3_1_slp"
12246   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12247         (lshiftrt:QI (match_dup 0)
12248                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
12249    (clobber (reg:CC 17))]
12250   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12251    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
12252   "@
12253    shr{b}\t{%1, %0|%0, %1}
12254    shr{b}\t{%b1, %0|%0, %b1}"
12255   [(set_attr "type" "ishift1")
12256    (set_attr "mode" "QI")])
12257
12258 ;; This pattern can't accept a variable shift count, since shifts by
12259 ;; zero don't affect the flags.  We assume that shifts by constant
12260 ;; zero are optimized away.
12261 (define_insn "*lshrqi2_one_bit_cmp"
12262   [(set (reg 17)
12263         (compare
12264           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12265                        (match_operand:QI 2 "const1_operand" ""))
12266           (const_int 0)))
12267    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12268         (lshiftrt:QI (match_dup 1) (match_dup 2)))]
12269   "ix86_match_ccmode (insn, CCGOCmode)
12270    && (TARGET_SHIFT1 || optimize_size)
12271    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
12272   "shr{b}\t%0"
12273   [(set_attr "type" "ishift")
12274    (set (attr "length") 
12275      (if_then_else (match_operand:SI 0 "register_operand" "") 
12276         (const_string "2")
12277         (const_string "*")))])
12278
12279 ;; This pattern can't accept a variable shift count, since shifts by
12280 ;; zero don't affect the flags.  We assume that shifts by constant
12281 ;; zero are optimized away.
12282 (define_insn "*lshrqi2_cmp"
12283   [(set (reg 17)
12284         (compare
12285           (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12286                        (match_operand:QI 2 "const_int_1_31_operand" "I"))
12287           (const_int 0)))
12288    (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12289         (lshiftrt:QI (match_dup 1) (match_dup 2)))]
12290   "ix86_match_ccmode (insn, CCGOCmode)
12291    && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
12292   "shr{b}\t{%2, %0|%0, %2}"
12293   [(set_attr "type" "ishift")
12294    (set_attr "mode" "QI")])
12295 \f
12296 ;; Rotate instructions
12297
12298 (define_expand "rotldi3"
12299   [(set (match_operand:DI 0 "nonimmediate_operand" "")
12300         (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "")
12301                    (match_operand:QI 2 "nonmemory_operand" "")))
12302    (clobber (reg:CC 17))]
12303   "TARGET_64BIT"
12304   "ix86_expand_binary_operator (ROTATE, DImode, operands); DONE;")
12305
12306 (define_insn "*rotlsi3_1_one_bit_rex64"
12307   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12308         (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12309                    (match_operand:QI 2 "const1_operand" "")))
12310    (clobber (reg:CC 17))]
12311   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)
12312    && (TARGET_SHIFT1 || optimize_size)"
12313   "rol{q}\t%0"
12314   [(set_attr "type" "rotate")
12315    (set (attr "length") 
12316      (if_then_else (match_operand:DI 0 "register_operand" "") 
12317         (const_string "2")
12318         (const_string "*")))])
12319
12320 (define_insn "*rotldi3_1_rex64"
12321   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
12322         (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
12323                    (match_operand:QI 2 "nonmemory_operand" "e,c")))
12324    (clobber (reg:CC 17))]
12325   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)"
12326   "@
12327    rol{q}\t{%2, %0|%0, %2}
12328    rol{q}\t{%b2, %0|%0, %b2}"
12329   [(set_attr "type" "rotate")
12330    (set_attr "mode" "DI")])
12331
12332 (define_expand "rotlsi3"
12333   [(set (match_operand:SI 0 "nonimmediate_operand" "")
12334         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
12335                    (match_operand:QI 2 "nonmemory_operand" "")))
12336    (clobber (reg:CC 17))]
12337   ""
12338   "ix86_expand_binary_operator (ROTATE, SImode, operands); DONE;")
12339
12340 (define_insn "*rotlsi3_1_one_bit"
12341   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12342         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12343                    (match_operand:QI 2 "const1_operand" "")))
12344    (clobber (reg:CC 17))]
12345   "ix86_binary_operator_ok (ROTATE, SImode, operands)
12346    && (TARGET_SHIFT1 || optimize_size)"
12347   "rol{l}\t%0"
12348   [(set_attr "type" "rotate")
12349    (set (attr "length") 
12350      (if_then_else (match_operand:SI 0 "register_operand" "") 
12351         (const_string "2")
12352         (const_string "*")))])
12353
12354 (define_insn "*rotlsi3_1_one_bit_zext"
12355   [(set (match_operand:DI 0 "register_operand" "=r")
12356         (zero_extend:DI
12357           (rotate:SI (match_operand:SI 1 "register_operand" "0")
12358                      (match_operand:QI 2 "const1_operand" ""))))
12359    (clobber (reg:CC 17))]
12360   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)
12361    && (TARGET_SHIFT1 || optimize_size)"
12362   "rol{l}\t%k0"
12363   [(set_attr "type" "rotate")
12364    (set_attr "length" "2")])
12365
12366 (define_insn "*rotlsi3_1"
12367   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12368         (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12369                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
12370    (clobber (reg:CC 17))]
12371   "ix86_binary_operator_ok (ROTATE, SImode, operands)"
12372   "@
12373    rol{l}\t{%2, %0|%0, %2}
12374    rol{l}\t{%b2, %0|%0, %b2}"
12375   [(set_attr "type" "rotate")
12376    (set_attr "mode" "SI")])
12377
12378 (define_insn "*rotlsi3_1_zext"
12379   [(set (match_operand:DI 0 "register_operand" "=r,r")
12380         (zero_extend:DI
12381           (rotate:SI (match_operand:SI 1 "register_operand" "0,0")
12382                      (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12383    (clobber (reg:CC 17))]
12384   "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)"
12385   "@
12386    rol{l}\t{%2, %k0|%k0, %2}
12387    rol{l}\t{%b2, %k0|%k0, %b2}"
12388   [(set_attr "type" "rotate")
12389    (set_attr "mode" "SI")])
12390
12391 (define_expand "rotlhi3"
12392   [(set (match_operand:HI 0 "nonimmediate_operand" "")
12393         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "")
12394                    (match_operand:QI 2 "nonmemory_operand" "")))
12395    (clobber (reg:CC 17))]
12396   "TARGET_HIMODE_MATH"
12397   "ix86_expand_binary_operator (ROTATE, HImode, operands); DONE;")
12398
12399 (define_insn "*rotlhi3_1_one_bit"
12400   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12401         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12402                    (match_operand:QI 2 "const1_operand" "")))
12403    (clobber (reg:CC 17))]
12404   "ix86_binary_operator_ok (ROTATE, HImode, operands)
12405    && (TARGET_SHIFT1 || optimize_size)"
12406   "rol{w}\t%0"
12407   [(set_attr "type" "rotate")
12408    (set (attr "length") 
12409      (if_then_else (match_operand 0 "register_operand" "") 
12410         (const_string "2")
12411         (const_string "*")))])
12412
12413 (define_insn "*rotlhi3_1"
12414   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12415         (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12416                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
12417    (clobber (reg:CC 17))]
12418   "ix86_binary_operator_ok (ROTATE, HImode, operands)"
12419   "@
12420    rol{w}\t{%2, %0|%0, %2}
12421    rol{w}\t{%b2, %0|%0, %b2}"
12422   [(set_attr "type" "rotate")
12423    (set_attr "mode" "HI")])
12424
12425 (define_expand "rotlqi3"
12426   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12427         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "")
12428                    (match_operand:QI 2 "nonmemory_operand" "")))
12429    (clobber (reg:CC 17))]
12430   "TARGET_QIMODE_MATH"
12431   "ix86_expand_binary_operator (ROTATE, QImode, operands); DONE;")
12432
12433 (define_insn "*rotlqi3_1_one_bit_slp"
12434   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12435         (rotate:QI (match_dup 0)
12436                    (match_operand:QI 1 "const1_operand" "")))
12437    (clobber (reg:CC 17))]
12438   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12439    && (TARGET_SHIFT1 || optimize_size)"
12440   "rol{b}\t%0"
12441   [(set_attr "type" "rotate1")
12442    (set (attr "length") 
12443      (if_then_else (match_operand 0 "register_operand" "") 
12444         (const_string "2")
12445         (const_string "*")))])
12446
12447 (define_insn "*rotlqi3_1_one_bit"
12448   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12449         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12450                    (match_operand:QI 2 "const1_operand" "")))
12451    (clobber (reg:CC 17))]
12452   "ix86_binary_operator_ok (ROTATE, QImode, operands)
12453    && (TARGET_SHIFT1 || optimize_size)"
12454   "rol{b}\t%0"
12455   [(set_attr "type" "rotate")
12456    (set (attr "length") 
12457      (if_then_else (match_operand 0 "register_operand" "") 
12458         (const_string "2")
12459         (const_string "*")))])
12460
12461 (define_insn "*rotlqi3_1_slp"
12462   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12463         (rotate:QI (match_dup 0)
12464                    (match_operand:QI 1 "nonmemory_operand" "I,c")))
12465    (clobber (reg:CC 17))]
12466   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12467    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
12468   "@
12469    rol{b}\t{%1, %0|%0, %1}
12470    rol{b}\t{%b1, %0|%0, %b1}"
12471   [(set_attr "type" "rotate1")
12472    (set_attr "mode" "QI")])
12473
12474 (define_insn "*rotlqi3_1"
12475   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12476         (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12477                    (match_operand:QI 2 "nonmemory_operand" "I,c")))
12478    (clobber (reg:CC 17))]
12479   "ix86_binary_operator_ok (ROTATE, QImode, operands)"
12480   "@
12481    rol{b}\t{%2, %0|%0, %2}
12482    rol{b}\t{%b2, %0|%0, %b2}"
12483   [(set_attr "type" "rotate")
12484    (set_attr "mode" "QI")])
12485
12486 (define_expand "rotrdi3"
12487   [(set (match_operand:DI 0 "nonimmediate_operand" "")
12488         (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "")
12489                      (match_operand:QI 2 "nonmemory_operand" "")))
12490    (clobber (reg:CC 17))]
12491   "TARGET_64BIT"
12492   "ix86_expand_binary_operator (ROTATERT, DImode, operands); DONE;")
12493
12494 (define_insn "*rotrdi3_1_one_bit_rex64"
12495   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12496         (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12497                      (match_operand:QI 2 "const1_operand" "")))
12498    (clobber (reg:CC 17))]
12499   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)
12500    && (TARGET_SHIFT1 || optimize_size)"
12501   "ror{q}\t%0"
12502   [(set_attr "type" "rotate")
12503    (set (attr "length") 
12504      (if_then_else (match_operand:DI 0 "register_operand" "") 
12505         (const_string "2")
12506         (const_string "*")))])
12507
12508 (define_insn "*rotrdi3_1_rex64"
12509   [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
12510         (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
12511                      (match_operand:QI 2 "nonmemory_operand" "J,c")))
12512    (clobber (reg:CC 17))]
12513   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
12514   "@
12515    ror{q}\t{%2, %0|%0, %2}
12516    ror{q}\t{%b2, %0|%0, %b2}"
12517   [(set_attr "type" "rotate")
12518    (set_attr "mode" "DI")])
12519
12520 (define_expand "rotrsi3"
12521   [(set (match_operand:SI 0 "nonimmediate_operand" "")
12522         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
12523                      (match_operand:QI 2 "nonmemory_operand" "")))
12524    (clobber (reg:CC 17))]
12525   ""
12526   "ix86_expand_binary_operator (ROTATERT, SImode, operands); DONE;")
12527
12528 (define_insn "*rotrsi3_1_one_bit"
12529   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12530         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12531                      (match_operand:QI 2 "const1_operand" "")))
12532    (clobber (reg:CC 17))]
12533   "ix86_binary_operator_ok (ROTATERT, SImode, operands)
12534    && (TARGET_SHIFT1 || optimize_size)"
12535   "ror{l}\t%0"
12536   [(set_attr "type" "rotate")
12537    (set (attr "length") 
12538      (if_then_else (match_operand:SI 0 "register_operand" "") 
12539         (const_string "2")
12540         (const_string "*")))])
12541
12542 (define_insn "*rotrsi3_1_one_bit_zext"
12543   [(set (match_operand:DI 0 "register_operand" "=r")
12544         (zero_extend:DI
12545           (rotatert:SI (match_operand:SI 1 "register_operand" "0")
12546                        (match_operand:QI 2 "const1_operand" ""))))
12547    (clobber (reg:CC 17))]
12548   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)
12549    && (TARGET_SHIFT1 || optimize_size)"
12550   "ror{l}\t%k0"
12551   [(set_attr "type" "rotate")
12552    (set (attr "length") 
12553      (if_then_else (match_operand:SI 0 "register_operand" "") 
12554         (const_string "2")
12555         (const_string "*")))])
12556
12557 (define_insn "*rotrsi3_1"
12558   [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12559         (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12560                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12561    (clobber (reg:CC 17))]
12562   "ix86_binary_operator_ok (ROTATERT, SImode, operands)"
12563   "@
12564    ror{l}\t{%2, %0|%0, %2}
12565    ror{l}\t{%b2, %0|%0, %b2}"
12566   [(set_attr "type" "rotate")
12567    (set_attr "mode" "SI")])
12568
12569 (define_insn "*rotrsi3_1_zext"
12570   [(set (match_operand:DI 0 "register_operand" "=r,r")
12571         (zero_extend:DI
12572           (rotatert:SI (match_operand:SI 1 "register_operand" "0,0")
12573                        (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12574    (clobber (reg:CC 17))]
12575   "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
12576   "@
12577    ror{l}\t{%2, %k0|%k0, %2}
12578    ror{l}\t{%b2, %k0|%k0, %b2}"
12579   [(set_attr "type" "rotate")
12580    (set_attr "mode" "SI")])
12581
12582 (define_expand "rotrhi3"
12583   [(set (match_operand:HI 0 "nonimmediate_operand" "")
12584         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "")
12585                      (match_operand:QI 2 "nonmemory_operand" "")))
12586    (clobber (reg:CC 17))]
12587   "TARGET_HIMODE_MATH"
12588   "ix86_expand_binary_operator (ROTATERT, HImode, operands); DONE;")
12589
12590 (define_insn "*rotrhi3_one_bit"
12591   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12592         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12593                      (match_operand:QI 2 "const1_operand" "")))
12594    (clobber (reg:CC 17))]
12595   "ix86_binary_operator_ok (ROTATERT, HImode, operands)
12596    && (TARGET_SHIFT1 || optimize_size)"
12597   "ror{w}\t%0"
12598   [(set_attr "type" "rotate")
12599    (set (attr "length") 
12600      (if_then_else (match_operand 0 "register_operand" "") 
12601         (const_string "2")
12602         (const_string "*")))])
12603
12604 (define_insn "*rotrhi3"
12605   [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12606         (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12607                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12608    (clobber (reg:CC 17))]
12609   "ix86_binary_operator_ok (ROTATERT, HImode, operands)"
12610   "@
12611    ror{w}\t{%2, %0|%0, %2}
12612    ror{w}\t{%b2, %0|%0, %b2}"
12613   [(set_attr "type" "rotate")
12614    (set_attr "mode" "HI")])
12615
12616 (define_expand "rotrqi3"
12617   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12618         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "")
12619                      (match_operand:QI 2 "nonmemory_operand" "")))
12620    (clobber (reg:CC 17))]
12621   "TARGET_QIMODE_MATH"
12622   "ix86_expand_binary_operator (ROTATERT, QImode, operands); DONE;")
12623
12624 (define_insn "*rotrqi3_1_one_bit"
12625   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12626         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12627                      (match_operand:QI 2 "const1_operand" "")))
12628    (clobber (reg:CC 17))]
12629   "ix86_binary_operator_ok (ROTATERT, QImode, operands)
12630    && (TARGET_SHIFT1 || optimize_size)"
12631   "ror{b}\t%0"
12632   [(set_attr "type" "rotate")
12633    (set (attr "length") 
12634      (if_then_else (match_operand 0 "register_operand" "") 
12635         (const_string "2")
12636         (const_string "*")))])
12637
12638 (define_insn "*rotrqi3_1_one_bit_slp"
12639   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12640         (rotatert:QI (match_dup 0)
12641                      (match_operand:QI 1 "const1_operand" "")))
12642    (clobber (reg:CC 17))]
12643   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12644    && (TARGET_SHIFT1 || optimize_size)"
12645   "ror{b}\t%0"
12646   [(set_attr "type" "rotate1")
12647    (set (attr "length") 
12648      (if_then_else (match_operand 0 "register_operand" "") 
12649         (const_string "2")
12650         (const_string "*")))])
12651
12652 (define_insn "*rotrqi3_1"
12653   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12654         (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12655                      (match_operand:QI 2 "nonmemory_operand" "I,c")))
12656    (clobber (reg:CC 17))]
12657   "ix86_binary_operator_ok (ROTATERT, QImode, operands)"
12658   "@
12659    ror{b}\t{%2, %0|%0, %2}
12660    ror{b}\t{%b2, %0|%0, %b2}"
12661   [(set_attr "type" "rotate")
12662    (set_attr "mode" "QI")])
12663
12664 (define_insn "*rotrqi3_1_slp"
12665   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12666         (rotatert:QI (match_dup 0)
12667                      (match_operand:QI 1 "nonmemory_operand" "I,c")))
12668    (clobber (reg:CC 17))]
12669   "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12670    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
12671   "@
12672    ror{b}\t{%1, %0|%0, %1}
12673    ror{b}\t{%b1, %0|%0, %b1}"
12674   [(set_attr "type" "rotate1")
12675    (set_attr "mode" "QI")])
12676 \f
12677 ;; Bit set / bit test instructions
12678
12679 (define_expand "extv"
12680   [(set (match_operand:SI 0 "register_operand" "")
12681         (sign_extract:SI (match_operand:SI 1 "register_operand" "")
12682                          (match_operand:SI 2 "immediate_operand" "")
12683                          (match_operand:SI 3 "immediate_operand" "")))]
12684   ""
12685 {
12686   /* Handle extractions from %ah et al.  */
12687   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
12688     FAIL;
12689
12690   /* From mips.md: extract_bit_field doesn't verify that our source
12691      matches the predicate, so check it again here.  */
12692   if (! register_operand (operands[1], VOIDmode))
12693     FAIL;
12694 })
12695
12696 (define_expand "extzv"
12697   [(set (match_operand:SI 0 "register_operand" "")
12698         (zero_extract:SI (match_operand 1 "ext_register_operand" "")
12699                          (match_operand:SI 2 "immediate_operand" "")
12700                          (match_operand:SI 3 "immediate_operand" "")))]
12701   ""
12702 {
12703   /* Handle extractions from %ah et al.  */
12704   if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
12705     FAIL;
12706
12707   /* From mips.md: extract_bit_field doesn't verify that our source
12708      matches the predicate, so check it again here.  */
12709   if (! register_operand (operands[1], VOIDmode))
12710     FAIL;
12711 })
12712
12713 (define_expand "insv"
12714   [(set (zero_extract (match_operand 0 "ext_register_operand" "")
12715                       (match_operand 1 "immediate_operand" "")
12716                       (match_operand 2 "immediate_operand" ""))
12717         (match_operand 3 "register_operand" ""))]
12718   ""
12719 {
12720   /* Handle extractions from %ah et al.  */
12721   if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
12722     FAIL;
12723
12724   /* From mips.md: insert_bit_field doesn't verify that our source
12725      matches the predicate, so check it again here.  */
12726   if (! register_operand (operands[0], VOIDmode))
12727     FAIL;
12728
12729   if (TARGET_64BIT)
12730     emit_insn (gen_movdi_insv_1_rex64 (operands[0], operands[3]));
12731   else
12732     emit_insn (gen_movsi_insv_1 (operands[0], operands[3]));
12733
12734   DONE;
12735 })
12736
12737 ;; %%% bts, btr, btc, bt.
12738 \f
12739 ;; Store-flag instructions.
12740
12741 ;; For all sCOND expanders, also expand the compare or test insn that
12742 ;; generates cc0.  Generate an equality comparison if `seq' or `sne'.
12743
12744 ;; %%% Do the expansion to SImode.  If PII, do things the xor+setcc way
12745 ;; to avoid partial register stalls.  Otherwise do things the setcc+movzx
12746 ;; way, which can later delete the movzx if only QImode is needed.
12747
12748 (define_expand "seq"
12749   [(set (match_operand:QI 0 "register_operand" "")
12750         (eq:QI (reg:CC 17) (const_int 0)))]
12751   ""
12752   "if (ix86_expand_setcc (EQ, operands[0])) DONE; else FAIL;")
12753
12754 (define_expand "sne"
12755   [(set (match_operand:QI 0 "register_operand" "")
12756         (ne:QI (reg:CC 17) (const_int 0)))]
12757   ""
12758   "if (ix86_expand_setcc (NE, operands[0])) DONE; else FAIL;")
12759
12760 (define_expand "sgt"
12761   [(set (match_operand:QI 0 "register_operand" "")
12762         (gt:QI (reg:CC 17) (const_int 0)))]
12763   ""
12764   "if (ix86_expand_setcc (GT, operands[0])) DONE; else FAIL;")
12765
12766 (define_expand "sgtu"
12767   [(set (match_operand:QI 0 "register_operand" "")
12768         (gtu:QI (reg:CC 17) (const_int 0)))]
12769   ""
12770   "if (ix86_expand_setcc (GTU, operands[0])) DONE; else FAIL;")
12771
12772 (define_expand "slt"
12773   [(set (match_operand:QI 0 "register_operand" "")
12774         (lt:QI (reg:CC 17) (const_int 0)))]
12775   ""
12776   "if (ix86_expand_setcc (LT, operands[0])) DONE; else FAIL;")
12777
12778 (define_expand "sltu"
12779   [(set (match_operand:QI 0 "register_operand" "")
12780         (ltu:QI (reg:CC 17) (const_int 0)))]
12781   ""
12782   "if (ix86_expand_setcc (LTU, operands[0])) DONE; else FAIL;")
12783
12784 (define_expand "sge"
12785   [(set (match_operand:QI 0 "register_operand" "")
12786         (ge:QI (reg:CC 17) (const_int 0)))]
12787   ""
12788   "if (ix86_expand_setcc (GE, operands[0])) DONE; else FAIL;")
12789
12790 (define_expand "sgeu"
12791   [(set (match_operand:QI 0 "register_operand" "")
12792         (geu:QI (reg:CC 17) (const_int 0)))]
12793   ""
12794   "if (ix86_expand_setcc (GEU, operands[0])) DONE; else FAIL;")
12795
12796 (define_expand "sle"
12797   [(set (match_operand:QI 0 "register_operand" "")
12798         (le:QI (reg:CC 17) (const_int 0)))]
12799   ""
12800   "if (ix86_expand_setcc (LE, operands[0])) DONE; else FAIL;")
12801
12802 (define_expand "sleu"
12803   [(set (match_operand:QI 0 "register_operand" "")
12804         (leu:QI (reg:CC 17) (const_int 0)))]
12805   ""
12806   "if (ix86_expand_setcc (LEU, operands[0])) DONE; else FAIL;")
12807
12808 (define_expand "sunordered"
12809   [(set (match_operand:QI 0 "register_operand" "")
12810         (unordered:QI (reg:CC 17) (const_int 0)))]
12811   "TARGET_80387 || TARGET_SSE"
12812   "if (ix86_expand_setcc (UNORDERED, operands[0])) DONE; else FAIL;")
12813
12814 (define_expand "sordered"
12815   [(set (match_operand:QI 0 "register_operand" "")
12816         (ordered:QI (reg:CC 17) (const_int 0)))]
12817   "TARGET_80387"
12818   "if (ix86_expand_setcc (ORDERED, operands[0])) DONE; else FAIL;")
12819
12820 (define_expand "suneq"
12821   [(set (match_operand:QI 0 "register_operand" "")
12822         (uneq:QI (reg:CC 17) (const_int 0)))]
12823   "TARGET_80387 || TARGET_SSE"
12824   "if (ix86_expand_setcc (UNEQ, operands[0])) DONE; else FAIL;")
12825
12826 (define_expand "sunge"
12827   [(set (match_operand:QI 0 "register_operand" "")
12828         (unge:QI (reg:CC 17) (const_int 0)))]
12829   "TARGET_80387 || TARGET_SSE"
12830   "if (ix86_expand_setcc (UNGE, operands[0])) DONE; else FAIL;")
12831
12832 (define_expand "sungt"
12833   [(set (match_operand:QI 0 "register_operand" "")
12834         (ungt:QI (reg:CC 17) (const_int 0)))]
12835   "TARGET_80387 || TARGET_SSE"
12836   "if (ix86_expand_setcc (UNGT, operands[0])) DONE; else FAIL;")
12837
12838 (define_expand "sunle"
12839   [(set (match_operand:QI 0 "register_operand" "")
12840         (unle:QI (reg:CC 17) (const_int 0)))]
12841   "TARGET_80387 || TARGET_SSE"
12842   "if (ix86_expand_setcc (UNLE, operands[0])) DONE; else FAIL;")
12843
12844 (define_expand "sunlt"
12845   [(set (match_operand:QI 0 "register_operand" "")
12846         (unlt:QI (reg:CC 17) (const_int 0)))]
12847   "TARGET_80387 || TARGET_SSE"
12848   "if (ix86_expand_setcc (UNLT, operands[0])) DONE; else FAIL;")
12849
12850 (define_expand "sltgt"
12851   [(set (match_operand:QI 0 "register_operand" "")
12852         (ltgt:QI (reg:CC 17) (const_int 0)))]
12853   "TARGET_80387 || TARGET_SSE"
12854   "if (ix86_expand_setcc (LTGT, operands[0])) DONE; else FAIL;")
12855
12856 (define_insn "*setcc_1"
12857   [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12858         (match_operator:QI 1 "ix86_comparison_operator"
12859           [(reg 17) (const_int 0)]))]
12860   ""
12861   "set%C1\t%0"
12862   [(set_attr "type" "setcc")
12863    (set_attr "mode" "QI")])
12864
12865 (define_insn "setcc_2"
12866   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12867         (match_operator:QI 1 "ix86_comparison_operator"
12868           [(reg 17) (const_int 0)]))]
12869   ""
12870   "set%C1\t%0"
12871   [(set_attr "type" "setcc")
12872    (set_attr "mode" "QI")])
12873
12874 ;; In general it is not safe to assume too much about CCmode registers,
12875 ;; so simplify-rtx stops when it sees a second one.  Under certain 
12876 ;; conditions this is safe on x86, so help combine not create
12877 ;;
12878 ;;      seta    %al
12879 ;;      testb   %al, %al
12880 ;;      sete    %al
12881
12882 (define_split 
12883   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12884         (ne:QI (match_operator 1 "ix86_comparison_operator"
12885                  [(reg 17) (const_int 0)])
12886             (const_int 0)))]
12887   ""
12888   [(set (match_dup 0) (match_dup 1))]
12889 {
12890   PUT_MODE (operands[1], QImode);
12891 })
12892
12893 (define_split 
12894   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
12895         (ne:QI (match_operator 1 "ix86_comparison_operator"
12896                  [(reg 17) (const_int 0)])
12897             (const_int 0)))]
12898   ""
12899   [(set (match_dup 0) (match_dup 1))]
12900 {
12901   PUT_MODE (operands[1], QImode);
12902 })
12903
12904 (define_split 
12905   [(set (match_operand:QI 0 "nonimmediate_operand" "")
12906         (eq:QI (match_operator 1 "ix86_comparison_operator"
12907                  [(reg 17) (const_int 0)])
12908             (const_int 0)))]
12909   ""
12910   [(set (match_dup 0) (match_dup 1))]
12911 {
12912   rtx new_op1 = copy_rtx (operands[1]);
12913   operands[1] = new_op1;
12914   PUT_MODE (new_op1, QImode);
12915   PUT_CODE (new_op1, REVERSE_CONDITION (GET_CODE (new_op1),
12916                                         GET_MODE (XEXP (new_op1, 0))));
12917
12918   /* Make sure that (a) the CCmode we have for the flags is strong
12919      enough for the reversed compare or (b) we have a valid FP compare.  */
12920   if (! ix86_comparison_operator (new_op1, VOIDmode))
12921     FAIL;
12922 })
12923
12924 (define_split 
12925   [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
12926         (eq:QI (match_operator 1 "ix86_comparison_operator"
12927                  [(reg 17) (const_int 0)])
12928             (const_int 0)))]
12929   ""
12930   [(set (match_dup 0) (match_dup 1))]
12931 {
12932   rtx new_op1 = copy_rtx (operands[1]);
12933   operands[1] = new_op1;
12934   PUT_MODE (new_op1, QImode);
12935   PUT_CODE (new_op1, REVERSE_CONDITION (GET_CODE (new_op1),
12936                                         GET_MODE (XEXP (new_op1, 0))));
12937
12938   /* Make sure that (a) the CCmode we have for the flags is strong
12939      enough for the reversed compare or (b) we have a valid FP compare.  */
12940   if (! ix86_comparison_operator (new_op1, VOIDmode))
12941     FAIL;
12942 })
12943
12944 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
12945 ;; subsequent logical operations are used to imitate conditional moves.
12946 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
12947 ;; it directly.  Further holding this value in pseudo register might bring
12948 ;; problem in implicit normalization in spill code.
12949 ;; So we don't define FLOAT_STORE_FLAG_VALUE and create these
12950 ;; instructions after reload by splitting the conditional move patterns.
12951
12952 (define_insn "*sse_setccsf"
12953   [(set (match_operand:SF 0 "register_operand" "=x")
12954         (match_operator:SF 1 "sse_comparison_operator"
12955           [(match_operand:SF 2 "register_operand" "0")
12956            (match_operand:SF 3 "nonimmediate_operand" "xm")]))]
12957   "TARGET_SSE && reload_completed"
12958   "cmp%D1ss\t{%3, %0|%0, %3}"
12959   [(set_attr "type" "ssecmp")
12960    (set_attr "mode" "SF")])
12961
12962 (define_insn "*sse_setccdf"
12963   [(set (match_operand:DF 0 "register_operand" "=Y")
12964         (match_operator:DF 1 "sse_comparison_operator"
12965           [(match_operand:DF 2 "register_operand" "0")
12966            (match_operand:DF 3 "nonimmediate_operand" "Ym")]))]
12967   "TARGET_SSE2 && reload_completed"
12968   "cmp%D1sd\t{%3, %0|%0, %3}"
12969   [(set_attr "type" "ssecmp")
12970    (set_attr "mode" "DF")])
12971 \f
12972 ;; Basic conditional jump instructions.
12973 ;; We ignore the overflow flag for signed branch instructions.
12974
12975 ;; For all bCOND expanders, also expand the compare or test insn that
12976 ;; generates reg 17.  Generate an equality comparison if `beq' or `bne'.
12977
12978 (define_expand "beq"
12979   [(set (pc)
12980         (if_then_else (match_dup 1)
12981                       (label_ref (match_operand 0 "" ""))
12982                       (pc)))]
12983   ""
12984   "ix86_expand_branch (EQ, operands[0]); DONE;")
12985
12986 (define_expand "bne"
12987   [(set (pc)
12988         (if_then_else (match_dup 1)
12989                       (label_ref (match_operand 0 "" ""))
12990                       (pc)))]
12991   ""
12992   "ix86_expand_branch (NE, operands[0]); DONE;")
12993
12994 (define_expand "bgt"
12995   [(set (pc)
12996         (if_then_else (match_dup 1)
12997                       (label_ref (match_operand 0 "" ""))
12998                       (pc)))]
12999   ""
13000   "ix86_expand_branch (GT, operands[0]); DONE;")
13001
13002 (define_expand "bgtu"
13003   [(set (pc)
13004         (if_then_else (match_dup 1)
13005                       (label_ref (match_operand 0 "" ""))
13006                       (pc)))]
13007   ""
13008   "ix86_expand_branch (GTU, operands[0]); DONE;")
13009
13010 (define_expand "blt"
13011   [(set (pc)
13012         (if_then_else (match_dup 1)
13013                       (label_ref (match_operand 0 "" ""))
13014                       (pc)))]
13015   ""
13016   "ix86_expand_branch (LT, operands[0]); DONE;")
13017
13018 (define_expand "bltu"
13019   [(set (pc)
13020         (if_then_else (match_dup 1)
13021                       (label_ref (match_operand 0 "" ""))
13022                       (pc)))]
13023   ""
13024   "ix86_expand_branch (LTU, operands[0]); DONE;")
13025
13026 (define_expand "bge"
13027   [(set (pc)
13028         (if_then_else (match_dup 1)
13029                       (label_ref (match_operand 0 "" ""))
13030                       (pc)))]
13031   ""
13032   "ix86_expand_branch (GE, operands[0]); DONE;")
13033
13034 (define_expand "bgeu"
13035   [(set (pc)
13036         (if_then_else (match_dup 1)
13037                       (label_ref (match_operand 0 "" ""))
13038                       (pc)))]
13039   ""
13040   "ix86_expand_branch (GEU, operands[0]); DONE;")
13041
13042 (define_expand "ble"
13043   [(set (pc)
13044         (if_then_else (match_dup 1)
13045                       (label_ref (match_operand 0 "" ""))
13046                       (pc)))]
13047   ""
13048   "ix86_expand_branch (LE, operands[0]); DONE;")
13049
13050 (define_expand "bleu"
13051   [(set (pc)
13052         (if_then_else (match_dup 1)
13053                       (label_ref (match_operand 0 "" ""))
13054                       (pc)))]
13055   ""
13056   "ix86_expand_branch (LEU, operands[0]); DONE;")
13057
13058 (define_expand "bunordered"
13059   [(set (pc)
13060         (if_then_else (match_dup 1)
13061                       (label_ref (match_operand 0 "" ""))
13062                       (pc)))]
13063   "TARGET_80387 || TARGET_SSE"
13064   "ix86_expand_branch (UNORDERED, operands[0]); DONE;")
13065
13066 (define_expand "bordered"
13067   [(set (pc)
13068         (if_then_else (match_dup 1)
13069                       (label_ref (match_operand 0 "" ""))
13070                       (pc)))]
13071   "TARGET_80387 || TARGET_SSE"
13072   "ix86_expand_branch (ORDERED, operands[0]); DONE;")
13073
13074 (define_expand "buneq"
13075   [(set (pc)
13076         (if_then_else (match_dup 1)
13077                       (label_ref (match_operand 0 "" ""))
13078                       (pc)))]
13079   "TARGET_80387 || TARGET_SSE"
13080   "ix86_expand_branch (UNEQ, operands[0]); DONE;")
13081
13082 (define_expand "bunge"
13083   [(set (pc)
13084         (if_then_else (match_dup 1)
13085                       (label_ref (match_operand 0 "" ""))
13086                       (pc)))]
13087   "TARGET_80387 || TARGET_SSE"
13088   "ix86_expand_branch (UNGE, operands[0]); DONE;")
13089
13090 (define_expand "bungt"
13091   [(set (pc)
13092         (if_then_else (match_dup 1)
13093                       (label_ref (match_operand 0 "" ""))
13094                       (pc)))]
13095   "TARGET_80387 || TARGET_SSE"
13096   "ix86_expand_branch (UNGT, operands[0]); DONE;")
13097
13098 (define_expand "bunle"
13099   [(set (pc)
13100         (if_then_else (match_dup 1)
13101                       (label_ref (match_operand 0 "" ""))
13102                       (pc)))]
13103   "TARGET_80387 || TARGET_SSE"
13104   "ix86_expand_branch (UNLE, operands[0]); DONE;")
13105
13106 (define_expand "bunlt"
13107   [(set (pc)
13108         (if_then_else (match_dup 1)
13109                       (label_ref (match_operand 0 "" ""))
13110                       (pc)))]
13111   "TARGET_80387 || TARGET_SSE"
13112   "ix86_expand_branch (UNLT, operands[0]); DONE;")
13113
13114 (define_expand "bltgt"
13115   [(set (pc)
13116         (if_then_else (match_dup 1)
13117                       (label_ref (match_operand 0 "" ""))
13118                       (pc)))]
13119   "TARGET_80387 || TARGET_SSE"
13120   "ix86_expand_branch (LTGT, operands[0]); DONE;")
13121
13122 (define_insn "*jcc_1"
13123   [(set (pc)
13124         (if_then_else (match_operator 1 "ix86_comparison_operator"
13125                                       [(reg 17) (const_int 0)])
13126                       (label_ref (match_operand 0 "" ""))
13127                       (pc)))]
13128   ""
13129   "%+j%C1\t%l0"
13130   [(set_attr "type" "ibr")
13131    (set_attr "modrm" "0")
13132    (set (attr "length")
13133            (if_then_else (and (ge (minus (match_dup 0) (pc))
13134                                   (const_int -126))
13135                               (lt (minus (match_dup 0) (pc))
13136                                   (const_int 128)))
13137              (const_int 2)
13138              (const_int 6)))])
13139
13140 (define_insn "*jcc_2"
13141   [(set (pc)
13142         (if_then_else (match_operator 1 "ix86_comparison_operator"
13143                                       [(reg 17) (const_int 0)])
13144                       (pc)
13145                       (label_ref (match_operand 0 "" ""))))]
13146   ""
13147   "%+j%c1\t%l0"
13148   [(set_attr "type" "ibr")
13149    (set_attr "modrm" "0")
13150    (set (attr "length")
13151            (if_then_else (and (ge (minus (match_dup 0) (pc))
13152                                   (const_int -126))
13153                               (lt (minus (match_dup 0) (pc))
13154                                   (const_int 128)))
13155              (const_int 2)
13156              (const_int 6)))])
13157
13158 ;; In general it is not safe to assume too much about CCmode registers,
13159 ;; so simplify-rtx stops when it sees a second one.  Under certain 
13160 ;; conditions this is safe on x86, so help combine not create
13161 ;;
13162 ;;      seta    %al
13163 ;;      testb   %al, %al
13164 ;;      je      Lfoo
13165
13166 (define_split 
13167   [(set (pc)
13168         (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
13169                                       [(reg 17) (const_int 0)])
13170                           (const_int 0))
13171                       (label_ref (match_operand 1 "" ""))
13172                       (pc)))]
13173   ""
13174   [(set (pc)
13175         (if_then_else (match_dup 0)
13176                       (label_ref (match_dup 1))
13177                       (pc)))]
13178 {
13179   PUT_MODE (operands[0], VOIDmode);
13180 })
13181   
13182 (define_split 
13183   [(set (pc)
13184         (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
13185                                       [(reg 17) (const_int 0)])
13186                           (const_int 0))
13187                       (label_ref (match_operand 1 "" ""))
13188                       (pc)))]
13189   ""
13190   [(set (pc)
13191         (if_then_else (match_dup 0)
13192                       (label_ref (match_dup 1))
13193                       (pc)))]
13194 {
13195   rtx new_op0 = copy_rtx (operands[0]);
13196   operands[0] = new_op0;
13197   PUT_MODE (new_op0, VOIDmode);
13198   PUT_CODE (new_op0, REVERSE_CONDITION (GET_CODE (new_op0),
13199                                         GET_MODE (XEXP (new_op0, 0))));
13200
13201   /* Make sure that (a) the CCmode we have for the flags is strong
13202      enough for the reversed compare or (b) we have a valid FP compare.  */
13203   if (! ix86_comparison_operator (new_op0, VOIDmode))
13204     FAIL;
13205 })
13206
13207 ;; Define combination compare-and-branch fp compare instructions to use
13208 ;; during early optimization.  Splitting the operation apart early makes
13209 ;; for bad code when we want to reverse the operation.
13210
13211 (define_insn "*fp_jcc_1"
13212   [(set (pc)
13213         (if_then_else (match_operator 0 "comparison_operator"
13214                         [(match_operand 1 "register_operand" "f")
13215                          (match_operand 2 "register_operand" "f")])
13216           (label_ref (match_operand 3 "" ""))
13217           (pc)))
13218    (clobber (reg:CCFP 18))
13219    (clobber (reg:CCFP 17))]
13220   "TARGET_CMOVE && TARGET_80387
13221    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13222    && FLOAT_MODE_P (GET_MODE (operands[1]))
13223    && GET_MODE (operands[1]) == GET_MODE (operands[2])
13224    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13225   "#")
13226
13227 (define_insn "*fp_jcc_1_sse"
13228   [(set (pc)
13229         (if_then_else (match_operator 0 "comparison_operator"
13230                         [(match_operand 1 "register_operand" "f#x,x#f")
13231                          (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
13232           (label_ref (match_operand 3 "" ""))
13233           (pc)))
13234    (clobber (reg:CCFP 18))
13235    (clobber (reg:CCFP 17))]
13236   "TARGET_80387
13237    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13238    && GET_MODE (operands[1]) == GET_MODE (operands[2])
13239    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13240   "#")
13241
13242 (define_insn "*fp_jcc_1_sse_only"
13243   [(set (pc)
13244         (if_then_else (match_operator 0 "comparison_operator"
13245                         [(match_operand 1 "register_operand" "x")
13246                          (match_operand 2 "nonimmediate_operand" "xm")])
13247           (label_ref (match_operand 3 "" ""))
13248           (pc)))
13249    (clobber (reg:CCFP 18))
13250    (clobber (reg:CCFP 17))]
13251   "SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13252    && GET_MODE (operands[1]) == GET_MODE (operands[2])
13253    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13254   "#")
13255
13256 (define_insn "*fp_jcc_2"
13257   [(set (pc)
13258         (if_then_else (match_operator 0 "comparison_operator"
13259                         [(match_operand 1 "register_operand" "f")
13260                          (match_operand 2 "register_operand" "f")])
13261           (pc)
13262           (label_ref (match_operand 3 "" ""))))
13263    (clobber (reg:CCFP 18))
13264    (clobber (reg:CCFP 17))]
13265   "TARGET_CMOVE && TARGET_80387
13266    && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13267    && FLOAT_MODE_P (GET_MODE (operands[1]))
13268    && GET_MODE (operands[1]) == GET_MODE (operands[2])
13269    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13270   "#")
13271
13272 (define_insn "*fp_jcc_2_sse"
13273   [(set (pc)
13274         (if_then_else (match_operator 0 "comparison_operator"
13275                         [(match_operand 1 "register_operand" "f#x,x#f")
13276                          (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
13277           (pc)
13278           (label_ref (match_operand 3 "" ""))))
13279    (clobber (reg:CCFP 18))
13280    (clobber (reg:CCFP 17))]
13281   "TARGET_80387
13282    && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13283    && GET_MODE (operands[1]) == GET_MODE (operands[2])
13284    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13285   "#")
13286
13287 (define_insn "*fp_jcc_2_sse_only"
13288   [(set (pc)
13289         (if_then_else (match_operator 0 "comparison_operator"
13290                         [(match_operand 1 "register_operand" "x")
13291                          (match_operand 2 "nonimmediate_operand" "xm")])
13292           (pc)
13293           (label_ref (match_operand 3 "" ""))))
13294    (clobber (reg:CCFP 18))
13295    (clobber (reg:CCFP 17))]
13296   "SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13297    && GET_MODE (operands[1]) == GET_MODE (operands[2])
13298    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13299   "#")
13300
13301 (define_insn "*fp_jcc_3"
13302   [(set (pc)
13303         (if_then_else (match_operator 0 "comparison_operator"
13304                         [(match_operand 1 "register_operand" "f")
13305                          (match_operand 2 "nonimmediate_operand" "fm")])
13306           (label_ref (match_operand 3 "" ""))
13307           (pc)))
13308    (clobber (reg:CCFP 18))
13309    (clobber (reg:CCFP 17))
13310    (clobber (match_scratch:HI 4 "=a"))]
13311   "TARGET_80387
13312    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
13313    && GET_MODE (operands[1]) == GET_MODE (operands[2])
13314    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
13315    && SELECT_CC_MODE (GET_CODE (operands[0]),
13316                       operands[1], operands[2]) == CCFPmode
13317    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13318   "#")
13319
13320 (define_insn "*fp_jcc_4"
13321   [(set (pc)
13322         (if_then_else (match_operator 0 "comparison_operator"
13323                         [(match_operand 1 "register_operand" "f")
13324                          (match_operand 2 "nonimmediate_operand" "fm")])
13325           (pc)
13326           (label_ref (match_operand 3 "" ""))))
13327    (clobber (reg:CCFP 18))
13328    (clobber (reg:CCFP 17))
13329    (clobber (match_scratch:HI 4 "=a"))]
13330   "TARGET_80387
13331    && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
13332    && GET_MODE (operands[1]) == GET_MODE (operands[2])
13333    && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
13334    && SELECT_CC_MODE (GET_CODE (operands[0]),
13335                       operands[1], operands[2]) == CCFPmode
13336    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13337   "#")
13338
13339 (define_insn "*fp_jcc_5"
13340   [(set (pc)
13341         (if_then_else (match_operator 0 "comparison_operator"
13342                         [(match_operand 1 "register_operand" "f")
13343                          (match_operand 2 "register_operand" "f")])
13344           (label_ref (match_operand 3 "" ""))
13345           (pc)))
13346    (clobber (reg:CCFP 18))
13347    (clobber (reg:CCFP 17))
13348    (clobber (match_scratch:HI 4 "=a"))]
13349   "TARGET_80387
13350    && FLOAT_MODE_P (GET_MODE (operands[1]))
13351    && GET_MODE (operands[1]) == GET_MODE (operands[2])
13352    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13353   "#")
13354
13355 (define_insn "*fp_jcc_6"
13356   [(set (pc)
13357         (if_then_else (match_operator 0 "comparison_operator"
13358                         [(match_operand 1 "register_operand" "f")
13359                          (match_operand 2 "register_operand" "f")])
13360           (pc)
13361           (label_ref (match_operand 3 "" ""))))
13362    (clobber (reg:CCFP 18))
13363    (clobber (reg:CCFP 17))
13364    (clobber (match_scratch:HI 4 "=a"))]
13365   "TARGET_80387
13366    && FLOAT_MODE_P (GET_MODE (operands[1]))
13367    && GET_MODE (operands[1]) == GET_MODE (operands[2])
13368    && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13369   "#")
13370
13371 (define_split
13372   [(set (pc)
13373         (if_then_else (match_operator 0 "comparison_operator"
13374                         [(match_operand 1 "register_operand" "")
13375                          (match_operand 2 "nonimmediate_operand" "")])
13376           (match_operand 3 "" "")
13377           (match_operand 4 "" "")))
13378    (clobber (reg:CCFP 18))
13379    (clobber (reg:CCFP 17))]
13380   "reload_completed"
13381   [(const_int 0)]
13382 {
13383   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
13384                         operands[3], operands[4], NULL_RTX);
13385   DONE;
13386 })
13387
13388 (define_split
13389   [(set (pc)
13390         (if_then_else (match_operator 0 "comparison_operator"
13391                         [(match_operand 1 "register_operand" "")
13392                          (match_operand 2 "nonimmediate_operand" "")])
13393           (match_operand 3 "" "")
13394           (match_operand 4 "" "")))
13395    (clobber (reg:CCFP 18))
13396    (clobber (reg:CCFP 17))
13397    (clobber (match_scratch:HI 5 "=a"))]
13398   "reload_completed"
13399   [(set (pc)
13400         (if_then_else (match_dup 6)
13401           (match_dup 3)
13402           (match_dup 4)))]
13403 {
13404   ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
13405                         operands[3], operands[4], operands[5]);
13406   DONE;
13407 })
13408 \f
13409 ;; Unconditional and other jump instructions
13410
13411 (define_insn "jump"
13412   [(set (pc)
13413         (label_ref (match_operand 0 "" "")))]
13414   ""
13415   "jmp\t%l0"
13416   [(set_attr "type" "ibr")
13417    (set (attr "length")
13418            (if_then_else (and (ge (minus (match_dup 0) (pc))
13419                                   (const_int -126))
13420                               (lt (minus (match_dup 0) (pc))
13421                                   (const_int 128)))
13422              (const_int 2)
13423              (const_int 5)))
13424    (set_attr "modrm" "0")])
13425
13426 (define_expand "indirect_jump"
13427   [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))]
13428   ""
13429   "")
13430
13431 (define_insn "*indirect_jump"
13432   [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))]
13433   "!TARGET_64BIT"
13434   "jmp\t%A0"
13435   [(set_attr "type" "ibr")
13436    (set_attr "length_immediate" "0")])
13437
13438 (define_insn "*indirect_jump_rtx64"
13439   [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))]
13440   "TARGET_64BIT"
13441   "jmp\t%A0"
13442   [(set_attr "type" "ibr")
13443    (set_attr "length_immediate" "0")])
13444
13445 (define_expand "tablejump"
13446   [(parallel [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))
13447               (use (label_ref (match_operand 1 "" "")))])]
13448   ""
13449 {
13450   /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
13451      relative.  Convert the relative address to an absolute address.  */
13452   if (flag_pic)
13453     {
13454       rtx op0, op1;
13455       enum rtx_code code;
13456
13457       if (TARGET_64BIT)
13458         {
13459           code = PLUS;
13460           op0 = operands[0];
13461           op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
13462         }
13463       else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
13464         {
13465           code = PLUS;
13466           op0 = operands[0];
13467           op1 = pic_offset_table_rtx;
13468         }
13469       else
13470         {
13471           code = MINUS;
13472           op0 = pic_offset_table_rtx;
13473           op1 = operands[0];
13474         }
13475
13476       operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
13477                                          OPTAB_DIRECT);
13478     }
13479 })
13480
13481 (define_insn "*tablejump_1"
13482   [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))
13483    (use (label_ref (match_operand 1 "" "")))]
13484   "!TARGET_64BIT"
13485   "jmp\t%A0"
13486   [(set_attr "type" "ibr")
13487    (set_attr "length_immediate" "0")])
13488
13489 (define_insn "*tablejump_1_rtx64"
13490   [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))
13491    (use (label_ref (match_operand 1 "" "")))]
13492   "TARGET_64BIT"
13493   "jmp\t%A0"
13494   [(set_attr "type" "ibr")
13495    (set_attr "length_immediate" "0")])
13496 \f
13497 ;; Loop instruction
13498 ;;
13499 ;; This is all complicated by the fact that since this is a jump insn
13500 ;; we must handle our own reloads.
13501
13502 (define_expand "doloop_end"
13503   [(use (match_operand 0 "" ""))        ; loop pseudo
13504    (use (match_operand 1 "" ""))        ; iterations; zero if unknown
13505    (use (match_operand 2 "" ""))        ; max iterations
13506    (use (match_operand 3 "" ""))        ; loop level 
13507    (use (match_operand 4 "" ""))]       ; label
13508   "!TARGET_64BIT && TARGET_USE_LOOP"
13509   "                                 
13510 {
13511   /* Only use cloop on innermost loops.  */
13512   if (INTVAL (operands[3]) > 1)
13513     FAIL;
13514   if (GET_MODE (operands[0]) != SImode)
13515     FAIL;
13516   emit_jump_insn (gen_doloop_end_internal (operands[4], operands[0],
13517                                            operands[0]));
13518   DONE;
13519 }")
13520
13521 (define_insn "doloop_end_internal"
13522   [(set (pc)
13523         (if_then_else (ne (match_operand:SI 1 "register_operand" "c,?*r,?*r")
13524                           (const_int 1))
13525                       (label_ref (match_operand 0 "" ""))
13526                       (pc)))
13527    (set (match_operand:SI 2 "register_operand" "=1,1,*m*r")
13528         (plus:SI (match_dup 1)
13529                  (const_int -1)))
13530    (clobber (match_scratch:SI 3 "=X,X,r"))
13531    (clobber (reg:CC 17))]
13532   "!TARGET_64BIT && TARGET_USE_LOOP"
13533 {
13534   if (which_alternative != 0)
13535     return "#";
13536   if (get_attr_length (insn) == 2)
13537     return "%+loop\t%l0";
13538   else
13539     return "dec{l}\t%1\;%+jne\t%l0";
13540 }
13541   [(set_attr "ppro_uops" "many")
13542    (set (attr "length")
13543         (if_then_else (and (eq_attr "alternative" "0")
13544                            (and (ge (minus (match_dup 0) (pc))
13545                                     (const_int -126))
13546                                 (lt (minus (match_dup 0) (pc))
13547                                     (const_int 128))))
13548                       (const_int 2)
13549                       (const_int 16)))
13550    ;; We don't know the type before shorten branches.  Optimistically expect
13551    ;; the loop instruction to match.
13552    (set (attr "type") (const_string "ibr"))])
13553
13554 (define_split
13555   [(set (pc)
13556         (if_then_else (ne (match_operand:SI 1 "register_operand" "")
13557                           (const_int 1))
13558                       (match_operand 0 "" "")
13559                       (pc)))
13560    (set (match_dup 1)
13561         (plus:SI (match_dup 1)
13562                  (const_int -1)))
13563    (clobber (match_scratch:SI 2 ""))
13564    (clobber (reg:CC 17))]
13565   "!TARGET_64BIT && TARGET_USE_LOOP
13566    && reload_completed
13567    && REGNO (operands[1]) != 2"
13568   [(parallel [(set (reg:CCZ 17)
13569                    (compare:CCZ (plus:SI (match_dup 1) (const_int -1))
13570                                  (const_int 0)))
13571               (set (match_dup 1) (plus:SI (match_dup 1) (const_int -1)))])
13572    (set (pc) (if_then_else (ne (reg:CCZ 17) (const_int 0))
13573                            (match_dup 0)
13574                            (pc)))]
13575   "")
13576   
13577 (define_split
13578   [(set (pc)
13579         (if_then_else (ne (match_operand:SI 1 "register_operand" "")
13580                           (const_int 1))
13581                       (match_operand 0 "" "")
13582                       (pc)))
13583    (set (match_operand:SI 2 "nonimmediate_operand" "")
13584         (plus:SI (match_dup 1)
13585                  (const_int -1)))
13586    (clobber (match_scratch:SI 3 ""))
13587    (clobber (reg:CC 17))]
13588   "!TARGET_64BIT && TARGET_USE_LOOP
13589    && reload_completed
13590    && (! REG_P (operands[2])
13591        || ! rtx_equal_p (operands[1], operands[2]))"
13592   [(set (match_dup 3) (match_dup 1))
13593    (parallel [(set (reg:CCZ 17)
13594                    (compare:CCZ (plus:SI (match_dup 3) (const_int -1))
13595                                 (const_int 0)))
13596               (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
13597    (set (match_dup 2) (match_dup 3))
13598    (set (pc) (if_then_else (ne (reg:CCZ 17) (const_int 0))
13599                            (match_dup 0)
13600                            (pc)))]
13601   "")
13602
13603 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
13604
13605 (define_peephole2
13606   [(set (reg 17) (match_operand 0 "" ""))
13607    (set (match_operand:QI 1 "register_operand" "")
13608         (match_operator:QI 2 "ix86_comparison_operator"
13609           [(reg 17) (const_int 0)]))
13610    (set (match_operand 3 "q_regs_operand" "")
13611         (zero_extend (match_dup 1)))]
13612   "(peep2_reg_dead_p (3, operands[1])
13613     || operands_match_p (operands[1], operands[3]))
13614    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
13615   [(set (match_dup 4) (match_dup 0))
13616    (set (strict_low_part (match_dup 5))
13617         (match_dup 2))]
13618 {
13619   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), 17);
13620   operands[5] = gen_lowpart (QImode, operands[3]);
13621   ix86_expand_clear (operands[3]);
13622 })
13623
13624 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
13625
13626 (define_peephole2
13627   [(set (reg 17) (match_operand 0 "" ""))
13628    (set (match_operand:QI 1 "register_operand" "")
13629         (match_operator:QI 2 "ix86_comparison_operator"
13630           [(reg 17) (const_int 0)]))
13631    (parallel [(set (match_operand 3 "q_regs_operand" "")
13632                    (zero_extend (match_dup 1)))
13633               (clobber (reg:CC 17))])]
13634   "(peep2_reg_dead_p (3, operands[1])
13635     || operands_match_p (operands[1], operands[3]))
13636    && ! reg_overlap_mentioned_p (operands[3], operands[0])"
13637   [(set (match_dup 4) (match_dup 0))
13638    (set (strict_low_part (match_dup 5))
13639         (match_dup 2))]
13640 {
13641   operands[4] = gen_rtx_REG (GET_MODE (operands[0]), 17);
13642   operands[5] = gen_lowpart (QImode, operands[3]);
13643   ix86_expand_clear (operands[3]);
13644 })
13645 \f
13646 ;; Call instructions.
13647
13648 ;; The predicates normally associated with named expanders are not properly
13649 ;; checked for calls.  This is a bug in the generic code, but it isn't that
13650 ;; easy to fix.  Ignore it for now and be prepared to fix things up.
13651
13652 ;; Call subroutine returning no value.
13653
13654 (define_expand "call_pop"
13655   [(parallel [(call (match_operand:QI 0 "" "")
13656                     (match_operand:SI 1 "" ""))
13657               (set (reg:SI 7)
13658                    (plus:SI (reg:SI 7)
13659                             (match_operand:SI 3 "" "")))])]
13660   "!TARGET_64BIT"
13661 {
13662   ix86_expand_call (NULL, operands[0], operands[1], operands[2], operands[3], 0);
13663   DONE;
13664 })
13665
13666 (define_insn "*call_pop_0"
13667   [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" ""))
13668          (match_operand:SI 1 "" ""))
13669    (set (reg:SI 7) (plus:SI (reg:SI 7)
13670                             (match_operand:SI 2 "immediate_operand" "")))]
13671   "!TARGET_64BIT"
13672 {
13673   if (SIBLING_CALL_P (insn))
13674     return "jmp\t%P0";
13675   else
13676     return "call\t%P0";
13677 }
13678   [(set_attr "type" "call")])
13679   
13680 (define_insn "*call_pop_1"
13681   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
13682          (match_operand:SI 1 "" ""))
13683    (set (reg:SI 7) (plus:SI (reg:SI 7)
13684                             (match_operand:SI 2 "immediate_operand" "i")))]
13685   "!TARGET_64BIT"
13686 {
13687   if (constant_call_address_operand (operands[0], Pmode))
13688     {
13689       if (SIBLING_CALL_P (insn))
13690         return "jmp\t%P0";
13691       else
13692         return "call\t%P0";
13693     }
13694   if (SIBLING_CALL_P (insn))
13695     return "jmp\t%A0";
13696   else
13697     return "call\t%A0";
13698 }
13699   [(set_attr "type" "call")])
13700
13701 (define_expand "call"
13702   [(call (match_operand:QI 0 "" "")
13703          (match_operand 1 "" ""))
13704    (use (match_operand 2 "" ""))]
13705   ""
13706 {
13707   ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 0);
13708   DONE;
13709 })
13710
13711 (define_expand "sibcall"
13712   [(call (match_operand:QI 0 "" "")
13713          (match_operand 1 "" ""))
13714    (use (match_operand 2 "" ""))]
13715   ""
13716 {
13717   ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 1);
13718   DONE;
13719 })
13720
13721 (define_insn "*call_0"
13722   [(call (mem:QI (match_operand 0 "constant_call_address_operand" ""))
13723          (match_operand 1 "" ""))]
13724   ""
13725 {
13726   if (SIBLING_CALL_P (insn))
13727     return "jmp\t%P0";
13728   else
13729     return "call\t%P0";
13730 }
13731   [(set_attr "type" "call")])
13732
13733 (define_insn "*call_1"
13734   [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
13735          (match_operand 1 "" ""))]
13736   "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
13737 {
13738   if (constant_call_address_operand (operands[0], QImode))
13739     return "call\t%P0";
13740   return "call\t%A0";
13741 }
13742   [(set_attr "type" "call")])
13743
13744 (define_insn "*sibcall_1"
13745   [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "s,c,d,a"))
13746          (match_operand 1 "" ""))]
13747   "SIBLING_CALL_P (insn) && !TARGET_64BIT"
13748 {
13749   if (constant_call_address_operand (operands[0], QImode))
13750     return "jmp\t%P0";
13751   return "jmp\t%A0";
13752 }
13753   [(set_attr "type" "call")])
13754
13755 (define_insn "*call_1_rex64"
13756   [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rsm"))
13757          (match_operand 1 "" ""))]
13758   "!SIBLING_CALL_P (insn) && TARGET_64BIT"
13759 {
13760   if (constant_call_address_operand (operands[0], QImode))
13761     return "call\t%P0";
13762   return "call\t%A0";
13763 }
13764   [(set_attr "type" "call")])
13765
13766 (define_insn "*sibcall_1_rex64"
13767   [(call (mem:QI (match_operand:DI 0 "constant_call_address_operand" ""))
13768          (match_operand 1 "" ""))]
13769   "SIBLING_CALL_P (insn) && TARGET_64BIT"
13770   "jmp\t%P0"
13771   [(set_attr "type" "call")])
13772
13773 (define_insn "*sibcall_1_rex64_v"
13774   [(call (mem:QI (reg:DI 40))
13775          (match_operand 0 "" ""))]
13776   "SIBLING_CALL_P (insn) && TARGET_64BIT"
13777   "jmp\t*%%r11"
13778   [(set_attr "type" "call")])
13779
13780
13781 ;; Call subroutine, returning value in operand 0
13782
13783 (define_expand "call_value_pop"
13784   [(parallel [(set (match_operand 0 "" "")
13785                    (call (match_operand:QI 1 "" "")
13786                          (match_operand:SI 2 "" "")))
13787               (set (reg:SI 7)
13788                    (plus:SI (reg:SI 7)
13789                             (match_operand:SI 4 "" "")))])]
13790   "!TARGET_64BIT"
13791 {
13792   ix86_expand_call (operands[0], operands[1], operands[2],
13793                     operands[3], operands[4], 0);
13794   DONE;
13795 })
13796
13797 (define_expand "call_value"
13798   [(set (match_operand 0 "" "")
13799         (call (match_operand:QI 1 "" "")
13800               (match_operand:SI 2 "" "")))
13801    (use (match_operand:SI 3 "" ""))]
13802   ;; Operand 2 not used on the i386.
13803   ""
13804 {
13805   ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 0);
13806   DONE;
13807 })
13808
13809 (define_expand "sibcall_value"
13810   [(set (match_operand 0 "" "")
13811         (call (match_operand:QI 1 "" "")
13812               (match_operand:SI 2 "" "")))
13813    (use (match_operand:SI 3 "" ""))]
13814   ;; Operand 2 not used on the i386.
13815   ""
13816 {
13817   ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 1);
13818   DONE;
13819 })
13820
13821 ;; Call subroutine returning any type.
13822
13823 (define_expand "untyped_call"
13824   [(parallel [(call (match_operand 0 "" "")
13825                     (const_int 0))
13826               (match_operand 1 "" "")
13827               (match_operand 2 "" "")])]
13828   ""
13829 {
13830   int i;
13831
13832   /* In order to give reg-stack an easier job in validating two
13833      coprocessor registers as containing a possible return value,
13834      simply pretend the untyped call returns a complex long double
13835      value.  */
13836
13837   ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
13838                      ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
13839                     operands[0], const0_rtx, GEN_INT (SSE_REGPARM_MAX - 1),
13840                     NULL, 0);
13841
13842   for (i = 0; i < XVECLEN (operands[2], 0); i++)
13843     {
13844       rtx set = XVECEXP (operands[2], 0, i);
13845       emit_move_insn (SET_DEST (set), SET_SRC (set));
13846     }
13847
13848   /* The optimizer does not know that the call sets the function value
13849      registers we stored in the result block.  We avoid problems by
13850      claiming that all hard registers are used and clobbered at this
13851      point.  */
13852   emit_insn (gen_blockage (const0_rtx));
13853
13854   DONE;
13855 })
13856 \f
13857 ;; Prologue and epilogue instructions
13858
13859 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
13860 ;; all of memory.  This blocks insns from being moved across this point.
13861
13862 (define_insn "blockage"
13863   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_BLOCKAGE)]
13864   ""
13865   ""
13866   [(set_attr "length" "0")])
13867
13868 ;; Insn emitted into the body of a function to return from a function.
13869 ;; This is only done if the function's epilogue is known to be simple.
13870 ;; See comments for ix86_can_use_return_insn_p in i386.c.
13871
13872 (define_expand "return"
13873   [(return)]
13874   "ix86_can_use_return_insn_p ()"
13875 {
13876   if (current_function_pops_args)
13877     {
13878       rtx popc = GEN_INT (current_function_pops_args);
13879       emit_jump_insn (gen_return_pop_internal (popc));
13880       DONE;
13881     }
13882 })
13883
13884 (define_insn "return_internal"
13885   [(return)]
13886   "reload_completed"
13887   "ret"
13888   [(set_attr "length" "1")
13889    (set_attr "length_immediate" "0")
13890    (set_attr "modrm" "0")])
13891
13892 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
13893 ;; instruction Athlon and K8 have.
13894
13895 (define_insn "return_internal_long"
13896   [(return)
13897    (unspec [(const_int 0)] UNSPEC_REP)]
13898   "reload_completed"
13899   "rep {;} ret"
13900   [(set_attr "length" "1")
13901    (set_attr "length_immediate" "0")
13902    (set_attr "prefix_rep" "1")
13903    (set_attr "modrm" "0")])
13904
13905 (define_insn "return_pop_internal"
13906   [(return)
13907    (use (match_operand:SI 0 "const_int_operand" ""))]
13908   "reload_completed"
13909   "ret\t%0"
13910   [(set_attr "length" "3")
13911    (set_attr "length_immediate" "2")
13912    (set_attr "modrm" "0")])
13913
13914 (define_insn "return_indirect_internal"
13915   [(return)
13916    (use (match_operand:SI 0 "register_operand" "r"))]
13917   "reload_completed"
13918   "jmp\t%A0"
13919   [(set_attr "type" "ibr")
13920    (set_attr "length_immediate" "0")])
13921
13922 (define_insn "nop"
13923   [(const_int 0)]
13924   ""
13925   "nop"
13926   [(set_attr "length" "1")
13927    (set_attr "length_immediate" "0")
13928    (set_attr "modrm" "0")
13929    (set_attr "ppro_uops" "one")])
13930
13931 ;; Align to 16-byte boundary, max skip in op0.  Used to avoid
13932 ;; branch prediction penalty for the third jump in a 16-byte
13933 ;; block on K8.
13934
13935 (define_insn "align"
13936   [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
13937   ""
13938 {
13939 #ifdef ASM_OUTPUT_MAX_SKIP_ALIGN
13940   ASM_OUTPUT_MAX_SKIP_ALIGN (asm_out_file, 4, (int)INTVAL (operands[0]));
13941 #else
13942   /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
13943      The align insn is used to avoid 3 jump instructions in the row to improve
13944      branch prediction and the benefits hardly outweight the cost of extra 8
13945      nops on the average inserted by full alignment pseudo operation.  */
13946 #endif
13947   return "";
13948 }
13949   [(set_attr "length" "16")])
13950
13951 (define_expand "prologue"
13952   [(const_int 1)]
13953   ""
13954   "ix86_expand_prologue (); DONE;")
13955
13956 (define_insn "set_got"
13957   [(set (match_operand:SI 0 "register_operand" "=r")
13958         (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
13959    (clobber (reg:CC 17))]
13960   "!TARGET_64BIT"
13961   { return output_set_got (operands[0]); }
13962   [(set_attr "type" "multi")
13963    (set_attr "length" "12")])
13964
13965 (define_expand "epilogue"
13966   [(const_int 1)]
13967   ""
13968   "ix86_expand_epilogue (1); DONE;")
13969
13970 (define_expand "sibcall_epilogue"
13971   [(const_int 1)]
13972   ""
13973   "ix86_expand_epilogue (0); DONE;")
13974
13975 (define_expand "eh_return"
13976   [(use (match_operand 0 "register_operand" ""))]
13977   ""
13978 {
13979   rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
13980
13981   /* Tricky bit: we write the address of the handler to which we will
13982      be returning into someone else's stack frame, one word below the
13983      stack address we wish to restore.  */
13984   tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
13985   tmp = plus_constant (tmp, -UNITS_PER_WORD);
13986   tmp = gen_rtx_MEM (Pmode, tmp);
13987   emit_move_insn (tmp, ra);
13988
13989   if (Pmode == SImode)
13990     emit_insn (gen_eh_return_si (sa));
13991   else
13992     emit_insn (gen_eh_return_di (sa));
13993   emit_barrier ();
13994   DONE;
13995 })
13996
13997 (define_insn_and_split "eh_return_si"
13998   [(unspec_volatile [(match_operand:SI 0 "register_operand" "c")]
13999                     UNSPECV_EH_RETURN)]
14000   "!TARGET_64BIT"
14001   "#"
14002   "reload_completed"
14003   [(const_int 1)]
14004   "ix86_expand_epilogue (2); DONE;")
14005
14006 (define_insn_and_split "eh_return_di"
14007   [(unspec_volatile [(match_operand:DI 0 "register_operand" "c")]
14008                     UNSPECV_EH_RETURN)]
14009   "TARGET_64BIT"
14010   "#"
14011   "reload_completed"
14012   [(const_int 1)]
14013   "ix86_expand_epilogue (2); DONE;")
14014
14015 (define_insn "leave"
14016   [(set (reg:SI 7) (plus:SI (reg:SI 6) (const_int 4)))
14017    (set (reg:SI 6) (mem:SI (reg:SI 6)))
14018    (clobber (mem:BLK (scratch)))]
14019   "!TARGET_64BIT"
14020   "leave"
14021   [(set_attr "type" "leave")])
14022
14023 (define_insn "leave_rex64"
14024   [(set (reg:DI 7) (plus:DI (reg:DI 6) (const_int 8)))
14025    (set (reg:DI 6) (mem:DI (reg:DI 6)))
14026    (clobber (mem:BLK (scratch)))]
14027   "TARGET_64BIT"
14028   "leave"
14029   [(set_attr "type" "leave")])
14030 \f
14031 (define_expand "ffssi2"
14032   [(parallel
14033      [(set (match_operand:SI 0 "register_operand" "") 
14034            (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "")))
14035       (clobber (match_scratch:SI 2 ""))
14036       (clobber (reg:CC 17))])]
14037   ""
14038   "")
14039
14040 (define_insn_and_split "*ffs_cmove"
14041   [(set (match_operand:SI 0 "register_operand" "=r") 
14042         (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
14043    (clobber (match_scratch:SI 2 "=&r"))
14044    (clobber (reg:CC 17))]
14045   "TARGET_CMOVE"
14046   "#"
14047   "&& reload_completed"
14048   [(set (match_dup 2) (const_int -1))
14049    (parallel [(set (reg:CCZ 17) (compare:CCZ (match_dup 1) (const_int 0)))
14050               (set (match_dup 0) (ctz:SI (match_dup 1)))])
14051    (set (match_dup 0) (if_then_else:SI
14052                         (eq (reg:CCZ 17) (const_int 0))
14053                         (match_dup 2)
14054                         (match_dup 0)))
14055    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
14056               (clobber (reg:CC 17))])]
14057   "")
14058
14059 (define_insn_and_split "*ffs_no_cmove"
14060   [(set (match_operand:SI 0 "nonimmediate_operand" "=r") 
14061         (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
14062    (clobber (match_scratch:SI 2 "=&q"))
14063    (clobber (reg:CC 17))]
14064   ""
14065   "#"
14066   "reload_completed"
14067   [(parallel [(set (reg:CCZ 17) (compare:CCZ (match_dup 1) (const_int 0)))
14068               (set (match_dup 0) (ctz:SI (match_dup 1)))])
14069    (set (strict_low_part (match_dup 3))
14070         (eq:QI (reg:CCZ 17) (const_int 0)))
14071    (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
14072               (clobber (reg:CC 17))])
14073    (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
14074               (clobber (reg:CC 17))])
14075    (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
14076               (clobber (reg:CC 17))])]
14077 {
14078   operands[3] = gen_lowpart (QImode, operands[2]);
14079   ix86_expand_clear (operands[2]);
14080 })
14081
14082 (define_insn "*ffssi_1"
14083   [(set (reg:CCZ 17)
14084         (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "rm")
14085                      (const_int 0)))
14086    (set (match_operand:SI 0 "register_operand" "=r")
14087         (ctz:SI (match_dup 1)))]
14088   ""
14089   "bsf{l}\t{%1, %0|%0, %1}"
14090   [(set_attr "prefix_0f" "1")
14091    (set_attr "ppro_uops" "few")])
14092
14093 (define_insn "ctzsi2"
14094   [(set (match_operand:SI 0 "register_operand" "=r")
14095         (ctz:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
14096    (clobber (reg:CC 17))]
14097   ""
14098   "bsf{l}\t{%1, %0|%0, %1}"
14099   [(set_attr "prefix_0f" "1")
14100    (set_attr "ppro_uops" "few")])
14101
14102 (define_expand "clzsi2"
14103   [(parallel
14104      [(set (match_operand:SI 0 "register_operand" "")
14105            (minus:SI (const_int 31)
14106                      (clz:SI (match_operand:SI 1 "nonimmediate_operand" ""))))
14107       (clobber (reg:CC 17))])
14108    (parallel
14109      [(set (match_dup 0) (xor:SI (match_dup 0) (const_int 31)))
14110       (clobber (reg:CC 17))])]
14111   ""
14112   "")
14113
14114 (define_insn "*bsr"
14115   [(set (match_operand:SI 0 "register_operand" "=r")
14116         (minus:SI (const_int 31)
14117                   (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
14118    (clobber (reg:CC 17))]
14119   ""
14120   "bsr{l}\t{%1, %0|%0, %1}"
14121   [(set_attr "prefix_0f" "1")
14122    (set_attr "ppro_uops" "few")])
14123 \f
14124 ;; Thread-local storage patterns for ELF.
14125 ;;
14126 ;; Note that these code sequences must appear exactly as shown
14127 ;; in order to allow linker relaxation.
14128
14129 (define_insn "*tls_global_dynamic_32_gnu"
14130   [(set (match_operand:SI 0 "register_operand" "=a")
14131         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14132                     (match_operand:SI 2 "tls_symbolic_operand" "")
14133                     (match_operand:SI 3 "call_insn_operand" "")]
14134                     UNSPEC_TLS_GD))
14135    (clobber (match_scratch:SI 4 "=d"))
14136    (clobber (match_scratch:SI 5 "=c"))
14137    (clobber (reg:CC 17))]
14138   "!TARGET_64BIT && TARGET_GNU_TLS"
14139   "lea{l}\t{%a2@TLSGD(,%1,1), %0|%0, %a2@TLSGD[%1*1]}\;call\t%P3"
14140   [(set_attr "type" "multi")
14141    (set_attr "length" "12")])
14142
14143 (define_insn "*tls_global_dynamic_32_sun"
14144   [(set (match_operand:SI 0 "register_operand" "=a")
14145         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14146                     (match_operand:SI 2 "tls_symbolic_operand" "")
14147                     (match_operand:SI 3 "call_insn_operand" "")]
14148                     UNSPEC_TLS_GD))
14149    (clobber (match_scratch:SI 4 "=d"))
14150    (clobber (match_scratch:SI 5 "=c"))
14151    (clobber (reg:CC 17))]
14152   "!TARGET_64BIT && TARGET_SUN_TLS"
14153   "lea{l}\t{%a2@DTLNDX(%1), %4|%4, %a2@DTLNDX[%1]}
14154         push{l}\t%4\;call\t%a2@TLSPLT\;pop{l}\t%4\;nop"
14155   [(set_attr "type" "multi")
14156    (set_attr "length" "14")])
14157
14158 (define_expand "tls_global_dynamic_32"
14159   [(parallel [(set (match_operand:SI 0 "register_operand" "")
14160                    (unspec:SI
14161                     [(match_dup 2)
14162                      (match_operand:SI 1 "tls_symbolic_operand" "")
14163                      (match_dup 3)]
14164                     UNSPEC_TLS_GD))
14165               (clobber (match_scratch:SI 4 ""))
14166               (clobber (match_scratch:SI 5 ""))
14167               (clobber (reg:CC 17))])]
14168   ""
14169 {
14170   if (flag_pic)
14171     operands[2] = pic_offset_table_rtx;
14172   else
14173     {
14174       operands[2] = gen_reg_rtx (Pmode);
14175       emit_insn (gen_set_got (operands[2]));
14176     }
14177   operands[3] = ix86_tls_get_addr ();
14178 })
14179
14180 (define_insn "*tls_global_dynamic_64"
14181   [(set (match_operand:DI 0 "register_operand" "=a")
14182         (call (mem:QI (match_operand:DI 2 "call_insn_operand" ""))
14183                       (match_operand:DI 3 "" "")))
14184    (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
14185               UNSPEC_TLS_GD)]
14186   "TARGET_64BIT"
14187   ".byte\t0x66\;lea{q}\t{%a1@TLSGD(%%rip), %%rdi|%%rdi, %a1@TLSGD[%%rip]}\;.word\t0x6666\;rex64\;call\t%P2"
14188   [(set_attr "type" "multi")
14189    (set_attr "length" "16")])
14190
14191 (define_expand "tls_global_dynamic_64"
14192   [(parallel [(set (match_operand:DI 0 "register_operand" "")
14193                    (call (mem:QI (match_dup 2)) (const_int 0)))
14194               (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
14195                          UNSPEC_TLS_GD)])]
14196   ""
14197 {
14198   operands[2] = ix86_tls_get_addr ();
14199 })
14200
14201 (define_insn "*tls_local_dynamic_base_32_gnu"
14202   [(set (match_operand:SI 0 "register_operand" "=a")
14203         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14204                     (match_operand:SI 2 "call_insn_operand" "")]
14205                    UNSPEC_TLS_LD_BASE))
14206    (clobber (match_scratch:SI 3 "=d"))
14207    (clobber (match_scratch:SI 4 "=c"))
14208    (clobber (reg:CC 17))]
14209   "!TARGET_64BIT && TARGET_GNU_TLS"
14210   "lea{l}\t{%&@TLSLDM(%1), %0|%0, %&@TLSLDM[%1]}\;call\t%P2"
14211   [(set_attr "type" "multi")
14212    (set_attr "length" "11")])
14213
14214 (define_insn "*tls_local_dynamic_base_32_sun"
14215   [(set (match_operand:SI 0 "register_operand" "=a")
14216         (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14217                     (match_operand:SI 2 "call_insn_operand" "")]
14218                    UNSPEC_TLS_LD_BASE))
14219    (clobber (match_scratch:SI 3 "=d"))
14220    (clobber (match_scratch:SI 4 "=c"))
14221    (clobber (reg:CC 17))]
14222   "!TARGET_64BIT && TARGET_SUN_TLS"
14223   "lea{l}\t{%&@TMDNX(%1), %3|%3, %&@TMDNX[%1]}
14224         push{l}\t%3\;call\t%&@TLSPLT\;pop{l}\t%3"
14225   [(set_attr "type" "multi")
14226    (set_attr "length" "13")])
14227
14228 (define_expand "tls_local_dynamic_base_32"
14229   [(parallel [(set (match_operand:SI 0 "register_operand" "")
14230                    (unspec:SI [(match_dup 1) (match_dup 2)]
14231                               UNSPEC_TLS_LD_BASE))
14232               (clobber (match_scratch:SI 3 ""))
14233               (clobber (match_scratch:SI 4 ""))
14234               (clobber (reg:CC 17))])]
14235   ""
14236 {
14237   if (flag_pic)
14238     operands[1] = pic_offset_table_rtx;
14239   else
14240     {
14241       operands[1] = gen_reg_rtx (Pmode);
14242       emit_insn (gen_set_got (operands[1]));
14243     }
14244   operands[2] = ix86_tls_get_addr ();
14245 })
14246
14247 (define_insn "*tls_local_dynamic_base_64"
14248   [(set (match_operand:DI 0 "register_operand" "=a")
14249         (call (mem:QI (match_operand:DI 1 "call_insn_operand" ""))
14250                       (match_operand:DI 2 "" "")))
14251    (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
14252   "TARGET_64BIT"
14253   "lea{q}\t{%&@TLSLD(%%rip), %%rdi|%%rdi, %&@TLSLD[%%rip]}\;call\t%P1"
14254   [(set_attr "type" "multi")
14255    (set_attr "length" "12")])
14256
14257 (define_expand "tls_local_dynamic_base_64"
14258   [(parallel [(set (match_operand:DI 0 "register_operand" "")
14259                    (call (mem:QI (match_dup 1)) (const_int 0)))
14260               (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])]
14261   ""
14262 {
14263   operands[1] = ix86_tls_get_addr ();
14264 })
14265
14266 ;; Local dynamic of a single variable is a lose.  Show combine how
14267 ;; to convert that back to global dynamic.
14268
14269 (define_insn_and_split "*tls_local_dynamic_32_once"
14270   [(set (match_operand:SI 0 "register_operand" "=a")
14271         (plus:SI (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14272                              (match_operand:SI 2 "call_insn_operand" "")]
14273                             UNSPEC_TLS_LD_BASE)
14274                  (const:SI (unspec:SI
14275                             [(match_operand:SI 3 "tls_symbolic_operand" "")]
14276                             UNSPEC_DTPOFF))))
14277    (clobber (match_scratch:SI 4 "=d"))
14278    (clobber (match_scratch:SI 5 "=c"))
14279    (clobber (reg:CC 17))]
14280   ""
14281   "#"
14282   ""
14283   [(parallel [(set (match_dup 0)
14284                    (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
14285                               UNSPEC_TLS_GD))
14286               (clobber (match_dup 4))
14287               (clobber (match_dup 5))
14288               (clobber (reg:CC 17))])]
14289   "")
14290
14291 ;; Load and add the thread base pointer from %gs:0.
14292
14293 (define_insn "*load_tp_si"
14294   [(set (match_operand:SI 0 "register_operand" "=r")
14295         (unspec:SI [(const_int 0)] UNSPEC_TP))]
14296   "!TARGET_64BIT"
14297   "mov{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}"
14298   [(set_attr "type" "imov")
14299    (set_attr "modrm" "0")
14300    (set_attr "length" "7")
14301    (set_attr "memory" "load")
14302    (set_attr "imm_disp" "false")])
14303
14304 (define_insn "*add_tp_si"
14305   [(set (match_operand:SI 0 "register_operand" "=r")
14306         (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
14307                  (match_operand:SI 1 "register_operand" "0")))
14308    (clobber (reg:CC 17))]
14309   "!TARGET_64BIT"
14310   "add{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}"
14311   [(set_attr "type" "alu")
14312    (set_attr "modrm" "0")
14313    (set_attr "length" "7")
14314    (set_attr "memory" "load")
14315    (set_attr "imm_disp" "false")])
14316
14317 (define_insn "*load_tp_di"
14318   [(set (match_operand:DI 0 "register_operand" "=r")
14319         (unspec:DI [(const_int 0)] UNSPEC_TP))]
14320   "TARGET_64BIT"
14321   "mov{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}"
14322   [(set_attr "type" "imov")
14323    (set_attr "modrm" "0")
14324    (set_attr "length" "7")
14325    (set_attr "memory" "load")
14326    (set_attr "imm_disp" "false")])
14327
14328 (define_insn "*add_tp_di"
14329   [(set (match_operand:DI 0 "register_operand" "=r")
14330         (plus:DI (unspec:DI [(const_int 0)] UNSPEC_TP)
14331                  (match_operand:DI 1 "register_operand" "0")))
14332    (clobber (reg:CC 17))]
14333   "TARGET_64BIT"
14334   "add{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}"
14335   [(set_attr "type" "alu")
14336    (set_attr "modrm" "0")
14337    (set_attr "length" "7")
14338    (set_attr "memory" "load")
14339    (set_attr "imm_disp" "false")])
14340 \f
14341 ;; These patterns match the binary 387 instructions for addM3, subM3,
14342 ;; mulM3 and divM3.  There are three patterns for each of DFmode and
14343 ;; SFmode.  The first is the normal insn, the second the same insn but
14344 ;; with one operand a conversion, and the third the same insn but with
14345 ;; the other operand a conversion.  The conversion may be SFmode or
14346 ;; SImode if the target mode DFmode, but only SImode if the target mode
14347 ;; is SFmode.
14348
14349 ;; Gcc is slightly more smart about handling normal two address instructions
14350 ;; so use special patterns for add and mull.
14351 (define_insn "*fop_sf_comm_nosse"
14352   [(set (match_operand:SF 0 "register_operand" "=f")
14353         (match_operator:SF 3 "binary_fp_operator"
14354                         [(match_operand:SF 1 "nonimmediate_operand" "%0")
14355                          (match_operand:SF 2 "nonimmediate_operand" "fm")]))]
14356   "TARGET_80387 && !TARGET_SSE_MATH
14357    && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'
14358    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14359   "* return output_387_binary_op (insn, operands);"
14360   [(set (attr "type") 
14361         (if_then_else (match_operand:SF 3 "mult_operator" "") 
14362            (const_string "fmul")
14363            (const_string "fop")))
14364    (set_attr "mode" "SF")])
14365
14366 (define_insn "*fop_sf_comm"
14367   [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
14368         (match_operator:SF 3 "binary_fp_operator"
14369                         [(match_operand:SF 1 "nonimmediate_operand" "%0,0")
14370                          (match_operand:SF 2 "nonimmediate_operand" "fm#x,xm#f")]))]
14371   "TARGET_80387 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
14372    && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'
14373    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14374   "* return output_387_binary_op (insn, operands);"
14375   [(set (attr "type") 
14376         (if_then_else (eq_attr "alternative" "1")
14377            (if_then_else (match_operand:SF 3 "mult_operator" "") 
14378               (const_string "ssemul")
14379               (const_string "sseadd"))
14380            (if_then_else (match_operand:SF 3 "mult_operator" "") 
14381               (const_string "fmul")
14382               (const_string "fop"))))
14383    (set_attr "mode" "SF")])
14384
14385 (define_insn "*fop_sf_comm_sse"
14386   [(set (match_operand:SF 0 "register_operand" "=x")
14387         (match_operator:SF 3 "binary_fp_operator"
14388                         [(match_operand:SF 1 "nonimmediate_operand" "%0")
14389                          (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
14390   "TARGET_SSE_MATH && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'
14391    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14392   "* return output_387_binary_op (insn, operands);"
14393   [(set (attr "type") 
14394         (if_then_else (match_operand:SF 3 "mult_operator" "") 
14395            (const_string "ssemul")
14396            (const_string "sseadd")))
14397    (set_attr "mode" "SF")])
14398
14399 (define_insn "*fop_df_comm_nosse"
14400   [(set (match_operand:DF 0 "register_operand" "=f")
14401         (match_operator:DF 3 "binary_fp_operator"
14402                         [(match_operand:DF 1 "nonimmediate_operand" "%0")
14403                          (match_operand:DF 2 "nonimmediate_operand" "fm")]))]
14404   "TARGET_80387 && (!TARGET_SSE2 || !TARGET_SSE_MATH)
14405    && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'
14406    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14407   "* return output_387_binary_op (insn, operands);"
14408   [(set (attr "type") 
14409         (if_then_else (match_operand:SF 3 "mult_operator" "") 
14410            (const_string "fmul")
14411            (const_string "fop")))
14412    (set_attr "mode" "DF")])
14413
14414 (define_insn "*fop_df_comm"
14415   [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
14416         (match_operator:DF 3 "binary_fp_operator"
14417                         [(match_operand:DF 1 "nonimmediate_operand" "%0,0")
14418                          (match_operand:DF 2 "nonimmediate_operand" "fm#Y,Ym#f")]))]
14419   "TARGET_80387 && TARGET_SSE_MATH && TARGET_SSE2 && TARGET_MIX_SSE_I387
14420    && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'
14421    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14422   "* return output_387_binary_op (insn, operands);"
14423   [(set (attr "type") 
14424         (if_then_else (eq_attr "alternative" "1")
14425            (if_then_else (match_operand:SF 3 "mult_operator" "") 
14426               (const_string "ssemul")
14427               (const_string "sseadd"))
14428            (if_then_else (match_operand:SF 3 "mult_operator" "") 
14429               (const_string "fmul")
14430               (const_string "fop"))))
14431    (set_attr "mode" "DF")])
14432
14433 (define_insn "*fop_df_comm_sse"
14434   [(set (match_operand:DF 0 "register_operand" "=Y")
14435         (match_operator:DF 3 "binary_fp_operator"
14436                         [(match_operand:DF 1 "nonimmediate_operand" "%0")
14437                          (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
14438   "TARGET_SSE2 && TARGET_SSE_MATH
14439    && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'
14440    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14441   "* return output_387_binary_op (insn, operands);"
14442   [(set (attr "type") 
14443         (if_then_else (match_operand:SF 3 "mult_operator" "") 
14444            (const_string "ssemul")
14445            (const_string "sseadd")))
14446    (set_attr "mode" "DF")])
14447
14448 (define_insn "*fop_xf_comm"
14449   [(set (match_operand:XF 0 "register_operand" "=f")
14450         (match_operator:XF 3 "binary_fp_operator"
14451                         [(match_operand:XF 1 "register_operand" "%0")
14452                          (match_operand:XF 2 "register_operand" "f")]))]
14453   "TARGET_80387
14454    && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'"
14455   "* return output_387_binary_op (insn, operands);"
14456   [(set (attr "type") 
14457         (if_then_else (match_operand:XF 3 "mult_operator" "") 
14458            (const_string "fmul")
14459            (const_string "fop")))
14460    (set_attr "mode" "XF")])
14461
14462 (define_insn "*fop_sf_1_nosse"
14463   [(set (match_operand:SF 0 "register_operand" "=f,f")
14464         (match_operator:SF 3 "binary_fp_operator"
14465                         [(match_operand:SF 1 "nonimmediate_operand" "0,fm")
14466                          (match_operand:SF 2 "nonimmediate_operand" "fm,0")]))]
14467   "TARGET_80387 && !TARGET_SSE_MATH
14468    && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'
14469    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14470   "* return output_387_binary_op (insn, operands);"
14471   [(set (attr "type") 
14472         (cond [(match_operand:SF 3 "mult_operator" "") 
14473                  (const_string "fmul")
14474                (match_operand:SF 3 "div_operator" "") 
14475                  (const_string "fdiv")
14476               ]
14477               (const_string "fop")))
14478    (set_attr "mode" "SF")])
14479
14480 (define_insn "*fop_sf_1"
14481   [(set (match_operand:SF 0 "register_operand" "=f,f,x")
14482         (match_operator:SF 3 "binary_fp_operator"
14483                         [(match_operand:SF 1 "nonimmediate_operand" "0,fm,0")
14484                          (match_operand:SF 2 "nonimmediate_operand" "fm,0,xm#f")]))]
14485   "TARGET_80387 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
14486    && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'
14487    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14488   "* return output_387_binary_op (insn, operands);"
14489   [(set (attr "type") 
14490         (cond [(and (eq_attr "alternative" "2")
14491                     (match_operand:SF 3 "mult_operator" ""))
14492                  (const_string "ssemul")
14493                (and (eq_attr "alternative" "2")
14494                     (match_operand:SF 3 "div_operator" ""))
14495                  (const_string "ssediv")
14496                (eq_attr "alternative" "2")
14497                  (const_string "sseadd")
14498                (match_operand:SF 3 "mult_operator" "") 
14499                  (const_string "fmul")
14500                (match_operand:SF 3 "div_operator" "") 
14501                  (const_string "fdiv")
14502               ]
14503               (const_string "fop")))
14504    (set_attr "mode" "SF")])
14505
14506 (define_insn "*fop_sf_1_sse"
14507   [(set (match_operand:SF 0 "register_operand" "=x")
14508         (match_operator:SF 3 "binary_fp_operator"
14509                         [(match_operand:SF 1 "register_operand" "0")
14510                          (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
14511   "TARGET_SSE_MATH
14512    && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'"
14513   "* return output_387_binary_op (insn, operands);"
14514   [(set (attr "type") 
14515         (cond [(match_operand:SF 3 "mult_operator" "")
14516                  (const_string "ssemul")
14517                (match_operand:SF 3 "div_operator" "")
14518                  (const_string "ssediv")
14519               ]
14520               (const_string "sseadd")))
14521    (set_attr "mode" "SF")])
14522
14523 ;; ??? Add SSE splitters for these!
14524 (define_insn "*fop_sf_2"
14525   [(set (match_operand:SF 0 "register_operand" "=f,f")
14526         (match_operator:SF 3 "binary_fp_operator"
14527           [(float:SF (match_operand:SI 1 "nonimmediate_operand" "m,?r"))
14528            (match_operand:SF 2 "register_operand" "0,0")]))]
14529   "TARGET_80387 && TARGET_USE_FIOP && !TARGET_SSE_MATH"
14530   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14531   [(set (attr "type") 
14532         (cond [(match_operand:SF 3 "mult_operator" "") 
14533                  (const_string "fmul")
14534                (match_operand:SF 3 "div_operator" "") 
14535                  (const_string "fdiv")
14536               ]
14537               (const_string "fop")))
14538    (set_attr "fp_int_src" "true")
14539    (set_attr "ppro_uops" "many")
14540    (set_attr "mode" "SI")])
14541
14542 (define_insn "*fop_sf_3"
14543   [(set (match_operand:SF 0 "register_operand" "=f,f")
14544         (match_operator:SF 3 "binary_fp_operator"
14545           [(match_operand:SF 1 "register_operand" "0,0")
14546            (float:SF (match_operand:SI 2 "nonimmediate_operand" "m,?r"))]))]
14547   "TARGET_80387 && TARGET_USE_FIOP && !TARGET_SSE_MATH"
14548   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14549   [(set (attr "type") 
14550         (cond [(match_operand:SF 3 "mult_operator" "") 
14551                  (const_string "fmul")
14552                (match_operand:SF 3 "div_operator" "") 
14553                  (const_string "fdiv")
14554               ]
14555               (const_string "fop")))
14556    (set_attr "fp_int_src" "true")
14557    (set_attr "ppro_uops" "many")
14558    (set_attr "mode" "SI")])
14559
14560 (define_insn "*fop_df_1_nosse"
14561   [(set (match_operand:DF 0 "register_operand" "=f,f")
14562         (match_operator:DF 3 "binary_fp_operator"
14563                         [(match_operand:DF 1 "nonimmediate_operand" "0,fm")
14564                          (match_operand:DF 2 "nonimmediate_operand" "fm,0")]))]
14565   "TARGET_80387 && (!TARGET_SSE2 || !TARGET_SSE_MATH)
14566    && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'
14567    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14568   "* return output_387_binary_op (insn, operands);"
14569   [(set (attr "type") 
14570         (cond [(match_operand:DF 3 "mult_operator" "") 
14571                  (const_string "fmul")
14572                (match_operand:DF 3 "div_operator" "")
14573                  (const_string "fdiv")
14574               ]
14575               (const_string "fop")))
14576    (set_attr "mode" "DF")])
14577
14578
14579 (define_insn "*fop_df_1"
14580   [(set (match_operand:DF 0 "register_operand" "=f#Y,f#Y,Y#f")
14581         (match_operator:DF 3 "binary_fp_operator"
14582                         [(match_operand:DF 1 "nonimmediate_operand" "0,fm,0")
14583                          (match_operand:DF 2 "nonimmediate_operand" "fm,0,Ym#f")]))]
14584   "TARGET_80387 && TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
14585    && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'
14586    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14587   "* return output_387_binary_op (insn, operands);"
14588   [(set (attr "type") 
14589         (cond [(and (eq_attr "alternative" "2")
14590                     (match_operand:SF 3 "mult_operator" ""))
14591                  (const_string "ssemul")
14592                (and (eq_attr "alternative" "2")
14593                     (match_operand:SF 3 "div_operator" ""))
14594                  (const_string "ssediv")
14595                (eq_attr "alternative" "2")
14596                  (const_string "sseadd")
14597                (match_operand:DF 3 "mult_operator" "") 
14598                  (const_string "fmul")
14599                (match_operand:DF 3 "div_operator" "") 
14600                  (const_string "fdiv")
14601               ]
14602               (const_string "fop")))
14603    (set_attr "mode" "DF")])
14604
14605 (define_insn "*fop_df_1_sse"
14606   [(set (match_operand:DF 0 "register_operand" "=Y")
14607         (match_operator:DF 3 "binary_fp_operator"
14608                         [(match_operand:DF 1 "register_operand" "0")
14609                          (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
14610   "TARGET_SSE2 && TARGET_SSE_MATH
14611    && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'"
14612   "* return output_387_binary_op (insn, operands);"
14613   [(set_attr "mode" "DF")
14614    (set (attr "type") 
14615         (cond [(match_operand:SF 3 "mult_operator" "")
14616                  (const_string "ssemul")
14617                (match_operand:SF 3 "div_operator" "")
14618                  (const_string "ssediv")
14619               ]
14620               (const_string "sseadd")))])
14621
14622 ;; ??? Add SSE splitters for these!
14623 (define_insn "*fop_df_2"
14624   [(set (match_operand:DF 0 "register_operand" "=f,f")
14625         (match_operator:DF 3 "binary_fp_operator"
14626            [(float:DF (match_operand:SI 1 "nonimmediate_operand" "m,?r"))
14627             (match_operand:DF 2 "register_operand" "0,0")]))]
14628   "TARGET_80387 && TARGET_USE_FIOP && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14629   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14630   [(set (attr "type") 
14631         (cond [(match_operand:DF 3 "mult_operator" "") 
14632                  (const_string "fmul")
14633                (match_operand:DF 3 "div_operator" "") 
14634                  (const_string "fdiv")
14635               ]
14636               (const_string "fop")))
14637    (set_attr "fp_int_src" "true")
14638    (set_attr "ppro_uops" "many")
14639    (set_attr "mode" "SI")])
14640
14641 (define_insn "*fop_df_3"
14642   [(set (match_operand:DF 0 "register_operand" "=f,f")
14643         (match_operator:DF 3 "binary_fp_operator"
14644            [(match_operand:DF 1 "register_operand" "0,0")
14645             (float:DF (match_operand:SI 2 "nonimmediate_operand" "m,?r"))]))]
14646   "TARGET_80387 && TARGET_USE_FIOP && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14647   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14648   [(set (attr "type") 
14649         (cond [(match_operand:DF 3 "mult_operator" "") 
14650                  (const_string "fmul")
14651                (match_operand:DF 3 "div_operator" "") 
14652                  (const_string "fdiv")
14653               ]
14654               (const_string "fop")))
14655    (set_attr "fp_int_src" "true")
14656    (set_attr "ppro_uops" "many")
14657    (set_attr "mode" "SI")])
14658
14659 (define_insn "*fop_df_4"
14660   [(set (match_operand:DF 0 "register_operand" "=f,f")
14661         (match_operator:DF 3 "binary_fp_operator"
14662            [(float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
14663             (match_operand:DF 2 "register_operand" "0,f")]))]
14664   "TARGET_80387 && (!TARGET_SSE2 || !TARGET_SSE_MATH)
14665    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14666   "* return output_387_binary_op (insn, operands);"
14667   [(set (attr "type") 
14668         (cond [(match_operand:DF 3 "mult_operator" "") 
14669                  (const_string "fmul")
14670                (match_operand:DF 3 "div_operator" "") 
14671                  (const_string "fdiv")
14672               ]
14673               (const_string "fop")))
14674    (set_attr "mode" "SF")])
14675
14676 (define_insn "*fop_df_5"
14677   [(set (match_operand:DF 0 "register_operand" "=f,f")
14678         (match_operator:DF 3 "binary_fp_operator"
14679           [(match_operand:DF 1 "register_operand" "0,f")
14680            (float_extend:DF
14681             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
14682   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14683   "* return output_387_binary_op (insn, operands);"
14684   [(set (attr "type") 
14685         (cond [(match_operand:DF 3 "mult_operator" "") 
14686                  (const_string "fmul")
14687                (match_operand:DF 3 "div_operator" "") 
14688                  (const_string "fdiv")
14689               ]
14690               (const_string "fop")))
14691    (set_attr "mode" "SF")])
14692
14693 (define_insn "*fop_df_6"
14694   [(set (match_operand:DF 0 "register_operand" "=f,f")
14695         (match_operator:DF 3 "binary_fp_operator"
14696           [(float_extend:DF
14697             (match_operand:SF 1 "register_operand" "0,f"))
14698            (float_extend:DF
14699             (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
14700   "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14701   "* return output_387_binary_op (insn, operands);"
14702   [(set (attr "type") 
14703         (cond [(match_operand:DF 3 "mult_operator" "") 
14704                  (const_string "fmul")
14705                (match_operand:DF 3 "div_operator" "") 
14706                  (const_string "fdiv")
14707               ]
14708               (const_string "fop")))
14709    (set_attr "mode" "SF")])
14710
14711 (define_insn "*fop_xf_1"
14712   [(set (match_operand:XF 0 "register_operand" "=f,f")
14713         (match_operator:XF 3 "binary_fp_operator"
14714                         [(match_operand:XF 1 "register_operand" "0,f")
14715                          (match_operand:XF 2 "register_operand" "f,0")]))]
14716   "TARGET_80387
14717    && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'"
14718   "* return output_387_binary_op (insn, operands);"
14719   [(set (attr "type") 
14720         (cond [(match_operand:XF 3 "mult_operator" "") 
14721                  (const_string "fmul")
14722                (match_operand:XF 3 "div_operator" "") 
14723                  (const_string "fdiv")
14724               ]
14725               (const_string "fop")))
14726    (set_attr "mode" "XF")])
14727
14728 (define_insn "*fop_xf_2"
14729   [(set (match_operand:XF 0 "register_operand" "=f,f")
14730         (match_operator:XF 3 "binary_fp_operator"
14731            [(float:XF (match_operand:SI 1 "nonimmediate_operand" "m,?r"))
14732             (match_operand:XF 2 "register_operand" "0,0")]))]
14733   "TARGET_80387 && TARGET_USE_FIOP"
14734   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14735   [(set (attr "type") 
14736         (cond [(match_operand:XF 3 "mult_operator" "") 
14737                  (const_string "fmul")
14738                (match_operand:XF 3 "div_operator" "") 
14739                  (const_string "fdiv")
14740               ]
14741               (const_string "fop")))
14742    (set_attr "fp_int_src" "true")
14743    (set_attr "mode" "SI")
14744    (set_attr "ppro_uops" "many")])
14745
14746 (define_insn "*fop_xf_3"
14747   [(set (match_operand:XF 0 "register_operand" "=f,f")
14748         (match_operator:XF 3 "binary_fp_operator"
14749           [(match_operand:XF 1 "register_operand" "0,0")
14750            (float:XF (match_operand:SI 2 "nonimmediate_operand" "m,?r"))]))]
14751   "TARGET_80387 && TARGET_USE_FIOP"
14752   "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14753   [(set (attr "type") 
14754         (cond [(match_operand:XF 3 "mult_operator" "") 
14755                  (const_string "fmul")
14756                (match_operand:XF 3 "div_operator" "") 
14757                  (const_string "fdiv")
14758               ]
14759               (const_string "fop")))
14760    (set_attr "fp_int_src" "true")
14761    (set_attr "mode" "SI")
14762    (set_attr "ppro_uops" "many")])
14763
14764 (define_insn "*fop_xf_4"
14765   [(set (match_operand:XF 0 "register_operand" "=f,f")
14766         (match_operator:XF 3 "binary_fp_operator"
14767            [(float_extend:XF (match_operand 1 "nonimmediate_operand" "fm,0"))
14768             (match_operand:XF 2 "register_operand" "0,f")]))]
14769   "TARGET_80387"
14770   "* return output_387_binary_op (insn, operands);"
14771   [(set (attr "type") 
14772         (cond [(match_operand:XF 3 "mult_operator" "") 
14773                  (const_string "fmul")
14774                (match_operand:XF 3 "div_operator" "") 
14775                  (const_string "fdiv")
14776               ]
14777               (const_string "fop")))
14778    (set_attr "mode" "SF")])
14779
14780 (define_insn "*fop_xf_5"
14781   [(set (match_operand:XF 0 "register_operand" "=f,f")
14782         (match_operator:XF 3 "binary_fp_operator"
14783           [(match_operand:XF 1 "register_operand" "0,f")
14784            (float_extend:XF
14785             (match_operand 2 "nonimmediate_operand" "fm,0"))]))]
14786   "TARGET_80387"
14787   "* return output_387_binary_op (insn, operands);"
14788   [(set (attr "type") 
14789         (cond [(match_operand:XF 3 "mult_operator" "") 
14790                  (const_string "fmul")
14791                (match_operand:XF 3 "div_operator" "") 
14792                  (const_string "fdiv")
14793               ]
14794               (const_string "fop")))
14795    (set_attr "mode" "SF")])
14796
14797 (define_insn "*fop_xf_6"
14798   [(set (match_operand:XF 0 "register_operand" "=f,f")
14799         (match_operator:XF 3 "binary_fp_operator"
14800           [(float_extend:XF
14801             (match_operand 1 "register_operand" "0,f"))
14802            (float_extend:XF
14803             (match_operand 2 "nonimmediate_operand" "fm,0"))]))]
14804   "TARGET_80387"
14805   "* return output_387_binary_op (insn, operands);"
14806   [(set (attr "type") 
14807         (cond [(match_operand:XF 3 "mult_operator" "") 
14808                  (const_string "fmul")
14809                (match_operand:XF 3 "div_operator" "") 
14810                  (const_string "fdiv")
14811               ]
14812               (const_string "fop")))
14813    (set_attr "mode" "SF")])
14814
14815 (define_split
14816   [(set (match_operand 0 "register_operand" "")
14817         (match_operator 3 "binary_fp_operator"
14818            [(float (match_operand:SI 1 "register_operand" ""))
14819             (match_operand 2 "register_operand" "")]))]
14820   "TARGET_80387 && reload_completed
14821    && FLOAT_MODE_P (GET_MODE (operands[0]))"
14822   [(const_int 0)]
14823
14824   operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
14825   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
14826   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
14827                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
14828                                           GET_MODE (operands[3]),
14829                                           operands[4],
14830                                           operands[2])));
14831   ix86_free_from_memory (GET_MODE (operands[1]));
14832   DONE;
14833 })
14834
14835 (define_split
14836   [(set (match_operand 0 "register_operand" "")
14837         (match_operator 3 "binary_fp_operator"
14838            [(match_operand 1 "register_operand" "")
14839             (float (match_operand:SI 2 "register_operand" ""))]))]
14840   "TARGET_80387 && reload_completed
14841    && FLOAT_MODE_P (GET_MODE (operands[0]))"
14842   [(const_int 0)]
14843 {
14844   operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
14845   operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
14846   emit_insn (gen_rtx_SET (VOIDmode, operands[0],
14847                           gen_rtx_fmt_ee (GET_CODE (operands[3]),
14848                                           GET_MODE (operands[3]),
14849                                           operands[1],
14850                                           operands[4])));
14851   ix86_free_from_memory (GET_MODE (operands[2]));
14852   DONE;
14853 })
14854 \f
14855 ;; FPU special functions.
14856
14857 (define_expand "sqrtsf2"
14858   [(set (match_operand:SF 0 "register_operand" "")
14859         (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
14860   "(! TARGET_NO_FANCY_MATH_387 && TARGET_80387) || TARGET_SSE_MATH"
14861 {
14862   if (!TARGET_SSE_MATH)
14863     operands[1] = force_reg (SFmode, operands[1]);
14864 })
14865
14866 (define_insn "sqrtsf2_1"
14867   [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
14868         (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "0#x,xm#f")))]
14869   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
14870    && (TARGET_SSE_MATH && TARGET_MIX_SSE_I387)"
14871   "@
14872    fsqrt
14873    sqrtss\t{%1, %0|%0, %1}"
14874   [(set_attr "type" "fpspc,sse")
14875    (set_attr "mode" "SF,SF")
14876    (set_attr "athlon_decode" "direct,*")])
14877
14878 (define_insn "sqrtsf2_1_sse_only"
14879   [(set (match_operand:SF 0 "register_operand" "=x")
14880         (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
14881   "TARGET_SSE_MATH && (!TARGET_80387 || !TARGET_MIX_SSE_I387)"
14882   "sqrtss\t{%1, %0|%0, %1}"
14883   [(set_attr "type" "sse")
14884    (set_attr "mode" "SF")
14885    (set_attr "athlon_decode" "*")])
14886
14887 (define_insn "sqrtsf2_i387"
14888   [(set (match_operand:SF 0 "register_operand" "=f")
14889         (sqrt:SF (match_operand:SF 1 "register_operand" "0")))]
14890   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
14891    && !TARGET_SSE_MATH"
14892   "fsqrt"
14893   [(set_attr "type" "fpspc")
14894    (set_attr "mode" "SF")
14895    (set_attr "athlon_decode" "direct")])
14896
14897 (define_expand "sqrtdf2"
14898   [(set (match_operand:DF 0 "register_operand" "")
14899         (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
14900   "(! TARGET_NO_FANCY_MATH_387 && TARGET_80387)
14901    || (TARGET_SSE2 && TARGET_SSE_MATH)"
14902 {
14903   if (!TARGET_SSE2 || !TARGET_SSE_MATH)
14904     operands[1] = force_reg (DFmode, operands[1]);
14905 })
14906
14907 (define_insn "sqrtdf2_1"
14908   [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
14909         (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "0#Y,Ym#f")))]
14910   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
14911    && (TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387)"
14912   "@
14913    fsqrt
14914    sqrtsd\t{%1, %0|%0, %1}"
14915   [(set_attr "type" "fpspc,sse")
14916    (set_attr "mode" "DF,DF")
14917    (set_attr "athlon_decode" "direct,*")])
14918
14919 (define_insn "sqrtdf2_1_sse_only"
14920   [(set (match_operand:DF 0 "register_operand" "=Y")
14921         (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
14922   "TARGET_SSE2 && TARGET_SSE_MATH && (!TARGET_80387 || !TARGET_MIX_SSE_I387)"
14923   "sqrtsd\t{%1, %0|%0, %1}"
14924   [(set_attr "type" "sse")
14925    (set_attr "mode" "DF")
14926    (set_attr "athlon_decode" "*")])
14927
14928 (define_insn "sqrtdf2_i387"
14929   [(set (match_operand:DF 0 "register_operand" "=f")
14930         (sqrt:DF (match_operand:DF 1 "register_operand" "0")))]
14931   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
14932    && (!TARGET_SSE2 || !TARGET_SSE_MATH)"
14933   "fsqrt"
14934   [(set_attr "type" "fpspc")
14935    (set_attr "mode" "DF")
14936    (set_attr "athlon_decode" "direct")])
14937
14938 (define_insn "*sqrtextendsfdf2"
14939   [(set (match_operand:DF 0 "register_operand" "=f")
14940         (sqrt:DF (float_extend:DF
14941                   (match_operand:SF 1 "register_operand" "0"))))]
14942   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
14943    && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14944   "fsqrt"
14945   [(set_attr "type" "fpspc")
14946    (set_attr "mode" "DF")
14947    (set_attr "athlon_decode" "direct")])
14948
14949 (define_insn "sqrtxf2"
14950   [(set (match_operand:XF 0 "register_operand" "=f")
14951         (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
14952   "TARGET_80387 && !TARGET_NO_FANCY_MATH_387 
14953    && (TARGET_IEEE_FP || flag_unsafe_math_optimizations) "
14954   "fsqrt"
14955   [(set_attr "type" "fpspc")
14956    (set_attr "mode" "XF")
14957    (set_attr "athlon_decode" "direct")])
14958
14959 (define_insn "*sqrtextenddfxf2"
14960   [(set (match_operand:XF 0 "register_operand" "=f")
14961         (sqrt:XF (float_extend:XF
14962                   (match_operand:DF 1 "register_operand" "0"))))]
14963   "TARGET_80387 && !TARGET_NO_FANCY_MATH_387"
14964   "fsqrt"
14965   [(set_attr "type" "fpspc")
14966    (set_attr "mode" "XF")
14967    (set_attr "athlon_decode" "direct")])
14968
14969 (define_insn "*sqrtextendsfxf2"
14970   [(set (match_operand:XF 0 "register_operand" "=f")
14971         (sqrt:XF (float_extend:XF
14972                   (match_operand:SF 1 "register_operand" "0"))))]
14973   "TARGET_80387 && !TARGET_NO_FANCY_MATH_387"
14974   "fsqrt"
14975   [(set_attr "type" "fpspc")
14976    (set_attr "mode" "XF")
14977    (set_attr "athlon_decode" "direct")])
14978
14979 (define_insn "sindf2"
14980   [(set (match_operand:DF 0 "register_operand" "=f")
14981         (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_SIN))]
14982   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 
14983    && flag_unsafe_math_optimizations"
14984   "fsin"
14985   [(set_attr "type" "fpspc")
14986    (set_attr "mode" "DF")])
14987
14988 (define_insn "sinsf2"
14989   [(set (match_operand:SF 0 "register_operand" "=f")
14990         (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_SIN))]
14991   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 
14992    && flag_unsafe_math_optimizations"
14993   "fsin"
14994   [(set_attr "type" "fpspc")
14995    (set_attr "mode" "SF")])
14996
14997 (define_insn "*sinextendsfdf2"
14998   [(set (match_operand:DF 0 "register_operand" "=f")
14999         (unspec:DF [(float_extend:DF
15000                      (match_operand:SF 1 "register_operand" "0"))]
15001                    UNSPEC_SIN))]
15002   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 
15003    && flag_unsafe_math_optimizations"
15004   "fsin"
15005   [(set_attr "type" "fpspc")
15006    (set_attr "mode" "DF")])
15007
15008 (define_insn "sinxf2"
15009   [(set (match_operand:XF 0 "register_operand" "=f")
15010         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
15011   "TARGET_80387 && !TARGET_NO_FANCY_MATH_387
15012    && flag_unsafe_math_optimizations"
15013   "fsin"
15014   [(set_attr "type" "fpspc")
15015    (set_attr "mode" "XF")])
15016
15017 (define_insn "cosdf2"
15018   [(set (match_operand:DF 0 "register_operand" "=f")
15019         (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_COS))]
15020   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 
15021    && flag_unsafe_math_optimizations"
15022   "fcos"
15023   [(set_attr "type" "fpspc")
15024    (set_attr "mode" "DF")])
15025
15026 (define_insn "cossf2"
15027   [(set (match_operand:SF 0 "register_operand" "=f")
15028         (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_COS))]
15029   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 
15030    && flag_unsafe_math_optimizations"
15031   "fcos"
15032   [(set_attr "type" "fpspc")
15033    (set_attr "mode" "SF")])
15034
15035 (define_insn "*cosextendsfdf2"
15036   [(set (match_operand:DF 0 "register_operand" "=f")
15037         (unspec:DF [(float_extend:DF
15038                      (match_operand:SF 1 "register_operand" "0"))]
15039                    UNSPEC_COS))]
15040   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 
15041    && flag_unsafe_math_optimizations"
15042   "fcos"
15043   [(set_attr "type" "fpspc")
15044    (set_attr "mode" "DF")])
15045
15046 (define_insn "cosxf2"
15047   [(set (match_operand:XF 0 "register_operand" "=f")
15048         (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
15049   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15050    && flag_unsafe_math_optimizations"
15051   "fcos"
15052   [(set_attr "type" "fpspc")
15053    (set_attr "mode" "XF")])
15054
15055 (define_insn "atan2df3_1"
15056   [(set (match_operand:DF 0 "register_operand" "=f")
15057         (unspec:DF [(match_operand:DF 2 "register_operand" "0")
15058                     (match_operand:DF 1 "register_operand" "u")]
15059                    UNSPEC_FPATAN))
15060    (clobber (match_scratch:DF 3 "=1"))]
15061   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15062    && flag_unsafe_math_optimizations"
15063   "fpatan"
15064   [(set_attr "type" "fpspc")
15065    (set_attr "mode" "DF")])
15066
15067 (define_expand "atan2df3"
15068   [(use (match_operand:DF 0 "register_operand" "=f"))
15069    (use (match_operand:DF 2 "register_operand" "0"))
15070    (use (match_operand:DF 1 "register_operand" "u"))]
15071   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15072    && flag_unsafe_math_optimizations"
15073 {
15074   rtx copy = gen_reg_rtx (DFmode);
15075   emit_move_insn (copy, operands[1]);
15076   emit_insn (gen_atan2df3_1 (operands[0], copy, operands[2]));
15077   DONE;
15078 })
15079
15080 (define_insn "atan2sf3_1"
15081   [(set (match_operand:SF 0 "register_operand" "=f")
15082         (unspec:SF [(match_operand:SF 2 "register_operand" "0")
15083                     (match_operand:SF 1 "register_operand" "u")]
15084                    UNSPEC_FPATAN))
15085    (clobber (match_scratch:SF 3 "=1"))]
15086   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15087    && flag_unsafe_math_optimizations"
15088   "fpatan"
15089   [(set_attr "type" "fpspc")
15090    (set_attr "mode" "SF")])
15091
15092 (define_expand "atan2sf3"
15093   [(use (match_operand:SF 0 "register_operand" "=f"))
15094    (use (match_operand:SF 2 "register_operand" "0"))
15095    (use (match_operand:SF 1 "register_operand" "u"))]
15096   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15097    && flag_unsafe_math_optimizations"
15098 {
15099   rtx copy = gen_reg_rtx (SFmode);
15100   emit_move_insn (copy, operands[1]);
15101   emit_insn (gen_atan2sf3_1 (operands[0], copy, operands[2]));
15102   DONE;
15103 })
15104
15105 (define_insn "atan2xf3_1"
15106   [(set (match_operand:XF 0 "register_operand" "=f")
15107         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15108                     (match_operand:XF 1 "register_operand" "u")]
15109                    UNSPEC_FPATAN))
15110    (clobber (match_scratch:XF 3 "=1"))]
15111   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15112    && flag_unsafe_math_optimizations"
15113   "fpatan"
15114   [(set_attr "type" "fpspc")
15115    (set_attr "mode" "XF")])
15116
15117 (define_expand "atan2xf3"
15118   [(use (match_operand:XF 0 "register_operand" "=f"))
15119    (use (match_operand:XF 2 "register_operand" "0"))
15120    (use (match_operand:XF 1 "register_operand" "u"))]
15121   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15122    && flag_unsafe_math_optimizations"
15123 {
15124   rtx copy = gen_reg_rtx (XFmode);
15125   emit_move_insn (copy, operands[1]);
15126   emit_insn (gen_atan2xf3_1 (operands[0], copy, operands[2]));
15127   DONE;
15128 })
15129
15130 (define_insn "*fyl2x_sfxf3"
15131   [(set (match_operand:SF 0 "register_operand" "=f")
15132          (unspec:SF [(match_operand:SF 2 "register_operand" "0")
15133                      (match_operand:XF 1 "register_operand" "u")]
15134                     UNSPEC_FYL2X))
15135    (clobber (match_scratch:SF 3 "=1"))]
15136   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15137    && flag_unsafe_math_optimizations"
15138   "fyl2x"
15139   [(set_attr "type" "fpspc")
15140    (set_attr "mode" "SF")])
15141
15142 (define_insn "*fyl2x_dfxf3"
15143   [(set (match_operand:DF 0 "register_operand" "=f")
15144          (unspec:DF [(match_operand:DF 2 "register_operand" "0")
15145                      (match_operand:XF 1 "register_operand" "u")]
15146                     UNSPEC_FYL2X))
15147    (clobber (match_scratch:DF 3 "=1"))]
15148   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15149    && flag_unsafe_math_optimizations"
15150   "fyl2x"
15151   [(set_attr "type" "fpspc")
15152    (set_attr "mode" "DF")])
15153
15154 (define_insn "*fyl2x_xf3"
15155   [(set (match_operand:XF 0 "register_operand" "=f")
15156         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15157                     (match_operand:XF 1 "register_operand" "u")]
15158                    UNSPEC_FYL2X))
15159    (clobber (match_scratch:XF 3 "=1"))]
15160   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15161    && flag_unsafe_math_optimizations"
15162   "fyl2x"
15163   [(set_attr "type" "fpspc")
15164    (set_attr "mode" "XF")])
15165
15166 (define_expand "logsf2"
15167   [(parallel [(set (match_operand:SF 0 "register_operand" "")
15168                    (unspec:SF [(match_operand:SF 1 "register_operand" "")
15169                                (match_dup 2)] UNSPEC_FYL2X))
15170               (clobber (match_scratch:SF 3 ""))])]
15171   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15172    && flag_unsafe_math_optimizations"
15173 {
15174   rtx temp;
15175
15176   operands[2] = gen_reg_rtx (XFmode);
15177   temp = standard_80387_constant_rtx (4); /* fldln2 */
15178   emit_move_insn (operands[2], temp);
15179 })
15180
15181 (define_expand "logdf2"
15182   [(parallel [(set (match_operand:DF 0 "register_operand" "")
15183                    (unspec:DF [(match_operand:DF 1 "register_operand" "")
15184                                (match_dup 2)] UNSPEC_FYL2X))
15185               (clobber (match_scratch:DF 3 ""))])]
15186   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15187    && flag_unsafe_math_optimizations"
15188 {
15189   rtx temp;
15190
15191   operands[2] = gen_reg_rtx (XFmode);
15192   temp = standard_80387_constant_rtx (4); /* fldln2 */
15193   emit_move_insn (operands[2], temp);
15194 })
15195
15196 (define_expand "logxf2"
15197   [(parallel [(set (match_operand:XF 0 "register_operand" "")
15198                    (unspec:XF [(match_operand:XF 1 "register_operand" "")
15199                                (match_dup 2)] UNSPEC_FYL2X))
15200               (clobber (match_scratch:XF 3 ""))])]
15201   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15202    && flag_unsafe_math_optimizations"
15203 {
15204   rtx temp;
15205
15206   operands[2] = gen_reg_rtx (XFmode);
15207   temp = standard_80387_constant_rtx (4); /* fldln2 */
15208   emit_move_insn (operands[2], temp);
15209 })
15210
15211 (define_insn "*fscale_sfxf3"
15212   [(set (match_operand:SF 0 "register_operand" "=f")
15213          (unspec:SF [(match_operand:XF 2 "register_operand" "0")
15214                      (match_operand:XF 1 "register_operand" "u")]
15215                     UNSPEC_FSCALE))
15216    (clobber (match_scratch:SF 3 "=1"))]
15217   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15218    && flag_unsafe_math_optimizations"
15219   "fscale\;fstp\t%y1"
15220   [(set_attr "type" "fpspc")
15221    (set_attr "mode" "SF")])
15222
15223 (define_insn "*fscale_dfxf3"
15224   [(set (match_operand:DF 0 "register_operand" "=f")
15225          (unspec:DF [(match_operand:XF 2 "register_operand" "0")
15226                      (match_operand:XF 1 "register_operand" "u")]
15227                     UNSPEC_FSCALE))
15228    (clobber (match_scratch:DF 3 "=1"))]
15229   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15230    && flag_unsafe_math_optimizations"
15231   "fscale\;fstp\t%y1"
15232   [(set_attr "type" "fpspc")
15233    (set_attr "mode" "DF")])
15234
15235 (define_insn "*fscale_xf3"
15236   [(set (match_operand:XF 0 "register_operand" "=f")
15237         (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15238                     (match_operand:XF 1 "register_operand" "u")]
15239                    UNSPEC_FSCALE))
15240    (clobber (match_scratch:XF 3 "=1"))]
15241   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15242    && flag_unsafe_math_optimizations"
15243   "fscale\;fstp\t%y1"
15244   [(set_attr "type" "fpspc")
15245    (set_attr "mode" "XF")])
15246
15247 (define_insn "*frndintxf2"
15248   [(set (match_operand:XF 0 "register_operand" "=f")
15249         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15250          UNSPEC_FRNDINT))]
15251   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15252    && flag_unsafe_math_optimizations"
15253   "frndint"
15254   [(set_attr "type" "fpspc")
15255    (set_attr "mode" "XF")])
15256
15257 (define_insn "*f2xm1xf2"
15258   [(set (match_operand:XF 0 "register_operand" "=f")
15259         (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15260          UNSPEC_F2XM1))]
15261   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15262    && flag_unsafe_math_optimizations"
15263   "f2xm1"
15264   [(set_attr "type" "fpspc")
15265    (set_attr "mode" "XF")])
15266
15267 (define_expand "expsf2"
15268   [(set (match_dup 2)
15269         (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15270    (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15271    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15272    (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15273    (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15274    (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
15275    (parallel [(set (match_operand:SF 0 "register_operand" "")
15276                    (unspec:SF [(match_dup 9) (match_dup 5)] UNSPEC_FSCALE))
15277               (clobber (match_scratch:SF 5 ""))])]
15278   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15279    && flag_unsafe_math_optimizations"
15280 {
15281   rtx temp;
15282   int i;
15283
15284   for (i=2; i<10; i++)
15285     operands[i] = gen_reg_rtx (XFmode);
15286   temp = standard_80387_constant_rtx (5); /* fldl2e */
15287   emit_move_insn (operands[3], temp);
15288   emit_move_insn (operands[8], CONST1_RTX (XFmode));  /* fld1 */
15289 })
15290
15291 (define_expand "expdf2"
15292   [(set (match_dup 2)
15293         (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15294    (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15295    (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15296    (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15297    (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15298    (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
15299    (parallel [(set (match_operand:DF 0 "register_operand" "")
15300                    (unspec:DF [(match_dup 9) (match_dup 5)] UNSPEC_FSCALE))
15301               (clobber (match_scratch:DF 5 ""))])]
15302   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15303    && flag_unsafe_math_optimizations"
15304 {
15305   rtx temp;
15306   int i;
15307
15308   for (i=2; i<10; i++)
15309     operands[i] = gen_reg_rtx (XFmode);
15310   temp = standard_80387_constant_rtx (5); /* fldl2e */
15311   emit_move_insn (operands[3], temp);
15312   emit_move_insn (operands[8], CONST1_RTX (XFmode));  /* fld1 */
15313 })
15314
15315 (define_expand "expxf2"
15316   [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
15317                                (match_dup 2)))
15318    (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
15319    (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
15320    (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
15321    (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
15322    (parallel [(set (match_operand:XF 0 "register_operand" "")
15323                    (unspec:XF [(match_dup 8) (match_dup 4)] UNSPEC_FSCALE))
15324               (clobber (match_scratch:XF 5 ""))])]
15325   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15326    && flag_unsafe_math_optimizations"
15327 {
15328   rtx temp;
15329   int i;
15330
15331   for (i=2; i<9; i++)
15332     operands[i] = gen_reg_rtx (XFmode);
15333   temp = standard_80387_constant_rtx (5); /* fldl2e */
15334   emit_move_insn (operands[2], temp);
15335   emit_move_insn (operands[7], CONST1_RTX (XFmode));  /* fld1 */
15336 })
15337
15338 (define_expand "atansf2"
15339   [(parallel [(set (match_operand:SF 0 "register_operand" "")
15340                    (unspec:SF [(match_dup 2)
15341                                (match_operand:SF 1 "register_operand" "")]
15342                     UNSPEC_FPATAN))
15343               (clobber (match_scratch:SF 3 ""))])]
15344   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15345    && flag_unsafe_math_optimizations"
15346 {
15347   operands[2] = gen_reg_rtx (SFmode);
15348   emit_move_insn (operands[2], CONST1_RTX (SFmode));  /* fld1 */
15349 })
15350
15351 (define_expand "atandf2"
15352   [(parallel [(set (match_operand:DF 0 "register_operand" "")
15353                    (unspec:DF [(match_dup 2)
15354                                (match_operand:DF 1 "register_operand" "")]
15355                     UNSPEC_FPATAN))
15356               (clobber (match_scratch:DF 3 ""))])]
15357   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15358    && flag_unsafe_math_optimizations"
15359 {
15360   operands[2] = gen_reg_rtx (DFmode);
15361   emit_move_insn (operands[2], CONST1_RTX (DFmode));  /* fld1 */
15362 })
15363
15364 (define_expand "atanxf2"
15365   [(parallel [(set (match_operand:XF 0 "register_operand" "")
15366                    (unspec:XF [(match_dup 2)
15367                                (match_operand:XF 1 "register_operand" "")]
15368                     UNSPEC_FPATAN))
15369               (clobber (match_scratch:XF 3 ""))])]
15370   "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
15371    && flag_unsafe_math_optimizations"
15372 {
15373   operands[2] = gen_reg_rtx (XFmode);
15374   emit_move_insn (operands[2], CONST1_RTX (XFmode));  /* fld1 */
15375 })
15376 \f
15377 ;; Block operation instructions
15378
15379 (define_insn "cld"
15380  [(set (reg:SI 19) (const_int 0))]
15381  ""
15382  "cld"
15383   [(set_attr "type" "cld")])
15384
15385 (define_expand "movstrsi"
15386   [(use (match_operand:BLK 0 "memory_operand" ""))
15387    (use (match_operand:BLK 1 "memory_operand" ""))
15388    (use (match_operand:SI 2 "nonmemory_operand" ""))
15389    (use (match_operand:SI 3 "const_int_operand" ""))]
15390   "! optimize_size"
15391 {
15392  if (ix86_expand_movstr (operands[0], operands[1], operands[2], operands[3]))
15393    DONE;
15394  else
15395    FAIL;
15396 })
15397
15398 (define_expand "movstrdi"
15399   [(use (match_operand:BLK 0 "memory_operand" ""))
15400    (use (match_operand:BLK 1 "memory_operand" ""))
15401    (use (match_operand:DI 2 "nonmemory_operand" ""))
15402    (use (match_operand:DI 3 "const_int_operand" ""))]
15403   "TARGET_64BIT"
15404 {
15405  if (ix86_expand_movstr (operands[0], operands[1], operands[2], operands[3]))
15406    DONE;
15407  else
15408    FAIL;
15409 })
15410
15411 ;; Most CPUs don't like single string operations
15412 ;; Handle this case here to simplify previous expander.
15413
15414 (define_expand "strmov"
15415   [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
15416    (set (match_operand 1 "memory_operand" "") (match_dup 4))
15417    (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
15418               (clobber (reg:CC 17))])
15419    (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
15420               (clobber (reg:CC 17))])]
15421   ""
15422 {
15423   rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
15424
15425   /* If .md ever supports :P for Pmode, these can be directly
15426      in the pattern above.  */
15427   operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
15428   operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
15429
15430   if (TARGET_SINGLE_STRINGOP || optimize_size)
15431     {
15432       emit_insn (gen_strmov_singleop (operands[0], operands[1],
15433                                       operands[2], operands[3],
15434                                       operands[5], operands[6]));
15435       DONE;
15436     }
15437
15438   operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
15439 })
15440
15441 (define_expand "strmov_singleop"
15442   [(parallel [(set (match_operand 1 "memory_operand" "")
15443                    (match_operand 3 "memory_operand" ""))
15444               (set (match_operand 0 "register_operand" "")
15445                    (match_operand 4 "" ""))
15446               (set (match_operand 2 "register_operand" "")
15447                    (match_operand 5 "" ""))
15448               (use (reg:SI 19))])]
15449   "TARGET_SINGLE_STRINGOP || optimize_size"
15450   "")
15451
15452 (define_insn "*strmovdi_rex_1"
15453   [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
15454         (mem:DI (match_operand:DI 3 "register_operand" "1")))
15455    (set (match_operand:DI 0 "register_operand" "=D")
15456         (plus:DI (match_dup 2)
15457                  (const_int 8)))
15458    (set (match_operand:DI 1 "register_operand" "=S")
15459         (plus:DI (match_dup 3)
15460                  (const_int 8)))
15461    (use (reg:SI 19))]
15462   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15463   "movsq"
15464   [(set_attr "type" "str")
15465    (set_attr "mode" "DI")
15466    (set_attr "memory" "both")])
15467
15468 (define_insn "*strmovsi_1"
15469   [(set (mem:SI (match_operand:SI 2 "register_operand" "0"))
15470         (mem:SI (match_operand:SI 3 "register_operand" "1")))
15471    (set (match_operand:SI 0 "register_operand" "=D")
15472         (plus:SI (match_dup 2)
15473                  (const_int 4)))
15474    (set (match_operand:SI 1 "register_operand" "=S")
15475         (plus:SI (match_dup 3)
15476                  (const_int 4)))
15477    (use (reg:SI 19))]
15478   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15479   "{movsl|movsd}"
15480   [(set_attr "type" "str")
15481    (set_attr "mode" "SI")
15482    (set_attr "memory" "both")])
15483
15484 (define_insn "*strmovsi_rex_1"
15485   [(set (mem:SI (match_operand:DI 2 "register_operand" "0"))
15486         (mem:SI (match_operand:DI 3 "register_operand" "1")))
15487    (set (match_operand:DI 0 "register_operand" "=D")
15488         (plus:DI (match_dup 2)
15489                  (const_int 4)))
15490    (set (match_operand:DI 1 "register_operand" "=S")
15491         (plus:DI (match_dup 3)
15492                  (const_int 4)))
15493    (use (reg:SI 19))]
15494   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15495   "{movsl|movsd}"
15496   [(set_attr "type" "str")
15497    (set_attr "mode" "SI")
15498    (set_attr "memory" "both")])
15499
15500 (define_insn "*strmovhi_1"
15501   [(set (mem:HI (match_operand:SI 2 "register_operand" "0"))
15502         (mem:HI (match_operand:SI 3 "register_operand" "1")))
15503    (set (match_operand:SI 0 "register_operand" "=D")
15504         (plus:SI (match_dup 2)
15505                  (const_int 2)))
15506    (set (match_operand:SI 1 "register_operand" "=S")
15507         (plus:SI (match_dup 3)
15508                  (const_int 2)))
15509    (use (reg:SI 19))]
15510   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15511   "movsw"
15512   [(set_attr "type" "str")
15513    (set_attr "memory" "both")
15514    (set_attr "mode" "HI")])
15515
15516 (define_insn "*strmovhi_rex_1"
15517   [(set (mem:HI (match_operand:DI 2 "register_operand" "0"))
15518         (mem:HI (match_operand:DI 3 "register_operand" "1")))
15519    (set (match_operand:DI 0 "register_operand" "=D")
15520         (plus:DI (match_dup 2)
15521                  (const_int 2)))
15522    (set (match_operand:DI 1 "register_operand" "=S")
15523         (plus:DI (match_dup 3)
15524                  (const_int 2)))
15525    (use (reg:SI 19))]
15526   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15527   "movsw"
15528   [(set_attr "type" "str")
15529    (set_attr "memory" "both")
15530    (set_attr "mode" "HI")])
15531
15532 (define_insn "*strmovqi_1"
15533   [(set (mem:QI (match_operand:SI 2 "register_operand" "0"))
15534         (mem:QI (match_operand:SI 3 "register_operand" "1")))
15535    (set (match_operand:SI 0 "register_operand" "=D")
15536         (plus:SI (match_dup 2)
15537                  (const_int 1)))
15538    (set (match_operand:SI 1 "register_operand" "=S")
15539         (plus:SI (match_dup 3)
15540                  (const_int 1)))
15541    (use (reg:SI 19))]
15542   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15543   "movsb"
15544   [(set_attr "type" "str")
15545    (set_attr "memory" "both")
15546    (set_attr "mode" "QI")])
15547
15548 (define_insn "*strmovqi_rex_1"
15549   [(set (mem:QI (match_operand:DI 2 "register_operand" "0"))
15550         (mem:QI (match_operand:DI 3 "register_operand" "1")))
15551    (set (match_operand:DI 0 "register_operand" "=D")
15552         (plus:DI (match_dup 2)
15553                  (const_int 1)))
15554    (set (match_operand:DI 1 "register_operand" "=S")
15555         (plus:DI (match_dup 3)
15556                  (const_int 1)))
15557    (use (reg:SI 19))]
15558   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15559   "movsb"
15560   [(set_attr "type" "str")
15561    (set_attr "memory" "both")
15562    (set_attr "mode" "QI")])
15563
15564 (define_expand "rep_mov"
15565   [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
15566               (set (match_operand 0 "register_operand" "")
15567                    (match_operand 5 "" ""))
15568               (set (match_operand 2 "register_operand" "")
15569                    (match_operand 6 "" ""))
15570               (set (match_operand 1 "memory_operand" "")
15571                    (match_operand 3 "memory_operand" ""))
15572               (use (match_dup 4))
15573               (use (reg:SI 19))])]
15574   ""
15575   "")
15576
15577 (define_insn "*rep_movdi_rex64"
15578   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
15579    (set (match_operand:DI 0 "register_operand" "=D") 
15580         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
15581                             (const_int 3))
15582                  (match_operand:DI 3 "register_operand" "0")))
15583    (set (match_operand:DI 1 "register_operand" "=S") 
15584         (plus:DI (ashift:DI (match_dup 5) (const_int 3))
15585                  (match_operand:DI 4 "register_operand" "1")))
15586    (set (mem:BLK (match_dup 3))
15587         (mem:BLK (match_dup 4)))
15588    (use (match_dup 5))
15589    (use (reg:SI 19))]
15590   "TARGET_64BIT"
15591   "{rep\;movsq|rep movsq}"
15592   [(set_attr "type" "str")
15593    (set_attr "prefix_rep" "1")
15594    (set_attr "memory" "both")
15595    (set_attr "mode" "DI")])
15596
15597 (define_insn "*rep_movsi"
15598   [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
15599    (set (match_operand:SI 0 "register_operand" "=D") 
15600         (plus:SI (ashift:SI (match_operand:SI 5 "register_operand" "2")
15601                             (const_int 2))
15602                  (match_operand:SI 3 "register_operand" "0")))
15603    (set (match_operand:SI 1 "register_operand" "=S") 
15604         (plus:SI (ashift:SI (match_dup 5) (const_int 2))
15605                  (match_operand:SI 4 "register_operand" "1")))
15606    (set (mem:BLK (match_dup 3))
15607         (mem:BLK (match_dup 4)))
15608    (use (match_dup 5))
15609    (use (reg:SI 19))]
15610   "!TARGET_64BIT"
15611   "{rep\;movsl|rep movsd}"
15612   [(set_attr "type" "str")
15613    (set_attr "prefix_rep" "1")
15614    (set_attr "memory" "both")
15615    (set_attr "mode" "SI")])
15616
15617 (define_insn "*rep_movsi_rex64"
15618   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
15619    (set (match_operand:DI 0 "register_operand" "=D") 
15620         (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
15621                             (const_int 2))
15622                  (match_operand:DI 3 "register_operand" "0")))
15623    (set (match_operand:DI 1 "register_operand" "=S") 
15624         (plus:DI (ashift:DI (match_dup 5) (const_int 2))
15625                  (match_operand:DI 4 "register_operand" "1")))
15626    (set (mem:BLK (match_dup 3))
15627         (mem:BLK (match_dup 4)))
15628    (use (match_dup 5))
15629    (use (reg:SI 19))]
15630   "TARGET_64BIT"
15631   "{rep\;movsl|rep movsd}"
15632   [(set_attr "type" "str")
15633    (set_attr "prefix_rep" "1")
15634    (set_attr "memory" "both")
15635    (set_attr "mode" "SI")])
15636
15637 (define_insn "*rep_movqi"
15638   [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
15639    (set (match_operand:SI 0 "register_operand" "=D") 
15640         (plus:SI (match_operand:SI 3 "register_operand" "0")
15641                  (match_operand:SI 5 "register_operand" "2")))
15642    (set (match_operand:SI 1 "register_operand" "=S") 
15643         (plus:SI (match_operand:SI 4 "register_operand" "1") (match_dup 5)))
15644    (set (mem:BLK (match_dup 3))
15645         (mem:BLK (match_dup 4)))
15646    (use (match_dup 5))
15647    (use (reg:SI 19))]
15648   "!TARGET_64BIT"
15649   "{rep\;movsb|rep movsb}"
15650   [(set_attr "type" "str")
15651    (set_attr "prefix_rep" "1")
15652    (set_attr "memory" "both")
15653    (set_attr "mode" "SI")])
15654
15655 (define_insn "*rep_movqi_rex64"
15656   [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
15657    (set (match_operand:DI 0 "register_operand" "=D") 
15658         (plus:DI (match_operand:DI 3 "register_operand" "0")
15659                  (match_operand:DI 5 "register_operand" "2")))
15660    (set (match_operand:DI 1 "register_operand" "=S") 
15661         (plus:DI (match_operand:DI 4 "register_operand" "1") (match_dup 5)))
15662    (set (mem:BLK (match_dup 3))
15663         (mem:BLK (match_dup 4)))
15664    (use (match_dup 5))
15665    (use (reg:SI 19))]
15666   "TARGET_64BIT"
15667   "{rep\;movsb|rep movsb}"
15668   [(set_attr "type" "str")
15669    (set_attr "prefix_rep" "1")
15670    (set_attr "memory" "both")
15671    (set_attr "mode" "SI")])
15672
15673 (define_expand "clrstrsi"
15674    [(use (match_operand:BLK 0 "memory_operand" ""))
15675     (use (match_operand:SI 1 "nonmemory_operand" ""))
15676     (use (match_operand 2 "const_int_operand" ""))]
15677   ""
15678 {
15679  if (ix86_expand_clrstr (operands[0], operands[1], operands[2]))
15680    DONE;
15681  else
15682    FAIL;
15683 })
15684
15685 (define_expand "clrstrdi"
15686    [(use (match_operand:BLK 0 "memory_operand" ""))
15687     (use (match_operand:DI 1 "nonmemory_operand" ""))
15688     (use (match_operand 2 "const_int_operand" ""))]
15689   "TARGET_64BIT"
15690 {
15691  if (ix86_expand_clrstr (operands[0], operands[1], operands[2]))
15692    DONE;
15693  else
15694    FAIL;
15695 })
15696
15697 ;; Most CPUs don't like single string operations
15698 ;; Handle this case here to simplify previous expander.
15699
15700 (define_expand "strset"
15701   [(set (match_operand 1 "memory_operand" "")
15702         (match_operand 2 "register_operand" ""))
15703    (parallel [(set (match_operand 0 "register_operand" "")
15704                    (match_dup 3))
15705               (clobber (reg:CC 17))])]
15706   ""
15707 {
15708   if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
15709     operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
15710
15711   /* If .md ever supports :P for Pmode, this can be directly
15712      in the pattern above.  */
15713   operands[3] = gen_rtx_PLUS (Pmode, operands[0],
15714                               GEN_INT (GET_MODE_SIZE (GET_MODE
15715                                                       (operands[2]))));
15716   if (TARGET_SINGLE_STRINGOP || optimize_size)
15717     {
15718       emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
15719                                       operands[3]));
15720       DONE;
15721     }
15722 })
15723
15724 (define_expand "strset_singleop"
15725   [(parallel [(set (match_operand 1 "memory_operand" "")
15726                    (match_operand 2 "register_operand" ""))
15727               (set (match_operand 0 "register_operand" "")
15728                    (match_operand 3 "" ""))
15729               (use (reg:SI 19))])]
15730   "TARGET_SINGLE_STRINGOP || optimize_size"
15731   "")
15732
15733 (define_insn "*strsetdi_rex_1"
15734   [(set (mem:SI (match_operand:DI 1 "register_operand" "0"))
15735         (match_operand:SI 2 "register_operand" "a"))
15736    (set (match_operand:DI 0 "register_operand" "=D")
15737         (plus:DI (match_dup 1)
15738                  (const_int 8)))
15739    (use (reg:SI 19))]
15740   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15741   "stosq"
15742   [(set_attr "type" "str")
15743    (set_attr "memory" "store")
15744    (set_attr "mode" "DI")])
15745
15746 (define_insn "*strsetsi_1"
15747   [(set (mem:SI (match_operand:SI 1 "register_operand" "0"))
15748         (match_operand:SI 2 "register_operand" "a"))
15749    (set (match_operand:SI 0 "register_operand" "=D")
15750         (plus:SI (match_dup 1)
15751                  (const_int 4)))
15752    (use (reg:SI 19))]
15753   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15754   "{stosl|stosd}"
15755   [(set_attr "type" "str")
15756    (set_attr "memory" "store")
15757    (set_attr "mode" "SI")])
15758
15759 (define_insn "*strsetsi_rex_1"
15760   [(set (mem:SI (match_operand:DI 1 "register_operand" "0"))
15761         (match_operand:SI 2 "register_operand" "a"))
15762    (set (match_operand:DI 0 "register_operand" "=D")
15763         (plus:DI (match_dup 1)
15764                  (const_int 4)))
15765    (use (reg:SI 19))]
15766   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15767   "{stosl|stosd}"
15768   [(set_attr "type" "str")
15769    (set_attr "memory" "store")
15770    (set_attr "mode" "SI")])
15771
15772 (define_insn "*strsethi_1"
15773   [(set (mem:HI (match_operand:SI 1 "register_operand" "0"))
15774         (match_operand:HI 2 "register_operand" "a"))
15775    (set (match_operand:SI 0 "register_operand" "=D")
15776         (plus:SI (match_dup 1)
15777                  (const_int 2)))
15778    (use (reg:SI 19))]
15779   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15780   "stosw"
15781   [(set_attr "type" "str")
15782    (set_attr "memory" "store")
15783    (set_attr "mode" "HI")])
15784
15785 (define_insn "*strsethi_rex_1"
15786   [(set (mem:HI (match_operand:DI 1 "register_operand" "0"))
15787         (match_operand:HI 2 "register_operand" "a"))
15788    (set (match_operand:DI 0 "register_operand" "=D")
15789         (plus:DI (match_dup 1)
15790                  (const_int 2)))
15791    (use (reg:SI 19))]
15792   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15793   "stosw"
15794   [(set_attr "type" "str")
15795    (set_attr "memory" "store")
15796    (set_attr "mode" "HI")])
15797
15798 (define_insn "*strsetqi_1"
15799   [(set (mem:QI (match_operand:SI 1 "register_operand" "0"))
15800         (match_operand:QI 2 "register_operand" "a"))
15801    (set (match_operand:SI 0 "register_operand" "=D")
15802         (plus:SI (match_dup 1)
15803                  (const_int 1)))
15804    (use (reg:SI 19))]
15805   "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15806   "stosb"
15807   [(set_attr "type" "str")
15808    (set_attr "memory" "store")
15809    (set_attr "mode" "QI")])
15810
15811 (define_insn "*strsetqi_rex_1"
15812   [(set (mem:QI (match_operand:DI 1 "register_operand" "0"))
15813         (match_operand:QI 2 "register_operand" "a"))
15814    (set (match_operand:DI 0 "register_operand" "=D")
15815         (plus:DI (match_dup 1)
15816                  (const_int 1)))
15817    (use (reg:SI 19))]
15818   "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
15819   "stosb"
15820   [(set_attr "type" "str")
15821    (set_attr "memory" "store")
15822    (set_attr "mode" "QI")])
15823
15824 (define_expand "rep_stos"
15825   [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
15826               (set (match_operand 0 "register_operand" "")
15827                    (match_operand 4 "" ""))
15828               (set (match_operand 2 "memory_operand" "") (const_int 0))
15829               (use (match_operand 3 "register_operand" ""))
15830               (use (match_dup 1))
15831               (use (reg:SI 19))])]
15832   ""
15833   "")
15834
15835 (define_insn "*rep_stosdi_rex64"
15836   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
15837    (set (match_operand:DI 0 "register_operand" "=D") 
15838         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
15839                             (const_int 3))
15840                  (match_operand:DI 3 "register_operand" "0")))
15841    (set (mem:BLK (match_dup 3))
15842         (const_int 0))
15843    (use (match_operand:DI 2 "register_operand" "a"))
15844    (use (match_dup 4))
15845    (use (reg:SI 19))]
15846   "TARGET_64BIT"
15847   "{rep\;stosq|rep stosq}"
15848   [(set_attr "type" "str")
15849    (set_attr "prefix_rep" "1")
15850    (set_attr "memory" "store")
15851    (set_attr "mode" "DI")])
15852
15853 (define_insn "*rep_stossi"
15854   [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
15855    (set (match_operand:SI 0 "register_operand" "=D") 
15856         (plus:SI (ashift:SI (match_operand:SI 4 "register_operand" "1")
15857                             (const_int 2))
15858                  (match_operand:SI 3 "register_operand" "0")))
15859    (set (mem:BLK (match_dup 3))
15860         (const_int 0))
15861    (use (match_operand:SI 2 "register_operand" "a"))
15862    (use (match_dup 4))
15863    (use (reg:SI 19))]
15864   "!TARGET_64BIT"
15865   "{rep\;stosl|rep stosd}"
15866   [(set_attr "type" "str")
15867    (set_attr "prefix_rep" "1")
15868    (set_attr "memory" "store")
15869    (set_attr "mode" "SI")])
15870
15871 (define_insn "*rep_stossi_rex64"
15872   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
15873    (set (match_operand:DI 0 "register_operand" "=D") 
15874         (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
15875                             (const_int 2))
15876                  (match_operand:DI 3 "register_operand" "0")))
15877    (set (mem:BLK (match_dup 3))
15878         (const_int 0))
15879    (use (match_operand:SI 2 "register_operand" "a"))
15880    (use (match_dup 4))
15881    (use (reg:SI 19))]
15882   "TARGET_64BIT"
15883   "{rep\;stosl|rep stosd}"
15884   [(set_attr "type" "str")
15885    (set_attr "prefix_rep" "1")
15886    (set_attr "memory" "store")
15887    (set_attr "mode" "SI")])
15888
15889 (define_insn "*rep_stosqi"
15890   [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
15891    (set (match_operand:SI 0 "register_operand" "=D") 
15892         (plus:SI (match_operand:SI 3 "register_operand" "0")
15893                  (match_operand:SI 4 "register_operand" "1")))
15894    (set (mem:BLK (match_dup 3))
15895         (const_int 0))
15896    (use (match_operand:QI 2 "register_operand" "a"))
15897    (use (match_dup 4))
15898    (use (reg:SI 19))]
15899   "!TARGET_64BIT"
15900   "{rep\;stosb|rep stosb}"
15901   [(set_attr "type" "str")
15902    (set_attr "prefix_rep" "1")
15903    (set_attr "memory" "store")
15904    (set_attr "mode" "QI")])
15905
15906 (define_insn "*rep_stosqi_rex64"
15907   [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
15908    (set (match_operand:DI 0 "register_operand" "=D") 
15909         (plus:DI (match_operand:DI 3 "register_operand" "0")
15910                  (match_operand:DI 4 "register_operand" "1")))
15911    (set (mem:BLK (match_dup 3))
15912         (const_int 0))
15913    (use (match_operand:QI 2 "register_operand" "a"))
15914    (use (match_dup 4))
15915    (use (reg:SI 19))]
15916   "TARGET_64BIT"
15917   "{rep\;stosb|rep stosb}"
15918   [(set_attr "type" "str")
15919    (set_attr "prefix_rep" "1")
15920    (set_attr "memory" "store")
15921    (set_attr "mode" "QI")])
15922
15923 (define_expand "cmpstrsi"
15924   [(set (match_operand:SI 0 "register_operand" "")
15925         (compare:SI (match_operand:BLK 1 "general_operand" "")
15926                     (match_operand:BLK 2 "general_operand" "")))
15927    (use (match_operand 3 "general_operand" ""))
15928    (use (match_operand 4 "immediate_operand" ""))]
15929   "! optimize_size || TARGET_INLINE_ALL_STRINGOPS"
15930 {
15931   rtx addr1, addr2, out, outlow, count, countreg, align;
15932
15933   /* Can't use this if the user has appropriated esi or edi.  */
15934   if (global_regs[4] || global_regs[5])
15935     FAIL;
15936
15937   out = operands[0];
15938   if (GET_CODE (out) != REG)
15939     out = gen_reg_rtx (SImode);
15940
15941   addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
15942   addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
15943   if (addr1 != XEXP (operands[1], 0))
15944     operands[1] = replace_equiv_address_nv (operands[1], addr1);
15945   if (addr2 != XEXP (operands[2], 0))
15946     operands[2] = replace_equiv_address_nv (operands[2], addr2);
15947
15948   count = operands[3];
15949   countreg = ix86_zero_extend_to_Pmode (count);
15950
15951   /* %%% Iff we are testing strict equality, we can use known alignment
15952      to good advantage.  This may be possible with combine, particularly
15953      once cc0 is dead.  */
15954   align = operands[4];
15955
15956   emit_insn (gen_cld ());
15957   if (GET_CODE (count) == CONST_INT)
15958     {
15959       if (INTVAL (count) == 0)
15960         {
15961           emit_move_insn (operands[0], const0_rtx);
15962           DONE;
15963         }
15964       emit_insn (gen_cmpstrqi_nz_1 (addr1, addr2, countreg, align,
15965                                     operands[1], operands[2]));
15966     }
15967   else
15968     {
15969       if (TARGET_64BIT)
15970         emit_insn (gen_cmpdi_1_rex64 (countreg, countreg));
15971       else
15972         emit_insn (gen_cmpsi_1 (countreg, countreg));
15973       emit_insn (gen_cmpstrqi_1 (addr1, addr2, countreg, align,
15974                                  operands[1], operands[2]));
15975     }
15976
15977   outlow = gen_lowpart (QImode, out);
15978   emit_insn (gen_cmpintqi (outlow));
15979   emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
15980
15981   if (operands[0] != out)
15982     emit_move_insn (operands[0], out);
15983
15984   DONE;
15985 })
15986
15987 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
15988
15989 (define_expand "cmpintqi"
15990   [(set (match_dup 1)
15991         (gtu:QI (reg:CC 17) (const_int 0)))
15992    (set (match_dup 2)
15993         (ltu:QI (reg:CC 17) (const_int 0)))
15994    (parallel [(set (match_operand:QI 0 "register_operand" "")
15995                    (minus:QI (match_dup 1)
15996                              (match_dup 2)))
15997               (clobber (reg:CC 17))])]
15998   ""
15999   "operands[1] = gen_reg_rtx (QImode);
16000    operands[2] = gen_reg_rtx (QImode);")
16001
16002 ;; memcmp recognizers.  The `cmpsb' opcode does nothing if the count is
16003 ;; zero.  Emit extra code to make sure that a zero-length compare is EQ.
16004
16005 (define_expand "cmpstrqi_nz_1"
16006   [(parallel [(set (reg:CC 17)
16007                    (compare:CC (match_operand 4 "memory_operand" "")
16008                                (match_operand 5 "memory_operand" "")))
16009               (use (match_operand 2 "register_operand" ""))
16010               (use (match_operand:SI 3 "immediate_operand" ""))
16011               (use (reg:SI 19))
16012               (clobber (match_operand 0 "register_operand" ""))
16013               (clobber (match_operand 1 "register_operand" ""))
16014               (clobber (match_dup 2))])]
16015   ""
16016   "")
16017
16018 (define_insn "*cmpstrqi_nz_1"
16019   [(set (reg:CC 17)
16020         (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
16021                     (mem:BLK (match_operand:SI 5 "register_operand" "1"))))
16022    (use (match_operand:SI 6 "register_operand" "2"))
16023    (use (match_operand:SI 3 "immediate_operand" "i"))
16024    (use (reg:SI 19))
16025    (clobber (match_operand:SI 0 "register_operand" "=S"))
16026    (clobber (match_operand:SI 1 "register_operand" "=D"))
16027    (clobber (match_operand:SI 2 "register_operand" "=c"))]
16028   "!TARGET_64BIT"
16029   "repz{\;| }cmpsb"
16030   [(set_attr "type" "str")
16031    (set_attr "mode" "QI")
16032    (set_attr "prefix_rep" "1")])
16033
16034 (define_insn "*cmpstrqi_nz_rex_1"
16035   [(set (reg:CC 17)
16036         (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
16037                     (mem:BLK (match_operand:DI 5 "register_operand" "1"))))
16038    (use (match_operand:DI 6 "register_operand" "2"))
16039    (use (match_operand:SI 3 "immediate_operand" "i"))
16040    (use (reg:SI 19))
16041    (clobber (match_operand:DI 0 "register_operand" "=S"))
16042    (clobber (match_operand:DI 1 "register_operand" "=D"))
16043    (clobber (match_operand:DI 2 "register_operand" "=c"))]
16044   "TARGET_64BIT"
16045   "repz{\;| }cmpsb"
16046   [(set_attr "type" "str")
16047    (set_attr "mode" "QI")
16048    (set_attr "prefix_rep" "1")])
16049
16050 ;; The same, but the count is not known to not be zero.
16051
16052 (define_expand "cmpstrqi_1"
16053   [(parallel [(set (reg:CC 17)
16054                 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
16055                                      (const_int 0))
16056                   (compare:CC (match_operand 4 "memory_operand" "")
16057                               (match_operand 5 "memory_operand" ""))
16058                   (const_int 0)))
16059               (use (match_operand:SI 3 "immediate_operand" ""))
16060               (use (reg:CC 17))
16061               (use (reg:SI 19))
16062               (clobber (match_operand 0 "register_operand" ""))
16063               (clobber (match_operand 1 "register_operand" ""))
16064               (clobber (match_dup 2))])]
16065   ""
16066   "")
16067
16068 (define_insn "*cmpstrqi_1"
16069   [(set (reg:CC 17)
16070         (if_then_else:CC (ne (match_operand:SI 6 "register_operand" "2")
16071                              (const_int 0))
16072           (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
16073                       (mem:BLK (match_operand:SI 5 "register_operand" "1")))
16074           (const_int 0)))
16075    (use (match_operand:SI 3 "immediate_operand" "i"))
16076    (use (reg:CC 17))
16077    (use (reg:SI 19))
16078    (clobber (match_operand:SI 0 "register_operand" "=S"))
16079    (clobber (match_operand:SI 1 "register_operand" "=D"))
16080    (clobber (match_operand:SI 2 "register_operand" "=c"))]
16081   "!TARGET_64BIT"
16082   "repz{\;| }cmpsb"
16083   [(set_attr "type" "str")
16084    (set_attr "mode" "QI")
16085    (set_attr "prefix_rep" "1")])
16086
16087 (define_insn "*cmpstrqi_rex_1"
16088   [(set (reg:CC 17)
16089         (if_then_else:CC (ne (match_operand:DI 6 "register_operand" "2")
16090                              (const_int 0))
16091           (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
16092                       (mem:BLK (match_operand:DI 5 "register_operand" "1")))
16093           (const_int 0)))
16094    (use (match_operand:SI 3 "immediate_operand" "i"))
16095    (use (reg:CC 17))
16096    (use (reg:SI 19))
16097    (clobber (match_operand:DI 0 "register_operand" "=S"))
16098    (clobber (match_operand:DI 1 "register_operand" "=D"))
16099    (clobber (match_operand:DI 2 "register_operand" "=c"))]
16100   "TARGET_64BIT"
16101   "repz{\;| }cmpsb"
16102   [(set_attr "type" "str")
16103    (set_attr "mode" "QI")
16104    (set_attr "prefix_rep" "1")])
16105
16106 (define_expand "strlensi"
16107   [(set (match_operand:SI 0 "register_operand" "")
16108         (unspec:SI [(match_operand:BLK 1 "general_operand" "")
16109                     (match_operand:QI 2 "immediate_operand" "")
16110                     (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
16111   ""
16112 {
16113  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
16114    DONE;
16115  else
16116    FAIL;
16117 })
16118
16119 (define_expand "strlendi"
16120   [(set (match_operand:DI 0 "register_operand" "")
16121         (unspec:DI [(match_operand:BLK 1 "general_operand" "")
16122                     (match_operand:QI 2 "immediate_operand" "")
16123                     (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
16124   ""
16125 {
16126  if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
16127    DONE;
16128  else
16129    FAIL;
16130 })
16131
16132 (define_expand "strlenqi_1"
16133   [(parallel [(set (match_operand 0 "register_operand" "") (match_operand 2 "" ""))
16134               (use (reg:SI 19))
16135               (clobber (match_operand 1 "register_operand" ""))
16136               (clobber (reg:CC 17))])]
16137   ""
16138   "")
16139
16140 (define_insn "*strlenqi_1"
16141   [(set (match_operand:SI 0 "register_operand" "=&c")
16142         (unspec:SI [(mem:BLK (match_operand:SI 5 "register_operand" "1"))
16143                     (match_operand:QI 2 "register_operand" "a")
16144                     (match_operand:SI 3 "immediate_operand" "i")
16145                     (match_operand:SI 4 "register_operand" "0")] UNSPEC_SCAS))
16146    (use (reg:SI 19))
16147    (clobber (match_operand:SI 1 "register_operand" "=D"))
16148    (clobber (reg:CC 17))]
16149   "!TARGET_64BIT"
16150   "repnz{\;| }scasb"
16151   [(set_attr "type" "str")
16152    (set_attr "mode" "QI")
16153    (set_attr "prefix_rep" "1")])
16154
16155 (define_insn "*strlenqi_rex_1"
16156   [(set (match_operand:DI 0 "register_operand" "=&c")
16157         (unspec:DI [(mem:BLK (match_operand:DI 5 "register_operand" "1"))
16158                     (match_operand:QI 2 "register_operand" "a")
16159                     (match_operand:DI 3 "immediate_operand" "i")
16160                     (match_operand:DI 4 "register_operand" "0")] UNSPEC_SCAS))
16161    (use (reg:SI 19))
16162    (clobber (match_operand:DI 1 "register_operand" "=D"))
16163    (clobber (reg:CC 17))]
16164   "TARGET_64BIT"
16165   "repnz{\;| }scasb"
16166   [(set_attr "type" "str")
16167    (set_attr "mode" "QI")
16168    (set_attr "prefix_rep" "1")])
16169
16170 ;; Peephole optimizations to clean up after cmpstr*.  This should be
16171 ;; handled in combine, but it is not currently up to the task.
16172 ;; When used for their truth value, the cmpstr* expanders generate
16173 ;; code like this:
16174 ;;
16175 ;;   repz cmpsb
16176 ;;   seta       %al
16177 ;;   setb       %dl
16178 ;;   cmpb       %al, %dl
16179 ;;   jcc        label
16180 ;;
16181 ;; The intermediate three instructions are unnecessary.
16182
16183 ;; This one handles cmpstr*_nz_1...
16184 (define_peephole2
16185   [(parallel[
16186      (set (reg:CC 17)
16187           (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
16188                       (mem:BLK (match_operand 5 "register_operand" ""))))
16189      (use (match_operand 6 "register_operand" ""))
16190      (use (match_operand:SI 3 "immediate_operand" ""))
16191      (use (reg:SI 19))
16192      (clobber (match_operand 0 "register_operand" ""))
16193      (clobber (match_operand 1 "register_operand" ""))
16194      (clobber (match_operand 2 "register_operand" ""))])
16195    (set (match_operand:QI 7 "register_operand" "")
16196         (gtu:QI (reg:CC 17) (const_int 0)))
16197    (set (match_operand:QI 8 "register_operand" "")
16198         (ltu:QI (reg:CC 17) (const_int 0)))
16199    (set (reg 17)
16200         (compare (match_dup 7) (match_dup 8)))
16201   ]
16202   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
16203   [(parallel[
16204      (set (reg:CC 17)
16205           (compare:CC (mem:BLK (match_dup 4))
16206                       (mem:BLK (match_dup 5))))
16207      (use (match_dup 6))
16208      (use (match_dup 3))
16209      (use (reg:SI 19))
16210      (clobber (match_dup 0))
16211      (clobber (match_dup 1))
16212      (clobber (match_dup 2))])]
16213   "")
16214
16215 ;; ...and this one handles cmpstr*_1.
16216 (define_peephole2
16217   [(parallel[
16218      (set (reg:CC 17)
16219           (if_then_else:CC (ne (match_operand 6 "register_operand" "")
16220                                (const_int 0))
16221             (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
16222                         (mem:BLK (match_operand 5 "register_operand" "")))
16223             (const_int 0)))
16224      (use (match_operand:SI 3 "immediate_operand" ""))
16225      (use (reg:CC 17))
16226      (use (reg:SI 19))
16227      (clobber (match_operand 0 "register_operand" ""))
16228      (clobber (match_operand 1 "register_operand" ""))
16229      (clobber (match_operand 2 "register_operand" ""))])
16230    (set (match_operand:QI 7 "register_operand" "")
16231         (gtu:QI (reg:CC 17) (const_int 0)))
16232    (set (match_operand:QI 8 "register_operand" "")
16233         (ltu:QI (reg:CC 17) (const_int 0)))
16234    (set (reg 17)
16235         (compare (match_dup 7) (match_dup 8)))
16236   ]
16237   "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
16238   [(parallel[
16239      (set (reg:CC 17)
16240           (if_then_else:CC (ne (match_dup 6)
16241                                (const_int 0))
16242             (compare:CC (mem:BLK (match_dup 4))
16243                         (mem:BLK (match_dup 5)))
16244             (const_int 0)))
16245      (use (match_dup 3))
16246      (use (reg:CC 17))
16247      (use (reg:SI 19))
16248      (clobber (match_dup 0))
16249      (clobber (match_dup 1))
16250      (clobber (match_dup 2))])]
16251   "")
16252
16253
16254 \f
16255 ;; Conditional move instructions.
16256
16257 (define_expand "movdicc"
16258   [(set (match_operand:DI 0 "register_operand" "")
16259         (if_then_else:DI (match_operand 1 "comparison_operator" "")
16260                          (match_operand:DI 2 "general_operand" "")
16261                          (match_operand:DI 3 "general_operand" "")))]
16262   "TARGET_64BIT"
16263   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
16264
16265 (define_insn "x86_movdicc_0_m1_rex64"
16266   [(set (match_operand:DI 0 "register_operand" "=r")
16267         (if_then_else:DI (match_operand 1 "ix86_carry_flag_operator" "")
16268           (const_int -1)
16269           (const_int 0)))
16270    (clobber (reg:CC 17))]
16271   "TARGET_64BIT"
16272   "sbb{q}\t%0, %0"
16273   ; Since we don't have the proper number of operands for an alu insn,
16274   ; fill in all the blanks.
16275   [(set_attr "type" "alu")
16276    (set_attr "pent_pair" "pu")
16277    (set_attr "memory" "none")
16278    (set_attr "imm_disp" "false")
16279    (set_attr "mode" "DI")
16280    (set_attr "length_immediate" "0")])
16281
16282 (define_insn "movdicc_c_rex64"
16283   [(set (match_operand:DI 0 "register_operand" "=r,r")
16284         (if_then_else:DI (match_operator 1 "ix86_comparison_operator" 
16285                                 [(reg 17) (const_int 0)])
16286                       (match_operand:DI 2 "nonimmediate_operand" "rm,0")
16287                       (match_operand:DI 3 "nonimmediate_operand" "0,rm")))]
16288   "TARGET_64BIT && TARGET_CMOVE
16289    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
16290   "@
16291    cmov%O2%C1\t{%2, %0|%0, %2}
16292    cmov%O2%c1\t{%3, %0|%0, %3}"
16293   [(set_attr "type" "icmov")
16294    (set_attr "mode" "DI")])
16295
16296 (define_expand "movsicc"
16297   [(set (match_operand:SI 0 "register_operand" "")
16298         (if_then_else:SI (match_operand 1 "comparison_operator" "")
16299                          (match_operand:SI 2 "general_operand" "")
16300                          (match_operand:SI 3 "general_operand" "")))]
16301   ""
16302   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
16303
16304 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
16305 ;; the register first winds up with `sbbl $0,reg', which is also weird.
16306 ;; So just document what we're doing explicitly.
16307
16308 (define_insn "x86_movsicc_0_m1"
16309   [(set (match_operand:SI 0 "register_operand" "=r")
16310         (if_then_else:SI (match_operand 1 "ix86_carry_flag_operator" "")
16311           (const_int -1)
16312           (const_int 0)))
16313    (clobber (reg:CC 17))]
16314   ""
16315   "sbb{l}\t%0, %0"
16316   ; Since we don't have the proper number of operands for an alu insn,
16317   ; fill in all the blanks.
16318   [(set_attr "type" "alu")
16319    (set_attr "pent_pair" "pu")
16320    (set_attr "memory" "none")
16321    (set_attr "imm_disp" "false")
16322    (set_attr "mode" "SI")
16323    (set_attr "length_immediate" "0")])
16324
16325 (define_insn "*movsicc_noc"
16326   [(set (match_operand:SI 0 "register_operand" "=r,r")
16327         (if_then_else:SI (match_operator 1 "ix86_comparison_operator" 
16328                                 [(reg 17) (const_int 0)])
16329                       (match_operand:SI 2 "nonimmediate_operand" "rm,0")
16330                       (match_operand:SI 3 "nonimmediate_operand" "0,rm")))]
16331   "TARGET_CMOVE
16332    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
16333   "@
16334    cmov%O2%C1\t{%2, %0|%0, %2}
16335    cmov%O2%c1\t{%3, %0|%0, %3}"
16336   [(set_attr "type" "icmov")
16337    (set_attr "mode" "SI")])
16338
16339 (define_expand "movhicc"
16340   [(set (match_operand:HI 0 "register_operand" "")
16341         (if_then_else:HI (match_operand 1 "comparison_operator" "")
16342                          (match_operand:HI 2 "general_operand" "")
16343                          (match_operand:HI 3 "general_operand" "")))]
16344   "TARGET_HIMODE_MATH"
16345   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
16346
16347 (define_insn "*movhicc_noc"
16348   [(set (match_operand:HI 0 "register_operand" "=r,r")
16349         (if_then_else:HI (match_operator 1 "ix86_comparison_operator" 
16350                                 [(reg 17) (const_int 0)])
16351                       (match_operand:HI 2 "nonimmediate_operand" "rm,0")
16352                       (match_operand:HI 3 "nonimmediate_operand" "0,rm")))]
16353   "TARGET_CMOVE
16354    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
16355   "@
16356    cmov%O2%C1\t{%2, %0|%0, %2}
16357    cmov%O2%c1\t{%3, %0|%0, %3}"
16358   [(set_attr "type" "icmov")
16359    (set_attr "mode" "HI")])
16360
16361 (define_expand "movqicc"
16362   [(set (match_operand:QI 0 "register_operand" "")
16363         (if_then_else:QI (match_operand 1 "comparison_operator" "")
16364                          (match_operand:QI 2 "general_operand" "")
16365                          (match_operand:QI 3 "general_operand" "")))]
16366   "TARGET_QIMODE_MATH"
16367   "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
16368
16369 (define_insn_and_split "*movqicc_noc"
16370   [(set (match_operand:QI 0 "register_operand" "=r,r")
16371         (if_then_else:QI (match_operator 1 "ix86_comparison_operator" 
16372                                 [(match_operand 4 "flags_reg_operand" "") (const_int 0)])
16373                       (match_operand:QI 2 "register_operand" "r,0")
16374                       (match_operand:QI 3 "register_operand" "0,r")))]
16375   "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
16376   "#"
16377   "&& reload_completed"
16378   [(set (match_dup 0)
16379         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
16380                       (match_dup 2)
16381                       (match_dup 3)))]
16382   "operands[0] = gen_lowpart (SImode, operands[0]);
16383    operands[2] = gen_lowpart (SImode, operands[2]);
16384    operands[3] = gen_lowpart (SImode, operands[3]);"
16385   [(set_attr "type" "icmov")
16386    (set_attr "mode" "SI")])
16387
16388 (define_expand "movsfcc"
16389   [(set (match_operand:SF 0 "register_operand" "")
16390         (if_then_else:SF (match_operand 1 "comparison_operator" "")
16391                          (match_operand:SF 2 "register_operand" "")
16392                          (match_operand:SF 3 "register_operand" "")))]
16393   "TARGET_CMOVE"
16394   "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
16395
16396 (define_insn "*movsfcc_1"
16397   [(set (match_operand:SF 0 "register_operand" "=f#r,f#r,r#f,r#f")
16398         (if_then_else:SF (match_operator 1 "fcmov_comparison_operator" 
16399                                 [(reg 17) (const_int 0)])
16400                       (match_operand:SF 2 "nonimmediate_operand" "f#r,0,rm#f,0")
16401                       (match_operand:SF 3 "nonimmediate_operand" "0,f#r,0,rm#f")))]
16402   "TARGET_CMOVE
16403    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
16404   "@
16405    fcmov%F1\t{%2, %0|%0, %2}
16406    fcmov%f1\t{%3, %0|%0, %3}
16407    cmov%O2%C1\t{%2, %0|%0, %2}
16408    cmov%O2%c1\t{%3, %0|%0, %3}"
16409   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
16410    (set_attr "mode" "SF,SF,SI,SI")])
16411
16412 (define_expand "movdfcc"
16413   [(set (match_operand:DF 0 "register_operand" "")
16414         (if_then_else:DF (match_operand 1 "comparison_operator" "")
16415                          (match_operand:DF 2 "register_operand" "")
16416                          (match_operand:DF 3 "register_operand" "")))]
16417   "TARGET_CMOVE"
16418   "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
16419
16420 (define_insn "*movdfcc_1"
16421   [(set (match_operand:DF 0 "register_operand" "=f#r,f#r,&r#f,&r#f")
16422         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator" 
16423                                 [(reg 17) (const_int 0)])
16424                       (match_operand:DF 2 "nonimmediate_operand" "f#r,0,rm#f,0")
16425                       (match_operand:DF 3 "nonimmediate_operand" "0,f#r,0,rm#f")))]
16426   "!TARGET_64BIT && TARGET_CMOVE
16427    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
16428   "@
16429    fcmov%F1\t{%2, %0|%0, %2}
16430    fcmov%f1\t{%3, %0|%0, %3}
16431    #
16432    #"
16433   [(set_attr "type" "fcmov,fcmov,multi,multi")
16434    (set_attr "mode" "DF")])
16435
16436 (define_insn "*movdfcc_1_rex64"
16437   [(set (match_operand:DF 0 "register_operand" "=f#r,f#r,r#f,r#f")
16438         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator" 
16439                                 [(reg 17) (const_int 0)])
16440                       (match_operand:DF 2 "nonimmediate_operand" "f#r,0#r,rm#f,0#f")
16441                       (match_operand:DF 3 "nonimmediate_operand" "0#r,f#r,0#f,rm#f")))]
16442   "TARGET_64BIT && TARGET_CMOVE
16443    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
16444   "@
16445    fcmov%F1\t{%2, %0|%0, %2}
16446    fcmov%f1\t{%3, %0|%0, %3}
16447    cmov%O2%C1\t{%2, %0|%0, %2}
16448    cmov%O2%c1\t{%3, %0|%0, %3}"
16449   [(set_attr "type" "fcmov,fcmov,icmov,icmov")
16450    (set_attr "mode" "DF")])
16451
16452 (define_split
16453   [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand" "")
16454         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator" 
16455                                 [(match_operand 4 "flags_reg_operand" "") (const_int 0)])
16456                       (match_operand:DF 2 "nonimmediate_operand" "")
16457                       (match_operand:DF 3 "nonimmediate_operand" "")))]
16458   "!TARGET_64BIT && reload_completed"
16459   [(set (match_dup 2)
16460         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
16461                       (match_dup 5)
16462                       (match_dup 7)))
16463    (set (match_dup 3)
16464         (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
16465                       (match_dup 6)
16466                       (match_dup 8)))]
16467   "split_di (operands+2, 1, operands+5, operands+6);
16468    split_di (operands+3, 1, operands+7, operands+8);
16469    split_di (operands, 1, operands+2, operands+3);")
16470
16471 (define_expand "movxfcc"
16472   [(set (match_operand:XF 0 "register_operand" "")
16473         (if_then_else:XF (match_operand 1 "comparison_operator" "")
16474                          (match_operand:XF 2 "register_operand" "")
16475                          (match_operand:XF 3 "register_operand" "")))]
16476   "TARGET_CMOVE"
16477   "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
16478
16479 (define_insn "*movxfcc_1"
16480   [(set (match_operand:XF 0 "register_operand" "=f,f")
16481         (if_then_else:XF (match_operator 1 "fcmov_comparison_operator" 
16482                                 [(reg 17) (const_int 0)])
16483                       (match_operand:XF 2 "register_operand" "f,0")
16484                       (match_operand:XF 3 "register_operand" "0,f")))]
16485   "TARGET_CMOVE"
16486   "@
16487    fcmov%F1\t{%2, %0|%0, %2}
16488    fcmov%f1\t{%3, %0|%0, %3}"
16489   [(set_attr "type" "fcmov")
16490    (set_attr "mode" "XF")])
16491
16492 (define_expand "minsf3"
16493   [(parallel [
16494      (set (match_operand:SF 0 "register_operand" "")
16495           (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "")
16496                                (match_operand:SF 2 "nonimmediate_operand" ""))
16497                            (match_dup 1)
16498                            (match_dup 2)))
16499      (clobber (reg:CC 17))])]
16500   "TARGET_SSE"
16501   "")
16502
16503 (define_insn "*minsf"
16504   [(set (match_operand:SF 0 "register_operand" "=x#f,f#x,f#x")
16505         (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "0,0,f#x")
16506                              (match_operand:SF 2 "nonimmediate_operand" "xm#f,f#x,0"))
16507                          (match_dup 1)
16508                          (match_dup 2)))
16509    (clobber (reg:CC 17))]
16510   "TARGET_SSE && TARGET_IEEE_FP"
16511   "#")
16512
16513 (define_insn "*minsf_nonieee"
16514   [(set (match_operand:SF 0 "register_operand" "=x#f,f#x")
16515         (if_then_else:SF (lt (match_operand:SF 1 "nonimmediate_operand" "%0,0")
16516                              (match_operand:SF 2 "nonimmediate_operand" "xm#f,f#x"))
16517                          (match_dup 1)
16518                          (match_dup 2)))
16519    (clobber (reg:CC 17))]
16520   "TARGET_SSE && !TARGET_IEEE_FP
16521    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
16522   "#")
16523
16524 (define_split
16525   [(set (match_operand:SF 0 "register_operand" "")
16526         (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "")
16527                              (match_operand:SF 2 "nonimmediate_operand" ""))
16528                          (match_operand:SF 3 "register_operand" "")
16529                          (match_operand:SF 4 "nonimmediate_operand" "")))
16530    (clobber (reg:CC 17))]
16531   "SSE_REG_P (operands[0]) && reload_completed
16532    && ((operands_match_p (operands[1], operands[3])
16533         && operands_match_p (operands[2], operands[4]))
16534        || (operands_match_p (operands[1], operands[4])
16535            && operands_match_p (operands[2], operands[3])))"
16536   [(set (match_dup 0)
16537         (if_then_else:SF (lt (match_dup 1)
16538                              (match_dup 2))
16539                          (match_dup 1)
16540                          (match_dup 2)))])
16541
16542 ;; Conditional addition patterns
16543 (define_expand "addqicc"
16544   [(match_operand:QI 0 "register_operand" "")
16545    (match_operand 1 "comparison_operator" "")
16546    (match_operand:QI 2 "register_operand" "")
16547    (match_operand:QI 3 "const_int_operand" "")]
16548   ""
16549   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
16550
16551 (define_expand "addhicc"
16552   [(match_operand:HI 0 "register_operand" "")
16553    (match_operand 1 "comparison_operator" "")
16554    (match_operand:HI 2 "register_operand" "")
16555    (match_operand:HI 3 "const_int_operand" "")]
16556   ""
16557   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
16558
16559 (define_expand "addsicc"
16560   [(match_operand:SI 0 "register_operand" "")
16561    (match_operand 1 "comparison_operator" "")
16562    (match_operand:SI 2 "register_operand" "")
16563    (match_operand:SI 3 "const_int_operand" "")]
16564   ""
16565   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
16566
16567 (define_expand "adddicc"
16568   [(match_operand:DI 0 "register_operand" "")
16569    (match_operand 1 "comparison_operator" "")
16570    (match_operand:DI 2 "register_operand" "")
16571    (match_operand:DI 3 "const_int_operand" "")]
16572   "TARGET_64BIT"
16573   "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
16574
16575 ;; We can't represent the LT test directly.  Do this by swapping the operands.
16576
16577 (define_split
16578   [(set (match_operand:SF 0 "fp_register_operand" "")
16579         (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "")
16580                              (match_operand:SF 2 "register_operand" ""))
16581                          (match_operand:SF 3 "register_operand" "")
16582                          (match_operand:SF 4 "register_operand" "")))
16583    (clobber (reg:CC 17))]
16584   "reload_completed
16585    && ((operands_match_p (operands[1], operands[3])
16586         && operands_match_p (operands[2], operands[4]))
16587        || (operands_match_p (operands[1], operands[4])
16588            && operands_match_p (operands[2], operands[3])))"
16589   [(set (reg:CCFP 17)
16590         (compare:CCFP (match_dup 2)
16591                       (match_dup 1)))
16592    (set (match_dup 0)
16593         (if_then_else:SF (ge (reg:CCFP 17) (const_int 0))
16594                          (match_dup 1)
16595                          (match_dup 2)))])
16596
16597 (define_insn "*minsf_sse"
16598   [(set (match_operand:SF 0 "register_operand" "=x")
16599         (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "0")
16600                              (match_operand:SF 2 "nonimmediate_operand" "xm"))
16601                          (match_dup 1)
16602                          (match_dup 2)))]
16603   "TARGET_SSE && reload_completed"
16604   "minss\t{%2, %0|%0, %2}"
16605   [(set_attr "type" "sse")
16606    (set_attr "mode" "SF")])
16607
16608 (define_expand "mindf3"
16609   [(parallel [
16610      (set (match_operand:DF 0 "register_operand" "")
16611           (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "")
16612                                (match_operand:DF 2 "nonimmediate_operand" ""))
16613                            (match_dup 1)
16614                            (match_dup 2)))
16615      (clobber (reg:CC 17))])]
16616   "TARGET_SSE2 && TARGET_SSE_MATH"
16617   "#")
16618
16619 (define_insn "*mindf"
16620   [(set (match_operand:DF 0 "register_operand" "=Y#f,f#Y,f#Y")
16621         (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "0,0,f#Y")
16622                              (match_operand:DF 2 "nonimmediate_operand" "Ym#f,f#Y,0"))
16623                          (match_dup 1)
16624                          (match_dup 2)))
16625    (clobber (reg:CC 17))]
16626   "TARGET_SSE2 && TARGET_IEEE_FP && TARGET_SSE_MATH"
16627   "#")
16628
16629 (define_insn "*mindf_nonieee"
16630   [(set (match_operand:DF 0 "register_operand" "=Y#f,f#Y")
16631         (if_then_else:DF (lt (match_operand:DF 1 "nonimmediate_operand" "%0,0")
16632                              (match_operand:DF 2 "nonimmediate_operand" "Ym#f,f#Y"))
16633                          (match_dup 1)
16634                          (match_dup 2)))
16635    (clobber (reg:CC 17))]
16636   "TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_IEEE_FP
16637    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
16638   "#")
16639
16640 (define_split
16641   [(set (match_operand:DF 0 "register_operand" "")
16642         (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "")
16643                              (match_operand:DF 2 "nonimmediate_operand" ""))
16644                          (match_operand:DF 3 "register_operand" "")
16645                          (match_operand:DF 4 "nonimmediate_operand" "")))
16646    (clobber (reg:CC 17))]
16647   "SSE_REG_P (operands[0]) && reload_completed
16648    && ((operands_match_p (operands[1], operands[3])
16649         && operands_match_p (operands[2], operands[4]))
16650        || (operands_match_p (operands[1], operands[4])
16651            && operands_match_p (operands[2], operands[3])))"
16652   [(set (match_dup 0)
16653         (if_then_else:DF (lt (match_dup 1)
16654                              (match_dup 2))
16655                          (match_dup 1)
16656                          (match_dup 2)))])
16657
16658 ;; We can't represent the LT test directly.  Do this by swapping the operands.
16659 (define_split
16660   [(set (match_operand:DF 0 "fp_register_operand" "")
16661         (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "")
16662                              (match_operand:DF 2 "register_operand" ""))
16663                          (match_operand:DF 3 "register_operand" "")
16664                          (match_operand:DF 4 "register_operand" "")))
16665    (clobber (reg:CC 17))]
16666   "reload_completed
16667    && ((operands_match_p (operands[1], operands[3])
16668         && operands_match_p (operands[2], operands[4]))
16669        || (operands_match_p (operands[1], operands[4])
16670            && operands_match_p (operands[2], operands[3])))"
16671   [(set (reg:CCFP 17)
16672         (compare:CCFP (match_dup 2)
16673                       (match_dup 1)))
16674    (set (match_dup 0)
16675         (if_then_else:DF (ge (reg:CCFP 17) (const_int 0))
16676                          (match_dup 1)
16677                          (match_dup 2)))])
16678
16679 (define_insn "*mindf_sse"
16680   [(set (match_operand:DF 0 "register_operand" "=Y")
16681         (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "0")
16682                              (match_operand:DF 2 "nonimmediate_operand" "Ym"))
16683                          (match_dup 1)
16684                          (match_dup 2)))]
16685   "TARGET_SSE2 && TARGET_SSE_MATH && reload_completed"
16686   "minsd\t{%2, %0|%0, %2}"
16687   [(set_attr "type" "sse")
16688    (set_attr "mode" "DF")])
16689
16690 (define_expand "maxsf3"
16691   [(parallel [
16692      (set (match_operand:SF 0 "register_operand" "")
16693           (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "")
16694                                (match_operand:SF 2 "nonimmediate_operand" ""))
16695                            (match_dup 1)
16696                            (match_dup 2)))
16697      (clobber (reg:CC 17))])]
16698   "TARGET_SSE"
16699   "#")
16700
16701 (define_insn "*maxsf"
16702   [(set (match_operand:SF 0 "register_operand" "=x#f,f#x,f#x")
16703         (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "0,0,f#x")
16704                              (match_operand:SF 2 "nonimmediate_operand" "xm#f,f#x,0"))
16705                          (match_dup 1)
16706                          (match_dup 2)))
16707    (clobber (reg:CC 17))]
16708   "TARGET_SSE && TARGET_IEEE_FP"
16709   "#")
16710
16711 (define_insn "*maxsf_nonieee"
16712   [(set (match_operand:SF 0 "register_operand" "=x#f,f#x")
16713         (if_then_else:SF (gt (match_operand:SF 1 "nonimmediate_operand" "%0,0")
16714                              (match_operand:SF 2 "nonimmediate_operand" "xm#f,f#x"))
16715                          (match_dup 1)
16716                          (match_dup 2)))
16717    (clobber (reg:CC 17))]
16718   "TARGET_SSE && !TARGET_IEEE_FP
16719    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
16720   "#")
16721
16722 (define_split
16723   [(set (match_operand:SF 0 "register_operand" "")
16724         (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "")
16725                              (match_operand:SF 2 "nonimmediate_operand" ""))
16726                          (match_operand:SF 3 "register_operand" "")
16727                          (match_operand:SF 4 "nonimmediate_operand" "")))
16728    (clobber (reg:CC 17))]
16729   "SSE_REG_P (operands[0]) && reload_completed
16730    && ((operands_match_p (operands[1], operands[3])
16731         && operands_match_p (operands[2], operands[4]))
16732        || (operands_match_p (operands[1], operands[4])
16733            && operands_match_p (operands[2], operands[3])))"
16734   [(set (match_dup 0)
16735         (if_then_else:SF (gt (match_dup 1)
16736                              (match_dup 2))
16737                          (match_dup 1)
16738                          (match_dup 2)))])
16739
16740 (define_split
16741   [(set (match_operand:SF 0 "fp_register_operand" "")
16742         (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "")
16743                              (match_operand:SF 2 "register_operand" ""))
16744                          (match_operand:SF 3 "register_operand" "")
16745                          (match_operand:SF 4 "register_operand" "")))
16746    (clobber (reg:CC 17))]
16747   "reload_completed
16748    && ((operands_match_p (operands[1], operands[3])
16749         && operands_match_p (operands[2], operands[4]))
16750        || (operands_match_p (operands[1], operands[4])
16751            && operands_match_p (operands[2], operands[3])))"
16752   [(set (reg:CCFP 17)
16753         (compare:CCFP (match_dup 1)
16754                       (match_dup 2)))
16755    (set (match_dup 0)
16756         (if_then_else:SF (gt (reg:CCFP 17) (const_int 0))
16757                          (match_dup 1)
16758                          (match_dup 2)))])
16759
16760 (define_insn "*maxsf_sse"
16761   [(set (match_operand:SF 0 "register_operand" "=x")
16762         (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "0")
16763                              (match_operand:SF 2 "nonimmediate_operand" "xm"))
16764                          (match_dup 1)
16765                          (match_dup 2)))]
16766   "TARGET_SSE && reload_completed"
16767   "maxss\t{%2, %0|%0, %2}"
16768   [(set_attr "type" "sse")
16769    (set_attr "mode" "SF")])
16770
16771 (define_expand "maxdf3"
16772   [(parallel [
16773      (set (match_operand:DF 0 "register_operand" "")
16774           (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "")
16775                                (match_operand:DF 2 "nonimmediate_operand" ""))
16776                            (match_dup 1)
16777                            (match_dup 2)))
16778      (clobber (reg:CC 17))])]
16779   "TARGET_SSE2 && TARGET_SSE_MATH"
16780   "#")
16781
16782 (define_insn "*maxdf"
16783   [(set (match_operand:DF 0 "register_operand" "=Y#f,f#Y,f#Y")
16784         (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "0,0,f#Y")
16785                              (match_operand:DF 2 "nonimmediate_operand" "Ym#f,f#Y,0"))
16786                          (match_dup 1)
16787                          (match_dup 2)))
16788    (clobber (reg:CC 17))]
16789   "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_IEEE_FP"
16790   "#")
16791
16792 (define_insn "*maxdf_nonieee"
16793   [(set (match_operand:DF 0 "register_operand" "=Y#f,f#Y")
16794         (if_then_else:DF (gt (match_operand:DF 1 "nonimmediate_operand" "%0,0")
16795                              (match_operand:DF 2 "nonimmediate_operand" "Ym#f,f#Y"))
16796                          (match_dup 1)
16797                          (match_dup 2)))
16798    (clobber (reg:CC 17))]
16799   "TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_IEEE_FP
16800    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
16801   "#")
16802
16803 (define_split
16804   [(set (match_operand:DF 0 "register_operand" "")
16805         (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "")
16806                              (match_operand:DF 2 "nonimmediate_operand" ""))
16807                          (match_operand:DF 3 "register_operand" "")
16808                          (match_operand:DF 4 "nonimmediate_operand" "")))
16809    (clobber (reg:CC 17))]
16810   "SSE_REG_P (operands[0]) && reload_completed
16811    && ((operands_match_p (operands[1], operands[3])
16812         && operands_match_p (operands[2], operands[4]))
16813        || (operands_match_p (operands[1], operands[4])
16814            && operands_match_p (operands[2], operands[3])))"
16815   [(set (match_dup 0)
16816         (if_then_else:DF (gt (match_dup 1)
16817                              (match_dup 2))
16818                          (match_dup 1)
16819                          (match_dup 2)))])
16820
16821 (define_split
16822   [(set (match_operand:DF 0 "fp_register_operand" "")
16823         (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "")
16824                              (match_operand:DF 2 "register_operand" ""))
16825                          (match_operand:DF 3 "register_operand" "")
16826                          (match_operand:DF 4 "register_operand" "")))
16827    (clobber (reg:CC 17))]
16828   "reload_completed
16829    && ((operands_match_p (operands[1], operands[3])
16830         && operands_match_p (operands[2], operands[4]))
16831        || (operands_match_p (operands[1], operands[4])
16832            && operands_match_p (operands[2], operands[3])))"
16833   [(set (reg:CCFP 17)
16834         (compare:CCFP (match_dup 1)
16835                       (match_dup 2)))
16836    (set (match_dup 0)
16837         (if_then_else:DF (gt (reg:CCFP 17) (const_int 0))
16838                          (match_dup 1)
16839                          (match_dup 2)))])
16840
16841 (define_insn "*maxdf_sse"
16842   [(set (match_operand:DF 0 "register_operand" "=Y")
16843         (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "0")
16844                              (match_operand:DF 2 "nonimmediate_operand" "Ym"))
16845                          (match_dup 1)
16846                          (match_dup 2)))]
16847   "TARGET_SSE2 && TARGET_SSE_MATH && reload_completed"
16848   "maxsd\t{%2, %0|%0, %2}"
16849   [(set_attr "type" "sse")
16850    (set_attr "mode" "DF")])
16851 \f
16852 ;; Misc patterns (?)
16853
16854 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
16855 ;; Otherwise there will be nothing to keep
16856 ;; 
16857 ;; [(set (reg ebp) (reg esp))]
16858 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
16859 ;;  (clobber (eflags)]
16860 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
16861 ;;
16862 ;; in proper program order.
16863 (define_insn "pro_epilogue_adjust_stack_1"
16864   [(set (match_operand:SI 0 "register_operand" "=r,r")
16865         (plus:SI (match_operand:SI 1 "register_operand" "0,r")
16866                  (match_operand:SI 2 "immediate_operand" "i,i")))
16867    (clobber (reg:CC 17))
16868    (clobber (mem:BLK (scratch)))]
16869   "!TARGET_64BIT"
16870 {
16871   switch (get_attr_type (insn))
16872     {
16873     case TYPE_IMOV:
16874       return "mov{l}\t{%1, %0|%0, %1}";
16875
16876     case TYPE_ALU:
16877       if (GET_CODE (operands[2]) == CONST_INT
16878           && (INTVAL (operands[2]) == 128
16879               || (INTVAL (operands[2]) < 0
16880                   && INTVAL (operands[2]) != -128)))
16881         {
16882           operands[2] = GEN_INT (-INTVAL (operands[2]));
16883           return "sub{l}\t{%2, %0|%0, %2}";
16884         }
16885       return "add{l}\t{%2, %0|%0, %2}";
16886
16887     case TYPE_LEA:
16888       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
16889       return "lea{l}\t{%a2, %0|%0, %a2}";
16890
16891     default:
16892       abort ();
16893     }
16894 }
16895   [(set (attr "type")
16896         (cond [(eq_attr "alternative" "0")
16897                  (const_string "alu")
16898                (match_operand:SI 2 "const0_operand" "")
16899                  (const_string "imov")
16900               ]
16901               (const_string "lea")))
16902    (set_attr "mode" "SI")])
16903
16904 (define_insn "pro_epilogue_adjust_stack_rex64"
16905   [(set (match_operand:DI 0 "register_operand" "=r,r")
16906         (plus:DI (match_operand:DI 1 "register_operand" "0,r")
16907                  (match_operand:DI 2 "x86_64_immediate_operand" "e,e")))
16908    (clobber (reg:CC 17))
16909    (clobber (mem:BLK (scratch)))]
16910   "TARGET_64BIT"
16911 {
16912   switch (get_attr_type (insn))
16913     {
16914     case TYPE_IMOV:
16915       return "mov{q}\t{%1, %0|%0, %1}";
16916
16917     case TYPE_ALU:
16918       if (GET_CODE (operands[2]) == CONST_INT
16919           /* Avoid overflows.  */
16920           && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
16921           && (INTVAL (operands[2]) == 128
16922               || (INTVAL (operands[2]) < 0
16923                   && INTVAL (operands[2]) != -128)))
16924         {
16925           operands[2] = GEN_INT (-INTVAL (operands[2]));
16926           return "sub{q}\t{%2, %0|%0, %2}";
16927         }
16928       return "add{q}\t{%2, %0|%0, %2}";
16929
16930     case TYPE_LEA:
16931       operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
16932       return "lea{q}\t{%a2, %0|%0, %a2}";
16933
16934     default:
16935       abort ();
16936     }
16937 }
16938   [(set (attr "type")
16939         (cond [(eq_attr "alternative" "0")
16940                  (const_string "alu")
16941                (match_operand:DI 2 "const0_operand" "")
16942                  (const_string "imov")
16943               ]
16944               (const_string "lea")))
16945    (set_attr "mode" "DI")])
16946
16947 (define_insn "pro_epilogue_adjust_stack_rex64_2"
16948   [(set (match_operand:DI 0 "register_operand" "=r,r")
16949         (plus:DI (match_operand:DI 1 "register_operand" "0,r")
16950                  (match_operand:DI 3 "immediate_operand" "i,i")))
16951    (use (match_operand:DI 2 "register_operand" "r,r"))
16952    (clobber (reg:CC 17))
16953    (clobber (mem:BLK (scratch)))]
16954   "TARGET_64BIT"
16955 {
16956   switch (get_attr_type (insn))
16957     {
16958     case TYPE_ALU:
16959       return "add{q}\t{%2, %0|%0, %2}";
16960
16961     case TYPE_LEA:
16962       operands[2] = gen_rtx_PLUS (DImode, operands[1], operands[2]);
16963       return "lea{q}\t{%a2, %0|%0, %a2}";
16964
16965     default:
16966       abort ();
16967     }
16968 }
16969   [(set_attr "type" "alu,lea")
16970    (set_attr "mode" "DI")])
16971
16972 ;; Placeholder for the conditional moves.  This one is split either to SSE
16973 ;; based moves emulation or to usual cmove sequence.  Little bit unfortunate
16974 ;; fact is that compares supported by the cmp??ss instructions are exactly
16975 ;; swapped of those supported by cmove sequence.
16976 ;; The EQ/NE comparisons also needs bit care, since they are not directly
16977 ;; supported by i387 comparisons and we do need to emit two conditional moves
16978 ;; in tandem.
16979
16980 (define_insn "sse_movsfcc"
16981   [(set (match_operand:SF 0 "register_operand" "=&x#rf,x#rf,?f#xr,?f#xr,?f#xr,?f#xr,?r#xf,?r#xf,?r#xf,?r#xf")
16982         (if_then_else:SF (match_operator 1 "sse_comparison_operator"
16983                         [(match_operand:SF 4 "nonimmediate_operand" "0#fx,x#fx,f#x,f#x,xm#f,xm#f,f#x,f#x,xm#f,xm#f")
16984                          (match_operand:SF 5 "nonimmediate_operand" "xm#f,xm#f,f#x,f#x,x#f,x#f,f#x,f#x,x#f,x#f")])
16985                       (match_operand:SF 2 "nonimmediate_operand" "x#fr,0#fr,f#fx,0#fx,f#fx,0#fx,rm#rx,0#rx,rm#rx,0#rx")
16986                       (match_operand:SF 3 "nonimmediate_operand" "x#fr,x#fr,0#fx,f#fx,0#fx,f#fx,0#fx,rm#rx,0#rx,rm#rx")))
16987    (clobber (match_scratch:SF 6 "=2,&4,X,X,X,X,X,X,X,X"))
16988    (clobber (reg:CC 17))]
16989   "TARGET_SSE
16990    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)
16991    /* Avoid combine from being smart and converting min/max
16992       instruction patterns into conditional moves.  */
16993    && ((GET_CODE (operands[1]) != LT && GET_CODE (operands[1]) != GT
16994         && GET_CODE (operands[1]) != UNLE && GET_CODE (operands[1]) != UNGE)
16995        || !rtx_equal_p (operands[4], operands[2])
16996        || !rtx_equal_p (operands[5], operands[3]))
16997    && (!TARGET_IEEE_FP
16998        || (GET_CODE (operands[1]) != EQ && GET_CODE (operands[1]) != NE))"
16999   "#")
17000
17001 (define_insn "sse_movsfcc_eq"
17002   [(set (match_operand:SF 0 "register_operand" "=&x#rf,x#rf,?f#xr,?f#xr,?r#xf,?r#xf")
17003         (if_then_else:SF (eq (match_operand:SF 3 "nonimmediate_operand" "%0#fx,x#fx,f#x,xm#f,f#x,xm#f")
17004                              (match_operand:SF 4 "nonimmediate_operand" "xm#f,xm#f,f#x,x#f,f#x,x#f"))
17005                       (match_operand:SF 1 "nonimmediate_operand" "x#fr,0#fr,0#fx,0#fx,0#rx,0#rx")
17006                       (match_operand:SF 2 "nonimmediate_operand" "x#fr,x#fr,f#fx,f#fx,rm#rx,rm#rx")))
17007    (clobber (match_scratch:SF 5 "=1,&3,X,X,X,X"))
17008    (clobber (reg:CC 17))]
17009   "TARGET_SSE
17010    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17011   "#")
17012
17013 (define_insn "sse_movdfcc"
17014   [(set (match_operand:DF 0 "register_operand" "=&Y#rf,Y#rf,?f#Yr,?f#Yr,?f#Yr,?f#Yr,?r#Yf,?r#Yf,?r#Yf,?r#Yf")
17015         (if_then_else:DF (match_operator 1 "sse_comparison_operator"
17016                         [(match_operand:DF 4 "nonimmediate_operand" "0#fY,Y#fY,f#Y,f#Y,Ym#f,Ym#f,f#Y,f#Y,Ym#f,Ym#f")
17017                          (match_operand:DF 5 "nonimmediate_operand" "Ym#f,Ym#f,f#Y,f#Y,Y#f,Y#f,f#Y,f#Y,Y#f,Y#f")])
17018                       (match_operand:DF 2 "nonimmediate_operand" "Y#fr,0#fr,f#fY,0#fY,f#fY,0#fY,rm#rY,0#rY,rm#rY,0#rY")
17019                       (match_operand:DF 3 "nonimmediate_operand" "Y#fr,Y#fr,0#fY,f#fY,0#fY,f#fY,0#fY,rm#rY,0#rY,rm#rY")))
17020    (clobber (match_scratch:DF 6 "=2,&4,X,X,X,X,X,X,X,X"))
17021    (clobber (reg:CC 17))]
17022   "TARGET_SSE2
17023    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)
17024    /* Avoid combine from being smart and converting min/max
17025       instruction patterns into conditional moves.  */
17026    && ((GET_CODE (operands[1]) != LT && GET_CODE (operands[1]) != GT
17027         && GET_CODE (operands[1]) != UNLE && GET_CODE (operands[1]) != UNGE)
17028        || !rtx_equal_p (operands[4], operands[2])
17029        || !rtx_equal_p (operands[5], operands[3]))
17030    && (!TARGET_IEEE_FP
17031        || (GET_CODE (operands[1]) != EQ && GET_CODE (operands[1]) != NE))"
17032   "#")
17033
17034 (define_insn "sse_movdfcc_eq"
17035   [(set (match_operand:DF 0 "register_operand" "=&Y#rf,Y#rf,?f#Yr,?f#Yr,?r#Yf,?r#Yf")
17036         (if_then_else:DF (eq (match_operand:DF 3 "nonimmediate_operand" "%0#fY,Y#fY,f#Y,Ym#f,f#Y,Ym#f")
17037                              (match_operand:DF 4 "nonimmediate_operand" "Ym#f,Ym#f,f#Y,Y#f,f#Y,Y#f"))
17038                       (match_operand:DF 1 "nonimmediate_operand" "Y#fr,0#fr,0#fY,0#fY,0#rY,0#rY")
17039                       (match_operand:DF 2 "nonimmediate_operand" "Y#fr,Y#fr,f#fY,f#fY,rm#rY,rm#rY")))
17040    (clobber (match_scratch:DF 5 "=1,&3,X,X,X,X"))
17041    (clobber (reg:CC 17))]
17042   "TARGET_SSE
17043    && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17044   "#")
17045
17046 ;; For non-sse moves just expand the usual cmove sequence.
17047 (define_split
17048   [(set (match_operand 0 "register_operand" "")
17049         (if_then_else (match_operator 1 "comparison_operator"
17050                         [(match_operand 4 "nonimmediate_operand" "")
17051                          (match_operand 5 "register_operand" "")])
17052                       (match_operand 2 "nonimmediate_operand" "")
17053                       (match_operand 3 "nonimmediate_operand" "")))
17054    (clobber (match_operand 6 "" ""))
17055    (clobber (reg:CC 17))]
17056   "!SSE_REG_P (operands[0]) && reload_completed
17057    && (GET_MODE (operands[0]) == SFmode
17058        || (TARGET_SSE2 && GET_MODE (operands[0]) == DFmode))"
17059   [(const_int 0)]
17060 {
17061    ix86_compare_op0 = operands[5];
17062    ix86_compare_op1 = operands[4];
17063    operands[1] = gen_rtx_fmt_ee (swap_condition (GET_CODE (operands[1])),
17064                                  VOIDmode, operands[5], operands[4]);
17065    ix86_expand_fp_movcc (operands);
17066    DONE;
17067 })
17068
17069 ;; Split SSE based conditional move into sequence:
17070 ;; cmpCC op0, op4   -  set op0 to 0 or ffffffff depending on the comparison
17071 ;; and   op2, op0   -  zero op2 if comparison was false
17072 ;; nand  op0, op3   -  load op3 to op0 if comparison was false
17073 ;; or    op2, op0   -  get the nonzero one into the result.
17074 (define_split
17075   [(set (match_operand:SF 0 "register_operand" "")
17076         (if_then_else:SF (match_operator 1 "sse_comparison_operator"
17077                            [(match_operand:SF 4 "register_operand" "")
17078                             (match_operand:SF 5 "nonimmediate_operand" "")])
17079                          (match_operand:SF 2 "register_operand" "")
17080                          (match_operand:SF 3 "register_operand" "")))
17081    (clobber (match_operand 6 "" ""))
17082    (clobber (reg:CC 17))]
17083   "SSE_REG_P (operands[0]) && reload_completed"
17084   [(set (match_dup 4) (match_op_dup 1 [(match_dup 4) (match_dup 5)]))
17085    (set (match_dup 2) (and:V4SF (match_dup 2)
17086                                 (match_dup 8)))
17087    (set (match_dup 8) (and:V4SF (not:V4SF (match_dup 8))
17088                                           (match_dup 3)))
17089    (set (match_dup 0) (ior:V4SF (match_dup 6)
17090                                 (match_dup 7)))]
17091 {
17092   /* If op2 == op3, op3 would be clobbered before it is used.  */
17093   if (operands_match_p (operands[2], operands[3]))
17094     {
17095       emit_move_insn (operands[0], operands[2]);
17096       DONE;
17097     }
17098
17099   PUT_MODE (operands[1], GET_MODE (operands[0]));
17100   if (operands_match_p (operands[0], operands[4]))
17101     operands[6] = operands[4], operands[7] = operands[2];
17102   else
17103     operands[6] = operands[2], operands[7] = operands[4];
17104   operands[0] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
17105   operands[2] = simplify_gen_subreg (V4SFmode, operands[2], SFmode, 0);
17106   operands[3] = simplify_gen_subreg (V4SFmode, operands[3], SFmode, 0);
17107   operands[8] = simplify_gen_subreg (V4SFmode, operands[4], SFmode, 0);
17108   operands[6] = simplify_gen_subreg (V4SFmode, operands[6], SFmode, 0);
17109   operands[7] = simplify_gen_subreg (V4SFmode, operands[7], SFmode, 0);
17110 })
17111
17112 (define_split
17113   [(set (match_operand:DF 0 "register_operand" "")
17114         (if_then_else:DF (match_operator 1 "sse_comparison_operator"
17115                            [(match_operand:DF 4 "register_operand" "")
17116                             (match_operand:DF 5 "nonimmediate_operand" "")])
17117                          (match_operand:DF 2 "register_operand" "")
17118                          (match_operand:DF 3 "register_operand" "")))
17119    (clobber (match_operand 6 "" ""))
17120    (clobber (reg:CC 17))]
17121   "SSE_REG_P (operands[0]) && reload_completed"
17122   [(set (match_dup 4) (match_op_dup 1 [(match_dup 4) (match_dup 5)]))
17123    (set (match_dup 2) (and:V2DF (match_dup 2)
17124                                 (match_dup 8)))
17125    (set (match_dup 8) (and:V2DF (not:V2DF (match_dup 8))
17126                                           (match_dup 3)))
17127    (set (match_dup 0) (ior:V2DF (match_dup 6)
17128                                 (match_dup 7)))]
17129 {
17130   if (GET_MODE (operands[2]) == DFmode
17131       && TARGET_SSE_PARTIAL_REGS && !optimize_size)
17132     {
17133       rtx op = simplify_gen_subreg (V2DFmode, operands[2], DFmode, 0);
17134       emit_insn (gen_sse2_unpcklpd (op, op, op));
17135       op = simplify_gen_subreg (V2DFmode, operands[3], DFmode, 0);
17136       emit_insn (gen_sse2_unpcklpd (op, op, op));
17137     }
17138
17139   /* If op2 == op3, op3 would be clobbered before it is used.  */
17140   if (operands_match_p (operands[2], operands[3]))
17141     {
17142       emit_move_insn (operands[0], operands[2]);
17143       DONE;
17144     }
17145
17146   PUT_MODE (operands[1], GET_MODE (operands[0]));
17147   if (operands_match_p (operands[0], operands[4]))
17148     operands[6] = operands[4], operands[7] = operands[2];
17149   else
17150     operands[6] = operands[2], operands[7] = operands[4];
17151   operands[0] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
17152   operands[2] = simplify_gen_subreg (V2DFmode, operands[2], DFmode, 0);
17153   operands[3] = simplify_gen_subreg (V2DFmode, operands[3], DFmode, 0);
17154   operands[8] = simplify_gen_subreg (V2DFmode, operands[4], DFmode, 0);
17155   operands[6] = simplify_gen_subreg (V2DFmode, operands[6], DFmode, 0);
17156   operands[7] = simplify_gen_subreg (V2DFmode, operands[7], DFmode, 0);
17157 })
17158
17159 ;; Special case of conditional move we can handle effectively.
17160 ;; Do not brother with the integer/floating point case, since these are
17161 ;; bot considerably slower, unlike in the generic case.
17162 (define_insn "*sse_movsfcc_const0_1"
17163   [(set (match_operand:SF 0 "register_operand" "=&x")
17164         (if_then_else:SF (match_operator 1 "sse_comparison_operator"
17165                         [(match_operand:SF 4 "register_operand" "0")
17166                          (match_operand:SF 5 "nonimmediate_operand" "xm")])
17167                       (match_operand:SF 2 "register_operand" "x")
17168                       (match_operand:SF 3 "const0_operand" "X")))]
17169   "TARGET_SSE"
17170   "#")
17171
17172 (define_insn "*sse_movsfcc_const0_2"
17173   [(set (match_operand:SF 0 "register_operand" "=&x")
17174         (if_then_else:SF (match_operator 1 "sse_comparison_operator"
17175                         [(match_operand:SF 4 "register_operand" "0")
17176                          (match_operand:SF 5 "nonimmediate_operand" "xm")])
17177                       (match_operand:SF 2 "const0_operand" "X")
17178                       (match_operand:SF 3 "register_operand" "x")))]
17179   "TARGET_SSE"
17180   "#")
17181
17182 (define_insn "*sse_movsfcc_const0_3"
17183   [(set (match_operand:SF 0 "register_operand" "=&x")
17184         (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
17185                         [(match_operand:SF 4 "nonimmediate_operand" "xm")
17186                          (match_operand:SF 5 "register_operand" "0")])
17187                       (match_operand:SF 2 "register_operand" "x")
17188                       (match_operand:SF 3 "const0_operand" "X")))]
17189   "TARGET_SSE"
17190   "#")
17191
17192 (define_insn "*sse_movsfcc_const0_4"
17193   [(set (match_operand:SF 0 "register_operand" "=&x")
17194         (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
17195                         [(match_operand:SF 4 "nonimmediate_operand" "xm")
17196                          (match_operand:SF 5 "register_operand" "0")])
17197                       (match_operand:SF 2 "const0_operand" "X")
17198                       (match_operand:SF 3 "register_operand" "x")))]
17199   "TARGET_SSE"
17200   "#")
17201
17202 (define_insn "*sse_movdfcc_const0_1"
17203   [(set (match_operand:DF 0 "register_operand" "=&Y")
17204         (if_then_else:DF (match_operator 1 "sse_comparison_operator"
17205                         [(match_operand:DF 4 "register_operand" "0")
17206                          (match_operand:DF 5 "nonimmediate_operand" "Ym")])
17207                       (match_operand:DF 2 "register_operand" "Y")
17208                       (match_operand:DF 3 "const0_operand" "X")))]
17209   "TARGET_SSE2"
17210   "#")
17211
17212 (define_insn "*sse_movdfcc_const0_2"
17213   [(set (match_operand:DF 0 "register_operand" "=&Y")
17214         (if_then_else:DF (match_operator 1 "sse_comparison_operator"
17215                         [(match_operand:DF 4 "register_operand" "0")
17216                          (match_operand:DF 5 "nonimmediate_operand" "Ym")])
17217                       (match_operand:DF 2 "const0_operand" "X")
17218                       (match_operand:DF 3 "register_operand" "Y")))]
17219   "TARGET_SSE2"
17220   "#")
17221
17222 (define_insn "*sse_movdfcc_const0_3"
17223   [(set (match_operand:DF 0 "register_operand" "=&Y")
17224         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
17225                         [(match_operand:DF 4 "nonimmediate_operand" "Ym")
17226                          (match_operand:DF 5 "register_operand" "0")])
17227                       (match_operand:DF 2 "register_operand" "Y")
17228                       (match_operand:DF 3 "const0_operand" "X")))]
17229   "TARGET_SSE2"
17230   "#")
17231
17232 (define_insn "*sse_movdfcc_const0_4"
17233   [(set (match_operand:DF 0 "register_operand" "=&Y")
17234         (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
17235                         [(match_operand:DF 4 "nonimmediate_operand" "Ym")
17236                          (match_operand:DF 5 "register_operand" "0")])
17237                       (match_operand:DF 2 "const0_operand" "X")
17238                       (match_operand:DF 3 "register_operand" "Y")))]
17239   "TARGET_SSE2"
17240   "#")
17241
17242 (define_split
17243   [(set (match_operand:SF 0 "register_operand" "")
17244         (if_then_else:SF (match_operator 1 "comparison_operator"
17245                            [(match_operand:SF 4 "nonimmediate_operand" "")
17246                             (match_operand:SF 5 "nonimmediate_operand" "")])
17247                          (match_operand:SF 2 "nonmemory_operand" "")
17248                          (match_operand:SF 3 "nonmemory_operand" "")))]
17249   "SSE_REG_P (operands[0]) && reload_completed
17250    && (const0_operand (operands[2], GET_MODE (operands[0]))
17251        || const0_operand (operands[3], GET_MODE (operands[0])))"
17252   [(set (match_dup 0) (match_op_dup 1 [(match_dup 0) (match_dup 5)]))
17253    (set (match_dup 8) (and:V4SF (match_dup 6) (match_dup 7)))]
17254 {
17255   PUT_MODE (operands[1], GET_MODE (operands[0]));
17256   if (!sse_comparison_operator (operands[1], VOIDmode)
17257       || !rtx_equal_p (operands[0], operands[4]))
17258     {
17259       rtx tmp = operands[5];
17260       operands[5] = operands[4];
17261       operands[4] = tmp;
17262       PUT_CODE (operands[1], swap_condition (GET_CODE (operands[1])));
17263     }
17264   if (!rtx_equal_p (operands[0], operands[4]))
17265     abort ();
17266   operands[8] = simplify_gen_subreg (V4SFmode, operands[0], SFmode, 0);
17267   if (const0_operand (operands[2], GET_MODE (operands[2])))
17268     {
17269       operands[7] = operands[3];
17270       operands[6] = gen_rtx_NOT (V4SFmode, operands[5]);
17271     }
17272   else
17273     {
17274       operands[7] = operands[2];
17275       operands[6] = operands[8];
17276     }
17277   operands[7] = simplify_gen_subreg (V4SFmode, operands[7], SFmode, 0);
17278 })
17279
17280 (define_split
17281   [(set (match_operand:DF 0 "register_operand" "")
17282         (if_then_else:DF (match_operator 1 "comparison_operator"
17283                            [(match_operand:DF 4 "nonimmediate_operand" "")
17284                             (match_operand:DF 5 "nonimmediate_operand" "")])
17285                          (match_operand:DF 2 "nonmemory_operand" "")
17286                          (match_operand:DF 3 "nonmemory_operand" "")))]
17287   "SSE_REG_P (operands[0]) && reload_completed
17288    && (const0_operand (operands[2], GET_MODE (operands[0]))
17289        || const0_operand (operands[3], GET_MODE (operands[0])))"
17290   [(set (match_dup 0) (match_op_dup 1 [(match_dup 0) (match_dup 5)]))
17291    (set (match_dup 8) (and:V2DF (match_dup 6) (match_dup 7)))]
17292 {
17293   if (TARGET_SSE_PARTIAL_REGS && !optimize_size
17294       && GET_MODE (operands[2]) == DFmode)
17295     {
17296       if (REG_P (operands[2]))
17297         {
17298           rtx op = simplify_gen_subreg (V2DFmode, operands[2], DFmode, 0);
17299           emit_insn (gen_sse2_unpcklpd (op, op, op));
17300         }
17301       if (REG_P (operands[3]))
17302         {
17303           rtx op = simplify_gen_subreg (V2DFmode, operands[3], DFmode, 0);
17304           emit_insn (gen_sse2_unpcklpd (op, op, op));
17305         }
17306     }
17307   PUT_MODE (operands[1], GET_MODE (operands[0]));
17308   if (!sse_comparison_operator (operands[1], VOIDmode)
17309       || !rtx_equal_p (operands[0], operands[4]))
17310     {
17311       rtx tmp = operands[5];
17312       operands[5] = operands[4];
17313       operands[4] = tmp;
17314       PUT_CODE (operands[1], swap_condition (GET_CODE (operands[1])));
17315     }
17316   if (!rtx_equal_p (operands[0], operands[4]))
17317     abort ();
17318   operands[8] = simplify_gen_subreg (V2DFmode, operands[0], DFmode, 0);
17319   if (const0_operand (operands[2], GET_MODE (operands[2])))
17320     {
17321       operands[7] = operands[3];
17322       operands[6] = gen_rtx_NOT (V2DFmode, operands[8]);
17323     }
17324   else
17325     {
17326       operands[7] = operands[2];
17327       operands[6] = operands[8];
17328     }
17329   operands[7] = simplify_gen_subreg (V2DFmode, operands[7], DFmode, 0);
17330 })
17331
17332 (define_expand "allocate_stack_worker"
17333   [(match_operand:SI 0 "register_operand" "")]
17334   "TARGET_STACK_PROBE"
17335 {
17336   if (reload_completed)
17337     {
17338       if (TARGET_64BIT)
17339         emit_insn (gen_allocate_stack_worker_rex64_postreload (operands[0]));
17340       else
17341         emit_insn (gen_allocate_stack_worker_postreload (operands[0]));
17342     }
17343   else
17344     {
17345       if (TARGET_64BIT)
17346         emit_insn (gen_allocate_stack_worker_rex64 (operands[0]));
17347       else
17348         emit_insn (gen_allocate_stack_worker_1 (operands[0]));
17349     }
17350   DONE;
17351 })
17352
17353 (define_insn "allocate_stack_worker_1"
17354   [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")]
17355     UNSPECV_STACK_PROBE)
17356    (set (reg:SI 7) (minus:SI (reg:SI 7) (match_dup 0)))
17357    (clobber (match_scratch:SI 1 "=0"))
17358    (clobber (reg:CC 17))]
17359   "!TARGET_64BIT && TARGET_STACK_PROBE"
17360   "call\t__alloca"
17361   [(set_attr "type" "multi")
17362    (set_attr "length" "5")])
17363
17364 (define_expand "allocate_stack_worker_postreload"
17365   [(parallel [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")]
17366                                     UNSPECV_STACK_PROBE)
17367               (set (reg:SI 7) (minus:SI (reg:SI 7) (match_dup 0)))
17368               (clobber (match_dup 0))
17369               (clobber (reg:CC 17))])]
17370   ""
17371   "")
17372
17373 (define_insn "allocate_stack_worker_rex64"
17374   [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")]
17375     UNSPECV_STACK_PROBE)
17376    (set (reg:DI 7) (minus:DI (reg:DI 7) (match_dup 0)))
17377    (clobber (match_scratch:DI 1 "=0"))
17378    (clobber (reg:CC 17))]
17379   "TARGET_64BIT && TARGET_STACK_PROBE"
17380   "call\t__alloca"
17381   [(set_attr "type" "multi")
17382    (set_attr "length" "5")])
17383
17384 (define_expand "allocate_stack_worker_rex64_postreload"
17385   [(parallel [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")]
17386                                     UNSPECV_STACK_PROBE)
17387               (set (reg:DI 7) (minus:DI (reg:DI 7) (match_dup 0)))
17388               (clobber (match_dup 0))
17389               (clobber (reg:CC 17))])]
17390   ""
17391   "")
17392
17393 (define_expand "allocate_stack"
17394   [(parallel [(set (match_operand:SI 0 "register_operand" "=r")
17395                    (minus:SI (reg:SI 7)
17396                              (match_operand:SI 1 "general_operand" "")))
17397               (clobber (reg:CC 17))])
17398    (parallel [(set (reg:SI 7)
17399                    (minus:SI (reg:SI 7) (match_dup 1)))
17400               (clobber (reg:CC 17))])]
17401   "TARGET_STACK_PROBE"
17402 {
17403 #ifdef CHECK_STACK_LIMIT
17404   if (GET_CODE (operands[1]) == CONST_INT
17405       && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
17406     emit_insn (gen_subsi3 (stack_pointer_rtx, stack_pointer_rtx,
17407                            operands[1]));
17408   else 
17409 #endif
17410     emit_insn (gen_allocate_stack_worker (copy_to_mode_reg (SImode,
17411                                                             operands[1])));
17412
17413   emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
17414   DONE;
17415 })
17416
17417 (define_expand "builtin_setjmp_receiver"
17418   [(label_ref (match_operand 0 "" ""))]
17419   "!TARGET_64BIT && flag_pic"
17420 {
17421   emit_insn (gen_set_got (pic_offset_table_rtx));
17422   DONE;
17423 })
17424 \f
17425 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
17426
17427 (define_split
17428   [(set (match_operand 0 "register_operand" "")
17429         (match_operator 3 "promotable_binary_operator"
17430            [(match_operand 1 "register_operand" "")
17431             (match_operand 2 "aligned_operand" "")]))
17432    (clobber (reg:CC 17))]
17433   "! TARGET_PARTIAL_REG_STALL && reload_completed
17434    && ((GET_MODE (operands[0]) == HImode 
17435         && ((!optimize_size && !TARGET_FAST_PREFIX)
17436             || GET_CODE (operands[2]) != CONST_INT
17437             || CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')))
17438        || (GET_MODE (operands[0]) == QImode 
17439            && (TARGET_PROMOTE_QImode || optimize_size)))"
17440   [(parallel [(set (match_dup 0)
17441                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
17442               (clobber (reg:CC 17))])]
17443   "operands[0] = gen_lowpart (SImode, operands[0]);
17444    operands[1] = gen_lowpart (SImode, operands[1]);
17445    if (GET_CODE (operands[3]) != ASHIFT)
17446      operands[2] = gen_lowpart (SImode, operands[2]);
17447    PUT_MODE (operands[3], SImode);")
17448
17449 ; Promote the QImode tests, as i386 has encoding of the AND
17450 ; instruction with 32-bit sign-extended immediate and thus the
17451 ; instruction size is unchanged, except in the %eax case for
17452 ; which it is increased by one byte, hence the ! optimize_size.
17453 (define_split
17454   [(set (match_operand 0 "flags_reg_operand" "")
17455         (match_operator 2 "compare_operator"
17456           [(and (match_operand 3 "aligned_operand" "")
17457                 (match_operand 4 "const_int_operand" ""))
17458            (const_int 0)]))
17459    (set (match_operand 1 "register_operand" "")
17460         (and (match_dup 3) (match_dup 4)))]
17461   "! TARGET_PARTIAL_REG_STALL && reload_completed
17462    /* Ensure that the operand will remain sign-extended immediate.  */
17463    && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)
17464    && ! optimize_size
17465    && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
17466        || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))"
17467   [(parallel [(set (match_dup 0)
17468                    (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
17469                                     (const_int 0)]))
17470               (set (match_dup 1)
17471                    (and:SI (match_dup 3) (match_dup 4)))])]
17472 {
17473   operands[4]
17474     = gen_int_mode (INTVAL (operands[4])
17475                     & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
17476   operands[1] = gen_lowpart (SImode, operands[1]);
17477   operands[3] = gen_lowpart (SImode, operands[3]);
17478 })
17479
17480 ; Don't promote the QImode tests, as i386 doesn't have encoding of
17481 ; the TEST instruction with 32-bit sign-extended immediate and thus
17482 ; the instruction size would at least double, which is not what we
17483 ; want even with ! optimize_size.
17484 (define_split
17485   [(set (match_operand 0 "flags_reg_operand" "")
17486         (match_operator 1 "compare_operator"
17487           [(and (match_operand:HI 2 "aligned_operand" "")
17488                 (match_operand:HI 3 "const_int_operand" ""))
17489            (const_int 0)]))]
17490   "! TARGET_PARTIAL_REG_STALL && reload_completed
17491    /* Ensure that the operand will remain sign-extended immediate.  */
17492    && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)
17493    && ! TARGET_FAST_PREFIX
17494    && ! optimize_size"
17495   [(set (match_dup 0)
17496         (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
17497                          (const_int 0)]))]
17498 {
17499   operands[3]
17500     = gen_int_mode (INTVAL (operands[3])
17501                     & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
17502   operands[2] = gen_lowpart (SImode, operands[2]);
17503 })
17504
17505 (define_split
17506   [(set (match_operand 0 "register_operand" "")
17507         (neg (match_operand 1 "register_operand" "")))
17508    (clobber (reg:CC 17))]
17509   "! TARGET_PARTIAL_REG_STALL && reload_completed
17510    && (GET_MODE (operands[0]) == HImode
17511        || (GET_MODE (operands[0]) == QImode 
17512            && (TARGET_PROMOTE_QImode || optimize_size)))"
17513   [(parallel [(set (match_dup 0)
17514                    (neg:SI (match_dup 1)))
17515               (clobber (reg:CC 17))])]
17516   "operands[0] = gen_lowpart (SImode, operands[0]);
17517    operands[1] = gen_lowpart (SImode, operands[1]);")
17518
17519 (define_split
17520   [(set (match_operand 0 "register_operand" "")
17521         (not (match_operand 1 "register_operand" "")))]
17522   "! TARGET_PARTIAL_REG_STALL && reload_completed
17523    && (GET_MODE (operands[0]) == HImode
17524        || (GET_MODE (operands[0]) == QImode 
17525            && (TARGET_PROMOTE_QImode || optimize_size)))"
17526   [(set (match_dup 0)
17527         (not:SI (match_dup 1)))]
17528   "operands[0] = gen_lowpart (SImode, operands[0]);
17529    operands[1] = gen_lowpart (SImode, operands[1]);")
17530
17531 (define_split 
17532   [(set (match_operand 0 "register_operand" "")
17533         (if_then_else (match_operator 1 "comparison_operator" 
17534                                 [(reg 17) (const_int 0)])
17535                       (match_operand 2 "register_operand" "")
17536                       (match_operand 3 "register_operand" "")))]
17537   "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE
17538    && (GET_MODE (operands[0]) == HImode
17539        || (GET_MODE (operands[0]) == QImode 
17540            && (TARGET_PROMOTE_QImode || optimize_size)))"
17541   [(set (match_dup 0)
17542         (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
17543   "operands[0] = gen_lowpart (SImode, operands[0]);
17544    operands[2] = gen_lowpart (SImode, operands[2]);
17545    operands[3] = gen_lowpart (SImode, operands[3]);")
17546                         
17547 \f
17548 ;; RTL Peephole optimizations, run before sched2.  These primarily look to
17549 ;; transform a complex memory operation into two memory to register operations.
17550
17551 ;; Don't push memory operands
17552 (define_peephole2
17553   [(set (match_operand:SI 0 "push_operand" "")
17554         (match_operand:SI 1 "memory_operand" ""))
17555    (match_scratch:SI 2 "r")]
17556   "! optimize_size && ! TARGET_PUSH_MEMORY"
17557   [(set (match_dup 2) (match_dup 1))
17558    (set (match_dup 0) (match_dup 2))]
17559   "")
17560
17561 (define_peephole2
17562   [(set (match_operand:DI 0 "push_operand" "")
17563         (match_operand:DI 1 "memory_operand" ""))
17564    (match_scratch:DI 2 "r")]
17565   "! optimize_size && ! TARGET_PUSH_MEMORY"
17566   [(set (match_dup 2) (match_dup 1))
17567    (set (match_dup 0) (match_dup 2))]
17568   "")
17569
17570 ;; We need to handle SFmode only, because DFmode and XFmode is split to
17571 ;; SImode pushes.
17572 (define_peephole2
17573   [(set (match_operand:SF 0 "push_operand" "")
17574         (match_operand:SF 1 "memory_operand" ""))
17575    (match_scratch:SF 2 "r")]
17576   "! optimize_size && ! TARGET_PUSH_MEMORY"
17577   [(set (match_dup 2) (match_dup 1))
17578    (set (match_dup 0) (match_dup 2))]
17579   "")
17580
17581 (define_peephole2
17582   [(set (match_operand:HI 0 "push_operand" "")
17583         (match_operand:HI 1 "memory_operand" ""))
17584    (match_scratch:HI 2 "r")]
17585   "! optimize_size && ! TARGET_PUSH_MEMORY"
17586   [(set (match_dup 2) (match_dup 1))
17587    (set (match_dup 0) (match_dup 2))]
17588   "")
17589
17590 (define_peephole2
17591   [(set (match_operand:QI 0 "push_operand" "")
17592         (match_operand:QI 1 "memory_operand" ""))
17593    (match_scratch:QI 2 "q")]
17594   "! optimize_size && ! TARGET_PUSH_MEMORY"
17595   [(set (match_dup 2) (match_dup 1))
17596    (set (match_dup 0) (match_dup 2))]
17597   "")
17598
17599 ;; Don't move an immediate directly to memory when the instruction
17600 ;; gets too big.
17601 (define_peephole2
17602   [(match_scratch:SI 1 "r")
17603    (set (match_operand:SI 0 "memory_operand" "")
17604         (const_int 0))]
17605   "! optimize_size
17606    && ! TARGET_USE_MOV0
17607    && TARGET_SPLIT_LONG_MOVES
17608    && get_attr_length (insn) >= ix86_cost->large_insn
17609    && peep2_regno_dead_p (0, FLAGS_REG)"
17610   [(parallel [(set (match_dup 1) (const_int 0))
17611               (clobber (reg:CC 17))])
17612    (set (match_dup 0) (match_dup 1))]
17613   "")
17614
17615 (define_peephole2
17616   [(match_scratch:HI 1 "r")
17617    (set (match_operand:HI 0 "memory_operand" "")
17618         (const_int 0))]
17619   "! optimize_size
17620    && ! TARGET_USE_MOV0
17621    && TARGET_SPLIT_LONG_MOVES
17622    && get_attr_length (insn) >= ix86_cost->large_insn
17623    && peep2_regno_dead_p (0, FLAGS_REG)"
17624   [(parallel [(set (match_dup 2) (const_int 0))
17625               (clobber (reg:CC 17))])
17626    (set (match_dup 0) (match_dup 1))]
17627   "operands[2] = gen_lowpart (SImode, operands[1]);")
17628
17629 (define_peephole2
17630   [(match_scratch:QI 1 "q")
17631    (set (match_operand:QI 0 "memory_operand" "")
17632         (const_int 0))]
17633   "! optimize_size
17634    && ! TARGET_USE_MOV0
17635    && TARGET_SPLIT_LONG_MOVES
17636    && get_attr_length (insn) >= ix86_cost->large_insn
17637    && peep2_regno_dead_p (0, FLAGS_REG)"
17638   [(parallel [(set (match_dup 2) (const_int 0))
17639               (clobber (reg:CC 17))])
17640    (set (match_dup 0) (match_dup 1))]
17641   "operands[2] = gen_lowpart (SImode, operands[1]);")
17642
17643 (define_peephole2
17644   [(match_scratch:SI 2 "r")
17645    (set (match_operand:SI 0 "memory_operand" "")
17646         (match_operand:SI 1 "immediate_operand" ""))]
17647   "! optimize_size
17648    && get_attr_length (insn) >= ix86_cost->large_insn
17649    && TARGET_SPLIT_LONG_MOVES"
17650   [(set (match_dup 2) (match_dup 1))
17651    (set (match_dup 0) (match_dup 2))]
17652   "")
17653
17654 (define_peephole2
17655   [(match_scratch:HI 2 "r")
17656    (set (match_operand:HI 0 "memory_operand" "")
17657         (match_operand:HI 1 "immediate_operand" ""))]
17658   "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
17659   && TARGET_SPLIT_LONG_MOVES"
17660   [(set (match_dup 2) (match_dup 1))
17661    (set (match_dup 0) (match_dup 2))]
17662   "")
17663
17664 (define_peephole2
17665   [(match_scratch:QI 2 "q")
17666    (set (match_operand:QI 0 "memory_operand" "")
17667         (match_operand:QI 1 "immediate_operand" ""))]
17668   "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
17669   && TARGET_SPLIT_LONG_MOVES"
17670   [(set (match_dup 2) (match_dup 1))
17671    (set (match_dup 0) (match_dup 2))]
17672   "")
17673
17674 ;; Don't compare memory with zero, load and use a test instead.
17675 (define_peephole2
17676   [(set (match_operand 0 "flags_reg_operand" "")
17677         (match_operator 1 "compare_operator"
17678           [(match_operand:SI 2 "memory_operand" "")
17679            (const_int 0)]))
17680    (match_scratch:SI 3 "r")]
17681   "ix86_match_ccmode (insn, CCNOmode) && ! optimize_size"
17682   [(set (match_dup 3) (match_dup 2))
17683    (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))]
17684   "")
17685
17686 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer. 
17687 ;; Don't split NOTs with a displacement operand, because resulting XOR
17688 ;; will not be pairable anyway.
17689 ;;
17690 ;; On AMD K6, NOT is vector decoded with memory operand that can not be
17691 ;; represented using a modRM byte.  The XOR replacement is long decoded,
17692 ;; so this split helps here as well.
17693 ;;
17694 ;; Note: Can't do this as a regular split because we can't get proper
17695 ;; lifetime information then.
17696
17697 (define_peephole2
17698   [(set (match_operand:SI 0 "nonimmediate_operand" "")
17699         (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
17700   "!optimize_size
17701    && peep2_regno_dead_p (0, FLAGS_REG)
17702    && ((TARGET_PENTIUM 
17703         && (GET_CODE (operands[0]) != MEM
17704             || !memory_displacement_operand (operands[0], SImode)))
17705        || (TARGET_K6 && long_memory_operand (operands[0], SImode)))"
17706   [(parallel [(set (match_dup 0)
17707                    (xor:SI (match_dup 1) (const_int -1)))
17708               (clobber (reg:CC 17))])]
17709   "")
17710
17711 (define_peephole2
17712   [(set (match_operand:HI 0 "nonimmediate_operand" "")
17713         (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
17714   "!optimize_size
17715    && peep2_regno_dead_p (0, FLAGS_REG)
17716    && ((TARGET_PENTIUM 
17717         && (GET_CODE (operands[0]) != MEM
17718             || !memory_displacement_operand (operands[0], HImode)))
17719        || (TARGET_K6 && long_memory_operand (operands[0], HImode)))"
17720   [(parallel [(set (match_dup 0)
17721                    (xor:HI (match_dup 1) (const_int -1)))
17722               (clobber (reg:CC 17))])]
17723   "")
17724
17725 (define_peephole2
17726   [(set (match_operand:QI 0 "nonimmediate_operand" "")
17727         (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
17728   "!optimize_size
17729    && peep2_regno_dead_p (0, FLAGS_REG)
17730    && ((TARGET_PENTIUM 
17731         && (GET_CODE (operands[0]) != MEM
17732             || !memory_displacement_operand (operands[0], QImode)))
17733        || (TARGET_K6 && long_memory_operand (operands[0], QImode)))"
17734   [(parallel [(set (match_dup 0)
17735                    (xor:QI (match_dup 1) (const_int -1)))
17736               (clobber (reg:CC 17))])]
17737   "")
17738
17739 ;; Non pairable "test imm, reg" instructions can be translated to
17740 ;; "and imm, reg" if reg dies.  The "and" form is also shorter (one
17741 ;; byte opcode instead of two, have a short form for byte operands),
17742 ;; so do it for other CPUs as well.  Given that the value was dead,
17743 ;; this should not create any new dependencies.  Pass on the sub-word
17744 ;; versions if we're concerned about partial register stalls.
17745
17746 (define_peephole2
17747   [(set (match_operand 0 "flags_reg_operand" "")
17748         (match_operator 1 "compare_operator"
17749           [(and:SI (match_operand:SI 2 "register_operand" "")
17750                    (match_operand:SI 3 "immediate_operand" ""))
17751            (const_int 0)]))]
17752   "ix86_match_ccmode (insn, CCNOmode)
17753    && (true_regnum (operands[2]) != 0
17754        || (GET_CODE (operands[3]) == CONST_INT
17755            && CONST_OK_FOR_LETTER_P (INTVAL (operands[3]), 'K')))
17756    && peep2_reg_dead_p (1, operands[2])"
17757   [(parallel
17758      [(set (match_dup 0)
17759            (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
17760                             (const_int 0)]))
17761       (set (match_dup 2)
17762            (and:SI (match_dup 2) (match_dup 3)))])]
17763   "")
17764
17765 ;; We don't need to handle HImode case, because it will be promoted to SImode
17766 ;; on ! TARGET_PARTIAL_REG_STALL
17767
17768 (define_peephole2
17769   [(set (match_operand 0 "flags_reg_operand" "")
17770         (match_operator 1 "compare_operator"
17771           [(and:QI (match_operand:QI 2 "register_operand" "")
17772                    (match_operand:QI 3 "immediate_operand" ""))
17773            (const_int 0)]))]
17774   "! TARGET_PARTIAL_REG_STALL
17775    && ix86_match_ccmode (insn, CCNOmode)
17776    && true_regnum (operands[2]) != 0
17777    && peep2_reg_dead_p (1, operands[2])"
17778   [(parallel
17779      [(set (match_dup 0)
17780            (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
17781                             (const_int 0)]))
17782       (set (match_dup 2)
17783            (and:QI (match_dup 2) (match_dup 3)))])]
17784   "")
17785
17786 (define_peephole2
17787   [(set (match_operand 0 "flags_reg_operand" "")
17788         (match_operator 1 "compare_operator"
17789           [(and:SI
17790              (zero_extract:SI
17791                (match_operand 2 "ext_register_operand" "")
17792                (const_int 8)
17793                (const_int 8))
17794              (match_operand 3 "const_int_operand" ""))
17795            (const_int 0)]))]
17796   "! TARGET_PARTIAL_REG_STALL
17797    && ix86_match_ccmode (insn, CCNOmode)
17798    && true_regnum (operands[2]) != 0
17799    && peep2_reg_dead_p (1, operands[2])"
17800   [(parallel [(set (match_dup 0)
17801                    (match_op_dup 1
17802                      [(and:SI
17803                         (zero_extract:SI
17804                           (match_dup 2)
17805                           (const_int 8)
17806                           (const_int 8))
17807                         (match_dup 3))
17808                       (const_int 0)]))
17809               (set (zero_extract:SI (match_dup 2)
17810                                     (const_int 8)
17811                                     (const_int 8))
17812                    (and:SI 
17813                      (zero_extract:SI
17814                        (match_dup 2)
17815                        (const_int 8)
17816                        (const_int 8))
17817                      (match_dup 3)))])]
17818   "")
17819
17820 ;; Don't do logical operations with memory inputs.
17821 (define_peephole2
17822   [(match_scratch:SI 2 "r")
17823    (parallel [(set (match_operand:SI 0 "register_operand" "")
17824                    (match_operator:SI 3 "arith_or_logical_operator"
17825                      [(match_dup 0)
17826                       (match_operand:SI 1 "memory_operand" "")]))
17827               (clobber (reg:CC 17))])]
17828   "! optimize_size && ! TARGET_READ_MODIFY"
17829   [(set (match_dup 2) (match_dup 1))
17830    (parallel [(set (match_dup 0)
17831                    (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
17832               (clobber (reg:CC 17))])]
17833   "")
17834
17835 (define_peephole2
17836   [(match_scratch:SI 2 "r")
17837    (parallel [(set (match_operand:SI 0 "register_operand" "")
17838                    (match_operator:SI 3 "arith_or_logical_operator"
17839                      [(match_operand:SI 1 "memory_operand" "")
17840                       (match_dup 0)]))
17841               (clobber (reg:CC 17))])]
17842   "! optimize_size && ! TARGET_READ_MODIFY"
17843   [(set (match_dup 2) (match_dup 1))
17844    (parallel [(set (match_dup 0)
17845                    (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
17846               (clobber (reg:CC 17))])]
17847   "")
17848
17849 ; Don't do logical operations with memory outputs
17850 ;
17851 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
17852 ; instruction into two 1-uop insns plus a 2-uop insn.  That last has
17853 ; the same decoder scheduling characteristics as the original.
17854
17855 (define_peephole2
17856   [(match_scratch:SI 2 "r")
17857    (parallel [(set (match_operand:SI 0 "memory_operand" "")
17858                    (match_operator:SI 3 "arith_or_logical_operator"
17859                      [(match_dup 0)
17860                       (match_operand:SI 1 "nonmemory_operand" "")]))
17861               (clobber (reg:CC 17))])]
17862   "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
17863   [(set (match_dup 2) (match_dup 0))
17864    (parallel [(set (match_dup 2)
17865                    (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
17866               (clobber (reg:CC 17))])
17867    (set (match_dup 0) (match_dup 2))]
17868   "")
17869
17870 (define_peephole2
17871   [(match_scratch:SI 2 "r")
17872    (parallel [(set (match_operand:SI 0 "memory_operand" "")
17873                    (match_operator:SI 3 "arith_or_logical_operator"
17874                      [(match_operand:SI 1 "nonmemory_operand" "")
17875                       (match_dup 0)]))
17876               (clobber (reg:CC 17))])]
17877   "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
17878   [(set (match_dup 2) (match_dup 0))
17879    (parallel [(set (match_dup 2)
17880                    (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
17881               (clobber (reg:CC 17))])
17882    (set (match_dup 0) (match_dup 2))]
17883   "")
17884
17885 ;; Attempt to always use XOR for zeroing registers.
17886 (define_peephole2
17887   [(set (match_operand 0 "register_operand" "")
17888         (const_int 0))]
17889   "(GET_MODE (operands[0]) == QImode
17890     || GET_MODE (operands[0]) == HImode
17891     || GET_MODE (operands[0]) == SImode
17892     || (GET_MODE (operands[0]) == DImode && TARGET_64BIT))
17893    && (! TARGET_USE_MOV0 || optimize_size)
17894    && peep2_regno_dead_p (0, FLAGS_REG)"
17895   [(parallel [(set (match_dup 0) (const_int 0))
17896               (clobber (reg:CC 17))])]
17897   "operands[0] = gen_lowpart (GET_MODE (operands[0]) == DImode ? DImode : SImode,
17898                               operands[0]);")
17899
17900 (define_peephole2
17901   [(set (strict_low_part (match_operand 0 "register_operand" ""))
17902         (const_int 0))]
17903   "(GET_MODE (operands[0]) == QImode
17904     || GET_MODE (operands[0]) == HImode)
17905    && (! TARGET_USE_MOV0 || optimize_size)
17906    && peep2_regno_dead_p (0, FLAGS_REG)"
17907   [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
17908               (clobber (reg:CC 17))])])
17909
17910 ;; For HI and SI modes, or $-1,reg is smaller than mov $-1,reg.
17911 (define_peephole2
17912   [(set (match_operand 0 "register_operand" "")
17913         (const_int -1))]
17914   "(GET_MODE (operands[0]) == HImode
17915     || GET_MODE (operands[0]) == SImode 
17916     || (GET_MODE (operands[0]) == DImode && TARGET_64BIT))
17917    && (optimize_size || TARGET_PENTIUM)
17918    && peep2_regno_dead_p (0, FLAGS_REG)"
17919   [(parallel [(set (match_dup 0) (const_int -1))
17920               (clobber (reg:CC 17))])]
17921   "operands[0] = gen_lowpart (GET_MODE (operands[0]) == DImode ? DImode : SImode,
17922                               operands[0]);")
17923
17924 ;; Attempt to convert simple leas to adds. These can be created by
17925 ;; move expanders.
17926 (define_peephole2
17927   [(set (match_operand:SI 0 "register_operand" "")
17928         (plus:SI (match_dup 0)
17929                  (match_operand:SI 1 "nonmemory_operand" "")))]
17930   "peep2_regno_dead_p (0, FLAGS_REG)"
17931   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
17932               (clobber (reg:CC 17))])]
17933   "")
17934
17935 (define_peephole2
17936   [(set (match_operand:SI 0 "register_operand" "")
17937         (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
17938                             (match_operand:DI 2 "nonmemory_operand" "")) 0))]
17939   "peep2_regno_dead_p (0, FLAGS_REG) && REGNO (operands[0]) == REGNO (operands[1])"
17940   [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
17941               (clobber (reg:CC 17))])]
17942   "operands[2] = gen_lowpart (SImode, operands[2]);")
17943
17944 (define_peephole2
17945   [(set (match_operand:DI 0 "register_operand" "")
17946         (plus:DI (match_dup 0)
17947                  (match_operand:DI 1 "x86_64_general_operand" "")))]
17948   "peep2_regno_dead_p (0, FLAGS_REG)"
17949   [(parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
17950               (clobber (reg:CC 17))])]
17951   "")
17952
17953 (define_peephole2
17954   [(set (match_operand:SI 0 "register_operand" "")
17955         (mult:SI (match_dup 0)
17956                  (match_operand:SI 1 "const_int_operand" "")))]
17957   "exact_log2 (INTVAL (operands[1])) >= 0
17958    && peep2_regno_dead_p (0, FLAGS_REG)"
17959   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
17960               (clobber (reg:CC 17))])]
17961   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
17962
17963 (define_peephole2
17964   [(set (match_operand:DI 0 "register_operand" "")
17965         (mult:DI (match_dup 0)
17966                  (match_operand:DI 1 "const_int_operand" "")))]
17967   "exact_log2 (INTVAL (operands[1])) >= 0
17968    && peep2_regno_dead_p (0, FLAGS_REG)"
17969   [(parallel [(set (match_dup 0) (ashift:DI (match_dup 0) (match_dup 2)))
17970               (clobber (reg:CC 17))])]
17971   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
17972
17973 (define_peephole2
17974   [(set (match_operand:SI 0 "register_operand" "")
17975         (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
17976                    (match_operand:DI 2 "const_int_operand" "")) 0))]
17977   "exact_log2 (INTVAL (operands[2])) >= 0
17978    && REGNO (operands[0]) == REGNO (operands[1])
17979    && peep2_regno_dead_p (0, FLAGS_REG)"
17980   [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
17981               (clobber (reg:CC 17))])]
17982   "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
17983
17984 ;; The ESP adjustments can be done by the push and pop instructions.  Resulting
17985 ;; code is shorter, since push is only 1 byte, while add imm, %esp 3 bytes.  On
17986 ;; many CPUs it is also faster, since special hardware to avoid esp
17987 ;; dependencies is present.
17988
17989 ;; While some of these conversions may be done using splitters, we use peepholes
17990 ;; in order to allow combine_stack_adjustments pass to see nonobfuscated RTL.
17991
17992 ;; Convert prologue esp subtractions to push.
17993 ;; We need register to push.  In order to keep verify_flow_info happy we have
17994 ;; two choices
17995 ;; - use scratch and clobber it in order to avoid dependencies
17996 ;; - use already live register
17997 ;; We can't use the second way right now, since there is no reliable way how to
17998 ;; verify that given register is live.  First choice will also most likely in
17999 ;; fewer dependencies.  On the place of esp adjustments it is very likely that
18000 ;; call clobbered registers are dead.  We may want to use base pointer as an
18001 ;; alternative when no register is available later.
18002
18003 (define_peephole2
18004   [(match_scratch:SI 0 "r")
18005    (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -4)))
18006               (clobber (reg:CC 17))
18007               (clobber (mem:BLK (scratch)))])]
18008   "optimize_size || !TARGET_SUB_ESP_4"
18009   [(clobber (match_dup 0))
18010    (parallel [(set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))
18011               (clobber (mem:BLK (scratch)))])])
18012
18013 (define_peephole2
18014   [(match_scratch:SI 0 "r")
18015    (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
18016               (clobber (reg:CC 17))
18017               (clobber (mem:BLK (scratch)))])]
18018   "optimize_size || !TARGET_SUB_ESP_8"
18019   [(clobber (match_dup 0))
18020    (set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))
18021    (parallel [(set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))
18022               (clobber (mem:BLK (scratch)))])])
18023
18024 ;; Convert esp subtractions to push.
18025 (define_peephole2
18026   [(match_scratch:SI 0 "r")
18027    (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -4)))
18028               (clobber (reg:CC 17))])]
18029   "optimize_size || !TARGET_SUB_ESP_4"
18030   [(clobber (match_dup 0))
18031    (set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))])
18032
18033 (define_peephole2
18034   [(match_scratch:SI 0 "r")
18035    (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
18036               (clobber (reg:CC 17))])]
18037   "optimize_size || !TARGET_SUB_ESP_8"
18038   [(clobber (match_dup 0))
18039    (set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))
18040    (set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))])
18041
18042 ;; Convert epilogue deallocator to pop.
18043 (define_peephole2
18044   [(match_scratch:SI 0 "r")
18045    (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))
18046               (clobber (reg:CC 17))
18047               (clobber (mem:BLK (scratch)))])]
18048   "optimize_size || !TARGET_ADD_ESP_4"
18049   [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
18050               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))
18051               (clobber (mem:BLK (scratch)))])]
18052   "")
18053
18054 ;; Two pops case is tricky, since pop causes dependency on destination register.
18055 ;; We use two registers if available.
18056 (define_peephole2
18057   [(match_scratch:SI 0 "r")
18058    (match_scratch:SI 1 "r")
18059    (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 8)))
18060               (clobber (reg:CC 17))
18061               (clobber (mem:BLK (scratch)))])]
18062   "optimize_size || !TARGET_ADD_ESP_8"
18063   [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
18064               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))
18065               (clobber (mem:BLK (scratch)))])
18066    (parallel [(set (match_dup 1) (mem:SI (reg:SI 7)))
18067               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
18068   "")
18069
18070 (define_peephole2
18071   [(match_scratch:SI 0 "r")
18072    (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 8)))
18073               (clobber (reg:CC 17))
18074               (clobber (mem:BLK (scratch)))])]
18075   "optimize_size"
18076   [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
18077               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))
18078               (clobber (mem:BLK (scratch)))])
18079    (parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
18080               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
18081   "")
18082
18083 ;; Convert esp additions to pop.
18084 (define_peephole2
18085   [(match_scratch:SI 0 "r")
18086    (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))
18087               (clobber (reg:CC 17))])]
18088   ""
18089   [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
18090               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
18091   "")
18092
18093 ;; Two pops case is tricky, since pop causes dependency on destination register.
18094 ;; We use two registers if available.
18095 (define_peephole2
18096   [(match_scratch:SI 0 "r")
18097    (match_scratch:SI 1 "r")
18098    (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 8)))
18099               (clobber (reg:CC 17))])]
18100   ""
18101   [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
18102               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])
18103    (parallel [(set (match_dup 1) (mem:SI (reg:SI 7)))
18104               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
18105   "")
18106
18107 (define_peephole2
18108   [(match_scratch:SI 0 "r")
18109    (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 8)))
18110               (clobber (reg:CC 17))])]
18111   "optimize_size"
18112   [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
18113               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])
18114    (parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
18115               (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
18116   "")
18117 \f
18118 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
18119 ;; required and register dies.  Similarly for 128 to plus -128.
18120 (define_peephole2
18121   [(set (match_operand 0 "flags_reg_operand" "")
18122         (match_operator 1 "compare_operator"
18123           [(match_operand 2 "register_operand" "")
18124            (match_operand 3 "const_int_operand" "")]))]
18125   "(INTVAL (operands[3]) == -1
18126     || INTVAL (operands[3]) == 1
18127     || INTVAL (operands[3]) == 128)
18128    && ix86_match_ccmode (insn, CCGCmode)
18129    && peep2_reg_dead_p (1, operands[2])"
18130   [(parallel [(set (match_dup 0)
18131                    (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
18132               (clobber (match_dup 2))])]
18133   "")
18134 \f
18135 (define_peephole2
18136   [(match_scratch:DI 0 "r")
18137    (parallel [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -8)))
18138               (clobber (reg:CC 17))
18139               (clobber (mem:BLK (scratch)))])]
18140   "optimize_size || !TARGET_SUB_ESP_4"
18141   [(clobber (match_dup 0))
18142    (parallel [(set (mem:DI (pre_dec:DI (reg:DI 7))) (match_dup 0))
18143               (clobber (mem:BLK (scratch)))])])
18144
18145 (define_peephole2
18146   [(match_scratch:DI 0 "r")
18147    (parallel [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -16)))
18148               (clobber (reg:CC 17))
18149               (clobber (mem:BLK (scratch)))])]
18150   "optimize_size || !TARGET_SUB_ESP_8"
18151   [(clobber (match_dup 0))
18152    (set (mem:DI (pre_dec:DI (reg:DI 7))) (match_dup 0))
18153    (parallel [(set (mem:DI (pre_dec:DI (reg:DI 7))) (match_dup 0))
18154               (clobber (mem:BLK (scratch)))])])
18155
18156 ;; Convert esp subtractions to push.
18157 (define_peephole2
18158   [(match_scratch:DI 0 "r")
18159    (parallel [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -8)))
18160               (clobber (reg:CC 17))])]
18161   "optimize_size || !TARGET_SUB_ESP_4"
18162   [(clobber (match_dup 0))
18163    (set (mem:DI (pre_dec:DI (reg:DI 7))) (match_dup 0))])
18164
18165 (define_peephole2
18166   [(match_scratch:DI 0 "r")
18167    (parallel [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -16)))
18168               (clobber (reg:CC 17))])]
18169   "optimize_size || !TARGET_SUB_ESP_8"
18170   [(clobber (match_dup 0))
18171    (set (mem:DI (pre_dec:DI (reg:DI 7))) (match_dup 0))
18172    (set (mem:DI (pre_dec:DI (reg:DI 7))) (match_dup 0))])
18173
18174 ;; Convert epilogue deallocator to pop.
18175 (define_peephole2
18176   [(match_scratch:DI 0 "r")
18177    (parallel [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))
18178               (clobber (reg:CC 17))
18179               (clobber (mem:BLK (scratch)))])]
18180   "optimize_size || !TARGET_ADD_ESP_4"
18181   [(parallel [(set (match_dup 0) (mem:DI (reg:DI 7)))
18182               (set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))
18183               (clobber (mem:BLK (scratch)))])]
18184   "")
18185
18186 ;; Two pops case is tricky, since pop causes dependency on destination register.
18187 ;; We use two registers if available.
18188 (define_peephole2
18189   [(match_scratch:DI 0 "r")
18190    (match_scratch:DI 1 "r")
18191    (parallel [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 16)))
18192               (clobber (reg:CC 17))
18193               (clobber (mem:BLK (scratch)))])]
18194   "optimize_size || !TARGET_ADD_ESP_8"
18195   [(parallel [(set (match_dup 0) (mem:DI (reg:DI 7)))
18196               (set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))
18197               (clobber (mem:BLK (scratch)))])
18198    (parallel [(set (match_dup 1) (mem:DI (reg:DI 7)))
18199               (set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))])]
18200   "")
18201
18202 (define_peephole2
18203   [(match_scratch:DI 0 "r")
18204    (parallel [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 16)))
18205               (clobber (reg:CC 17))
18206               (clobber (mem:BLK (scratch)))])]
18207   "optimize_size"
18208   [(parallel [(set (match_dup 0) (mem:DI (reg:DI 7)))
18209               (set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))
18210               (clobber (mem:BLK (scratch)))])
18211    (parallel [(set (match_dup 0) (mem:DI (reg:DI 7)))
18212               (set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))])]
18213   "")
18214
18215 ;; Convert esp additions to pop.
18216 (define_peephole2
18217   [(match_scratch:DI 0 "r")
18218    (parallel [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))
18219               (clobber (reg:CC 17))])]
18220   ""
18221   [(parallel [(set (match_dup 0) (mem:DI (reg:DI 7)))
18222               (set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))])]
18223   "")
18224
18225 ;; Two pops case is tricky, since pop causes dependency on destination register.
18226 ;; We use two registers if available.
18227 (define_peephole2
18228   [(match_scratch:DI 0 "r")
18229    (match_scratch:DI 1 "r")
18230    (parallel [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 16)))
18231               (clobber (reg:CC 17))])]
18232   ""
18233   [(parallel [(set (match_dup 0) (mem:DI (reg:DI 7)))
18234               (set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))])
18235    (parallel [(set (match_dup 1) (mem:DI (reg:DI 7)))
18236               (set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))])]
18237   "")
18238
18239 (define_peephole2
18240   [(match_scratch:DI 0 "r")
18241    (parallel [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 16)))
18242               (clobber (reg:CC 17))])]
18243   "optimize_size"
18244   [(parallel [(set (match_dup 0) (mem:DI (reg:DI 7)))
18245               (set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))])
18246    (parallel [(set (match_dup 0) (mem:DI (reg:DI 7)))
18247               (set (reg:DI 7) (plus:DI (reg:DI 7) (const_int 8)))])]
18248   "")
18249 \f
18250 ;; Imul $32bit_imm, mem, reg is vector decoded, while
18251 ;; imul $32bit_imm, reg, reg is direct decoded.
18252 (define_peephole2
18253   [(match_scratch:DI 3 "r")
18254    (parallel [(set (match_operand:DI 0 "register_operand" "")
18255                    (mult:DI (match_operand:DI 1 "memory_operand" "")
18256                             (match_operand:DI 2 "immediate_operand" "")))
18257               (clobber (reg:CC 17))])]
18258   "TARGET_K8 && !optimize_size
18259    && (GET_CODE (operands[2]) != CONST_INT
18260        || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
18261   [(set (match_dup 3) (match_dup 1))
18262    (parallel [(set (match_dup 0) (mult:DI (match_dup 3) (match_dup 2)))
18263               (clobber (reg:CC 17))])]
18264 "")
18265
18266 (define_peephole2
18267   [(match_scratch:SI 3 "r")
18268    (parallel [(set (match_operand:SI 0 "register_operand" "")
18269                    (mult:SI (match_operand:SI 1 "memory_operand" "")
18270                             (match_operand:SI 2 "immediate_operand" "")))
18271               (clobber (reg:CC 17))])]
18272   "TARGET_K8 && !optimize_size
18273    && (GET_CODE (operands[2]) != CONST_INT
18274        || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
18275   [(set (match_dup 3) (match_dup 1))
18276    (parallel [(set (match_dup 0) (mult:SI (match_dup 3) (match_dup 2)))
18277               (clobber (reg:CC 17))])]
18278 "")
18279
18280 (define_peephole2
18281   [(match_scratch:SI 3 "r")
18282    (parallel [(set (match_operand:DI 0 "register_operand" "")
18283                    (zero_extend:DI
18284                      (mult:SI (match_operand:SI 1 "memory_operand" "")
18285                               (match_operand:SI 2 "immediate_operand" ""))))
18286               (clobber (reg:CC 17))])]
18287   "TARGET_K8 && !optimize_size
18288    && (GET_CODE (operands[2]) != CONST_INT
18289        || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
18290   [(set (match_dup 3) (match_dup 1))
18291    (parallel [(set (match_dup 0) (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
18292               (clobber (reg:CC 17))])]
18293 "")
18294
18295 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
18296 ;; Convert it into imul reg, reg
18297 ;; It would be better to force assembler to encode instruction using long
18298 ;; immediate, but there is apparently no way to do so.
18299 (define_peephole2
18300   [(parallel [(set (match_operand:DI 0 "register_operand" "")
18301                    (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
18302                             (match_operand:DI 2 "const_int_operand" "")))
18303               (clobber (reg:CC 17))])
18304    (match_scratch:DI 3 "r")]
18305   "TARGET_K8 && !optimize_size
18306    && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')"
18307   [(set (match_dup 3) (match_dup 2))
18308    (parallel [(set (match_dup 0) (mult:DI (match_dup 0) (match_dup 3)))
18309               (clobber (reg:CC 17))])]
18310 {
18311   if (!rtx_equal_p (operands[0], operands[1]))
18312     emit_move_insn (operands[0], operands[1]);
18313 })
18314
18315 (define_peephole2
18316   [(parallel [(set (match_operand:SI 0 "register_operand" "")
18317                    (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
18318                             (match_operand:SI 2 "const_int_operand" "")))
18319               (clobber (reg:CC 17))])
18320    (match_scratch:SI 3 "r")]
18321   "TARGET_K8 && !optimize_size
18322    && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')"
18323   [(set (match_dup 3) (match_dup 2))
18324    (parallel [(set (match_dup 0) (mult:SI (match_dup 0) (match_dup 3)))
18325               (clobber (reg:CC 17))])]
18326 {
18327   if (!rtx_equal_p (operands[0], operands[1]))
18328     emit_move_insn (operands[0], operands[1]);
18329 })
18330
18331 (define_peephole2
18332   [(parallel [(set (match_operand:HI 0 "register_operand" "")
18333                    (mult:HI (match_operand:HI 1 "nonimmediate_operand" "")
18334                             (match_operand:HI 2 "immediate_operand" "")))
18335               (clobber (reg:CC 17))])
18336    (match_scratch:HI 3 "r")]
18337   "TARGET_K8 && !optimize_size"
18338   [(set (match_dup 3) (match_dup 2))
18339    (parallel [(set (match_dup 0) (mult:HI (match_dup 0) (match_dup 3)))
18340               (clobber (reg:CC 17))])]
18341 {
18342   if (!rtx_equal_p (operands[0], operands[1]))
18343     emit_move_insn (operands[0], operands[1]);
18344 })
18345 \f
18346 ;; Call-value patterns last so that the wildcard operand does not
18347 ;; disrupt insn-recog's switch tables.
18348
18349 (define_insn "*call_value_pop_0"
18350   [(set (match_operand 0 "" "")
18351         (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
18352               (match_operand:SI 2 "" "")))
18353    (set (reg:SI 7) (plus:SI (reg:SI 7)
18354                             (match_operand:SI 3 "immediate_operand" "")))]
18355   "!TARGET_64BIT"
18356 {
18357   if (SIBLING_CALL_P (insn))
18358     return "jmp\t%P1";
18359   else
18360     return "call\t%P1";
18361 }
18362   [(set_attr "type" "callv")])
18363
18364 (define_insn "*call_value_pop_1"
18365   [(set (match_operand 0 "" "")
18366         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
18367               (match_operand:SI 2 "" "")))
18368    (set (reg:SI 7) (plus:SI (reg:SI 7)
18369                             (match_operand:SI 3 "immediate_operand" "i")))]
18370   "!TARGET_64BIT"
18371 {
18372   if (constant_call_address_operand (operands[1], QImode))
18373     {
18374       if (SIBLING_CALL_P (insn))
18375         return "jmp\t%P1";
18376       else
18377         return "call\t%P1";
18378     }
18379   if (SIBLING_CALL_P (insn))
18380     return "jmp\t%A1";
18381   else
18382     return "call\t%A1";
18383 }
18384   [(set_attr "type" "callv")])
18385
18386 (define_insn "*call_value_0"
18387   [(set (match_operand 0 "" "")
18388         (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
18389               (match_operand:SI 2 "" "")))]
18390   "!TARGET_64BIT"
18391 {
18392   if (SIBLING_CALL_P (insn))
18393     return "jmp\t%P1";
18394   else
18395     return "call\t%P1";
18396 }
18397   [(set_attr "type" "callv")])
18398
18399 (define_insn "*call_value_0_rex64"
18400   [(set (match_operand 0 "" "")
18401         (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
18402               (match_operand:DI 2 "const_int_operand" "")))]
18403   "TARGET_64BIT"
18404 {
18405   if (SIBLING_CALL_P (insn))
18406     return "jmp\t%P1";
18407   else
18408     return "call\t%P1";
18409 }
18410   [(set_attr "type" "callv")])
18411
18412 (define_insn "*call_value_1"
18413   [(set (match_operand 0 "" "")
18414         (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
18415               (match_operand:SI 2 "" "")))]
18416   "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
18417 {
18418   if (constant_call_address_operand (operands[1], QImode))
18419     return "call\t%P1";
18420   return "call\t%A1";
18421 }
18422   [(set_attr "type" "callv")])
18423
18424 (define_insn "*sibcall_value_1"
18425   [(set (match_operand 0 "" "")
18426         (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "s,c,d,a"))
18427               (match_operand:SI 2 "" "")))]
18428   "SIBLING_CALL_P (insn) && !TARGET_64BIT"
18429 {
18430   if (constant_call_address_operand (operands[1], QImode))
18431     return "jmp\t%P1";
18432   return "jmp\t%A1";
18433 }
18434   [(set_attr "type" "callv")])
18435
18436 (define_insn "*call_value_1_rex64"
18437   [(set (match_operand 0 "" "")
18438         (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rsm"))
18439               (match_operand:DI 2 "" "")))]
18440   "!SIBLING_CALL_P (insn) && TARGET_64BIT"
18441 {
18442   if (constant_call_address_operand (operands[1], QImode))
18443     return "call\t%P1";
18444   return "call\t%A1";
18445 }
18446   [(set_attr "type" "callv")])
18447
18448 (define_insn "*sibcall_value_1_rex64"
18449   [(set (match_operand 0 "" "")
18450         (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
18451               (match_operand:DI 2 "" "")))]
18452   "SIBLING_CALL_P (insn) && TARGET_64BIT"
18453   "jmp\t%P1"
18454   [(set_attr "type" "callv")])
18455
18456 (define_insn "*sibcall_value_1_rex64_v"
18457   [(set (match_operand 0 "" "")
18458         (call (mem:QI (reg:DI 40))
18459               (match_operand:DI 1 "" "")))]
18460   "SIBLING_CALL_P (insn) && TARGET_64BIT"
18461   "jmp\t*%%r11"
18462   [(set_attr "type" "callv")])
18463 \f
18464 (define_insn "trap"
18465   [(trap_if (const_int 1) (const_int 5))]
18466   ""
18467   "int\t$5")
18468
18469 ;;; ix86 doesn't have conditional trap instructions, but we fake them
18470 ;;; for the sake of bounds checking.  By emitting bounds checks as
18471 ;;; conditional traps rather than as conditional jumps around
18472 ;;; unconditional traps we avoid introducing spurious basic-block
18473 ;;; boundaries and facilitate elimination of redundant checks.  In
18474 ;;; honor of the too-inflexible-for-BPs `bound' instruction, we use
18475 ;;; interrupt 5.
18476 ;;; 
18477 ;;; FIXME: Static branch prediction rules for ix86 are such that
18478 ;;; forward conditional branches predict as untaken.  As implemented
18479 ;;; below, pseudo conditional traps violate that rule.  We should use
18480 ;;; .pushsection/.popsection to place all of the `int 5's in a special
18481 ;;; section loaded at the end of the text segment and branch forward
18482 ;;; there on bounds-failure, and then jump back immediately (in case
18483 ;;; the system chooses to ignore bounds violations, or to report
18484 ;;; violations and continue execution).
18485
18486 (define_expand "conditional_trap"
18487   [(trap_if (match_operator 0 "comparison_operator"
18488              [(match_dup 2) (const_int 0)])
18489             (match_operand 1 "const_int_operand" ""))]
18490   ""
18491 {
18492   emit_insn (gen_rtx_TRAP_IF (VOIDmode,
18493                               ix86_expand_compare (GET_CODE (operands[0]),
18494                                                    NULL, NULL),
18495                               operands[1]));
18496   DONE;
18497 })
18498
18499 (define_insn "*conditional_trap_1"
18500   [(trap_if (match_operator 0 "comparison_operator"
18501              [(reg 17) (const_int 0)])
18502             (match_operand 1 "const_int_operand" ""))]
18503   ""
18504 {
18505   operands[2] = gen_label_rtx ();
18506   output_asm_insn ("j%c0\t%l2\; int\t%1", operands);
18507   (*targetm.asm_out.internal_label) (asm_out_file, "L",
18508                              CODE_LABEL_NUMBER (operands[2]));
18509   RET;
18510 })
18511
18512         ;; Pentium III SIMD instructions.
18513
18514 ;; Moves for SSE/MMX regs.
18515
18516 (define_insn "*movv4sf_internal"
18517   [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,x,m")
18518         (match_operand:V4SF 1 "vector_move_operand" "C,xm,x"))]
18519   "TARGET_SSE
18520    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
18521   "@
18522     xorps\t%0, %0
18523     movaps\t{%1, %0|%0, %1}
18524     movaps\t{%1, %0|%0, %1}"
18525   [(set_attr "type" "ssemov")
18526    (set_attr "mode" "V4SF")])
18527
18528 (define_split
18529   [(set (match_operand:V4SF 0 "register_operand" "")
18530         (match_operand:V4SF 1 "zero_extended_scalar_load_operand" ""))]
18531   "TARGET_SSE && reload_completed"
18532   [(set (match_dup 0)
18533         (vec_merge:V4SF
18534          (vec_duplicate:V4SF (match_dup 1))
18535          (match_dup 2)
18536          (const_int 1)))]
18537 {
18538   operands[1] = simplify_gen_subreg (SFmode, operands[1], V4SFmode, 0);
18539   operands[2] = CONST0_RTX (V4SFmode);
18540 })
18541
18542 (define_insn "*movv4si_internal"
18543   [(set (match_operand:V4SI 0 "nonimmediate_operand" "=x,x,m")
18544         (match_operand:V4SI 1 "vector_move_operand" "C,xm,x"))]
18545   "TARGET_SSE
18546    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
18547 {
18548   switch (which_alternative)
18549     {
18550     case 0:
18551       if (get_attr_mode (insn) == MODE_V4SF)
18552         return "xorps\t%0, %0";
18553       else
18554         return "pxor\t%0, %0";
18555     case 1:
18556     case 2:
18557       if (get_attr_mode (insn) == MODE_V4SF)
18558         return "movaps\t{%1, %0|%0, %1}";
18559       else
18560         return "movdqa\t{%1, %0|%0, %1}";
18561     default:
18562       abort ();
18563     }
18564 }
18565   [(set_attr "type" "ssemov")
18566    (set (attr "mode")
18567         (cond [(eq_attr "alternative" "0,1")
18568                  (if_then_else
18569                    (ne (symbol_ref "optimize_size")
18570                        (const_int 0))
18571                    (const_string "V4SF")
18572                    (const_string "TI"))
18573                (eq_attr "alternative" "2")
18574                  (if_then_else
18575                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
18576                             (const_int 0))
18577                         (ne (symbol_ref "optimize_size")
18578                             (const_int 0)))
18579                    (const_string "V4SF")
18580                    (const_string "TI"))]
18581                (const_string "TI")))])
18582
18583 (define_insn "*movv2di_internal"
18584   [(set (match_operand:V2DI 0 "nonimmediate_operand" "=x,x,m")
18585         (match_operand:V2DI 1 "vector_move_operand" "C,xm,x"))]
18586   "TARGET_SSE
18587    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
18588 {
18589   switch (which_alternative)
18590     {
18591     case 0:
18592       if (get_attr_mode (insn) == MODE_V4SF)
18593         return "xorps\t%0, %0";
18594       else
18595         return "pxor\t%0, %0";
18596     case 1:
18597     case 2:
18598       if (get_attr_mode (insn) == MODE_V4SF)
18599         return "movaps\t{%1, %0|%0, %1}";
18600       else
18601         return "movdqa\t{%1, %0|%0, %1}";
18602     default:
18603       abort ();
18604     }
18605 }
18606   [(set_attr "type" "ssemov")
18607    (set (attr "mode")
18608         (cond [(eq_attr "alternative" "0,1")
18609                  (if_then_else
18610                    (ne (symbol_ref "optimize_size")
18611                        (const_int 0))
18612                    (const_string "V4SF")
18613                    (const_string "TI"))
18614                (eq_attr "alternative" "2")
18615                  (if_then_else
18616                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
18617                             (const_int 0))
18618                         (ne (symbol_ref "optimize_size")
18619                             (const_int 0)))
18620                    (const_string "V4SF")
18621                    (const_string "TI"))]
18622                (const_string "TI")))])
18623
18624 (define_split
18625   [(set (match_operand:V2DF 0 "register_operand" "")
18626         (match_operand:V2DF 1 "zero_extended_scalar_load_operand" ""))]
18627   "TARGET_SSE2 && reload_completed"
18628   [(set (match_dup 0)
18629         (vec_merge:V2DF
18630          (vec_duplicate:V2DF (match_dup 1))
18631          (match_dup 2)
18632          (const_int 1)))]
18633 {
18634   operands[1] = simplify_gen_subreg (DFmode, operands[1], V2DFmode, 0);
18635   operands[2] = CONST0_RTX (V2DFmode);
18636 })
18637
18638 (define_insn "*movv2si_internal"
18639   [(set (match_operand:V2SI 0 "nonimmediate_operand"
18640                                         "=y,y ,m,!y,!*Y,*x,?*x,?m")
18641         (match_operand:V2SI 1 "vector_move_operand"
18642                                         "C ,ym,y,*Y,y  ,C ,*xm,*x"))]
18643   "TARGET_MMX
18644    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
18645   "@
18646     pxor\t%0, %0
18647     movq\t{%1, %0|%0, %1}
18648     movq\t{%1, %0|%0, %1}
18649     movdq2q\t{%1, %0|%0, %1}
18650     movq2dq\t{%1, %0|%0, %1}
18651     pxor\t%0, %0
18652     movq\t{%1, %0|%0, %1}
18653     movq\t{%1, %0|%0, %1}"
18654   [(set_attr "type" "mmxmov,mmxmov,mmxmov,ssecvt,ssecvt,ssemov,ssemov,ssemov")
18655    (set_attr "mode" "DI")])
18656
18657 (define_insn "*movv4hi_internal"
18658   [(set (match_operand:V4HI 0 "nonimmediate_operand"
18659                                         "=y,y ,m,!y,!*Y,*x,?*x,?m")
18660         (match_operand:V4HI 1 "vector_move_operand"
18661                                         "C ,ym,y,*Y,y  ,C ,*xm,*x"))]
18662   "TARGET_MMX
18663    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
18664   "@
18665     pxor\t%0, %0
18666     movq\t{%1, %0|%0, %1}
18667     movq\t{%1, %0|%0, %1}
18668     movdq2q\t{%1, %0|%0, %1}
18669     movq2dq\t{%1, %0|%0, %1}
18670     pxor\t%0, %0
18671     movq\t{%1, %0|%0, %1}
18672     movq\t{%1, %0|%0, %1}"
18673   [(set_attr "type" "mmxmov,mmxmov,mmxmov,ssecvt,ssecvt,ssemov,ssemov,ssemov")
18674    (set_attr "mode" "DI")])
18675
18676 (define_insn "*movv8qi_internal"
18677   [(set (match_operand:V8QI 0 "nonimmediate_operand"
18678                                         "=y,y ,m,!y,!*Y,*x,?*x,?m")
18679         (match_operand:V8QI 1 "vector_move_operand"
18680                                         "C ,ym,y,*Y,y  ,C ,*xm,*x"))]
18681   "TARGET_MMX
18682    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
18683   "@
18684     pxor\t%0, %0
18685     movq\t{%1, %0|%0, %1}
18686     movq\t{%1, %0|%0, %1}
18687     movdq2q\t{%1, %0|%0, %1}
18688     movq2dq\t{%1, %0|%0, %1}
18689     pxor\t%0, %0
18690     movq\t{%1, %0|%0, %1}
18691     movq\t{%1, %0|%0, %1}"
18692   [(set_attr "type" "mmxmov,mmxmov,mmxmov,ssecvt,ssecvt,ssemov,ssemov,ssemov")
18693    (set_attr "mode" "DI")])
18694
18695 (define_insn "*movv2sf_internal"
18696   [(set (match_operand:V2SF 0 "nonimmediate_operand"
18697                                         "=y,y ,m,!y,!*Y,*x,?*x,?m")
18698         (match_operand:V2SF 1 "vector_move_operand"
18699                                         "C ,ym,y,*Y,y  ,C ,*xm,*x"))]
18700   "TARGET_MMX
18701    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
18702   "@
18703     pxor\t%0, %0
18704     movq\t{%1, %0|%0, %1}
18705     movq\t{%1, %0|%0, %1}
18706     movdq2q\t{%1, %0|%0, %1}
18707     movq2dq\t{%1, %0|%0, %1}
18708     xorps\t%0, %0
18709     movq\t{%1, %0|%0, %1}
18710     movq\t{%1, %0|%0, %1}"
18711   [(set_attr "type" "mmxmov,mmxmov,mmxmov,ssecvt,ssecvt,ssemov,ssemov,ssemov")
18712    (set_attr "mode" "DI")])
18713
18714 (define_expand "movti"
18715   [(set (match_operand:TI 0 "nonimmediate_operand" "")
18716         (match_operand:TI 1 "nonimmediate_operand" ""))]
18717   "TARGET_SSE || TARGET_64BIT"
18718 {
18719   if (TARGET_64BIT)
18720     ix86_expand_move (TImode, operands);
18721   else
18722     ix86_expand_vector_move (TImode, operands);
18723   DONE;
18724 })
18725
18726 (define_expand "movtf"
18727   [(set (match_operand:TF 0 "nonimmediate_operand" "")
18728         (match_operand:TF 1 "nonimmediate_operand" ""))]
18729   "TARGET_64BIT"
18730 {
18731   ix86_expand_move (TFmode, operands);
18732   DONE;
18733 })
18734
18735 (define_insn "*movv2df_internal"
18736   [(set (match_operand:V2DF 0 "nonimmediate_operand" "=x,x,m")
18737         (match_operand:V2DF 1 "vector_move_operand" "C,xm,x"))]
18738   "TARGET_SSE
18739    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
18740 {
18741   switch (which_alternative)
18742     {
18743     case 0:
18744       if (get_attr_mode (insn) == MODE_V4SF)
18745         return "xorps\t%0, %0";
18746       else
18747         return "xorpd\t%0, %0";
18748     case 1:
18749     case 2:
18750       if (get_attr_mode (insn) == MODE_V4SF)
18751         return "movaps\t{%1, %0|%0, %1}";
18752       else
18753         return "movapd\t{%1, %0|%0, %1}";
18754     default:
18755       abort ();
18756     }
18757 }
18758   [(set_attr "type" "ssemov")
18759    (set (attr "mode")
18760         (cond [(eq (symbol_ref "TARGET_SSE2") (const_int 0))
18761                  (const_string "V4SF")
18762                (eq_attr "alternative" "0,1")
18763                  (if_then_else
18764                    (ne (symbol_ref "optimize_size")
18765                        (const_int 0))
18766                    (const_string "V4SF")
18767                    (const_string "V2DF"))
18768                (eq_attr "alternative" "2")
18769                  (if_then_else
18770                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
18771                             (const_int 0))
18772                         (ne (symbol_ref "optimize_size")
18773                             (const_int 0)))
18774                    (const_string "V4SF")
18775                    (const_string "V2DF"))]
18776                (const_string "V2DF")))])
18777
18778 (define_insn "*movv8hi_internal"
18779   [(set (match_operand:V8HI 0 "nonimmediate_operand" "=x,x,m")
18780         (match_operand:V8HI 1 "vector_move_operand" "C,xm,x"))]
18781   "TARGET_SSE
18782    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
18783 {
18784   switch (which_alternative)
18785     {
18786     case 0:
18787       if (get_attr_mode (insn) == MODE_V4SF)
18788         return "xorps\t%0, %0";
18789       else
18790         return "pxor\t%0, %0";
18791     case 1:
18792     case 2:
18793       if (get_attr_mode (insn) == MODE_V4SF)
18794         return "movaps\t{%1, %0|%0, %1}";
18795       else
18796         return "movdqa\t{%1, %0|%0, %1}";
18797     default:
18798       abort ();
18799     }
18800 }
18801   [(set_attr "type" "ssemov")
18802    (set (attr "mode")
18803         (cond [(eq_attr "alternative" "0,1")
18804                  (if_then_else
18805                    (ne (symbol_ref "optimize_size")
18806                        (const_int 0))
18807                    (const_string "V4SF")
18808                    (const_string "TI"))
18809                (eq_attr "alternative" "2")
18810                  (if_then_else
18811                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
18812                             (const_int 0))
18813                         (ne (symbol_ref "optimize_size")
18814                             (const_int 0)))
18815                    (const_string "V4SF")
18816                    (const_string "TI"))]
18817                (const_string "TI")))])
18818
18819 (define_insn "*movv16qi_internal"
18820   [(set (match_operand:V16QI 0 "nonimmediate_operand" "=x,x,m")
18821         (match_operand:V16QI 1 "vector_move_operand" "C,xm,x"))]
18822   "TARGET_SSE
18823    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
18824 {
18825   switch (which_alternative)
18826     {
18827     case 0:
18828       if (get_attr_mode (insn) == MODE_V4SF)
18829         return "xorps\t%0, %0";
18830       else
18831         return "pxor\t%0, %0";
18832     case 1:
18833     case 2:
18834       if (get_attr_mode (insn) == MODE_V4SF)
18835         return "movaps\t{%1, %0|%0, %1}";
18836       else
18837         return "movdqa\t{%1, %0|%0, %1}";
18838     default:
18839       abort ();
18840     }
18841 }
18842   [(set_attr "type" "ssemov")
18843    (set (attr "mode")
18844         (cond [(eq_attr "alternative" "0,1")
18845                  (if_then_else
18846                    (ne (symbol_ref "optimize_size")
18847                        (const_int 0))
18848                    (const_string "V4SF")
18849                    (const_string "TI"))
18850                (eq_attr "alternative" "2")
18851                  (if_then_else
18852                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
18853                             (const_int 0))
18854                         (ne (symbol_ref "optimize_size")
18855                             (const_int 0)))
18856                    (const_string "V4SF")
18857                    (const_string "TI"))]
18858                (const_string "TI")))])
18859
18860 (define_expand "movv2df"
18861   [(set (match_operand:V2DF 0 "nonimmediate_operand" "")
18862         (match_operand:V2DF 1 "nonimmediate_operand" ""))]
18863   "TARGET_SSE"
18864 {
18865   ix86_expand_vector_move (V2DFmode, operands);
18866   DONE;
18867 })
18868
18869 (define_expand "movv8hi"
18870   [(set (match_operand:V8HI 0 "nonimmediate_operand" "")
18871         (match_operand:V8HI 1 "nonimmediate_operand" ""))]
18872   "TARGET_SSE"
18873 {
18874   ix86_expand_vector_move (V8HImode, operands);
18875   DONE;
18876 })
18877
18878 (define_expand "movv16qi"
18879   [(set (match_operand:V16QI 0 "nonimmediate_operand" "")
18880         (match_operand:V16QI 1 "nonimmediate_operand" ""))]
18881   "TARGET_SSE"
18882 {
18883   ix86_expand_vector_move (V16QImode, operands);
18884   DONE;
18885 })
18886
18887 (define_expand "movv4sf"
18888   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
18889         (match_operand:V4SF 1 "nonimmediate_operand" ""))]
18890   "TARGET_SSE"
18891 {
18892   ix86_expand_vector_move (V4SFmode, operands);
18893   DONE;
18894 })
18895
18896 (define_expand "movv4si"
18897   [(set (match_operand:V4SI 0 "nonimmediate_operand" "")
18898         (match_operand:V4SI 1 "nonimmediate_operand" ""))]
18899   "TARGET_SSE"
18900 {
18901   ix86_expand_vector_move (V4SImode, operands);
18902   DONE;
18903 })
18904
18905 (define_expand "movv2di"
18906   [(set (match_operand:V2DI 0 "nonimmediate_operand" "")
18907         (match_operand:V2DI 1 "nonimmediate_operand" ""))]
18908   "TARGET_SSE"
18909 {
18910   ix86_expand_vector_move (V2DImode, operands);
18911   DONE;
18912 })
18913
18914 (define_expand "movv2si"
18915   [(set (match_operand:V2SI 0 "nonimmediate_operand" "")
18916         (match_operand:V2SI 1 "nonimmediate_operand" ""))]
18917   "TARGET_MMX"
18918 {
18919   ix86_expand_vector_move (V2SImode, operands);
18920   DONE;
18921 })
18922
18923 (define_expand "movv4hi"
18924   [(set (match_operand:V4HI 0 "nonimmediate_operand" "")
18925         (match_operand:V4HI 1 "nonimmediate_operand" ""))]
18926   "TARGET_MMX"
18927 {
18928   ix86_expand_vector_move (V4HImode, operands);
18929   DONE;
18930 })
18931
18932 (define_expand "movv8qi"
18933   [(set (match_operand:V8QI 0 "nonimmediate_operand" "")
18934         (match_operand:V8QI 1 "nonimmediate_operand" ""))]
18935   "TARGET_MMX"
18936 {
18937   ix86_expand_vector_move (V8QImode, operands);
18938   DONE;
18939 })
18940
18941 (define_expand "movv2sf"
18942   [(set (match_operand:V2SF 0 "nonimmediate_operand" "")
18943         (match_operand:V2SF 1 "nonimmediate_operand" ""))]
18944   "TARGET_MMX"
18945 {
18946   ix86_expand_vector_move (V2SFmode, operands);
18947   DONE;
18948 })
18949
18950 (define_insn "*pushti"
18951   [(set (match_operand:TI 0 "push_operand" "=<")
18952         (match_operand:TI 1 "register_operand" "x"))]
18953   "TARGET_SSE"
18954   "#")
18955
18956 (define_insn "*pushv2df"
18957   [(set (match_operand:V2DF 0 "push_operand" "=<")
18958         (match_operand:V2DF 1 "register_operand" "x"))]
18959   "TARGET_SSE"
18960   "#")
18961
18962 (define_insn "*pushv2di"
18963   [(set (match_operand:V2DI 0 "push_operand" "=<")
18964         (match_operand:V2DI 1 "register_operand" "x"))]
18965   "TARGET_SSE"
18966   "#")
18967
18968 (define_insn "*pushv8hi"
18969   [(set (match_operand:V8HI 0 "push_operand" "=<")
18970         (match_operand:V8HI 1 "register_operand" "x"))]
18971   "TARGET_SSE"
18972   "#")
18973
18974 (define_insn "*pushv16qi"
18975   [(set (match_operand:V16QI 0 "push_operand" "=<")
18976         (match_operand:V16QI 1 "register_operand" "x"))]
18977   "TARGET_SSE"
18978   "#")
18979
18980 (define_insn "*pushv4sf"
18981   [(set (match_operand:V4SF 0 "push_operand" "=<")
18982         (match_operand:V4SF 1 "register_operand" "x"))]
18983   "TARGET_SSE"
18984   "#")
18985
18986 (define_insn "*pushv4si"
18987   [(set (match_operand:V4SI 0 "push_operand" "=<")
18988         (match_operand:V4SI 1 "register_operand" "x"))]
18989   "TARGET_SSE"
18990   "#")
18991
18992 (define_insn "*pushv2si"
18993   [(set (match_operand:V2SI 0 "push_operand" "=<")
18994         (match_operand:V2SI 1 "register_operand" "y"))]
18995   "TARGET_MMX"
18996   "#")
18997
18998 (define_insn "*pushv4hi"
18999   [(set (match_operand:V4HI 0 "push_operand" "=<")
19000         (match_operand:V4HI 1 "register_operand" "y"))]
19001   "TARGET_MMX"
19002   "#")
19003
19004 (define_insn "*pushv8qi"
19005   [(set (match_operand:V8QI 0 "push_operand" "=<")
19006         (match_operand:V8QI 1 "register_operand" "y"))]
19007   "TARGET_MMX"
19008   "#")
19009
19010 (define_insn "*pushv2sf"
19011   [(set (match_operand:V2SF 0 "push_operand" "=<")
19012         (match_operand:V2SF 1 "register_operand" "y"))]
19013   "TARGET_MMX"
19014   "#")
19015
19016 (define_split
19017   [(set (match_operand 0 "push_operand" "")
19018         (match_operand 1 "register_operand" ""))]
19019   "!TARGET_64BIT && reload_completed
19020    && (SSE_REG_P (operands[1]) || MMX_REG_P (operands[1]))"
19021   [(set (reg:SI 7) (plus:SI (reg:SI 7) (match_dup 3)))
19022    (set (match_dup 2) (match_dup 1))]
19023   "operands[2] = change_address (operands[0], GET_MODE (operands[0]),
19024                                  stack_pointer_rtx);
19025    operands[3] = GEN_INT (-GET_MODE_SIZE (GET_MODE (operands[0])));")
19026
19027 (define_split
19028   [(set (match_operand 0 "push_operand" "")
19029         (match_operand 1 "register_operand" ""))]
19030   "TARGET_64BIT && reload_completed
19031    && (SSE_REG_P (operands[1]) || MMX_REG_P (operands[1]))"
19032   [(set (reg:DI 7) (plus:DI (reg:DI 7) (match_dup 3)))
19033    (set (match_dup 2) (match_dup 1))]
19034   "operands[2] = change_address (operands[0], GET_MODE (operands[0]),
19035                                  stack_pointer_rtx);
19036    operands[3] = GEN_INT (-GET_MODE_SIZE (GET_MODE (operands[0])));")
19037
19038
19039 (define_insn "*movti_internal"
19040   [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
19041         (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
19042   "TARGET_SSE && !TARGET_64BIT
19043    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
19044 {
19045   switch (which_alternative)
19046     {
19047     case 0:
19048       if (get_attr_mode (insn) == MODE_V4SF)
19049         return "xorps\t%0, %0";
19050       else
19051         return "pxor\t%0, %0";
19052     case 1:
19053     case 2:
19054       if (get_attr_mode (insn) == MODE_V4SF)
19055         return "movaps\t{%1, %0|%0, %1}";
19056       else
19057         return "movdqa\t{%1, %0|%0, %1}";
19058     default:
19059       abort ();
19060     }
19061 }
19062   [(set_attr "type" "ssemov,ssemov,ssemov")
19063    (set (attr "mode")
19064         (cond [(eq_attr "alternative" "0,1")
19065                  (if_then_else
19066                    (ne (symbol_ref "optimize_size")
19067                        (const_int 0))
19068                    (const_string "V4SF")
19069                    (const_string "TI"))
19070                (eq_attr "alternative" "2")
19071                  (if_then_else
19072                    (ne (symbol_ref "optimize_size")
19073                        (const_int 0))
19074                    (const_string "V4SF")
19075                    (const_string "TI"))]
19076                (const_string "TI")))])
19077
19078 (define_insn "*movti_rex64"
19079   [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o,x,x,xm")
19080         (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
19081   "TARGET_64BIT
19082    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
19083 {
19084   switch (which_alternative)
19085     {
19086     case 0:
19087     case 1:
19088       return "#";
19089     case 2:
19090       if (get_attr_mode (insn) == MODE_V4SF)
19091         return "xorps\t%0, %0";
19092       else
19093         return "pxor\t%0, %0";
19094     case 3:
19095     case 4:
19096       if (get_attr_mode (insn) == MODE_V4SF)
19097         return "movaps\t{%1, %0|%0, %1}";
19098       else
19099         return "movdqa\t{%1, %0|%0, %1}";
19100     default:
19101       abort ();
19102     }
19103 }
19104   [(set_attr "type" "*,*,ssemov,ssemov,ssemov")
19105    (set (attr "mode")
19106         (cond [(eq_attr "alternative" "2,3")
19107                  (if_then_else
19108                    (ne (symbol_ref "optimize_size")
19109                        (const_int 0))
19110                    (const_string "V4SF")
19111                    (const_string "TI"))
19112                (eq_attr "alternative" "4")
19113                  (if_then_else
19114                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
19115                             (const_int 0))
19116                         (ne (symbol_ref "optimize_size")
19117                             (const_int 0)))
19118                    (const_string "V4SF")
19119                    (const_string "TI"))]
19120                (const_string "DI")))])
19121
19122 (define_insn "*movtf_rex64"
19123   [(set (match_operand:TF 0 "nonimmediate_operand" "=r,o,x,x,xm")
19124         (match_operand:TF 1 "general_operand" "riFo,riF,C,xm,x"))]
19125   "TARGET_64BIT
19126    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
19127 {
19128   switch (which_alternative)
19129     {
19130     case 0:
19131     case 1:
19132       return "#";
19133     case 2:
19134       if (get_attr_mode (insn) == MODE_V4SF)
19135         return "xorps\t%0, %0";
19136       else
19137         return "pxor\t%0, %0";
19138     case 3:
19139     case 4:
19140       if (get_attr_mode (insn) == MODE_V4SF)
19141         return "movaps\t{%1, %0|%0, %1}";
19142       else
19143         return "movdqa\t{%1, %0|%0, %1}";
19144     default:
19145       abort ();
19146     }
19147 }
19148   [(set_attr "type" "*,*,ssemov,ssemov,ssemov")
19149    (set (attr "mode")
19150         (cond [(eq_attr "alternative" "2,3")
19151                  (if_then_else
19152                    (ne (symbol_ref "optimize_size")
19153                        (const_int 0))
19154                    (const_string "V4SF")
19155                    (const_string "TI"))
19156                (eq_attr "alternative" "4")
19157                  (if_then_else
19158                    (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
19159                             (const_int 0))
19160                         (ne (symbol_ref "optimize_size")
19161                             (const_int 0)))
19162                    (const_string "V4SF")
19163                    (const_string "TI"))]
19164                (const_string "DI")))])
19165
19166 (define_split
19167   [(set (match_operand:TI 0 "nonimmediate_operand" "")
19168         (match_operand:TI 1 "general_operand" ""))]
19169   "reload_completed && !SSE_REG_P (operands[0])
19170    && !SSE_REG_P (operands[1])"
19171   [(const_int 0)]
19172   "ix86_split_long_move (operands); DONE;")
19173
19174 (define_split
19175   [(set (match_operand:TF 0 "nonimmediate_operand" "")
19176         (match_operand:TF 1 "general_operand" ""))]
19177   "reload_completed && !SSE_REG_P (operands[0])
19178    && !SSE_REG_P (operands[1])"
19179   [(const_int 0)]
19180   "ix86_split_long_move (operands); DONE;")
19181
19182 ;; These two patterns are useful for specifying exactly whether to use
19183 ;; movaps or movups
19184 (define_expand "sse_movaps"
19185   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
19186         (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "")]
19187                      UNSPEC_MOVA))]
19188   "TARGET_SSE"
19189 {
19190   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
19191     {
19192       rtx tmp = gen_reg_rtx (V4SFmode);
19193       emit_insn (gen_sse_movaps (tmp, operands[1]));
19194       emit_move_insn (operands[0], tmp);
19195       DONE;
19196     }
19197 })
19198
19199 (define_insn "*sse_movaps_1"
19200   [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,m")
19201         (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "xm,x")]
19202                      UNSPEC_MOVA))]
19203   "TARGET_SSE
19204    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
19205   "movaps\t{%1, %0|%0, %1}"
19206   [(set_attr "type" "ssemov,ssemov")
19207    (set_attr "mode" "V4SF")])
19208
19209 (define_expand "sse_movups"
19210   [(set (match_operand:V4SF 0 "nonimmediate_operand" "")
19211         (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "")]
19212                      UNSPEC_MOVU))]
19213   "TARGET_SSE"
19214 {
19215   if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
19216     {
19217       rtx tmp = gen_reg_rtx (V4SFmode);
19218       emit_insn (gen_sse_movups (tmp, operands[1]));
19219       emit_move_insn (operands[0], tmp);
19220       DONE;
19221     }
19222 })
19223
19224 (define_insn "*sse_movups_1"
19225   [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,m")
19226         (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "xm,x")]
19227                      UNSPEC_MOVU))]
19228   "TARGET_SSE
19229    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
19230   "movups\t{%1, %0|%0, %1}"
19231   [(set_attr "type" "ssecvt,ssecvt")
19232    (set_attr "mode" "V4SF")])
19233
19234 ;; SSE Strange Moves.
19235
19236 (define_insn "sse_movmskps"
19237   [(set (match_operand:SI 0 "register_operand" "=r")
19238         (unspec:SI [(match_operand:V4SF 1 "register_operand" "x")]
19239                    UNSPEC_MOVMSK))]
19240   "TARGET_SSE"
19241   "movmskps\t{%1, %0|%0, %1}"
19242   [(set_attr "type" "ssecvt")
19243    (set_attr "mode" "V4SF")])
19244
19245 (define_insn "mmx_pmovmskb"
19246   [(set (match_operand:SI 0 "register_operand" "=r")
19247         (unspec:SI [(match_operand:V8QI 1 "register_operand" "y")]
19248                    UNSPEC_MOVMSK))]
19249   "TARGET_SSE || TARGET_3DNOW_A"
19250   "pmovmskb\t{%1, %0|%0, %1}"
19251   [(set_attr "type" "ssecvt")
19252    (set_attr "mode" "V4SF")])
19253
19254
19255 (define_insn "mmx_maskmovq"
19256   [(set (mem:V8QI (match_operand:SI 0 "register_operand" "D"))
19257         (unspec:V8QI [(match_operand:V8QI 1 "register_operand" "y")
19258                       (match_operand:V8QI 2 "register_operand" "y")]
19259                      UNSPEC_MASKMOV))]
19260   "(TARGET_SSE || TARGET_3DNOW_A) && !TARGET_64BIT"
19261   ;; @@@ check ordering of operands in intel/nonintel syntax
19262   "maskmovq\t{%2, %1|%1, %2}"
19263   [(set_attr "type" "mmxcvt")
19264    (set_attr "mode" "DI")])
19265
19266 (define_insn "mmx_maskmovq_rex"
19267   [(set (mem:V8QI (match_operand:DI 0 "register_operand" "D"))
19268         (unspec:V8QI [(match_operand:V8QI 1 "register_operand" "y")
19269                       (match_operand:V8QI 2 "register_operand" "y")]
19270                      UNSPEC_MASKMOV))]
19271   "(TARGET_SSE || TARGET_3DNOW_A) && TARGET_64BIT"
19272   ;; @@@ check ordering of operands in intel/nonintel syntax
19273   "maskmovq\t{%2, %1|%1, %2}"
19274   [(set_attr "type" "mmxcvt")
19275    (set_attr "mode" "DI")])
19276
19277 (define_insn "sse_movntv4sf"
19278   [(set (match_operand:V4SF 0 "memory_operand" "=m")
19279         (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "x")]
19280                      UNSPEC_MOVNT))]
19281   "TARGET_SSE"
19282   "movntps\t{%1, %0|%0, %1}"
19283   [(set_attr "type" "ssemov")
19284    (set_attr "mode" "V4SF")])
19285
19286 (define_insn "sse_movntdi"
19287   [(set (match_operand:DI 0 "memory_operand" "=m")
19288         (unspec:DI [(match_operand:DI 1 "register_operand" "y")]
19289                    UNSPEC_MOVNT))]
19290   "TARGET_SSE || TARGET_3DNOW_A"
19291   "movntq\t{%1, %0|%0, %1}"
19292   [(set_attr "type" "mmxmov")
19293    (set_attr "mode" "DI")])
19294
19295 (define_insn "sse_movhlps"
19296   [(set (match_operand:V4SF 0 "register_operand" "=x")
19297         (vec_merge:V4SF
19298          (match_operand:V4SF 1 "register_operand" "0")
19299          (vec_select:V4SF (match_operand:V4SF 2 "register_operand" "x")
19300                           (parallel [(const_int 2)
19301                                      (const_int 3)
19302                                      (const_int 0)
19303                                      (const_int 1)]))
19304          (const_int 3)))]
19305   "TARGET_SSE"
19306   "movhlps\t{%2, %0|%0, %2}"
19307   [(set_attr "type" "ssecvt")
19308    (set_attr "mode" "V4SF")])
19309
19310 (define_insn "sse_movlhps"
19311   [(set (match_operand:V4SF 0 "register_operand" "=x")
19312         (vec_merge:V4SF
19313          (match_operand:V4SF 1 "register_operand" "0")
19314          (vec_select:V4SF (match_operand:V4SF 2 "register_operand" "x")
19315                           (parallel [(const_int 2)
19316                                      (const_int 3)
19317                                      (const_int 0)
19318                                      (const_int 1)]))
19319          (const_int 12)))]
19320   "TARGET_SSE"
19321   "movlhps\t{%2, %0|%0, %2}"
19322   [(set_attr "type" "ssecvt")
19323    (set_attr "mode" "V4SF")])
19324
19325 (define_insn "sse_movhps"
19326   [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,m")
19327         (vec_merge:V4SF
19328          (match_operand:V4SF 1 "nonimmediate_operand" "0,0")
19329          (match_operand:V4SF 2 "nonimmediate_operand" "m,x")
19330          (const_int 12)))]
19331   "TARGET_SSE
19332    && (GET_CODE (operands[1]) == MEM || GET_CODE (operands[2]) == MEM)"
19333   "movhps\t{%2, %0|%0, %2}"
19334   [(set_attr "type" "ssecvt")
19335    (set_attr "mode" "V4SF")])
19336
19337 (define_insn "sse_movlps"
19338   [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,m")
19339         (vec_merge:V4SF
19340          (match_operand:V4SF 1 "nonimmediate_operand" "0,0")
19341          (match_operand:V4SF 2 "nonimmediate_operand" "m,x")
19342          (const_int 3)))]
19343   "TARGET_SSE
19344    && (GET_CODE (operands[1]) == MEM || GET_CODE (operands[2]) == MEM)"
19345   "movlps\t{%2, %0|%0, %2}"
19346   [(set_attr "type" "ssecvt")
19347    (set_attr "mode" "V4SF")])
19348
19349 (define_expand "sse_loadss"
19350   [(match_operand:V4SF 0 "register_operand" "")
19351    (match_operand:SF 1 "memory_operand" "")]
19352   "TARGET_SSE"
19353 {
19354   emit_insn (gen_sse_loadss_1 (operands[0], operands[1],
19355                                CONST0_RTX (V4SFmode)));
19356   DONE;
19357 })
19358
19359 (define_insn "sse_loadss_1"
19360   [(set (match_operand:V4SF 0 "register_operand" "=x")
19361         (vec_merge:V4SF
19362          (vec_duplicate:V4SF (match_operand:SF 1 "memory_operand" "m"))
19363          (match_operand:V4SF 2 "const0_operand" "X")
19364          (const_int 1)))]
19365   "TARGET_SSE"
19366   "movss\t{%1, %0|%0, %1}"
19367   [(set_attr "type" "ssemov")
19368    (set_attr "mode" "SF")])
19369
19370 (define_insn "sse_movss"
19371   [(set (match_operand:V4SF 0 "register_operand" "=x")
19372         (vec_merge:V4SF
19373          (match_operand:V4SF 1 "register_operand" "0")
19374          (match_operand:V4SF 2 "register_operand" "x")
19375          (const_int 1)))]
19376   "TARGET_SSE"
19377   "movss\t{%2, %0|%0, %2}"
19378   [(set_attr "type" "ssemov")
19379    (set_attr "mode" "SF")])
19380
19381 (define_insn "sse_storess"
19382   [(set (match_operand:SF 0 "memory_operand" "=m")
19383         (vec_select:SF
19384          (match_operand:V4SF 1 "register_operand" "x")
19385          (parallel [(const_int 0)])))]
19386   "TARGET_SSE"
19387   "movss\t{%1, %0|%0, %1}"
19388   [(set_attr "type" "ssemov")
19389    (set_attr "mode" "SF")])
19390
19391 (define_insn "sse_shufps"
19392   [(set (match_operand:V4SF 0 "register_operand" "=x")
19393         (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "0")
19394                       (match_operand:V4SF 2 "nonimmediate_operand" "xm")
19395                       (match_operand:SI 3 "immediate_operand" "i")]
19396                      UNSPEC_SHUFFLE))]
19397   "TARGET_SSE"
19398   ;; @@@ check operand order for intel/nonintel syntax
19399   "shufps\t{%3, %2, %0|%0, %2, %3}"
19400   [(set_attr "type" "ssecvt")
19401    (set_attr "mode" "V4SF")])
19402
19403
19404 ;; SSE arithmetic
19405
19406 (define_insn "addv4sf3"
19407   [(set (match_operand:V4SF 0 "register_operand" "=x")
19408         (plus:V4SF (match_operand:V4SF 1 "register_operand" "0")
19409                    (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
19410   "TARGET_SSE"
19411   "addps\t{%2, %0|%0, %2}"
19412   [(set_attr "type" "sseadd")
19413    (set_attr "mode" "V4SF")])
19414
19415 (define_insn "vmaddv4sf3"
19416   [(set (match_operand:V4SF 0 "register_operand" "=x")
19417         (vec_merge:V4SF
19418          (plus:V4SF (match_operand:V4SF 1 "register_operand" "0")
19419                     (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
19420          (match_dup 1)
19421          (const_int 1)))]
19422   "TARGET_SSE"
19423   "addss\t{%2, %0|%0, %2}"
19424   [(set_attr "type" "sseadd")
19425    (set_attr "mode" "SF")])
19426
19427 (define_insn "subv4sf3"
19428   [(set (match_operand:V4SF 0 "register_operand" "=x")
19429         (minus:V4SF (match_operand:V4SF 1 "register_operand" "0")
19430                     (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
19431   "TARGET_SSE"
19432   "subps\t{%2, %0|%0, %2}"
19433   [(set_attr "type" "sseadd")
19434    (set_attr "mode" "V4SF")])
19435
19436 (define_insn "vmsubv4sf3"
19437   [(set (match_operand:V4SF 0 "register_operand" "=x")
19438         (vec_merge:V4SF
19439          (minus:V4SF (match_operand:V4SF 1 "register_operand" "0")
19440                      (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
19441          (match_dup 1)
19442          (const_int 1)))]
19443   "TARGET_SSE"
19444   "subss\t{%2, %0|%0, %2}"
19445   [(set_attr "type" "sseadd")
19446    (set_attr "mode" "SF")])
19447
19448 (define_insn "mulv4sf3"
19449   [(set (match_operand:V4SF 0 "register_operand" "=x")
19450         (mult:V4SF (match_operand:V4SF 1 "register_operand" "0")
19451                    (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
19452   "TARGET_SSE"
19453   "mulps\t{%2, %0|%0, %2}"
19454   [(set_attr "type" "ssemul")
19455    (set_attr "mode" "V4SF")])
19456
19457 (define_insn "vmmulv4sf3"
19458   [(set (match_operand:V4SF 0 "register_operand" "=x")
19459         (vec_merge:V4SF
19460          (mult:V4SF (match_operand:V4SF 1 "register_operand" "0")
19461                     (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
19462          (match_dup 1)
19463          (const_int 1)))]
19464   "TARGET_SSE"
19465   "mulss\t{%2, %0|%0, %2}"
19466   [(set_attr "type" "ssemul")
19467    (set_attr "mode" "SF")])
19468
19469 (define_insn "divv4sf3"
19470   [(set (match_operand:V4SF 0 "register_operand" "=x")
19471         (div:V4SF (match_operand:V4SF 1 "register_operand" "0")
19472                   (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
19473   "TARGET_SSE"
19474   "divps\t{%2, %0|%0, %2}"
19475   [(set_attr "type" "ssediv")
19476    (set_attr "mode" "V4SF")])
19477
19478 (define_insn "vmdivv4sf3"
19479   [(set (match_operand:V4SF 0 "register_operand" "=x")
19480         (vec_merge:V4SF
19481          (div:V4SF (match_operand:V4SF 1 "register_operand" "0")
19482                    (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
19483          (match_dup 1)
19484          (const_int 1)))]
19485   "TARGET_SSE"
19486   "divss\t{%2, %0|%0, %2}"
19487   [(set_attr "type" "ssediv")
19488    (set_attr "mode" "SF")])
19489
19490
19491 ;; SSE square root/reciprocal
19492
19493 (define_insn "rcpv4sf2"
19494   [(set (match_operand:V4SF 0 "register_operand" "=x")
19495         (unspec:V4SF
19496          [(match_operand:V4SF 1 "nonimmediate_operand" "xm")] UNSPEC_RCP))]
19497   "TARGET_SSE"
19498   "rcpps\t{%1, %0|%0, %1}"
19499   [(set_attr "type" "sse")
19500    (set_attr "mode" "V4SF")])
19501
19502 (define_insn "vmrcpv4sf2"
19503   [(set (match_operand:V4SF 0 "register_operand" "=x")
19504         (vec_merge:V4SF
19505          (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
19506                       UNSPEC_RCP)
19507          (match_operand:V4SF 2 "register_operand" "0")
19508          (const_int 1)))]
19509   "TARGET_SSE"
19510   "rcpss\t{%1, %0|%0, %1}"
19511   [(set_attr "type" "sse")
19512    (set_attr "mode" "SF")])
19513
19514 (define_insn "rsqrtv4sf2"
19515   [(set (match_operand:V4SF 0 "register_operand" "=x")
19516         (unspec:V4SF
19517          [(match_operand:V4SF 1 "nonimmediate_operand" "xm")] UNSPEC_RSQRT))]
19518   "TARGET_SSE"
19519   "rsqrtps\t{%1, %0|%0, %1}"
19520   [(set_attr "type" "sse")
19521    (set_attr "mode" "V4SF")])
19522
19523 (define_insn "vmrsqrtv4sf2"
19524   [(set (match_operand:V4SF 0 "register_operand" "=x")
19525         (vec_merge:V4SF
19526          (unspec:V4SF [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
19527                       UNSPEC_RSQRT)
19528          (match_operand:V4SF 2 "register_operand" "0")
19529          (const_int 1)))]
19530   "TARGET_SSE"
19531   "rsqrtss\t{%1, %0|%0, %1}"
19532   [(set_attr "type" "sse")
19533    (set_attr "mode" "SF")])
19534
19535 (define_insn "sqrtv4sf2"
19536   [(set (match_operand:V4SF 0 "register_operand" "=x")
19537         (sqrt:V4SF (match_operand:V4SF 1 "nonimmediate_operand" "xm")))]
19538   "TARGET_SSE"
19539   "sqrtps\t{%1, %0|%0, %1}"
19540   [(set_attr "type" "sse")
19541    (set_attr "mode" "V4SF")])
19542
19543 (define_insn "vmsqrtv4sf2"
19544   [(set (match_operand:V4SF 0 "register_operand" "=x")
19545         (vec_merge:V4SF
19546          (sqrt:V4SF (match_operand:V4SF 1 "nonimmediate_operand" "xm"))
19547          (match_operand:V4SF 2 "register_operand" "0")
19548          (const_int 1)))]
19549   "TARGET_SSE"
19550   "sqrtss\t{%1, %0|%0, %1}"
19551   [(set_attr "type" "sse")
19552    (set_attr "mode" "SF")])
19553
19554 ;; SSE logical operations.
19555
19556 ;; SSE defines logical operations on floating point values.  This brings
19557 ;; interesting challenge to RTL representation where logicals are only valid
19558 ;; on integral types.  We deal with this by representing the floating point
19559 ;; logical as logical on arguments casted to TImode as this is what hardware
19560 ;; really does.  Unfortunately hardware requires the type information to be
19561 ;; present and thus we must avoid subregs from being simplified and eliminated
19562 ;; in later compilation phases.
19563 ;;
19564 ;; We have following variants from each instruction:
19565 ;; sse_andsf3 - the operation taking V4SF vector operands
19566 ;;              and doing TImode cast on them
19567 ;; *sse_andsf3_memory - the operation taking one memory operand casted to
19568 ;;                      TImode, since backend insist on eliminating casts
19569 ;;                      on memory operands
19570 ;; sse_andti3_sf_1 - the operation taking SF scalar operands.
19571 ;;                   We can not accept memory operand here as instruction reads
19572 ;;                   whole scalar.  This is generated only post reload by GCC
19573 ;;                   scalar float operations that expands to logicals (fabs)
19574 ;; sse_andti3_sf_2 - the operation taking SF scalar input and TImode
19575 ;;                   memory operand.  Eventually combine can be able
19576 ;;                   to synthesize these using splitter.
19577 ;; sse2_anddf3, *sse2_anddf3_memory
19578 ;;              
19579 ;; 
19580 ;; These are not called andti3 etc. because we really really don't want
19581 ;; the compiler to widen DImode ands to TImode ands and then try to move
19582 ;; into DImode subregs of SSE registers, and them together, and move out
19583 ;; of DImode subregs again!
19584 ;; SSE1 single precision floating point logical operation
19585 (define_expand "sse_andv4sf3"
19586   [(set (match_operand:V4SF 0 "register_operand" "")
19587         (and:V4SF (match_operand:V4SF 1 "register_operand" "")
19588                   (match_operand:V4SF 2 "nonimmediate_operand" "")))]
19589   "TARGET_SSE"
19590   "")
19591
19592 (define_insn "*sse_andv4sf3"
19593   [(set (match_operand:V4SF 0 "register_operand" "=x")
19594         (and:V4SF (match_operand:V4SF 1 "nonimmediate_operand" "%0")
19595                   (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
19596   "TARGET_SSE
19597    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19598   "andps\t{%2, %0|%0, %2}"
19599   [(set_attr "type" "sselog")
19600    (set_attr "mode" "V4SF")])
19601
19602 (define_expand "sse_nandv4sf3"
19603   [(set (match_operand:V4SF 0 "register_operand" "")
19604         (and:V4SF (not:V4SF (match_operand:V4SF 1 "register_operand" ""))
19605                   (match_operand:V4SF 2 "nonimmediate_operand" "")))]
19606   "TARGET_SSE"
19607   "")
19608
19609 (define_insn "*sse_nandv4sf3"
19610   [(set (match_operand:V4SF 0 "register_operand" "=x")
19611         (and:V4SF (not:V4SF (match_operand:V4SF 1 "register_operand" "0"))
19612                   (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
19613   "TARGET_SSE"
19614   "andnps\t{%2, %0|%0, %2}"
19615   [(set_attr "type" "sselog")
19616    (set_attr "mode" "V4SF")])
19617
19618 (define_expand "sse_iorv4sf3"
19619   [(set (match_operand:V4SF 0 "register_operand" "")
19620         (ior:V4SF (match_operand:V4SF 1 "register_operand" "")
19621                   (match_operand:V4SF 2 "nonimmediate_operand" "")))]
19622   "TARGET_SSE"
19623   "")
19624
19625 (define_insn "*sse_iorv4sf3"
19626   [(set (match_operand:V4SF 0 "register_operand" "=x")
19627         (ior:V4SF (match_operand:V4SF 1 "nonimmediate_operand" "%0")
19628                   (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
19629   "TARGET_SSE
19630    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19631   "orps\t{%2, %0|%0, %2}"
19632   [(set_attr "type" "sselog")
19633    (set_attr "mode" "V4SF")])
19634
19635 (define_expand "sse_xorv4sf3"
19636   [(set (match_operand:V4SF 0 "register_operand" "")
19637         (xor:V4SF (match_operand:V4SF 1 "register_operand" "")
19638                   (match_operand:V4SF 2 "nonimmediate_operand" "")))]
19639   "TARGET_SSE"
19640   "")
19641
19642 (define_insn "*sse_xorv4sf3"
19643   [(set (match_operand:V4SF 0 "register_operand" "=x")
19644         (xor:V4SF (match_operand:V4SF 1 "nonimmediate_operand" "%0")
19645                   (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
19646   "TARGET_SSE
19647    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19648   "xorps\t{%2, %0|%0, %2}"
19649   [(set_attr "type" "sselog")
19650    (set_attr "mode" "V4SF")])
19651
19652 ;; SSE2 double precision floating point logical operation
19653
19654 (define_expand "sse2_andv2df3"
19655   [(set (match_operand:V2DF 0 "register_operand" "")
19656         (and:V2DF (match_operand:V2DF 1 "register_operand" "")
19657                   (match_operand:V2DF 2 "nonimmediate_operand" "")))]
19658   "TARGET_SSE2"
19659   "")
19660
19661 (define_insn "*sse2_andv2df3"
19662   [(set (match_operand:V2DF 0 "register_operand" "=x")
19663         (and:V2DF (match_operand:V2DF 1 "nonimmediate_operand" "%0")
19664                   (match_operand:V2DF 2 "nonimmediate_operand" "xm")))]
19665   "TARGET_SSE2
19666    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19667   "andpd\t{%2, %0|%0, %2}"
19668   [(set_attr "type" "sselog")
19669    (set_attr "mode" "V2DF")])
19670
19671 (define_expand "sse2_nandv2df3"
19672   [(set (match_operand:V2DF 0 "register_operand" "")
19673         (and:V2DF (not:V2DF (match_operand:V2DF 1 "register_operand" ""))
19674                   (match_operand:V2DF 2 "nonimmediate_operand" "")))]
19675   "TARGET_SSE2"
19676   "")
19677
19678 (define_insn "*sse2_nandv2df3"
19679   [(set (match_operand:V2DF 0 "register_operand" "=x")
19680         (and:V2DF (not:V2DF (match_operand:V2DF 1 "register_operand" "0"))
19681                   (match_operand:V2DF 2 "nonimmediate_operand" "xm")))]
19682   "TARGET_SSE2"
19683   "andnpd\t{%2, %0|%0, %2}"
19684   [(set_attr "type" "sselog")
19685    (set_attr "mode" "V2DF")])
19686
19687 (define_expand "sse2_iorv2df3"
19688   [(set (match_operand:V2DF 0 "register_operand" "")
19689         (ior:V2DF (match_operand:V2DF 1 "register_operand" "")
19690                   (match_operand:V2DF 2 "nonimmediate_operand" "")))]
19691   "TARGET_SSE2"
19692   "")
19693
19694 (define_insn "*sse2_iorv2df3"
19695   [(set (match_operand:V2DF 0 "register_operand" "=x")
19696         (ior:V2DF (match_operand:V2DF 1 "nonimmediate_operand" "%0")
19697                   (match_operand:V2DF 2 "nonimmediate_operand" "xm")))]
19698   "TARGET_SSE2
19699    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19700   "orpd\t{%2, %0|%0, %2}"
19701   [(set_attr "type" "sselog")
19702    (set_attr "mode" "V2DF")])
19703
19704 (define_expand "sse2_xorv2df3"
19705   [(set (match_operand:V2DF 0 "register_operand" "")
19706         (xor:V2DF (match_operand:V2DF 1 "nonimmediate_operand" "")
19707                   (match_operand:V2DF 2 "nonimmediate_operand" "")))]
19708   "TARGET_SSE2"
19709   "")
19710
19711 (define_insn "*sse2_xorv2df3"
19712   [(set (match_operand:V2DF 0 "register_operand" "=x")
19713         (xor:V2DF (match_operand:V2DF 1 "nonimmediate_operand" "%0")
19714                   (match_operand:V2DF 2 "nonimmediate_operand" "xm")))]
19715   "TARGET_SSE2
19716    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19717   "xorpd\t{%2, %0|%0, %2}"
19718   [(set_attr "type" "sselog")
19719    (set_attr "mode" "V2DF")])
19720
19721 ;; SSE2 integral logicals.  These patterns must always come after floating
19722 ;; point ones since we don't want compiler to use integer opcodes on floating
19723 ;; point SSE values to avoid matching of subregs in the match_operand.
19724 (define_insn "*sse2_andti3"
19725   [(set (match_operand:TI 0 "register_operand" "=x")
19726         (and:TI (match_operand:TI 1 "nonimmediate_operand" "%0")
19727                 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
19728   "TARGET_SSE2
19729    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19730   "pand\t{%2, %0|%0, %2}"
19731   [(set_attr "type" "sselog")
19732    (set_attr "mode" "TI")])
19733
19734 (define_insn "sse2_andv2di3"
19735   [(set (match_operand:V2DI 0 "register_operand" "=x")
19736         (and:V2DI (match_operand:V2DI 1 "nonimmediate_operand" "%0")
19737                   (match_operand:V2DI 2 "nonimmediate_operand" "xm")))]
19738   "TARGET_SSE2
19739    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19740   "pand\t{%2, %0|%0, %2}"
19741   [(set_attr "type" "sselog")
19742    (set_attr "mode" "TI")])
19743
19744 (define_insn "*sse2_nandti3"
19745   [(set (match_operand:TI 0 "register_operand" "=x")
19746         (and:TI (not:TI (match_operand:TI 1 "register_operand" "0"))
19747                 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
19748   "TARGET_SSE2"
19749   "pandn\t{%2, %0|%0, %2}"
19750   [(set_attr "type" "sselog")
19751    (set_attr "mode" "TI")])
19752
19753 (define_insn "sse2_nandv2di3"
19754   [(set (match_operand:V2DI 0 "register_operand" "=x")
19755         (and:V2DI (not:V2DI (match_operand:V2DI 1 "register_operand" "0"))
19756                   (match_operand:V2DI 2 "nonimmediate_operand" "xm")))]
19757   "TARGET_SSE2
19758    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19759   "pandn\t{%2, %0|%0, %2}"
19760   [(set_attr "type" "sselog")
19761    (set_attr "mode" "TI")])
19762
19763 (define_insn "*sse2_iorti3"
19764   [(set (match_operand:TI 0 "register_operand" "=x")
19765         (ior:TI (match_operand:TI 1 "nonimmediate_operand" "%0")
19766                 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
19767   "TARGET_SSE2
19768    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19769   "por\t{%2, %0|%0, %2}"
19770   [(set_attr "type" "sselog")
19771    (set_attr "mode" "TI")])
19772
19773 (define_insn "sse2_iorv2di3"
19774   [(set (match_operand:V2DI 0 "register_operand" "=x")
19775         (ior:V2DI (match_operand:V2DI 1 "nonimmediate_operand" "%0")
19776                   (match_operand:V2DI 2 "nonimmediate_operand" "xm")))]
19777   "TARGET_SSE2
19778    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19779   "por\t{%2, %0|%0, %2}"
19780   [(set_attr "type" "sselog")
19781    (set_attr "mode" "TI")])
19782
19783 (define_insn "*sse2_xorti3"
19784   [(set (match_operand:TI 0 "register_operand" "=x")
19785         (xor:TI (match_operand:TI 1 "nonimmediate_operand" "%0")
19786                 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
19787   "TARGET_SSE2
19788    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19789   "pxor\t{%2, %0|%0, %2}"
19790   [(set_attr "type" "sselog")
19791    (set_attr "mode" "TI")])
19792
19793 (define_insn "sse2_xorv2di3"
19794   [(set (match_operand:V2DI 0 "register_operand" "=x")
19795         (xor:V2DI (match_operand:V2DI 1 "nonimmediate_operand" "%0")
19796                   (match_operand:V2DI 2 "nonimmediate_operand" "xm")))]
19797   "TARGET_SSE2
19798    && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
19799   "pxor\t{%2, %0|%0, %2}"
19800   [(set_attr "type" "sselog")
19801    (set_attr "mode" "TI")])
19802
19803 ;; Use xor, but don't show input operands so they aren't live before
19804 ;; this insn.
19805 (define_insn "sse_clrv4sf"
19806   [(set (match_operand:V4SF 0 "register_operand" "=x")
19807         (match_operand:V4SF 1 "const0_operand" "X"))]
19808   "TARGET_SSE"
19809 {
19810   if (get_attr_mode (insn) == MODE_TI)
19811     return "pxor\t{%0, %0|%0, %0}";
19812   else
19813     return "xorps\t{%0, %0|%0, %0}";
19814 }
19815   [(set_attr "type" "sselog")
19816    (set_attr "memory" "none")
19817    (set (attr "mode")
19818         (if_then_else
19819            (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
19820                          (const_int 0))
19821                      (ne (symbol_ref "TARGET_SSE2")
19822                          (const_int 0)))
19823                 (eq (symbol_ref "optimize_size")
19824                     (const_int 0)))
19825          (const_string "TI")
19826          (const_string "V4SF")))])
19827
19828 ;; Use xor, but don't show input operands so they aren't live before
19829 ;; this insn.
19830 (define_insn "sse_clrv2df"
19831   [(set (match_operand:V2DF 0 "register_operand" "=x")
19832         (unspec:V2DF [(const_int 0)] UNSPEC_NOP))]
19833   "TARGET_SSE2"
19834   "xorpd\t{%0, %0|%0, %0}"
19835   [(set_attr "type" "sselog")
19836    (set_attr "memory" "none")
19837    (set_attr "mode" "V4SF")])
19838
19839 ;; SSE mask-generating compares
19840
19841 (define_insn "maskcmpv4sf3"
19842   [(set (match_operand:V4SI 0 "register_operand" "=x")
19843         (match_operator:V4SI 3 "sse_comparison_operator"
19844                 [(match_operand:V4SF 1 "register_operand" "0")
19845                  (match_operand:V4SF 2 "register_operand" "x")]))]
19846   "TARGET_SSE"
19847   "cmp%D3ps\t{%2, %0|%0, %2}"
19848   [(set_attr "type" "ssecmp")
19849    (set_attr "mode" "V4SF")])
19850
19851 (define_insn "maskncmpv4sf3"
19852   [(set (match_operand:V4SI 0 "register_operand" "=x")
19853         (not:V4SI
19854          (match_operator:V4SI 3 "sse_comparison_operator"
19855                 [(match_operand:V4SF 1 "register_operand" "0")
19856                  (match_operand:V4SF 2 "register_operand" "x")])))]
19857   "TARGET_SSE"
19858 {
19859   if (GET_CODE (operands[3]) == UNORDERED)
19860     return "cmpordps\t{%2, %0|%0, %2}";
19861   else
19862     return "cmpn%D3ps\t{%2, %0|%0, %2}";
19863 }
19864   [(set_attr "type" "ssecmp")
19865    (set_attr "mode" "V4SF")])
19866
19867 (define_insn "vmmaskcmpv4sf3"
19868   [(set (match_operand:V4SI 0 "register_operand" "=x")
19869         (vec_merge:V4SI
19870          (match_operator:V4SI 3 "sse_comparison_operator"
19871                 [(match_operand:V4SF 1 "register_operand" "0")
19872                  (match_operand:V4SF 2 "register_operand" "x")])
19873          (subreg:V4SI (match_dup 1) 0)
19874          (const_int 1)))]
19875   "TARGET_SSE"
19876   "cmp%D3ss\t{%2, %0|%0, %2}"
19877   [(set_attr "type" "ssecmp")
19878    (set_attr "mode" "SF")])
19879
19880 (define_insn "vmmaskncmpv4sf3"
19881   [(set (match_operand:V4SI 0 "register_operand" "=x")
19882         (vec_merge:V4SI
19883          (not:V4SI
19884           (match_operator:V4SI 3 "sse_comparison_operator"
19885                 [(match_operand:V4SF 1 "register_operand" "0")
19886                  (match_operand:V4SF 2 "register_operand" "x")]))
19887          (subreg:V4SI (match_dup 1) 0)
19888          (const_int 1)))]
19889   "TARGET_SSE"
19890 {
19891   if (GET_CODE (operands[3]) == UNORDERED)
19892     return "cmpordss\t{%2, %0|%0, %2}";
19893   else
19894     return "cmpn%D3ss\t{%2, %0|%0, %2}";
19895 }
19896   [(set_attr "type" "ssecmp")
19897    (set_attr "mode" "SF")])
19898
19899 (define_insn "sse_comi"
19900   [(set (reg:CCFP 17)
19901         (compare:CCFP (vec_select:SF
19902                        (match_operand:V4SF 0 "register_operand" "x")
19903                        (parallel [(const_int 0)]))
19904                       (vec_select:SF
19905                        (match_operand:V4SF 1 "register_operand" "x")
19906                        (parallel [(const_int 0)]))))]
19907   "TARGET_SSE"
19908   "comiss\t{%1, %0|%0, %1}"
19909   [(set_attr "type" "ssecomi")
19910    (set_attr "mode" "SF")])
19911
19912 (define_insn "sse_ucomi"
19913   [(set (reg:CCFPU 17)
19914         (compare:CCFPU (vec_select:SF
19915                         (match_operand:V4SF 0 "register_operand" "x")
19916                         (parallel [(const_int 0)]))
19917                        (vec_select:SF
19918                         (match_operand:V4SF 1 "register_operand" "x")
19919                         (parallel [(const_int 0)]))))]
19920   "TARGET_SSE"
19921   "ucomiss\t{%1, %0|%0, %1}"
19922   [(set_attr "type" "ssecomi")
19923    (set_attr "mode" "SF")])
19924
19925
19926 ;; SSE unpack
19927
19928 (define_insn "sse_unpckhps"
19929   [(set (match_operand:V4SF 0 "register_operand" "=x")
19930         (vec_merge:V4SF
19931          (vec_select:V4SF (match_operand:V4SF 1 "register_operand" "0")
19932                           (parallel [(const_int 2)
19933                                      (const_int 0)
19934                                      (const_int 3)
19935                                      (const_int 1)]))
19936          (vec_select:V4SF (match_operand:V4SF 2 "register_operand" "x")
19937                           (parallel [(const_int 0)
19938                                      (const_int 2)
19939                                      (const_int 1)
19940                                      (const_int 3)]))
19941          (const_int 5)))]
19942   "TARGET_SSE"
19943   "unpckhps\t{%2, %0|%0, %2}"
19944   [(set_attr "type" "ssecvt")
19945    (set_attr "mode" "V4SF")])
19946
19947 (define_insn "sse_unpcklps"
19948   [(set (match_operand:V4SF 0 "register_operand" "=x")
19949         (vec_merge:V4SF
19950          (vec_select:V4SF (match_operand:V4SF 1 "register_operand" "0")
19951                           (parallel [(const_int 0)
19952                                      (const_int 2)
19953                                      (const_int 1)
19954                                      (const_int 3)]))
19955          (vec_select:V4SF (match_operand:V4SF 2 "register_operand" "x")
19956                           (parallel [(const_int 2)
19957                                      (const_int 0)
19958                                      (const_int 3)
19959                                      (const_int 1)]))
19960          (const_int 5)))]
19961   "TARGET_SSE"
19962   "unpcklps\t{%2, %0|%0, %2}"
19963   [(set_attr "type" "ssecvt")
19964    (set_attr "mode" "V4SF")])
19965
19966
19967 ;; SSE min/max
19968
19969 (define_insn "smaxv4sf3"
19970   [(set (match_operand:V4SF 0 "register_operand" "=x")
19971         (smax:V4SF (match_operand:V4SF 1 "register_operand" "0")
19972                    (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
19973   "TARGET_SSE"
19974   "maxps\t{%2, %0|%0, %2}"
19975   [(set_attr "type" "sse")
19976    (set_attr "mode" "V4SF")])
19977
19978 (define_insn "vmsmaxv4sf3"
19979   [(set (match_operand:V4SF 0 "register_operand" "=x")
19980         (vec_merge:V4SF
19981          (smax:V4SF (match_operand:V4SF 1 "register_operand" "0")
19982                     (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
19983          (match_dup 1)
19984          (const_int 1)))]
19985   "TARGET_SSE"
19986   "maxss\t{%2, %0|%0, %2}"
19987   [(set_attr "type" "sse")
19988    (set_attr "mode" "SF")])
19989
19990 (define_insn "sminv4sf3"
19991   [(set (match_operand:V4SF 0 "register_operand" "=x")
19992         (smin:V4SF (match_operand:V4SF 1 "register_operand" "0")
19993                    (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
19994   "TARGET_SSE"
19995   "minps\t{%2, %0|%0, %2}"
19996   [(set_attr "type" "sse")
19997    (set_attr "mode" "V4SF")])
19998
19999 (define_insn "vmsminv4sf3"
20000   [(set (match_operand:V4SF 0 "register_operand" "=x")
20001         (vec_merge:V4SF
20002          (smin:V4SF (match_operand:V4SF 1 "register_operand" "0")
20003                     (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
20004          (match_dup 1)
20005          (const_int 1)))]
20006   "TARGET_SSE"
20007   "minss\t{%2, %0|%0, %2}"
20008   [(set_attr "type" "sse")
20009    (set_attr "mode" "SF")])
20010
20011 ;; SSE <-> integer/MMX conversions
20012
20013 (define_insn "cvtpi2ps"
20014   [(set (match_operand:V4SF 0 "register_operand" "=x")
20015         (vec_merge:V4SF
20016          (match_operand:V4SF 1 "register_operand" "0")
20017          (vec_duplicate:V4SF
20018           (float:V2SF (match_operand:V2SI 2 "nonimmediate_operand" "ym")))
20019          (const_int 12)))]
20020   "TARGET_SSE"
20021   "cvtpi2ps\t{%2, %0|%0, %2}"
20022   [(set_attr "type" "ssecvt")
20023    (set_attr "mode" "V4SF")])
20024
20025 (define_insn "cvtps2pi"
20026   [(set (match_operand:V2SI 0 "register_operand" "=y")
20027         (vec_select:V2SI
20028          (fix:V4SI (match_operand:V4SF 1 "nonimmediate_operand" "xm"))
20029          (parallel [(const_int 0) (const_int 1)])))]
20030   "TARGET_SSE"
20031   "cvtps2pi\t{%1, %0|%0, %1}"
20032   [(set_attr "type" "ssecvt")
20033    (set_attr "mode" "V4SF")])
20034
20035 (define_insn "cvttps2pi"
20036   [(set (match_operand:V2SI 0 "register_operand" "=y")
20037         (vec_select:V2SI
20038          (unspec:V4SI [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
20039                       UNSPEC_FIX)
20040          (parallel [(const_int 0) (const_int 1)])))]
20041   "TARGET_SSE"
20042   "cvttps2pi\t{%1, %0|%0, %1}"
20043   [(set_attr "type" "ssecvt")
20044    (set_attr "mode" "SF")])
20045
20046 (define_insn "cvtsi2ss"
20047   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
20048         (vec_merge:V4SF
20049          (match_operand:V4SF 1 "register_operand" "0,0")
20050          (vec_duplicate:V4SF
20051           (float:SF (match_operand:SI 2 "nonimmediate_operand" "r,rm")))
20052          (const_int 14)))]
20053   "TARGET_SSE"
20054   "cvtsi2ss\t{%2, %0|%0, %2}"
20055   [(set_attr "type" "sseicvt")
20056    (set_attr "athlon_decode" "vector,double")
20057    (set_attr "mode" "SF")])
20058
20059 (define_insn "cvtsi2ssq"
20060   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
20061         (vec_merge:V4SF
20062          (match_operand:V4SF 1 "register_operand" "0,0")
20063          (vec_duplicate:V4SF
20064           (float:SF (match_operand:DI 2 "nonimmediate_operand" "r,rm")))
20065          (const_int 14)))]
20066   "TARGET_SSE && TARGET_64BIT"
20067   "cvtsi2ssq\t{%2, %0|%0, %2}"
20068   [(set_attr "type" "sseicvt")
20069    (set_attr "athlon_decode" "vector,double")
20070    (set_attr "mode" "SF")])
20071
20072 (define_insn "cvtss2si"
20073   [(set (match_operand:SI 0 "register_operand" "=r,r")
20074         (vec_select:SI
20075          (fix:V4SI (match_operand:V4SF 1 "nonimmediate_operand" "x,m"))
20076          (parallel [(const_int 0)])))]
20077   "TARGET_SSE"
20078   "cvtss2si\t{%1, %0|%0, %1}"
20079   [(set_attr "type" "sseicvt")
20080    (set_attr "athlon_decode" "double,vector")
20081    (set_attr "mode" "SI")])
20082
20083 (define_insn "cvtss2siq"
20084   [(set (match_operand:DI 0 "register_operand" "=r,r")
20085         (vec_select:DI
20086          (fix:V4DI (match_operand:V4SF 1 "nonimmediate_operand" "x,m"))
20087          (parallel [(const_int 0)])))]
20088   "TARGET_SSE"
20089   "cvtss2siq\t{%1, %0|%0, %1}"
20090   [(set_attr "type" "sseicvt")
20091    (set_attr "athlon_decode" "double,vector")
20092    (set_attr "mode" "DI")])
20093
20094 (define_insn "cvttss2si"
20095   [(set (match_operand:SI 0 "register_operand" "=r,r")
20096         (vec_select:SI
20097          (unspec:V4SI [(match_operand:V4SF 1 "nonimmediate_operand" "x,xm")]
20098                       UNSPEC_FIX)
20099          (parallel [(const_int 0)])))]
20100   "TARGET_SSE"
20101   "cvttss2si\t{%1, %0|%0, %1}"
20102   [(set_attr "type" "sseicvt")
20103    (set_attr "mode" "SF")
20104    (set_attr "athlon_decode" "double,vector")])
20105
20106 (define_insn "cvttss2siq"
20107   [(set (match_operand:DI 0 "register_operand" "=r,r")
20108         (vec_select:DI
20109          (unspec:V4DI [(match_operand:V4SF 1 "nonimmediate_operand" "x,xm")]
20110                       UNSPEC_FIX)
20111          (parallel [(const_int 0)])))]
20112   "TARGET_SSE && TARGET_64BIT"
20113   "cvttss2siq\t{%1, %0|%0, %1}"
20114   [(set_attr "type" "sseicvt")
20115    (set_attr "mode" "SF")
20116    (set_attr "athlon_decode" "double,vector")])
20117
20118
20119 ;; MMX insns
20120
20121 ;; MMX arithmetic
20122
20123 (define_insn "addv8qi3"
20124   [(set (match_operand:V8QI 0 "register_operand" "=y")
20125         (plus:V8QI (match_operand:V8QI 1 "register_operand" "%0")
20126                    (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
20127   "TARGET_MMX"
20128   "paddb\t{%2, %0|%0, %2}"
20129   [(set_attr "type" "mmxadd")
20130    (set_attr "mode" "DI")])
20131
20132 (define_insn "addv4hi3"
20133   [(set (match_operand:V4HI 0 "register_operand" "=y")
20134         (plus:V4HI (match_operand:V4HI 1 "register_operand" "%0")
20135                    (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20136   "TARGET_MMX"
20137   "paddw\t{%2, %0|%0, %2}"
20138   [(set_attr "type" "mmxadd")
20139    (set_attr "mode" "DI")])
20140
20141 (define_insn "addv2si3"
20142   [(set (match_operand:V2SI 0 "register_operand" "=y")
20143         (plus:V2SI (match_operand:V2SI 1 "register_operand" "%0")
20144                    (match_operand:V2SI 2 "nonimmediate_operand" "ym")))]
20145   "TARGET_MMX"
20146   "paddd\t{%2, %0|%0, %2}"
20147   [(set_attr "type" "mmxadd")
20148    (set_attr "mode" "DI")])
20149
20150 (define_insn "mmx_adddi3"
20151   [(set (match_operand:DI 0 "register_operand" "=y")
20152         (unspec:DI
20153          [(plus:DI (match_operand:DI 1 "register_operand" "%0")
20154                    (match_operand:DI 2 "nonimmediate_operand" "ym"))]
20155          UNSPEC_NOP))]
20156   "TARGET_MMX"
20157   "paddq\t{%2, %0|%0, %2}"
20158   [(set_attr "type" "mmxadd")
20159    (set_attr "mode" "DI")])
20160
20161 (define_insn "ssaddv8qi3"
20162   [(set (match_operand:V8QI 0 "register_operand" "=y")
20163         (ss_plus:V8QI (match_operand:V8QI 1 "register_operand" "%0")
20164                       (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
20165   "TARGET_MMX"
20166   "paddsb\t{%2, %0|%0, %2}"
20167   [(set_attr "type" "mmxadd")
20168    (set_attr "mode" "DI")])
20169
20170 (define_insn "ssaddv4hi3"
20171   [(set (match_operand:V4HI 0 "register_operand" "=y")
20172         (ss_plus:V4HI (match_operand:V4HI 1 "register_operand" "%0")
20173                       (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20174   "TARGET_MMX"
20175   "paddsw\t{%2, %0|%0, %2}"
20176   [(set_attr "type" "mmxadd")
20177    (set_attr "mode" "DI")])
20178
20179 (define_insn "usaddv8qi3"
20180   [(set (match_operand:V8QI 0 "register_operand" "=y")
20181         (us_plus:V8QI (match_operand:V8QI 1 "register_operand" "%0")
20182                       (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
20183   "TARGET_MMX"
20184   "paddusb\t{%2, %0|%0, %2}"
20185   [(set_attr "type" "mmxadd")
20186    (set_attr "mode" "DI")])
20187
20188 (define_insn "usaddv4hi3"
20189   [(set (match_operand:V4HI 0 "register_operand" "=y")
20190         (us_plus:V4HI (match_operand:V4HI 1 "register_operand" "%0")
20191                       (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20192   "TARGET_MMX"
20193   "paddusw\t{%2, %0|%0, %2}"
20194   [(set_attr "type" "mmxadd")
20195    (set_attr "mode" "DI")])
20196
20197 (define_insn "subv8qi3"
20198   [(set (match_operand:V8QI 0 "register_operand" "=y")
20199         (minus:V8QI (match_operand:V8QI 1 "register_operand" "0")
20200                     (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
20201   "TARGET_MMX"
20202   "psubb\t{%2, %0|%0, %2}"
20203   [(set_attr "type" "mmxadd")
20204    (set_attr "mode" "DI")])
20205
20206 (define_insn "subv4hi3"
20207   [(set (match_operand:V4HI 0 "register_operand" "=y")
20208         (minus:V4HI (match_operand:V4HI 1 "register_operand" "0")
20209                     (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20210   "TARGET_MMX"
20211   "psubw\t{%2, %0|%0, %2}"
20212   [(set_attr "type" "mmxadd")
20213    (set_attr "mode" "DI")])
20214
20215 (define_insn "subv2si3"
20216   [(set (match_operand:V2SI 0 "register_operand" "=y")
20217         (minus:V2SI (match_operand:V2SI 1 "register_operand" "0")
20218                     (match_operand:V2SI 2 "nonimmediate_operand" "ym")))]
20219   "TARGET_MMX"
20220   "psubd\t{%2, %0|%0, %2}"
20221   [(set_attr "type" "mmxadd")
20222    (set_attr "mode" "DI")])
20223
20224 (define_insn "mmx_subdi3"
20225   [(set (match_operand:DI 0 "register_operand" "=y")
20226         (unspec:DI
20227          [(minus:DI (match_operand:DI 1 "register_operand" "0")
20228                     (match_operand:DI 2 "nonimmediate_operand" "ym"))]
20229          UNSPEC_NOP))]
20230   "TARGET_MMX"
20231   "psubq\t{%2, %0|%0, %2}"
20232   [(set_attr "type" "mmxadd")
20233    (set_attr "mode" "DI")])
20234
20235 (define_insn "sssubv8qi3"
20236   [(set (match_operand:V8QI 0 "register_operand" "=y")
20237         (ss_minus:V8QI (match_operand:V8QI 1 "register_operand" "0")
20238                        (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
20239   "TARGET_MMX"
20240   "psubsb\t{%2, %0|%0, %2}"
20241   [(set_attr "type" "mmxadd")
20242    (set_attr "mode" "DI")])
20243
20244 (define_insn "sssubv4hi3"
20245   [(set (match_operand:V4HI 0 "register_operand" "=y")
20246         (ss_minus:V4HI (match_operand:V4HI 1 "register_operand" "0")
20247                        (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20248   "TARGET_MMX"
20249   "psubsw\t{%2, %0|%0, %2}"
20250   [(set_attr "type" "mmxadd")
20251    (set_attr "mode" "DI")])
20252
20253 (define_insn "ussubv8qi3"
20254   [(set (match_operand:V8QI 0 "register_operand" "=y")
20255         (us_minus:V8QI (match_operand:V8QI 1 "register_operand" "0")
20256                        (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
20257   "TARGET_MMX"
20258   "psubusb\t{%2, %0|%0, %2}"
20259   [(set_attr "type" "mmxadd")
20260    (set_attr "mode" "DI")])
20261
20262 (define_insn "ussubv4hi3"
20263   [(set (match_operand:V4HI 0 "register_operand" "=y")
20264         (us_minus:V4HI (match_operand:V4HI 1 "register_operand" "0")
20265                        (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20266   "TARGET_MMX"
20267   "psubusw\t{%2, %0|%0, %2}"
20268   [(set_attr "type" "mmxadd")
20269    (set_attr "mode" "DI")])
20270
20271 (define_insn "mulv4hi3"
20272   [(set (match_operand:V4HI 0 "register_operand" "=y")
20273         (mult:V4HI (match_operand:V4HI 1 "register_operand" "0")
20274                    (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20275   "TARGET_MMX"
20276   "pmullw\t{%2, %0|%0, %2}"
20277   [(set_attr "type" "mmxmul")
20278    (set_attr "mode" "DI")])
20279
20280 (define_insn "smulv4hi3_highpart"
20281   [(set (match_operand:V4HI 0 "register_operand" "=y")
20282         (truncate:V4HI
20283          (lshiftrt:V4SI
20284           (mult:V4SI (sign_extend:V4SI
20285                       (match_operand:V4HI 1 "register_operand" "0"))
20286                      (sign_extend:V4SI
20287                       (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
20288           (const_int 16))))]
20289   "TARGET_MMX"
20290   "pmulhw\t{%2, %0|%0, %2}"
20291   [(set_attr "type" "mmxmul")
20292    (set_attr "mode" "DI")])
20293
20294 (define_insn "umulv4hi3_highpart"
20295   [(set (match_operand:V4HI 0 "register_operand" "=y")
20296         (truncate:V4HI
20297          (lshiftrt:V4SI
20298           (mult:V4SI (zero_extend:V4SI
20299                       (match_operand:V4HI 1 "register_operand" "0"))
20300                      (zero_extend:V4SI
20301                       (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
20302           (const_int 16))))]
20303   "TARGET_SSE || TARGET_3DNOW_A"
20304   "pmulhuw\t{%2, %0|%0, %2}"
20305   [(set_attr "type" "mmxmul")
20306    (set_attr "mode" "DI")])
20307
20308 (define_insn "mmx_pmaddwd"
20309   [(set (match_operand:V2SI 0 "register_operand" "=y")
20310         (plus:V2SI
20311          (mult:V2SI
20312           (sign_extend:V2SI
20313            (vec_select:V2HI (match_operand:V4HI 1 "register_operand" "0")
20314                             (parallel [(const_int 0) (const_int 2)])))
20315           (sign_extend:V2SI
20316            (vec_select:V2HI (match_operand:V4HI 2 "nonimmediate_operand" "ym")
20317                             (parallel [(const_int 0) (const_int 2)]))))
20318          (mult:V2SI
20319           (sign_extend:V2SI (vec_select:V2HI (match_dup 1)
20320                                              (parallel [(const_int 1)
20321                                                         (const_int 3)])))
20322           (sign_extend:V2SI (vec_select:V2HI (match_dup 2)
20323                                              (parallel [(const_int 1)
20324                                                         (const_int 3)]))))))]
20325   "TARGET_MMX"
20326   "pmaddwd\t{%2, %0|%0, %2}"
20327   [(set_attr "type" "mmxmul")
20328    (set_attr "mode" "DI")])
20329
20330
20331 ;; MMX logical operations
20332 ;; Note we don't want to declare these as regular iordi3 insns to prevent
20333 ;; normal code that also wants to use the FPU from getting broken.
20334 ;; The UNSPECs are there to prevent the combiner from getting overly clever.
20335 (define_insn "mmx_iordi3"
20336   [(set (match_operand:DI 0 "register_operand" "=y")
20337         (unspec:DI
20338          [(ior:DI (match_operand:DI 1 "register_operand" "%0")
20339                   (match_operand:DI 2 "nonimmediate_operand" "ym"))]
20340          UNSPEC_NOP))]
20341   "TARGET_MMX"
20342   "por\t{%2, %0|%0, %2}"
20343   [(set_attr "type" "mmxadd")
20344    (set_attr "mode" "DI")])
20345
20346 (define_insn "mmx_xordi3"
20347   [(set (match_operand:DI 0 "register_operand" "=y")
20348         (unspec:DI
20349          [(xor:DI (match_operand:DI 1 "register_operand" "%0")
20350                   (match_operand:DI 2 "nonimmediate_operand" "ym"))]
20351          UNSPEC_NOP))]
20352   "TARGET_MMX"
20353   "pxor\t{%2, %0|%0, %2}"
20354   [(set_attr "type" "mmxadd")
20355    (set_attr "mode" "DI")
20356    (set_attr "memory" "none")])
20357
20358 ;; Same as pxor, but don't show input operands so that we don't think
20359 ;; they are live.
20360 (define_insn "mmx_clrdi"
20361   [(set (match_operand:DI 0 "register_operand" "=y")
20362         (unspec:DI [(const_int 0)] UNSPEC_NOP))]
20363   "TARGET_MMX"
20364   "pxor\t{%0, %0|%0, %0}"
20365   [(set_attr "type" "mmxadd")
20366    (set_attr "mode" "DI")
20367    (set_attr "memory" "none")])
20368
20369 (define_insn "mmx_anddi3"
20370   [(set (match_operand:DI 0 "register_operand" "=y")
20371         (unspec:DI
20372          [(and:DI (match_operand:DI 1 "register_operand" "%0")
20373                   (match_operand:DI 2 "nonimmediate_operand" "ym"))]
20374          UNSPEC_NOP))]
20375   "TARGET_MMX"
20376   "pand\t{%2, %0|%0, %2}"
20377   [(set_attr "type" "mmxadd")
20378    (set_attr "mode" "DI")])
20379
20380 (define_insn "mmx_nanddi3"
20381   [(set (match_operand:DI 0 "register_operand" "=y")
20382         (unspec:DI
20383          [(and:DI (not:DI (match_operand:DI 1 "register_operand" "0"))
20384                           (match_operand:DI 2 "nonimmediate_operand" "ym"))]
20385          UNSPEC_NOP))]
20386   "TARGET_MMX"
20387   "pandn\t{%2, %0|%0, %2}"
20388   [(set_attr "type" "mmxadd")
20389    (set_attr "mode" "DI")])
20390
20391
20392 ;; MMX unsigned averages/sum of absolute differences
20393
20394 (define_insn "mmx_uavgv8qi3"
20395   [(set (match_operand:V8QI 0 "register_operand" "=y")
20396         (ashiftrt:V8QI
20397          (plus:V8QI (plus:V8QI
20398                      (match_operand:V8QI 1 "register_operand" "0")
20399                      (match_operand:V8QI 2 "nonimmediate_operand" "ym"))
20400                     (const_vector:V8QI [(const_int 1)
20401                                         (const_int 1)
20402                                         (const_int 1)
20403                                         (const_int 1)
20404                                         (const_int 1)
20405                                         (const_int 1)
20406                                         (const_int 1)
20407                                         (const_int 1)]))
20408          (const_int 1)))]
20409   "TARGET_SSE || TARGET_3DNOW_A"
20410   "pavgb\t{%2, %0|%0, %2}"
20411   [(set_attr "type" "mmxshft")
20412    (set_attr "mode" "DI")])
20413
20414 (define_insn "mmx_uavgv4hi3"
20415   [(set (match_operand:V4HI 0 "register_operand" "=y")
20416         (ashiftrt:V4HI
20417          (plus:V4HI (plus:V4HI
20418                      (match_operand:V4HI 1 "register_operand" "0")
20419                      (match_operand:V4HI 2 "nonimmediate_operand" "ym"))
20420                     (const_vector:V4HI [(const_int 1)
20421                                         (const_int 1)
20422                                         (const_int 1)
20423                                         (const_int 1)]))
20424          (const_int 1)))]
20425   "TARGET_SSE || TARGET_3DNOW_A"
20426   "pavgw\t{%2, %0|%0, %2}"
20427   [(set_attr "type" "mmxshft")
20428    (set_attr "mode" "DI")])
20429
20430 (define_insn "mmx_psadbw"
20431   [(set (match_operand:DI 0 "register_operand" "=y")
20432         (unspec:DI [(match_operand:V8QI 1 "register_operand" "0")
20433                     (match_operand:V8QI 2 "nonimmediate_operand" "ym")]
20434                    UNSPEC_PSADBW))]
20435   "TARGET_SSE || TARGET_3DNOW_A"
20436   "psadbw\t{%2, %0|%0, %2}"
20437   [(set_attr "type" "mmxshft")
20438    (set_attr "mode" "DI")])
20439
20440
20441 ;; MMX insert/extract/shuffle
20442
20443 (define_insn "mmx_pinsrw"
20444   [(set (match_operand:V4HI 0 "register_operand" "=y")
20445         (vec_merge:V4HI (match_operand:V4HI 1 "register_operand" "0")
20446                         (vec_duplicate:V4HI
20447                          (truncate:HI (match_operand:SI 2 "nonimmediate_operand" "rm")))
20448                         (match_operand:SI 3 "const_0_to_15_operand" "N")))]
20449   "TARGET_SSE || TARGET_3DNOW_A"
20450   "pinsrw\t{%3, %2, %0|%0, %2, %3}"
20451   [(set_attr "type" "mmxcvt")
20452    (set_attr "mode" "DI")])
20453
20454 (define_insn "mmx_pextrw"
20455   [(set (match_operand:SI 0 "register_operand" "=r")
20456         (zero_extend:SI (vec_select:HI (match_operand:V4HI 1 "register_operand" "y")
20457                                        (parallel
20458                                         [(match_operand:SI 2 "const_0_to_3_operand" "N")]))))]
20459   "TARGET_SSE || TARGET_3DNOW_A"
20460   "pextrw\t{%2, %1, %0|%0, %1, %2}"
20461   [(set_attr "type" "mmxcvt")
20462    (set_attr "mode" "DI")])
20463
20464 (define_insn "mmx_pshufw"
20465   [(set (match_operand:V4HI 0 "register_operand" "=y")
20466         (unspec:V4HI [(match_operand:V4HI 1 "register_operand" "0")
20467                       (match_operand:SI 2 "immediate_operand" "i")]
20468                      UNSPEC_SHUFFLE))]
20469   "TARGET_SSE || TARGET_3DNOW_A"
20470   "pshufw\t{%2, %1, %0|%0, %1, %2}"
20471   [(set_attr "type" "mmxcvt")
20472    (set_attr "mode" "DI")])
20473
20474
20475 ;; MMX mask-generating comparisons
20476
20477 (define_insn "eqv8qi3"
20478   [(set (match_operand:V8QI 0 "register_operand" "=y")
20479         (eq:V8QI (match_operand:V8QI 1 "register_operand" "0")
20480                  (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
20481   "TARGET_MMX"
20482   "pcmpeqb\t{%2, %0|%0, %2}"
20483   [(set_attr "type" "mmxcmp")
20484    (set_attr "mode" "DI")])
20485
20486 (define_insn "eqv4hi3"
20487   [(set (match_operand:V4HI 0 "register_operand" "=y")
20488         (eq:V4HI (match_operand:V4HI 1 "register_operand" "0")
20489                  (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20490   "TARGET_MMX"
20491   "pcmpeqw\t{%2, %0|%0, %2}"
20492   [(set_attr "type" "mmxcmp")
20493    (set_attr "mode" "DI")])
20494
20495 (define_insn "eqv2si3"
20496   [(set (match_operand:V2SI 0 "register_operand" "=y")
20497         (eq:V2SI (match_operand:V2SI 1 "register_operand" "0")
20498                  (match_operand:V2SI 2 "nonimmediate_operand" "ym")))]
20499   "TARGET_MMX"
20500   "pcmpeqd\t{%2, %0|%0, %2}"
20501   [(set_attr "type" "mmxcmp")
20502    (set_attr "mode" "DI")])
20503
20504 (define_insn "gtv8qi3"
20505   [(set (match_operand:V8QI 0 "register_operand" "=y")
20506         (gt:V8QI (match_operand:V8QI 1 "register_operand" "0")
20507                  (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
20508   "TARGET_MMX"
20509   "pcmpgtb\t{%2, %0|%0, %2}"
20510   [(set_attr "type" "mmxcmp")
20511    (set_attr "mode" "DI")])
20512
20513 (define_insn "gtv4hi3"
20514   [(set (match_operand:V4HI 0 "register_operand" "=y")
20515         (gt:V4HI (match_operand:V4HI 1 "register_operand" "0")
20516                  (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20517   "TARGET_MMX"
20518   "pcmpgtw\t{%2, %0|%0, %2}"
20519   [(set_attr "type" "mmxcmp")
20520    (set_attr "mode" "DI")])
20521
20522 (define_insn "gtv2si3"
20523   [(set (match_operand:V2SI 0 "register_operand" "=y")
20524         (gt:V2SI (match_operand:V2SI 1 "register_operand" "0")
20525                  (match_operand:V2SI 2 "nonimmediate_operand" "ym")))]
20526   "TARGET_MMX"
20527   "pcmpgtd\t{%2, %0|%0, %2}"
20528   [(set_attr "type" "mmxcmp")
20529    (set_attr "mode" "DI")])
20530
20531
20532 ;; MMX max/min insns
20533
20534 (define_insn "umaxv8qi3"
20535   [(set (match_operand:V8QI 0 "register_operand" "=y")
20536         (umax:V8QI (match_operand:V8QI 1 "register_operand" "0")
20537                    (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
20538   "TARGET_SSE || TARGET_3DNOW_A"
20539   "pmaxub\t{%2, %0|%0, %2}"
20540   [(set_attr "type" "mmxadd")
20541    (set_attr "mode" "DI")])
20542
20543 (define_insn "smaxv4hi3"
20544   [(set (match_operand:V4HI 0 "register_operand" "=y")
20545         (smax:V4HI (match_operand:V4HI 1 "register_operand" "0")
20546                    (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20547   "TARGET_SSE || TARGET_3DNOW_A"
20548   "pmaxsw\t{%2, %0|%0, %2}"
20549   [(set_attr "type" "mmxadd")
20550    (set_attr "mode" "DI")])
20551
20552 (define_insn "uminv8qi3"
20553   [(set (match_operand:V8QI 0 "register_operand" "=y")
20554         (umin:V8QI (match_operand:V8QI 1 "register_operand" "0")
20555                    (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
20556   "TARGET_SSE || TARGET_3DNOW_A"
20557   "pminub\t{%2, %0|%0, %2}"
20558   [(set_attr "type" "mmxadd")
20559    (set_attr "mode" "DI")])
20560
20561 (define_insn "sminv4hi3"
20562   [(set (match_operand:V4HI 0 "register_operand" "=y")
20563         (smin:V4HI (match_operand:V4HI 1 "register_operand" "0")
20564                    (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
20565   "TARGET_SSE || TARGET_3DNOW_A"
20566   "pminsw\t{%2, %0|%0, %2}"
20567   [(set_attr "type" "mmxadd")
20568    (set_attr "mode" "DI")])
20569
20570
20571 ;; MMX shifts
20572
20573 (define_insn "ashrv4hi3"
20574   [(set (match_operand:V4HI 0 "register_operand" "=y")
20575         (ashiftrt:V4HI (match_operand:V4HI 1 "register_operand" "0")
20576                        (match_operand:DI 2 "nonmemory_operand" "yi")))]
20577   "TARGET_MMX"
20578   "psraw\t{%2, %0|%0, %2}"
20579   [(set_attr "type" "mmxshft")
20580    (set_attr "mode" "DI")])
20581
20582 (define_insn "ashrv2si3"
20583   [(set (match_operand:V2SI 0 "register_operand" "=y")
20584         (ashiftrt:V2SI (match_operand:V2SI 1 "register_operand" "0")
20585                        (match_operand:DI 2 "nonmemory_operand" "yi")))]
20586   "TARGET_MMX"
20587   "psrad\t{%2, %0|%0, %2}"
20588   [(set_attr "type" "mmxshft")
20589    (set_attr "mode" "DI")])
20590
20591 (define_insn "lshrv4hi3"
20592   [(set (match_operand:V4HI 0 "register_operand" "=y")
20593         (lshiftrt:V4HI (match_operand:V4HI 1 "register_operand" "0")
20594                        (match_operand:DI 2 "nonmemory_operand" "yi")))]
20595   "TARGET_MMX"
20596   "psrlw\t{%2, %0|%0, %2}"
20597   [(set_attr "type" "mmxshft")
20598    (set_attr "mode" "DI")])
20599
20600 (define_insn "lshrv2si3"
20601   [(set (match_operand:V2SI 0 "register_operand" "=y")
20602         (lshiftrt:V2SI (match_operand:V2SI 1 "register_operand" "0")
20603                        (match_operand:DI 2 "nonmemory_operand" "yi")))]
20604   "TARGET_MMX"
20605   "psrld\t{%2, %0|%0, %2}"
20606   [(set_attr "type" "mmxshft")
20607    (set_attr "mode" "DI")])
20608
20609 ;; See logical MMX insns.
20610 (define_insn "mmx_lshrdi3"
20611   [(set (match_operand:DI 0 "register_operand" "=y")
20612         (unspec:DI
20613           [(lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
20614                        (match_operand:DI 2 "nonmemory_operand" "yi"))]
20615           UNSPEC_NOP))]
20616   "TARGET_MMX"
20617   "psrlq\t{%2, %0|%0, %2}"
20618   [(set_attr "type" "mmxshft")
20619    (set_attr "mode" "DI")])
20620
20621 (define_insn "ashlv4hi3"
20622   [(set (match_operand:V4HI 0 "register_operand" "=y")
20623         (ashift:V4HI (match_operand:V4HI 1 "register_operand" "0")
20624                        (match_operand:DI 2 "nonmemory_operand" "yi")))]
20625   "TARGET_MMX"
20626   "psllw\t{%2, %0|%0, %2}"
20627   [(set_attr "type" "mmxshft")
20628    (set_attr "mode" "DI")])
20629
20630 (define_insn "ashlv2si3"
20631   [(set (match_operand:V2SI 0 "register_operand" "=y")
20632         (ashift:V2SI (match_operand:V2SI 1 "register_operand" "0")
20633                        (match_operand:DI 2 "nonmemory_operand" "yi")))]
20634   "TARGET_MMX"
20635   "pslld\t{%2, %0|%0, %2}"
20636   [(set_attr "type" "mmxshft")
20637    (set_attr "mode" "DI")])
20638
20639 ;; See logical MMX insns.
20640 (define_insn "mmx_ashldi3"
20641   [(set (match_operand:DI 0 "register_operand" "=y")
20642         (unspec:DI
20643          [(ashift:DI (match_operand:DI 1 "register_operand" "0")
20644                      (match_operand:DI 2 "nonmemory_operand" "yi"))]
20645          UNSPEC_NOP))]
20646   "TARGET_MMX"
20647   "psllq\t{%2, %0|%0, %2}"
20648   [(set_attr "type" "mmxshft")
20649    (set_attr "mode" "DI")])
20650
20651
20652 ;; MMX pack/unpack insns.
20653
20654 (define_insn "mmx_packsswb"
20655   [(set (match_operand:V8QI 0 "register_operand" "=y")
20656         (vec_concat:V8QI
20657          (ss_truncate:V4QI (match_operand:V4HI 1 "register_operand" "0"))
20658          (ss_truncate:V4QI (match_operand:V4HI 2 "register_operand" "y"))))]
20659   "TARGET_MMX"
20660   "packsswb\t{%2, %0|%0, %2}"
20661   [(set_attr "type" "mmxshft")
20662    (set_attr "mode" "DI")])
20663
20664 (define_insn "mmx_packssdw"
20665   [(set (match_operand:V4HI 0 "register_operand" "=y")
20666         (vec_concat:V4HI
20667          (ss_truncate:V2HI (match_operand:V2SI 1 "register_operand" "0"))
20668          (ss_truncate:V2HI (match_operand:V2SI 2 "register_operand" "y"))))]
20669   "TARGET_MMX"
20670   "packssdw\t{%2, %0|%0, %2}"
20671   [(set_attr "type" "mmxshft")
20672    (set_attr "mode" "DI")])
20673
20674 (define_insn "mmx_packuswb"
20675   [(set (match_operand:V8QI 0 "register_operand" "=y")
20676         (vec_concat:V8QI
20677          (us_truncate:V4QI (match_operand:V4HI 1 "register_operand" "0"))
20678          (us_truncate:V4QI (match_operand:V4HI 2 "register_operand" "y"))))]
20679   "TARGET_MMX"
20680   "packuswb\t{%2, %0|%0, %2}"
20681   [(set_attr "type" "mmxshft")
20682    (set_attr "mode" "DI")])
20683
20684 (define_insn "mmx_punpckhbw"
20685   [(set (match_operand:V8QI 0 "register_operand" "=y")
20686         (vec_merge:V8QI
20687          (vec_select:V8QI (match_operand:V8QI 1 "register_operand" "0")
20688                           (parallel [(const_int 4)
20689                                      (const_int 0)
20690                                      (const_int 5)
20691                                      (const_int 1)
20692                                      (const_int 6)
20693                                      (const_int 2)
20694                                      (const_int 7)
20695                                      (const_int 3)]))
20696          (vec_select:V8QI (match_operand:V8QI 2 "register_operand" "y")
20697                           (parallel [(const_int 0)
20698                                      (const_int 4)
20699                                      (const_int 1)
20700                                      (const_int 5)
20701                                      (const_int 2)
20702                                      (const_int 6)
20703                                      (const_int 3)
20704                                      (const_int 7)]))
20705          (const_int 85)))]
20706   "TARGET_MMX"
20707   "punpckhbw\t{%2, %0|%0, %2}"
20708   [(set_attr "type" "mmxcvt")
20709    (set_attr "mode" "DI")])
20710
20711 (define_insn "mmx_punpckhwd"
20712   [(set (match_operand:V4HI 0 "register_operand" "=y")
20713         (vec_merge:V4HI
20714          (vec_select:V4HI (match_operand:V4HI 1 "register_operand" "0")
20715                           (parallel [(const_int 0)
20716                                      (const_int 2)
20717                                      (const_int 1)
20718                                      (const_int 3)]))
20719          (vec_select:V4HI (match_operand:V4HI 2 "register_operand" "y")
20720                           (parallel [(const_int 2)
20721                                      (const_int 0)
20722                                      (const_int 3)
20723                                      (const_int 1)]))
20724          (const_int 5)))]
20725   "TARGET_MMX"
20726   "punpckhwd\t{%2, %0|%0, %2}"
20727   [(set_attr "type" "mmxcvt")
20728    (set_attr "mode" "DI")])
20729
20730 (define_insn "mmx_punpckhdq"
20731   [(set (match_operand:V2SI 0 "register_operand" "=y")
20732         (vec_merge:V2SI
20733          (match_operand:V2SI 1 "register_operand" "0")
20734          (vec_select:V2SI (match_operand:V2SI 2 "register_operand" "y")
20735                           (parallel [(const_int 1)
20736                                      (const_int 0)]))
20737          (const_int 1)))]
20738   "TARGET_MMX"
20739   "punpckhdq\t{%2, %0|%0, %2}"
20740   [(set_attr "type" "mmxcvt")
20741    (set_attr "mode" "DI")])
20742
20743 (define_insn "mmx_punpcklbw"
20744   [(set (match_operand:V8QI 0 "register_operand" "=y")
20745         (vec_merge:V8QI
20746          (vec_select:V8QI (match_operand:V8QI 1 "register_operand" "0")
20747                           (parallel [(const_int 0)
20748                                      (const_int 4)
20749                                      (const_int 1)
20750                                      (const_int 5)
20751                                      (const_int 2)
20752                                      (const_int 6)
20753                                      (const_int 3)
20754                                      (const_int 7)]))
20755          (vec_select:V8QI (match_operand:V8QI 2 "register_operand" "y")
20756                           (parallel [(const_int 4)
20757                                      (const_int 0)
20758                                      (const_int 5)
20759                                      (const_int 1)
20760                                      (const_int 6)
20761                                      (const_int 2)
20762                                      (const_int 7)
20763                                      (const_int 3)]))
20764          (const_int 85)))]
20765   "TARGET_MMX"
20766   "punpcklbw\t{%2, %0|%0, %2}"
20767   [(set_attr "type" "mmxcvt")
20768    (set_attr "mode" "DI")])
20769
20770 (define_insn "mmx_punpcklwd"
20771   [(set (match_operand:V4HI 0 "register_operand" "=y")
20772         (vec_merge:V4HI
20773          (vec_select:V4HI (match_operand:V4HI 1 "register_operand" "0")
20774                           (parallel [(const_int 2)
20775                                      (const_int 0)
20776                                      (const_int 3)
20777                                      (const_int 1)]))
20778          (vec_select:V4HI (match_operand:V4HI 2 "register_operand" "y")
20779                           (parallel [(const_int 0)
20780                                      (const_int 2)
20781                                      (const_int 1)
20782                                      (const_int 3)]))
20783          (const_int 5)))]
20784   "TARGET_MMX"
20785   "punpcklwd\t{%2, %0|%0, %2}"
20786   [(set_attr "type" "mmxcvt")
20787    (set_attr "mode" "DI")])
20788
20789 (define_insn "mmx_punpckldq"
20790   [(set (match_operand:V2SI 0 "register_operand" "=y")
20791         (vec_merge:V2SI
20792          (vec_select:V2SI (match_operand:V2SI 1 "register_operand" "0")
20793                            (parallel [(const_int 1)
20794                                       (const_int 0)]))
20795          (match_operand:V2SI 2 "register_operand" "y")
20796          (const_int 1)))]
20797   "TARGET_MMX"
20798   "punpckldq\t{%2, %0|%0, %2}"
20799   [(set_attr "type" "mmxcvt")
20800    (set_attr "mode" "DI")])
20801
20802
20803 ;; Miscellaneous stuff
20804
20805 (define_insn "emms"
20806   [(unspec_volatile [(const_int 0)] UNSPECV_EMMS)
20807    (clobber (reg:XF 8))
20808    (clobber (reg:XF 9))
20809    (clobber (reg:XF 10))
20810    (clobber (reg:XF 11))
20811    (clobber (reg:XF 12))
20812    (clobber (reg:XF 13))
20813    (clobber (reg:XF 14))
20814    (clobber (reg:XF 15))
20815    (clobber (reg:DI 29))
20816    (clobber (reg:DI 30))
20817    (clobber (reg:DI 31))
20818    (clobber (reg:DI 32))
20819    (clobber (reg:DI 33))
20820    (clobber (reg:DI 34))
20821    (clobber (reg:DI 35))
20822    (clobber (reg:DI 36))]
20823   "TARGET_MMX"
20824   "emms"
20825   [(set_attr "type" "mmx")
20826    (set_attr "memory" "unknown")])
20827
20828 (define_insn "ldmxcsr"
20829   [(unspec_volatile [(match_operand:SI 0 "memory_operand" "m")]
20830                     UNSPECV_LDMXCSR)]
20831   "TARGET_SSE"
20832   "ldmxcsr\t%0"
20833   [(set_attr "type" "sse")
20834    (set_attr "memory" "load")])
20835
20836 (define_insn "stmxcsr"
20837   [(set (match_operand:SI 0 "memory_operand" "=m")
20838         (unspec_volatile:SI [(const_int 0)] UNSPECV_STMXCSR))]
20839   "TARGET_SSE"
20840   "stmxcsr\t%0"
20841   [(set_attr "type" "sse")
20842    (set_attr "memory" "store")])
20843
20844 (define_expand "sfence"
20845   [(set (match_dup 0)
20846         (unspec:BLK [(match_dup 0)] UNSPEC_SFENCE))]
20847   "TARGET_SSE || TARGET_3DNOW_A"
20848 {
20849   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
20850   MEM_VOLATILE_P (operands[0]) = 1;
20851 })
20852
20853 (define_insn "*sfence_insn"
20854   [(set (match_operand:BLK 0 "" "")
20855         (unspec:BLK [(match_dup 0)] UNSPEC_SFENCE))]
20856   "TARGET_SSE || TARGET_3DNOW_A"
20857   "sfence"
20858   [(set_attr "type" "sse")
20859    (set_attr "memory" "unknown")])
20860
20861 (define_expand "sse_prologue_save"
20862   [(parallel [(set (match_operand:BLK 0 "" "")
20863                    (unspec:BLK [(reg:DI 21)
20864                                 (reg:DI 22)
20865                                 (reg:DI 23)
20866                                 (reg:DI 24)
20867                                 (reg:DI 25)
20868                                 (reg:DI 26)
20869                                 (reg:DI 27)
20870                                 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
20871               (use (match_operand:DI 1 "register_operand" ""))
20872               (use (match_operand:DI 2 "immediate_operand" ""))
20873               (use (label_ref:DI (match_operand 3 "" "")))])]
20874   "TARGET_64BIT"
20875   "")
20876
20877 (define_insn "*sse_prologue_save_insn"
20878   [(set (mem:BLK (plus:DI (match_operand:DI 0 "register_operand" "R")
20879                           (match_operand:DI 4 "const_int_operand" "n")))
20880         (unspec:BLK [(reg:DI 21)
20881                      (reg:DI 22)
20882                      (reg:DI 23)
20883                      (reg:DI 24)
20884                      (reg:DI 25)
20885                      (reg:DI 26)
20886                      (reg:DI 27)
20887                      (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
20888    (use (match_operand:DI 1 "register_operand" "r"))
20889    (use (match_operand:DI 2 "const_int_operand" "i"))
20890    (use (label_ref:DI (match_operand 3 "" "X")))]
20891   "TARGET_64BIT
20892    && INTVAL (operands[4]) + SSE_REGPARM_MAX * 16 - 16 < 128
20893    && INTVAL (operands[4]) + INTVAL (operands[2]) * 16 >= -128"
20894   "*
20895 {
20896   int i;
20897   operands[0] = gen_rtx_MEM (Pmode,
20898                              gen_rtx_PLUS (Pmode, operands[0], operands[4]));
20899   output_asm_insn (\"jmp\\t%A1\", operands);
20900   for (i = SSE_REGPARM_MAX - 1; i >= INTVAL (operands[2]); i--)
20901     {
20902       operands[4] = adjust_address (operands[0], DImode, i*16);
20903       operands[5] = gen_rtx_REG (TImode, SSE_REGNO (i));
20904       PUT_MODE (operands[4], TImode);
20905       if (GET_CODE (XEXP (operands[0], 0)) != PLUS)
20906         output_asm_insn (\"rex\", operands);
20907       output_asm_insn (\"movaps\\t{%5, %4|%4, %5}\", operands);
20908     }
20909   (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
20910                              CODE_LABEL_NUMBER (operands[3]));
20911   RET;
20912 }
20913   "
20914   [(set_attr "type" "other")
20915    (set_attr "length_immediate" "0")
20916    (set_attr "length_address" "0")
20917    (set_attr "length" "135")
20918    (set_attr "memory" "store")
20919    (set_attr "modrm" "0")
20920    (set_attr "mode" "DI")])
20921
20922 ;; 3Dnow! instructions
20923
20924 (define_insn "addv2sf3"
20925   [(set (match_operand:V2SF 0 "register_operand" "=y")
20926         (plus:V2SF (match_operand:V2SF 1 "register_operand" "0")
20927                    (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
20928   "TARGET_3DNOW"
20929   "pfadd\\t{%2, %0|%0, %2}"
20930   [(set_attr "type" "mmxadd")
20931    (set_attr "mode" "V2SF")])
20932
20933 (define_insn "subv2sf3"
20934   [(set (match_operand:V2SF 0 "register_operand" "=y")
20935         (minus:V2SF (match_operand:V2SF 1 "register_operand" "0")
20936                     (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
20937   "TARGET_3DNOW"
20938   "pfsub\\t{%2, %0|%0, %2}"
20939   [(set_attr "type" "mmxadd")
20940    (set_attr "mode" "V2SF")])
20941
20942 (define_insn "subrv2sf3"
20943   [(set (match_operand:V2SF 0 "register_operand" "=y")
20944         (minus:V2SF (match_operand:V2SF 2 "nonimmediate_operand" "ym")
20945                     (match_operand:V2SF 1 "register_operand" "0")))]
20946   "TARGET_3DNOW"
20947   "pfsubr\\t{%2, %0|%0, %2}"
20948   [(set_attr "type" "mmxadd")
20949    (set_attr "mode" "V2SF")])
20950
20951 (define_insn "gtv2sf3"
20952   [(set (match_operand:V2SI 0 "register_operand" "=y")
20953         (gt:V2SI (match_operand:V2SF 1 "register_operand" "0")
20954                  (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
20955  "TARGET_3DNOW"
20956   "pfcmpgt\\t{%2, %0|%0, %2}"
20957   [(set_attr "type" "mmxcmp")
20958    (set_attr "mode" "V2SF")])
20959
20960 (define_insn "gev2sf3"
20961   [(set (match_operand:V2SI 0 "register_operand" "=y")
20962         (ge:V2SI (match_operand:V2SF 1 "register_operand" "0")
20963                  (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
20964   "TARGET_3DNOW"
20965   "pfcmpge\\t{%2, %0|%0, %2}"
20966   [(set_attr "type" "mmxcmp")
20967    (set_attr "mode" "V2SF")])
20968
20969 (define_insn "eqv2sf3"
20970   [(set (match_operand:V2SI 0 "register_operand" "=y")
20971         (eq:V2SI (match_operand:V2SF 1 "register_operand" "0")
20972                  (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
20973   "TARGET_3DNOW"
20974   "pfcmpeq\\t{%2, %0|%0, %2}"
20975   [(set_attr "type" "mmxcmp")
20976    (set_attr "mode" "V2SF")])
20977
20978 (define_insn "pfmaxv2sf3"
20979   [(set (match_operand:V2SF 0 "register_operand" "=y")
20980         (smax:V2SF (match_operand:V2SF 1 "register_operand" "0")
20981                    (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
20982   "TARGET_3DNOW"
20983   "pfmax\\t{%2, %0|%0, %2}"
20984   [(set_attr "type" "mmxadd")
20985    (set_attr "mode" "V2SF")])
20986
20987 (define_insn "pfminv2sf3"
20988   [(set (match_operand:V2SF 0 "register_operand" "=y")
20989         (smin:V2SF (match_operand:V2SF 1 "register_operand" "0")
20990                    (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
20991   "TARGET_3DNOW"
20992   "pfmin\\t{%2, %0|%0, %2}"
20993   [(set_attr "type" "mmxadd")
20994    (set_attr "mode" "V2SF")])
20995
20996 (define_insn "mulv2sf3"
20997   [(set (match_operand:V2SF 0 "register_operand" "=y")
20998         (mult:V2SF (match_operand:V2SF 1 "register_operand" "0")
20999                    (match_operand:V2SF 2 "nonimmediate_operand" "ym")))]
21000   "TARGET_3DNOW"
21001   "pfmul\\t{%2, %0|%0, %2}"
21002   [(set_attr "type" "mmxmul")
21003    (set_attr "mode" "V2SF")])
21004
21005 (define_insn "femms"
21006   [(unspec_volatile [(const_int 0)] UNSPECV_FEMMS)
21007    (clobber (reg:XF 8))
21008    (clobber (reg:XF 9))
21009    (clobber (reg:XF 10))
21010    (clobber (reg:XF 11))
21011    (clobber (reg:XF 12))
21012    (clobber (reg:XF 13))
21013    (clobber (reg:XF 14))
21014    (clobber (reg:XF 15))
21015    (clobber (reg:DI 29))
21016    (clobber (reg:DI 30))
21017    (clobber (reg:DI 31))
21018    (clobber (reg:DI 32))
21019    (clobber (reg:DI 33))
21020    (clobber (reg:DI 34))
21021    (clobber (reg:DI 35))
21022    (clobber (reg:DI 36))]
21023   "TARGET_3DNOW"
21024   "femms"
21025   [(set_attr "type" "mmx")
21026    (set_attr "memory" "none")]) 
21027
21028 (define_insn "pf2id"
21029   [(set (match_operand:V2SI 0 "register_operand" "=y")
21030         (fix:V2SI (match_operand:V2SF 1 "nonimmediate_operand" "ym")))]
21031   "TARGET_3DNOW"
21032   "pf2id\\t{%1, %0|%0, %1}"
21033   [(set_attr "type" "mmxcvt")
21034    (set_attr "mode" "V2SF")])
21035
21036 (define_insn "pf2iw"
21037   [(set (match_operand:V2SI 0 "register_operand" "=y")
21038         (sign_extend:V2SI
21039            (ss_truncate:V2HI
21040               (fix:V2SI (match_operand:V2SF 1 "nonimmediate_operand" "ym")))))]
21041   "TARGET_3DNOW_A"
21042   "pf2iw\\t{%1, %0|%0, %1}"
21043   [(set_attr "type" "mmxcvt")
21044    (set_attr "mode" "V2SF")])
21045
21046 (define_insn "pfacc"
21047   [(set (match_operand:V2SF 0 "register_operand" "=y")
21048         (vec_concat:V2SF
21049            (plus:SF
21050               (vec_select:SF (match_operand:V2SF 1 "register_operand" "0")
21051                              (parallel [(const_int  0)]))
21052               (vec_select:SF (match_dup 1)
21053                              (parallel [(const_int 1)])))
21054            (plus:SF
21055               (vec_select:SF (match_operand:V2SF 2 "nonimmediate_operand" "y")
21056                              (parallel [(const_int  0)]))
21057               (vec_select:SF (match_dup 2)
21058                              (parallel [(const_int 1)])))))]
21059   "TARGET_3DNOW"
21060   "pfacc\\t{%2, %0|%0, %2}"
21061   [(set_attr "type" "mmxadd")
21062    (set_attr "mode" "V2SF")])
21063
21064 (define_insn "pfnacc"
21065   [(set (match_operand:V2SF 0 "register_operand" "=y")
21066         (vec_concat:V2SF
21067            (minus:SF
21068               (vec_select:SF (match_operand:V2SF 1 "register_operand" "0")
21069                              (parallel [(const_int 0)]))
21070               (vec_select:SF (match_dup 1)
21071                              (parallel [(const_int 1)])))
21072            (minus:SF
21073               (vec_select:SF (match_operand:V2SF 2 "nonimmediate_operand" "y")
21074                              (parallel [(const_int  0)]))
21075               (vec_select:SF (match_dup 2)
21076                              (parallel [(const_int 1)])))))]
21077   "TARGET_3DNOW_A"
21078   "pfnacc\\t{%2, %0|%0, %2}"
21079   [(set_attr "type" "mmxadd")
21080    (set_attr "mode" "V2SF")])
21081
21082 (define_insn "pfpnacc"
21083   [(set (match_operand:V2SF 0 "register_operand" "=y")
21084         (vec_concat:V2SF
21085            (minus:SF
21086               (vec_select:SF (match_operand:V2SF 1 "register_operand" "0")
21087                              (parallel [(const_int 0)]))
21088               (vec_select:SF (match_dup 1)
21089                              (parallel [(const_int 1)])))
21090            (plus:SF
21091               (vec_select:SF (match_operand:V2SF 2 "nonimmediate_operand" "y")
21092                              (parallel [(const_int 0)]))
21093               (vec_select:SF (match_dup 2)
21094                              (parallel [(const_int 1)])))))]
21095   "TARGET_3DNOW_A"
21096   "pfpnacc\\t{%2, %0|%0, %2}"
21097   [(set_attr "type" "mmxadd")
21098    (set_attr "mode" "V2SF")])
21099
21100 (define_insn "pi2fw"
21101   [(set (match_operand:V2SF 0 "register_operand" "=y")
21102         (float:V2SF
21103            (vec_concat:V2SI
21104               (sign_extend:SI
21105                  (truncate:HI
21106                     (vec_select:SI (match_operand:V2SI 1 "nonimmediate_operand" "ym")
21107                                    (parallel [(const_int 0)]))))
21108               (sign_extend:SI
21109                  (truncate:HI
21110                     (vec_select:SI (match_dup 1)
21111                                    (parallel [(const_int  1)])))))))]
21112   "TARGET_3DNOW_A"
21113   "pi2fw\\t{%1, %0|%0, %1}"
21114   [(set_attr "type" "mmxcvt")
21115    (set_attr "mode" "V2SF")])
21116
21117 (define_insn "floatv2si2"
21118   [(set (match_operand:V2SF 0 "register_operand" "=y")
21119         (float:V2SF (match_operand:V2SI 1 "nonimmediate_operand" "ym")))]
21120   "TARGET_3DNOW"
21121   "pi2fd\\t{%1, %0|%0, %1}"
21122   [(set_attr "type" "mmxcvt")
21123    (set_attr "mode" "V2SF")])
21124
21125 ;; This insn is identical to pavgb in operation, but the opcode is
21126 ;; different.  To avoid accidentally matching pavgb, use an unspec.
21127
21128 (define_insn "pavgusb"
21129  [(set (match_operand:V8QI 0 "register_operand" "=y")
21130        (unspec:V8QI
21131           [(match_operand:V8QI 1 "register_operand" "0")
21132            (match_operand:V8QI 2 "nonimmediate_operand" "ym")]
21133           UNSPEC_PAVGUSB))]
21134   "TARGET_3DNOW"
21135   "pavgusb\\t{%2, %0|%0, %2}"
21136   [(set_attr "type" "mmxshft")
21137    (set_attr "mode" "TI")])
21138
21139 ;; 3DNow reciprocal and sqrt
21140  
21141 (define_insn "pfrcpv2sf2"
21142   [(set (match_operand:V2SF 0 "register_operand" "=y")
21143         (unspec:V2SF [(match_operand:V2SF 1 "nonimmediate_operand" "ym")]
21144         UNSPEC_PFRCP))]
21145   "TARGET_3DNOW"
21146   "pfrcp\\t{%1, %0|%0, %1}"
21147   [(set_attr "type" "mmx")
21148    (set_attr "mode" "TI")])
21149
21150 (define_insn "pfrcpit1v2sf3"
21151   [(set (match_operand:V2SF 0 "register_operand" "=y")
21152         (unspec:V2SF [(match_operand:V2SF 1 "register_operand" "0")
21153                       (match_operand:V2SF 2 "nonimmediate_operand" "ym")]
21154                      UNSPEC_PFRCPIT1))]
21155   "TARGET_3DNOW"
21156   "pfrcpit1\\t{%2, %0|%0, %2}"
21157   [(set_attr "type" "mmx")
21158    (set_attr "mode" "TI")])
21159
21160 (define_insn "pfrcpit2v2sf3"
21161   [(set (match_operand:V2SF 0 "register_operand" "=y")
21162         (unspec:V2SF [(match_operand:V2SF 1 "register_operand" "0")
21163                       (match_operand:V2SF 2 "nonimmediate_operand" "ym")]
21164                      UNSPEC_PFRCPIT2))]
21165   "TARGET_3DNOW"
21166   "pfrcpit2\\t{%2, %0|%0, %2}"
21167   [(set_attr "type" "mmx")
21168    (set_attr "mode" "TI")])
21169
21170 (define_insn "pfrsqrtv2sf2"
21171   [(set (match_operand:V2SF 0 "register_operand" "=y")
21172         (unspec:V2SF [(match_operand:V2SF 1 "nonimmediate_operand" "ym")]
21173                      UNSPEC_PFRSQRT))]
21174   "TARGET_3DNOW"
21175   "pfrsqrt\\t{%1, %0|%0, %1}"
21176   [(set_attr "type" "mmx")
21177    (set_attr "mode" "TI")])
21178                 
21179 (define_insn "pfrsqit1v2sf3"
21180   [(set (match_operand:V2SF 0 "register_operand" "=y")
21181         (unspec:V2SF [(match_operand:V2SF 1 "register_operand" "0")
21182                       (match_operand:V2SF 2 "nonimmediate_operand" "ym")]
21183                      UNSPEC_PFRSQIT1))]
21184   "TARGET_3DNOW"
21185   "pfrsqit1\\t{%2, %0|%0, %2}"
21186   [(set_attr "type" "mmx")
21187    (set_attr "mode" "TI")])
21188
21189 (define_insn "pmulhrwv4hi3"
21190   [(set (match_operand:V4HI 0 "register_operand" "=y")
21191         (truncate:V4HI
21192            (lshiftrt:V4SI
21193               (plus:V4SI
21194                  (mult:V4SI
21195                     (sign_extend:V4SI
21196                        (match_operand:V4HI 1 "register_operand" "0"))
21197                     (sign_extend:V4SI
21198                        (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
21199                  (const_vector:V4SI [(const_int 32768)
21200                                      (const_int 32768)
21201                                      (const_int 32768)
21202                                      (const_int 32768)]))
21203               (const_int 16))))]
21204   "TARGET_3DNOW"
21205   "pmulhrw\\t{%2, %0|%0, %2}"
21206   [(set_attr "type" "mmxmul")
21207    (set_attr "mode" "TI")])
21208
21209 (define_insn "pswapdv2si2"
21210   [(set (match_operand:V2SI 0 "register_operand" "=y")
21211         (vec_select:V2SI (match_operand:V2SI 1 "nonimmediate_operand" "ym")
21212                          (parallel [(const_int 1) (const_int 0)])))]
21213   "TARGET_3DNOW_A"
21214   "pswapd\\t{%1, %0|%0, %1}"
21215   [(set_attr "type" "mmxcvt")
21216    (set_attr "mode" "TI")])
21217
21218 (define_insn "pswapdv2sf2"
21219   [(set (match_operand:V2SF 0 "register_operand" "=y")
21220         (vec_select:V2SF (match_operand:V2SF 1 "nonimmediate_operand" "ym")
21221                          (parallel [(const_int 1) (const_int 0)])))]
21222   "TARGET_3DNOW_A"
21223   "pswapd\\t{%1, %0|%0, %1}"
21224   [(set_attr "type" "mmxcvt")
21225    (set_attr "mode" "TI")])
21226
21227 (define_expand "prefetch"
21228   [(prefetch (match_operand 0 "address_operand" "")
21229              (match_operand:SI 1 "const_int_operand" "")
21230              (match_operand:SI 2 "const_int_operand" ""))]
21231   "TARGET_PREFETCH_SSE || TARGET_3DNOW"
21232 {
21233   int rw = INTVAL (operands[1]);
21234   int locality = INTVAL (operands[2]);
21235
21236   if (rw != 0 && rw != 1)
21237     abort ();
21238   if (locality < 0 || locality > 3)
21239     abort ();
21240   if (GET_MODE (operands[0]) != Pmode && GET_MODE (operands[0]) != VOIDmode)
21241     abort ();
21242
21243   /* Use 3dNOW prefetch in case we are asking for write prefetch not
21244      suported by SSE counterpart or the SSE prefetch is not available
21245      (K6 machines).  Otherwise use SSE prefetch as it allows specifying
21246      of locality.  */
21247   if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
21248     operands[2] = GEN_INT (3);
21249   else
21250     operands[1] = const0_rtx;
21251 })
21252
21253 (define_insn "*prefetch_sse"
21254   [(prefetch (match_operand:SI 0 "address_operand" "p")
21255              (const_int 0)
21256              (match_operand:SI 1 "const_int_operand" ""))]
21257   "TARGET_PREFETCH_SSE && !TARGET_64BIT"
21258 {
21259   static const char * const patterns[4] = {
21260    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
21261   };
21262
21263   int locality = INTVAL (operands[1]);
21264   if (locality < 0 || locality > 3)
21265     abort ();
21266
21267   return patterns[locality];  
21268 }
21269   [(set_attr "type" "sse")
21270    (set_attr "memory" "none")])
21271
21272 (define_insn "*prefetch_sse_rex"
21273   [(prefetch (match_operand:DI 0 "address_operand" "p")
21274              (const_int 0)
21275              (match_operand:SI 1 "const_int_operand" ""))]
21276   "TARGET_PREFETCH_SSE && TARGET_64BIT"
21277 {
21278   static const char * const patterns[4] = {
21279    "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
21280   };
21281
21282   int locality = INTVAL (operands[1]);
21283   if (locality < 0 || locality > 3)
21284     abort ();
21285
21286   return patterns[locality];  
21287 }
21288   [(set_attr "type" "sse")
21289    (set_attr "memory" "none")])
21290
21291 (define_insn "*prefetch_3dnow"
21292   [(prefetch (match_operand:SI 0 "address_operand" "p")
21293              (match_operand:SI 1 "const_int_operand" "n")
21294              (const_int 3))]
21295   "TARGET_3DNOW && !TARGET_64BIT"
21296 {
21297   if (INTVAL (operands[1]) == 0)
21298     return "prefetch\t%a0";
21299   else
21300     return "prefetchw\t%a0";
21301 }
21302   [(set_attr "type" "mmx")
21303    (set_attr "memory" "none")])
21304
21305 (define_insn "*prefetch_3dnow_rex"
21306   [(prefetch (match_operand:DI 0 "address_operand" "p")
21307              (match_operand:SI 1 "const_int_operand" "n")
21308              (const_int 3))]
21309   "TARGET_3DNOW && TARGET_64BIT"
21310 {
21311   if (INTVAL (operands[1]) == 0)
21312     return "prefetch\t%a0";
21313   else
21314     return "prefetchw\t%a0";
21315 }
21316   [(set_attr "type" "mmx")
21317    (set_attr "memory" "none")])
21318
21319 ;; SSE2 support
21320
21321 (define_insn "addv2df3"
21322   [(set (match_operand:V2DF 0 "register_operand" "=x")
21323         (plus:V2DF (match_operand:V2DF 1 "register_operand" "0")
21324                    (match_operand:V2DF 2 "nonimmediate_operand" "xm")))]
21325   "TARGET_SSE2"
21326   "addpd\t{%2, %0|%0, %2}"
21327   [(set_attr "type" "sseadd")
21328    (set_attr "mode" "V2DF")])
21329
21330 (define_insn "vmaddv2df3"
21331   [(set (match_operand:V2DF 0 "register_operand" "=x")
21332         (vec_merge:V2DF (plus:V2DF (match_operand:V2DF 1 "register_operand" "0")
21333                                    (match_operand:V2DF 2 "nonimmediate_operand" "xm"))
21334                         (match_dup 1)
21335                         (const_int 1)))]
21336   "TARGET_SSE2"
21337   "addsd\t{%2, %0|%0, %2}"
21338   [(set_attr "type" "sseadd")
21339    (set_attr "mode" "DF")])
21340
21341 (define_insn "subv2df3"
21342   [(set (match_operand:V2DF 0 "register_operand" "=x")
21343         (minus:V2DF (match_operand:V2DF 1 "register_operand" "0")
21344                    (match_operand:V2DF 2 "nonimmediate_operand" "xm")))]
21345   "TARGET_SSE2"
21346   "subpd\t{%2, %0|%0, %2}"
21347   [(set_attr "type" "sseadd")
21348    (set_attr "mode" "V2DF")])
21349
21350 (define_insn "vmsubv2df3"
21351   [(set (match_operand:V2DF 0 "register_operand" "=x")
21352         (vec_merge:V2DF (minus:V2DF (match_operand:V2DF 1 "register_operand" "0")
21353                                    (match_operand:V2DF 2 "nonimmediate_operand" "xm"))
21354                         (match_dup 1)
21355                         (const_int 1)))]
21356   "TARGET_SSE2"
21357   "subsd\t{%2, %0|%0, %2}"
21358   [(set_attr "type" "sseadd")
21359    (set_attr "mode" "DF")])
21360
21361 (define_insn "mulv2df3"
21362   [(set (match_operand:V2DF 0 "register_operand" "=x")
21363         (mult:V2DF (match_operand:V2DF 1 "register_operand" "0")
21364                    (match_operand:V2DF 2 "nonimmediate_operand" "xm")))]
21365   "TARGET_SSE2"
21366   "mulpd\t{%2, %0|%0, %2}"
21367   [(set_attr "type" "ssemul")
21368    (set_attr "mode" "V2DF")])
21369
21370 (define_insn "vmmulv2df3"
21371   [(set (match_operand:V2DF 0 "register_operand" "=x")
21372         (vec_merge:V2DF (mult:V2DF (match_operand:V2DF 1 "register_operand" "0")
21373                                    (match_operand:V2DF 2 "nonimmediate_operand" "xm"))
21374                         (match_dup 1)
21375                         (const_int 1)))]
21376   "TARGET_SSE2"
21377   "mulsd\t{%2, %0|%0, %2}"
21378   [(set_attr "type" "ssemul")
21379    (set_attr "mode" "DF")])
21380
21381 (define_insn "divv2df3"
21382   [(set (match_operand:V2DF 0 "register_operand" "=x")
21383         (div:V2DF (match_operand:V2DF 1 "register_operand" "0")
21384                   (match_operand:V2DF 2 "nonimmediate_operand" "xm")))]
21385   "TARGET_SSE2"
21386   "divpd\t{%2, %0|%0, %2}"
21387   [(set_attr "type" "ssediv")
21388    (set_attr "mode" "V2DF")])
21389
21390 (define_insn "vmdivv2df3"
21391   [(set (match_operand:V2DF 0 "register_operand" "=x")
21392         (vec_merge:V2DF (div:V2DF (match_operand:V2DF 1 "register_operand" "0")
21393                                   (match_operand:V2DF 2 "nonimmediate_operand" "xm"))
21394                         (match_dup 1)
21395                         (const_int 1)))]
21396   "TARGET_SSE2"
21397   "divsd\t{%2, %0|%0, %2}"
21398   [(set_attr "type" "ssediv")
21399    (set_attr "mode" "DF")])
21400
21401 ;; SSE min/max
21402
21403 (define_insn "smaxv2df3"
21404   [(set (match_operand:V2DF 0 "register_operand" "=x")
21405         (smax:V2DF (match_operand:V2DF 1 "register_operand" "0")
21406                    (match_operand:V2DF 2 "nonimmediate_operand" "xm")))]
21407   "TARGET_SSE2"
21408   "maxpd\t{%2, %0|%0, %2}"
21409   [(set_attr "type" "sseadd")
21410    (set_attr "mode" "V2DF")])
21411
21412 (define_insn "vmsmaxv2df3"
21413   [(set (match_operand:V2DF 0 "register_operand" "=x")
21414         (vec_merge:V2DF (smax:V2DF (match_operand:V2DF 1 "register_operand" "0")
21415                                    (match_operand:V2DF 2 "nonimmediate_operand" "xm"))
21416                         (match_dup 1)
21417                         (const_int 1)))]
21418   "TARGET_SSE2"
21419   "maxsd\t{%2, %0|%0, %2}"
21420   [(set_attr "type" "sseadd")
21421    (set_attr "mode" "DF")])
21422
21423 (define_insn "sminv2df3"
21424   [(set (match_operand:V2DF 0 "register_operand" "=x")
21425         (smin:V2DF (match_operand:V2DF 1 "register_operand" "0")
21426                    (match_operand:V2DF 2 "nonimmediate_operand" "xm")))]
21427   "TARGET_SSE2"
21428   "minpd\t{%2, %0|%0, %2}"
21429   [(set_attr "type" "sseadd")
21430    (set_attr "mode" "V2DF")])
21431
21432 (define_insn "vmsminv2df3"
21433   [(set (match_operand:V2DF 0 "register_operand" "=x")
21434         (vec_merge:V2DF (smin:V2DF (match_operand:V2DF 1 "register_operand" "0")
21435                                    (match_operand:V2DF 2 "nonimmediate_operand" "xm"))
21436                         (match_dup 1)
21437                         (const_int 1)))]
21438   "TARGET_SSE2"
21439   "minsd\t{%2, %0|%0, %2}"
21440   [(set_attr "type" "sseadd")
21441    (set_attr "mode" "DF")])
21442 ;; SSE2 square root.  There doesn't appear to be an extension for the
21443 ;; reciprocal/rsqrt instructions if the Intel manual is to be believed.
21444
21445 (define_insn "sqrtv2df2"
21446   [(set (match_operand:V2DF 0 "register_operand" "=x")
21447         (sqrt:V2DF (match_operand:V2DF 1 "register_operand" "xm")))]
21448   "TARGET_SSE2"
21449   "sqrtpd\t{%1, %0|%0, %1}"
21450   [(set_attr "type" "sse")
21451    (set_attr "mode" "V2DF")])
21452
21453 (define_insn "vmsqrtv2df2"
21454   [(set (match_operand:V2DF 0 "register_operand" "=x")
21455         (vec_merge:V2DF (sqrt:V2DF (match_operand:V2DF 1 "register_operand" "xm"))
21456                         (match_operand:V2DF 2 "register_operand" "0")
21457                         (const_int 1)))]
21458   "TARGET_SSE2"
21459   "sqrtsd\t{%1, %0|%0, %1}"
21460   [(set_attr "type" "sse")
21461    (set_attr "mode" "SF")])
21462
21463 ;; SSE mask-generating compares
21464
21465 (define_insn "maskcmpv2df3"
21466   [(set (match_operand:V2DI 0 "register_operand" "=x")
21467         (match_operator:V2DI 3 "sse_comparison_operator"
21468                              [(match_operand:V2DF 1 "register_operand" "0")
21469                               (match_operand:V2DF 2 "nonimmediate_operand" "x")]))]
21470   "TARGET_SSE2"
21471   "cmp%D3pd\t{%2, %0|%0, %2}"
21472   [(set_attr "type" "ssecmp")
21473    (set_attr "mode" "V2DF")])
21474
21475 (define_insn "maskncmpv2df3"
21476   [(set (match_operand:V2DI 0 "register_operand" "=x")
21477         (not:V2DI
21478          (match_operator:V2DI 3 "sse_comparison_operator"
21479                               [(match_operand:V2DF 1 "register_operand" "0")
21480                                (match_operand:V2DF 2 "nonimmediate_operand" "x")])))]
21481   "TARGET_SSE2"
21482 {
21483   if (GET_CODE (operands[3]) == UNORDERED)
21484     return "cmpordps\t{%2, %0|%0, %2}";
21485   else
21486     return "cmpn%D3pd\t{%2, %0|%0, %2}";
21487 }
21488   [(set_attr "type" "ssecmp")
21489    (set_attr "mode" "V2DF")])
21490
21491 (define_insn "vmmaskcmpv2df3"
21492   [(set (match_operand:V2DI 0 "register_operand" "=x")
21493         (vec_merge:V2DI
21494          (match_operator:V2DI 3 "sse_comparison_operator"
21495                               [(match_operand:V2DF 1 "register_operand" "0")
21496                                (match_operand:V2DF 2 "nonimmediate_operand" "x")])
21497          (subreg:V2DI (match_dup 1) 0)
21498          (const_int 1)))]
21499   "TARGET_SSE2"
21500   "cmp%D3sd\t{%2, %0|%0, %2}"
21501   [(set_attr "type" "ssecmp")
21502    (set_attr "mode" "DF")])
21503
21504 (define_insn "vmmaskncmpv2df3"
21505   [(set (match_operand:V2DI 0 "register_operand" "=x")
21506         (vec_merge:V2DI
21507          (not:V2DI
21508           (match_operator:V2DI 3 "sse_comparison_operator"
21509                                [(match_operand:V2DF 1 "register_operand" "0")
21510                                 (match_operand:V2DF 2 "nonimmediate_operand" "x")]))
21511          (subreg:V2DI (match_dup 1) 0)
21512          (const_int 1)))]
21513   "TARGET_SSE2"
21514 {
21515   if (GET_CODE (operands[3]) == UNORDERED)
21516     return "cmpordsd\t{%2, %0|%0, %2}";
21517   else
21518     return "cmpn%D3sd\t{%2, %0|%0, %2}";
21519 }
21520   [(set_attr "type" "ssecmp")
21521    (set_attr "mode" "DF")])
21522
21523 (define_insn "sse2_comi"
21524   [(set (reg:CCFP 17)
21525         (compare:CCFP (vec_select:DF
21526                        (match_operand:V2DF 0 "register_operand" "x")
21527                        (parallel [(const_int 0)]))
21528                       (vec_select:DF
21529                        (match_operand:V2DF 1 "register_operand" "x")
21530                        (parallel [(const_int 0)]))))]
21531   "TARGET_SSE2"
21532   "comisd\t{%1, %0|%0, %1}"
21533   [(set_attr "type" "ssecomi")
21534    (set_attr "mode" "DF")])
21535
21536 (define_insn "sse2_ucomi"
21537   [(set (reg:CCFPU 17)
21538         (compare:CCFPU (vec_select:DF
21539                          (match_operand:V2DF 0 "register_operand" "x")
21540                          (parallel [(const_int 0)]))
21541                         (vec_select:DF
21542                          (match_operand:V2DF 1 "register_operand" "x")
21543                          (parallel [(const_int 0)]))))]
21544   "TARGET_SSE2"
21545   "ucomisd\t{%1, %0|%0, %1}"
21546   [(set_attr "type" "ssecomi")
21547    (set_attr "mode" "DF")])
21548
21549 ;; SSE Strange Moves.
21550
21551 (define_insn "sse2_movmskpd"
21552   [(set (match_operand:SI 0 "register_operand" "=r")
21553         (unspec:SI [(match_operand:V2DF 1 "register_operand" "x")]
21554                    UNSPEC_MOVMSK))]
21555   "TARGET_SSE2"
21556   "movmskpd\t{%1, %0|%0, %1}"
21557   [(set_attr "type" "ssecvt")
21558    (set_attr "mode" "V2DF")])
21559
21560 (define_insn "sse2_pmovmskb"
21561   [(set (match_operand:SI 0 "register_operand" "=r")
21562         (unspec:SI [(match_operand:V16QI 1 "register_operand" "x")]
21563                    UNSPEC_MOVMSK))]
21564   "TARGET_SSE2"
21565   "pmovmskb\t{%1, %0|%0, %1}"
21566   [(set_attr "type" "ssecvt")
21567    (set_attr "mode" "V2DF")])
21568
21569 (define_insn "sse2_maskmovdqu"
21570   [(set (mem:V16QI (match_operand:SI 0 "register_operand" "D"))
21571         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "x")
21572                        (match_operand:V16QI 2 "register_operand" "x")]
21573                       UNSPEC_MASKMOV))]
21574   "TARGET_SSE2"
21575   ;; @@@ check ordering of operands in intel/nonintel syntax
21576   "maskmovdqu\t{%2, %1|%1, %2}"
21577   [(set_attr "type" "ssecvt")
21578    (set_attr "mode" "TI")])
21579
21580 (define_insn "sse2_maskmovdqu_rex64"
21581   [(set (mem:V16QI (match_operand:DI 0 "register_operand" "D"))
21582         (unspec:V16QI [(match_operand:V16QI 1 "register_operand" "x")
21583                        (match_operand:V16QI 2 "register_operand" "x")]
21584                       UNSPEC_MASKMOV))]
21585   "TARGET_SSE2"
21586   ;; @@@ check ordering of operands in intel/nonintel syntax
21587   "maskmovdqu\t{%2, %1|%1, %2}"
21588   [(set_attr "type" "ssecvt")
21589    (set_attr "mode" "TI")])
21590
21591 (define_insn "sse2_movntv2df"
21592   [(set (match_operand:V2DF 0 "memory_operand" "=m")
21593         (unspec:V2DF [(match_operand:V2DF 1 "register_operand" "x")]
21594                      UNSPEC_MOVNT))]
21595   "TARGET_SSE2"
21596   "movntpd\t{%1, %0|%0, %1}"
21597   [(set_attr "type" "ssecvt")
21598    (set_attr "mode" "V2DF")])
21599
21600 (define_insn "sse2_movntv2di"
21601   [(set (match_operand:V2DI 0 "memory_operand" "=m")
21602         (unspec:V2DI [(match_operand:V2DI 1 "register_operand" "x")]
21603                      UNSPEC_MOVNT))]
21604   "TARGET_SSE2"
21605   "movntdq\t{%1, %0|%0, %1}"
21606   [(set_attr "type" "ssecvt")
21607    (set_attr "mode" "TI")])
21608
21609 (define_insn "sse2_movntsi"
21610   [(set (match_operand:SI 0 "memory_operand" "=m")
21611         (unspec:SI [(match_operand:SI 1 "register_operand" "r")]
21612                    UNSPEC_MOVNT))]
21613   "TARGET_SSE2"
21614   "movnti\t{%1, %0|%0, %1}"
21615   [(set_attr "type" "ssecvt")
21616    (set_attr "mode" "V2DF")])
21617
21618 ;; SSE <-> integer/MMX conversions
21619
21620 ;; Conversions between SI and SF
21621
21622 (define_insn "cvtdq2ps"
21623   [(set (match_operand:V4SF 0 "register_operand" "=x")
21624         (float:V4SF (match_operand:V4SI 1 "nonimmediate_operand" "xm")))]
21625   "TARGET_SSE2"
21626   "cvtdq2ps\t{%1, %0|%0, %1}"
21627   [(set_attr "type" "ssecvt")
21628    (set_attr "mode" "V2DF")])
21629
21630 (define_insn "cvtps2dq"
21631   [(set (match_operand:V4SI 0 "register_operand" "=x")
21632         (fix:V4SI (match_operand:V4SF 1 "nonimmediate_operand" "xm")))]
21633   "TARGET_SSE2"
21634   "cvtps2dq\t{%1, %0|%0, %1}"
21635   [(set_attr "type" "ssecvt")
21636    (set_attr "mode" "TI")])
21637
21638 (define_insn "cvttps2dq"
21639   [(set (match_operand:V4SI 0 "register_operand" "=x")
21640         (unspec:V4SI [(match_operand:V4SF 1 "nonimmediate_operand" "xm")]
21641                      UNSPEC_FIX))]
21642   "TARGET_SSE2"
21643   "cvttps2dq\t{%1, %0|%0, %1}"
21644   [(set_attr "type" "ssecvt")
21645    (set_attr "mode" "TI")])
21646
21647 ;; Conversions between SI and DF
21648
21649 (define_insn "cvtdq2pd"
21650   [(set (match_operand:V2DF 0 "register_operand" "=x")
21651         (float:V2DF (vec_select:V2SI
21652                      (match_operand:V4SI 1 "nonimmediate_operand" "xm")
21653                      (parallel
21654                       [(const_int 0)
21655                        (const_int 1)]))))]
21656   "TARGET_SSE2"
21657   "cvtdq2pd\t{%1, %0|%0, %1}"
21658   [(set_attr "type" "ssecvt")
21659    (set_attr "mode" "V2DF")])
21660
21661 (define_insn "cvtpd2dq"
21662   [(set (match_operand:V4SI 0 "register_operand" "=x")
21663         (vec_concat:V4SI
21664          (fix:V2SI (match_operand:V2DF 1 "nonimmediate_operand" "xm"))
21665          (const_vector:V2SI [(const_int 0) (const_int 0)])))]
21666   "TARGET_SSE2"
21667   "cvtpd2dq\t{%1, %0|%0, %1}"
21668   [(set_attr "type" "ssecvt")
21669    (set_attr "mode" "TI")])
21670
21671 (define_insn "cvttpd2dq"
21672   [(set (match_operand:V4SI 0 "register_operand" "=x")
21673         (vec_concat:V4SI
21674          (unspec:V2SI [(match_operand:V2DF 1 "nonimmediate_operand" "xm")]
21675                       UNSPEC_FIX)
21676          (const_vector:V2SI [(const_int 0) (const_int 0)])))]
21677   "TARGET_SSE2"
21678   "cvttpd2dq\t{%1, %0|%0, %1}"
21679   [(set_attr "type" "ssecvt")
21680    (set_attr "mode" "TI")])
21681
21682 (define_insn "cvtpd2pi"
21683   [(set (match_operand:V2SI 0 "register_operand" "=y")
21684         (fix:V2SI (match_operand:V2DF 1 "nonimmediate_operand" "xm")))]
21685   "TARGET_SSE2"
21686   "cvtpd2pi\t{%1, %0|%0, %1}"
21687   [(set_attr "type" "ssecvt")
21688    (set_attr "mode" "TI")])
21689
21690 (define_insn "cvttpd2pi"
21691   [(set (match_operand:V2SI 0 "register_operand" "=y")
21692         (unspec:V2SI [(match_operand:V2DF 1 "nonimmediate_operand" "xm")]
21693                      UNSPEC_FIX))]
21694   "TARGET_SSE2"
21695   "cvttpd2pi\t{%1, %0|%0, %1}"
21696   [(set_attr "type" "ssecvt")
21697    (set_attr "mode" "TI")])
21698
21699 (define_insn "cvtpi2pd"
21700   [(set (match_operand:V2DF 0 "register_operand" "=x")
21701         (float:V2DF (match_operand:V2SI 1 "nonimmediate_operand" "ym")))]
21702   "TARGET_SSE2"
21703   "cvtpi2pd\t{%1, %0|%0, %1}"
21704   [(set_attr "type" "ssecvt")
21705    (set_attr "mode" "TI")])
21706
21707 ;; Conversions between SI and DF
21708
21709 (define_insn "cvtsd2si"
21710   [(set (match_operand:SI 0 "register_operand" "=r,r")
21711         (fix:SI (vec_select:DF (match_operand:V2DF 1 "register_operand" "x,m")
21712                                (parallel [(const_int 0)]))))]
21713   "TARGET_SSE2"
21714   "cvtsd2si\t{%1, %0|%0, %1}"
21715   [(set_attr "type" "sseicvt")
21716    (set_attr "athlon_decode" "double,vector")
21717    (set_attr "mode" "SI")])
21718
21719 (define_insn "cvtsd2siq"
21720   [(set (match_operand:DI 0 "register_operand" "=r,r")
21721         (fix:DI (vec_select:DF (match_operand:V2DF 1 "register_operand" "x,m")
21722                                (parallel [(const_int 0)]))))]
21723   "TARGET_SSE2 && TARGET_64BIT"
21724   "cvtsd2siq\t{%1, %0|%0, %1}"
21725   [(set_attr "type" "sseicvt")
21726    (set_attr "athlon_decode" "double,vector")
21727    (set_attr "mode" "DI")])
21728
21729 (define_insn "cvttsd2si"
21730   [(set (match_operand:SI 0 "register_operand" "=r,r")
21731         (unspec:SI [(vec_select:DF (match_operand:V2DF 1 "register_operand" "x,xm")
21732                                    (parallel [(const_int 0)]))] UNSPEC_FIX))]
21733   "TARGET_SSE2"
21734   "cvttsd2si\t{%1, %0|%0, %1}"
21735   [(set_attr "type" "sseicvt")
21736    (set_attr "mode" "SI")
21737    (set_attr "athlon_decode" "double,vector")])
21738
21739 (define_insn "cvttsd2siq"
21740   [(set (match_operand:DI 0 "register_operand" "=r,r")
21741         (unspec:DI [(vec_select:DF (match_operand:V2DF 1 "register_operand" "x,xm")
21742                                    (parallel [(const_int 0)]))] UNSPEC_FIX))]
21743   "TARGET_SSE2 && TARGET_64BIT"
21744   "cvttsd2siq\t{%1, %0|%0, %1}"
21745   [(set_attr "type" "sseicvt")
21746    (set_attr "mode" "DI")
21747    (set_attr "athlon_decode" "double,vector")])
21748
21749 (define_insn "cvtsi2sd"
21750   [(set (match_operand:V2DF 0 "register_operand" "=x,x")
21751         (vec_merge:V2DF (match_operand:V2DF 1 "register_operand" "0,0")
21752                         (vec_duplicate:V2DF
21753                           (float:DF
21754                             (match_operand:SI 2 "nonimmediate_operand" "r,rm")))
21755                         (const_int 2)))]
21756   "TARGET_SSE2"
21757   "cvtsi2sd\t{%2, %0|%0, %2}"
21758   [(set_attr "type" "sseicvt")
21759    (set_attr "mode" "DF")
21760    (set_attr "athlon_decode" "double,direct")])
21761
21762 (define_insn "cvtsi2sdq"
21763   [(set (match_operand:V2DF 0 "register_operand" "=x,x")
21764         (vec_merge:V2DF (match_operand:V2DF 1 "register_operand" "0,0")
21765                         (vec_duplicate:V2DF
21766                           (float:DF
21767                             (match_operand:DI 2 "nonimmediate_operand" "r,rm")))
21768                         (const_int 2)))]
21769   "TARGET_SSE2 && TARGET_64BIT"
21770   "cvtsi2sdq\t{%2, %0|%0, %2}"
21771   [(set_attr "type" "sseicvt")
21772    (set_attr "mode" "DF")
21773    (set_attr "athlon_decode" "double,direct")])
21774
21775 ;; Conversions between SF and DF
21776
21777 (define_insn "cvtsd2ss"
21778   [(set (match_operand:V4SF 0 "register_operand" "=x,x")
21779         (vec_merge:V4SF (match_operand:V4SF 1 "register_operand" "0,0")
21780                         (vec_duplicate:V4SF
21781                           (float_truncate:V2SF
21782                             (match_operand:V2DF 2 "nonimmediate_operand" "x,xm")))
21783                         (const_int 14)))]
21784   "TARGET_SSE2"
21785   "cvtsd2ss\t{%2, %0|%0, %2}"
21786   [(set_attr "type" "ssecvt")
21787    (set_attr "athlon_decode" "vector,double")
21788    (set_attr "mode" "SF")])
21789
21790 (define_insn "cvtss2sd"
21791   [(set (match_operand:V2DF 0 "register_operand" "=x")
21792         (vec_merge:V2DF (match_operand:V2DF 1 "register_operand" "0")
21793                         (float_extend:V2DF
21794                           (vec_select:V2SF
21795                             (match_operand:V4SF 2 "nonimmediate_operand" "xm")
21796                             (parallel [(const_int 0)
21797                                        (const_int 1)])))
21798                         (const_int 2)))]
21799   "TARGET_SSE2"
21800   "cvtss2sd\t{%2, %0|%0, %2}"
21801   [(set_attr "type" "ssecvt")
21802    (set_attr "mode" "DF")])
21803
21804 (define_insn "cvtpd2ps"
21805   [(set (match_operand:V4SF 0 "register_operand" "=x")
21806         (subreg:V4SF
21807           (vec_concat:V4SI
21808             (subreg:V2SI (float_truncate:V2SF
21809                            (match_operand:V2DF 1 "nonimmediate_operand" "xm")) 0)
21810             (const_vector:V2SI [(const_int 0) (const_int 0)])) 0))]
21811   "TARGET_SSE2"
21812   "cvtpd2ps\t{%1, %0|%0, %1}"
21813   [(set_attr "type" "ssecvt")
21814    (set_attr "mode" "V4SF")])
21815
21816 (define_insn "cvtps2pd"
21817   [(set (match_operand:V2DF 0 "register_operand" "=x")
21818         (float_extend:V2DF
21819           (vec_select:V2SF (match_operand:V4SF 1 "nonimmediate_operand" "xm")
21820                            (parallel [(const_int 0)
21821                                       (const_int 1)]))))]
21822   "TARGET_SSE2"
21823   "cvtps2pd\t{%1, %0|%0, %1}"
21824   [(set_attr "type" "ssecvt")
21825    (set_attr "mode" "V2DF")])
21826
21827 ;; SSE2 variants of MMX insns
21828
21829 ;; MMX arithmetic
21830
21831 (define_insn "addv16qi3"
21832   [(set (match_operand:V16QI 0 "register_operand" "=x")
21833         (plus:V16QI (match_operand:V16QI 1 "register_operand" "%0")
21834                     (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
21835   "TARGET_SSE2"
21836   "paddb\t{%2, %0|%0, %2}"
21837   [(set_attr "type" "sseiadd")
21838    (set_attr "mode" "TI")])
21839
21840 (define_insn "addv8hi3"
21841   [(set (match_operand:V8HI 0 "register_operand" "=x")
21842         (plus:V8HI (match_operand:V8HI 1 "register_operand" "%0")
21843                    (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
21844   "TARGET_SSE2"
21845   "paddw\t{%2, %0|%0, %2}"
21846   [(set_attr "type" "sseiadd")
21847    (set_attr "mode" "TI")])
21848
21849 (define_insn "addv4si3"
21850   [(set (match_operand:V4SI 0 "register_operand" "=x")
21851         (plus:V4SI (match_operand:V4SI 1 "register_operand" "%0")
21852                    (match_operand:V4SI 2 "nonimmediate_operand" "xm")))]
21853   "TARGET_SSE2"
21854   "paddd\t{%2, %0|%0, %2}"
21855   [(set_attr "type" "sseiadd")
21856    (set_attr "mode" "TI")])
21857
21858 (define_insn "addv2di3"
21859   [(set (match_operand:V2DI 0 "register_operand" "=x")
21860         (plus:V2DI (match_operand:V2DI 1 "register_operand" "%0")
21861                    (match_operand:V2DI 2 "nonimmediate_operand" "xm")))]
21862   "TARGET_SSE2"
21863   "paddq\t{%2, %0|%0, %2}"
21864   [(set_attr "type" "sseiadd")
21865    (set_attr "mode" "TI")])
21866
21867 (define_insn "ssaddv16qi3"
21868   [(set (match_operand:V16QI 0 "register_operand" "=x")
21869         (ss_plus:V16QI (match_operand:V16QI 1 "register_operand" "%0")
21870                        (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
21871   "TARGET_SSE2"
21872   "paddsb\t{%2, %0|%0, %2}"
21873   [(set_attr "type" "sseiadd")
21874    (set_attr "mode" "TI")])
21875
21876 (define_insn "ssaddv8hi3"
21877   [(set (match_operand:V8HI 0 "register_operand" "=x")
21878         (ss_plus:V8HI (match_operand:V8HI 1 "register_operand" "%0")
21879                       (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
21880   "TARGET_SSE2"
21881   "paddsw\t{%2, %0|%0, %2}"
21882   [(set_attr "type" "sseiadd")
21883    (set_attr "mode" "TI")])
21884
21885 (define_insn "usaddv16qi3"
21886   [(set (match_operand:V16QI 0 "register_operand" "=x")
21887         (us_plus:V16QI (match_operand:V16QI 1 "register_operand" "%0")
21888                        (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
21889   "TARGET_SSE2"
21890   "paddusb\t{%2, %0|%0, %2}"
21891   [(set_attr "type" "sseiadd")
21892    (set_attr "mode" "TI")])
21893
21894 (define_insn "usaddv8hi3"
21895   [(set (match_operand:V8HI 0 "register_operand" "=x")
21896         (us_plus:V8HI (match_operand:V8HI 1 "register_operand" "%0")
21897                       (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
21898   "TARGET_SSE2"
21899   "paddusw\t{%2, %0|%0, %2}"
21900   [(set_attr "type" "sseiadd")
21901    (set_attr "mode" "TI")])
21902
21903 (define_insn "subv16qi3"
21904   [(set (match_operand:V16QI 0 "register_operand" "=x")
21905         (minus:V16QI (match_operand:V16QI 1 "register_operand" "0")
21906                      (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
21907   "TARGET_SSE2"
21908   "psubb\t{%2, %0|%0, %2}"
21909   [(set_attr "type" "sseiadd")
21910    (set_attr "mode" "TI")])
21911
21912 (define_insn "subv8hi3"
21913   [(set (match_operand:V8HI 0 "register_operand" "=x")
21914         (minus:V8HI (match_operand:V8HI 1 "register_operand" "0")
21915                     (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
21916   "TARGET_SSE2"
21917   "psubw\t{%2, %0|%0, %2}"
21918   [(set_attr "type" "sseiadd")
21919    (set_attr "mode" "TI")])
21920
21921 (define_insn "subv4si3"
21922   [(set (match_operand:V4SI 0 "register_operand" "=x")
21923         (minus:V4SI (match_operand:V4SI 1 "register_operand" "0")
21924                     (match_operand:V4SI 2 "nonimmediate_operand" "xm")))]
21925   "TARGET_SSE2"
21926   "psubd\t{%2, %0|%0, %2}"
21927   [(set_attr "type" "sseiadd")
21928    (set_attr "mode" "TI")])
21929
21930 (define_insn "subv2di3"
21931   [(set (match_operand:V2DI 0 "register_operand" "=x")
21932         (minus:V2DI (match_operand:V2DI 1 "register_operand" "0")
21933                     (match_operand:V2DI 2 "nonimmediate_operand" "xm")))]
21934   "TARGET_SSE2"
21935   "psubq\t{%2, %0|%0, %2}"
21936   [(set_attr "type" "sseiadd")
21937    (set_attr "mode" "TI")])
21938
21939 (define_insn "sssubv16qi3"
21940   [(set (match_operand:V16QI 0 "register_operand" "=x")
21941         (ss_minus:V16QI (match_operand:V16QI 1 "register_operand" "0")
21942                         (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
21943   "TARGET_SSE2"
21944   "psubsb\t{%2, %0|%0, %2}"
21945   [(set_attr "type" "sseiadd")
21946    (set_attr "mode" "TI")])
21947
21948 (define_insn "sssubv8hi3"
21949   [(set (match_operand:V8HI 0 "register_operand" "=x")
21950         (ss_minus:V8HI (match_operand:V8HI 1 "register_operand" "0")
21951                        (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
21952   "TARGET_SSE2"
21953   "psubsw\t{%2, %0|%0, %2}"
21954   [(set_attr "type" "sseiadd")
21955    (set_attr "mode" "TI")])
21956
21957 (define_insn "ussubv16qi3"
21958   [(set (match_operand:V16QI 0 "register_operand" "=x")
21959         (us_minus:V16QI (match_operand:V16QI 1 "register_operand" "0")
21960                         (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
21961   "TARGET_SSE2"
21962   "psubusb\t{%2, %0|%0, %2}"
21963   [(set_attr "type" "sseiadd")
21964    (set_attr "mode" "TI")])
21965
21966 (define_insn "ussubv8hi3"
21967   [(set (match_operand:V8HI 0 "register_operand" "=x")
21968         (us_minus:V8HI (match_operand:V8HI 1 "register_operand" "0")
21969                        (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
21970   "TARGET_SSE2"
21971   "psubusw\t{%2, %0|%0, %2}"
21972   [(set_attr "type" "sseiadd")
21973    (set_attr "mode" "TI")])
21974
21975 (define_insn "mulv8hi3"
21976   [(set (match_operand:V8HI 0 "register_operand" "=x")
21977         (mult:V8HI (match_operand:V8HI 1 "register_operand" "0")
21978                    (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
21979   "TARGET_SSE2"
21980   "pmullw\t{%2, %0|%0, %2}"
21981   [(set_attr "type" "sseimul")
21982    (set_attr "mode" "TI")])
21983
21984 (define_insn "smulv8hi3_highpart"
21985   [(set (match_operand:V8HI 0 "register_operand" "=x")
21986         (truncate:V8HI
21987          (lshiftrt:V8SI
21988           (mult:V8SI (sign_extend:V8SI (match_operand:V8HI 1 "register_operand" "0"))
21989                      (sign_extend:V8SI (match_operand:V8HI 2 "nonimmediate_operand" "xm")))
21990           (const_int 16))))]
21991   "TARGET_SSE2"
21992   "pmulhw\t{%2, %0|%0, %2}"
21993   [(set_attr "type" "sseimul")
21994    (set_attr "mode" "TI")])
21995
21996 (define_insn "umulv8hi3_highpart"
21997   [(set (match_operand:V8HI 0 "register_operand" "=x")
21998         (truncate:V8HI
21999          (lshiftrt:V8SI
22000           (mult:V8SI (zero_extend:V8SI (match_operand:V8HI 1 "register_operand" "0"))
22001                      (zero_extend:V8SI (match_operand:V8HI 2 "nonimmediate_operand" "xm")))
22002           (const_int 16))))]
22003   "TARGET_SSE2"
22004   "pmulhuw\t{%2, %0|%0, %2}"
22005   [(set_attr "type" "sseimul")
22006    (set_attr "mode" "TI")])
22007
22008 (define_insn "sse2_umulsidi3"
22009   [(set (match_operand:DI 0 "register_operand" "=y")
22010         (mult:DI (zero_extend:DI (vec_select:SI
22011                                   (match_operand:V2SI 1 "register_operand" "0")
22012                                   (parallel [(const_int 0)])))
22013                  (zero_extend:DI (vec_select:SI
22014                                   (match_operand:V2SI 2 "nonimmediate_operand" "ym")
22015                                   (parallel [(const_int 0)])))))]
22016   "TARGET_SSE2"
22017   "pmuludq\t{%2, %0|%0, %2}"
22018   [(set_attr "type" "sseimul")
22019    (set_attr "mode" "TI")])
22020
22021 (define_insn "sse2_umulv2siv2di3"
22022   [(set (match_operand:V2DI 0 "register_operand" "=x")
22023         (mult:V2DI (zero_extend:V2DI
22024                      (vec_select:V2SI
22025                        (match_operand:V4SI 1 "register_operand" "0")
22026                        (parallel [(const_int 0) (const_int 2)])))
22027                    (zero_extend:V2DI
22028                      (vec_select:V2SI
22029                        (match_operand:V4SI 2 "nonimmediate_operand" "xm")
22030                        (parallel [(const_int 0) (const_int 2)])))))]
22031   "TARGET_SSE2"
22032   "pmuludq\t{%2, %0|%0, %2}"
22033   [(set_attr "type" "sseimul")
22034    (set_attr "mode" "TI")])
22035
22036 (define_insn "sse2_pmaddwd"
22037   [(set (match_operand:V4SI 0 "register_operand" "=x")
22038         (plus:V4SI
22039          (mult:V4SI
22040           (sign_extend:V4SI (vec_select:V4HI (match_operand:V8HI 1 "register_operand" "0")
22041                                              (parallel [(const_int 0)
22042                                                         (const_int 2)
22043                                                         (const_int 4)
22044                                                         (const_int 6)])))
22045           (sign_extend:V4SI (vec_select:V4HI (match_operand:V8HI 2 "nonimmediate_operand" "xm")
22046                                              (parallel [(const_int 0)
22047                                                         (const_int 2)
22048                                                         (const_int 4)
22049                                                         (const_int 6)]))))
22050          (mult:V4SI
22051           (sign_extend:V4SI (vec_select:V4HI (match_dup 1)
22052                                              (parallel [(const_int 1)
22053                                                         (const_int 3)
22054                                                         (const_int 5)
22055                                                         (const_int 7)])))
22056           (sign_extend:V4SI (vec_select:V4HI (match_dup 2)
22057                                              (parallel [(const_int 1)
22058                                                         (const_int 3)
22059                                                         (const_int 5)
22060                                                         (const_int 7)]))))))]
22061   "TARGET_SSE2"
22062   "pmaddwd\t{%2, %0|%0, %2}"
22063   [(set_attr "type" "sseiadd")
22064    (set_attr "mode" "TI")])
22065
22066 ;; Same as pxor, but don't show input operands so that we don't think
22067 ;; they are live.
22068 (define_insn "sse2_clrti"
22069   [(set (match_operand:TI 0 "register_operand" "=x") (const_int 0))]
22070   "TARGET_SSE2"
22071 {
22072   if (get_attr_mode (insn) == MODE_TI)
22073     return "pxor\t%0, %0";
22074   else
22075     return "xorps\t%0, %0";
22076 }
22077   [(set_attr "type" "ssemov")
22078    (set_attr "memory" "none")
22079    (set (attr "mode")
22080               (if_then_else
22081                 (ne (symbol_ref "optimize_size")
22082                     (const_int 0))
22083                 (const_string "V4SF")
22084                 (const_string "TI")))])
22085
22086 ;; MMX unsigned averages/sum of absolute differences
22087
22088 (define_insn "sse2_uavgv16qi3"
22089   [(set (match_operand:V16QI 0 "register_operand" "=x")
22090         (ashiftrt:V16QI
22091          (plus:V16QI (plus:V16QI
22092                      (match_operand:V16QI 1 "register_operand" "0")
22093                      (match_operand:V16QI 2 "nonimmediate_operand" "xm"))
22094                      (const_vector:V16QI [(const_int 1) (const_int 1)
22095                                           (const_int 1) (const_int 1)
22096                                           (const_int 1) (const_int 1)
22097                                           (const_int 1) (const_int 1)
22098                                           (const_int 1) (const_int 1)
22099                                           (const_int 1) (const_int 1)
22100                                           (const_int 1) (const_int 1)
22101                                           (const_int 1) (const_int 1)]))
22102          (const_int 1)))]
22103   "TARGET_SSE2"
22104   "pavgb\t{%2, %0|%0, %2}"
22105   [(set_attr "type" "sseiadd")
22106    (set_attr "mode" "TI")])
22107
22108 (define_insn "sse2_uavgv8hi3"
22109   [(set (match_operand:V8HI 0 "register_operand" "=x")
22110         (ashiftrt:V8HI
22111          (plus:V8HI (plus:V8HI
22112                      (match_operand:V8HI 1 "register_operand" "0")
22113                      (match_operand:V8HI 2 "nonimmediate_operand" "xm"))
22114                     (const_vector:V8HI [(const_int 1) (const_int 1)
22115                                         (const_int 1) (const_int 1)
22116                                         (const_int 1) (const_int 1)
22117                                         (const_int 1) (const_int 1)]))
22118          (const_int 1)))]
22119   "TARGET_SSE2"
22120   "pavgw\t{%2, %0|%0, %2}"
22121   [(set_attr "type" "sseiadd")
22122    (set_attr "mode" "TI")])
22123
22124 ;; @@@ this isn't the right representation.
22125 (define_insn "sse2_psadbw"
22126   [(set (match_operand:V2DI 0 "register_operand" "=x")
22127         (unspec:V2DI [(match_operand:V16QI 1 "register_operand" "0")
22128                       (match_operand:V16QI 2 "nonimmediate_operand" "xm")]
22129                      UNSPEC_PSADBW))]
22130   "TARGET_SSE2"
22131   "psadbw\t{%2, %0|%0, %2}"
22132   [(set_attr "type" "sseiadd")
22133    (set_attr "mode" "TI")])
22134
22135
22136 ;; MMX insert/extract/shuffle
22137
22138 (define_insn "sse2_pinsrw"
22139   [(set (match_operand:V8HI 0 "register_operand" "=x")
22140         (vec_merge:V8HI (match_operand:V8HI 1 "register_operand" "0")
22141                         (vec_duplicate:V8HI
22142                          (truncate:HI
22143                            (match_operand:SI 2 "nonimmediate_operand" "rm")))
22144                         (match_operand:SI 3 "const_0_to_255_operand" "N")))]
22145   "TARGET_SSE2"
22146   "pinsrw\t{%3, %2, %0|%0, %2, %3}"
22147   [(set_attr "type" "ssecvt")
22148    (set_attr "mode" "TI")])
22149
22150 (define_insn "sse2_pextrw"
22151   [(set (match_operand:SI 0 "register_operand" "=r")
22152         (zero_extend:SI
22153           (vec_select:HI (match_operand:V8HI 1 "register_operand" "x")
22154                          (parallel
22155                           [(match_operand:SI 2 "const_0_to_7_operand" "N")]))))]
22156   "TARGET_SSE2"
22157   "pextrw\t{%2, %1, %0|%0, %1, %2}"
22158   [(set_attr "type" "ssecvt")
22159    (set_attr "mode" "TI")])
22160
22161 (define_insn "sse2_pshufd"
22162   [(set (match_operand:V4SI 0 "register_operand" "=x")
22163         (unspec:V4SI [(match_operand:V4SI 1 "register_operand" "0")
22164                       (match_operand:SI 2 "immediate_operand" "i")]
22165                      UNSPEC_SHUFFLE))]
22166   "TARGET_SSE2"
22167   "pshufd\t{%2, %1, %0|%0, %1, %2}"
22168   [(set_attr "type" "ssecvt")
22169    (set_attr "mode" "TI")])
22170
22171 (define_insn "sse2_pshuflw"
22172   [(set (match_operand:V8HI 0 "register_operand" "=x")
22173         (unspec:V8HI [(match_operand:V8HI 1 "register_operand" "0")
22174                       (match_operand:SI 2 "immediate_operand" "i")]
22175                      UNSPEC_PSHUFLW))]
22176   "TARGET_SSE2"
22177   "pshuflw\t{%2, %1, %0|%0, %1, %2}"
22178   [(set_attr "type" "ssecvt")
22179    (set_attr "mode" "TI")])
22180
22181 (define_insn "sse2_pshufhw"
22182   [(set (match_operand:V8HI 0 "register_operand" "=x")
22183         (unspec:V8HI [(match_operand:V8HI 1 "register_operand" "0")
22184                       (match_operand:SI 2 "immediate_operand" "i")]
22185                      UNSPEC_PSHUFHW))]
22186   "TARGET_SSE2"
22187   "pshufhw\t{%2, %1, %0|%0, %1, %2}"
22188   [(set_attr "type" "ssecvt")
22189    (set_attr "mode" "TI")])
22190
22191 ;; MMX mask-generating comparisons
22192
22193 (define_insn "eqv16qi3"
22194   [(set (match_operand:V16QI 0 "register_operand" "=x")
22195         (eq:V16QI (match_operand:V16QI 1 "register_operand" "0")
22196                  (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
22197   "TARGET_SSE2"
22198   "pcmpeqb\t{%2, %0|%0, %2}"
22199   [(set_attr "type" "ssecmp")
22200    (set_attr "mode" "TI")])
22201
22202 (define_insn "eqv8hi3"
22203   [(set (match_operand:V8HI 0 "register_operand" "=x")
22204         (eq:V8HI (match_operand:V8HI 1 "register_operand" "0")
22205                  (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
22206   "TARGET_SSE2"
22207   "pcmpeqw\t{%2, %0|%0, %2}"
22208   [(set_attr "type" "ssecmp")
22209    (set_attr "mode" "TI")])
22210
22211 (define_insn "eqv4si3"
22212   [(set (match_operand:V4SI 0 "register_operand" "=x")
22213         (eq:V4SI (match_operand:V4SI 1 "register_operand" "0")
22214                  (match_operand:V4SI 2 "nonimmediate_operand" "xm")))]
22215   "TARGET_SSE2"
22216   "pcmpeqd\t{%2, %0|%0, %2}"
22217   [(set_attr "type" "ssecmp")
22218    (set_attr "mode" "TI")])
22219
22220 (define_insn "gtv16qi3"
22221   [(set (match_operand:V16QI 0 "register_operand" "=x")
22222         (gt:V16QI (match_operand:V16QI 1 "register_operand" "0")
22223                  (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
22224   "TARGET_SSE2"
22225   "pcmpgtb\t{%2, %0|%0, %2}"
22226   [(set_attr "type" "ssecmp")
22227    (set_attr "mode" "TI")])
22228
22229 (define_insn "gtv8hi3"
22230   [(set (match_operand:V8HI 0 "register_operand" "=x")
22231         (gt:V8HI (match_operand:V8HI 1 "register_operand" "0")
22232                  (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
22233   "TARGET_SSE2"
22234   "pcmpgtw\t{%2, %0|%0, %2}"
22235   [(set_attr "type" "ssecmp")
22236    (set_attr "mode" "TI")])
22237
22238 (define_insn "gtv4si3"
22239   [(set (match_operand:V4SI 0 "register_operand" "=x")
22240         (gt:V4SI (match_operand:V4SI 1 "register_operand" "0")
22241                  (match_operand:V4SI 2 "nonimmediate_operand" "xm")))]
22242   "TARGET_SSE2"
22243   "pcmpgtd\t{%2, %0|%0, %2}"
22244   [(set_attr "type" "ssecmp")
22245    (set_attr "mode" "TI")])
22246
22247
22248 ;; MMX max/min insns
22249
22250 (define_insn "umaxv16qi3"
22251   [(set (match_operand:V16QI 0 "register_operand" "=x")
22252         (umax:V16QI (match_operand:V16QI 1 "register_operand" "0")
22253                    (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
22254   "TARGET_SSE2"
22255   "pmaxub\t{%2, %0|%0, %2}"
22256   [(set_attr "type" "sseiadd")
22257    (set_attr "mode" "TI")])
22258
22259 (define_insn "smaxv8hi3"
22260   [(set (match_operand:V8HI 0 "register_operand" "=x")
22261         (smax:V8HI (match_operand:V8HI 1 "register_operand" "0")
22262                    (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
22263   "TARGET_SSE2"
22264   "pmaxsw\t{%2, %0|%0, %2}"
22265   [(set_attr "type" "sseiadd")
22266    (set_attr "mode" "TI")])
22267
22268 (define_insn "uminv16qi3"
22269   [(set (match_operand:V16QI 0 "register_operand" "=x")
22270         (umin:V16QI (match_operand:V16QI 1 "register_operand" "0")
22271                    (match_operand:V16QI 2 "nonimmediate_operand" "xm")))]
22272   "TARGET_SSE2"
22273   "pminub\t{%2, %0|%0, %2}"
22274   [(set_attr "type" "sseiadd")
22275    (set_attr "mode" "TI")])
22276
22277 (define_insn "sminv8hi3"
22278   [(set (match_operand:V8HI 0 "register_operand" "=x")
22279         (smin:V8HI (match_operand:V8HI 1 "register_operand" "0")
22280                    (match_operand:V8HI 2 "nonimmediate_operand" "xm")))]
22281   "TARGET_SSE2"
22282   "pminsw\t{%2, %0|%0, %2}"
22283   [(set_attr "type" "sseiadd")
22284    (set_attr "mode" "TI")])
22285
22286
22287 ;; MMX shifts
22288
22289 (define_insn "ashrv8hi3"
22290   [(set (match_operand:V8HI 0 "register_operand" "=x")
22291         (ashiftrt:V8HI (match_operand:V8HI 1 "register_operand" "0")
22292                        (match_operand:SI 2 "nonmemory_operand" "xi")))]
22293   "TARGET_SSE2"
22294   "psraw\t{%2, %0|%0, %2}"
22295   [(set_attr "type" "sseishft")
22296    (set_attr "mode" "TI")])
22297
22298 (define_insn "ashrv4si3"
22299   [(set (match_operand:V4SI 0 "register_operand" "=x")
22300         (ashiftrt:V4SI (match_operand:V4SI 1 "register_operand" "0")
22301                        (match_operand:SI 2 "nonmemory_operand" "xi")))]
22302   "TARGET_SSE2"
22303   "psrad\t{%2, %0|%0, %2}"
22304   [(set_attr "type" "sseishft")
22305    (set_attr "mode" "TI")])
22306
22307 (define_insn "lshrv8hi3"
22308   [(set (match_operand:V8HI 0 "register_operand" "=x")
22309         (lshiftrt:V8HI (match_operand:V8HI 1 "register_operand" "0")
22310                        (match_operand:SI 2 "nonmemory_operand" "xi")))]
22311   "TARGET_SSE2"
22312   "psrlw\t{%2, %0|%0, %2}"
22313   [(set_attr "type" "sseishft")
22314    (set_attr "mode" "TI")])
22315
22316 (define_insn "lshrv4si3"
22317   [(set (match_operand:V4SI 0 "register_operand" "=x")
22318         (lshiftrt:V4SI (match_operand:V4SI 1 "register_operand" "0")
22319                        (match_operand:SI 2 "nonmemory_operand" "xi")))]
22320   "TARGET_SSE2"
22321   "psrld\t{%2, %0|%0, %2}"
22322   [(set_attr "type" "sseishft")
22323    (set_attr "mode" "TI")])
22324
22325 (define_insn "lshrv2di3"
22326   [(set (match_operand:V2DI 0 "register_operand" "=x")
22327         (lshiftrt:V2DI (match_operand:V2DI 1 "register_operand" "0")
22328                        (match_operand:SI 2 "nonmemory_operand" "xi")))]
22329   "TARGET_SSE2"
22330   "psrlq\t{%2, %0|%0, %2}"
22331   [(set_attr "type" "sseishft")
22332    (set_attr "mode" "TI")])
22333
22334 (define_insn "ashlv8hi3"
22335   [(set (match_operand:V8HI 0 "register_operand" "=x")
22336         (ashift:V8HI (match_operand:V8HI 1 "register_operand" "0")
22337                      (match_operand:SI 2 "nonmemory_operand" "xi")))]
22338   "TARGET_SSE2"
22339   "psllw\t{%2, %0|%0, %2}"
22340   [(set_attr "type" "sseishft")
22341    (set_attr "mode" "TI")])
22342
22343 (define_insn "ashlv4si3"
22344   [(set (match_operand:V4SI 0 "register_operand" "=x")
22345         (ashift:V4SI (match_operand:V4SI 1 "register_operand" "0")
22346                      (match_operand:SI 2 "nonmemory_operand" "xi")))]
22347   "TARGET_SSE2"
22348   "pslld\t{%2, %0|%0, %2}"
22349   [(set_attr "type" "sseishft")
22350    (set_attr "mode" "TI")])
22351
22352 (define_insn "ashlv2di3"
22353   [(set (match_operand:V2DI 0 "register_operand" "=x")
22354         (ashift:V2DI (match_operand:V2DI 1 "register_operand" "0")
22355                      (match_operand:SI 2 "nonmemory_operand" "xi")))]
22356   "TARGET_SSE2"
22357   "psllq\t{%2, %0|%0, %2}"
22358   [(set_attr "type" "sseishft")
22359    (set_attr "mode" "TI")])
22360
22361 (define_insn "ashrv8hi3_ti"
22362   [(set (match_operand:V8HI 0 "register_operand" "=x")
22363         (ashiftrt:V8HI (match_operand:V8HI 1 "register_operand" "0")
22364                        (subreg:SI (match_operand:V2DI 2 "nonmemory_operand" "xi") 0)))]
22365   "TARGET_SSE2"
22366   "psraw\t{%2, %0|%0, %2}"
22367   [(set_attr "type" "sseishft")
22368    (set_attr "mode" "TI")])
22369
22370 (define_insn "ashrv4si3_ti"
22371   [(set (match_operand:V4SI 0 "register_operand" "=x")
22372         (ashiftrt:V4SI (match_operand:V4SI 1 "register_operand" "0")
22373                        (subreg:SI (match_operand:V2DI 2 "nonmemory_operand" "xi") 0)))]
22374   "TARGET_SSE2"
22375   "psrad\t{%2, %0|%0, %2}"
22376   [(set_attr "type" "sseishft")
22377    (set_attr "mode" "TI")])
22378
22379 (define_insn "lshrv8hi3_ti"
22380   [(set (match_operand:V8HI 0 "register_operand" "=x")
22381         (lshiftrt:V8HI (match_operand:V8HI 1 "register_operand" "0")
22382                        (subreg:SI (match_operand:V2DI 2 "nonmemory_operand" "xi") 0)))]
22383   "TARGET_SSE2"
22384   "psrlw\t{%2, %0|%0, %2}"
22385   [(set_attr "type" "sseishft")
22386    (set_attr "mode" "TI")])
22387
22388 (define_insn "lshrv4si3_ti"
22389   [(set (match_operand:V4SI 0 "register_operand" "=x")
22390         (lshiftrt:V4SI (match_operand:V4SI 1 "register_operand" "0")
22391                        (subreg:SI (match_operand:V2DI 2 "nonmemory_operand" "xi") 0)))]
22392   "TARGET_SSE2"
22393   "psrld\t{%2, %0|%0, %2}"
22394   [(set_attr "type" "sseishft")
22395    (set_attr "mode" "TI")])
22396
22397 (define_insn "lshrv2di3_ti"
22398   [(set (match_operand:V2DI 0 "register_operand" "=x")
22399         (lshiftrt:V2DI (match_operand:V2DI 1 "register_operand" "0")
22400                        (subreg:SI (match_operand:V2DI 2 "nonmemory_operand" "xi") 0)))]
22401   "TARGET_SSE2"
22402   "psrlq\t{%2, %0|%0, %2}"
22403   [(set_attr "type" "sseishft")
22404    (set_attr "mode" "TI")])
22405
22406 (define_insn "ashlv8hi3_ti"
22407   [(set (match_operand:V8HI 0 "register_operand" "=x")
22408         (ashift:V8HI (match_operand:V8HI 1 "register_operand" "0")
22409                      (subreg:SI (match_operand:V2DI 2 "nonmemory_operand" "xi") 0)))]
22410   "TARGET_SSE2"
22411   "psllw\t{%2, %0|%0, %2}"
22412   [(set_attr "type" "sseishft")
22413    (set_attr "mode" "TI")])
22414
22415 (define_insn "ashlv4si3_ti"
22416   [(set (match_operand:V4SI 0 "register_operand" "=x")
22417         (ashift:V4SI (match_operand:V4SI 1 "register_operand" "0")
22418                      (subreg:SI (match_operand:V2DI 2 "nonmemory_operand" "xi") 0)))]
22419   "TARGET_SSE2"
22420   "pslld\t{%2, %0|%0, %2}"
22421   [(set_attr "type" "sseishft")
22422    (set_attr "mode" "TI")])
22423
22424 (define_insn "ashlv2di3_ti"
22425   [(set (match_operand:V2DI 0 "register_operand" "=x")
22426         (ashift:V2DI (match_operand:V2DI 1 "register_operand" "0")
22427                      (subreg:SI (match_operand:V2DI 2 "nonmemory_operand" "xi") 0)))]
22428   "TARGET_SSE2"
22429   "psllq\t{%2, %0|%0, %2}"
22430   [(set_attr "type" "sseishft")
22431    (set_attr "mode" "TI")])
22432
22433 ;; See logical MMX insns for the reason for the unspec.  Strictly speaking
22434 ;; we wouldn't need here it since we never generate TImode arithmetic.
22435
22436 ;; There has to be some kind of prize for the weirdest new instruction...
22437 (define_insn "sse2_ashlti3"
22438   [(set (match_operand:TI 0 "register_operand" "=x")
22439         (unspec:TI
22440          [(ashift:TI (match_operand:TI 1 "register_operand" "0")
22441                      (mult:SI (match_operand:SI 2 "immediate_operand" "i")
22442                                (const_int 8)))] UNSPEC_NOP))]
22443   "TARGET_SSE2"
22444   "pslldq\t{%2, %0|%0, %2}"
22445   [(set_attr "type" "sseishft")
22446    (set_attr "mode" "TI")])
22447
22448 (define_insn "sse2_lshrti3"
22449   [(set (match_operand:TI 0 "register_operand" "=x")
22450         (unspec:TI
22451          [(lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
22452                        (mult:SI (match_operand:SI 2 "immediate_operand" "i")
22453                                 (const_int 8)))] UNSPEC_NOP))]
22454   "TARGET_SSE2"
22455   "psrldq\t{%2, %0|%0, %2}"
22456   [(set_attr "type" "sseishft")
22457    (set_attr "mode" "TI")])
22458
22459 ;; SSE unpack
22460
22461 (define_insn "sse2_unpckhpd"
22462   [(set (match_operand:V2DF 0 "register_operand" "=x")
22463         (vec_concat:V2DF
22464          (vec_select:DF (match_operand:V2DF 1 "register_operand" "0")
22465                         (parallel [(const_int 1)]))
22466          (vec_select:DF (match_operand:V2DF 2 "register_operand" "x")
22467                         (parallel [(const_int 1)]))))]
22468   "TARGET_SSE2"
22469   "unpckhpd\t{%2, %0|%0, %2}"
22470   [(set_attr "type" "ssecvt")
22471    (set_attr "mode" "V2DF")])
22472
22473 (define_insn "sse2_unpcklpd"
22474   [(set (match_operand:V2DF 0 "register_operand" "=x")
22475         (vec_concat:V2DF
22476          (vec_select:DF (match_operand:V2DF 1 "register_operand" "0")
22477                         (parallel [(const_int 0)]))
22478          (vec_select:DF (match_operand:V2DF 2 "register_operand" "x")
22479                         (parallel [(const_int 0)]))))]
22480   "TARGET_SSE2"
22481   "unpcklpd\t{%2, %0|%0, %2}"
22482   [(set_attr "type" "ssecvt")
22483    (set_attr "mode" "V2DF")])
22484
22485 ;; MMX pack/unpack insns.
22486
22487 (define_insn "sse2_packsswb"
22488   [(set (match_operand:V16QI 0 "register_operand" "=x")
22489         (vec_concat:V16QI
22490          (ss_truncate:V8QI (match_operand:V8HI 1 "register_operand" "0"))
22491          (ss_truncate:V8QI (match_operand:V8HI 2 "register_operand" "x"))))]
22492   "TARGET_SSE2"
22493   "packsswb\t{%2, %0|%0, %2}"
22494   [(set_attr "type" "ssecvt")
22495    (set_attr "mode" "TI")])
22496
22497 (define_insn "sse2_packssdw"
22498   [(set (match_operand:V8HI 0 "register_operand" "=x")
22499         (vec_concat:V8HI
22500          (ss_truncate:V4HI (match_operand:V4SI 1 "register_operand" "0"))
22501          (ss_truncate:V4HI (match_operand:V4SI 2 "register_operand" "x"))))]
22502   "TARGET_SSE2"
22503   "packssdw\t{%2, %0|%0, %2}"
22504   [(set_attr "type" "ssecvt")
22505    (set_attr "mode" "TI")])
22506
22507 (define_insn "sse2_packuswb"
22508   [(set (match_operand:V16QI 0 "register_operand" "=x")
22509         (vec_concat:V16QI
22510          (us_truncate:V8QI (match_operand:V8HI 1 "register_operand" "0"))
22511          (us_truncate:V8QI (match_operand:V8HI 2 "register_operand" "x"))))]
22512   "TARGET_SSE2"
22513   "packuswb\t{%2, %0|%0, %2}"
22514   [(set_attr "type" "ssecvt")
22515    (set_attr "mode" "TI")])
22516
22517 (define_insn "sse2_punpckhbw"
22518   [(set (match_operand:V16QI 0 "register_operand" "=x")
22519         (vec_merge:V16QI
22520          (vec_select:V16QI (match_operand:V16QI 1 "register_operand" "0")
22521                            (parallel [(const_int 8) (const_int 0)
22522                                       (const_int 9) (const_int 1)
22523                                       (const_int 10) (const_int 2)
22524                                       (const_int 11) (const_int 3)
22525                                       (const_int 12) (const_int 4)
22526                                       (const_int 13) (const_int 5)
22527                                       (const_int 14) (const_int 6)
22528                                       (const_int 15) (const_int 7)]))
22529          (vec_select:V16QI (match_operand:V16QI 2 "register_operand" "x")
22530                            (parallel [(const_int 0) (const_int 8)
22531                                       (const_int 1) (const_int 9)
22532                                       (const_int 2) (const_int 10)
22533                                       (const_int 3) (const_int 11)
22534                                       (const_int 4) (const_int 12)
22535                                       (const_int 5) (const_int 13)
22536                                       (const_int 6) (const_int 14)
22537                                       (const_int 7) (const_int 15)]))
22538          (const_int 21845)))]
22539   "TARGET_SSE2"
22540   "punpckhbw\t{%2, %0|%0, %2}"
22541   [(set_attr "type" "ssecvt")
22542    (set_attr "mode" "TI")])
22543
22544 (define_insn "sse2_punpckhwd"
22545   [(set (match_operand:V8HI 0 "register_operand" "=x")
22546         (vec_merge:V8HI
22547          (vec_select:V8HI (match_operand:V8HI 1 "register_operand" "0")
22548                           (parallel [(const_int 4) (const_int 0)
22549                                      (const_int 5) (const_int 1)
22550                                      (const_int 6) (const_int 2)
22551                                      (const_int 7) (const_int 3)]))
22552          (vec_select:V8HI (match_operand:V8HI 2 "register_operand" "x")
22553                           (parallel [(const_int 0) (const_int 4)
22554                                      (const_int 1) (const_int 5)
22555                                      (const_int 2) (const_int 6)
22556                                      (const_int 3) (const_int 7)]))
22557          (const_int 85)))]
22558   "TARGET_SSE2"
22559   "punpckhwd\t{%2, %0|%0, %2}"
22560   [(set_attr "type" "ssecvt")
22561    (set_attr "mode" "TI")])
22562
22563 (define_insn "sse2_punpckhdq"
22564   [(set (match_operand:V4SI 0 "register_operand" "=x")
22565         (vec_merge:V4SI
22566          (vec_select:V4SI (match_operand:V4SI 1 "register_operand" "0")
22567                           (parallel [(const_int 2) (const_int 0)
22568                                      (const_int 3) (const_int 1)]))
22569          (vec_select:V4SI (match_operand:V4SI 2 "register_operand" "x")
22570                           (parallel [(const_int 0) (const_int 2)
22571                                      (const_int 1) (const_int 3)]))
22572          (const_int 5)))]
22573   "TARGET_SSE2"
22574   "punpckhdq\t{%2, %0|%0, %2}"
22575   [(set_attr "type" "ssecvt")
22576    (set_attr "mode" "TI")])
22577
22578 (define_insn "sse2_punpcklbw"
22579   [(set (match_operand:V16QI 0 "register_operand" "=x")
22580         (vec_merge:V16QI
22581          (vec_select:V16QI (match_operand:V16QI 1 "register_operand" "0")
22582                            (parallel [(const_int 0) (const_int 8)
22583                                       (const_int 1) (const_int 9)
22584                                       (const_int 2) (const_int 10)
22585                                       (const_int 3) (const_int 11)
22586                                       (const_int 4) (const_int 12)
22587                                       (const_int 5) (const_int 13)
22588                                       (const_int 6) (const_int 14)
22589                                       (const_int 7) (const_int 15)]))
22590          (vec_select:V16QI (match_operand:V16QI 2 "register_operand" "x")
22591                            (parallel [(const_int 8) (const_int 0)
22592                                       (const_int 9) (const_int 1)
22593                                       (const_int 10) (const_int 2)
22594                                       (const_int 11) (const_int 3)
22595                                       (const_int 12) (const_int 4)
22596                                       (const_int 13) (const_int 5)
22597                                       (const_int 14) (const_int 6)
22598                                       (const_int 15) (const_int 7)]))
22599          (const_int 21845)))]
22600   "TARGET_SSE2"
22601   "punpcklbw\t{%2, %0|%0, %2}"
22602   [(set_attr "type" "ssecvt")
22603    (set_attr "mode" "TI")])
22604
22605 (define_insn "sse2_punpcklwd"
22606   [(set (match_operand:V8HI 0 "register_operand" "=x")
22607         (vec_merge:V8HI
22608          (vec_select:V8HI (match_operand:V8HI 1 "register_operand" "0")
22609                           (parallel [(const_int 0) (const_int 4)
22610                                      (const_int 1) (const_int 5)
22611                                      (const_int 2) (const_int 6)
22612                                      (const_int 3) (const_int 7)]))
22613          (vec_select:V8HI (match_operand:V8HI 2 "register_operand" "x")
22614                           (parallel [(const_int 4) (const_int 0)
22615                                      (const_int 5) (const_int 1)
22616                                      (const_int 6) (const_int 2)
22617                                      (const_int 7) (const_int 3)]))
22618          (const_int 85)))]
22619   "TARGET_SSE2"
22620   "punpcklwd\t{%2, %0|%0, %2}"
22621   [(set_attr "type" "ssecvt")
22622    (set_attr "mode" "TI")])
22623
22624 (define_insn "sse2_punpckldq"
22625   [(set (match_operand:V4SI 0 "register_operand" "=x")
22626         (vec_merge:V4SI
22627          (vec_select:V4SI (match_operand:V4SI 1 "register_operand" "0")
22628                           (parallel [(const_int 0) (const_int 2)
22629                                      (const_int 1) (const_int 3)]))
22630          (vec_select:V4SI (match_operand:V4SI 2 "register_operand" "x")
22631                           (parallel [(const_int 2) (const_int 0)
22632                                      (const_int 3) (const_int 1)]))
22633          (const_int 5)))]
22634   "TARGET_SSE2"
22635   "punpckldq\t{%2, %0|%0, %2}"
22636   [(set_attr "type" "ssecvt")
22637    (set_attr "mode" "TI")])
22638
22639 (define_insn "sse2_punpcklqdq"
22640   [(set (match_operand:V2DI 0 "register_operand" "=x")
22641         (vec_merge:V2DI
22642          (vec_select:V2DI (match_operand:V2DI 2 "register_operand" "x")
22643                           (parallel [(const_int 1)
22644                                      (const_int 0)]))
22645          (match_operand:V2DI 1 "register_operand" "0")
22646          (const_int 1)))]
22647   "TARGET_SSE2"
22648   "punpcklqdq\t{%2, %0|%0, %2}"
22649   [(set_attr "type" "ssecvt")
22650    (set_attr "mode" "TI")])
22651
22652 (define_insn "sse2_punpckhqdq"
22653   [(set (match_operand:V2DI 0 "register_operand" "=x")
22654         (vec_merge:V2DI
22655          (match_operand:V2DI 1 "register_operand" "0")
22656          (vec_select:V2DI (match_operand:V2DI 2 "register_operand" "x")
22657                           (parallel [(const_int 1)
22658                                      (const_int 0)]))
22659          (const_int 1)))]
22660   "TARGET_SSE2"
22661   "punpckhqdq\t{%2, %0|%0, %2}"
22662   [(set_attr "type" "ssecvt")
22663    (set_attr "mode" "TI")])
22664
22665 ;; SSE2 moves
22666
22667 (define_insn "sse2_movapd"
22668   [(set (match_operand:V2DF 0 "nonimmediate_operand" "=x,m")
22669         (unspec:V2DF [(match_operand:V2DF 1 "nonimmediate_operand" "xm,x")]
22670                      UNSPEC_MOVA))]
22671   "TARGET_SSE2
22672    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
22673   "movapd\t{%1, %0|%0, %1}"
22674   [(set_attr "type" "ssemov")
22675    (set_attr "mode" "V2DF")])
22676
22677 (define_insn "sse2_movupd"
22678   [(set (match_operand:V2DF 0 "nonimmediate_operand" "=x,m")
22679         (unspec:V2DF [(match_operand:V2DF 1 "nonimmediate_operand" "xm,x")]
22680                      UNSPEC_MOVU))]
22681   "TARGET_SSE2
22682    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
22683   "movupd\t{%1, %0|%0, %1}"
22684   [(set_attr "type" "ssecvt")
22685    (set_attr "mode" "V2DF")])
22686
22687 (define_insn "sse2_movdqa"
22688   [(set (match_operand:V16QI 0 "nonimmediate_operand" "=x,m")
22689         (unspec:V16QI [(match_operand:V16QI 1 "nonimmediate_operand" "xm,x")]
22690                        UNSPEC_MOVA))]
22691   "TARGET_SSE2
22692    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
22693   "movdqa\t{%1, %0|%0, %1}"
22694   [(set_attr "type" "ssemov")
22695    (set_attr "mode" "TI")])
22696
22697 (define_insn "sse2_movdqu"
22698   [(set (match_operand:V16QI 0 "nonimmediate_operand" "=x,m")
22699         (unspec:V16QI [(match_operand:V16QI 1 "nonimmediate_operand" "xm,x")]
22700                        UNSPEC_MOVU))]
22701   "TARGET_SSE2
22702    && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
22703   "movdqu\t{%1, %0|%0, %1}"
22704   [(set_attr "type" "ssecvt")
22705    (set_attr "mode" "TI")])
22706
22707 (define_insn "sse2_movdq2q"
22708   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,y")
22709         (vec_select:DI (match_operand:V2DI 1 "register_operand" "x,x")
22710                        (parallel [(const_int 0)])))]
22711   "TARGET_SSE2 && !TARGET_64BIT"
22712   "@
22713    movq\t{%1, %0|%0, %1}
22714    movdq2q\t{%1, %0|%0, %1}"
22715   [(set_attr "type" "ssecvt")
22716    (set_attr "mode" "TI")])
22717
22718 (define_insn "sse2_movdq2q_rex64"
22719   [(set (match_operand:DI 0 "nonimmediate_operand" "=m,y,r")
22720         (vec_select:DI (match_operand:V2DI 1 "register_operand" "x,x,x")
22721                        (parallel [(const_int 0)])))]
22722   "TARGET_SSE2 && TARGET_64BIT"
22723   "@
22724    movq\t{%1, %0|%0, %1}
22725    movdq2q\t{%1, %0|%0, %1}
22726    movd\t{%1, %0|%0, %1}"
22727   [(set_attr "type" "ssecvt")
22728    (set_attr "mode" "TI")])
22729
22730 (define_insn "sse2_movq2dq"
22731   [(set (match_operand:V2DI 0 "register_operand" "=x,?x")
22732         (vec_concat:V2DI (match_operand:DI 1 "nonimmediate_operand" "m,y")
22733                          (const_int 0)))]
22734   "TARGET_SSE2 && !TARGET_64BIT"
22735   "@
22736    movq\t{%1, %0|%0, %1}
22737    movq2dq\t{%1, %0|%0, %1}"
22738   [(set_attr "type" "ssecvt,ssemov")
22739    (set_attr "mode" "TI")])
22740
22741 (define_insn "sse2_movq2dq_rex64"
22742   [(set (match_operand:V2DI 0 "register_operand" "=x,?x,?x")
22743         (vec_concat:V2DI (match_operand:DI 1 "nonimmediate_operand" "m,y,r")
22744                          (const_int 0)))]
22745   "TARGET_SSE2 && TARGET_64BIT"
22746   "@
22747    movq\t{%1, %0|%0, %1}
22748    movq2dq\t{%1, %0|%0, %1}
22749    movd\t{%1, %0|%0, %1}"
22750   [(set_attr "type" "ssecvt,ssemov,ssecvt")
22751    (set_attr "mode" "TI")])
22752
22753 (define_insn "sse2_movq"
22754   [(set (match_operand:V2DI 0 "register_operand" "=x")
22755         (vec_concat:V2DI (vec_select:DI
22756                           (match_operand:V2DI 1 "nonimmediate_operand" "xm")
22757                           (parallel [(const_int 0)]))
22758                          (const_int 0)))]
22759   "TARGET_SSE2"
22760   "movq\t{%1, %0|%0, %1}"
22761   [(set_attr "type" "ssemov")
22762    (set_attr "mode" "TI")])
22763
22764 (define_insn "sse2_loadd"
22765   [(set (match_operand:V4SI 0 "register_operand" "=x")
22766         (vec_merge:V4SI
22767          (vec_duplicate:V4SI (match_operand:SI 1 "nonimmediate_operand" "mr"))
22768          (const_vector:V4SI [(const_int 0)
22769                              (const_int 0)
22770                              (const_int 0)
22771                              (const_int 0)])
22772          (const_int 1)))]
22773   "TARGET_SSE2"
22774   "movd\t{%1, %0|%0, %1}"
22775   [(set_attr "type" "ssemov")
22776    (set_attr "mode" "TI")])
22777
22778 (define_insn "sse2_stored"
22779   [(set (match_operand:SI 0 "nonimmediate_operand" "=mr")
22780         (vec_select:SI
22781          (match_operand:V4SI 1 "register_operand" "x")
22782          (parallel [(const_int 0)])))]
22783   "TARGET_SSE2"
22784   "movd\t{%1, %0|%0, %1}"
22785   [(set_attr "type" "ssemov")
22786    (set_attr "mode" "TI")])
22787
22788 (define_insn "sse2_movhpd"
22789   [(set (match_operand:V2DF 0 "nonimmediate_operand" "=x,m")
22790         (vec_merge:V2DF
22791          (match_operand:V2DF 1 "nonimmediate_operand" "0,0")
22792          (match_operand:V2DF 2 "nonimmediate_operand" "m,x")
22793          (const_int 2)))]
22794   "TARGET_SSE2 && (GET_CODE (operands[1]) == MEM || GET_CODE (operands[2]) == MEM)"
22795   "movhpd\t{%2, %0|%0, %2}"
22796   [(set_attr "type" "ssecvt")
22797    (set_attr "mode" "V2DF")])
22798
22799 (define_expand "sse2_loadsd"
22800   [(match_operand:V2DF 0 "register_operand" "")
22801    (match_operand:DF 1 "memory_operand" "")]
22802   "TARGET_SSE2"
22803 {
22804   emit_insn (gen_sse2_loadsd_1 (operands[0], operands[1],
22805                                 CONST0_RTX (V2DFmode)));
22806   DONE;
22807 })
22808
22809 (define_insn "sse2_loadsd_1"
22810   [(set (match_operand:V2DF 0 "register_operand" "=x")
22811         (vec_merge:V2DF
22812          (vec_duplicate:V2DF (match_operand:DF 1 "memory_operand" "m"))
22813          (match_operand:V2DF 2 "const0_operand" "X")
22814          (const_int 1)))]
22815   "TARGET_SSE2"
22816   "movsd\t{%1, %0|%0, %1}"
22817   [(set_attr "type" "ssecvt")
22818    (set_attr "mode" "DF")])
22819
22820 (define_insn "sse2_movsd"
22821   [(set (match_operand:V2DF 0 "nonimmediate_operand" "=x,x,m")
22822         (vec_merge:V2DF
22823          (match_operand:V2DF 1 "nonimmediate_operand" "0,0,0")
22824          (match_operand:V2DF 2 "nonimmediate_operand" "x,m,x")
22825          (const_int 1)))]
22826   "TARGET_SSE2 && ix86_binary_operator_ok (UNKNOWN, V2DFmode, operands)"
22827   "@movsd\t{%2, %0|%0, %2}
22828     movlpd\t{%2, %0|%0, %2}
22829     movlpd\t{%2, %0|%0, %2}"
22830   [(set_attr "type" "ssecvt")
22831    (set_attr "mode" "DF,V2DF,V2DF")])
22832
22833 (define_insn "sse2_storesd"
22834   [(set (match_operand:DF 0 "memory_operand" "=m")
22835         (vec_select:DF
22836          (match_operand:V2DF 1 "register_operand" "x")
22837          (parallel [(const_int 0)])))]
22838   "TARGET_SSE2"
22839   "movsd\t{%1, %0|%0, %1}"
22840   [(set_attr "type" "ssecvt")
22841    (set_attr "mode" "DF")])
22842
22843 (define_insn "sse2_shufpd"
22844   [(set (match_operand:V2DF 0 "register_operand" "=x")
22845         (unspec:V2DF [(match_operand:V2DF 1 "register_operand" "0")
22846                       (match_operand:V2DF 2 "nonimmediate_operand" "xm")
22847                       (match_operand:SI 3 "immediate_operand" "i")]
22848                      UNSPEC_SHUFFLE))]
22849   "TARGET_SSE2"
22850   ;; @@@ check operand order for intel/nonintel syntax
22851   "shufpd\t{%3, %2, %0|%0, %2, %3}"
22852   [(set_attr "type" "ssecvt")
22853    (set_attr "mode" "V2DF")])
22854
22855 (define_insn "sse2_clflush"
22856   [(unspec_volatile [(match_operand 0 "address_operand" "p")]
22857                     UNSPECV_CLFLUSH)]
22858   "TARGET_SSE2"
22859   "clflush %0"
22860   [(set_attr "type" "sse")
22861    (set_attr "memory" "unknown")])
22862
22863 (define_expand "sse2_mfence"
22864   [(set (match_dup 0)
22865         (unspec:BLK [(match_dup 0)] UNSPEC_MFENCE))]
22866   "TARGET_SSE2"
22867 {
22868   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
22869   MEM_VOLATILE_P (operands[0]) = 1;
22870 })
22871
22872 (define_insn "*mfence_insn"
22873   [(set (match_operand:BLK 0 "" "")
22874         (unspec:BLK [(match_dup 0)] UNSPEC_MFENCE))]
22875   "TARGET_SSE2"
22876   "mfence"
22877   [(set_attr "type" "sse")
22878    (set_attr "memory" "unknown")])
22879
22880 (define_expand "sse2_lfence"
22881   [(set (match_dup 0)
22882         (unspec:BLK [(match_dup 0)] UNSPEC_LFENCE))]
22883   "TARGET_SSE2"
22884 {
22885   operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
22886   MEM_VOLATILE_P (operands[0]) = 1;
22887 })
22888
22889 (define_insn "*lfence_insn"
22890   [(set (match_operand:BLK 0 "" "")
22891         (unspec:BLK [(match_dup 0)] UNSPEC_LFENCE))]
22892   "TARGET_SSE2"
22893   "lfence"
22894   [(set_attr "type" "sse")
22895    (set_attr "memory" "unknown")])
22896
22897 ;; SSE3
22898
22899 (define_insn "mwait"
22900   [(unspec_volatile [(match_operand:SI 0 "register_operand" "a")
22901                      (match_operand:SI 1 "register_operand" "c")]
22902                     UNSPECV_MWAIT)]
22903   "TARGET_SSE3"
22904   "mwait\t%0, %1"
22905   [(set_attr "length" "3")])
22906
22907 (define_insn "monitor"
22908   [(unspec_volatile [(match_operand:SI 0 "register_operand" "a")
22909                      (match_operand:SI 1 "register_operand" "c")
22910                      (match_operand:SI 2 "register_operand" "d")]
22911                     UNSPECV_MONITOR)]
22912   "TARGET_SSE3"
22913   "monitor\t%0, %1, %2"
22914   [(set_attr "length" "3")])
22915
22916 ;; SSE3 arithmetic
22917
22918 (define_insn "addsubv4sf3"
22919   [(set (match_operand:V4SF 0 "register_operand" "=x")
22920         (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "0")
22921                       (match_operand:V4SF 2 "nonimmediate_operand" "xm")]
22922                      UNSPEC_ADDSUB))]
22923   "TARGET_SSE3"
22924   "addsubps\t{%2, %0|%0, %2}"
22925   [(set_attr "type" "sseadd")
22926    (set_attr "mode" "V4SF")])
22927
22928 (define_insn "addsubv2df3"
22929   [(set (match_operand:V2DF 0 "register_operand" "=x")
22930         (unspec:V2DF [(match_operand:V2DF 1 "register_operand" "0")
22931                       (match_operand:V2DF 2 "nonimmediate_operand" "xm")]
22932                      UNSPEC_ADDSUB))]
22933   "TARGET_SSE3"
22934   "addsubpd\t{%2, %0|%0, %2}"
22935   [(set_attr "type" "sseadd")
22936    (set_attr "mode" "V2DF")])
22937
22938 (define_insn "haddv4sf3"
22939   [(set (match_operand:V4SF 0 "register_operand" "=x")
22940         (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "0")
22941                       (match_operand:V4SF 2 "nonimmediate_operand" "xm")]
22942                      UNSPEC_HADD))]
22943   "TARGET_SSE3"
22944   "haddps\t{%2, %0|%0, %2}"
22945   [(set_attr "type" "sseadd")
22946    (set_attr "mode" "V4SF")])
22947
22948 (define_insn "haddv2df3"
22949   [(set (match_operand:V2DF 0 "register_operand" "=x")
22950         (unspec:V2DF [(match_operand:V2DF 1 "register_operand" "0")
22951                       (match_operand:V2DF 2 "nonimmediate_operand" "xm")]
22952                      UNSPEC_HADD))]
22953   "TARGET_SSE3"
22954   "haddpd\t{%2, %0|%0, %2}"
22955   [(set_attr "type" "sseadd")
22956    (set_attr "mode" "V2DF")])
22957
22958 (define_insn "hsubv4sf3"
22959   [(set (match_operand:V4SF 0 "register_operand" "=x")
22960         (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "0")
22961                       (match_operand:V4SF 2 "nonimmediate_operand" "xm")]
22962                      UNSPEC_HSUB))]
22963   "TARGET_SSE3"
22964   "hsubps\t{%2, %0|%0, %2}"
22965   [(set_attr "type" "sseadd")
22966    (set_attr "mode" "V4SF")])
22967
22968 (define_insn "hsubv2df3"
22969   [(set (match_operand:V2DF 0 "register_operand" "=x")
22970         (unspec:V2DF [(match_operand:V2DF 1 "register_operand" "0")
22971                       (match_operand:V2DF 2 "nonimmediate_operand" "xm")]
22972                      UNSPEC_HSUB))]
22973   "TARGET_SSE3"
22974   "hsubpd\t{%2, %0|%0, %2}"
22975   [(set_attr "type" "sseadd")
22976    (set_attr "mode" "V2DF")])
22977
22978 (define_insn "movshdup"
22979   [(set (match_operand:V4SF 0 "register_operand" "=x")
22980         (unspec:V4SF
22981          [(match_operand:V4SF 1 "nonimmediate_operand" "xm")] UNSPEC_MOVSHDUP))]
22982   "TARGET_SSE3"
22983   "movshdup\t{%1, %0|%0, %1}"
22984   [(set_attr "type" "sse")
22985    (set_attr "mode" "V4SF")])
22986
22987 (define_insn "movsldup"
22988   [(set (match_operand:V4SF 0 "register_operand" "=x")
22989         (unspec:V4SF
22990          [(match_operand:V4SF 1 "nonimmediate_operand" "xm")] UNSPEC_MOVSLDUP))]
22991   "TARGET_SSE3"
22992   "movsldup\t{%1, %0|%0, %1}"
22993   [(set_attr "type" "sse")
22994    (set_attr "mode" "V4SF")])
22995
22996 (define_insn "lddqu"
22997   [(set (match_operand:V16QI 0 "register_operand" "=x")
22998         (unspec:V16QI [(match_operand:V16QI 1 "memory_operand" "m")]
22999                        UNSPEC_LDQQU))]
23000   "TARGET_SSE3"
23001   "lddqu\t{%1, %0|%0, %1}"
23002   [(set_attr "type" "ssecvt")
23003    (set_attr "mode" "TI")])
23004
23005 (define_insn "loadddup"
23006   [(set (match_operand:V2DF 0 "register_operand" "=x")
23007         (vec_duplicate:V2DF (match_operand:DF 1 "memory_operand" "m")))]
23008   "TARGET_SSE3"
23009   "movddup\t{%1, %0|%0, %1}"
23010   [(set_attr "type" "ssecvt")
23011    (set_attr "mode" "DF")])
23012
23013 (define_insn "movddup"
23014   [(set (match_operand:V2DF 0 "register_operand" "=x")
23015         (vec_duplicate:V2DF
23016          (vec_select:DF (match_operand:V2DF 1 "register_operand" "x")
23017                         (parallel [(const_int 0)]))))]
23018   "TARGET_SSE3"
23019   "movddup\t{%1, %0|%0, %1}"
23020   [(set_attr "type" "ssecvt")
23021    (set_attr "mode" "DF")])