i386.md (zero_extendsidi2_32): Break out from ...
[gcc.git] / gcc / config / i386 / i386.md
1 ;; GCC machine description for IA-32 and x86-64.
2 ;; Copyright (C) 1988, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001
3 ;; Free Software Foundation, Inc.
4 ;; Mostly by William Schelter.
5 ;; x86_64 support added by Jan Hubicka
6 ;;
7 ;; This file is part of GNU CC.
8 ;;
9 ;; GNU CC is free software; you can redistribute it and/or modify
10 ;; it under the terms of the GNU General Public License as published by
11 ;; the Free Software Foundation; either version 2, or (at your option)
12 ;; any later version.
13 ;;
14 ;; GNU CC is distributed in the hope that it will be useful,
15 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
16 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 ;; GNU General Public License for more details.
18 ;;
19 ;; You should have received a copy of the GNU General Public License
20 ;; along with GNU CC; see the file COPYING. If not, write to
21 ;; the Free Software Foundation, 59 Temple Place - Suite 330,
22 ;; Boston, MA 02111-1307, USA. */
23 ;;
24 ;; The original PO technology requires these to be ordered by speed,
25 ;; so that assigner will pick the fastest.
26 ;;
27 ;; See file "rtl.def" for documentation on define_insn, match_*, et. al.
28 ;;
29 ;; Macro #define NOTICE_UPDATE_CC in file i386.h handles condition code
30 ;; updates for most instructions.
31 ;;
32 ;; Macro REG_CLASS_FROM_LETTER in file i386.h defines the register
33 ;; constraint letters.
34 ;;
35 ;; The special asm out single letter directives following a '%' are:
36 ;; 'z' mov%z1 would be movl, movw, or movb depending on the mode of
37 ;; operands[1].
38 ;; 'L' Print the opcode suffix for a 32-bit integer opcode.
39 ;; 'W' Print the opcode suffix for a 16-bit integer opcode.
40 ;; 'B' Print the opcode suffix for an 8-bit integer opcode.
41 ;; 'Q' Print the opcode suffix for a 64-bit float opcode.
42 ;; 'S' Print the opcode suffix for a 32-bit float opcode.
43 ;; 'T' Print the opcode suffix for an 80-bit extended real XFmode float opcode.
44 ;; 'J' Print the appropriate jump operand.
45 ;;
46 ;; 'b' Print the QImode name of the register for the indicated operand.
47 ;; %b0 would print %al if operands[0] is reg 0.
48 ;; 'w' Likewise, print the HImode name of the register.
49 ;; 'k' Likewise, print the SImode name of the register.
50 ;; 'h' Print the QImode name for a "high" register, either ah, bh, ch or dh.
51 ;; 'y' Print "st(0)" instead of "st" as a register.
52 ;;
53 ;; UNSPEC usage:
54 ;; 0 This is a `scas' operation. The mode of the UNSPEC is always SImode.
55 ;; operand 0 is the memory address to scan.
56 ;; operand 1 is a register containing the value to scan for. The mode
57 ;; of the scas opcode will be the same as the mode of this operand.
58 ;; operand 2 is the known alignment of operand 0.
59 ;; 1 This is a `sin' operation. The mode of the UNSPEC is MODE_FLOAT.
60 ;; operand 0 is the argument for `sin'.
61 ;; 2 This is a `cos' operation. The mode of the UNSPEC is MODE_FLOAT.
62 ;; operand 0 is the argument for `cos'.
63 ;; 3 This is part of a `stack probe' operation. The mode of the UNSPEC is
64 ;; always SImode. operand 0 is the size of the stack allocation.
65 ;; 4 This is the source of a fake SET of the frame pointer which is used to
66 ;; prevent insns referencing it being scheduled across the initial
67 ;; decrement of the stack pointer.
68 ;; 5 This is a `bsf' operation.
69 ;; 6 This is the @GOT offset of a PIC address.
70 ;; 7 This is the @GOTOFF offset of a PIC address.
71 ;; 8 This is a reference to a symbol's @PLT address.
72 ;; 9 This is an `fnstsw' operation.
73 ;; 10 This is a `sahf' operation.
74 ;; 11 This is a `fstcw' operation
75 ;; 12 This is behaviour of add when setting carry flag.
76
77 ;; For SSE/MMX support:
78 ;; 30 This is `fix', guaranteed to be truncating.
79 ;; 31 This is a `emms' operation.
80 ;; 32 This is a `maskmov' operation.
81 ;; 33 This is a `movmsk' operation.
82 ;; 34 This is a `non-temporal' move.
83 ;; 35 This is a `prefetch' operation.
84 ;; 36 This is used to distinguish COMISS from UCOMISS.
85 ;; 37 This is a `ldmxcsr' operation.
86 ;; 38 This is a forced `movaps' instruction (rather than whatever movti does)
87 ;; 39 This is a forced `movups' instruction (rather than whatever movti does)
88 ;; 40 This is a `stmxcsr' operation.
89 ;; 41 This is a `shuffle' operation.
90 ;; 42 This is a `rcp' operation.
91 ;; 43 This is a `rsqsrt' operation.
92 ;; 44 This is a `sfence' operation.
93 ;; 45 This is a noop to prevent excessive combiner cleverness.
94
95 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
96 ;; from i386.c.
97
98 \f
99 ;; Processor type. This attribute must exactly match the processor_type
100 ;; enumeration in i386.h.
101 (define_attr "cpu" "i386,i486,pentium,pentiumpro,k6,athlon,pentium4"
102 (const (symbol_ref "ix86_cpu")))
103
104 ;; A basic instruction type. Refinements due to arguments to be
105 ;; provided in other attributes.
106 (define_attr "type"
107 "other,multi,alu1,negnot,alu,icmp,test,imov,imovx,lea,incdec,ishift,imul,idiv,ibr,setcc,push,pop,call,callv,icmov,fmov,fop,fop1,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,str,cld,sse,mmx"
108 (const_string "other"))
109
110 ;; Main data type used by the insn
111 (define_attr "mode" "unknown,none,QI,HI,SI,DI,unknownfp,SF,DF,XF,TI"
112 (const_string "unknown"))
113
114 ;; Set for i387 operations.
115 (define_attr "i387" ""
116 (if_then_else (eq_attr "type" "fmov,fop,fop1,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch")
117 (const_int 1)
118 (const_int 0)))
119
120 ;; The (bounding maximum) length of an instruction immediate.
121 (define_attr "length_immediate" ""
122 (cond [(eq_attr "type" "incdec,setcc,icmov,ibr,str,cld,lea,other,multi,idiv,sse,mmx")
123 (const_int 0)
124 (eq_attr "i387" "1")
125 (const_int 0)
126 (eq_attr "type" "alu1,negnot,alu,icmp,imovx,ishift,imul,push,pop")
127 (symbol_ref "ix86_attr_length_immediate_default(insn,1)")
128 (eq_attr "type" "imov,test")
129 (symbol_ref "ix86_attr_length_immediate_default(insn,0)")
130 (eq_attr "type" "call")
131 (if_then_else (match_operand 0 "constant_call_address_operand" "")
132 (const_int 4)
133 (const_int 0))
134 (eq_attr "type" "callv")
135 (if_then_else (match_operand 1 "constant_call_address_operand" "")
136 (const_int 4)
137 (const_int 0))
138 (eq_attr "type" "ibr")
139 (if_then_else (and (ge (minus (match_dup 0) (pc))
140 (const_int -128))
141 (lt (minus (match_dup 0) (pc))
142 (const_int 124)))
143 (const_int 1)
144 (const_int 4))
145 ]
146 (symbol_ref "/* Update immediate_length and other attributes! */ abort(),1")))
147
148 ;; The (bounding maximum) length of an instruction address.
149 (define_attr "length_address" ""
150 (cond [(eq_attr "type" "str,cld,other,multi,fxch")
151 (const_int 0)
152 (and (eq_attr "type" "call")
153 (match_operand 1 "constant_call_address_operand" ""))
154 (const_int 0)
155 (and (eq_attr "type" "callv")
156 (match_operand 1 "constant_call_address_operand" ""))
157 (const_int 0)
158 ]
159 (symbol_ref "ix86_attr_length_address_default (insn)")))
160
161 ;; Set when length prefix is used.
162 (define_attr "prefix_data16" ""
163 (if_then_else (eq_attr "mode" "HI")
164 (const_int 1)
165 (const_int 0)))
166
167 ;; Set when string REP prefix is used.
168 (define_attr "prefix_rep" "" (const_int 0))
169
170 ;; Set when 0f opcode prefix is used.
171 (define_attr "prefix_0f" ""
172 (if_then_else (eq_attr "type" "imovx,setcc,icmov,sse,mmx")
173 (const_int 1)
174 (const_int 0)))
175
176 ;; Set when modrm byte is used.
177 (define_attr "modrm" ""
178 (cond [(eq_attr "type" "str,cld")
179 (const_int 0)
180 (eq_attr "i387" "1")
181 (const_int 0)
182 (and (eq_attr "type" "incdec")
183 (ior (match_operand:SI 1 "register_operand" "")
184 (match_operand:HI 1 "register_operand" "")))
185 (const_int 0)
186 (and (eq_attr "type" "push")
187 (not (match_operand 1 "memory_operand" "")))
188 (const_int 0)
189 (and (eq_attr "type" "pop")
190 (not (match_operand 0 "memory_operand" "")))
191 (const_int 0)
192 (and (eq_attr "type" "imov")
193 (and (match_operand 0 "register_operand" "")
194 (match_operand 1 "immediate_operand" "")))
195 (const_int 0)
196 ]
197 (const_int 1)))
198
199 ;; The (bounding maximum) length of an instruction in bytes.
200 (define_attr "length" ""
201 (cond [(eq_attr "type" "other,multi")
202 (const_int 16)
203 ]
204 (plus (plus (attr "modrm")
205 (plus (attr "prefix_0f")
206 (plus (attr "i387")
207 (const_int 1))))
208 (plus (attr "prefix_rep")
209 (plus (attr "prefix_data16")
210 (plus (attr "length_immediate")
211 (attr "length_address")))))))
212
213 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
214 ;; `store' if there is a simple memory reference therein, or `unknown'
215 ;; if the instruction is complex.
216
217 (define_attr "memory" "none,load,store,both,unknown"
218 (cond [(eq_attr "type" "other,multi,str")
219 (const_string "unknown")
220 (eq_attr "type" "lea,fcmov,fpspc,cld")
221 (const_string "none")
222 (eq_attr "type" "push")
223 (if_then_else (match_operand 1 "memory_operand" "")
224 (const_string "both")
225 (const_string "store"))
226 (eq_attr "type" "pop,setcc")
227 (if_then_else (match_operand 0 "memory_operand" "")
228 (const_string "both")
229 (const_string "load"))
230 (eq_attr "type" "icmp,test")
231 (if_then_else (ior (match_operand 0 "memory_operand" "")
232 (match_operand 1 "memory_operand" ""))
233 (const_string "load")
234 (const_string "none"))
235 (eq_attr "type" "ibr")
236 (if_then_else (match_operand 0 "memory_operand" "")
237 (const_string "load")
238 (const_string "none"))
239 (eq_attr "type" "call")
240 (if_then_else (match_operand 0 "constant_call_address_operand" "")
241 (const_string "none")
242 (const_string "load"))
243 (eq_attr "type" "callv")
244 (if_then_else (match_operand 1 "constant_call_address_operand" "")
245 (const_string "none")
246 (const_string "load"))
247 (and (eq_attr "type" "alu1,negnot")
248 (match_operand 1 "memory_operand" ""))
249 (const_string "both")
250 (and (match_operand 0 "memory_operand" "")
251 (match_operand 1 "memory_operand" ""))
252 (const_string "both")
253 (match_operand 0 "memory_operand" "")
254 (const_string "store")
255 (match_operand 1 "memory_operand" "")
256 (const_string "load")
257 (and (eq_attr "type" "!icmp,test,alu1,negnot,fop1,fsgn,imov,imovx,fmov,fcmp,sse,mmx")
258 (match_operand 2 "memory_operand" ""))
259 (const_string "load")
260 (and (eq_attr "type" "icmov")
261 (match_operand 3 "memory_operand" ""))
262 (const_string "load")
263 ]
264 (const_string "none")))
265
266 ;; Indicates if an instruction has both an immediate and a displacement.
267
268 (define_attr "imm_disp" "false,true,unknown"
269 (cond [(eq_attr "type" "other,multi")
270 (const_string "unknown")
271 (and (eq_attr "type" "icmp,test,imov")
272 (and (match_operand 0 "memory_displacement_operand" "")
273 (match_operand 1 "immediate_operand" "")))
274 (const_string "true")
275 (and (eq_attr "type" "alu,ishift,imul,idiv")
276 (and (match_operand 0 "memory_displacement_operand" "")
277 (match_operand 2 "immediate_operand" "")))
278 (const_string "true")
279 ]
280 (const_string "false")))
281
282 ;; Indicates if an FP operation has an integer source.
283
284 (define_attr "fp_int_src" "false,true"
285 (const_string "false"))
286
287 ;; Describe a user's asm statement.
288 (define_asm_attributes
289 [(set_attr "length" "128")
290 (set_attr "type" "multi")])
291 \f
292 ;; Pentium Scheduling
293 ;;
294 ;; The Pentium is an in-order core with two integer pipelines.
295
296 ;; True for insns that behave like prefixed insns on the Pentium.
297 (define_attr "pent_prefix" "false,true"
298 (if_then_else (ior (eq_attr "prefix_0f" "1")
299 (ior (eq_attr "prefix_data16" "1")
300 (eq_attr "prefix_rep" "1")))
301 (const_string "true")
302 (const_string "false")))
303
304 ;; Categorize how an instruction slots.
305
306 ;; The non-MMX Pentium slots an instruction with prefixes on U pipe only,
307 ;; while MMX Pentium can slot it on either U or V. Model non-MMX Pentium
308 ;; rules, because it results in noticeably better code on non-MMX Pentium
309 ;; and doesn't hurt much on MMX. (Prefixed instructions are not very
310 ;; common, so the scheduler usualy has a non-prefixed insn to pair).
311
312 (define_attr "pent_pair" "uv,pu,pv,np"
313 (cond [(eq_attr "imm_disp" "true")
314 (const_string "np")
315 (ior (eq_attr "type" "alu1,alu,imov,icmp,test,lea,incdec")
316 (and (eq_attr "type" "pop,push")
317 (eq_attr "memory" "!both")))
318 (if_then_else (eq_attr "pent_prefix" "true")
319 (const_string "pu")
320 (const_string "uv"))
321 (eq_attr "type" "ibr")
322 (const_string "pv")
323 (and (eq_attr "type" "ishift")
324 (match_operand 2 "const_int_operand" ""))
325 (const_string "pu")
326 (and (eq_attr "type" "call")
327 (match_operand 0 "constant_call_address_operand" ""))
328 (const_string "pv")
329 (and (eq_attr "type" "callv")
330 (match_operand 1 "constant_call_address_operand" ""))
331 (const_string "pv")
332 ]
333 (const_string "np")))
334
335 ;; Rough readiness numbers. Fine tuning happens in i386.c.
336 ;;
337 ;; u describes pipe U
338 ;; v describes pipe V
339 ;; uv describes either pipe U or V for those that can issue to either
340 ;; np describes not paring
341 ;; fpu describes fpu
342 ;; fpm describes fp insns of different types are not pipelined.
343 ;;
344 ;; ??? fxch isn't handled; not an issue until sched3 after reg-stack is real.
345
346 (define_function_unit "pent_np" 1 0
347 (and (eq_attr "cpu" "pentium")
348 (eq_attr "type" "imul"))
349 11 11)
350
351 (define_function_unit "pent_mul" 1 1
352 (and (eq_attr "cpu" "pentium")
353 (eq_attr "type" "imul"))
354 11 11)
355
356 ;; Rep movs takes minimally 12 cycles.
357 (define_function_unit "pent_np" 1 0
358 (and (eq_attr "cpu" "pentium")
359 (eq_attr "type" "str"))
360 12 12)
361
362 ; ??? IDIV for SI takes 46 cycles, for HI 30, for QI 22
363 (define_function_unit "pent_np" 1 0
364 (and (eq_attr "cpu" "pentium")
365 (eq_attr "type" "idiv"))
366 46 46)
367
368 ; Fp reg-reg moves takes 1 cycle. Loads takes 1 cycle for SF/DF mode,
369 ; 3 cycles for XFmode. Stores takes 2 cycles for SF/DF and 3 for XF.
370 ; fldz and fld1 takes 2 cycles. Only reg-reg moves are pairable.
371 ; The integer <-> fp conversion is not modeled correctly. Fild behaves
372 ; like normal fp operation and fist takes 6 cycles.
373
374 (define_function_unit "fpu" 1 0
375 (and (eq_attr "cpu" "pentium")
376 (and (eq_attr "type" "fmov")
377 (and (eq_attr "memory" "load,store")
378 (eq_attr "mode" "XF"))))
379 3 3)
380
381 (define_function_unit "pent_np" 1 0
382 (and (eq_attr "cpu" "pentium")
383 (and (eq_attr "type" "fmov")
384 (and (eq_attr "memory" "load,store")
385 (eq_attr "mode" "XF"))))
386 3 3)
387
388 (define_function_unit "fpu" 1 0
389 (and (eq_attr "cpu" "pentium")
390 (and (eq_attr "type" "fmov")
391 (ior (match_operand 1 "immediate_operand" "")
392 (eq_attr "memory" "store"))))
393 2 2)
394
395 (define_function_unit "pent_np" 1 0
396 (and (eq_attr "cpu" "pentium")
397 (and (eq_attr "type" "fmov")
398 (ior (match_operand 1 "immediate_operand" "")
399 (eq_attr "memory" "store"))))
400 2 2)
401
402 (define_function_unit "pent_np" 1 0
403 (and (eq_attr "cpu" "pentium")
404 (eq_attr "type" "cld"))
405 2 2)
406
407 (define_function_unit "fpu" 1 0
408 (and (eq_attr "cpu" "pentium")
409 (and (eq_attr "type" "fmov")
410 (eq_attr "memory" "none,load")))
411 1 1)
412
413 ; Read/Modify/Write instructions usually take 3 cycles.
414 (define_function_unit "pent_u" 1 0
415 (and (eq_attr "cpu" "pentium")
416 (and (eq_attr "type" "alu,alu1,ishift")
417 (and (eq_attr "pent_pair" "pu")
418 (eq_attr "memory" "both"))))
419 3 3)
420
421 (define_function_unit "pent_uv" 2 0
422 (and (eq_attr "cpu" "pentium")
423 (and (eq_attr "type" "alu,alu1,ishift")
424 (and (eq_attr "pent_pair" "!np")
425 (eq_attr "memory" "both"))))
426 3 3)
427
428 (define_function_unit "pent_np" 1 0
429 (and (eq_attr "cpu" "pentium")
430 (and (eq_attr "type" "alu,alu1,negnot,ishift")
431 (and (eq_attr "pent_pair" "np")
432 (eq_attr "memory" "both"))))
433 3 3)
434
435 ; Read/Modify or Modify/Write instructions usually take 2 cycles.
436 (define_function_unit "pent_u" 1 0
437 (and (eq_attr "cpu" "pentium")
438 (and (eq_attr "type" "alu,ishift")
439 (and (eq_attr "pent_pair" "pu")
440 (eq_attr "memory" "load,store"))))
441 2 2)
442
443 (define_function_unit "pent_uv" 2 0
444 (and (eq_attr "cpu" "pentium")
445 (and (eq_attr "type" "alu,ishift")
446 (and (eq_attr "pent_pair" "!np")
447 (eq_attr "memory" "load,store"))))
448 2 2)
449
450 (define_function_unit "pent_np" 1 0
451 (and (eq_attr "cpu" "pentium")
452 (and (eq_attr "type" "alu,ishift")
453 (and (eq_attr "pent_pair" "np")
454 (eq_attr "memory" "load,store"))))
455 2 2)
456
457 ; Insns w/o memory operands and move instructions usually take one cycle.
458 (define_function_unit "pent_u" 1 0
459 (and (eq_attr "cpu" "pentium")
460 (eq_attr "pent_pair" "pu"))
461 1 1)
462
463 (define_function_unit "pent_v" 1 0
464 (and (eq_attr "cpu" "pentium")
465 (eq_attr "pent_pair" "pv"))
466 1 1)
467
468 (define_function_unit "pent_uv" 2 0
469 (and (eq_attr "cpu" "pentium")
470 (eq_attr "pent_pair" "!np"))
471 1 1)
472
473 (define_function_unit "pent_np" 1 0
474 (and (eq_attr "cpu" "pentium")
475 (eq_attr "pent_pair" "np"))
476 1 1)
477
478 ; Pairable insns only conflict with other non-pairable insns.
479 (define_function_unit "pent_np" 1 0
480 (and (eq_attr "cpu" "pentium")
481 (and (eq_attr "type" "alu,alu1,ishift")
482 (and (eq_attr "pent_pair" "!np")
483 (eq_attr "memory" "both"))))
484 3 3
485 [(eq_attr "pent_pair" "np")])
486
487 (define_function_unit "pent_np" 1 0
488 (and (eq_attr "cpu" "pentium")
489 (and (eq_attr "type" "alu,alu1,ishift")
490 (and (eq_attr "pent_pair" "!np")
491 (eq_attr "memory" "load,store"))))
492 2 2
493 [(eq_attr "pent_pair" "np")])
494
495 (define_function_unit "pent_np" 1 0
496 (and (eq_attr "cpu" "pentium")
497 (eq_attr "pent_pair" "!np"))
498 1 1
499 [(eq_attr "pent_pair" "np")])
500
501 ; Floating point instructions usually blocks cycle longer when combined with
502 ; integer instructions, because of the inpaired fxch instruction.
503 (define_function_unit "pent_np" 1 0
504 (and (eq_attr "cpu" "pentium")
505 (eq_attr "type" "fmov,fop,fop1,fsgn,fmul,fpspc,fcmov,fcmp"))
506 2 2
507 [(eq_attr "type" "!fmov,fop,fop1,fsgn,fmul,fpspc,fcmov,fcmp")])
508
509 (define_function_unit "fpu" 1 0
510 (and (eq_attr "cpu" "pentium")
511 (eq_attr "type" "fcmp,fxch,fsgn"))
512 1 1)
513
514 ; Addition takes 3 cycles; assume other random cruft does as well.
515 ; ??? Trivial fp operations such as fabs or fchs takes only one cycle.
516 (define_function_unit "fpu" 1 0
517 (and (eq_attr "cpu" "pentium")
518 (eq_attr "type" "fop,fop1"))
519 3 1)
520
521 ; Multiplication takes 3 cycles and is only half pipelined.
522 (define_function_unit "fpu" 1 0
523 (and (eq_attr "cpu" "pentium")
524 (eq_attr "type" "fmul"))
525 3 1)
526
527 (define_function_unit "pent_mul" 1 1
528 (and (eq_attr "cpu" "pentium")
529 (eq_attr "type" "fmul"))
530 2 2)
531
532 ; ??? This is correct only for fdiv and sqrt -- sin/cos take 65-100 cycles.
533 ; They can overlap with integer insns. Only the last two cycles can overlap
534 ; with other fp insns. Only fsin/fcos can overlap with multiplies.
535 ; Only last two cycles of fsin/fcos can overlap with other instructions.
536 (define_function_unit "fpu" 1 0
537 (and (eq_attr "cpu" "pentium")
538 (eq_attr "type" "fdiv"))
539 39 37)
540
541 (define_function_unit "pent_mul" 1 1
542 (and (eq_attr "cpu" "pentium")
543 (eq_attr "type" "fdiv"))
544 39 39)
545
546 (define_function_unit "fpu" 1 0
547 (and (eq_attr "cpu" "pentium")
548 (eq_attr "type" "fpspc"))
549 70 68)
550
551 (define_function_unit "pent_mul" 1 1
552 (and (eq_attr "cpu" "pentium")
553 (eq_attr "type" "fpspc"))
554 70 70)
555 \f
556 ;; Pentium Pro/PII Scheduling
557 ;;
558 ;; The PPro has an out-of-order core, but the instruction decoders are
559 ;; naturally in-order and asymmetric. We get best performance by scheduling
560 ;; for the decoders, for in doing so we give the oo execution unit the
561 ;; most choices.
562
563 ;; Categorize how many uops an ia32 instruction evaluates to:
564 ;; one -- an instruction with 1 uop can be decoded by any of the
565 ;; three decoders.
566 ;; few -- an instruction with 1 to 4 uops can be decoded only by
567 ;; decoder 0.
568 ;; many -- a complex instruction may take an unspecified number of
569 ;; cycles to decode in decoder 0.
570
571 (define_attr "ppro_uops" "one,few,many"
572 (cond [(eq_attr "type" "other,multi,call,callv,fpspc,str")
573 (const_string "many")
574 (eq_attr "type" "icmov,fcmov,str,cld")
575 (const_string "few")
576 (eq_attr "type" "imov")
577 (if_then_else (eq_attr "memory" "store,both")
578 (const_string "few")
579 (const_string "one"))
580 (eq_attr "memory" "!none")
581 (const_string "few")
582 ]
583 (const_string "one")))
584
585 ;; Rough readiness numbers. Fine tuning happens in i386.c.
586 ;;
587 ;; p0 describes port 0.
588 ;; p01 describes ports 0 and 1 as a pair; alu insns can issue to either.
589 ;; p2 describes port 2 for loads.
590 ;; p34 describes ports 3 and 4 for stores.
591 ;; fpu describes the fpu accessed via port 0.
592 ;; ??? It is less than clear if there are separate fadd and fmul units
593 ;; that could operate in parallel.
594 ;;
595 ;; ??? fxch isn't handled; not an issue until sched3 after reg-stack is real.
596
597 (define_function_unit "ppro_p0" 1 0
598 (and (eq_attr "cpu" "pentiumpro")
599 (eq_attr "type" "ishift,lea,ibr,cld"))
600 1 1)
601
602 (define_function_unit "ppro_p0" 1 0
603 (and (eq_attr "cpu" "pentiumpro")
604 (eq_attr "type" "imul"))
605 4 1)
606
607 ;; ??? Does the divider lock out the pipe while it works,
608 ;; or is there a disconnected unit?
609 (define_function_unit "ppro_p0" 1 0
610 (and (eq_attr "cpu" "pentiumpro")
611 (eq_attr "type" "idiv"))
612 17 17)
613
614 (define_function_unit "ppro_p0" 1 0
615 (and (eq_attr "cpu" "pentiumpro")
616 (eq_attr "type" "fop,fop1,fsgn"))
617 3 1)
618
619 (define_function_unit "ppro_p0" 1 0
620 (and (eq_attr "cpu" "pentiumpro")
621 (eq_attr "type" "fcmov"))
622 2 1)
623
624 (define_function_unit "ppro_p0" 1 0
625 (and (eq_attr "cpu" "pentiumpro")
626 (eq_attr "type" "fcmp"))
627 1 1)
628
629 (define_function_unit "ppro_p0" 1 0
630 (and (eq_attr "cpu" "pentiumpro")
631 (eq_attr "type" "fmov"))
632 1 1)
633
634 (define_function_unit "ppro_p0" 1 0
635 (and (eq_attr "cpu" "pentiumpro")
636 (eq_attr "type" "fmul"))
637 5 1)
638
639 (define_function_unit "ppro_p0" 1 0
640 (and (eq_attr "cpu" "pentiumpro")
641 (eq_attr "type" "fdiv,fpspc"))
642 56 1)
643
644 (define_function_unit "ppro_p01" 2 0
645 (and (eq_attr "cpu" "pentiumpro")
646 (eq_attr "type" "!imov,fmov"))
647 1 1)
648
649 (define_function_unit "ppro_p01" 2 0
650 (and (and (eq_attr "cpu" "pentiumpro")
651 (eq_attr "type" "imov,fmov"))
652 (eq_attr "memory" "none"))
653 1 1)
654
655 (define_function_unit "ppro_p2" 1 0
656 (and (eq_attr "cpu" "pentiumpro")
657 (ior (eq_attr "type" "pop")
658 (eq_attr "memory" "load,both")))
659 3 1)
660
661 (define_function_unit "ppro_p34" 1 0
662 (and (eq_attr "cpu" "pentiumpro")
663 (ior (eq_attr "type" "push")
664 (eq_attr "memory" "store,both")))
665 1 1)
666
667 (define_function_unit "fpu" 1 0
668 (and (eq_attr "cpu" "pentiumpro")
669 (eq_attr "type" "fop,fop1,fsgn,fmov,fcmp,fcmov"))
670 1 1)
671
672 (define_function_unit "fpu" 1 0
673 (and (eq_attr "cpu" "pentiumpro")
674 (eq_attr "type" "fmul"))
675 5 2)
676
677 (define_function_unit "fpu" 1 0
678 (and (eq_attr "cpu" "pentiumpro")
679 (eq_attr "type" "fdiv,fpspc"))
680 56 56)
681
682 ;; imul uses the fpu. ??? does it have the same throughput as fmul?
683 (define_function_unit "fpu" 1 0
684 (and (eq_attr "cpu" "pentiumpro")
685 (eq_attr "type" "imul"))
686 4 1)
687 \f
688 ;; AMD K6/K6-2 Scheduling
689 ;;
690 ;; The K6 has similar architecture to PPro. Important difference is, that
691 ;; there are only two decoders and they seems to be much slower than execution
692 ;; units. So we have to pay much more attention to proper decoding for
693 ;; schedulers. We share most of scheduler code for PPro in i386.c
694 ;;
695 ;; The fp unit is not pipelined and do one operation per two cycles including
696 ;; the FXCH.
697 ;;
698 ;; alu describes both ALU units (ALU-X and ALU-Y).
699 ;; alux describes X alu unit
700 ;; fpu describes FPU unit
701 ;; load describes load unit.
702 ;; branch describes branch unit.
703 ;; store decsribes store unit. This unit is not modelled completely and only
704 ;; used to model lea operation. Otherwise it lie outside of the critical
705 ;; path.
706 ;;
707 ;; ??? fxch isn't handled; not an issue until sched3 after reg-stack is real.
708
709 ;; The decoder specification is in the PPro section above!
710
711 ;; Shift instructions and certain arithmetic are issued only to X pipe.
712 (define_function_unit "k6_alux" 1 0
713 (and (eq_attr "cpu" "k6")
714 (eq_attr "type" "ishift,alu1,negnot,cld"))
715 1 1)
716
717 ;; The QI mode arithmetic is issued to X pipe only.
718 (define_function_unit "k6_alux" 1 0
719 (and (eq_attr "cpu" "k6")
720 (and (eq_attr "type" "alu,alu1,negnot,icmp,test,imovx,incdec")
721 (match_operand:QI 0 "general_operand" "")))
722 1 1)
723
724 (define_function_unit "k6_alu" 2 0
725 (and (eq_attr "cpu" "k6")
726 (eq_attr "type" "ishift,alu1,negnot,alu,icmp,test,imovx,incdec,setcc,lea"))
727 1 1)
728
729 (define_function_unit "k6_alu" 2 0
730 (and (eq_attr "cpu" "k6")
731 (and (eq_attr "type" "imov")
732 (eq_attr "memory" "none")))
733 1 1)
734
735 (define_function_unit "k6_branch" 1 0
736 (and (eq_attr "cpu" "k6")
737 (eq_attr "type" "call,callv,ibr"))
738 1 1)
739
740 ;; Load unit have two cycle latency, but we take care for it in adjust_cost
741 (define_function_unit "k6_load" 1 0
742 (and (eq_attr "cpu" "k6")
743 (ior (eq_attr "type" "pop")
744 (eq_attr "memory" "load,both")))
745 1 1)
746
747 (define_function_unit "k6_load" 1 0
748 (and (eq_attr "cpu" "k6")
749 (and (eq_attr "type" "str")
750 (eq_attr "memory" "load,both")))
751 10 10)
752
753 ;; Lea have two instructions, so latency is probably 2
754 (define_function_unit "k6_store" 1 0
755 (and (eq_attr "cpu" "k6")
756 (eq_attr "type" "lea"))
757 2 1)
758
759 (define_function_unit "k6_store" 1 0
760 (and (eq_attr "cpu" "k6")
761 (eq_attr "type" "str"))
762 10 10)
763
764 (define_function_unit "k6_store" 1 0
765 (and (eq_attr "cpu" "k6")
766 (ior (eq_attr "type" "push")
767 (eq_attr "memory" "store,both")))
768 1 1)
769
770 (define_function_unit "k6_fpu" 1 1
771 (and (eq_attr "cpu" "k6")
772 (eq_attr "type" "fop,fop1,fmov,fcmp"))
773 2 2)
774
775 (define_function_unit "k6_fpu" 1 1
776 (and (eq_attr "cpu" "k6")
777 (eq_attr "type" "fmul"))
778 2 2)
779
780 ;; ??? Guess
781 (define_function_unit "k6_fpu" 1 1
782 (and (eq_attr "cpu" "k6")
783 (eq_attr "type" "fdiv,fpspc"))
784 56 56)
785
786 (define_function_unit "k6_alu" 2 0
787 (and (eq_attr "cpu" "k6")
788 (eq_attr "type" "imul"))
789 2 2)
790
791 (define_function_unit "k6_alux" 1 0
792 (and (eq_attr "cpu" "k6")
793 (eq_attr "type" "imul"))
794 2 2)
795
796 ;; ??? Guess
797 (define_function_unit "k6_alu" 2 0
798 (and (eq_attr "cpu" "k6")
799 (eq_attr "type" "idiv"))
800 17 17)
801
802 (define_function_unit "k6_alux" 1 0
803 (and (eq_attr "cpu" "k6")
804 (eq_attr "type" "idiv"))
805 17 17)
806 \f
807 ;; AMD Athlon Scheduling
808 ;;
809 ;; The Athlon does contain three pipelined FP units, three integer units and
810 ;; three address generation units.
811 ;;
812 ;; The predecode logic is determining boundaries of instructions in the 64
813 ;; byte cache line. So the cache line straddling problem of K6 might be issue
814 ;; here as well, but it is not noted in the documentation.
815 ;;
816 ;; Three DirectPath instructions decoders and only one VectorPath decoder
817 ;; is available. They can decode three DirectPath instructions or one VectorPath
818 ;; instruction per cycle.
819 ;; Decoded macro instructions are then passed to 72 entry instruction control
820 ;; unit, that passes
821 ;; it to the specialized integer (18 entry) and fp (36 entry) schedulers.
822 ;;
823 ;; The load/store queue unit is not attached to the schedulers but
824 ;; communicates with all the execution units seperately instead.
825
826 (define_attr "athlon_decode" "direct,vector"
827 (cond [(eq_attr "type" "call,imul,idiv,other,multi,fcmov,fpspc,str,pop,cld,fcmov")
828 (const_string "vector")
829 (and (eq_attr "type" "push")
830 (match_operand 1 "memory_operand" ""))
831 (const_string "vector")
832 (and (eq_attr "type" "fmov")
833 (and (eq_attr "memory" "load,store")
834 (eq_attr "mode" "XF")))
835 (const_string "vector")]
836 (const_string "direct")))
837
838 (define_function_unit "athlon_vectordec" 1 0
839 (and (eq_attr "cpu" "athlon")
840 (eq_attr "athlon_decode" "vector"))
841 1 1)
842
843 (define_function_unit "athlon_directdec" 3 0
844 (and (eq_attr "cpu" "athlon")
845 (eq_attr "athlon_decode" "direct"))
846 1 1)
847
848 (define_function_unit "athlon_vectordec" 1 0
849 (and (eq_attr "cpu" "athlon")
850 (eq_attr "athlon_decode" "direct"))
851 1 1 [(eq_attr "athlon_decode" "vector")])
852
853 (define_function_unit "athlon_ieu" 3 0
854 (and (eq_attr "cpu" "athlon")
855 (eq_attr "type" "alu1,negnot,alu,icmp,test,imov,imovx,lea,incdec,ishift,ibr,call,callv,icmov,cld,pop,setcc,push,pop"))
856 1 1)
857
858 (define_function_unit "athlon_ieu" 3 0
859 (and (eq_attr "cpu" "athlon")
860 (eq_attr "type" "str"))
861 15 15)
862
863 (define_function_unit "athlon_ieu" 3 0
864 (and (eq_attr "cpu" "athlon")
865 (eq_attr "type" "imul"))
866 5 0)
867
868 (define_function_unit "athlon_ieu" 3 0
869 (and (eq_attr "cpu" "athlon")
870 (eq_attr "type" "idiv"))
871 42 0)
872
873 (define_function_unit "athlon_muldiv" 1 0
874 (and (eq_attr "cpu" "athlon")
875 (eq_attr "type" "imul"))
876 5 0)
877
878 (define_function_unit "athlon_muldiv" 1 0
879 (and (eq_attr "cpu" "athlon")
880 (eq_attr "type" "idiv"))
881 42 42)
882
883 (define_attr "athlon_fpunits" "none,store,mul,add,muladd,any"
884 (cond [(eq_attr "type" "fop,fop1,fcmp")
885 (const_string "add")
886 (eq_attr "type" "fmul,fdiv,fpspc,fsgn,fcmov")
887 (const_string "mul")
888 (and (eq_attr "type" "fmov") (eq_attr "memory" "store,both"))
889 (const_string "store")
890 (and (eq_attr "type" "fmov") (eq_attr "memory" "load"))
891 (const_string "any")
892 (and (eq_attr "type" "fmov")
893 (ior (match_operand:SI 1 "register_operand" "")
894 (match_operand 1 "immediate_operand" "")))
895 (const_string "store")
896 (eq_attr "type" "fmov")
897 (const_string "muladd")]
898 (const_string "none")))
899
900 ;; We use latencies 1 for definitions. This is OK to model colisions
901 ;; in execution units. The real latencies are modeled in the "fp" pipeline.
902
903 ;; fsin, fcos: 96-192
904 ;; fsincos: 107-211
905 ;; fsqrt: 19 for SFmode, 27 for DFmode, 35 for XFmode.
906 (define_function_unit "athlon_fp" 3 0
907 (and (eq_attr "cpu" "athlon")
908 (eq_attr "type" "fpspc"))
909 100 1)
910
911 ;; 16 cycles for SFmode, 20 for DFmode and 24 for XFmode.
912 (define_function_unit "athlon_fp" 3 0
913 (and (eq_attr "cpu" "athlon")
914 (eq_attr "type" "fdiv"))
915 24 1)
916
917 (define_function_unit "athlon_fp" 3 0
918 (and (eq_attr "cpu" "athlon")
919 (eq_attr "type" "fop,fop1,fmul"))
920 4 1)
921
922 ;; XFmode loads are slow.
923 ;; XFmode store is slow too (8 cycles), but we don't need to model it, because
924 ;; there are no dependent instructions.
925
926 (define_function_unit "athlon_fp" 3 0
927 (and (eq_attr "cpu" "athlon")
928 (and (eq_attr "type" "fmov")
929 (and (eq_attr "memory" "load")
930 (eq_attr "mode" "XF"))))
931 10 1)
932
933 (define_function_unit "athlon_fp" 3 0
934 (and (eq_attr "cpu" "athlon")
935 (eq_attr "type" "fmov,fsgn"))
936 2 1)
937
938 ;; fcmp and ftst instructions
939 (define_function_unit "athlon_fp" 3 0
940 (and (eq_attr "cpu" "athlon")
941 (and (eq_attr "type" "fcmp")
942 (eq_attr "athlon_decode" "direct")))
943 3 1)
944
945 ;; fcmpi instructions.
946 (define_function_unit "athlon_fp" 3 0
947 (and (eq_attr "cpu" "athlon")
948 (and (eq_attr "type" "fcmp")
949 (eq_attr "athlon_decode" "vector")))
950 3 1)
951
952 (define_function_unit "athlon_fp" 3 0
953 (and (eq_attr "cpu" "athlon")
954 (eq_attr "type" "fcmov"))
955 7 1)
956
957 (define_function_unit "athlon_fp_mul" 1 0
958 (and (eq_attr "cpu" "athlon")
959 (eq_attr "athlon_fpunits" "mul"))
960 1 1)
961
962 (define_function_unit "athlon_fp_add" 1 0
963 (and (eq_attr "cpu" "athlon")
964 (eq_attr "athlon_fpunits" "add"))
965 1 1)
966
967 (define_function_unit "athlon_fp_muladd" 2 0
968 (and (eq_attr "cpu" "athlon")
969 (eq_attr "athlon_fpunits" "muladd,mul,add"))
970 1 1)
971
972 (define_function_unit "athlon_fp_store" 1 0
973 (and (eq_attr "cpu" "athlon")
974 (eq_attr "athlon_fpunits" "store"))
975 1 1)
976
977 ;; We don't need to model the Adress Generation Unit, since we don't model
978 ;; the re-order buffer yet and thus we never schedule more than three operations
979 ;; at time. Later we may want to experiment with MD_SCHED macros modeling the
980 ;; decoders independently on the functional units.
981
982 ;(define_function_unit "athlon_agu" 3 0
983 ; (and (eq_attr "cpu" "athlon")
984 ; (and (eq_attr "memory" "!none")
985 ; (eq_attr "athlon_fpunits" "none")))
986 ; 1 1)
987
988 ;; Model load unit to avoid too long sequences of loads. We don't need to
989 ;; model store queue, since it is hardly going to be bottleneck.
990
991 (define_function_unit "athlon_load" 2 0
992 (and (eq_attr "cpu" "athlon")
993 (eq_attr "memory" "load,both"))
994 1 1)
995
996 \f
997 ;; Compare instructions.
998
999 ;; All compare insns have expanders that save the operands away without
1000 ;; actually generating RTL. The bCOND or sCOND (emitted immediately
1001 ;; after the cmp) will actually emit the cmpM.
1002
1003 (define_expand "cmpdi"
1004 [(set (reg:CC 17)
1005 (compare:CC (match_operand:DI 0 "general_operand" "")
1006 (match_operand:DI 1 "general_operand" "")))]
1007 ""
1008 "
1009 {
1010 if ((GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1011 || (CONSTANT_P (operands[0]) && CONSTANT_P (operands[1])))
1012 operands[0] = force_reg (DImode, operands[0]);
1013 ix86_compare_op0 = operands[0];
1014 ix86_compare_op1 = operands[1];
1015 DONE;
1016 }")
1017
1018 (define_expand "cmpsi"
1019 [(set (reg:CC 17)
1020 (compare:CC (match_operand:SI 0 "cmpsi_operand" "")
1021 (match_operand:SI 1 "general_operand" "")))]
1022 ""
1023 "
1024 {
1025 if ((GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1026 || (CONSTANT_P (operands[0]) && CONSTANT_P (operands[1])))
1027 operands[0] = force_reg (SImode, operands[0]);
1028 ix86_compare_op0 = operands[0];
1029 ix86_compare_op1 = operands[1];
1030 DONE;
1031 }")
1032
1033 (define_expand "cmphi"
1034 [(set (reg:CC 17)
1035 (compare:CC (match_operand:HI 0 "general_operand" "")
1036 (match_operand:HI 1 "general_operand" "")))]
1037 ""
1038 "
1039 {
1040 if ((GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1041 || (CONSTANT_P (operands[0]) && CONSTANT_P (operands[1])))
1042 operands[0] = force_reg (HImode, operands[0]);
1043 ix86_compare_op0 = operands[0];
1044 ix86_compare_op1 = operands[1];
1045 DONE;
1046 }")
1047
1048 (define_expand "cmpqi"
1049 [(set (reg:CC 17)
1050 (compare:CC (match_operand:QI 0 "general_operand" "")
1051 (match_operand:QI 1 "general_operand" "")))]
1052 "TARGET_QIMODE_MATH"
1053 "
1054 {
1055 if ((GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1056 || (CONSTANT_P (operands[0]) && CONSTANT_P (operands[1])))
1057 operands[0] = force_reg (QImode, operands[0]);
1058 ix86_compare_op0 = operands[0];
1059 ix86_compare_op1 = operands[1];
1060 DONE;
1061 }")
1062
1063 (define_insn "*cmpsi_ccno_1"
1064 [(set (reg 17)
1065 (compare (match_operand:SI 0 "nonimmediate_operand" "r,?mr")
1066 (match_operand:SI 1 "const0_operand" "n,n")))]
1067 "ix86_match_ccmode (insn, CCNOmode)"
1068 "@
1069 test{l}\\t{%0, %0|%0, %0}
1070 cmp{l}\\t{%1, %0|%0, %1}"
1071 [(set_attr "type" "test,icmp")
1072 (set_attr "length_immediate" "0,1")
1073 (set_attr "mode" "SI")])
1074
1075 (define_insn "*cmpsi_minus_1"
1076 [(set (reg 17)
1077 (compare (minus:SI (match_operand:SI 0 "nonimmediate_operand" "rm,r")
1078 (match_operand:SI 1 "general_operand" "ri,mr"))
1079 (const_int 0)))]
1080 "ix86_match_ccmode (insn, CCGOCmode)"
1081 "cmp{l}\\t{%1, %0|%0, %1}"
1082 [(set_attr "type" "icmp")
1083 (set_attr "mode" "SI")])
1084
1085 (define_expand "cmpsi_1"
1086 [(set (reg:CC 17)
1087 (compare:CC (match_operand:SI 0 "nonimmediate_operand" "rm,r")
1088 (match_operand:SI 1 "general_operand" "ri,mr")))]
1089 ""
1090 "")
1091
1092 (define_insn "*cmpsi_1_insn"
1093 [(set (reg 17)
1094 (compare (match_operand:SI 0 "nonimmediate_operand" "rm,r")
1095 (match_operand:SI 1 "general_operand" "ri,mr")))]
1096 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
1097 && ix86_match_ccmode (insn, CCmode)"
1098 "cmp{l}\\t{%1, %0|%0, %1}"
1099 [(set_attr "type" "icmp")
1100 (set_attr "mode" "SI")])
1101
1102 (define_insn "*cmphi_ccno_1"
1103 [(set (reg 17)
1104 (compare (match_operand:HI 0 "nonimmediate_operand" "r,?mr")
1105 (match_operand:HI 1 "const0_operand" "n,n")))]
1106 "ix86_match_ccmode (insn, CCNOmode)"
1107 "@
1108 test{w}\\t{%0, %0|%0, %0}
1109 cmp{w}\\t{%1, %0|%0, %1}"
1110 [(set_attr "type" "test,icmp")
1111 (set_attr "length_immediate" "0,1")
1112 (set_attr "mode" "HI")])
1113
1114 (define_insn "*cmphi_minus_1"
1115 [(set (reg 17)
1116 (compare (minus:HI (match_operand:HI 0 "nonimmediate_operand" "rm,r")
1117 (match_operand:HI 1 "general_operand" "ri,mr"))
1118 (const_int 0)))]
1119 "ix86_match_ccmode (insn, CCGOCmode)"
1120 "cmp{w}\\t{%1, %0|%0, %1}"
1121 [(set_attr "type" "icmp")
1122 (set_attr "mode" "HI")])
1123
1124 (define_insn "*cmphi_1"
1125 [(set (reg 17)
1126 (compare (match_operand:HI 0 "nonimmediate_operand" "rm,r")
1127 (match_operand:HI 1 "general_operand" "ri,mr")))]
1128 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
1129 && ix86_match_ccmode (insn, CCmode)"
1130 "cmp{w}\\t{%1, %0|%0, %1}"
1131 [(set_attr "type" "icmp")
1132 (set_attr "mode" "HI")])
1133
1134 (define_insn "*cmpqi_ccno_1"
1135 [(set (reg 17)
1136 (compare (match_operand:QI 0 "nonimmediate_operand" "q,?mq")
1137 (match_operand:QI 1 "const0_operand" "n,n")))]
1138 "ix86_match_ccmode (insn, CCNOmode)"
1139 "@
1140 test{b}\\t{%0, %0|%0, %0}
1141 cmp{b}\\t{$0, %0|%0, 0}"
1142 [(set_attr "type" "test,icmp")
1143 (set_attr "length_immediate" "0,1")
1144 (set_attr "mode" "QI")])
1145
1146 (define_insn "*cmpqi_1"
1147 [(set (reg 17)
1148 (compare (match_operand:QI 0 "nonimmediate_operand" "qm,q")
1149 (match_operand:QI 1 "general_operand" "qi,mq")))]
1150 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
1151 && ix86_match_ccmode (insn, CCmode)"
1152 "cmp{b}\\t{%1, %0|%0, %1}"
1153 [(set_attr "type" "icmp")
1154 (set_attr "mode" "QI")])
1155
1156 (define_insn "*cmpqi_minus_1"
1157 [(set (reg 17)
1158 (compare (minus:QI (match_operand:QI 0 "nonimmediate_operand" "qm,q")
1159 (match_operand:QI 1 "general_operand" "qi,mq"))
1160 (const_int 0)))]
1161 "ix86_match_ccmode (insn, CCGOCmode)"
1162 "cmp{b}\\t{%1, %0|%0, %1}"
1163 [(set_attr "type" "icmp")
1164 (set_attr "mode" "QI")])
1165
1166 (define_insn "*cmpqi_ext_1"
1167 [(set (reg 17)
1168 (compare
1169 (match_operand:QI 0 "general_operand" "Qm")
1170 (subreg:QI
1171 (zero_extract:SI
1172 (match_operand 1 "ext_register_operand" "Q")
1173 (const_int 8)
1174 (const_int 8)) 0)))]
1175 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1176 "cmp{b}\\t{%h1, %0|%0, %h1}"
1177 [(set_attr "type" "icmp")
1178 (set_attr "mode" "QI")])
1179
1180 (define_insn "*cmpqi_ext_1_rex64"
1181 [(set (reg 17)
1182 (compare
1183 (match_operand:QI 0 "ext_register_operand" "Q")
1184 (subreg:QI
1185 (zero_extract:SI
1186 (match_operand 1 "ext_register_operand" "Q")
1187 (const_int 8)
1188 (const_int 8)) 0)))]
1189 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1190 "cmp{b}\\t{%h1, %0|%0, %h1}"
1191 [(set_attr "type" "icmp")
1192 (set_attr "mode" "QI")])
1193
1194 (define_insn "*cmpqi_ext_2"
1195 [(set (reg 17)
1196 (compare
1197 (subreg:QI
1198 (zero_extract:SI
1199 (match_operand 0 "ext_register_operand" "Q")
1200 (const_int 8)
1201 (const_int 8)) 0)
1202 (match_operand:QI 1 "const0_operand" "n")))]
1203 "ix86_match_ccmode (insn, CCNOmode)"
1204 "test{b}\\t%h0, %h0"
1205 [(set_attr "type" "test")
1206 (set_attr "length_immediate" "0")
1207 (set_attr "mode" "QI")])
1208
1209 (define_expand "cmpqi_ext_3"
1210 [(set (reg:CC 17)
1211 (compare:CC
1212 (subreg:QI
1213 (zero_extract:SI
1214 (match_operand 0 "ext_register_operand" "")
1215 (const_int 8)
1216 (const_int 8)) 0)
1217 (match_operand:QI 1 "general_operand" "")))]
1218 ""
1219 "")
1220
1221 (define_insn "cmpqi_ext_3_insn"
1222 [(set (reg 17)
1223 (compare
1224 (subreg:QI
1225 (zero_extract:SI
1226 (match_operand 0 "ext_register_operand" "Q")
1227 (const_int 8)
1228 (const_int 8)) 0)
1229 (match_operand:QI 1 "general_operand" "Qmn")))]
1230 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1231 "cmp{b}\\t{%1, %h0|%h0, %1}"
1232 [(set_attr "type" "icmp")
1233 (set_attr "mode" "QI")])
1234
1235 (define_insn "cmpqi_ext_3_insn_rex64"
1236 [(set (reg 17)
1237 (compare
1238 (subreg:QI
1239 (zero_extract:SI
1240 (match_operand 0 "ext_register_operand" "Q")
1241 (const_int 8)
1242 (const_int 8)) 0)
1243 (match_operand:QI 1 "nonmemory_operand" "Qn")))]
1244 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
1245 "cmp{b}\\t{%1, %h0|%h0, %1}"
1246 [(set_attr "type" "icmp")
1247 (set_attr "mode" "QI")])
1248
1249 (define_insn "*cmpqi_ext_4"
1250 [(set (reg 17)
1251 (compare
1252 (subreg:QI
1253 (zero_extract:SI
1254 (match_operand 0 "ext_register_operand" "Q")
1255 (const_int 8)
1256 (const_int 8)) 0)
1257 (subreg:QI
1258 (zero_extract:SI
1259 (match_operand 1 "ext_register_operand" "Q")
1260 (const_int 8)
1261 (const_int 8)) 0)))]
1262 "ix86_match_ccmode (insn, CCmode)"
1263 "cmp{b}\\t{%h1, %h0|%h0, %h1}"
1264 [(set_attr "type" "icmp")
1265 (set_attr "mode" "QI")])
1266
1267 ;; These implement float point compares.
1268 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
1269 ;; which would allow mix and match FP modes on the compares. Which is what
1270 ;; the old patterns did, but with many more of them.
1271
1272 (define_expand "cmpxf"
1273 [(set (reg:CC 17)
1274 (compare:CC (match_operand:XF 0 "cmp_fp_expander_operand" "")
1275 (match_operand:XF 1 "cmp_fp_expander_operand" "")))]
1276 "TARGET_80387 && !TARGET_64BIT"
1277 "
1278 {
1279 ix86_compare_op0 = operands[0];
1280 ix86_compare_op1 = operands[1];
1281 DONE;
1282 }")
1283
1284 (define_expand "cmptf"
1285 [(set (reg:CC 17)
1286 (compare:CC (match_operand:TF 0 "cmp_fp_expander_operand" "")
1287 (match_operand:TF 1 "cmp_fp_expander_operand" "")))]
1288 "TARGET_80387"
1289 "
1290 {
1291 ix86_compare_op0 = operands[0];
1292 ix86_compare_op1 = operands[1];
1293 DONE;
1294 }")
1295
1296 (define_expand "cmpdf"
1297 [(set (reg:CC 17)
1298 (compare:CC (match_operand:DF 0 "cmp_fp_expander_operand" "")
1299 (match_operand:DF 1 "cmp_fp_expander_operand" "")))]
1300 "TARGET_80387 || TARGET_SSE2"
1301 "
1302 {
1303 ix86_compare_op0 = operands[0];
1304 ix86_compare_op1 = operands[1];
1305 DONE;
1306 }")
1307
1308 (define_expand "cmpsf"
1309 [(set (reg:CC 17)
1310 (compare:CC (match_operand:SF 0 "cmp_fp_expander_operand" "")
1311 (match_operand:SF 1 "cmp_fp_expander_operand" "")))]
1312 "TARGET_80387 || TARGET_SSE"
1313 "
1314 {
1315 ix86_compare_op0 = operands[0];
1316 ix86_compare_op1 = operands[1];
1317 DONE;
1318 }")
1319
1320 ;; FP compares, step 1:
1321 ;; Set the FP condition codes.
1322 ;;
1323 ;; CCFPmode compare with exceptions
1324 ;; CCFPUmode compare with no exceptions
1325
1326 ;; %%% It is an unfortunate fact that ftst has no non-popping variant,
1327 ;; and that fp moves clobber the condition codes, and that there is
1328 ;; currently no way to describe this fact to reg-stack. So there are
1329 ;; no splitters yet for this.
1330
1331 ;; %%% YIKES! This scheme does not retain a strong connection between
1332 ;; the real compare and the ultimate cc0 user, so CC_REVERSE does not
1333 ;; work! Only allow tos/mem with tos in op 0.
1334 ;;
1335 ;; Hmm, of course, this is what the actual _hardware_ does. Perhaps
1336 ;; things aren't as bad as they sound...
1337
1338 (define_insn "*cmpfp_0"
1339 [(set (match_operand:HI 0 "register_operand" "=a")
1340 (unspec:HI
1341 [(compare:CCFP (match_operand 1 "register_operand" "f")
1342 (match_operand 2 "const0_operand" "X"))] 9))]
1343 "TARGET_80387
1344 && FLOAT_MODE_P (GET_MODE (operands[1]))
1345 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1346 "*
1347 {
1348 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
1349 return \"ftst\;fnstsw\\t%0\;fstp\\t%y0\";
1350 else
1351 return \"ftst\;fnstsw\\t%0\";
1352 }"
1353 [(set_attr "type" "multi")
1354 (set_attr "mode" "unknownfp")])
1355
1356 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
1357 ;; used to manage the reg stack popping would not be preserved.
1358
1359 (define_insn "*cmpfp_2_sf"
1360 [(set (reg:CCFP 18)
1361 (compare:CCFP
1362 (match_operand:SF 0 "register_operand" "f")
1363 (match_operand:SF 1 "nonimmediate_operand" "fm")))]
1364 "TARGET_80387"
1365 "* return output_fp_compare (insn, operands, 0, 0);"
1366 [(set_attr "type" "fcmp")
1367 (set_attr "mode" "SF")])
1368
1369 (define_insn "*cmpfp_2_sf_1"
1370 [(set (match_operand:HI 0 "register_operand" "=a")
1371 (unspec:HI
1372 [(compare:CCFP
1373 (match_operand:SF 1 "register_operand" "f")
1374 (match_operand:SF 2 "nonimmediate_operand" "fm"))] 9))]
1375 "TARGET_80387"
1376 "* return output_fp_compare (insn, operands, 2, 0);"
1377 [(set_attr "type" "fcmp")
1378 (set_attr "mode" "SF")])
1379
1380 (define_insn "*cmpfp_2_df"
1381 [(set (reg:CCFP 18)
1382 (compare:CCFP
1383 (match_operand:DF 0 "register_operand" "f")
1384 (match_operand:DF 1 "nonimmediate_operand" "fm")))]
1385 "TARGET_80387"
1386 "* return output_fp_compare (insn, operands, 0, 0);"
1387 [(set_attr "type" "fcmp")
1388 (set_attr "mode" "DF")])
1389
1390 (define_insn "*cmpfp_2_df_1"
1391 [(set (match_operand:HI 0 "register_operand" "=a")
1392 (unspec:HI
1393 [(compare:CCFP
1394 (match_operand:DF 1 "register_operand" "f")
1395 (match_operand:DF 2 "nonimmediate_operand" "fm"))] 9))]
1396 "TARGET_80387"
1397 "* return output_fp_compare (insn, operands, 2, 0);"
1398 [(set_attr "type" "multi")
1399 (set_attr "mode" "DF")])
1400
1401 (define_insn "*cmpfp_2_xf"
1402 [(set (reg:CCFP 18)
1403 (compare:CCFP
1404 (match_operand:XF 0 "register_operand" "f")
1405 (match_operand:XF 1 "register_operand" "f")))]
1406 "TARGET_80387 && !TARGET_64BIT"
1407 "* return output_fp_compare (insn, operands, 0, 0);"
1408 [(set_attr "type" "fcmp")
1409 (set_attr "mode" "XF")])
1410
1411 (define_insn "*cmpfp_2_tf"
1412 [(set (reg:CCFP 18)
1413 (compare:CCFP
1414 (match_operand:TF 0 "register_operand" "f")
1415 (match_operand:TF 1 "register_operand" "f")))]
1416 "TARGET_80387"
1417 "* return output_fp_compare (insn, operands, 0, 0);"
1418 [(set_attr "type" "fcmp")
1419 (set_attr "mode" "XF")])
1420
1421 (define_insn "*cmpfp_2_xf_1"
1422 [(set (match_operand:HI 0 "register_operand" "=a")
1423 (unspec:HI
1424 [(compare:CCFP
1425 (match_operand:XF 1 "register_operand" "f")
1426 (match_operand:XF 2 "register_operand" "f"))] 9))]
1427 "TARGET_80387 && !TARGET_64BIT"
1428 "* return output_fp_compare (insn, operands, 2, 0);"
1429 [(set_attr "type" "multi")
1430 (set_attr "mode" "XF")])
1431
1432 (define_insn "*cmpfp_2_tf_1"
1433 [(set (match_operand:HI 0 "register_operand" "=a")
1434 (unspec:HI
1435 [(compare:CCFP
1436 (match_operand:TF 1 "register_operand" "f")
1437 (match_operand:TF 2 "register_operand" "f"))] 9))]
1438 "TARGET_80387"
1439 "* return output_fp_compare (insn, operands, 2, 0);"
1440 [(set_attr "type" "multi")
1441 (set_attr "mode" "XF")])
1442
1443 (define_insn "*cmpfp_2u"
1444 [(set (reg:CCFPU 18)
1445 (compare:CCFPU
1446 (match_operand 0 "register_operand" "f")
1447 (match_operand 1 "register_operand" "f")))]
1448 "TARGET_80387
1449 && FLOAT_MODE_P (GET_MODE (operands[0]))
1450 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1451 "* return output_fp_compare (insn, operands, 0, 1);"
1452 [(set_attr "type" "fcmp")
1453 (set_attr "mode" "unknownfp")])
1454
1455 (define_insn "*cmpfp_2u_1"
1456 [(set (match_operand:HI 0 "register_operand" "=a")
1457 (unspec:HI
1458 [(compare:CCFPU
1459 (match_operand 1 "register_operand" "f")
1460 (match_operand 2 "register_operand" "f"))] 9))]
1461 "TARGET_80387
1462 && FLOAT_MODE_P (GET_MODE (operands[1]))
1463 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
1464 "* return output_fp_compare (insn, operands, 2, 1);"
1465 [(set_attr "type" "multi")
1466 (set_attr "mode" "unknownfp")])
1467
1468 ;; Patterns to match the SImode-in-memory ficom instructions.
1469 ;;
1470 ;; %%% Play games with accepting gp registers, as otherwise we have to
1471 ;; force them to memory during rtl generation, which is no good. We
1472 ;; can get rid of this once we teach reload to do memory input reloads
1473 ;; via pushes.
1474
1475 (define_insn "*ficom_1"
1476 [(set (reg:CCFP 18)
1477 (compare:CCFP
1478 (match_operand 0 "register_operand" "f,f")
1479 (float (match_operand:SI 1 "nonimmediate_operand" "m,?r"))))]
1480 "0 && TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[0]))
1481 && GET_MODE (XEXP (SET_SRC (PATTERN (insn)), 1)) == GET_MODE (operands[0])"
1482 "#")
1483
1484 ;; Split the not-really-implemented gp register case into a
1485 ;; push-op-pop sequence.
1486 ;;
1487 ;; %%% This is most efficient, but am I gonna get in trouble
1488 ;; for separating cc0_setter and cc0_user?
1489
1490 (define_split
1491 [(set (reg:CCFP 18)
1492 (compare:CCFP
1493 (match_operand:SF 0 "register_operand" "")
1494 (float (match_operand:SI 1 "register_operand" ""))))]
1495 "0 && TARGET_80387 && reload_completed"
1496 [(set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 1))
1497 (set (reg:CCFP 18) (compare:CCFP (match_dup 0) (match_dup 2)))
1498 (parallel [(set (match_dup 1) (mem:SI (reg:SI 7)))
1499 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
1500 "operands[2] = gen_rtx_MEM (Pmode, stack_pointer_rtx);
1501 operands[2] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[2]);")
1502
1503 ;; FP compares, step 2
1504 ;; Move the fpsw to ax.
1505
1506 (define_insn "x86_fnstsw_1"
1507 [(set (match_operand:HI 0 "register_operand" "=a")
1508 (unspec:HI [(reg 18)] 9))]
1509 "TARGET_80387"
1510 "fnstsw\\t%0"
1511 [(set_attr "length" "2")
1512 (set_attr "mode" "SI")
1513 (set_attr "i387" "1")
1514 (set_attr "ppro_uops" "few")])
1515
1516 ;; FP compares, step 3
1517 ;; Get ax into flags, general case.
1518
1519 (define_insn "x86_sahf_1"
1520 [(set (reg:CC 17)
1521 (unspec:CC [(match_operand:HI 0 "register_operand" "a")] 10))]
1522 "!TARGET_64BIT"
1523 "sahf"
1524 [(set_attr "length" "1")
1525 (set_attr "athlon_decode" "vector")
1526 (set_attr "mode" "SI")
1527 (set_attr "ppro_uops" "one")])
1528
1529 ;; Pentium Pro can do steps 1 through 3 in one go.
1530
1531 (define_insn "*cmpfp_i"
1532 [(set (reg:CCFP 17)
1533 (compare:CCFP (match_operand 0 "register_operand" "f")
1534 (match_operand 1 "register_operand" "f")))]
1535 "TARGET_80387 && TARGET_CMOVE
1536 && !SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1537 && FLOAT_MODE_P (GET_MODE (operands[0]))
1538 && GET_MODE (operands[0]) == GET_MODE (operands[0])"
1539 "* return output_fp_compare (insn, operands, 1, 0);"
1540 [(set_attr "type" "fcmp")
1541 (set_attr "mode" "unknownfp")
1542 (set_attr "athlon_decode" "vector")])
1543
1544 (define_insn "*cmpfp_i_sse"
1545 [(set (reg:CCFP 17)
1546 (compare:CCFP (match_operand 0 "register_operand" "f#x,x#f")
1547 (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
1548 "TARGET_80387
1549 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1550 && GET_MODE (operands[0]) == GET_MODE (operands[0])"
1551 "* return output_fp_compare (insn, operands, 1, 0);"
1552 [(set_attr "type" "fcmp,sse")
1553 (set_attr "mode" "unknownfp")
1554 (set_attr "athlon_decode" "vector")])
1555
1556 (define_insn "*cmpfp_i_sse_only"
1557 [(set (reg:CCFP 17)
1558 (compare:CCFP (match_operand 0 "register_operand" "x")
1559 (match_operand 1 "nonimmediate_operand" "xm")))]
1560 "SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1561 && GET_MODE (operands[0]) == GET_MODE (operands[0])"
1562 "* return output_fp_compare (insn, operands, 1, 0);"
1563 [(set_attr "type" "sse")
1564 (set_attr "mode" "unknownfp")
1565 (set_attr "athlon_decode" "vector")])
1566
1567 (define_insn "*cmpfp_iu"
1568 [(set (reg:CCFPU 17)
1569 (compare:CCFPU (match_operand 0 "register_operand" "f")
1570 (match_operand 1 "register_operand" "f")))]
1571 "TARGET_80387 && TARGET_CMOVE
1572 && !SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1573 && FLOAT_MODE_P (GET_MODE (operands[0]))
1574 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1575 "* return output_fp_compare (insn, operands, 1, 1);"
1576 [(set_attr "type" "fcmp")
1577 (set_attr "mode" "unknownfp")
1578 (set_attr "athlon_decode" "vector")])
1579
1580 (define_insn "*cmpfp_iu_sse"
1581 [(set (reg:CCFPU 17)
1582 (compare:CCFPU (match_operand 0 "register_operand" "f#x,x#f")
1583 (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
1584 "TARGET_80387
1585 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1586 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1587 "* return output_fp_compare (insn, operands, 1, 1);"
1588 [(set_attr "type" "fcmp,sse")
1589 (set_attr "mode" "unknownfp")
1590 (set_attr "athlon_decode" "vector")])
1591
1592 (define_insn "*cmpfp_iu_sse_only"
1593 [(set (reg:CCFPU 17)
1594 (compare:CCFPU (match_operand 0 "register_operand" "x")
1595 (match_operand 1 "nonimmediate_operand" "xm")))]
1596 "SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1597 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1598 "* return output_fp_compare (insn, operands, 1, 1);"
1599 [(set_attr "type" "sse")
1600 (set_attr "mode" "unknownfp")
1601 (set_attr "athlon_decode" "vector")])
1602 \f
1603 ;; Move instructions.
1604
1605 ;; General case of fullword move.
1606
1607 (define_expand "movsi"
1608 [(set (match_operand:SI 0 "nonimmediate_operand" "")
1609 (match_operand:SI 1 "general_operand" ""))]
1610 ""
1611 "ix86_expand_move (SImode, operands); DONE;")
1612
1613 ;; Push/pop instructions. They are separate since autoinc/dec is not a
1614 ;; general_operand.
1615 ;;
1616 ;; %%% We don't use a post-inc memory reference because x86 is not a
1617 ;; general AUTO_INC_DEC host, which impacts how it is treated in flow.
1618 ;; Changing this impacts compiler performance on other non-AUTO_INC_DEC
1619 ;; targets without our curiosities, and it is just as easy to represent
1620 ;; this differently.
1621
1622 (define_insn "*pushsi2"
1623 [(set (match_operand:SI 0 "push_operand" "=<")
1624 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1625 "!TARGET_64BIT"
1626 "push{l}\\t%1"
1627 [(set_attr "type" "push")
1628 (set_attr "mode" "SI")])
1629
1630 ;; For 64BIT abi we always round up to 8 bytes.
1631 (define_insn "*pushsi2_rex64"
1632 [(set (match_operand:SI 0 "push_operand" "=X")
1633 (match_operand:SI 1 "nonmemory_no_elim_operand" "ri"))]
1634 "TARGET_64BIT"
1635 "push{q}\\t%q1"
1636 [(set_attr "type" "push")
1637 (set_attr "mode" "SI")])
1638
1639 (define_insn "*pushsi2_prologue"
1640 [(set (match_operand:SI 0 "push_operand" "=<")
1641 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))
1642 (set (reg:SI 6) (reg:SI 6))]
1643 "!TARGET_64BIT"
1644 "push{l}\\t%1"
1645 [(set_attr "type" "push")
1646 (set_attr "mode" "SI")])
1647
1648 (define_insn "*popsi1_epilogue"
1649 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1650 (mem:SI (reg:SI 7)))
1651 (set (reg:SI 7)
1652 (plus:SI (reg:SI 7) (const_int 4)))
1653 (set (reg:SI 6) (reg:SI 6))]
1654 "!TARGET_64BIT"
1655 "pop{l}\\t%0"
1656 [(set_attr "type" "pop")
1657 (set_attr "mode" "SI")])
1658
1659 (define_insn "popsi1"
1660 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1661 (mem:SI (reg:SI 7)))
1662 (set (reg:SI 7)
1663 (plus:SI (reg:SI 7) (const_int 4)))]
1664 "!TARGET_64BIT"
1665 "pop{l}\\t%0"
1666 [(set_attr "type" "pop")
1667 (set_attr "mode" "SI")])
1668
1669 (define_insn "*movsi_xor"
1670 [(set (match_operand:SI 0 "register_operand" "=r")
1671 (match_operand:SI 1 "const0_operand" "i"))
1672 (clobber (reg:CC 17))]
1673 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1674 "xor{l}\\t{%0, %0|%0, %0}"
1675 [(set_attr "type" "alu1")
1676 (set_attr "mode" "SI")
1677 (set_attr "length_immediate" "0")])
1678
1679 (define_insn "*movsi_or"
1680 [(set (match_operand:SI 0 "register_operand" "=r")
1681 (match_operand:SI 1 "immediate_operand" "i"))
1682 (clobber (reg:CC 17))]
1683 "reload_completed && GET_CODE (operands[1]) == CONST_INT
1684 && INTVAL (operands[1]) == -1
1685 && (TARGET_PENTIUM || optimize_size)"
1686 "*
1687 {
1688 operands[1] = constm1_rtx;
1689 return \"or{l}\\t{%1, %0|%0, %1}\";
1690 }"
1691 [(set_attr "type" "alu1")
1692 (set_attr "mode" "SI")
1693 (set_attr "length_immediate" "1")])
1694
1695 (define_insn "*movsi_1"
1696 [(set (match_operand:SI 0 "nonimmediate_operand" "=*a,r,*a,m,!*y,!r")
1697 (match_operand:SI 1 "general_operand" "im,rinm,rinm,rin,r,*y"))]
1698 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1699 "*
1700 {
1701 switch (get_attr_type (insn))
1702 {
1703 case TYPE_MMX:
1704 return \"movd\\t{%1, %0|%0, %1}\";
1705
1706 case TYPE_LEA:
1707 return \"lea{l}\\t{%1, %0|%0, %1}\";
1708
1709 default:
1710 if (flag_pic && SYMBOLIC_CONST (operands[1]))
1711 abort();
1712 return \"mov{l}\\t{%1, %0|%0, %1}\";
1713 }
1714 }"
1715 [(set (attr "type")
1716 (cond [(ior (match_operand:SI 0 "mmx_reg_operand" "")
1717 (match_operand:SI 1 "mmx_reg_operand" ""))
1718 (const_string "mmx")
1719 (and (ne (symbol_ref "flag_pic") (const_int 0))
1720 (match_operand:SI 1 "symbolic_operand" ""))
1721 (const_string "lea")
1722 ]
1723 (const_string "imov")))
1724 (set_attr "modrm" "0,*,0,*,*,*")
1725 (set_attr "mode" "SI")])
1726
1727 ;; Stores and loads of ax to arbitary constant address.
1728 ;; We fake an second form of instruction to force reload to load address
1729 ;; into register when rax is not available
1730 (define_insn "*movabssi_1_rex64"
1731 [(set (mem:SI (match_operand:DI 0 "x86_64_movabs_operand" "i,r,r"))
1732 (match_operand:SI 1 "nonmemory_operand" "a,er,i"))]
1733 "TARGET_64BIT"
1734 "@
1735 movabs{l}\\t{%1, %P0|%P0, %1}
1736 mov{l}\\t{%1, %a0|%a0, %1}
1737 movabs{l}\\t{%1, %a0|%a0, %1}"
1738 [(set_attr "type" "imov")
1739 (set_attr "modrm" "0,*,*")
1740 (set_attr "length_address" "8,0,0")
1741 (set_attr "length_immediate" "0,*,*")
1742 (set_attr "memory" "store")
1743 (set_attr "mode" "SI")])
1744
1745 (define_insn "*movabssi_2_rex64"
1746 [(set (match_operand:SI 0 "register_operand" "=a,r")
1747 (mem:SI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1748 "TARGET_64BIT"
1749 "@
1750 movabs{l}\\t{%P1, %0|%0, %P1}
1751 mov{l}\\t{%a1, %0|%0, %a1}"
1752 [(set_attr "type" "imov")
1753 (set_attr "modrm" "0,*")
1754 (set_attr "length_address" "8,0")
1755 (set_attr "length_immediate" "0")
1756 (set_attr "memory" "load")
1757 (set_attr "mode" "SI")])
1758
1759 (define_insn "*swapsi"
1760 [(set (match_operand:SI 0 "register_operand" "+r")
1761 (match_operand:SI 1 "register_operand" "+r"))
1762 (set (match_dup 1)
1763 (match_dup 0))]
1764 ""
1765 "xchg{l}\\t%1, %0"
1766 [(set_attr "type" "imov")
1767 (set_attr "pent_pair" "np")
1768 (set_attr "athlon_decode" "vector")
1769 (set_attr "mode" "SI")
1770 (set_attr "modrm" "0")
1771 (set_attr "ppro_uops" "few")])
1772
1773 (define_expand "movhi"
1774 [(set (match_operand:HI 0 "nonimmediate_operand" "")
1775 (match_operand:HI 1 "general_operand" ""))]
1776 ""
1777 "ix86_expand_move (HImode, operands); DONE;")
1778
1779 (define_insn "*pushhi2"
1780 [(set (match_operand:HI 0 "push_operand" "=<,<")
1781 (match_operand:HI 1 "general_no_elim_operand" "n,r*m"))]
1782 "!TARGET_64BIT"
1783 "@
1784 push{w}\\t{|WORD PTR }%1
1785 push{w}\\t%1"
1786 [(set_attr "type" "push")
1787 (set_attr "mode" "HI")])
1788
1789 (define_insn "*movhi_1"
1790 [(set (match_operand:HI 0 "nonimmediate_operand" "=*a,r,r,*a,r,m")
1791 (match_operand:HI 1 "general_operand" "i,r,rn,rm,rm,rn"))]
1792 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1793 "*
1794 {
1795 switch (get_attr_type (insn))
1796 {
1797 case TYPE_IMOVX:
1798 /* movzwl is faster than movw on p2 due to partial word stalls,
1799 though not as fast as an aligned movl. */
1800 return \"movz{wl|x}\\t{%1, %k0|%k0, %1}\";
1801 default:
1802 if (get_attr_mode (insn) == MODE_SI)
1803 return \"mov{l}\\t{%k1, %k0|%k0, %k1}\";
1804 else
1805 return \"mov{w}\\t{%1, %0|%0, %1}\";
1806 }
1807 }"
1808 [(set (attr "type")
1809 (cond [(and (eq_attr "alternative" "0,1")
1810 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1811 (const_int 0))
1812 (eq (symbol_ref "TARGET_HIMODE_MATH")
1813 (const_int 0))))
1814 (const_string "imov")
1815 (and (eq_attr "alternative" "2,3,4")
1816 (match_operand:HI 1 "aligned_operand" ""))
1817 (const_string "imov")
1818 (and (ne (symbol_ref "TARGET_MOVX")
1819 (const_int 0))
1820 (eq_attr "alternative" "0,1,3,4"))
1821 (const_string "imovx")
1822 ]
1823 (const_string "imov")))
1824 (set (attr "mode")
1825 (cond [(eq_attr "type" "imovx")
1826 (const_string "SI")
1827 (and (eq_attr "alternative" "2,3,4")
1828 (match_operand:HI 1 "aligned_operand" ""))
1829 (const_string "SI")
1830 (and (eq_attr "alternative" "0,1")
1831 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1832 (const_int 0))
1833 (eq (symbol_ref "TARGET_HIMODE_MATH")
1834 (const_int 0))))
1835 (const_string "SI")
1836 ]
1837 (const_string "HI")))
1838 (set_attr "modrm" "0,*,*,0,*,*")])
1839
1840 ;; Stores and loads of ax to arbitary constant address.
1841 ;; We fake an second form of instruction to force reload to load address
1842 ;; into register when rax is not available
1843 (define_insn "*movabshi_1_rex64"
1844 [(set (mem:HI (match_operand:DI 0 "x86_64_movabs_operand" "i,r,r"))
1845 (match_operand:HI 1 "nonmemory_operand" "a,er,i"))]
1846 "TARGET_64BIT"
1847 "@
1848 movabs{w}\\t{%1, %P0|%P0, %1}
1849 mov{w}\\t{%1, %a0|%a0, %1}
1850 movabs{w}\\t{%1, %a0|%a0, %1}"
1851 [(set_attr "type" "imov")
1852 (set_attr "modrm" "0,*,*")
1853 (set_attr "length_address" "8,0,0")
1854 (set_attr "length_immediate" "0,*,*")
1855 (set_attr "memory" "store")
1856 (set_attr "mode" "HI")])
1857
1858 (define_insn "*movabshi_2_rex64"
1859 [(set (match_operand:HI 0 "register_operand" "=a,r")
1860 (mem:HI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1861 "TARGET_64BIT"
1862 "@
1863 movabs{w}\\t{%P1, %0|%0, %P1}
1864 mov{w}\\t{%a1, %0|%0, %a1}"
1865 [(set_attr "type" "imov")
1866 (set_attr "modrm" "0,*")
1867 (set_attr "length_address" "8,0")
1868 (set_attr "length_immediate" "0")
1869 (set_attr "memory" "load")
1870 (set_attr "mode" "HI")])
1871
1872 (define_insn "*swaphi_1"
1873 [(set (match_operand:HI 0 "register_operand" "+r")
1874 (match_operand:HI 1 "register_operand" "+r"))
1875 (set (match_dup 1)
1876 (match_dup 0))]
1877 "TARGET_PARTIAL_REG_STALL"
1878 "xchg{w}\\t%1, %0"
1879 [(set_attr "type" "imov")
1880 (set_attr "pent_pair" "np")
1881 (set_attr "mode" "HI")
1882 (set_attr "modrm" "0")
1883 (set_attr "ppro_uops" "few")])
1884
1885 (define_insn "*swaphi_2"
1886 [(set (match_operand:HI 0 "register_operand" "+r")
1887 (match_operand:HI 1 "register_operand" "+r"))
1888 (set (match_dup 1)
1889 (match_dup 0))]
1890 "! TARGET_PARTIAL_REG_STALL"
1891 "xchg{l}\\t%k1, %k0"
1892 [(set_attr "type" "imov")
1893 (set_attr "pent_pair" "np")
1894 (set_attr "mode" "SI")
1895 (set_attr "modrm" "0")
1896 (set_attr "ppro_uops" "few")])
1897
1898 (define_expand "movstricthi"
1899 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" ""))
1900 (match_operand:HI 1 "general_operand" ""))]
1901 "! TARGET_PARTIAL_REG_STALL"
1902 "
1903 {
1904 /* Don't generate memory->memory moves, go through a register */
1905 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1906 operands[1] = force_reg (HImode, operands[1]);
1907 }")
1908
1909 (define_insn "*movstricthi_1"
1910 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+rm,r"))
1911 (match_operand:HI 1 "general_operand" "rn,m"))]
1912 "! TARGET_PARTIAL_REG_STALL
1913 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1914 "mov{w}\\t{%1, %0|%0, %1}"
1915 [(set_attr "type" "imov")
1916 (set_attr "mode" "HI")])
1917
1918 (define_insn "*movstricthi_xor"
1919 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
1920 (match_operand:HI 1 "const0_operand" "i"))
1921 (clobber (reg:CC 17))]
1922 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1923 "xor{w}\\t{%0, %0|%0, %0}"
1924 [(set_attr "type" "alu1")
1925 (set_attr "mode" "HI")
1926 (set_attr "length_immediate" "0")])
1927
1928 (define_expand "movqi"
1929 [(set (match_operand:QI 0 "nonimmediate_operand" "")
1930 (match_operand:QI 1 "general_operand" ""))]
1931 ""
1932 "ix86_expand_move (QImode, operands); DONE;")
1933
1934 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1935 ;; "push a byte". But actually we use pushw, which has the effect
1936 ;; of rounding the amount pushed up to a halfword.
1937
1938 (define_insn "*pushqi2"
1939 [(set (match_operand:QI 0 "push_operand" "=X,X")
1940 (match_operand:QI 1 "nonmemory_no_elim_operand" "n,r"))]
1941 "!TARGET_64BIT"
1942 "@
1943 push{w}\\t{|word ptr }%1
1944 push{w}\\t%w1"
1945 [(set_attr "type" "push")
1946 (set_attr "mode" "HI")])
1947
1948 ;; Situation is quite tricky about when to choose full sized (SImode) move
1949 ;; over QImode moves. For Q_REG -> Q_REG move we use full size only for
1950 ;; partial register dependency machines (such as AMD Athlon), where QImode
1951 ;; moves issue extra dependency and for partial register stalls machines
1952 ;; that don't use QImode patterns (and QImode move cause stall on the next
1953 ;; instruction).
1954 ;;
1955 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
1956 ;; register stall machines with, where we use QImode instructions, since
1957 ;; partial register stall can be caused there. Then we use movzx.
1958 (define_insn "*movqi_1"
1959 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
1960 (match_operand:QI 1 "general_operand" " q,qn,qm,q,rn,qm,qn"))]
1961 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1962 "*
1963 {
1964 switch (get_attr_type (insn))
1965 {
1966 case TYPE_IMOVX:
1967 if (!ANY_QI_REG_P (operands[1]) && GET_CODE (operands[1]) != MEM)
1968 abort ();
1969 return \"movz{bl|x}\\t{%1, %k0|%k0, %1}\";
1970 default:
1971 if (get_attr_mode (insn) == MODE_SI)
1972 return \"mov{l}\\t{%k1, %k0|%k0, %k1}\";
1973 else
1974 return \"mov{b}\\t{%1, %0|%0, %1}\";
1975 }
1976 }"
1977 [(set (attr "type")
1978 (cond [(and (eq_attr "alternative" "3")
1979 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1980 (const_int 0))
1981 (eq (symbol_ref "TARGET_QIMODE_MATH")
1982 (const_int 0))))
1983 (const_string "imov")
1984 (eq_attr "alternative" "3,5")
1985 (const_string "imovx")
1986 (and (ne (symbol_ref "TARGET_MOVX")
1987 (const_int 0))
1988 (eq_attr "alternative" "2"))
1989 (const_string "imovx")
1990 ]
1991 (const_string "imov")))
1992 (set (attr "mode")
1993 (cond [(eq_attr "alternative" "3,4,5")
1994 (const_string "SI")
1995 (eq_attr "alternative" "6")
1996 (const_string "QI")
1997 (eq_attr "type" "imovx")
1998 (const_string "SI")
1999 (and (eq_attr "type" "imov")
2000 (and (eq_attr "alternative" "0,1,2")
2001 (ne (symbol_ref "TARGET_PARTIAL_REG_DEPENDENCY")
2002 (const_int 0))))
2003 (const_string "SI")
2004 ;; Avoid partial register stalls when not using QImode arithmetic
2005 (and (eq_attr "type" "imov")
2006 (and (eq_attr "alternative" "0,1,2")
2007 (and (ne (symbol_ref "TARGET_PARTIAL_REG_STALL")
2008 (const_int 0))
2009 (eq (symbol_ref "TARGET_QIMODE_MATH")
2010 (const_int 0)))))
2011 (const_string "SI")
2012 ]
2013 (const_string "QI")))])
2014
2015 (define_expand "reload_outqi"
2016 [(parallel [(match_operand:QI 0 "" "=m")
2017 (match_operand:QI 1 "register_operand" "r")
2018 (match_operand:QI 2 "register_operand" "=&q")])]
2019 ""
2020 "
2021 {
2022 rtx op0, op1, op2;
2023 op0 = operands[0]; op1 = operands[1]; op2 = operands[2];
2024
2025 if (reg_overlap_mentioned_p (op2, op0))
2026 abort ();
2027 if (! q_regs_operand (op1, QImode))
2028 {
2029 emit_insn (gen_movqi (op2, op1));
2030 op1 = op2;
2031 }
2032 emit_insn (gen_movqi (op0, op1));
2033 DONE;
2034 }")
2035
2036 (define_insn "*swapqi"
2037 [(set (match_operand:QI 0 "register_operand" "+r")
2038 (match_operand:QI 1 "register_operand" "+r"))
2039 (set (match_dup 1)
2040 (match_dup 0))]
2041 ""
2042 "xchg{b}\\t%1, %0"
2043 [(set_attr "type" "imov")
2044 (set_attr "pent_pair" "np")
2045 (set_attr "mode" "QI")
2046 (set_attr "modrm" "0")
2047 (set_attr "ppro_uops" "few")])
2048
2049 (define_expand "movstrictqi"
2050 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
2051 (match_operand:QI 1 "general_operand" ""))]
2052 "! TARGET_PARTIAL_REG_STALL"
2053 "
2054 {
2055 /* Don't generate memory->memory moves, go through a register */
2056 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
2057 operands[1] = force_reg (QImode, operands[1]);
2058 }")
2059
2060 (define_insn "*movstrictqi_1"
2061 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
2062 (match_operand:QI 1 "general_operand" "*qn,m"))]
2063 "! TARGET_PARTIAL_REG_STALL
2064 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2065 "mov{b}\\t{%1, %0|%0, %1}"
2066 [(set_attr "type" "imov")
2067 (set_attr "mode" "QI")])
2068
2069 (define_insn "*movstrictqi_xor"
2070 [(set (strict_low_part (match_operand:QI 0 "q_regs_operand" "+q"))
2071 (match_operand:QI 1 "const0_operand" "i"))
2072 (clobber (reg:CC 17))]
2073 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
2074 "xor{b}\\t{%0, %0|%0, %0}"
2075 [(set_attr "type" "alu1")
2076 (set_attr "mode" "QI")
2077 (set_attr "length_immediate" "0")])
2078
2079 (define_insn "*movsi_extv_1"
2080 [(set (match_operand:SI 0 "register_operand" "=R")
2081 (sign_extract:SI (match_operand:SI 1 "ext_register_operand" "Q")
2082 (const_int 8)
2083 (const_int 8)))]
2084 ""
2085 "movs{bl|x}\\t{%h1, %0|%0, %h1}"
2086 [(set_attr "type" "imovx")
2087 (set_attr "mode" "SI")])
2088
2089 (define_insn "*movhi_extv_1"
2090 [(set (match_operand:HI 0 "register_operand" "=R")
2091 (sign_extract:HI (match_operand:SI 1 "ext_register_operand" "Q")
2092 (const_int 8)
2093 (const_int 8)))]
2094 ""
2095 "movs{bl|x}\\t{%h1, %k0|%k0, %h1}"
2096 [(set_attr "type" "imovx")
2097 (set_attr "mode" "SI")])
2098
2099 (define_insn "*movqi_extv_1"
2100 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
2101 (sign_extract:QI (match_operand:SI 1 "ext_register_operand" "Q,Q")
2102 (const_int 8)
2103 (const_int 8)))]
2104 "!TARGET_64BIT"
2105 "*
2106 {
2107 switch (get_attr_type (insn))
2108 {
2109 case TYPE_IMOVX:
2110 return \"movs{bl|x}\\t{%h1, %k0|%k0, %h1}\";
2111 default:
2112 return \"mov{b}\\t{%h1, %0|%0, %h1}\";
2113 }
2114 }"
2115 [(set (attr "type")
2116 (if_then_else (and (match_operand:QI 0 "register_operand" "")
2117 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
2118 (ne (symbol_ref "TARGET_MOVX")
2119 (const_int 0))))
2120 (const_string "imovx")
2121 (const_string "imov")))
2122 (set (attr "mode")
2123 (if_then_else (eq_attr "type" "imovx")
2124 (const_string "SI")
2125 (const_string "QI")))])
2126
2127 (define_insn "*movqi_extv_1_rex64"
2128 [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2129 (sign_extract:QI (match_operand:SI 1 "ext_register_operand" "Q,Q")
2130 (const_int 8)
2131 (const_int 8)))]
2132 "TARGET_64BIT"
2133 "*
2134 {
2135 switch (get_attr_type (insn))
2136 {
2137 case TYPE_IMOVX:
2138 return \"movs{bl|x}\\t{%h1, %k0|%k0, %h1}\";
2139 default:
2140 return \"mov{b}\\t{%h1, %0|%0, %h1}\";
2141 }
2142 }"
2143 [(set (attr "type")
2144 (if_then_else (and (match_operand:QI 0 "register_operand" "")
2145 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
2146 (ne (symbol_ref "TARGET_MOVX")
2147 (const_int 0))))
2148 (const_string "imovx")
2149 (const_string "imov")))
2150 (set (attr "mode")
2151 (if_then_else (eq_attr "type" "imovx")
2152 (const_string "SI")
2153 (const_string "QI")))])
2154
2155 ;; Stores and loads of ax to arbitary constant address.
2156 ;; We fake an second form of instruction to force reload to load address
2157 ;; into register when rax is not available
2158 (define_insn "*movabsqi_1_rex64"
2159 [(set (mem:QI (match_operand:DI 0 "x86_64_movabs_operand" "i,r,r"))
2160 (match_operand:QI 1 "nonmemory_operand" "a,er,i"))]
2161 "TARGET_64BIT"
2162 "@
2163 movabs{q}\\t{%1, %P0|%P0, %1}
2164 mov{q}\\t{%1, %a0|%a0, %1}
2165 movabs{q}\\t{%1, %a0|%a0, %1}"
2166 [(set_attr "type" "imov")
2167 (set_attr "modrm" "0,*,*")
2168 (set_attr "length_address" "8,0,0")
2169 (set_attr "length_immediate" "0,*,*")
2170 (set_attr "memory" "store")
2171 (set_attr "mode" "QI")])
2172
2173 (define_insn "*movabsqi_2_rex64"
2174 [(set (match_operand:QI 0 "register_operand" "=a,r")
2175 (mem:QI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2176 "TARGET_64BIT"
2177 "@
2178 movabs{q}\\t{%P1, %0|%0, %P1}
2179 mov{q}\\t{%a1, %0|%0, %a1}"
2180 [(set_attr "type" "imov")
2181 (set_attr "modrm" "0,*")
2182 (set_attr "length_address" "8,0")
2183 (set_attr "length_immediate" "0")
2184 (set_attr "memory" "load")
2185 (set_attr "mode" "QI")])
2186
2187 (define_insn "*movsi_extzv_1"
2188 [(set (match_operand:SI 0 "register_operand" "=R")
2189 (zero_extract:SI (match_operand 1 "ext_register_operand" "Q")
2190 (const_int 8)
2191 (const_int 8)))]
2192 ""
2193 "movz{bl|x}\\t{%h1, %0|%0, %h1}"
2194 [(set_attr "type" "imovx")
2195 (set_attr "mode" "SI")])
2196
2197 (define_insn "*movqi_extzv_2"
2198 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
2199 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2200 (const_int 8)
2201 (const_int 8)) 0))]
2202 "!TARGET_64BIT"
2203 "*
2204 {
2205 switch (get_attr_type (insn))
2206 {
2207 case TYPE_IMOVX:
2208 return \"movz{bl|x}\\t{%h1, %k0|%k0, %h1}\";
2209 default:
2210 return \"mov{b}\\t{%h1, %0|%0, %h1}\";
2211 }
2212 }"
2213 [(set (attr "type")
2214 (if_then_else (and (match_operand:QI 0 "register_operand" "")
2215 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
2216 (ne (symbol_ref "TARGET_MOVX")
2217 (const_int 0))))
2218 (const_string "imovx")
2219 (const_string "imov")))
2220 (set (attr "mode")
2221 (if_then_else (eq_attr "type" "imovx")
2222 (const_string "SI")
2223 (const_string "QI")))])
2224
2225 (define_insn "*movqi_extzv_2_rex64"
2226 [(set (match_operand:QI 0 "register_operand" "=Q,?R")
2227 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
2228 (const_int 8)
2229 (const_int 8)) 0))]
2230 "TARGET_64BIT"
2231 "*
2232 {
2233 switch (get_attr_type (insn))
2234 {
2235 case TYPE_IMOVX:
2236 return \"movz{bl|x}\\t{%h1, %k0|%k0, %h1}\";
2237 default:
2238 return \"mov{b}\\t{%h1, %0|%0, %h1}\";
2239 }
2240 }"
2241 [(set (attr "type")
2242 (if_then_else (ior (not (match_operand:QI 0 "q_regs_operand" ""))
2243 (ne (symbol_ref "TARGET_MOVX")
2244 (const_int 0)))
2245 (const_string "imovx")
2246 (const_string "imov")))
2247 (set (attr "mode")
2248 (if_then_else (eq_attr "type" "imovx")
2249 (const_string "SI")
2250 (const_string "QI")))])
2251
2252 (define_insn "*movsi_insv_1"
2253 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2254 (const_int 8)
2255 (const_int 8))
2256 (match_operand:SI 1 "nonimmediate_operand" "Qm"))]
2257 "!TARGET_64BIT"
2258 "mov{b}\\t{%b1, %h0|%h0, %b1}"
2259 [(set_attr "type" "imov")
2260 (set_attr "mode" "QI")])
2261
2262 (define_insn "*movsi_insv_1_rex64"
2263 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2264 (const_int 8)
2265 (const_int 8))
2266 (match_operand:SI 1 "ext_register_operand" "Q"))]
2267 "TARGET_64BIT"
2268 "mov{b}\\t{%b1, %h0|%h0, %b1}"
2269 [(set_attr "type" "imov")
2270 (set_attr "mode" "QI")])
2271
2272 (define_insn "*movqi_insv_2"
2273 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
2274 (const_int 8)
2275 (const_int 8))
2276 (and:SI (lshiftrt:SI (match_operand:SI 1 "ext_register_operand" "Q")
2277 (const_int 8))
2278 (const_int 255)))]
2279 ""
2280 "mov{b}\\t{%h1, %h0|%h0, %h1}"
2281 [(set_attr "type" "imov")
2282 (set_attr "mode" "QI")])
2283
2284 (define_expand "movdi"
2285 [(set (match_operand:DI 0 "nonimmediate_operand" "")
2286 (match_operand:DI 1 "general_operand" ""))]
2287 ""
2288 "ix86_expand_move (DImode, operands); DONE;")
2289
2290 (define_insn "*pushdi"
2291 [(set (match_operand:DI 0 "push_operand" "=<")
2292 (match_operand:DI 1 "general_no_elim_operand" "riF*m"))]
2293 "!TARGET_64BIT"
2294 "#")
2295
2296 (define_insn "pushdi2_rex64"
2297 [(set (match_operand:DI 0 "push_operand" "=<,!<")
2298 (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
2299 "TARGET_64BIT"
2300 "@
2301 push{q}\\t%1
2302 #"
2303 [(set_attr "type" "push,multi")
2304 (set_attr "mode" "DI")])
2305
2306 ;; Convert impossible pushes of immediate to existing instructions.
2307 ;; First try to get scratch register and go trought it. In case this
2308 ;; fails, push sign extended lower part first and then overwrite
2309 ;; upper part by 32bit move.
2310 (define_peephole2
2311 [(match_scratch:DI 2 "r")
2312 (set (match_operand:DI 0 "push_operand" "")
2313 (match_operand:DI 1 "immediate_operand" ""))]
2314 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2315 && !x86_64_immediate_operand (operands[1], DImode)"
2316 [(set (match_dup 2) (match_dup 1))
2317 (set (match_dup 0) (match_dup 2))]
2318 "")
2319
2320 ;; We need to define this as both peepholer and splitter for case
2321 ;; peephole2 pass is not run.
2322 (define_peephole2
2323 [(set (match_operand:DI 0 "push_operand" "")
2324 (match_operand:DI 1 "immediate_operand" ""))]
2325 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2326 && !x86_64_immediate_operand (operands[1], DImode) && 1"
2327 [(set (match_dup 0) (match_dup 1))
2328 (set (match_dup 2) (match_dup 3))]
2329 "split_di (operands + 1, 1, operands + 2, operands + 3);
2330 operands[1] = gen_lowpart (DImode, operands[2]);
2331 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
2332 GEN_INT (4)));
2333 ")
2334
2335 (define_split
2336 [(set (match_operand:DI 0 "push_operand" "")
2337 (match_operand:DI 1 "immediate_operand" ""))]
2338 "TARGET_64BIT && (flow2_completed || (reload_completed && !flag_peephole2))
2339 && !symbolic_operand (operands[1], DImode)
2340 && !x86_64_immediate_operand (operands[1], DImode)"
2341 [(set (match_dup 0) (match_dup 1))
2342 (set (match_dup 2) (match_dup 3))]
2343 "split_di (operands + 1, 1, operands + 2, operands + 3);
2344 operands[1] = gen_lowpart (DImode, operands[2]);
2345 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
2346 GEN_INT (4)));
2347 ")
2348
2349 (define_insn "*pushdi2_prologue_rex64"
2350 [(set (match_operand:DI 0 "push_operand" "=<")
2351 (match_operand:DI 1 "general_no_elim_operand" "re*m"))
2352 (set (reg:DI 6) (reg:DI 6))]
2353 "TARGET_64BIT"
2354 "push{q}\\t%1"
2355 [(set_attr "type" "push")
2356 (set_attr "mode" "DI")])
2357
2358 (define_insn "*popdi1_epilogue_rex64"
2359 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
2360 (mem:DI (reg:DI 7)))
2361 (set (reg:DI 7)
2362 (plus:DI (reg:DI 7) (const_int 8)))
2363 (set (reg:DI 6) (reg:DI 6))]
2364 "TARGET_64BIT"
2365 "pop{q}\\t%0"
2366 [(set_attr "type" "pop")
2367 (set_attr "mode" "DI")])
2368
2369 (define_insn "popdi1"
2370 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
2371 (mem:DI (reg:DI 7)))
2372 (set (reg:DI 7)
2373 (plus:DI (reg:DI 7) (const_int 8)))]
2374 "TARGET_64BIT"
2375 "pop{q}\\t%0"
2376 [(set_attr "type" "pop")
2377 (set_attr "mode" "DI")])
2378
2379 (define_insn "*movdi_xor_rex64"
2380 [(set (match_operand:DI 0 "register_operand" "=r")
2381 (match_operand:DI 1 "const0_operand" "i"))
2382 (clobber (reg:CC 17))]
2383 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)
2384 && TARGET_64BIT"
2385 "xor{l}\\t{%k0, %k0|%k0, %k0}"
2386 [(set_attr "type" "alu1")
2387 (set_attr "mode" "SI")
2388 (set_attr "length_immediate" "0")])
2389
2390 (define_insn "*movdi_or_rex64"
2391 [(set (match_operand:DI 0 "register_operand" "=r")
2392 (match_operand:DI 1 "const_int_operand" "i"))
2393 (clobber (reg:CC 17))]
2394 "reload_completed && GET_CODE (operands[1]) == CONST_INT
2395 && TARGET_64BIT
2396 && INTVAL (operands[1]) == -1
2397 && (TARGET_PENTIUM || optimize_size)"
2398 "*
2399 {
2400 operands[1] = constm1_rtx;
2401 return \"or{q}\\t{%1, %0|%0, %1}\";
2402 }"
2403 [(set_attr "type" "alu1")
2404 (set_attr "mode" "DI")
2405 (set_attr "length_immediate" "1")])
2406
2407 (define_insn "*movdi_2"
2408 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,!m*y,!*y")
2409 (match_operand:DI 1 "general_operand" "riFo,riF,*y,m"))]
2410 "!TARGET_64BIT
2411 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2412 "@
2413 #
2414 #
2415 movq\\t{%1, %0|%0, %1}
2416 movq\\t{%1, %0|%0, %1}"
2417 [(set_attr "type" "*,*,mmx,mmx")])
2418
2419 (define_split
2420 [(set (match_operand:DI 0 "push_operand" "")
2421 (match_operand:DI 1 "general_operand" ""))]
2422 "!TARGET_64BIT && reload_completed && ! MMX_REG_P (operands[1])"
2423 [(const_int 0)]
2424 "if (!ix86_split_long_move (operands)) abort (); DONE;")
2425
2426 ;; %%% This multiword shite has got to go.
2427 (define_split
2428 [(set (match_operand:DI 0 "nonimmediate_operand" "")
2429 (match_operand:DI 1 "general_operand" ""))]
2430 "!TARGET_64BIT && reload_completed && ! MMX_REG_P (operands[0])
2431 && ! MMX_REG_P (operands[1])"
2432 [(set (match_dup 2) (match_dup 5))
2433 (set (match_dup 3) (match_dup 6))]
2434 "if (ix86_split_long_move (operands)) DONE;")
2435
2436 (define_insn "*movdi_1_rex64"
2437 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,r,mr,!mr,!m*y,!*y,*m,*Y")
2438 (match_operand:DI 1 "general_operand" "Z,rem,i,re,n,*y,m,*Y,*m"))]
2439 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2440 && TARGET_64BIT"
2441 "*
2442 {
2443 switch (get_attr_type (insn))
2444 {
2445 case TYPE_SSE:
2446 case TYPE_MMX:
2447 return \"movd\\t{%1, %0|%0, %1}\";
2448 case TYPE_MULTI:
2449 return \"#\";
2450 case TYPE_LEA:
2451 return \"lea{q}\\t{%a1, %0|%0, %a1}\";
2452 default:
2453 if (flag_pic && SYMBOLIC_CONST (operands[1]))
2454 abort ();
2455 if (get_attr_mode (insn) == MODE_SI)
2456 return \"mov{l}\\t{%k1, %k0|%k0, %k1}\";
2457 else if (which_alternative == 2)
2458 return \"movabs{q}\\t{%1, %0|%0, %1}\";
2459 else
2460 return \"mov{q}\\t{%1, %0|%0, %1}\";
2461 }
2462 }"
2463 [(set (attr "type")
2464 (cond [(eq_attr "alternative" "5,6")
2465 (const_string "mmx")
2466 (eq_attr "alternative" "7,8")
2467 (const_string "sse")
2468 (eq_attr "alternative" "4")
2469 (const_string "multi")
2470 (and (ne (symbol_ref "flag_pic") (const_int 0))
2471 (match_operand:DI 1 "symbolic_operand" ""))
2472 (const_string "lea")
2473 ]
2474 (const_string "imov")))
2475 (set_attr "modrm" "*,0,0,*,*,*,*,*,*")
2476 (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*")
2477 (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI")])
2478
2479 ;; Stores and loads of ax to arbitary constant address.
2480 ;; We fake an second form of instruction to force reload to load address
2481 ;; into register when rax is not available
2482 (define_insn "*movabsdi_1_rex64"
2483 [(set (mem:DI (match_operand:DI 0 "x86_64_movabs_operand" "i,r,r"))
2484 (match_operand:DI 1 "nonmemory_operand" "a,er,i"))]
2485 "TARGET_64BIT"
2486 "@
2487 movabs{q}\\t{%1, %P0|%P0, %1}
2488 mov{q}\\t{%1, %a0|%a0, %1}
2489 movabs{q}\\t{%1, %a0|%a0, %1}"
2490 [(set_attr "type" "imov")
2491 (set_attr "modrm" "0,*,*")
2492 (set_attr "length_address" "8,0,0")
2493 (set_attr "length_immediate" "0,*,*")
2494 (set_attr "memory" "store")
2495 (set_attr "mode" "DI")])
2496
2497 (define_insn "*movabsdi_2_rex64"
2498 [(set (match_operand:DI 0 "register_operand" "=a,r")
2499 (mem:DI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2500 "TARGET_64BIT"
2501 "@
2502 movabs{q}\\t{%P1, %0|%0, %P1}
2503 mov{q}\\t{%a1, %0|%0, %a1}"
2504 [(set_attr "type" "imov")
2505 (set_attr "modrm" "0,*")
2506 (set_attr "length_address" "8,0")
2507 (set_attr "length_immediate" "0")
2508 (set_attr "memory" "load")
2509 (set_attr "mode" "DI")])
2510
2511 ;; Convert impossible stores of immediate to existing instructions.
2512 ;; First try to get scratch register and go trought it. In case this
2513 ;; fails, move by 32bit parts.
2514 (define_peephole2
2515 [(match_scratch:DI 2 "r")
2516 (set (match_operand:DI 0 "memory_operand" "")
2517 (match_operand:DI 1 "immediate_operand" ""))]
2518 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2519 && !x86_64_immediate_operand (operands[1], DImode)"
2520 [(set (match_dup 2) (match_dup 1))
2521 (set (match_dup 0) (match_dup 2))]
2522 "")
2523
2524 ;; We need to define this as both peepholer and splitter for case
2525 ;; peephole2 pass is not run.
2526 (define_peephole2
2527 [(set (match_operand:DI 0 "memory_operand" "")
2528 (match_operand:DI 1 "immediate_operand" ""))]
2529 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2530 && !x86_64_immediate_operand (operands[1], DImode) && 1"
2531 [(set (match_dup 2) (match_dup 3))
2532 (set (match_dup 4) (match_dup 5))]
2533 "split_di (operands, 2, operands + 2, operands + 4);")
2534
2535 (define_split
2536 [(set (match_operand:DI 0 "memory_operand" "")
2537 (match_operand:DI 1 "immediate_operand" ""))]
2538 "TARGET_64BIT && (flow2_completed || (reload_completed && !flag_peephole2))
2539 && !symbolic_operand (operands[1], DImode)
2540 && !x86_64_immediate_operand (operands[1], DImode)"
2541 [(set (match_dup 2) (match_dup 3))
2542 (set (match_dup 4) (match_dup 5))]
2543 "split_di (operands, 2, operands + 2, operands + 4);")
2544
2545 (define_insn "*swapdi_rex64"
2546 [(set (match_operand:DI 0 "register_operand" "+r")
2547 (match_operand:DI 1 "register_operand" "+r"))
2548 (set (match_dup 1)
2549 (match_dup 0))]
2550 "TARGET_64BIT"
2551 "xchg{q}\\t%1, %0"
2552 [(set_attr "type" "imov")
2553 (set_attr "pent_pair" "np")
2554 (set_attr "athlon_decode" "vector")
2555 (set_attr "mode" "DI")
2556 (set_attr "modrm" "0")
2557 (set_attr "ppro_uops" "few")])
2558
2559
2560 (define_expand "movsf"
2561 [(set (match_operand:SF 0 "nonimmediate_operand" "")
2562 (match_operand:SF 1 "general_operand" ""))]
2563 ""
2564 "ix86_expand_move (SFmode, operands); DONE;")
2565
2566 (define_insn "*pushsf"
2567 [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2568 (match_operand:SF 1 "general_no_elim_operand" "f#rx,rFm#fx,x#rf"))]
2569 "!TARGET_64BIT"
2570 "*
2571 {
2572 switch (which_alternative)
2573 {
2574 case 0:
2575 /* %%% We loose REG_DEAD notes for controling pops if we split late. */
2576 operands[0] = gen_rtx_MEM (SFmode, stack_pointer_rtx);
2577 operands[2] = stack_pointer_rtx;
2578 operands[3] = GEN_INT (4);
2579 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2580 return \"sub{l}\\t{%3, %2|%2, %3}\;fstp%z0\\t%y0\";
2581 else
2582 return \"sub{l}\\t{%3, %2|%2, %3}\;fst%z0\\t%y0\";
2583
2584 case 1:
2585 return \"push{l}\\t%1\";
2586 case 2:
2587 return \"#\";
2588
2589 default:
2590 abort ();
2591 }
2592 }"
2593 [(set_attr "type" "multi,push,multi")
2594 (set_attr "mode" "SF,SI,SF")])
2595
2596 (define_insn "*pushsf_rex64"
2597 [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2598 (match_operand:SF 1 "nonmemory_no_elim_operand" "f#rx,rF#fx,x#rf"))]
2599 "TARGET_64BIT"
2600 "*
2601 {
2602 switch (which_alternative)
2603 {
2604 case 0:
2605 /* %%% We loose REG_DEAD notes for controling pops if we split late. */
2606 operands[0] = gen_rtx_MEM (SFmode, stack_pointer_rtx);
2607 operands[2] = stack_pointer_rtx;
2608 operands[3] = GEN_INT (8);
2609 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2610 return \"sub{q}\\t{%3, %2|%2, %3}\;fstp%z0\\t%y0\";
2611 else
2612 return \"sub{q}\\t{%3, %2|%2, %3}\;fst%z0\\t%y0\";
2613
2614 case 1:
2615 return \"push{q}\\t%q1\";
2616
2617 case 2:
2618 return \"#\";
2619
2620 default:
2621 abort ();
2622 }
2623 }"
2624 [(set_attr "type" "multi,push,multi")
2625 (set_attr "mode" "SF,DI,SF")])
2626
2627 (define_split
2628 [(set (match_operand:SF 0 "push_operand" "")
2629 (match_operand:SF 1 "memory_operand" ""))]
2630 "reload_completed
2631 && GET_CODE (operands[1]) == MEM
2632 && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
2633 && CONSTANT_POOL_ADDRESS_P (XEXP (operands[1], 0))"
2634 [(set (match_dup 0)
2635 (match_dup 1))]
2636 "operands[1] = get_pool_constant (XEXP (operands[1], 0));")
2637
2638
2639 ;; %%% Kill this when call knows how to work this out.
2640 (define_split
2641 [(set (match_operand:SF 0 "push_operand" "")
2642 (match_operand:SF 1 "register_operand" ""))]
2643 "!TARGET_64BIT && ANY_FP_REGNO_P (REGNO (operands[1]))"
2644 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -4)))
2645 (set (mem:SF (reg:SI 7)) (match_dup 1))])
2646
2647 (define_split
2648 [(set (match_operand:SF 0 "push_operand" "")
2649 (match_operand:SF 1 "register_operand" ""))]
2650 "TARGET_64BIT && ANY_FP_REGNO_P (REGNO (operands[1]))"
2651 [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -8)))
2652 (set (mem:SF (reg:DI 7)) (match_dup 1))])
2653
2654 (define_insn "*movsf_1"
2655 [(set (match_operand:SF 0 "nonimmediate_operand" "=f#xr,m,f#xr,r#xf,m,x#rf,x#rf,x#rf,m")
2656 (match_operand:SF 1 "general_operand" "fm#rx,f#rx,G,rmF#fx,Fr#fx,H,x,xm#rf,x#rf"))]
2657 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2658 && (reload_in_progress || reload_completed
2659 || GET_CODE (operands[1]) != CONST_DOUBLE
2660 || memory_operand (operands[0], SFmode))"
2661 "*
2662 {
2663 switch (which_alternative)
2664 {
2665 case 0:
2666 if (REG_P (operands[1])
2667 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2668 return \"fstp\\t%y0\";
2669 else if (STACK_TOP_P (operands[0]))
2670 return \"fld%z1\\t%y1\";
2671 else
2672 return \"fst\\t%y0\";
2673
2674 case 1:
2675 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2676 return \"fstp%z0\\t%y0\";
2677 else
2678 return \"fst%z0\\t%y0\";
2679
2680 case 2:
2681 switch (standard_80387_constant_p (operands[1]))
2682 {
2683 case 1:
2684 return \"fldz\";
2685 case 2:
2686 return \"fld1\";
2687 }
2688 abort();
2689
2690 case 3:
2691 case 4:
2692 return \"mov{l}\\t{%1, %0|%0, %1}\";
2693 case 5:
2694 return \"pxor\\t%0, %0\";
2695 case 6:
2696 if (TARGET_PARTIAL_REG_DEPENDENCY)
2697 return \"movaps\\t{%1, %0|%0, %1}\";
2698 else
2699 return \"movss\\t{%1, %0|%0, %1}\";
2700 case 7:
2701 case 8:
2702 return \"movss\\t{%1, %0|%0, %1}\";
2703
2704 default:
2705 abort();
2706 }
2707 }"
2708 [(set_attr "type" "fmov,fmov,fmov,imov,imov,sse,sse,sse,sse")
2709 (set_attr "mode" "SF,SF,SF,SI,SI,TI,SF,SF,SF")])
2710
2711 (define_insn "*swapsf"
2712 [(set (match_operand:SF 0 "register_operand" "+f")
2713 (match_operand:SF 1 "register_operand" "+f"))
2714 (set (match_dup 1)
2715 (match_dup 0))]
2716 "reload_completed || !TARGET_SSE2"
2717 "*
2718 {
2719 if (STACK_TOP_P (operands[0]))
2720 return \"fxch\\t%1\";
2721 else
2722 return \"fxch\\t%0\";
2723 }"
2724 [(set_attr "type" "fxch")
2725 (set_attr "mode" "SF")])
2726
2727 (define_expand "movdf"
2728 [(set (match_operand:DF 0 "nonimmediate_operand" "")
2729 (match_operand:DF 1 "general_operand" ""))]
2730 ""
2731 "ix86_expand_move (DFmode, operands); DONE;")
2732
2733 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2734 ;; Size of pushdf using integer insturctions is 2+2*memory operand size
2735 ;; On the average, pushdf using integers can be still shorter. Allow this
2736 ;; pattern for optimize_size too.
2737
2738 (define_insn "*pushdf_nointeger"
2739 [(set (match_operand:DF 0 "push_operand" "=<,<,<,<")
2740 (match_operand:DF 1 "general_no_elim_operand" "f#Y,Fo#fY,*r#fY,Y#f"))]
2741 "!TARGET_64BIT && !TARGET_INTEGER_DFMODE_MOVES"
2742 "*
2743 {
2744 switch (which_alternative)
2745 {
2746 case 0:
2747 /* %%% We loose REG_DEAD notes for controling pops if we split late. */
2748 operands[0] = gen_rtx_MEM (DFmode, stack_pointer_rtx);
2749 operands[2] = stack_pointer_rtx;
2750 operands[3] = GEN_INT (8);
2751 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2752 return \"sub{l}\\t{%3, %2|%2, %3}\;fstp%z0\\t%y0\";
2753 else
2754 return \"sub{l}\\t{%3, %2|%2, %3}\;fst%z0\\t%y0\";
2755
2756 case 1:
2757 case 2:
2758 case 3:
2759 return \"#\";
2760
2761 default:
2762 abort ();
2763 }
2764 }"
2765 [(set_attr "type" "multi")
2766 (set_attr "mode" "DF,SI,SI,DF")])
2767
2768 (define_insn "*pushdf_integer"
2769 [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2770 (match_operand:DF 1 "general_no_elim_operand" "f#rY,rFo#fY,Y#rf"))]
2771 "TARGET_64BIT || TARGET_INTEGER_DFMODE_MOVES"
2772 "*
2773 {
2774 switch (which_alternative)
2775 {
2776 case 0:
2777 /* %%% We loose REG_DEAD notes for controling pops if we split late. */
2778 operands[0] = gen_rtx_MEM (DFmode, stack_pointer_rtx);
2779 operands[2] = stack_pointer_rtx;
2780 operands[3] = GEN_INT (8);
2781 if (TARGET_64BIT)
2782 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2783 return \"sub{q}\\t{%3, %2|%2, %3}\;fstp%z0\\t%y0\";
2784 else
2785 return \"sub{q}\\t{%3, %2|%2, %3}\;fst%z0\\t%y0\";
2786 else
2787 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2788 return \"sub{l}\\t{%3, %2|%2, %3}\;fstp%z0\\t%y0\";
2789 else
2790 return \"sub{l}\\t{%3, %2|%2, %3}\;fst%z0\\t%y0\";
2791
2792
2793 case 1:
2794 case 2:
2795 return \"#\";
2796
2797 default:
2798 abort ();
2799 }
2800 }"
2801 [(set_attr "type" "multi")
2802 (set_attr "mode" "DF,SI,DF")])
2803
2804 ;; %%% Kill this when call knows how to work this out.
2805 (define_split
2806 [(set (match_operand:DF 0 "push_operand" "")
2807 (match_operand:DF 1 "register_operand" ""))]
2808 "!TARGET_64BIT && reload_completed && ANY_FP_REGNO_P (REGNO (operands[1]))"
2809 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
2810 (set (mem:DF (reg:SI 7)) (match_dup 1))]
2811 "")
2812
2813 (define_split
2814 [(set (match_operand:DF 0 "push_operand" "")
2815 (match_operand:DF 1 "register_operand" ""))]
2816 "TARGET_64BIT && reload_completed && ANY_FP_REGNO_P (REGNO (operands[1]))"
2817 [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -8)))
2818 (set (mem:DF (reg:DI 7)) (match_dup 1))]
2819 "")
2820
2821 (define_split
2822 [(set (match_operand:DF 0 "push_operand" "")
2823 (match_operand:DF 1 "general_operand" ""))]
2824 "reload_completed"
2825 [(const_int 0)]
2826 "if (!ix86_split_long_move (operands)) abort (); DONE;")
2827
2828 ;; Moving is usually shorter when only FP registers are used. This separate
2829 ;; movdf pattern avoids the use of integer registers for FP operations
2830 ;; when optimizing for size.
2831
2832 (define_insn "*movdf_nointeger"
2833 [(set (match_operand:DF 0 "nonimmediate_operand" "=f#Y,m,f#Y,*r,o,Y#f,Y#f,Y#f,m")
2834 (match_operand:DF 1 "general_operand" "fm#Y,f#Y,G,*roF,F*r,H,Y#f,YHm#f,Y#f"))]
2835 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2836 && (optimize_size || !TARGET_INTEGER_DFMODE_MOVES)
2837 && (reload_in_progress || reload_completed
2838 || GET_CODE (operands[1]) != CONST_DOUBLE
2839 || memory_operand (operands[0], DFmode))"
2840 "*
2841 {
2842 switch (which_alternative)
2843 {
2844 case 0:
2845 if (REG_P (operands[1])
2846 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2847 return \"fstp\\t%y0\";
2848 else if (STACK_TOP_P (operands[0]))
2849 return \"fld%z1\\t%y1\";
2850 else
2851 return \"fst\\t%y0\";
2852
2853 case 1:
2854 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2855 return \"fstp%z0\\t%y0\";
2856 else
2857 return \"fst%z0\\t%y0\";
2858
2859 case 2:
2860 switch (standard_80387_constant_p (operands[1]))
2861 {
2862 case 1:
2863 return \"fldz\";
2864 case 2:
2865 return \"fld1\";
2866 }
2867 abort();
2868
2869 case 3:
2870 case 4:
2871 return \"#\";
2872 case 5:
2873 return \"pxor\\t%0, %0\";
2874 case 6:
2875 if (TARGET_PARTIAL_REG_DEPENDENCY)
2876 return \"movapd\\t{%1, %0|%0, %1}\";
2877 else
2878 return \"movsd\\t{%1, %0|%0, %1}\";
2879 case 7:
2880 case 8:
2881 return \"movsd\\t{%1, %0|%0, %1}\";
2882
2883 default:
2884 abort();
2885 }
2886 }"
2887 [(set_attr "type" "fmov,fmov,fmov,multi,multi,sse,sse,sse,sse")
2888 (set_attr "mode" "DF,DF,DF,SI,SI,TI,DF,DF,DF")])
2889
2890 (define_insn "*movdf_integer"
2891 [(set (match_operand:DF 0 "nonimmediate_operand" "=f#Yr,m,f#Yr,r#Yf,o,Y#rf,Y#rf,Y#rf,m")
2892 (match_operand:DF 1 "general_operand" "fm#Yr,f#Yr,G,roF#Yf,Fr#Yf,H,Y#rf,Ym#rf,Y#rf"))]
2893 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2894 && !optimize_size && TARGET_INTEGER_DFMODE_MOVES
2895 && (reload_in_progress || reload_completed
2896 || GET_CODE (operands[1]) != CONST_DOUBLE
2897 || memory_operand (operands[0], DFmode))"
2898 "*
2899 {
2900 switch (which_alternative)
2901 {
2902 case 0:
2903 if (REG_P (operands[1])
2904 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2905 return \"fstp\\t%y0\";
2906 else if (STACK_TOP_P (operands[0]))
2907 return \"fld%z1\\t%y1\";
2908 else
2909 return \"fst\\t%y0\";
2910
2911 case 1:
2912 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2913 return \"fstp%z0\\t%y0\";
2914 else
2915 return \"fst%z0\\t%y0\";
2916
2917 case 2:
2918 switch (standard_80387_constant_p (operands[1]))
2919 {
2920 case 1:
2921 return \"fldz\";
2922 case 2:
2923 return \"fld1\";
2924 }
2925 abort();
2926
2927 case 3:
2928 case 4:
2929 return \"#\";
2930
2931 case 5:
2932 return \"pxor\\t%0, %0\";
2933 case 6:
2934 if (TARGET_PARTIAL_REG_DEPENDENCY)
2935 return \"movapd\\t{%1, %0|%0, %1}\";
2936 else
2937 return \"movsd\\t{%1, %0|%0, %1}\";
2938 case 7:
2939 case 8:
2940 return \"movsd\\t{%1, %0|%0, %1}\";
2941
2942 default:
2943 abort();
2944 }
2945 }"
2946 [(set_attr "type" "fmov,fmov,fmov,multi,multi,sse,sse,sse,sse")
2947 (set_attr "mode" "DF,DF,DF,SI,SI,TI,DF,DF,DF")])
2948
2949 (define_split
2950 [(set (match_operand:DF 0 "nonimmediate_operand" "")
2951 (match_operand:DF 1 "general_operand" ""))]
2952 "reload_completed
2953 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2954 && ! (ANY_FP_REG_P (operands[0]) ||
2955 (GET_CODE (operands[0]) == SUBREG
2956 && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2957 && ! (ANY_FP_REG_P (operands[1]) ||
2958 (GET_CODE (operands[1]) == SUBREG
2959 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2960 [(set (match_dup 2) (match_dup 5))
2961 (set (match_dup 3) (match_dup 6))]
2962 "if (ix86_split_long_move (operands)) DONE;")
2963
2964 (define_insn "*swapdf"
2965 [(set (match_operand:DF 0 "register_operand" "+f")
2966 (match_operand:DF 1 "register_operand" "+f"))
2967 (set (match_dup 1)
2968 (match_dup 0))]
2969 "reload_completed || !TARGET_SSE2"
2970 "*
2971 {
2972 if (STACK_TOP_P (operands[0]))
2973 return \"fxch\\t%1\";
2974 else
2975 return \"fxch\\t%0\";
2976 }"
2977 [(set_attr "type" "fxch")
2978 (set_attr "mode" "DF")])
2979
2980 (define_expand "movxf"
2981 [(set (match_operand:XF 0 "nonimmediate_operand" "")
2982 (match_operand:XF 1 "general_operand" ""))]
2983 "!TARGET_64BIT"
2984 "ix86_expand_move (XFmode, operands); DONE;")
2985
2986 (define_expand "movtf"
2987 [(set (match_operand:TF 0 "nonimmediate_operand" "")
2988 (match_operand:TF 1 "general_operand" ""))]
2989 ""
2990 "ix86_expand_move (TFmode, operands); DONE;")
2991
2992 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2993 ;; Size of pushdf using integer insturctions is 3+3*memory operand size
2994 ;; Pushing using integer instructions is longer except for constants
2995 ;; and direct memory references.
2996 ;; (assuming that any given constant is pushed only once, but this ought to be
2997 ;; handled elsewhere).
2998
2999 (define_insn "*pushxf_nointeger"
3000 [(set (match_operand:XF 0 "push_operand" "=X,X,X")
3001 (match_operand:XF 1 "general_no_elim_operand" "f,Fo,*r"))]
3002 "optimize_size && !TARGET_64BIT"
3003 "*
3004 {
3005 switch (which_alternative)
3006 {
3007 case 0:
3008 /* %%% We loose REG_DEAD notes for controling pops if we split late. */
3009 operands[0] = gen_rtx_MEM (XFmode, stack_pointer_rtx);
3010 operands[2] = stack_pointer_rtx;
3011 operands[3] = GEN_INT (12);
3012 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3013 return \"sub{l}\\t{%3, %2|%2, %3}\;fstp%z0\\t%y0\";
3014 else
3015 return \"sub{l}\\t{%3, %2|%2, %3}\;fst%z0\\t%y0\";
3016
3017 case 1:
3018 case 2:
3019 return \"#\";
3020
3021 default:
3022 abort ();
3023 }
3024 }"
3025 [(set_attr "type" "multi")
3026 (set_attr "mode" "XF,SI,SI")])
3027
3028 (define_insn "*pushtf_nointeger"
3029 [(set (match_operand:TF 0 "push_operand" "=<,<,<")
3030 (match_operand:TF 1 "general_no_elim_operand" "f,Fo,*r"))]
3031 "optimize_size"
3032 "*
3033 {
3034 switch (which_alternative)
3035 {
3036 case 0:
3037 /* %%% We loose REG_DEAD notes for controling pops if we split late. */
3038 operands[0] = gen_rtx_MEM (XFmode, stack_pointer_rtx);
3039 operands[2] = stack_pointer_rtx;
3040 operands[3] = GEN_INT (16);
3041 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3042 return \"sub{l}\\t{%3, %2|%2, %3}\;fstp%z0\\t%y0\";
3043 else
3044 return \"sub{l}\\t{%3, %2|%2, %3}\;fst%z0\\t%y0\";
3045
3046 case 1:
3047 case 2:
3048 return \"#\";
3049
3050 default:
3051 abort ();
3052 }
3053 }"
3054 [(set_attr "type" "multi")
3055 (set_attr "mode" "XF,SI,SI")])
3056
3057 (define_insn "*pushxf_integer"
3058 [(set (match_operand:XF 0 "push_operand" "=<,<")
3059 (match_operand:XF 1 "general_no_elim_operand" "f#r,ro#f"))]
3060 "!optimize_size && !TARGET_64BIT"
3061 "*
3062 {
3063 switch (which_alternative)
3064 {
3065 case 0:
3066 /* %%% We loose REG_DEAD notes for controling pops if we split late. */
3067 operands[0] = gen_rtx_MEM (XFmode, stack_pointer_rtx);
3068 operands[2] = stack_pointer_rtx;
3069 operands[3] = GEN_INT (12);
3070 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3071 return \"sub{l}\\t{%3, %2|%2, %3}\;fstp%z0\\t%y0\";
3072 else
3073 return \"sub{l}\\t{%3, %2|%2, %3}\;fst%z0\\t%y0\";
3074
3075 case 1:
3076 return \"#\";
3077
3078 default:
3079 abort ();
3080 }
3081 }"
3082 [(set_attr "type" "multi")
3083 (set_attr "mode" "XF,SI")])
3084
3085 (define_insn "*pushtf_integer"
3086 [(set (match_operand:TF 0 "push_operand" "=<,<")
3087 (match_operand:TF 1 "general_no_elim_operand" "f#r,rFo#f"))]
3088 "!optimize_size"
3089 "*
3090 {
3091 switch (which_alternative)
3092 {
3093 case 0:
3094 /* %%% We loose REG_DEAD notes for controling pops if we split late. */
3095 operands[0] = gen_rtx_MEM (XFmode, stack_pointer_rtx);
3096 operands[2] = stack_pointer_rtx;
3097 operands[3] = GEN_INT (16);
3098 if (TARGET_64BIT)
3099 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3100 return \"sub{q}\\t{%3, %2|%2, %3}\;fstp%z0\\t%y0\";
3101 else
3102 return \"sub{q}\\t{%3, %2|%2, %3}\;fst%z0\\t%y0\";
3103 else
3104 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3105 return \"sub{l}\\t{%3, %2|%2, %3}\;fstp%z0\\t%y0\";
3106 else
3107 return \"sub{l}\\t{%3, %2|%2, %3}\;fst%z0\\t%y0\";
3108
3109 case 1:
3110 return \"#\";
3111
3112 default:
3113 abort ();
3114 }
3115 }"
3116 [(set_attr "type" "multi")
3117 (set_attr "mode" "XF,SI")])
3118
3119 (define_split
3120 [(set (match_operand 0 "push_operand" "")
3121 (match_operand 1 "general_operand" ""))]
3122 "reload_completed
3123 && (GET_MODE (operands[0]) == XFmode
3124 || GET_MODE (operands[0]) == TFmode
3125 || GET_MODE (operands[0]) == DFmode)
3126 && (!REG_P (operands[1]) || !ANY_FP_REGNO_P (REGNO (operands[1])))"
3127 [(const_int 0)]
3128 "if (!ix86_split_long_move (operands)) abort (); DONE;")
3129
3130 (define_split
3131 [(set (match_operand:XF 0 "push_operand" "")
3132 (match_operand:XF 1 "register_operand" ""))]
3133 "!TARGET_64BIT && ANY_FP_REGNO_P (REGNO (operands[1]))"
3134 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -12)))
3135 (set (mem:XF (reg:SI 7)) (match_dup 1))])
3136
3137 (define_split
3138 [(set (match_operand:TF 0 "push_operand" "")
3139 (match_operand:TF 1 "register_operand" ""))]
3140 "!TARGET_64BIT && ANY_FP_REGNO_P (REGNO (operands[1]))"
3141 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -16)))
3142 (set (mem:TF (reg:SI 7)) (match_dup 1))])
3143
3144 (define_split
3145 [(set (match_operand:TF 0 "push_operand" "")
3146 (match_operand:TF 1 "register_operand" ""))]
3147 "TARGET_64BIT && ANY_FP_REGNO_P (REGNO (operands[1]))"
3148 [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -16)))
3149 (set (mem:TF (reg:DI 7)) (match_dup 1))])
3150
3151 ;; Do not use integer registers when optimizing for size
3152 (define_insn "*movxf_nointeger"
3153 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,*r,o")
3154 (match_operand:XF 1 "general_operand" "fm,f,G,*roF,F*r"))]
3155 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
3156 && !TARGET_64BIT
3157 && optimize_size
3158 && (reload_in_progress || reload_completed
3159 || GET_CODE (operands[1]) != CONST_DOUBLE
3160 || memory_operand (operands[0], XFmode))"
3161 "*
3162 {
3163 switch (which_alternative)
3164 {
3165 case 0:
3166 if (REG_P (operands[1])
3167 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3168 return \"fstp\\t%y0\";
3169 else if (STACK_TOP_P (operands[0]))
3170 return \"fld%z1\\t%y1\";
3171 else
3172 return \"fst\\t%y0\";
3173
3174 case 1:
3175 /* There is no non-popping store to memory for XFmode. So if
3176 we need one, follow the store with a load. */
3177 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3178 return \"fstp%z0\\t%y0\;fld%z0\\t%y0\";
3179 else
3180 return \"fstp%z0\\t%y0\";
3181
3182 case 2:
3183 switch (standard_80387_constant_p (operands[1]))
3184 {
3185 case 1:
3186 return \"fldz\";
3187 case 2:
3188 return \"fld1\";
3189 }
3190 break;
3191
3192 case 3: case 4:
3193 return \"#\";
3194 }
3195 abort();
3196 }"
3197 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
3198 (set_attr "mode" "XF,XF,XF,SI,SI")])
3199
3200 (define_insn "*movtf_nointeger"
3201 [(set (match_operand:TF 0 "nonimmediate_operand" "=f,m,f,*r,o")
3202 (match_operand:TF 1 "general_operand" "fm,f,G,*roF,F*r"))]
3203 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
3204 && optimize_size
3205 && (reload_in_progress || reload_completed
3206 || GET_CODE (operands[1]) != CONST_DOUBLE
3207 || memory_operand (operands[0], TFmode))"
3208 "*
3209 {
3210 switch (which_alternative)
3211 {
3212 case 0:
3213 if (REG_P (operands[1])
3214 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3215 return \"fstp\\t%y0\";
3216 else if (STACK_TOP_P (operands[0]))
3217 return \"fld%z1\\t%y1\";
3218 else
3219 return \"fst\\t%y0\";
3220
3221 case 1:
3222 /* There is no non-popping store to memory for XFmode. So if
3223 we need one, follow the store with a load. */
3224 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3225 return \"fstp%z0\\t%y0\;fld%z0\\t%y0\";
3226 else
3227 return \"fstp%z0\\t%y0\";
3228
3229 case 2:
3230 switch (standard_80387_constant_p (operands[1]))
3231 {
3232 case 1:
3233 return \"fldz\";
3234 case 2:
3235 return \"fld1\";
3236 }
3237 break;
3238
3239 case 3: case 4:
3240 return \"#\";
3241 }
3242 abort();
3243 }"
3244 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
3245 (set_attr "mode" "XF,XF,XF,SI,SI")])
3246
3247 (define_insn "*movxf_integer"
3248 [(set (match_operand:XF 0 "nonimmediate_operand" "=f#r,m,f#r,r#f,o")
3249 (match_operand:XF 1 "general_operand" "fm#r,f#r,G,roF#f,Fr#f"))]
3250 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
3251 && !TARGET_64BIT
3252 && !optimize_size
3253 && (reload_in_progress || reload_completed
3254 || GET_CODE (operands[1]) != CONST_DOUBLE
3255 || memory_operand (operands[0], XFmode))"
3256 "*
3257 {
3258 switch (which_alternative)
3259 {
3260 case 0:
3261 if (REG_P (operands[1])
3262 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3263 return \"fstp\\t%y0\";
3264 else if (STACK_TOP_P (operands[0]))
3265 return \"fld%z1\\t%y1\";
3266 else
3267 return \"fst\\t%y0\";
3268
3269 case 1:
3270 /* There is no non-popping store to memory for XFmode. So if
3271 we need one, follow the store with a load. */
3272 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3273 return \"fstp%z0\\t%y0\;fld%z0\\t%y0\";
3274 else
3275 return \"fstp%z0\\t%y0\";
3276
3277 case 2:
3278 switch (standard_80387_constant_p (operands[1]))
3279 {
3280 case 1:
3281 return \"fldz\";
3282 case 2:
3283 return \"fld1\";
3284 }
3285 break;
3286
3287 case 3: case 4:
3288 return \"#\";
3289 }
3290 abort();
3291 }"
3292 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
3293 (set_attr "mode" "XF,XF,XF,SI,SI")])
3294
3295 (define_insn "*movtf_integer"
3296 [(set (match_operand:TF 0 "nonimmediate_operand" "=f#r,m,f#r,r#f,o")
3297 (match_operand:TF 1 "general_operand" "fm#r,f#r,G,roF#f,Fr#f"))]
3298 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
3299 && !optimize_size
3300 && (reload_in_progress || reload_completed
3301 || GET_CODE (operands[1]) != CONST_DOUBLE
3302 || memory_operand (operands[0], TFmode))"
3303 "*
3304 {
3305 switch (which_alternative)
3306 {
3307 case 0:
3308 if (REG_P (operands[1])
3309 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3310 return \"fstp\\t%y0\";
3311 else if (STACK_TOP_P (operands[0]))
3312 return \"fld%z1\\t%y1\";
3313 else
3314 return \"fst\\t%y0\";
3315
3316 case 1:
3317 /* There is no non-popping store to memory for XFmode. So if
3318 we need one, follow the store with a load. */
3319 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3320 return \"fstp%z0\\t%y0\;fld%z0\\t%y0\";
3321 else
3322 return \"fstp%z0\\t%y0\";
3323
3324 case 2:
3325 switch (standard_80387_constant_p (operands[1]))
3326 {
3327 case 1:
3328 return \"fldz\";
3329 case 2:
3330 return \"fld1\";
3331 }
3332 break;
3333
3334 case 3: case 4:
3335 return \"#\";
3336 }
3337 abort();
3338 }"
3339 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
3340 (set_attr "mode" "XF,XF,XF,SI,SI")])
3341
3342 (define_split
3343 [(set (match_operand 0 "nonimmediate_operand" "")
3344 (match_operand 1 "general_operand" ""))]
3345 "reload_completed
3346 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
3347 && (GET_MODE (operands[0]) == XFmode || GET_MODE (operands[0]) == TFmode)
3348 && ! (ANY_FP_REG_P (operands[0]) ||
3349 (GET_CODE (operands[0]) == SUBREG
3350 && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
3351 && ! (ANY_FP_REG_P (operands[1]) ||
3352 (GET_CODE (operands[1]) == SUBREG
3353 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
3354 [(set (match_dup 2) (match_dup 5))
3355 (set (match_dup 3) (match_dup 6))
3356 (set (match_dup 4) (match_dup 7))]
3357 "if (ix86_split_long_move (operands)) DONE;")
3358
3359 (define_split
3360 [(set (match_operand 0 "register_operand" "")
3361 (match_operand 1 "memory_operand" ""))]
3362 "reload_completed
3363 && GET_CODE (operands[1]) == MEM
3364 && (GET_MODE (operands[0]) == XFmode || GET_MODE (operands[0]) == TFmode
3365 || GET_MODE (operands[0]) == SFmode || GET_MODE (operands[0]) == DFmode)
3366 && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
3367 && CONSTANT_POOL_ADDRESS_P (XEXP (operands[1], 0))
3368 && (!(SSE_REG_P (operands[0]) ||
3369 (GET_CODE (operands[0]) == SUBREG
3370 && SSE_REG_P (SUBREG_REG (operands[0]))))
3371 || standard_sse_constant_p (get_pool_constant (XEXP (operands[1], 0))))
3372 && (!(FP_REG_P (operands[0]) ||
3373 (GET_CODE (operands[0]) == SUBREG
3374 && FP_REG_P (SUBREG_REG (operands[0]))))
3375 || standard_80387_constant_p (get_pool_constant (XEXP (operands[1], 0))))"
3376 [(set (match_dup 0)
3377 (match_dup 1))]
3378 "operands[1] = get_pool_constant (XEXP (operands[1], 0));")
3379
3380 (define_insn "swapxf"
3381 [(set (match_operand:XF 0 "register_operand" "+f")
3382 (match_operand:XF 1 "register_operand" "+f"))
3383 (set (match_dup 1)
3384 (match_dup 0))]
3385 ""
3386 "*
3387 {
3388 if (STACK_TOP_P (operands[0]))
3389 return \"fxch\\t%1\";
3390 else
3391 return \"fxch\\t%0\";
3392 }"
3393 [(set_attr "type" "fxch")
3394 (set_attr "mode" "XF")])
3395
3396 (define_insn "swaptf"
3397 [(set (match_operand:TF 0 "register_operand" "+f")
3398 (match_operand:TF 1 "register_operand" "+f"))
3399 (set (match_dup 1)
3400 (match_dup 0))]
3401 ""
3402 "*
3403 {
3404 if (STACK_TOP_P (operands[0]))
3405 return \"fxch\\t%1\";
3406 else
3407 return \"fxch\\t%0\";
3408 }"
3409 [(set_attr "type" "fxch")
3410 (set_attr "mode" "XF")])
3411 \f
3412 ;; Zero extension instructions
3413
3414 (define_expand "zero_extendhisi2"
3415 [(set (match_operand:SI 0 "register_operand" "")
3416 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
3417 ""
3418 "
3419 {
3420 if (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3421 {
3422 operands[1] = force_reg (HImode, operands[1]);
3423 emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
3424 DONE;
3425 }
3426 }")
3427
3428 (define_insn "zero_extendhisi2_and"
3429 [(set (match_operand:SI 0 "register_operand" "=r")
3430 (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
3431 (clobber (reg:CC 17))]
3432 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3433 "#"
3434 [(set_attr "type" "alu1")
3435 (set_attr "mode" "SI")])
3436
3437 (define_split
3438 [(set (match_operand:SI 0 "register_operand" "")
3439 (zero_extend:SI (match_operand:HI 1 "register_operand" "")))
3440 (clobber (reg:CC 17))]
3441 "reload_completed && TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3442 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
3443 (clobber (reg:CC 17))])]
3444 "")
3445
3446 (define_insn "*zero_extendhisi2_movzwl"
3447 [(set (match_operand:SI 0 "register_operand" "=r")
3448 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3449 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3450 "movz{wl|x}\\t{%1, %0|%0, %1}"
3451 [(set_attr "type" "imovx")
3452 (set_attr "mode" "SI")])
3453
3454 (define_expand "zero_extendqihi2"
3455 [(parallel
3456 [(set (match_operand:HI 0 "register_operand" "")
3457 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3458 (clobber (reg:CC 17))])]
3459 ""
3460 "")
3461
3462 (define_insn "*zero_extendqihi2_and"
3463 [(set (match_operand:HI 0 "register_operand" "=r,?&q")
3464 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3465 (clobber (reg:CC 17))]
3466 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3467 "#"
3468 [(set_attr "type" "alu1")
3469 (set_attr "mode" "HI")])
3470
3471 (define_insn "*zero_extendqihi2_movzbw_and"
3472 [(set (match_operand:HI 0 "register_operand" "=r,r")
3473 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3474 (clobber (reg:CC 17))]
3475 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3476 "#"
3477 [(set_attr "type" "imovx,alu1")
3478 (set_attr "mode" "HI")])
3479
3480 (define_insn "*zero_extendqihi2_movzbw"
3481 [(set (match_operand:HI 0 "register_operand" "=r")
3482 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3483 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3484 "movz{bw|x}\\t{%1, %0|%0, %1}"
3485 [(set_attr "type" "imovx")
3486 (set_attr "mode" "HI")])
3487
3488 ;; For the movzbw case strip only the clobber
3489 (define_split
3490 [(set (match_operand:HI 0 "register_operand" "")
3491 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3492 (clobber (reg:CC 17))]
3493 "reload_completed
3494 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3495 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3496 [(set (match_operand:HI 0 "register_operand" "")
3497 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))])
3498
3499 ;; When source and destination does not overlap, clear destination
3500 ;; first and then do the movb
3501 (define_split
3502 [(set (match_operand:HI 0 "register_operand" "")
3503 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3504 (clobber (reg:CC 17))]
3505 "reload_completed
3506 && ANY_QI_REG_P (operands[0])
3507 && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3508 && !reg_overlap_mentioned_p (operands[0], operands[1])"
3509 [(set (match_dup 0) (const_int 0))
3510 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3511 "operands[2] = gen_lowpart (QImode, operands[0]);")
3512
3513 ;; Rest is handled by single and.
3514 (define_split
3515 [(set (match_operand:HI 0 "register_operand" "")
3516 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))
3517 (clobber (reg:CC 17))]
3518 "reload_completed
3519 && true_regnum (operands[0]) == true_regnum (operands[1])"
3520 [(parallel [(set (match_dup 0) (and:HI (match_dup 0) (const_int 255)))
3521 (clobber (reg:CC 17))])]
3522 "")
3523
3524 (define_expand "zero_extendqisi2"
3525 [(parallel
3526 [(set (match_operand:SI 0 "register_operand" "")
3527 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3528 (clobber (reg:CC 17))])]
3529 ""
3530 "")
3531
3532 (define_insn "*zero_extendqisi2_and"
3533 [(set (match_operand:SI 0 "register_operand" "=r,?&q")
3534 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3535 (clobber (reg:CC 17))]
3536 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3537 "#"
3538 [(set_attr "type" "alu1")
3539 (set_attr "mode" "SI")])
3540
3541 (define_insn "*zero_extendqisi2_movzbw_and"
3542 [(set (match_operand:SI 0 "register_operand" "=r,r")
3543 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3544 (clobber (reg:CC 17))]
3545 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3546 "#"
3547 [(set_attr "type" "imovx,alu1")
3548 (set_attr "mode" "SI")])
3549
3550 (define_insn "*zero_extendqisi2_movzbw"
3551 [(set (match_operand:SI 0 "register_operand" "=r")
3552 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3553 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3554 "movz{bl|x}\\t{%1, %0|%0, %1}"
3555 [(set_attr "type" "imovx")
3556 (set_attr "mode" "SI")])
3557
3558 ;; For the movzbl case strip only the clobber
3559 (define_split
3560 [(set (match_operand:SI 0 "register_operand" "")
3561 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3562 (clobber (reg:CC 17))]
3563 "reload_completed
3564 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3565 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3566 [(set (match_dup 0)
3567 (zero_extend:SI (match_dup 1)))])
3568
3569 ;; When source and destination does not overlap, clear destination
3570 ;; first and then do the movb
3571 (define_split
3572 [(set (match_operand:SI 0 "register_operand" "")
3573 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3574 (clobber (reg:CC 17))]
3575 "reload_completed
3576 && ANY_QI_REG_P (operands[0])
3577 && (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM)
3578 && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3579 && !reg_overlap_mentioned_p (operands[0], operands[1])"
3580 [(set (match_dup 0) (const_int 0))
3581 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3582 "operands[2] = gen_lowpart (QImode, operands[0]);")
3583
3584 ;; Rest is handled by single and.
3585 (define_split
3586 [(set (match_operand:SI 0 "register_operand" "")
3587 (zero_extend:SI (match_operand:QI 1 "register_operand" "")))
3588 (clobber (reg:CC 17))]
3589 "reload_completed
3590 && true_regnum (operands[0]) == true_regnum (operands[1])"
3591 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 255)))
3592 (clobber (reg:CC 17))])]
3593 "")
3594
3595 ;; %%% Kill me once multi-word ops are sane.
3596 (define_expand "zero_extendsidi2"
3597 [(set (match_operand:DI 0 "register_operand" "=r")
3598 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm")))]
3599 ""
3600 "if (!TARGET_64BIT)
3601 {
3602 emit_insn (gen_zero_extendsidi2_32 (operands[0], operands[1]));
3603 DONE;
3604 }
3605 ")
3606
3607 (define_insn "zero_extendsidi2_32"
3608 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?*o")
3609 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "0,rm,r")))
3610 (clobber (reg:CC 17))]
3611 "!TARGET_64BIT"
3612 "#"
3613 [(set_attr "mode" "SI")])
3614
3615 (define_insn "zero_extendsidi2_rex64"
3616 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
3617 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm,0")))]
3618 "TARGET_64BIT"
3619 "@
3620 mov\\t{%k1, %k0|%k0, %k1}
3621 #"
3622 [(set_attr "type" "imovx,imov")
3623 (set_attr "mode" "SI,DI")])
3624
3625 (define_split
3626 [(set (match_operand:DI 0 "memory_operand" "")
3627 (zero_extend:DI (match_dup 0)))]
3628 ""
3629 [(set (match_dup 4) (const_int 0))]
3630 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3631
3632 (define_split
3633 [(set (match_operand:DI 0 "register_operand" "")
3634 (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3635 (clobber (reg:CC 17))]
3636 "reload_completed && true_regnum (operands[0]) == true_regnum (operands[1])
3637 && !TARGET_64BIT"
3638 [(set (match_dup 4) (const_int 0))]
3639 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3640
3641 (define_split
3642 [(set (match_operand:DI 0 "nonimmediate_operand" "")
3643 (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3644 (clobber (reg:CC 17))]
3645 "reload_completed && !TARGET_64BIT"
3646 [(set (match_dup 3) (match_dup 1))
3647 (set (match_dup 4) (const_int 0))]
3648 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3649
3650 (define_insn "zero_extendhidi2"
3651 [(set (match_operand:DI 0 "register_operand" "=r,r")
3652 (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "r,m")))]
3653 "TARGET_64BIT"
3654 "@
3655 movz{wl|x}\\t{%1, %k0|%k0, %1}
3656 movz{wq|x}\\t{%1, %0|%0, %1}"
3657 [(set_attr "type" "imovx")
3658 (set_attr "mode" "SI,DI")])
3659
3660 (define_insn "zero_extendqidi2"
3661 [(set (match_operand:DI 0 "register_operand" "=r,r")
3662 (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "Q,m")))]
3663 "TARGET_64BIT"
3664 "@
3665 movz{bl|x}\\t{%1, %k0|%k0, %1}
3666 movz{bq|x}\\t{%1, %0|%0, %1}"
3667 [(set_attr "type" "imovx")
3668 (set_attr "mode" "SI,DI")])
3669 \f
3670 ;; Sign extension instructions
3671
3672 (define_expand "extendsidi2"
3673 [(parallel [(set (match_operand:DI 0 "register_operand" "")
3674 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3675 (clobber (reg:CC 17))
3676 (clobber (match_scratch:SI 2 ""))])]
3677 ""
3678 "
3679 {
3680 if (TARGET_64BIT)
3681 {
3682 emit_insn (gen_extendsidi2_rex64 (operands[0], operands[1]));
3683 DONE;
3684 }
3685 }")
3686
3687 (define_insn "*extendsidi2_1"
3688 [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3689 (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3690 (clobber (reg:CC 17))
3691 (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3692 "!TARGET_64BIT"
3693 "#")
3694
3695 (define_insn "extendsidi2_rex64"
3696 [(set (match_operand:DI 0 "register_operand" "=*a,r")
3697 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3698 "TARGET_64BIT"
3699 "@
3700 {cltq|cdqe}
3701 movs{lq|x}\\t{%1,%0|%0, %1}"
3702 [(set_attr "type" "imovx")
3703 (set_attr "mode" "DI")
3704 (set_attr "prefix_0f" "0")
3705 (set_attr "modrm" "0,1")])
3706
3707 (define_insn "extendhidi2"
3708 [(set (match_operand:DI 0 "register_operand" "=r")
3709 (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3710 "TARGET_64BIT"
3711 "movs{wq|x}\\t{%1,%0|%0, %1}"
3712 [(set_attr "type" "imovx")
3713 (set_attr "mode" "DI")])
3714
3715 (define_insn "extendqidi2"
3716 [(set (match_operand:DI 0 "register_operand" "=r")
3717 (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3718 "TARGET_64BIT"
3719 "movs{bq|x}\\t{%1,%0|%0, %1}"
3720 [(set_attr "type" "imovx")
3721 (set_attr "mode" "DI")])
3722
3723 ;; Extend to memory case when source register does die.
3724 (define_split
3725 [(set (match_operand:DI 0 "memory_operand" "")
3726 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3727 (clobber (reg:CC 17))
3728 (clobber (match_operand:SI 2 "register_operand" ""))]
3729 "(reload_completed
3730 && dead_or_set_p (insn, operands[1])
3731 && !reg_mentioned_p (operands[1], operands[0]))"
3732 [(set (match_dup 3) (match_dup 1))
3733 (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3734 (clobber (reg:CC 17))])
3735 (set (match_dup 4) (match_dup 1))]
3736 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3737
3738 ;; Extend to memory case when source register does not die.
3739 (define_split
3740 [(set (match_operand:DI 0 "memory_operand" "")
3741 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3742 (clobber (reg:CC 17))
3743 (clobber (match_operand:SI 2 "register_operand" ""))]
3744 "reload_completed"
3745 [(const_int 0)]
3746 "
3747 {
3748 split_di (&operands[0], 1, &operands[3], &operands[4]);
3749
3750 emit_move_insn (operands[3], operands[1]);
3751
3752 /* Generate a cltd if possible and doing so it profitable. */
3753 if (true_regnum (operands[1]) == 0
3754 && true_regnum (operands[2]) == 1
3755 && (optimize_size || TARGET_USE_CLTD))
3756 {
3757 emit_insn (gen_ashrsi3_31 (operands[2], operands[1], GEN_INT (31)));
3758 }
3759 else
3760 {
3761 emit_move_insn (operands[2], operands[1]);
3762 emit_insn (gen_ashrsi3_31 (operands[2], operands[2], GEN_INT (31)));
3763 }
3764 emit_move_insn (operands[4], operands[2]);
3765 DONE;
3766 }")
3767
3768 ;; Extend to register case. Optimize case where source and destination
3769 ;; registers match and cases where we can use cltd.
3770 (define_split
3771 [(set (match_operand:DI 0 "register_operand" "")
3772 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3773 (clobber (reg:CC 17))
3774 (clobber (match_scratch:SI 2 ""))]
3775 "reload_completed"
3776 [(const_int 0)]
3777 "
3778 {
3779 split_di (&operands[0], 1, &operands[3], &operands[4]);
3780
3781 if (true_regnum (operands[3]) != true_regnum (operands[1]))
3782 emit_move_insn (operands[3], operands[1]);
3783
3784 /* Generate a cltd if possible and doing so it profitable. */
3785 if (true_regnum (operands[3]) == 0
3786 && (optimize_size || TARGET_USE_CLTD))
3787 {
3788 emit_insn (gen_ashrsi3_31 (operands[4], operands[3], GEN_INT (31)));
3789 DONE;
3790 }
3791
3792 if (true_regnum (operands[4]) != true_regnum (operands[1]))
3793 emit_move_insn (operands[4], operands[1]);
3794
3795 emit_insn (gen_ashrsi3_31 (operands[4], operands[4], GEN_INT (31)));
3796 DONE;
3797 }")
3798
3799 (define_insn "extendhisi2"
3800 [(set (match_operand:SI 0 "register_operand" "=*a,r")
3801 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3802 ""
3803 "*
3804 {
3805 switch (get_attr_prefix_0f (insn))
3806 {
3807 case 0:
3808 return \"{cwtl|cwde}\";
3809 default:
3810 return \"movs{wl|x}\\t{%1,%0|%0, %1}\";
3811 }
3812 }"
3813 [(set_attr "type" "imovx")
3814 (set_attr "mode" "SI")
3815 (set (attr "prefix_0f")
3816 ;; movsx is short decodable while cwtl is vector decoded.
3817 (if_then_else (and (eq_attr "cpu" "!k6")
3818 (eq_attr "alternative" "0"))
3819 (const_string "0")
3820 (const_string "1")))
3821 (set (attr "modrm")
3822 (if_then_else (eq_attr "prefix_0f" "0")
3823 (const_string "0")
3824 (const_string "1")))])
3825
3826 (define_insn "*extendhisi2_zext"
3827 [(set (match_operand:DI 0 "register_operand" "=*a,r")
3828 (zero_extend:DI
3829 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3830 "TARGET_64BIT"
3831 "*
3832 {
3833 switch (get_attr_prefix_0f (insn))
3834 {
3835 case 0:
3836 return \"{cwtl|cwde}\";
3837 default:
3838 return \"movs{wl|x}\\t{%1,%k0|%k0, %1}\";
3839 }
3840 }"
3841 [(set_attr "type" "imovx")
3842 (set_attr "mode" "SI")
3843 (set (attr "prefix_0f")
3844 ;; movsx is short decodable while cwtl is vector decoded.
3845 (if_then_else (and (eq_attr "cpu" "!k6")
3846 (eq_attr "alternative" "0"))
3847 (const_string "0")
3848 (const_string "1")))
3849 (set (attr "modrm")
3850 (if_then_else (eq_attr "prefix_0f" "0")
3851 (const_string "0")
3852 (const_string "1")))])
3853
3854 (define_insn "extendqihi2"
3855 [(set (match_operand:HI 0 "register_operand" "=*a,r")
3856 (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3857 ""
3858 "*
3859 {
3860 switch (get_attr_prefix_0f (insn))
3861 {
3862 case 0:
3863 return \"{cbtw|cbw}\";
3864 default:
3865 return \"movs{bw|x}\\t{%1,%0|%0, %1}\";
3866 }
3867 }"
3868 [(set_attr "type" "imovx")
3869 (set_attr "mode" "HI")
3870 (set (attr "prefix_0f")
3871 ;; movsx is short decodable while cwtl is vector decoded.
3872 (if_then_else (and (eq_attr "cpu" "!k6")
3873 (eq_attr "alternative" "0"))
3874 (const_string "0")
3875 (const_string "1")))
3876 (set (attr "modrm")
3877 (if_then_else (eq_attr "prefix_0f" "0")
3878 (const_string "0")
3879 (const_string "1")))])
3880
3881 (define_insn "extendqisi2"
3882 [(set (match_operand:SI 0 "register_operand" "=r")
3883 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3884 ""
3885 "movs{bl|x}\\t{%1,%0|%0, %1}"
3886 [(set_attr "type" "imovx")
3887 (set_attr "mode" "SI")])
3888
3889 (define_insn "*extendqisi2_zext"
3890 [(set (match_operand:DI 0 "register_operand" "=r")
3891 (zero_extend:DI
3892 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3893 "TARGET_64BIT"
3894 "movs{bl|x}\\t{%1,%k0|%k0, %1}"
3895 [(set_attr "type" "imovx")
3896 (set_attr "mode" "SI")])
3897 \f
3898 ;; Conversions between float and double.
3899
3900 ;; These are all no-ops in the model used for the 80387. So just
3901 ;; emit moves.
3902
3903 ;; %%% Kill these when call knows how to work out a DFmode push earlier.
3904 (define_insn "*dummy_extendsfdf2"
3905 [(set (match_operand:DF 0 "push_operand" "=<")
3906 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fY")))]
3907 "0"
3908 "#")
3909
3910 (define_split
3911 [(set (match_operand:DF 0 "push_operand" "")
3912 (float_extend:DF (match_operand:SF 1 "register_operand" "")))]
3913 "FP_REGNO_P (REGNO (operands[1])) && !TARGET_64BIT"
3914 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
3915 (set (mem:DF (reg:SI 7)) (float_extend:DF (match_dup 1)))])
3916
3917 (define_split
3918 [(set (match_operand:DF 0 "push_operand" "")
3919 (float_extend:DF (match_operand:SF 1 "register_operand" "")))]
3920 "FP_REGNO_P (REGNO (operands[1])) && TARGET_64BIT"
3921 [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -8)))
3922 (set (mem:DF (reg:DI 7)) (float_extend:DF (match_dup 1)))])
3923
3924 (define_insn "*dummy_extendsfxf2"
3925 [(set (match_operand:XF 0 "push_operand" "=<")
3926 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "f")))]
3927 "0"
3928 "#")
3929
3930 (define_split
3931 [(set (match_operand:XF 0 "push_operand" "")
3932 (float_extend:XF (match_operand:SF 1 "register_operand" "")))]
3933 "FP_REGNO_P (REGNO (operands[1])) && !TARGET_64BIT"
3934 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -12)))
3935 (set (mem:XF (reg:SI 7)) (float_extend:XF (match_dup 1)))])
3936
3937 (define_insn "*dummy_extendsftf2"
3938 [(set (match_operand:TF 0 "push_operand" "=<")
3939 (float_extend:TF (match_operand:SF 1 "nonimmediate_operand" "f")))]
3940 "0"
3941 "#")
3942
3943 (define_split
3944 [(set (match_operand:TF 0 "push_operand" "")
3945 (float_extend:TF (match_operand:SF 1 "register_operand" "")))]
3946 "FP_REGNO_P (REGNO (operands[1])) && !TARGET_64BIT"
3947 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -16)))
3948 (set (mem:TF (reg:SI 7)) (float_extend:TF (match_dup 1)))])
3949
3950 (define_split
3951 [(set (match_operand:TF 0 "push_operand" "")
3952 (float_extend:TF (match_operand:SF 1 "register_operand" "")))]
3953 "FP_REGNO_P (REGNO (operands[1])) && TARGET_64BIT"
3954 [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -16)))
3955 (set (mem:DF (reg:DI 7)) (float_extend:TF (match_dup 1)))])
3956
3957 (define_insn "*dummy_extenddfxf2"
3958 [(set (match_operand:XF 0 "push_operand" "=<")
3959 (float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "f")))]
3960 "0"
3961 "#")
3962
3963 (define_split
3964 [(set (match_operand:XF 0 "push_operand" "")
3965 (float_extend:XF (match_operand:DF 1 "register_operand" "")))]
3966 "FP_REGNO_P (REGNO (operands[1])) && !TARGET_64BIT"
3967 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -12)))
3968 (set (mem:DF (reg:SI 7)) (float_extend:XF (match_dup 1)))])
3969
3970 (define_insn "*dummy_extenddftf2"
3971 [(set (match_operand:TF 0 "push_operand" "=<")
3972 (float_extend:TF (match_operand:DF 1 "nonimmediate_operand" "f")))]
3973 "0"
3974 "#")
3975
3976 (define_split
3977 [(set (match_operand:TF 0 "push_operand" "")
3978 (float_extend:TF (match_operand:DF 1 "register_operand" "")))]
3979 "FP_REGNO_P (REGNO (operands[1])) && !TARGET_64BIT"
3980 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -16)))
3981 (set (mem:TF (reg:SI 7)) (float_extend:XF (match_dup 1)))])
3982
3983 (define_split
3984 [(set (match_operand:TF 0 "push_operand" "")
3985 (float_extend:TF (match_operand:DF 1 "register_operand" "")))]
3986 "FP_REGNO_P (REGNO (operands[1])) && TARGET_64BIT"
3987 [(set (reg:DI 7) (plus:DI (reg:DI 7) (const_int -16)))
3988 (set (mem:TF (reg:DI 7)) (float_extend:XF (match_dup 1)))])
3989
3990 (define_expand "extendsfdf2"
3991 [(set (match_operand:DF 0 "nonimmediate_operand" "")
3992 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "")))]
3993 "TARGET_80387 || TARGET_SSE2"
3994 "
3995 {
3996 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3997 operands[1] = force_reg (SFmode, operands[1]);
3998 }")
3999
4000 (define_insn "*extendsfdf2_1"
4001 [(set (match_operand:DF 0 "nonimmediate_operand" "=f#Y,mf#Y,Y#f")
4002 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm#Y,f#Y,mY#f")))]
4003 "(TARGET_80387 || TARGET_SSE2)
4004 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
4005 "*
4006 {
4007 switch (which_alternative)
4008 {
4009 case 0:
4010 if (REG_P (operands[1])
4011 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4012 return \"fstp\\t%y0\";
4013 else if (STACK_TOP_P (operands[0]))
4014 return \"fld%z1\\t%y1\";
4015 else
4016 return \"fst\\t%y0\";
4017
4018 case 1:
4019 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4020 return \"fstp%z0\\t%y0\";
4021
4022 else
4023 return \"fst%z0\\t%y0\";
4024 case 2:
4025 return \"cvtss2sd\\t{%1, %0|%0, %1}\";
4026
4027 default:
4028 abort ();
4029 }
4030 }"
4031 [(set_attr "type" "fmov,fmov,sse")
4032 (set_attr "mode" "SF,XF,DF")])
4033
4034 (define_insn "*extendsfdf2_1_sse_only"
4035 [(set (match_operand:DF 0 "register_operand" "=Y")
4036 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "mY")))]
4037 "!TARGET_80387 && TARGET_SSE2
4038 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
4039 "cvtss2sd\\t{%1, %0|%0, %1}"
4040 [(set_attr "type" "sse")
4041 (set_attr "mode" "DF")])
4042
4043 (define_expand "extendsfxf2"
4044 [(set (match_operand:XF 0 "nonimmediate_operand" "")
4045 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "")))]
4046 "TARGET_80387 && !TARGET_64BIT"
4047 "
4048 {
4049 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
4050 operands[1] = force_reg (SFmode, operands[1]);
4051 }")
4052
4053 (define_insn "*extendsfxf2_1"
4054 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
4055 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
4056 "TARGET_80387 && !TARGET_64BIT
4057 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
4058 "*
4059 {
4060 switch (which_alternative)
4061 {
4062 case 0:
4063 if (REG_P (operands[1])
4064 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4065 return \"fstp\\t%y0\";
4066 else if (STACK_TOP_P (operands[0]))
4067 return \"fld%z1\\t%y1\";
4068 else
4069 return \"fst\\t%y0\";
4070
4071 case 1:
4072 /* There is no non-popping store to memory for XFmode. So if
4073 we need one, follow the store with a load. */
4074 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4075 return \"fstp%z0\\t%y0\\n\\tfld%z0\\t%y0\";
4076 else
4077 return \"fstp%z0\\t%y0\";
4078
4079 default:
4080 abort ();
4081 }
4082 }"
4083 [(set_attr "type" "fmov")
4084 (set_attr "mode" "SF,XF")])
4085
4086 (define_expand "extendsftf2"
4087 [(set (match_operand:TF 0 "nonimmediate_operand" "")
4088 (float_extend:TF (match_operand:SF 1 "nonimmediate_operand" "")))]
4089 "TARGET_80387"
4090 "
4091 {
4092 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
4093 operands[1] = force_reg (SFmode, operands[1]);
4094 }")
4095
4096 (define_insn "*extendsftf2_1"
4097 [(set (match_operand:TF 0 "nonimmediate_operand" "=f,m")
4098 (float_extend:TF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
4099 "TARGET_80387
4100 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
4101 "*
4102 {
4103 switch (which_alternative)
4104 {
4105 case 0:
4106 if (REG_P (operands[1])
4107 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4108 return \"fstp\\t%y0\";
4109 else if (STACK_TOP_P (operands[0]))
4110 return \"fld%z1\\t%y1\";
4111 else
4112 return \"fst\\t%y0\";
4113
4114 case 1:
4115 /* There is no non-popping store to memory for XFmode. So if
4116 we need one, follow the store with a load. */
4117 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4118 return \"fstp%z0\\t%y0\\n\\tfld%z0\\t%y0\";
4119 else
4120 return \"fstp%z0\\t%y0\";
4121
4122 default:
4123 abort ();
4124 }
4125 }"
4126 [(set_attr "type" "fmov")
4127 (set_attr "mode" "SF,XF")])
4128
4129 (define_expand "extenddfxf2"
4130 [(set (match_operand:XF 0 "nonimmediate_operand" "")
4131 (float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "")))]
4132 "TARGET_80387 && !TARGET_64BIT"
4133 "
4134 {
4135 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
4136 operands[1] = force_reg (DFmode, operands[1]);
4137 }")
4138
4139 (define_insn "*extenddfxf2_1"
4140 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
4141 (float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "fm,f")))]
4142 "TARGET_80387 && !TARGET_64BIT
4143 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
4144 "*
4145 {
4146 switch (which_alternative)
4147 {
4148 case 0:
4149 if (REG_P (operands[1])
4150 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4151 return \"fstp\\t%y0\";
4152 else if (STACK_TOP_P (operands[0]))
4153 return \"fld%z1\\t%y1\";
4154 else
4155 return \"fst\\t%y0\";
4156
4157 case 1:
4158 /* There is no non-popping store to memory for XFmode. So if
4159 we need one, follow the store with a load. */
4160 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4161 return \"fstp%z0\\t%y0\\n\\tfld%z0\\t%y0\";
4162 else
4163 return \"fstp%z0\\t%y0\";
4164
4165 default:
4166 abort ();
4167 }
4168 }"
4169 [(set_attr "type" "fmov")
4170 (set_attr "mode" "DF,XF")])
4171
4172 (define_expand "extenddftf2"
4173 [(set (match_operand:TF 0 "nonimmediate_operand" "")
4174 (float_extend:TF (match_operand:DF 1 "nonimmediate_operand" "")))]
4175 "TARGET_80387"
4176 "
4177 {
4178 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
4179 operands[1] = force_reg (DFmode, operands[1]);
4180 }")
4181
4182 (define_insn "*extenddftf2_1"
4183 [(set (match_operand:TF 0 "nonimmediate_operand" "=f,m")
4184 (float_extend:TF (match_operand:DF 1 "nonimmediate_operand" "fm,f")))]
4185 "TARGET_80387
4186 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
4187 "*
4188 {
4189 switch (which_alternative)
4190 {
4191 case 0:
4192 if (REG_P (operands[1])
4193 && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4194 return \"fstp\\t%y0\";
4195 else if (STACK_TOP_P (operands[0]))
4196 return \"fld%z1\\t%y1\";
4197 else
4198 return \"fst\\t%y0\";
4199
4200 case 1:
4201 /* There is no non-popping store to memory for XFmode. So if
4202 we need one, follow the store with a load. */
4203 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4204 return \"fstp%z0\\t%y0\\n\\tfld%z0\\t%y0\";
4205 else
4206 return \"fstp%z0\\t%y0\";
4207
4208 default:
4209 abort ();
4210 }
4211 }"
4212 [(set_attr "type" "fmov")
4213 (set_attr "mode" "DF,XF")])
4214
4215 ;; %%% This seems bad bad news.
4216 ;; This cannot output into an f-reg because there is no way to be sure
4217 ;; of truncating in that case. Otherwise this is just like a simple move
4218 ;; insn. So we pretend we can output to a reg in order to get better
4219 ;; register preferencing, but we really use a stack slot.
4220
4221 (define_expand "truncdfsf2"
4222 [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
4223 (float_truncate:SF
4224 (match_operand:DF 1 "register_operand" "")))
4225 (clobber (match_dup 2))])]
4226 "TARGET_80387 || TARGET_SSE2"
4227 "
4228 if (TARGET_80387)
4229 operands[2] = assign_386_stack_local (SFmode, 0);
4230 else
4231 {
4232 emit_insn (gen_truncdfsf2_sse_only (operands[0], operands[1]));
4233 DONE;
4234 }
4235 ")
4236
4237 (define_insn "*truncdfsf2_1"
4238 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f")
4239 (float_truncate:SF
4240 (match_operand:DF 1 "register_operand" "f,0")))
4241 (clobber (match_operand:SF 2 "memory_operand" "=X,m"))]
4242 "TARGET_80387 && !TARGET_SSE2"
4243 "*
4244 {
4245 switch (which_alternative)
4246 {
4247 case 0:
4248 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4249 return \"fstp%z0\\t%y0\";
4250 else
4251 return \"fst%z0\\t%y0\";
4252 case 1:
4253 return \"fstp%z2\\t%y2\;fld%z2\\t%y2\";
4254 }
4255 abort ();
4256 }"
4257 [(set_attr "type" "fmov,multi")
4258 (set_attr "mode" "SF,SF")])
4259
4260 (define_insn "*truncdfsf2_1_sse"
4261 [(set (match_operand:SF 0 "nonimmediate_operand" "=*!m,?f,Y")
4262 (float_truncate:SF
4263 (match_operand:DF 1 "nonimmediate_operand" "f,0,mY")))
4264 (clobber (match_operand:SF 2 "memory_operand" "=X,m,X"))]
4265 "TARGET_80387 && TARGET_SSE2"
4266 "*
4267 {
4268 switch (which_alternative)
4269 {
4270 case 0:
4271 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4272 return \"fstp%z0\\t%y0\";
4273 else
4274 return \"fst%z0\\t%y0\";
4275 case 1:
4276 return \"fstp%z2\\t%y2\;fld%z2\\t%y2\";
4277 case 2:
4278 case 3:
4279 return \"cvtsd2ss\\t{%1, %0|%0, %1}\";
4280 }
4281 abort ();
4282 }"
4283 [(set_attr "type" "fmov,multi,sse")
4284 (set_attr "mode" "SF,SF,DF")])
4285
4286 (define_insn "*truncdfsf2_2"
4287 [(set (match_operand:SF 0 "nonimmediate_operand" "=Y,!m")
4288 (float_truncate:SF
4289 (match_operand:DF 1 "nonimmediate_operand" "mY,f")))]
4290 "TARGET_80387 && TARGET_SSE2
4291 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
4292 "*
4293 {
4294 switch (which_alternative)
4295 {
4296 case 0:
4297 return \"cvtsd2ss\\t{%1, %0|%0, %1}\";
4298 case 1:
4299 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4300 return \"fstp%z0\\t%y0\";
4301 else
4302 return \"fst%z0\\t%y0\";
4303 }
4304 }"
4305 [(set_attr "type" "sse,fmov")
4306 (set_attr "mode" "DF,SF")])
4307
4308 (define_insn "truncdfsf2_3"
4309 [(set (match_operand:SF 0 "nonimmediate_operand" "=m")
4310 (float_truncate:SF
4311 (match_operand:DF 1 "register_operand" "f")))]
4312 "TARGET_80387"
4313 "*
4314 {
4315 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4316 return \"fstp%z0\\t%y0\";
4317 else
4318 return \"fst%z0\\t%y0\";
4319 }"
4320 [(set_attr "type" "fmov")
4321 (set_attr "mode" "SF")])
4322
4323 (define_insn "truncdfsf2_sse_only"
4324 [(set (match_operand:SF 0 "register_operand" "=Y")
4325 (float_truncate:SF
4326 (match_operand:DF 1 "nonimmediate_operand" "mY")))]
4327 "!TARGET_80387 && TARGET_SSE2"
4328 "cvtsd2ss\\t{%1, %0|%0, %1}"
4329 [(set_attr "type" "sse")
4330 (set_attr "mode" "DF")])
4331
4332 (define_split
4333 [(set (match_operand:SF 0 "memory_operand" "")
4334 (float_truncate:SF
4335 (match_operand:DF 1 "register_operand" "")))
4336 (clobber (match_operand:SF 2 "memory_operand" ""))]
4337 "TARGET_80387"
4338 [(set (match_dup 0) (float_truncate:SF (match_dup 1)))]
4339 "")
4340
4341 (define_split
4342 [(set (match_operand:SF 0 "nonimmediate_operand" "")
4343 (float_truncate:SF
4344 (match_operand:DF 1 "nonimmediate_operand" "")))
4345 (clobber (match_operand 2 "" ""))]
4346 "TARGET_80387 && !FP_REG_P (operands[0]) && !FP_REG_P (operands[1])"
4347 [(set (match_dup 0) (float_truncate:SF (match_dup 1)))]
4348 "")
4349
4350 (define_split
4351 [(set (match_operand:SF 0 "register_operand" "")
4352 (float_truncate:SF
4353 (match_operand:DF 1 "register_operand" "")))
4354 (clobber (match_operand:SF 2 "memory_operand" ""))]
4355 "TARGET_80387 && reload_completed
4356 && FP_REG_P (operands[0])"
4357 [(set (match_dup 2) (float_truncate:SF (match_dup 1)))
4358 (set (match_dup 0) (match_dup 2))]
4359 "")
4360
4361 (define_expand "truncxfsf2"
4362 [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
4363 (float_truncate:SF
4364 (match_operand:XF 1 "register_operand" "")))
4365 (clobber (match_dup 2))])]
4366 "TARGET_80387 && !TARGET_64BIT"
4367 "operands[2] = assign_386_stack_local (SFmode, 0);")
4368
4369 (define_insn "*truncxfsf2_1"
4370 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,f")
4371 (float_truncate:SF
4372 (match_operand:XF 1 "register_operand" "f,0")))
4373 (clobber (match_operand:SF 2 "memory_operand" "=m,m"))]
4374 "TARGET_80387 && !TARGET_64BIT"
4375 "*
4376 {
4377 switch (which_alternative)
4378 {
4379 case 0:
4380 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4381 return \"fstp%z0\\t%y0\";
4382 else
4383 return \"fst%z0\\t%y0\";
4384 case 1:
4385 return \"fstp%z2\\t%y2\;fld%z2\\t%y2\";
4386 }
4387 abort ();
4388 }"
4389 [(set_attr "type" "fmov,multi")
4390 (set_attr "mode" "SF")])
4391
4392 (define_insn "*truncxfsf2_2"
4393 [(set (match_operand:SF 0 "memory_operand" "=m")
4394 (float_truncate:SF
4395 (match_operand:XF 1 "register_operand" "f")))]
4396 "TARGET_80387 && !TARGET_64BIT"
4397 "*
4398 {
4399 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4400 return \"fstp%z0\\t%y0\";
4401 else
4402 return \"fst%z0\\t%y0\";
4403 }"
4404 [(set_attr "type" "fmov")
4405 (set_attr "mode" "SF")])
4406
4407 (define_split
4408 [(set (match_operand:SF 0 "memory_operand" "")
4409 (float_truncate:SF
4410 (match_operand:XF 1 "register_operand" "")))
4411 (clobber (match_operand:SF 2 "memory_operand" ""))]
4412 "TARGET_80387"
4413 [(set (match_dup 0) (float_truncate:SF (match_dup 1)))]
4414 "")
4415
4416 (define_split
4417 [(set (match_operand:SF 0 "register_operand" "")
4418 (float_truncate:SF
4419 (match_operand:XF 1 "register_operand" "")))
4420 (clobber (match_operand:SF 2 "memory_operand" ""))]
4421 "TARGET_80387 && reload_completed"
4422 [(set (match_dup 2) (float_truncate:SF (match_dup 1)))
4423 (set (match_dup 0) (match_dup 2))]
4424 "")
4425
4426 (define_expand "trunctfsf2"
4427 [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
4428 (float_truncate:SF
4429 (match_operand:TF 1 "register_operand" "")))
4430 (clobber (match_dup 2))])]
4431 "TARGET_80387"
4432 "operands[2] = assign_386_stack_local (SFmode, 0);")
4433
4434 (define_insn "*trunctfsf2_1"
4435 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,f")
4436 (float_truncate:SF
4437 (match_operand:TF 1 "register_operand" "f,0")))
4438 (clobber (match_operand:SF 2 "memory_operand" "=m,m"))]
4439 "TARGET_80387"
4440 "*
4441 {
4442 switch (which_alternative)
4443 {
4444 case 0:
4445 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4446 return \"fstp%z0\\t%y0\";
4447 else
4448 return \"fst%z0\\t%y0\";
4449 case 1:
4450 return \"fstp%z2\\t%y2\;fld%z2\\t%y2\";
4451 }
4452 abort ();
4453 }"
4454 [(set_attr "type" "fmov,multi")
4455 (set_attr "mode" "SF")])
4456
4457 (define_insn "*trunctfsf2_2"
4458 [(set (match_operand:SF 0 "nonimmediate_operand" "=m")
4459 (float_truncate:SF
4460 (match_operand:TF 1 "register_operand" "f")))]
4461 "TARGET_80387"
4462 "*
4463 {
4464 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4465 return \"fstp%z0\\t%y0\";
4466 else
4467 return \"fst%z0\\t%y0\";
4468 }"
4469 [(set_attr "type" "fmov")
4470 (set_attr "mode" "SF")])
4471
4472 (define_split
4473 [(set (match_operand:SF 0 "memory_operand" "")
4474 (float_truncate:SF
4475 (match_operand:TF 1 "register_operand" "")))
4476 (clobber (match_operand:SF 2 "memory_operand" ""))]
4477 "TARGET_80387"
4478 [(set (match_dup 0) (float_truncate:SF (match_dup 1)))]
4479 "")
4480
4481 (define_split
4482 [(set (match_operand:SF 0 "register_operand" "")
4483 (float_truncate:SF
4484 (match_operand:TF 1 "register_operand" "")))
4485 (clobber (match_operand:SF 2 "memory_operand" ""))]
4486 "TARGET_80387 && reload_completed"
4487 [(set (match_dup 2) (float_truncate:SF (match_dup 1)))
4488 (set (match_dup 0) (match_dup 2))]
4489 "")
4490
4491
4492 (define_expand "truncxfdf2"
4493 [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
4494 (float_truncate:DF
4495 (match_operand:XF 1 "register_operand" "")))
4496 (clobber (match_dup 2))])]
4497 "TARGET_80387 && !TARGET_64BIT"
4498 "operands[2] = assign_386_stack_local (DFmode, 0);")
4499
4500 (define_insn "*truncxfdf2_1"
4501 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,f")
4502 (float_truncate:DF
4503 (match_operand:XF 1 "register_operand" "f,0")))
4504 (clobber (match_operand:DF 2 "memory_operand" "=m,m"))]
4505 "TARGET_80387 && !TARGET_64BIT"
4506 "*
4507 {
4508 switch (which_alternative)
4509 {
4510 case 0:
4511 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4512 return \"fstp%z0\\t%y0\";
4513 else
4514 return \"fst%z0\\t%y0\";
4515 case 1:
4516 return \"fstp%z2\\t%y2\;fld%z2\\t%y2\";
4517 }
4518 abort ();
4519 }"
4520 [(set_attr "type" "fmov,multi")
4521 (set_attr "mode" "DF")])
4522
4523 (define_insn "*truncxfdf2_2"
4524 [(set (match_operand:DF 0 "memory_operand" "=m")
4525 (float_truncate:DF
4526 (match_operand:XF 1 "register_operand" "f")))]
4527 "TARGET_80387 && !TARGET_64BIT"
4528 "*
4529 {
4530 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4531 return \"fstp%z0\\t%y0\";
4532 else
4533 return \"fst%z0\\t%y0\";
4534 }"
4535 [(set_attr "type" "fmov")
4536 (set_attr "mode" "DF")])
4537
4538 (define_split
4539 [(set (match_operand:DF 0 "memory_operand" "")
4540 (float_truncate:DF
4541 (match_operand:XF 1 "register_operand" "")))
4542 (clobber (match_operand:DF 2 "memory_operand" ""))]
4543 "TARGET_80387"
4544 [(set (match_dup 0) (float_truncate:DF (match_dup 1)))]
4545 "")
4546
4547 (define_split
4548 [(set (match_operand:DF 0 "register_operand" "")
4549 (float_truncate:DF
4550 (match_operand:XF 1 "register_operand" "")))
4551 (clobber (match_operand:DF 2 "memory_operand" ""))]
4552 "TARGET_80387 && reload_completed"
4553 [(set (match_dup 2) (float_truncate:DF (match_dup 1)))
4554 (set (match_dup 0) (match_dup 2))]
4555 "")
4556
4557 (define_expand "trunctfdf2"
4558 [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
4559 (float_truncate:DF
4560 (match_operand:TF 1 "register_operand" "")))
4561 (clobber (match_dup 2))])]
4562 "TARGET_80387"
4563 "operands[2] = assign_386_stack_local (DFmode, 0);")
4564
4565 (define_insn "*trunctfdf2_1"
4566 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,f")
4567 (float_truncate:DF
4568 (match_operand:TF 1 "register_operand" "f,0")))
4569 (clobber (match_operand:DF 2 "memory_operand" "=m,m"))]
4570 "TARGET_80387"
4571 "*
4572 {
4573 switch (which_alternative)
4574 {
4575 case 0:
4576 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4577 return \"fstp%z0\\t%y0\";
4578 else
4579 return \"fst%z0\\t%y0\";
4580 case 1:
4581 return \"fstp%z2\\t%y2\;fld%z2\\t%y2\";
4582 }
4583 abort ();
4584 }"
4585 [(set_attr "type" "fmov,multi")
4586 (set_attr "mode" "DF")])
4587
4588 (define_insn "*trunctfdf2_2"
4589 [(set (match_operand:DF 0 "memory_operand" "=m")
4590 (float_truncate:DF
4591 (match_operand:TF 1 "register_operand" "f")))]
4592 "TARGET_80387"
4593 "*
4594 {
4595 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
4596 return \"fstp%z0\\t%y0\";
4597 else
4598 return \"fst%z0\\t%y0\";
4599 }"
4600 [(set_attr "type" "fmov")
4601 (set_attr "mode" "DF")])
4602
4603 (define_split
4604 [(set (match_operand:DF 0 "memory_operand" "")
4605 (float_truncate:DF
4606 (match_operand:TF 1 "register_operand" "")))
4607 (clobber (match_operand:DF 2 "memory_operand" ""))]
4608 "TARGET_80387"
4609 [(set (match_dup 0) (float_truncate:DF (match_dup 1)))]
4610 "")
4611
4612 (define_split
4613 [(set (match_operand:DF 0 "register_operand" "")
4614 (float_truncate:DF
4615 (match_operand:TF 1 "register_operand" "")))
4616 (clobber (match_operand:DF 2 "memory_operand" ""))]
4617 "TARGET_80387 && reload_completed"
4618 [(set (match_dup 2) (float_truncate:DF (match_dup 1)))
4619 (set (match_dup 0) (match_dup 2))]
4620 "")
4621
4622 \f
4623 ;; %%% Break up all these bad boys.
4624
4625 ;; Signed conversion to DImode.
4626
4627 (define_expand "fix_truncxfdi2"
4628 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4629 (fix:DI (match_operand:XF 1 "register_operand" "")))
4630 (clobber (match_dup 2))
4631 (clobber (match_dup 3))
4632 (clobber (match_scratch:SI 4 ""))
4633 (clobber (match_scratch:XF 5 ""))])]
4634 "TARGET_80387 && !TARGET_64BIT"
4635 "operands[2] = assign_386_stack_local (SImode, 0);
4636 operands[3] = assign_386_stack_local (DImode, 1);")
4637
4638 (define_expand "fix_trunctfdi2"
4639 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4640 (fix:DI (match_operand:TF 1 "register_operand" "")))
4641 (clobber (match_dup 2))
4642 (clobber (match_dup 3))
4643 (clobber (match_scratch:SI 4 ""))
4644 (clobber (match_scratch:TF 5 ""))])]
4645 "TARGET_80387"
4646 "operands[2] = assign_386_stack_local (SImode, 0);
4647 operands[3] = assign_386_stack_local (DImode, 1);")
4648
4649 (define_expand "fix_truncdfdi2"
4650 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4651 (fix:DI (match_operand:DF 1 "register_operand" "")))
4652 (clobber (match_dup 2))
4653 (clobber (match_dup 3))
4654 (clobber (match_scratch:SI 4 ""))
4655 (clobber (match_scratch:DF 5 ""))])]
4656 "TARGET_80387"
4657 "operands[2] = assign_386_stack_local (SImode, 0);
4658 operands[3] = assign_386_stack_local (DImode, 1);")
4659
4660 (define_expand "fix_truncsfdi2"
4661 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4662 (fix:DI (match_operand:SF 1 "register_operand" "")))
4663 (clobber (match_dup 2))
4664 (clobber (match_dup 3))
4665 (clobber (match_scratch:SI 4 ""))
4666 (clobber (match_scratch:SF 5 ""))])]
4667 "TARGET_80387"
4668 "operands[2] = assign_386_stack_local (SImode, 0);
4669 operands[3] = assign_386_stack_local (DImode, 1);")
4670
4671 (define_insn "*fix_truncdi_1"
4672 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4673 (fix:DI (match_operand 1 "register_operand" "f,f")))
4674 (clobber (match_operand:SI 2 "memory_operand" "=o,o"))
4675 (clobber (match_operand:DI 3 "memory_operand" "=m,m"))
4676 (clobber (match_scratch:SI 4 "=&r,&r"))
4677 (clobber (match_scratch 5 "=&f,&f"))]
4678 "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))"
4679 "* return output_fix_trunc (insn, operands);"
4680 [(set_attr "type" "multi")])
4681
4682 (define_split
4683 [(set (match_operand:DI 0 "register_operand" "")
4684 (fix:DI (match_operand 1 "register_operand" "")))
4685 (clobber (match_operand:SI 2 "memory_operand" ""))
4686 (clobber (match_operand:DI 3 "memory_operand" ""))
4687 (clobber (match_scratch:SI 4 ""))
4688 (clobber (match_scratch 5 ""))]
4689 "reload_completed && !reg_overlap_mentioned_p (operands[4], operands[3])"
4690 [(parallel [(set (match_dup 3) (fix:DI (match_dup 1)))
4691 (clobber (match_dup 2))
4692 (clobber (match_dup 3))
4693 (clobber (match_dup 4))
4694 (clobber (match_dup 5))])
4695 (set (match_dup 0) (match_dup 3))]
4696 "")
4697
4698 ;; Signed conversion to SImode.
4699
4700 (define_expand "fix_truncxfsi2"
4701 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4702 (fix:SI (match_operand:XF 1 "register_operand" "")))
4703 (clobber (match_dup 2))
4704 (clobber (match_dup 3))
4705 (clobber (match_scratch:SI 4 ""))])]
4706 "TARGET_80387 && !TARGET_64BIT"
4707 "operands[2] = assign_386_stack_local (SImode, 0);
4708 operands[3] = assign_386_stack_local (SImode, 1);")
4709
4710 (define_expand "fix_trunctfsi2"
4711 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4712 (fix:SI (match_operand:TF 1 "register_operand" "")))
4713 (clobber (match_dup 2))
4714 (clobber (match_dup 3))
4715 (clobber (match_scratch:SI 4 ""))])]
4716 "TARGET_80387"
4717 "operands[2] = assign_386_stack_local (SImode, 0);
4718 operands[3] = assign_386_stack_local (SImode, 1);")
4719
4720 (define_expand "fix_truncdfsi2"
4721 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4722 (fix:SI (match_operand:DF 1 "register_operand" "")))
4723 (clobber (match_dup 2))
4724 (clobber (match_dup 3))
4725 (clobber (match_scratch:SI 4 ""))])]
4726 "TARGET_80387 || TARGET_SSE2"
4727 "
4728 {
4729 if (TARGET_SSE2)
4730 {
4731 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4732 emit_insn (gen_fix_truncdfsi_sse (out, operands[1]));
4733 if (out != operands[0])
4734 emit_move_insn (operands[0], out);
4735 DONE;
4736 }
4737 else
4738 {
4739 operands[2] = assign_386_stack_local (SImode, 0);
4740 operands[3] = assign_386_stack_local (SImode, 1);
4741 }
4742 }")
4743
4744 (define_expand "fix_truncsfsi2"
4745 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4746 (fix:SI (match_operand:SF 1 "register_operand" "")))
4747 (clobber (match_dup 2))
4748 (clobber (match_dup 3))
4749 (clobber (match_scratch:SI 4 ""))])]
4750 "TARGET_80387 || TARGET_SSE"
4751 "
4752 {
4753 if (TARGET_SSE2)
4754 {
4755 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4756 emit_insn (gen_fix_truncdfsi_sse (out, operands[1]));
4757 if (out != operands[0])
4758 emit_move_insn (operands[0], out);
4759 DONE;
4760 }
4761 else
4762 {
4763 operands[2] = assign_386_stack_local (SImode, 0);
4764 operands[3] = assign_386_stack_local (SImode, 1);
4765 }
4766 }")
4767
4768 (define_insn "*fix_truncsi_1"
4769 [(set (match_operand:SI 0 "nonimmediate_operand" "=m,?r")
4770 (fix:SI (match_operand 1 "register_operand" "f,f")))
4771 (clobber (match_operand:SI 2 "memory_operand" "=o,o"))
4772 (clobber (match_operand:SI 3 "memory_operand" "=m,m"))
4773 (clobber (match_scratch:SI 4 "=&r,r"))]
4774 "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4775 && (!TARGET_SSE2 || !SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4776 "* return output_fix_trunc (insn, operands);"
4777 [(set_attr "type" "multi")])
4778
4779 ;; When SSE available, it is always faster to use it!
4780 (define_insn "fix_truncsfsi_sse"
4781 [(set (match_operand:SI 0 "register_operand" "=r")
4782 (fix:SI (match_operand:SF 1 "nonimmediate_operand" "xm")))]
4783 "TARGET_SSE"
4784 "cvttss2si\\t{%1, %0|%0, %1}"
4785 [(set_attr "type" "sse")])
4786
4787 (define_insn "fix_truncdfsi_sse"
4788 [(set (match_operand:SI 0 "register_operand" "=r")
4789 (fix:SI (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
4790 "TARGET_SSE2"
4791 "cvttsd2si\\t{%1, %0|%0, %1}"
4792 [(set_attr "type" "sse")])
4793
4794 (define_split
4795 [(set (match_operand:SI 0 "register_operand" "")
4796 (fix:SI (match_operand 1 "register_operand" "")))
4797 (clobber (match_operand:SI 2 "memory_operand" ""))
4798 (clobber (match_operand:SI 3 "memory_operand" ""))
4799 (clobber (match_scratch:SI 4 ""))]
4800 "reload_completed"
4801 [(parallel [(set (match_dup 3) (fix:SI (match_dup 1)))
4802 (clobber (match_dup 2))
4803 (clobber (match_dup 3))
4804 (clobber (match_dup 4))])
4805 (set (match_dup 0) (match_dup 3))]
4806 "")
4807
4808 ;; Signed conversion to HImode.
4809
4810 (define_expand "fix_truncxfhi2"
4811 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4812 (fix:HI (match_operand:XF 1 "register_operand" "")))
4813 (clobber (match_dup 2))
4814 (clobber (match_dup 3))
4815 (clobber (match_scratch:SI 4 ""))])]
4816 "TARGET_80387 && !TARGET_64BIT"
4817 "operands[2] = assign_386_stack_local (SImode, 0);
4818 operands[3] = assign_386_stack_local (HImode, 1);")
4819
4820 (define_expand "fix_trunctfhi2"
4821 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4822 (fix:HI (match_operand:TF 1 "register_operand" "")))
4823 (clobber (match_dup 2))
4824 (clobber (match_dup 3))
4825 (clobber (match_scratch:SI 4 ""))])]
4826 "TARGET_80387"
4827 "operands[2] = assign_386_stack_local (SImode, 0);
4828 operands[3] = assign_386_stack_local (HImode, 1);")
4829
4830 (define_expand "fix_truncdfhi2"
4831 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4832 (fix:HI (match_operand:DF 1 "register_operand" "")))
4833 (clobber (match_dup 2))
4834 (clobber (match_dup 3))
4835 (clobber (match_scratch:SI 4 ""))])]
4836 "TARGET_80387 && !TARGET_SSE2"
4837 "operands[2] = assign_386_stack_local (SImode, 0);
4838 operands[3] = assign_386_stack_local (HImode, 1);")
4839
4840 (define_expand "fix_truncsfhi2"
4841 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4842 (fix:HI (match_operand:SF 1 "register_operand" "")))
4843 (clobber (match_dup 2))
4844 (clobber (match_dup 3))
4845 (clobber (match_scratch:SI 4 ""))])]
4846 "TARGET_80387 && !TARGET_SSE"
4847 "operands[2] = assign_386_stack_local (SImode, 0);
4848 operands[3] = assign_386_stack_local (HImode, 1);")
4849
4850 (define_insn "*fix_trunchi_1"
4851 [(set (match_operand:HI 0 "nonimmediate_operand" "=m,?r")
4852 (fix:HI (match_operand 1 "register_operand" "f,f")))
4853 (clobber (match_operand:SI 2 "memory_operand" "=o,o"))
4854 (clobber (match_operand:HI 3 "memory_operand" "=m,m"))
4855 (clobber (match_scratch:SI 4 "=&r,r"))]
4856 "TARGET_80387 && FLOAT_MODE_P (GET_MODE (operands[1]))
4857 && (TARGET_SSE2 || !SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4858 "* return output_fix_trunc (insn, operands);"
4859 [(set_attr "type" "multi")])
4860
4861 (define_split
4862 [(set (match_operand:HI 0 "register_operand" "")
4863 (fix:HI (match_operand 1 "register_operand" "")))
4864 (clobber (match_operand:SI 2 "memory_operand" ""))
4865 (clobber (match_operand:HI 3 "memory_operand" ""))
4866 (clobber (match_scratch:SI 4 ""))]
4867 "reload_completed"
4868 [(parallel [(set (match_dup 3) (fix:HI (match_dup 1)))
4869 (clobber (match_dup 2))
4870 (clobber (match_dup 3))
4871 (clobber (match_dup 4))])
4872 (set (match_dup 0) (match_dup 3))]
4873 "")
4874
4875 ;; %%% Kill these when reload knows how to do it.
4876 (define_split
4877 [(set (match_operand 0 "register_operand" "")
4878 (fix (match_operand 1 "register_operand" "")))]
4879 "reload_completed && FLOAT_MODE_P (GET_MODE (operands[1]))
4880 && FP_REG_P (operands[1])"
4881 [(const_int 0)]
4882 "
4883 {
4884 operands[2] = ix86_force_to_memory (GET_MODE (operands[0]), operands[0]);
4885 operands[2] = gen_rtx_FIX (GET_MODE (operands[2]), operands[1]);
4886 emit_insn (gen_rtx_SET (VOIDmode, operands[2], operands[1]));
4887 emit_move_insn (operands[0], operands[2]);
4888 ix86_free_from_memory (GET_MODE (operands[0]));
4889 DONE;
4890 }")
4891
4892 ;; %% Not used yet.
4893 (define_insn "x86_fnstcw_1"
4894 [(set (match_operand:HI 0 "memory_operand" "=m")
4895 (unspec:HI [(reg:HI 18)] 11))]
4896 "TARGET_80387"
4897 "fnstcw\\t%0"
4898 [(set_attr "length" "2")
4899 (set_attr "mode" "HI")
4900 (set_attr "i387" "1")
4901 (set_attr "ppro_uops" "few")])
4902
4903 (define_insn "x86_fldcw_1"
4904 [(set (reg:HI 18)
4905 (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] 12))]
4906 "TARGET_80387"
4907 "fldcw\\t%0"
4908 [(set_attr "length" "2")
4909 (set_attr "mode" "HI")
4910 (set_attr "i387" "1")
4911 (set_attr "athlon_decode" "vector")
4912 (set_attr "ppro_uops" "few")])
4913 \f
4914 ;; Conversion between fixed point and floating point.
4915
4916 ;; Even though we only accept memory inputs, the backend _really_
4917 ;; wants to be able to do this between registers.
4918
4919 (define_insn "floathisf2"
4920 [(set (match_operand:SF 0 "register_operand" "=f,f")
4921 (float:SF (match_operand:HI 1 "nonimmediate_operand" "m,r")))]
4922 "TARGET_80387 && !TARGET_SSE"
4923 "@
4924 fild%z1\\t%1
4925 #"
4926 [(set_attr "type" "fmov,multi")
4927 (set_attr "mode" "SF")
4928 (set_attr "fp_int_src" "true")])
4929
4930 (define_expand "floatsisf2"
4931 [(set (match_operand:SF 0 "register_operand" "")
4932 (float:SF (match_operand:SI 1 "nonimmediate_operand" "")))]
4933 "TARGET_SSE || TARGET_80387"
4934 "")
4935
4936 (define_insn "*floatsisf2_i387"
4937 [(set (match_operand:SF 0 "register_operand" "=f,?f,x")
4938 (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,r,mr")))]
4939 "TARGET_80387 && (!TARGET_SSE || TARGET_MIX_SSE_I387)"
4940 "@
4941 fild%z1\\t%1
4942 #
4943 cvtsi2ss\\t{%1, %0|%0, %1}"
4944 [(set_attr "type" "fmov,multi,sse")
4945 (set_attr "mode" "SF")
4946 (set_attr "fp_int_src" "true")])
4947
4948 (define_insn "*floatsisf2_sse"
4949 [(set (match_operand:SF 0 "register_operand" "=x")
4950 (float:SF (match_operand:SI 1 "nonimmediate_operand" "mr")))]
4951 "TARGET_80387 && TARGET_SSE"
4952 "cvtsi2ss\\t{%1, %0|%0, %1}"
4953 [(set_attr "type" "sse")
4954 (set_attr "mode" "SF")
4955 (set_attr "fp_int_src" "true")])
4956
4957 (define_insn "floatdisf2"
4958 [(set (match_operand:SF 0 "register_operand" "=f,f")
4959 (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,r")))]
4960 "TARGET_80387"
4961 "@
4962 fild%z1\\t%1
4963 #"
4964 [(set_attr "type" "fmov,multi")
4965 (set_attr "mode" "SF")
4966 (set_attr "fp_int_src" "true")])
4967
4968 (define_insn "floathidf2"
4969 [(set (match_operand:DF 0 "register_operand" "=f,f")
4970 (float:DF (match_operand:HI 1 "nonimmediate_operand" "m,r")))]
4971 "TARGET_80387 && !TARGET_SSE2"
4972 "@
4973 fild%z1\\t%1
4974 #"
4975 [(set_attr "type" "fmov,multi")
4976 (set_attr "mode" "DF")
4977 (set_attr "fp_int_src" "true")])
4978
4979 (define_expand "floatsidf2"
4980 [(set (match_operand:DF 0 "register_operand" "")
4981 (float:DF (match_operand:SI 1 "nonimmediate_operand" "")))]
4982 ""
4983 "")
4984
4985 (define_insn "*floatsidf2_i387"
4986 [(set (match_operand:DF 0 "register_operand" "=f,?f,Y")
4987 (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,r,mr")))]
4988 "TARGET_80387 && (!TARGET_SSE2 || TARGET_MIX_SSE_I387)"
4989 "@
4990 fild%z1\\t%1
4991 #
4992 cvtsi2sd\\t{%1, %0|%0, %1}"
4993 [(set_attr "type" "fmov,multi,sse")
4994 (set_attr "mode" "DF")
4995 (set_attr "fp_int_src" "true")])
4996
4997 (define_insn "*floatsidf2_sse"
4998 [(set (match_operand:DF 0 "register_operand" "=Y")
4999 (float:DF (match_operand:SI 1 "nonimmediate_operand" "mr")))]
5000 "TARGET_SSE2"
5001 "cvtsi2sd\\t{%1, %0|%0, %1}"
5002 [(set_attr "type" "sse")
5003 (set_attr "mode" "DF")
5004 (set_attr "fp_int_src" "true")])
5005
5006 (define_insn "floatdidf2"
5007 [(set (match_operand:DF 0 "register_operand" "=f,f")
5008 (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,r")))]
5009 "TARGET_80387 && TARGET_SSE2"
5010 "@
5011 fild%z1\\t%1
5012 #"
5013 [(set_attr "type" "fmov,multi")
5014 (set_attr "mode" "DF")
5015 (set_attr "fp_int_src" "true")])
5016
5017 (define_insn "floathixf2"
5018 [(set (match_operand:XF 0 "register_operand" "=f,f")
5019 (float:XF (match_operand:HI 1 "nonimmediate_operand" "m,r")))]
5020 "TARGET_80387 && !TARGET_64BIT"
5021 "@
5022 fild%z1\\t%1
5023 #"
5024 [(set_attr "type" "fmov,multi")
5025 (set_attr "mode" "XF")
5026 (set_attr "fp_int_src" "true")])
5027
5028 (define_insn "floathitf2"
5029 [(set (match_operand:TF 0 "register_operand" "=f,f")
5030 (float:TF (match_operand:HI 1 "nonimmediate_operand" "m,r")))]
5031 "TARGET_80387"
5032 "@
5033 fild%z1\\t%1
5034 #"
5035 [(set_attr "type" "fmov,multi")
5036 (set_attr "mode" "XF")
5037 (set_attr "fp_int_src" "true")])
5038
5039 (define_insn "floatsixf2"
5040 [(set (match_operand:XF 0 "register_operand" "=f,f")
5041 (float:XF (match_operand:SI 1 "nonimmediate_operand" "m,r")))]
5042 "TARGET_80387 && !TARGET_64BIT"
5043 "@
5044 fild%z1\\t%1
5045 #"
5046 [(set_attr "type" "fmov,multi")
5047 (set_attr "mode" "XF")
5048 (set_attr "fp_int_src" "true")])
5049
5050 (define_insn "floatsitf2"
5051 [(set (match_operand:TF 0 "register_operand" "=f,f")
5052 (float:TF (match_operand:SI 1 "nonimmediate_operand" "m,r")))]
5053 "TARGET_80387"
5054 "@
5055 fild%z1\\t%1
5056 #"
5057 [(set_attr "type" "fmov,multi")
5058 (set_attr "mode" "XF")
5059 (set_attr "fp_int_src" "true")])
5060
5061 (define_insn "floatdixf2"
5062 [(set (match_operand:XF 0 "register_operand" "=f,f")
5063 (float:XF (match_operand:DI 1 "nonimmediate_operand" "m,r")))]
5064 "TARGET_80387 && !TARGET_64BIT"
5065 "@
5066 fild%z1\\t%1
5067 #"
5068 [(set_attr "type" "fmov,multi")
5069 (set_attr "mode" "XF")
5070 (set_attr "fp_int_src" "true")])
5071
5072 (define_insn "floatditf2"
5073 [(set (match_operand:TF 0 "register_operand" "=f,f")
5074 (float:TF (match_operand:DI 1 "nonimmediate_operand" "m,r")))]
5075 "TARGET_80387"
5076 "@
5077 fild%z1\\t%1
5078 #"
5079 [(set_attr "type" "fmov,multi")
5080 (set_attr "mode" "XF")
5081 (set_attr "fp_int_src" "true")])
5082
5083 ;; %%% Kill these when reload knows how to do it.
5084 (define_split
5085 [(set (match_operand 0 "register_operand" "")
5086 (float (match_operand 1 "register_operand" "")))]
5087 "reload_completed && FLOAT_MODE_P (GET_MODE (operands[0]))
5088 && FP_REG_P (operands[0])"
5089 [(const_int 0)]
5090 "
5091 {
5092 operands[2] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
5093 operands[2] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[2]);
5094 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[2]));
5095 ix86_free_from_memory (GET_MODE (operands[1]));
5096 DONE;
5097 }")
5098 \f
5099 ;; Add instructions
5100
5101 ;; %%% define_expand from the very first?
5102 ;; %%% splits for addsidi3
5103 ; [(set (match_operand:DI 0 "nonimmediate_operand" "")
5104 ; (plus:DI (match_operand:DI 1 "general_operand" "")
5105 ; (zero_extend:DI (match_operand:SI 2 "general_operand" ""))))]
5106
5107 (define_insn "adddi3"
5108 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
5109 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5110 (match_operand:DI 2 "general_operand" "roiF,riF")))
5111 (clobber (reg:CC 17))]
5112 ""
5113 "#")
5114
5115 (define_split
5116 [(set (match_operand:DI 0 "nonimmediate_operand" "")
5117 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
5118 (match_operand:DI 2 "general_operand" "")))
5119 (clobber (reg:CC 17))]
5120 "reload_completed && !TARGET_64BIT"
5121 [(parallel [(set (reg:CC 17) (unspec:CC [(match_dup 1) (match_dup 2)] 12))
5122 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))])
5123 (parallel [(set (match_dup 3)
5124 (plus:SI (plus:SI (ltu:SI (reg:CC 17) (const_int 0))
5125 (match_dup 4))
5126 (match_dup 5)))
5127 (clobber (reg:CC 17))])]
5128 "split_di (operands+0, 1, operands+0, operands+3);
5129 split_di (operands+1, 1, operands+1, operands+4);
5130 split_di (operands+2, 1, operands+2, operands+5);")
5131
5132 (define_insn "*addsi3_carry"
5133 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
5134 (plus:SI (plus:SI (ltu:SI (reg:CC 17) (const_int 0))
5135 (match_operand:SI 1 "nonimmediate_operand" "%0,0"))
5136 (match_operand:SI 2 "general_operand" "ri,rm")))
5137 (clobber (reg:CC 17))]
5138 "ix86_binary_operator_ok (PLUS, SImode, operands)"
5139 "adc{l}\\t{%2, %0|%0, %2}"
5140 [(set_attr "type" "alu")
5141 (set_attr "pent_pair" "pu")
5142 (set_attr "mode" "SI")
5143 (set_attr "ppro_uops" "few")])
5144
5145 (define_insn "*addsi3_cc"
5146 [(set (reg:CC 17) (unspec:CC [(match_operand:SI 1 "nonimmediate_operand" "%0,0")
5147 (match_operand:SI 2 "general_operand" "ri,rm")] 12))
5148 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
5149 (plus:SI (match_dup 1) (match_dup 2)))]
5150 "ix86_binary_operator_ok (PLUS, SImode, operands)"
5151 "add{l}\\t{%2, %0|%0, %2}"
5152 [(set_attr "type" "alu")
5153 (set_attr "mode" "SI")])
5154
5155 (define_insn "addqi3_cc"
5156 [(set (reg:CC 17) (unspec:CC [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
5157 (match_operand:QI 2 "general_operand" "qi,qm")] 12))
5158 (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
5159 (plus:QI (match_dup 1) (match_dup 2)))]
5160 "ix86_binary_operator_ok (PLUS, QImode, operands)"
5161 "add{b}\\t{%2, %0|%0, %2}"
5162 [(set_attr "type" "alu")
5163 (set_attr "mode" "QI")])
5164
5165 (define_expand "addsi3"
5166 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
5167 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
5168 (match_operand:SI 2 "general_operand" "")))
5169 (clobber (reg:CC 17))])]
5170 ""
5171 "ix86_expand_binary_operator (PLUS, SImode, operands); DONE;")
5172
5173 (define_insn "*lea_0"
5174 [(set (match_operand:SI 0 "register_operand" "=r")
5175 (match_operand:SI 1 "address_operand" "p"))]
5176 ""
5177 "lea{l}\\t{%a1, %0|%0, %a1}"
5178 [(set_attr "type" "lea")
5179 (set_attr "mode" "SI")])
5180
5181 ;; The lea patterns for non-Pmodes needs to be matched by several
5182 ;; insns converted to real lea by splitters.
5183
5184 (define_insn_and_split "*lea_general_1"
5185 [(set (match_operand 0 "register_operand" "=r")
5186 (plus (plus (match_operand 1 "register_operand" "r")
5187 (match_operand 2 "register_operand" "r"))
5188 (match_operand 3 "immediate_operand" "i")))]
5189 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
5190 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5191 && GET_MODE (operands[0]) == GET_MODE (operands[1])
5192 && GET_MODE (operands[0]) == GET_MODE (operands[2])
5193 && (GET_MODE (operands[0]) == GET_MODE (operands[3])
5194 || GET_MODE (operands[3]) == VOIDmode)"
5195 "#"
5196 "&& reload_completed"
5197 [(const_int 0)]
5198 "
5199 {
5200 rtx pat;
5201 operands[0] = gen_lowpart (SImode, operands[0]);
5202 operands[1] = gen_lowpart (Pmode, operands[1]);
5203 operands[2] = gen_lowpart (Pmode, operands[2]);
5204 operands[3] = gen_lowpart (Pmode, operands[3]);
5205 pat = gen_rtx_PLUS (Pmode, gen_rtx_PLUS (Pmode, operands[1], operands[2]),
5206 operands[3]);
5207 if (Pmode != SImode)
5208 pat = gen_rtx_SUBREG (SImode, pat, 0);
5209 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5210 DONE;
5211 }"
5212 [(set_attr "type" "lea")
5213 (set_attr "mode" "SI")])
5214
5215 (define_insn_and_split "*lea_general_2"
5216 [(set (match_operand 0 "register_operand" "=r")
5217 (plus (mult (match_operand 1 "register_operand" "r")
5218 (match_operand 2 "const248_operand" "i"))
5219 (match_operand 3 "nonmemory_operand" "ri")))]
5220 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
5221 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5222 && GET_MODE (operands[0]) == GET_MODE (operands[1])
5223 && (GET_MODE (operands[0]) == GET_MODE (operands[3])
5224 || GET_MODE (operands[3]) == VOIDmode)"
5225 "#"
5226 "&& reload_completed"
5227 [(const_int 0)]
5228 "
5229 {
5230 rtx pat;
5231 operands[0] = gen_lowpart (SImode, operands[0]);
5232 operands[1] = gen_lowpart (Pmode, operands[1]);
5233 operands[3] = gen_lowpart (Pmode, operands[3]);
5234 pat = gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], operands[2]),
5235 operands[3]);
5236 if (Pmode != SImode)
5237 pat = gen_rtx_SUBREG (SImode, pat, 0);
5238 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5239 DONE;
5240 }"
5241 [(set_attr "type" "lea")
5242 (set_attr "mode" "SI")])
5243
5244 (define_insn_and_split "*lea_general_3"
5245 [(set (match_operand 0 "register_operand" "=r")
5246 (plus (plus (mult (match_operand 1 "register_operand" "r")
5247 (match_operand 2 "const248_operand" "i"))
5248 (match_operand 3 "register_operand" "r"))
5249 (match_operand 4 "immediate_operand" "i")))]
5250 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode)
5251 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5252 && GET_MODE (operands[0]) == GET_MODE (operands[1])
5253 && GET_MODE (operands[0]) == GET_MODE (operands[3])"
5254 "#"
5255 "&& reload_completed"
5256 [(const_int 0)]
5257 "
5258 {
5259 rtx pat;
5260 operands[0] = gen_lowpart (SImode, operands[0]);
5261 operands[1] = gen_lowpart (Pmode, operands[1]);
5262 operands[3] = gen_lowpart (Pmode, operands[3]);
5263 operands[4] = gen_lowpart (Pmode, operands[4]);
5264 pat = gen_rtx_PLUS (Pmode,
5265 gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1],
5266 operands[2]),
5267 operands[3]),
5268 operands[4]);
5269 if (Pmode != SImode)
5270 pat = gen_rtx_SUBREG (SImode, pat, 0);
5271 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5272 DONE;
5273 }"
5274 [(set_attr "type" "lea")
5275 (set_attr "mode" "SI")])
5276
5277 (define_insn "*addsi_1"
5278 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,rm,r")
5279 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,r")
5280 (match_operand:SI 2 "general_operand" "rmni,rni,rni")))
5281 (clobber (reg:CC 17))]
5282 "ix86_binary_operator_ok (PLUS, SImode, operands)"
5283 "*
5284 {
5285 switch (get_attr_type (insn))
5286 {
5287 case TYPE_LEA:
5288 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5289 return \"lea{l}\\t{%a2, %0|%0, %a2}\";
5290
5291 case TYPE_INCDEC:
5292 if (! rtx_equal_p (operands[0], operands[1]))
5293 abort ();
5294 if (operands[2] == const1_rtx)
5295 return \"inc{l}\\t%0\";
5296 else if (operands[2] == constm1_rtx)
5297 return \"dec{l}\\t%0\";
5298 else
5299 abort();
5300
5301 default:
5302 if (! rtx_equal_p (operands[0], operands[1]))
5303 abort ();
5304
5305 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5306 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5307 if (GET_CODE (operands[2]) == CONST_INT
5308 && (INTVAL (operands[2]) == 128
5309 || (INTVAL (operands[2]) < 0
5310 && INTVAL (operands[2]) != -128)))
5311 {
5312 operands[2] = GEN_INT (-INTVAL (operands[2]));
5313 return \"sub{l}\\t{%2, %0|%0, %2}\";
5314 }
5315 return \"add{l}\\t{%2, %0|%0, %2}\";
5316 }
5317 }"
5318 [(set (attr "type")
5319 (cond [(eq_attr "alternative" "2")
5320 (const_string "lea")
5321 ; Current assemblers are broken and do not allow @GOTOFF in
5322 ; ought but a memory context.
5323 (match_operand:SI 2 "pic_symbolic_operand" "")
5324 (const_string "lea")
5325 (match_operand:SI 2 "incdec_operand" "")
5326 (const_string "incdec")
5327 ]
5328 (const_string "alu")))
5329 (set_attr "mode" "SI")])
5330
5331 ;; Convert lea to the lea pattern to avoid flags dependency.
5332 (define_split
5333 [(set (match_operand 0 "register_operand" "")
5334 (plus (match_operand 1 "register_operand" "")
5335 (match_operand 2 "nonmemory_operand" "")))
5336 (clobber (reg:CC 17))]
5337 "reload_completed
5338 && true_regnum (operands[0]) != true_regnum (operands[1])"
5339 [(const_int 0)]
5340 "
5341 {
5342 rtx pat;
5343 /* In -fPIC mode the constructs like (const (unspec [symbol_ref]))
5344 may confuse gen_lowpart. */
5345 if (GET_MODE (operands[0]) != Pmode)
5346 {
5347 operands[1] = gen_lowpart (Pmode, operands[1]);
5348 operands[2] = gen_lowpart (Pmode, operands[2]);
5349 }
5350 operands[0] = gen_lowpart (SImode, operands[0]);
5351 pat = gen_rtx_PLUS (Pmode, operands[1], operands[2]);
5352 if (Pmode != SImode)
5353 pat = gen_rtx_SUBREG (SImode, pat, 0);
5354 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5355 DONE;
5356 }")
5357
5358 (define_insn "*addsi_2"
5359 [(set (reg 17)
5360 (compare
5361 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
5362 (match_operand:SI 2 "general_operand" "rmni,rni"))
5363 (const_int 0)))
5364 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
5365 (plus:SI (match_dup 1) (match_dup 2)))]
5366 "ix86_match_ccmode (insn, CCGOCmode)
5367 && ix86_binary_operator_ok (PLUS, SImode, operands)
5368 /* Current assemblers are broken and do not allow @GOTOFF in
5369 ought but a memory context. */
5370 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5371 "*
5372 {
5373 switch (get_attr_type (insn))
5374 {
5375 case TYPE_INCDEC:
5376 if (! rtx_equal_p (operands[0], operands[1]))
5377 abort ();
5378 if (operands[2] == const1_rtx)
5379 return \"inc{l}\\t%0\";
5380 else if (operands[2] == constm1_rtx)
5381 return \"dec{l}\\t%0\";
5382 else
5383 abort();
5384
5385 default:
5386 if (! rtx_equal_p (operands[0], operands[1]))
5387 abort ();
5388 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5389 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5390 if (GET_CODE (operands[2]) == CONST_INT
5391 && (INTVAL (operands[2]) == 128
5392 || (INTVAL (operands[2]) < 0
5393 && INTVAL (operands[2]) != -128)))
5394 {
5395 operands[2] = GEN_INT (-INTVAL (operands[2]));
5396 return \"sub{l}\\t{%2, %0|%0, %2}\";
5397 }
5398 return \"add{l}\\t{%2, %0|%0, %2}\";
5399 }
5400 }"
5401 [(set (attr "type")
5402 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5403 (const_string "incdec")
5404 (const_string "alu")))
5405 (set_attr "mode" "SI")])
5406
5407 (define_insn "*addsi_3"
5408 [(set (reg 17)
5409 (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5410 (match_operand:SI 1 "nonimmediate_operand" "%0")))
5411 (clobber (match_scratch:SI 0 "=r"))]
5412 "ix86_match_ccmode (insn, CCZmode)
5413 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5414 /* Current assemblers are broken and do not allow @GOTOFF in
5415 ought but a memory context. */
5416 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5417 "*
5418 {
5419 switch (get_attr_type (insn))
5420 {
5421 case TYPE_INCDEC:
5422 if (! rtx_equal_p (operands[0], operands[1]))
5423 abort ();
5424 if (operands[2] == const1_rtx)
5425 return \"inc{l}\\t%0\";
5426 else if (operands[2] == constm1_rtx)
5427 return \"dec{l}\\t%0\";
5428 else
5429 abort();
5430
5431 default:
5432 if (! rtx_equal_p (operands[0], operands[1]))
5433 abort ();
5434 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5435 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5436 if (GET_CODE (operands[2]) == CONST_INT
5437 && (INTVAL (operands[2]) == 128
5438 || (INTVAL (operands[2]) < 0
5439 && INTVAL (operands[2]) != -128)))
5440 {
5441 operands[2] = GEN_INT (-INTVAL (operands[2]));
5442 return \"sub{l}\\t{%2, %0|%0, %2}\";
5443 }
5444 return \"add{l}\\t{%2, %0|%0, %2}\";
5445 }
5446 }"
5447 [(set (attr "type")
5448 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5449 (const_string "incdec")
5450 (const_string "alu")))
5451 (set_attr "mode" "SI")])
5452
5453 ; For comparisons agains 1, -1 and 128, we may generate better code
5454 ; by converting cmp to add, inc or dec as done by peephole2. This pattern
5455 ; is matched then. We can't accept general immediate, because for
5456 ; case of overflows, the result is messed up.
5457 ; This pattern also don't hold of 0x80000000, since the value overflows
5458 ; when negated.
5459 ; Also carry flag is reversed compared to cmp, so this converison is valid
5460 ; only for comparisons not depending on it.
5461 (define_insn "*addsi_4"
5462 [(set (reg 17)
5463 (compare (match_operand:SI 1 "nonimmediate_operand" "0")
5464 (match_operand:SI 2 "const_int_operand" "n")))
5465 (clobber (match_scratch:SI 0 "=rm"))]
5466 "ix86_match_ccmode (insn, CCGCmode)
5467 && (INTVAL (operands[2]) & 0xffffffff) != 0x80000000"
5468 "*
5469 {
5470 switch (get_attr_type (insn))
5471 {
5472 case TYPE_INCDEC:
5473 if (operands[2] == constm1_rtx)
5474 return \"inc{l}\\t%0\";
5475 else if (operands[2] == const1_rtx)
5476 return \"dec{l}\\t%0\";
5477 else
5478 abort();
5479
5480 default:
5481 if (! rtx_equal_p (operands[0], operands[1]))
5482 abort ();
5483 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5484 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5485 if ((INTVAL (operands[2]) == -128
5486 || (INTVAL (operands[2]) > 0
5487 && INTVAL (operands[2]) != 128)))
5488 return \"sub{l}\\t{%2, %0|%0, %2}\";
5489 operands[2] = GEN_INT (-INTVAL (operands[2]));
5490 return \"add{l}\\t{%2, %0|%0, %2}\";
5491 }
5492 }"
5493 [(set (attr "type")
5494 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5495 (const_string "incdec")
5496 (const_string "alu")))
5497 (set_attr "mode" "SI")])
5498
5499 (define_insn "*addsi_5"
5500 [(set (reg 17)
5501 (compare
5502 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5503 (match_operand:SI 2 "general_operand" "rmni"))
5504 (const_int 0)))
5505 (clobber (match_scratch:SI 0 "=r"))]
5506 "ix86_match_ccmode (insn, CCGOCmode)
5507 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5508 /* Current assemblers are broken and do not allow @GOTOFF in
5509 ought but a memory context. */
5510 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5511 "*
5512 {
5513 switch (get_attr_type (insn))
5514 {
5515 case TYPE_INCDEC:
5516 if (! rtx_equal_p (operands[0], operands[1]))
5517 abort ();
5518 if (operands[2] == const1_rtx)
5519 return \"inc{l}\\t%0\";
5520 else if (operands[2] == constm1_rtx)
5521 return \"dec{l}\\t%0\";
5522 else
5523 abort();
5524
5525 default:
5526 if (! rtx_equal_p (operands[0], operands[1]))
5527 abort ();
5528 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5529 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5530 if (GET_CODE (operands[2]) == CONST_INT
5531 && (INTVAL (operands[2]) == 128
5532 || (INTVAL (operands[2]) < 0
5533 && INTVAL (operands[2]) != -128)))
5534 {
5535 operands[2] = GEN_INT (-INTVAL (operands[2]));
5536 return \"sub{l}\\t{%2, %0|%0, %2}\";
5537 }
5538 return \"add{l}\\t{%2, %0|%0, %2}\";
5539 }
5540 }"
5541 [(set (attr "type")
5542 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5543 (const_string "incdec")
5544 (const_string "alu")))
5545 (set_attr "mode" "SI")])
5546
5547 (define_expand "addhi3"
5548 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
5549 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "")
5550 (match_operand:HI 2 "general_operand" "")))
5551 (clobber (reg:CC 17))])]
5552 "TARGET_HIMODE_MATH"
5553 "ix86_expand_binary_operator (PLUS, HImode, operands); DONE;")
5554
5555 ;; %%% After Dave's SUBREG_BYTE stuff goes in, re-enable incb %ah
5556 ;; type optimizations enabled by define-splits. This is not important
5557 ;; for PII, and in fact harmful because of partial register stalls.
5558
5559 (define_insn "*addhi_1_lea"
5560 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
5561 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r")
5562 (match_operand:HI 2 "general_operand" "ri,rm,rni")))
5563 (clobber (reg:CC 17))]
5564 "!TARGET_PARTIAL_REG_STALL
5565 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5566 "*
5567 {
5568 switch (get_attr_type (insn))
5569 {
5570 case TYPE_LEA:
5571 return \"#\";
5572 case TYPE_INCDEC:
5573 if (operands[2] == const1_rtx)
5574 return \"inc{w}\\t%0\";
5575 else if (operands[2] == constm1_rtx
5576 || (GET_CODE (operands[2]) == CONST_INT
5577 && INTVAL (operands[2]) == 65535))
5578 return \"dec{w}\\t%0\";
5579 abort();
5580
5581 default:
5582 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5583 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5584 if (GET_CODE (operands[2]) == CONST_INT
5585 && (INTVAL (operands[2]) == 128
5586 || (INTVAL (operands[2]) < 0
5587 && INTVAL (operands[2]) != -128)))
5588 {
5589 operands[2] = GEN_INT (-INTVAL (operands[2]));
5590 return \"sub{w}\\t{%2, %0|%0, %2}\";
5591 }
5592 return \"add{w}\\t{%2, %0|%0, %2}\";
5593 }
5594 }"
5595 [(set (attr "type")
5596 (if_then_else (eq_attr "alternative" "2")
5597 (const_string "lea")
5598 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5599 (const_string "incdec")
5600 (const_string "alu"))))
5601 (set_attr "mode" "HI,HI,SI")])
5602
5603 (define_insn "*addhi_1"
5604 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
5605 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
5606 (match_operand:HI 2 "general_operand" "ri,rm")))
5607 (clobber (reg:CC 17))]
5608 "TARGET_PARTIAL_REG_STALL
5609 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5610 "*
5611 {
5612 switch (get_attr_type (insn))
5613 {
5614 case TYPE_INCDEC:
5615 if (operands[2] == const1_rtx)
5616 return \"inc{w}\\t%0\";
5617 else if (operands[2] == constm1_rtx
5618 || (GET_CODE (operands[2]) == CONST_INT
5619 && INTVAL (operands[2]) == 65535))
5620 return \"dec{w}\\t%0\";
5621 abort();
5622
5623 default:
5624 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5625 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5626 if (GET_CODE (operands[2]) == CONST_INT
5627 && (INTVAL (operands[2]) == 128
5628 || (INTVAL (operands[2]) < 0
5629 && INTVAL (operands[2]) != -128)))
5630 {
5631 operands[2] = GEN_INT (-INTVAL (operands[2]));
5632 return \"sub{w}\\t{%2, %0|%0, %2}\";
5633 }
5634 return \"add{w}\\t{%2, %0|%0, %2}\";
5635 }
5636 }"
5637 [(set (attr "type")
5638 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5639 (const_string "incdec")
5640 (const_string "alu")))
5641 (set_attr "mode" "HI")])
5642
5643 (define_insn "*addhi_2"
5644 [(set (reg 17)
5645 (compare
5646 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
5647 (match_operand:HI 2 "general_operand" "rmni,rni"))
5648 (const_int 0)))
5649 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
5650 (plus:HI (match_dup 1) (match_dup 2)))]
5651 "ix86_match_ccmode (insn, CCGOCmode)
5652 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5653 "*
5654 {
5655 switch (get_attr_type (insn))
5656 {
5657 case TYPE_INCDEC:
5658 if (operands[2] == const1_rtx)
5659 return \"inc{w}\\t%0\";
5660 else if (operands[2] == constm1_rtx
5661 || (GET_CODE (operands[2]) == CONST_INT
5662 && INTVAL (operands[2]) == 65535))
5663 return \"dec{w}\\t%0\";
5664 abort();
5665
5666 default:
5667 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5668 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5669 if (GET_CODE (operands[2]) == CONST_INT
5670 && (INTVAL (operands[2]) == 128
5671 || (INTVAL (operands[2]) < 0
5672 && INTVAL (operands[2]) != -128)))
5673 {
5674 operands[2] = GEN_INT (-INTVAL (operands[2]));
5675 return \"sub{w}\\t{%2, %0|%0, %2}\";
5676 }
5677 return \"add{w}\\t{%2, %0|%0, %2}\";
5678 }
5679 }"
5680 [(set (attr "type")
5681 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5682 (const_string "incdec")
5683 (const_string "alu")))
5684 (set_attr "mode" "HI")])
5685
5686 (define_insn "*addhi_3"
5687 [(set (reg 17)
5688 (compare (neg:HI (match_operand:HI 2 "general_operand" "rmni"))
5689 (match_operand:HI 1 "nonimmediate_operand" "%0")))
5690 (clobber (match_scratch:HI 0 "=r"))]
5691 "ix86_match_ccmode (insn, CCZmode)
5692 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5693 "*
5694 {
5695 switch (get_attr_type (insn))
5696 {
5697 case TYPE_INCDEC:
5698 if (operands[2] == const1_rtx)
5699 return \"inc{w}\\t%0\";
5700 else if (operands[2] == constm1_rtx
5701 || (GET_CODE (operands[2]) == CONST_INT
5702 && INTVAL (operands[2]) == 65535))
5703 return \"dec{w}\\t%0\";
5704 abort();
5705
5706 default:
5707 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5708 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5709 if (GET_CODE (operands[2]) == CONST_INT
5710 && (INTVAL (operands[2]) == 128
5711 || (INTVAL (operands[2]) < 0
5712 && INTVAL (operands[2]) != -128)))
5713 {
5714 operands[2] = GEN_INT (-INTVAL (operands[2]));
5715 return \"sub{w}\\t{%2, %0|%0, %2}\";
5716 }
5717 return \"add{w}\\t{%2, %0|%0, %2}\";
5718 }
5719 }"
5720 [(set (attr "type")
5721 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5722 (const_string "incdec")
5723 (const_string "alu")))
5724 (set_attr "mode" "HI")])
5725
5726 ; See comments above addsi_3_imm for details.
5727 (define_insn "*addhi_4"
5728 [(set (reg 17)
5729 (compare (match_operand:HI 1 "nonimmediate_operand" "0")
5730 (match_operand:HI 2 "const_int_operand" "n")))
5731 (clobber (match_scratch:HI 0 "=rm"))]
5732 "ix86_match_ccmode (insn, CCGCmode)
5733 && (INTVAL (operands[2]) & 0xffff) != 0x8000"
5734 "*
5735 {
5736 switch (get_attr_type (insn))
5737 {
5738 case TYPE_INCDEC:
5739 if (operands[2] == constm1_rtx
5740 || (GET_CODE (operands[2]) == CONST_INT
5741 && INTVAL (operands[2]) == 65535))
5742 return \"inc{w}\\t%0\";
5743 else if (operands[2] == const1_rtx)
5744 return \"dec{w}\\t%0\";
5745 else
5746 abort();
5747
5748 default:
5749 if (! rtx_equal_p (operands[0], operands[1]))
5750 abort ();
5751 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5752 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5753 if ((INTVAL (operands[2]) == -128
5754 || (INTVAL (operands[2]) > 0
5755 && INTVAL (operands[2]) != 128)))
5756 return \"sub{w}\\t{%2, %0|%0, %2}\";
5757 operands[2] = GEN_INT (-INTVAL (operands[2]));
5758 return \"add{w}\\t{%2, %0|%0, %2}\";
5759 }
5760 }"
5761 [(set (attr "type")
5762 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5763 (const_string "incdec")
5764 (const_string "alu")))
5765 (set_attr "mode" "SI")])
5766
5767
5768 (define_insn "*addhi_5"
5769 [(set (reg 17)
5770 (compare
5771 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
5772 (match_operand:HI 2 "general_operand" "rmni"))
5773 (const_int 0)))
5774 (clobber (match_scratch:HI 0 "=r"))]
5775 "ix86_match_ccmode (insn, CCGOCmode)
5776 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5777 "*
5778 {
5779 switch (get_attr_type (insn))
5780 {
5781 case TYPE_INCDEC:
5782 if (operands[2] == const1_rtx)
5783 return \"inc{w}\\t%0\";
5784 else if (operands[2] == constm1_rtx
5785 || (GET_CODE (operands[2]) == CONST_INT
5786 && INTVAL (operands[2]) == 65535))
5787 return \"dec{w}\\t%0\";
5788 abort();
5789
5790 default:
5791 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5792 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5793 if (GET_CODE (operands[2]) == CONST_INT
5794 && (INTVAL (operands[2]) == 128
5795 || (INTVAL (operands[2]) < 0
5796 && INTVAL (operands[2]) != -128)))
5797 {
5798 operands[2] = GEN_INT (-INTVAL (operands[2]));
5799 return \"sub{w}\\t{%2, %0|%0, %2}\";
5800 }
5801 return \"add{w}\\t{%2, %0|%0, %2}\";
5802 }
5803 }"
5804 [(set (attr "type")
5805 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5806 (const_string "incdec")
5807 (const_string "alu")))
5808 (set_attr "mode" "HI")])
5809
5810 (define_expand "addqi3"
5811 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
5812 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "")
5813 (match_operand:QI 2 "general_operand" "")))
5814 (clobber (reg:CC 17))])]
5815 "TARGET_QIMODE_MATH"
5816 "ix86_expand_binary_operator (PLUS, QImode, operands); DONE;")
5817
5818 ;; %%% Potential partial reg stall on alternative 2. What to do?
5819 (define_insn "*addqi_1_lea"
5820 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r,r")
5821 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,r")
5822 (match_operand:QI 2 "general_operand" "qn,qmn,rn,rn")))
5823 (clobber (reg:CC 17))]
5824 "!TARGET_PARTIAL_REG_STALL
5825 && ix86_binary_operator_ok (PLUS, QImode, operands)"
5826 "*
5827 {
5828 int widen = (which_alternative == 2);
5829 switch (get_attr_type (insn))
5830 {
5831 case TYPE_LEA:
5832 return \"#\";
5833 case TYPE_INCDEC:
5834 if (operands[2] == const1_rtx)
5835 return widen ? \"inc{l}\\t%k0\" : \"inc{b}\\t%0\";
5836 else if (operands[2] == constm1_rtx
5837 || (GET_CODE (operands[2]) == CONST_INT
5838 && INTVAL (operands[2]) == 255))
5839 return widen ? \"dec{l}\\t%k0\" : \"dec{b}\\t%0\";
5840 abort();
5841
5842 default:
5843 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5844 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5845 if (GET_CODE (operands[2]) == CONST_INT
5846 && (INTVAL (operands[2]) == 128
5847 || (INTVAL (operands[2]) < 0
5848 && INTVAL (operands[2]) != -128)))
5849 {
5850 operands[2] = GEN_INT (-INTVAL (operands[2]));
5851 if (widen)
5852 return \"sub{l}\\t{%2, %k0|%k0, %2}\";
5853 else
5854 return \"sub{b}\\t{%2, %0|%0, %2}\";
5855 }
5856 if (widen)
5857 return \"add{l}\\t{%k2, %k0|%k0, %k2}\";
5858 else
5859 return \"add{b}\\t{%2, %0|%0, %2}\";
5860 }
5861 }"
5862 [(set (attr "type")
5863 (if_then_else (eq_attr "alternative" "3")
5864 (const_string "lea")
5865 (if_then_else (match_operand:QI 2 "incdec_operand" "")
5866 (const_string "incdec")
5867 (const_string "alu"))))
5868 (set_attr "mode" "QI,QI,SI,SI")])
5869
5870 (define_insn "*addqi_1"
5871 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
5872 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
5873 (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
5874 (clobber (reg:CC 17))]
5875 "TARGET_PARTIAL_REG_STALL
5876 && ix86_binary_operator_ok (PLUS, QImode, operands)"
5877 "*
5878 {
5879 int widen = (which_alternative == 2);
5880 switch (get_attr_type (insn))
5881 {
5882 case TYPE_INCDEC:
5883 if (operands[2] == const1_rtx)
5884 return widen ? \"inc{l}\\t%k0\" : \"inc{b}\\t%0\";
5885 else if (operands[2] == constm1_rtx
5886 || (GET_CODE (operands[2]) == CONST_INT
5887 && INTVAL (operands[2]) == 255))
5888 return widen ? \"dec{l}\\t%k0\" : \"dec{b}\\t%0\";
5889 abort();
5890
5891 default:
5892 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5893 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5894 if (GET_CODE (operands[2]) == CONST_INT
5895 && (INTVAL (operands[2]) == 128
5896 || (INTVAL (operands[2]) < 0
5897 && INTVAL (operands[2]) != -128)))
5898 {
5899 operands[2] = GEN_INT (-INTVAL (operands[2]));
5900 if (widen)
5901 return \"sub{l}\\t{%2, %k0|%k0, %2}\";
5902 else
5903 return \"sub{b}\\t{%2, %0|%0, %2}\";
5904 }
5905 if (widen)
5906 return \"add{l}\\t{%k2, %k0|%k0, %k2}\";
5907 else
5908 return \"add{b}\\t{%2, %0|%0, %2}\";
5909 }
5910 }"
5911 [(set (attr "type")
5912 (if_then_else (match_operand:QI 2 "incdec_operand" "")
5913 (const_string "incdec")
5914 (const_string "alu")))
5915 (set_attr "mode" "QI,QI,SI")])
5916
5917 (define_insn "*addqi_2"
5918 [(set (reg 17)
5919 (compare
5920 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
5921 (match_operand:QI 2 "general_operand" "qmni,qni"))
5922 (const_int 0)))
5923 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
5924 (plus:QI (match_dup 1) (match_dup 2)))]
5925 "ix86_match_ccmode (insn, CCGOCmode)
5926 && ix86_binary_operator_ok (PLUS, QImode, operands)"
5927 "*
5928 {
5929 switch (get_attr_type (insn))
5930 {
5931 case TYPE_INCDEC:
5932 if (operands[2] == const1_rtx)
5933 return \"inc{b}\\t%0\";
5934 else if (operands[2] == constm1_rtx
5935 || (GET_CODE (operands[2]) == CONST_INT
5936 && INTVAL (operands[2]) == 255))
5937 return \"dec{b}\\t%0\";
5938 abort();
5939
5940 default:
5941 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
5942 if (GET_CODE (operands[2]) == CONST_INT
5943 && INTVAL (operands[2]) < 0)
5944 {
5945 operands[2] = GEN_INT (-INTVAL (operands[2]));
5946 return \"sub{b}\\t{%2, %0|%0, %2}\";
5947 }
5948 return \"add{b}\\t{%2, %0|%0, %2}\";
5949 }
5950 }"
5951 [(set (attr "type")
5952 (if_then_else (match_operand:QI 2 "incdec_operand" "")
5953 (const_string "incdec")
5954 (const_string "alu")))
5955 (set_attr "mode" "QI")])
5956
5957 (define_insn "*addqi_3"
5958 [(set (reg 17)
5959 (compare (neg:QI (match_operand:QI 2 "general_operand" "qmni"))
5960 (match_operand:QI 1 "nonimmediate_operand" "%0")))
5961 (clobber (match_scratch:QI 0 "=q"))]
5962 "ix86_match_ccmode (insn, CCZmode)
5963 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5964 "*
5965 {
5966 switch (get_attr_type (insn))
5967 {
5968 case TYPE_INCDEC:
5969 if (operands[2] == const1_rtx)
5970 return \"inc{b}\\t%0\";
5971 else if (operands[2] == constm1_rtx
5972 || (GET_CODE (operands[2]) == CONST_INT
5973 && INTVAL (operands[2]) == 255))
5974 return \"dec{b}\\t%0\";
5975 abort();
5976
5977 default:
5978 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
5979 if (GET_CODE (operands[2]) == CONST_INT
5980 && INTVAL (operands[2]) < 0)
5981 {
5982 operands[2] = GEN_INT (-INTVAL (operands[2]));
5983 return \"sub{b}\\t{%2, %0|%0, %2}\";
5984 }
5985 return \"add{b}\\t{%2, %0|%0, %2}\";
5986 }
5987 }"
5988 [(set (attr "type")
5989 (if_then_else (match_operand:QI 2 "incdec_operand" "")
5990 (const_string "incdec")
5991 (const_string "alu")))
5992 (set_attr "mode" "QI")])
5993
5994 ; See comments above addsi_3_imm for details.
5995 (define_insn "*addqi_4"
5996 [(set (reg 17)
5997 (compare (match_operand:QI 1 "nonimmediate_operand" "0")
5998 (match_operand:QI 2 "const_int_operand" "n")))
5999 (clobber (match_scratch:QI 0 "=qm"))]
6000 "ix86_match_ccmode (insn, CCGCmode)
6001 && (INTVAL (operands[2]) & 0xff) != 0x80"
6002 "*
6003 {
6004 switch (get_attr_type (insn))
6005 {
6006 case TYPE_INCDEC:
6007 if (operands[2] == constm1_rtx
6008 || (GET_CODE (operands[2]) == CONST_INT
6009 && INTVAL (operands[2]) == 255))
6010 return \"inc{b}\\t%0\";
6011 else if (operands[2] == const1_rtx)
6012 return \"dec{b}\\t%0\";
6013 else
6014 abort();
6015
6016 default:
6017 if (! rtx_equal_p (operands[0], operands[1]))
6018 abort ();
6019 if (INTVAL (operands[2]) < 0)
6020 {
6021 operands[2] = GEN_INT (-INTVAL (operands[2]));
6022 return \"add{b}\\t{%2, %0|%0, %2}\";
6023 }
6024 return \"sub{b}\\t{%2, %0|%0, %2}\";
6025 }
6026 }"
6027 [(set (attr "type")
6028 (if_then_else (match_operand:HI 2 "incdec_operand" "")
6029 (const_string "incdec")
6030 (const_string "alu")))
6031 (set_attr "mode" "QI")])
6032
6033
6034 (define_insn "*addqi_5"
6035 [(set (reg 17)
6036 (compare
6037 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6038 (match_operand:QI 2 "general_operand" "qmni"))
6039 (const_int 0)))
6040 (clobber (match_scratch:QI 0 "=q"))]
6041 "ix86_match_ccmode (insn, CCGOCmode)
6042 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6043 "*
6044 {
6045 switch (get_attr_type (insn))
6046 {
6047 case TYPE_INCDEC:
6048 if (operands[2] == const1_rtx)
6049 return \"inc{b}\\t%0\";
6050 else if (operands[2] == constm1_rtx
6051 || (GET_CODE (operands[2]) == CONST_INT
6052 && INTVAL (operands[2]) == 255))
6053 return \"dec{b}\\t%0\";
6054 abort();
6055
6056 default:
6057 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
6058 if (GET_CODE (operands[2]) == CONST_INT
6059 && INTVAL (operands[2]) < 0)
6060 {
6061 operands[2] = GEN_INT (-INTVAL (operands[2]));
6062 return \"sub{b}\\t{%2, %0|%0, %2}\";
6063 }
6064 return \"add{b}\\t{%2, %0|%0, %2}\";
6065 }
6066 }"
6067 [(set (attr "type")
6068 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6069 (const_string "incdec")
6070 (const_string "alu")))
6071 (set_attr "mode" "QI")])
6072
6073
6074 (define_insn "addqi_ext_1"
6075 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
6076 (const_int 8)
6077 (const_int 8))
6078 (plus:SI
6079 (zero_extract:SI
6080 (match_operand 1 "ext_register_operand" "0")
6081 (const_int 8)
6082 (const_int 8))
6083 (match_operand:QI 2 "general_operand" "qmn")))
6084 (clobber (reg:CC 17))]
6085 "!TARGET_64BIT"
6086 "*
6087 {
6088 switch (get_attr_type (insn))
6089 {
6090 case TYPE_INCDEC:
6091 if (operands[2] == const1_rtx)
6092 return \"inc{b}\\t%h0\";
6093 else if (operands[2] == constm1_rtx
6094 || (GET_CODE (operands[2]) == CONST_INT
6095 && INTVAL (operands[2]) == 255))
6096 return \"dec{b}\\t%h0\";
6097 abort();
6098
6099 default:
6100 return \"add{b}\\t{%2, %h0|%h0, %2}\";
6101 }
6102 }"
6103 [(set (attr "type")
6104 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6105 (const_string "incdec")
6106 (const_string "alu")))
6107 (set_attr "mode" "QI")])
6108
6109 (define_insn "*addqi_ext_1_rex64"
6110 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6111 (const_int 8)
6112 (const_int 8))
6113 (plus:SI
6114 (zero_extract:SI
6115 (match_operand 1 "ext_register_operand" "0")
6116 (const_int 8)
6117 (const_int 8))
6118 (match_operand:QI 2 "nonmemory_operand" "Qn")))
6119 (clobber (reg:CC 17))]
6120 "TARGET_64BIT"
6121 "*
6122 {
6123 switch (get_attr_type (insn))
6124 {
6125 case TYPE_INCDEC:
6126 if (operands[2] == const1_rtx)
6127 return \"inc{b}\\t%h0\";
6128 else if (operands[2] == constm1_rtx
6129 || (GET_CODE (operands[2]) == CONST_INT
6130 && INTVAL (operands[2]) == 255))
6131 return \"dec{b}\\t%h0\";
6132 abort();
6133
6134 default:
6135 return \"add{b}\\t{%2, %h0|%h0, %2}\";
6136 }
6137 }"
6138 [(set (attr "type")
6139 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6140 (const_string "incdec")
6141 (const_string "alu")))
6142 (set_attr "mode" "QI")])
6143
6144 (define_insn "*addqi_ext_2"
6145 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6146 (const_int 8)
6147 (const_int 8))
6148 (plus:SI
6149 (zero_extract:SI
6150 (match_operand 1 "ext_register_operand" "%0")
6151 (const_int 8)
6152 (const_int 8))
6153 (zero_extract:SI
6154 (match_operand 2 "ext_register_operand" "Q")
6155 (const_int 8)
6156 (const_int 8))))
6157 (clobber (reg:CC 17))]
6158 ""
6159 "add{b}\\t{%h2, %h0|%h0, %h2}"
6160 [(set_attr "type" "alu")
6161 (set_attr "mode" "QI")])
6162
6163 ;; The patterns that match these are at the end of this file.
6164
6165 (define_expand "addxf3"
6166 [(set (match_operand:XF 0 "register_operand" "")
6167 (plus:XF (match_operand:XF 1 "register_operand" "")
6168 (match_operand:XF 2 "register_operand" "")))]
6169 "TARGET_80387 && !TARGET_64BIT"
6170 "")
6171
6172 (define_expand "addtf3"
6173 [(set (match_operand:TF 0 "register_operand" "")
6174 (plus:TF (match_operand:TF 1 "register_operand" "")
6175 (match_operand:TF 2 "register_operand" "")))]
6176 "TARGET_80387"
6177 "")
6178
6179 (define_expand "adddf3"
6180 [(set (match_operand:DF 0 "register_operand" "")
6181 (plus:DF (match_operand:DF 1 "register_operand" "")
6182 (match_operand:DF 2 "nonimmediate_operand" "")))]
6183 "TARGET_80387 || TARGET_SSE2"
6184 "")
6185
6186 (define_expand "addsf3"
6187 [(set (match_operand:SF 0 "register_operand" "")
6188 (plus:SF (match_operand:SF 1 "register_operand" "")
6189 (match_operand:SF 2 "nonimmediate_operand" "")))]
6190 "TARGET_80387 || TARGET_SSE"
6191 "")
6192 \f
6193 ;; Subtract instructions
6194
6195 ;; %%% define_expand from the very first?
6196 ;; %%% splits for subsidi3
6197
6198 (define_insn "subdi3"
6199 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
6200 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6201 (match_operand:DI 2 "general_operand" "roiF,riF")))
6202 (clobber (reg:CC 17))]
6203 ""
6204 "#")
6205
6206 (define_split
6207 [(set (match_operand:DI 0 "nonimmediate_operand" "")
6208 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6209 (match_operand:DI 2 "general_operand" "")))
6210 (clobber (reg:CC 17))]
6211 "reload_completed && !TARGET_64BIT"
6212 [(parallel [(set (reg:CC 17) (compare:CC (match_dup 1) (match_dup 2)))
6213 (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 2)))])
6214 (parallel [(set (match_dup 3)
6215 (minus:SI (match_dup 4)
6216 (plus:SI (ltu:SI (reg:CC 17) (const_int 0))
6217 (match_dup 5))))
6218 (clobber (reg:CC 17))])]
6219 "split_di (operands+0, 1, operands+0, operands+3);
6220 split_di (operands+1, 1, operands+1, operands+4);
6221 split_di (operands+2, 1, operands+2, operands+5);")
6222
6223 (define_insn "subsi3_carry"
6224 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6225 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6226 (plus:SI (ltu:SI (reg:CC 17) (const_int 0))
6227 (match_operand:SI 2 "general_operand" "ri,rm"))))
6228 (clobber (reg:CC 17))]
6229 "ix86_binary_operator_ok (MINUS, SImode, operands)"
6230 "sbb{l}\\t{%2, %0|%0, %2}"
6231 [(set_attr "type" "alu")
6232 (set_attr "pent_pair" "pu")
6233 (set_attr "ppro_uops" "few")
6234 (set_attr "mode" "SI")])
6235
6236 (define_expand "subsi3"
6237 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
6238 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "")
6239 (match_operand:SI 2 "general_operand" "")))
6240 (clobber (reg:CC 17))])]
6241 ""
6242 "ix86_expand_binary_operator (MINUS, SImode, operands); DONE;")
6243
6244 (define_insn "*subsi_1"
6245 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6246 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6247 (match_operand:SI 2 "general_operand" "ri,rm")))
6248 (clobber (reg:CC 17))]
6249 "ix86_binary_operator_ok (MINUS, SImode, operands)"
6250 "sub{l}\\t{%2, %0|%0, %2}"
6251 [(set_attr "type" "alu")
6252 (set_attr "mode" "SI")])
6253
6254 (define_insn "*subsi_2"
6255 [(set (reg 17)
6256 (compare
6257 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6258 (match_operand:SI 2 "general_operand" "ri,rm"))
6259 (const_int 0)))
6260 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6261 (minus:SI (match_dup 1) (match_dup 2)))]
6262 "ix86_match_ccmode (insn, CCGOCmode)
6263 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6264 "sub{l}\\t{%2, %0|%0, %2}"
6265 [(set_attr "type" "alu")
6266 (set_attr "mode" "SI")])
6267
6268 (define_insn "*subsi_3"
6269 [(set (reg 17)
6270 (compare (match_operand:SI 1 "nonimmediate_operand" "0,0")
6271 (match_operand:SI 2 "general_operand" "ri,rm")))
6272 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6273 (minus:SI (match_dup 1) (match_dup 2)))]
6274 "ix86_match_ccmode (insn, CCmode)
6275 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6276 "sub{l}\\t{%2, %0|%0, %2}"
6277 [(set_attr "type" "alu")
6278 (set_attr "mode" "SI")])
6279
6280 (define_expand "subhi3"
6281 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
6282 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "")
6283 (match_operand:HI 2 "general_operand" "")))
6284 (clobber (reg:CC 17))])]
6285 "TARGET_HIMODE_MATH"
6286 "ix86_expand_binary_operator (MINUS, HImode, operands); DONE;")
6287
6288 (define_insn "*subhi_1"
6289 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6290 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6291 (match_operand:HI 2 "general_operand" "ri,rm")))
6292 (clobber (reg:CC 17))]
6293 "ix86_binary_operator_ok (MINUS, HImode, operands)"
6294 "sub{w}\\t{%2, %0|%0, %2}"
6295 [(set_attr "type" "alu")
6296 (set_attr "mode" "HI")])
6297
6298 (define_insn "*subhi_2"
6299 [(set (reg 17)
6300 (compare
6301 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6302 (match_operand:HI 2 "general_operand" "ri,rm"))
6303 (const_int 0)))
6304 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6305 (minus:HI (match_dup 1) (match_dup 2)))]
6306 "ix86_match_ccmode (insn, CCGOCmode)
6307 && ix86_binary_operator_ok (MINUS, HImode, operands)"
6308 "sub{w}\\t{%2, %0|%0, %2}"
6309 [(set_attr "type" "alu")
6310 (set_attr "mode" "HI")])
6311
6312 (define_insn "*subhi_3"
6313 [(set (reg 17)
6314 (compare (match_operand:HI 1 "nonimmediate_operand" "0,0")
6315 (match_operand:HI 2 "general_operand" "ri,rm")))
6316 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6317 (minus:HI (match_dup 1) (match_dup 2)))]
6318 "ix86_match_ccmode (insn, CCmode)
6319 && ix86_binary_operator_ok (MINUS, HImode, operands)"
6320 "sub{w}\\t{%2, %0|%0, %2}"
6321 [(set_attr "type" "alu")
6322 (set_attr "mode" "HI")])
6323
6324 (define_expand "subqi3"
6325 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6326 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6327 (match_operand:QI 2 "general_operand" "")))
6328 (clobber (reg:CC 17))])]
6329 "TARGET_QIMODE_MATH"
6330 "ix86_expand_binary_operator (MINUS, QImode, operands); DONE;")
6331
6332 (define_insn "*subqi_1"
6333 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6334 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6335 (match_operand:QI 2 "general_operand" "qn,qmn")))
6336 (clobber (reg:CC 17))]
6337 "ix86_binary_operator_ok (MINUS, QImode, operands)"
6338 "sub{b}\\t{%2, %0|%0, %2}"
6339 [(set_attr "type" "alu")
6340 (set_attr "mode" "QI")])
6341
6342 (define_insn "*subqi_2"
6343 [(set (reg 17)
6344 (compare
6345 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6346 (match_operand:QI 2 "general_operand" "qi,qm"))
6347 (const_int 0)))
6348 (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6349 (minus:HI (match_dup 1) (match_dup 2)))]
6350 "ix86_match_ccmode (insn, CCGOCmode)
6351 && ix86_binary_operator_ok (MINUS, QImode, operands)"
6352 "sub{b}\\t{%2, %0|%0, %2}"
6353 [(set_attr "type" "alu")
6354 (set_attr "mode" "QI")])
6355
6356 (define_insn "*subqi_3"
6357 [(set (reg 17)
6358 (compare (match_operand:QI 1 "nonimmediate_operand" "0,0")
6359 (match_operand:QI 2 "general_operand" "qi,qm")))
6360 (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6361 (minus:HI (match_dup 1) (match_dup 2)))]
6362 "ix86_match_ccmode (insn, CCmode)
6363 && ix86_binary_operator_ok (MINUS, QImode, operands)"
6364 "sub{b}\\t{%2, %0|%0, %2}"
6365 [(set_attr "type" "alu")
6366 (set_attr "mode" "QI")])
6367
6368 ;; The patterns that match these are at the end of this file.
6369
6370 (define_expand "subxf3"
6371 [(set (match_operand:XF 0 "register_operand" "")
6372 (minus:XF (match_operand:XF 1 "register_operand" "")
6373 (match_operand:XF 2 "register_operand" "")))]
6374 "TARGET_80387 && !TARGET_64BIT"
6375 "")
6376
6377 (define_expand "subtf3"
6378 [(set (match_operand:TF 0 "register_operand" "")
6379 (minus:TF (match_operand:TF 1 "register_operand" "")
6380 (match_operand:TF 2 "register_operand" "")))]
6381 "TARGET_80387"
6382 "")
6383
6384 (define_expand "subdf3"
6385 [(set (match_operand:DF 0 "register_operand" "")
6386 (minus:DF (match_operand:DF 1 "register_operand" "")
6387 (match_operand:DF 2 "nonimmediate_operand" "")))]
6388 "TARGET_80387 || TARGET_SSE2"
6389 "")
6390
6391 (define_expand "subsf3"
6392 [(set (match_operand:SF 0 "register_operand" "")
6393 (minus:SF (match_operand:SF 1 "register_operand" "")
6394 (match_operand:SF 2 "nonimmediate_operand" "")))]
6395 "TARGET_80387 || TARGET_SSE"
6396 "")
6397 \f
6398 ;; Multiply instructions
6399
6400 (define_expand "mulsi3"
6401 [(parallel [(set (match_operand:SI 0 "register_operand" "")
6402 (mult:SI (match_operand:SI 1 "register_operand" "")
6403 (match_operand:SI 2 "general_operand" "")))
6404 (clobber (reg:CC 17))])]
6405 ""
6406 "")
6407
6408 (define_insn "*mulsi3_1"
6409 [(set (match_operand:SI 0 "register_operand" "=r,r,r")
6410 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,0,0")
6411 (match_operand:SI 2 "general_operand" "K,i,mr")))
6412 (clobber (reg:CC 17))]
6413 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6414 ; For the {r,0,i} alternative (i.e., register <- register * immediate),
6415 ; there are two ways of writing the exact same machine instruction
6416 ; in assembly language. One, for example, is:
6417 ;
6418 ; imul $12, %eax
6419 ;
6420 ; while the other is:
6421 ;
6422 ; imul $12, %eax, %eax
6423 ;
6424 ; The first is simply short-hand for the latter. But, some assemblers,
6425 ; like the SCO OSR5 COFF assembler, don't handle the first form.
6426 "@
6427 imul{l}\\t{%2, %1, %0|%0, %1, %2}
6428 imul{l}\\t{%2, %1, %0|%0, %1, %2}
6429 imul{l}\\t{%2, %0|%0, %2}"
6430 [(set_attr "type" "imul")
6431 (set_attr "prefix_0f" "0,0,1")
6432 (set_attr "mode" "SI")])
6433
6434 (define_expand "mulhi3"
6435 [(parallel [(set (match_operand:HI 0 "register_operand" "")
6436 (mult:HI (match_operand:HI 1 "register_operand" "")
6437 (match_operand:HI 2 "general_operand" "")))
6438 (clobber (reg:CC 17))])]
6439 "TARGET_HIMODE_MATH"
6440 "")
6441
6442 (define_insn "*mulhi3_1"
6443 [(set (match_operand:HI 0 "register_operand" "=r,r,r")
6444 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,0,0")
6445 (match_operand:HI 2 "general_operand" "K,i,mr")))
6446 (clobber (reg:CC 17))]
6447 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6448 ; %%% There was a note about "Assembler has weird restrictions",
6449 ; concerning alternative 1 when op1 == op0. True?
6450 "@
6451 imul{w}\\t{%2, %1, %0|%0, %1, %2}
6452 imul{w}\\t{%2, %1, %0|%0, %1, %2}
6453 imul{w}\\t{%2, %0|%0, %2}"
6454 [(set_attr "type" "imul")
6455 (set_attr "prefix_0f" "0,0,1")
6456 (set_attr "mode" "HI")])
6457
6458 (define_insn "mulqi3"
6459 [(set (match_operand:QI 0 "register_operand" "=a")
6460 (mult:QI (match_operand:QI 1 "register_operand" "%0")
6461 (match_operand:QI 2 "nonimmediate_operand" "qm")))
6462 (clobber (reg:CC 17))]
6463 "TARGET_QIMODE_MATH"
6464 "mul{b}\\t%2"
6465 [(set_attr "type" "imul")
6466 (set_attr "length_immediate" "0")
6467 (set_attr "mode" "QI")])
6468
6469 (define_insn "umulqihi3"
6470 [(set (match_operand:HI 0 "register_operand" "=a")
6471 (mult:HI (zero_extend:HI (match_operand:QI 1 "register_operand" "%0"))
6472 (zero_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6473 (clobber (reg:CC 17))]
6474 "TARGET_QIMODE_MATH"
6475 "mul{b}\\t%2"
6476 [(set_attr "type" "imul")
6477 (set_attr "length_immediate" "0")
6478 (set_attr "mode" "QI")])
6479
6480 (define_insn "mulqihi3"
6481 [(set (match_operand:HI 0 "register_operand" "=a")
6482 (mult:HI (sign_extend:HI (match_operand:QI 1 "register_operand" "%0"))
6483 (sign_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6484 (clobber (reg:CC 17))]
6485 "TARGET_QIMODE_MATH"
6486 "imul{b}\\t%2"
6487 [(set_attr "type" "imul")
6488 (set_attr "length_immediate" "0")
6489 (set_attr "mode" "QI")])
6490
6491 (define_insn "umulsi3"
6492 [(set (match_operand:SI 0 "register_operand" "=a")
6493 (mult:SI (match_operand:SI 1 "register_operand" "%0")
6494 (match_operand:SI 2 "nonimmediate_operand" "rm")))
6495 (clobber (match_operand:SI 3 "register_operand" "=d"))
6496 (clobber (reg:CC 17))]
6497 ""
6498 "mul{l}\\t%2"
6499 [(set_attr "type" "imul")
6500 (set_attr "ppro_uops" "few")
6501 (set_attr "length_immediate" "0")
6502 (set_attr "mode" "SI")])
6503
6504 ;; We can't use this pattern in 64bit mode, since it results in two separate 32bit registers
6505 (define_insn "umulsidi3"
6506 [(set (match_operand:DI 0 "register_operand" "=A")
6507 (mult:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
6508 (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
6509 (clobber (reg:CC 17))]
6510 "!TARGET_64BIT"
6511 "mul{l}\\t%2"
6512 [(set_attr "type" "imul")
6513 (set_attr "ppro_uops" "few")
6514 (set_attr "length_immediate" "0")
6515 (set_attr "mode" "SI")])
6516
6517 (define_insn "mulsidi3"
6518 [(set (match_operand:DI 0 "register_operand" "=A")
6519 (mult:DI (sign_extend:DI (match_operand:SI 1 "register_operand" "%0"))
6520 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
6521 (clobber (reg:CC 17))]
6522 "!TARGET_64BIT"
6523 "imul{l}\\t%2"
6524 [(set_attr "type" "imul")
6525 (set_attr "length_immediate" "0")
6526 (set_attr "mode" "SI")])
6527
6528 (define_insn "umulsi3_highpart"
6529 [(set (match_operand:SI 0 "register_operand" "=d")
6530 (truncate:SI
6531 (lshiftrt:DI
6532 (mult:DI (zero_extend:DI
6533 (match_operand:SI 1 "register_operand" "%a"))
6534 (zero_extend:DI
6535 (match_operand:SI 2 "nonimmediate_operand" "rm")))
6536 (const_int 32))))
6537 (clobber (match_scratch:SI 3 "=a"))
6538 (clobber (reg:CC 17))]
6539 "!TARGET_64BIT"
6540 "mul{l}\\t%2"
6541 [(set_attr "type" "imul")
6542 (set_attr "ppro_uops" "few")
6543 (set_attr "length_immediate" "0")
6544 (set_attr "mode" "SI")])
6545
6546 (define_insn "smulsi3_highpart"
6547 [(set (match_operand:SI 0 "register_operand" "=d")
6548 (truncate:SI
6549 (lshiftrt:DI
6550 (mult:DI (sign_extend:DI
6551 (match_operand:SI 1 "register_operand" "%a"))
6552 (sign_extend:DI
6553 (match_operand:SI 2 "nonimmediate_operand" "rm")))
6554 (const_int 32))))
6555 (clobber (match_scratch:SI 3 "=a"))
6556 (clobber (reg:CC 17))]
6557 ""
6558 "imul{l}\\t%2"
6559 [(set_attr "type" "imul")
6560 (set_attr "ppro_uops" "few")
6561 (set_attr "mode" "SI")])
6562
6563 ;; The patterns that match these are at the end of this file.
6564
6565 (define_expand "mulxf3"
6566 [(set (match_operand:XF 0 "register_operand" "")
6567 (mult:XF (match_operand:XF 1 "register_operand" "")
6568 (match_operand:XF 2 "register_operand" "")))]
6569 "TARGET_80387 && !TARGET_64BIT"
6570 "")
6571
6572 (define_expand "multf3"
6573 [(set (match_operand:TF 0 "register_operand" "")
6574 (mult:TF (match_operand:TF 1 "register_operand" "")
6575 (match_operand:TF 2 "register_operand" "")))]
6576 "TARGET_80387"
6577 "")
6578
6579 (define_expand "muldf3"
6580 [(set (match_operand:DF 0 "register_operand" "")
6581 (mult:DF (match_operand:DF 1 "register_operand" "")
6582 (match_operand:DF 2 "nonimmediate_operand" "")))]
6583 "TARGET_80387 || TARGET_SSE2"
6584 "")
6585
6586 (define_expand "mulsf3"
6587 [(set (match_operand:SF 0 "register_operand" "")
6588 (mult:SF (match_operand:SF 1 "register_operand" "")
6589 (match_operand:SF 2 "nonimmediate_operand" "")))]
6590 "TARGET_80387 || TARGET_SSE"
6591 "")
6592 \f
6593 ;; Divide instructions
6594
6595 (define_insn "divqi3"
6596 [(set (match_operand:QI 0 "register_operand" "=a")
6597 (div:QI (match_operand:HI 1 "register_operand" "0")
6598 (match_operand:QI 2 "nonimmediate_operand" "qm")))
6599 (clobber (reg:CC 17))]
6600 "TARGET_QIMODE_MATH"
6601 "idiv{b}\\t%2"
6602 [(set_attr "type" "idiv")
6603 (set_attr "mode" "QI")
6604 (set_attr "ppro_uops" "few")])
6605
6606 (define_insn "udivqi3"
6607 [(set (match_operand:QI 0 "register_operand" "=a")
6608 (udiv:QI (match_operand:HI 1 "register_operand" "0")
6609 (match_operand:QI 2 "nonimmediate_operand" "qm")))
6610 (clobber (reg:CC 17))]
6611 "TARGET_QIMODE_MATH"
6612 "div{b}\\t%2"
6613 [(set_attr "type" "idiv")
6614 (set_attr "mode" "QI")
6615 (set_attr "ppro_uops" "few")])
6616
6617 ;; The patterns that match these are at the end of this file.
6618
6619 (define_expand "divxf3"
6620 [(set (match_operand:XF 0 "register_operand" "")
6621 (div:XF (match_operand:XF 1 "register_operand" "")
6622 (match_operand:XF 2 "register_operand" "")))]
6623 "TARGET_80387 && !TARGET_64BIT"
6624 "")
6625
6626 (define_expand "divtf3"
6627 [(set (match_operand:TF 0 "register_operand" "")
6628 (div:TF (match_operand:TF 1 "register_operand" "")
6629 (match_operand:TF 2 "register_operand" "")))]
6630 "TARGET_80387"
6631 "")
6632
6633 (define_expand "divdf3"
6634 [(set (match_operand:DF 0 "register_operand" "")
6635 (div:DF (match_operand:DF 1 "register_operand" "")
6636 (match_operand:DF 2 "nonimmediate_operand" "")))]
6637 "TARGET_80387 || TARGET_SSE2"
6638 "")
6639
6640 (define_expand "divsf3"
6641 [(set (match_operand:SF 0 "register_operand" "")
6642 (div:SF (match_operand:SF 1 "register_operand" "")
6643 (match_operand:SF 2 "nonimmediate_operand" "")))]
6644 "TARGET_80387 || TARGET_SSE"
6645 "")
6646 \f
6647 ;; Remainder instructions.
6648 (define_expand "divmodsi4"
6649 [(parallel [(set (match_operand:SI 0 "register_operand" "")
6650 (div:SI (match_operand:SI 1 "register_operand" "")
6651 (match_operand:SI 2 "nonimmediate_operand" "")))
6652 (set (match_operand:SI 3 "register_operand" "")
6653 (mod:SI (match_dup 1) (match_dup 2)))
6654 (clobber (reg:CC 17))])]
6655 ""
6656 "")
6657
6658 ;; Allow to come the parameter in eax or edx to avoid extra moves.
6659 ;; Penalize eax case sligthly because it results in worse scheduling
6660 ;; of code.
6661 (define_insn "*divmodsi4_nocltd"
6662 [(set (match_operand:SI 0 "register_operand" "=&a,?a")
6663 (div:SI (match_operand:SI 2 "register_operand" "1,0")
6664 (match_operand:SI 3 "nonimmediate_operand" "rm,rm")))
6665 (set (match_operand:SI 1 "register_operand" "=&d,&d")
6666 (mod:SI (match_dup 2) (match_dup 3)))
6667 (clobber (reg:CC 17))]
6668 "!optimize_size && !TARGET_USE_CLTD"
6669 "#"
6670 [(set_attr "type" "multi")])
6671
6672 (define_insn "*divmodsi4_cltd"
6673 [(set (match_operand:SI 0 "register_operand" "=a")
6674 (div:SI (match_operand:SI 2 "register_operand" "a")
6675 (match_operand:SI 3 "nonimmediate_operand" "rm")))
6676 (set (match_operand:SI 1 "register_operand" "=&d")
6677 (mod:SI (match_dup 2) (match_dup 3)))
6678 (clobber (reg:CC 17))]
6679 "optimize_size || TARGET_USE_CLTD"
6680 "#"
6681 [(set_attr "type" "multi")])
6682
6683 (define_insn "*divmodsi_noext"
6684 [(set (match_operand:SI 0 "register_operand" "=a")
6685 (div:SI (match_operand:SI 1 "register_operand" "0")
6686 (match_operand:SI 2 "nonimmediate_operand" "rm")))
6687 (set (match_operand:SI 3 "register_operand" "=d")
6688 (mod:SI (match_dup 1) (match_dup 2)))
6689 (use (match_operand:SI 4 "register_operand" "3"))
6690 (clobber (reg:CC 17))]
6691 ""
6692 "idiv{l}\\t%2"
6693 [(set_attr "type" "idiv")
6694 (set_attr "mode" "SI")
6695 (set_attr "ppro_uops" "few")])
6696
6697 (define_split
6698 [(set (match_operand:SI 0 "register_operand" "")
6699 (div:SI (match_operand:SI 1 "register_operand" "")
6700 (match_operand:SI 2 "nonimmediate_operand" "")))
6701 (set (match_operand:SI 3 "register_operand" "")
6702 (mod:SI (match_dup 1) (match_dup 2)))
6703 (clobber (reg:CC 17))]
6704 "reload_completed"
6705 [(parallel [(set (match_dup 3)
6706 (ashiftrt:SI (match_dup 4) (const_int 31)))
6707 (clobber (reg:CC 17))])
6708 (parallel [(set (match_dup 0)
6709 (div:SI (reg:SI 0) (match_dup 2)))
6710 (set (match_dup 3)
6711 (mod:SI (reg:SI 0) (match_dup 2)))
6712 (use (match_dup 3))
6713 (clobber (reg:CC 17))])]
6714 "
6715 {
6716 /* Avoid use of cltd in favour of a mov+shift. */
6717 if (!TARGET_USE_CLTD && !optimize_size)
6718 {
6719 if (true_regnum (operands[1]))
6720 emit_move_insn (operands[0], operands[1]);
6721 else
6722 emit_move_insn (operands[3], operands[1]);
6723 operands[4] = operands[3];
6724 }
6725 else
6726 {
6727 if (true_regnum (operands[1]))
6728 abort();
6729 operands[4] = operands[1];
6730 }
6731 }")
6732 ;; %%% Split me.
6733 (define_insn "divmodhi4"
6734 [(set (match_operand:HI 0 "register_operand" "=a")
6735 (div:HI (match_operand:HI 1 "register_operand" "0")
6736 (match_operand:HI 2 "nonimmediate_operand" "rm")))
6737 (set (match_operand:HI 3 "register_operand" "=&d")
6738 (mod:HI (match_dup 1) (match_dup 2)))
6739 (clobber (reg:CC 17))]
6740 "TARGET_HIMODE_MATH"
6741 "cwtd\;idiv{w}\\t%2"
6742 [(set_attr "type" "multi")
6743 (set_attr "length_immediate" "0")
6744 (set_attr "mode" "SI")])
6745
6746 (define_insn "udivmodsi4"
6747 [(set (match_operand:SI 0 "register_operand" "=a")
6748 (udiv:SI (match_operand:SI 1 "register_operand" "0")
6749 (match_operand:SI 2 "nonimmediate_operand" "rm")))
6750 (set (match_operand:SI 3 "register_operand" "=&d")
6751 (umod:SI (match_dup 1) (match_dup 2)))
6752 (clobber (reg:CC 17))]
6753 ""
6754 "xor{l}\\t%3, %3\;div{l}\\t%2"
6755 [(set_attr "type" "multi")
6756 (set_attr "length_immediate" "0")
6757 (set_attr "mode" "SI")])
6758
6759 (define_insn "*udivmodsi4_noext"
6760 [(set (match_operand:SI 0 "register_operand" "=a")
6761 (udiv:SI (match_operand:SI 1 "register_operand" "0")
6762 (match_operand:SI 2 "nonimmediate_operand" "rm")))
6763 (set (match_operand:SI 3 "register_operand" "=d")
6764 (umod:SI (match_dup 1) (match_dup 2)))
6765 (use (match_dup 3))
6766 (clobber (reg:CC 17))]
6767 ""
6768 "div{l}\\t%2"
6769 [(set_attr "type" "idiv")
6770 (set_attr "ppro_uops" "few")
6771 (set_attr "mode" "SI")])
6772
6773 (define_split
6774 [(set (match_operand:SI 0 "register_operand" "")
6775 (udiv:SI (match_operand:SI 1 "register_operand" "")
6776 (match_operand:SI 2 "nonimmediate_operand" "")))
6777 (set (match_operand:SI 3 "register_operand" "")
6778 (umod:SI (match_dup 1) (match_dup 2)))
6779 (clobber (reg:CC 17))]
6780 "reload_completed"
6781 [(set (match_dup 3) (const_int 0))
6782 (parallel [(set (match_dup 0)
6783 (udiv:SI (match_dup 1) (match_dup 2)))
6784 (set (match_dup 3)
6785 (umod:SI (match_dup 1) (match_dup 2)))
6786 (use (match_dup 3))
6787 (clobber (reg:CC 17))])]
6788 "")
6789
6790 (define_expand "udivmodhi4"
6791 [(set (match_dup 4) (const_int 0))
6792 (parallel [(set (match_operand:HI 0 "register_operand" "")
6793 (udiv:HI (match_operand:HI 1 "register_operand" "")
6794 (match_operand:HI 2 "nonimmediate_operand" "")))
6795 (set (match_operand:HI 3 "register_operand" "")
6796 (umod:HI (match_dup 1) (match_dup 2)))
6797 (use (match_dup 4))
6798 (clobber (reg:CC 17))])]
6799 "TARGET_HIMODE_MATH"
6800 "operands[4] = gen_reg_rtx (HImode);")
6801
6802 (define_insn "*udivmodhi_noext"
6803 [(set (match_operand:HI 0 "register_operand" "=a")
6804 (udiv:HI (match_operand:HI 1 "register_operand" "0")
6805 (match_operand:HI 2 "nonimmediate_operand" "rm")))
6806 (set (match_operand:HI 3 "register_operand" "=d")
6807 (umod:HI (match_dup 1) (match_dup 2)))
6808 (use (match_operand:HI 4 "register_operand" "3"))
6809 (clobber (reg:CC 17))]
6810 ""
6811 "div{w}\\t%2"
6812 [(set_attr "type" "idiv")
6813 (set_attr "mode" "HI")
6814 (set_attr "ppro_uops" "few")])
6815
6816 ;; We can not use div/idiv for double division, because it causes
6817 ;; "division by zero" on the overflow and that's not what we expect
6818 ;; from truncate. Because true (non truncating) double division is
6819 ;; never generated, we can't create this insn anyway.
6820 ;
6821 ;(define_insn ""
6822 ; [(set (match_operand:SI 0 "register_operand" "=a")
6823 ; (truncate:SI
6824 ; (udiv:DI (match_operand:DI 1 "register_operand" "A")
6825 ; (zero_extend:DI
6826 ; (match_operand:SI 2 "nonimmediate_operand" "rm")))))
6827 ; (set (match_operand:SI 3 "register_operand" "=d")
6828 ; (truncate:SI
6829 ; (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
6830 ; (clobber (reg:CC 17))]
6831 ; ""
6832 ; "div{l}\\t{%2, %0|%0, %2}"
6833 ; [(set_attr "type" "idiv")
6834 ; (set_attr "ppro_uops" "few")])
6835 \f
6836 ;;- Logical AND instructions
6837
6838 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
6839 ;; Note that this excludes ah.
6840
6841
6842 (define_insn "testsi_1"
6843 [(set (reg 17)
6844 (compare
6845 (and:SI (match_operand:SI 0 "nonimmediate_operand" "%*a,r,rm")
6846 (match_operand:SI 1 "nonmemory_operand" "in,in,rin"))
6847 (const_int 0)))]
6848 "ix86_match_ccmode (insn, CCNOmode)"
6849 "test{l}\\t{%1, %0|%0, %1}"
6850 [(set_attr "type" "test")
6851 (set_attr "modrm" "0,1,1")
6852 (set_attr "mode" "SI")
6853 (set_attr "pent_pair" "uv,np,uv")])
6854
6855 (define_expand "testsi_ccno_1"
6856 [(set (reg:CCNO 17)
6857 (compare:CCNO
6858 (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
6859 (match_operand:SI 1 "nonmemory_operand" ""))
6860 (const_int 0)))]
6861 ""
6862 "")
6863
6864 (define_insn "*testhi_1"
6865 [(set (reg 17)
6866 (compare (and:HI (match_operand:HI 0 "nonimmediate_operand" "%*a,r,rm")
6867 (match_operand:HI 1 "nonmemory_operand" "n,n,rn"))
6868 (const_int 0)))]
6869 "ix86_match_ccmode (insn, CCNOmode)"
6870 "test{w}\\t{%1, %0|%0, %1}"
6871 [(set_attr "type" "test")
6872 (set_attr "modrm" "0,1,1")
6873 (set_attr "mode" "HI")
6874 (set_attr "pent_pair" "uv,np,uv")])
6875
6876 (define_expand "testqi_ccz_1"
6877 [(set (reg:CCZ 17)
6878 (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
6879 (match_operand:QI 1 "nonmemory_operand" ""))
6880 (const_int 0)))]
6881 ""
6882 "")
6883
6884 (define_insn "*testqi_1"
6885 [(set (reg 17)
6886 (compare (and:QI (match_operand:QI 0 "nonimmediate_operand" "%*a,q,qm,r")
6887 (match_operand:QI 1 "nonmemory_operand" "n,n,qn,n"))
6888 (const_int 0)))]
6889 "ix86_match_ccmode (insn, CCNOmode)"
6890 "*
6891 {
6892 if (which_alternative == 3)
6893 {
6894 if (GET_CODE (operands[1]) == CONST_INT
6895 && (INTVAL (operands[1]) & 0xffffff00))
6896 operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
6897 return \"test{l}\\t{%1, %k0|%k0, %1}\";
6898 }
6899 return \"test{b}\\t{%1, %0|%0, %1}\";
6900 }"
6901 [(set_attr "type" "test")
6902 (set_attr "modrm" "0,1,1,1")
6903 (set_attr "mode" "QI,QI,QI,SI")
6904 (set_attr "pent_pair" "uv,np,uv,np")])
6905
6906 (define_expand "testqi_ext_ccno_0"
6907 [(set (reg:CCNO 17)
6908 (compare:CCNO
6909 (and:SI
6910 (zero_extract:SI
6911 (match_operand 0 "ext_register_operand" "")
6912 (const_int 8)
6913 (const_int 8))
6914 (match_operand 1 "const_int_operand" ""))
6915 (const_int 0)))]
6916 ""
6917 "")
6918
6919 (define_insn "*testqi_ext_0"
6920 [(set (reg 17)
6921 (compare
6922 (and:SI
6923 (zero_extract:SI
6924 (match_operand 0 "ext_register_operand" "Q")
6925 (const_int 8)
6926 (const_int 8))
6927 (match_operand 1 "const_int_operand" "n"))
6928 (const_int 0)))]
6929 "(unsigned HOST_WIDE_INT) INTVAL (operands[1]) <= 0xff
6930 && ix86_match_ccmode (insn, CCNOmode)"
6931 "test{b}\\t{%1, %h0|%h0, %1}"
6932 [(set_attr "type" "test")
6933 (set_attr "mode" "QI")
6934 (set_attr "length_immediate" "1")
6935 (set_attr "pent_pair" "np")])
6936
6937 (define_insn "*testqi_ext_1"
6938 [(set (reg 17)
6939 (compare
6940 (and:SI
6941 (zero_extract:SI
6942 (match_operand 0 "ext_register_operand" "Q")
6943 (const_int 8)
6944 (const_int 8))
6945 (zero_extend:SI
6946 (match_operand:QI 1 "nonimmediate_operand" "Qm")))
6947 (const_int 0)))]
6948 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
6949 "test{b}\\t{%1, %h0|%h0, %1}"
6950 [(set_attr "type" "test")
6951 (set_attr "mode" "QI")])
6952
6953 (define_insn "*testqi_ext_1_rex64"
6954 [(set (reg 17)
6955 (compare
6956 (and:SI
6957 (zero_extract:SI
6958 (match_operand 0 "ext_register_operand" "Q")
6959 (const_int 8)
6960 (const_int 8))
6961 (zero_extend:SI
6962 (match_operand:QI 1 "ext_register_operand" "Q")))
6963 (const_int 0)))]
6964 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
6965 "test{b}\\t{%1, %h0|%h0, %1}"
6966 [(set_attr "type" "test")
6967 (set_attr "mode" "QI")])
6968
6969 (define_insn "*testqi_ext_2"
6970 [(set (reg 17)
6971 (compare
6972 (and:SI
6973 (zero_extract:SI
6974 (match_operand 0 "ext_register_operand" "Q")
6975 (const_int 8)
6976 (const_int 8))
6977 (zero_extract:SI
6978 (match_operand 1 "ext_register_operand" "Q")
6979 (const_int 8)
6980 (const_int 8)))
6981 (const_int 0)))]
6982 "ix86_match_ccmode (insn, CCNOmode)"
6983 "test{b}\\t{%h1, %h0|%h0, %h1}"
6984 [(set_attr "type" "test")
6985 (set_attr "mode" "QI")])
6986
6987 ;; Combine likes to form bit extractions for some tests. Humor it.
6988 (define_insn "*testqi_ext_3"
6989 [(set (reg 17)
6990 (compare (zero_extract:SI
6991 (match_operand 0 "nonimmediate_operand" "rm")
6992 (match_operand:SI 1 "const_int_operand" "")
6993 (match_operand:SI 2 "const_int_operand" ""))
6994 (const_int 0)))]
6995 "ix86_match_ccmode (insn, CCNOmode)
6996 && (GET_MODE (operands[0]) == SImode
6997 || GET_MODE (operands[0]) == HImode
6998 || GET_MODE (operands[0]) == QImode)"
6999 "#")
7000
7001 (define_split
7002 [(set (reg 17)
7003 (compare (zero_extract:SI
7004 (match_operand 0 "nonimmediate_operand" "rm")
7005 (match_operand:SI 1 "const_int_operand" "")
7006 (match_operand:SI 2 "const_int_operand" ""))
7007 (const_int 0)))]
7008 "ix86_match_ccmode (insn, CCNOmode)"
7009 [(set (reg:CCNO 17) (compare:CCNO (match_dup 3) (const_int 0)))]
7010 "
7011 {
7012 HOST_WIDE_INT len = INTVAL (operands[1]);
7013 HOST_WIDE_INT pos = INTVAL (operands[2]);
7014 HOST_WIDE_INT mask;
7015 enum machine_mode mode;
7016
7017 mode = GET_MODE (operands[0]);
7018 if (GET_CODE (operands[0]) == MEM)
7019 {
7020 /* ??? Combine likes to put non-volatile mem extractions in QImode
7021 no matter the size of the test. So find a mode that works. */
7022 if (! MEM_VOLATILE_P (operands[0]))
7023 {
7024 mode = smallest_mode_for_size (pos + len, MODE_INT);
7025 operands[0] = change_address (operands[0], mode, NULL_RTX);
7026 }
7027 }
7028 else if (mode == HImode && pos + len <= 8)
7029 {
7030 /* Small HImode tests can be converted to QImode. */
7031 mode = QImode;
7032 operands[0] = gen_lowpart (QImode, operands[0]);
7033 }
7034
7035 mask = ((HOST_WIDE_INT)1 << (pos + len)) - 1;
7036 mask &= ~(((HOST_WIDE_INT)1 << pos) - 1);
7037
7038 operands[3] = gen_rtx_AND (mode, operands[0], GEN_INT (mask));
7039 }")
7040
7041 ;; %%% This used to optimize known byte-wide and operations to memory,
7042 ;; and sometimes to QImode registers. If this is considered useful,
7043 ;; it should be done with splitters.
7044
7045 (define_expand "andsi3"
7046 [(set (match_operand:SI 0 "nonimmediate_operand" "")
7047 (and:SI (match_operand:SI 1 "nonimmediate_operand" "")
7048 (match_operand:SI 2 "general_operand" "")))
7049 (clobber (reg:CC 17))]
7050 ""
7051 "ix86_expand_binary_operator (AND, SImode, operands); DONE;")
7052
7053 (define_insn "*andsi_1"
7054 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
7055 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
7056 (match_operand:SI 2 "general_operand" "ri,rm,L")))
7057 (clobber (reg:CC 17))]
7058 "ix86_binary_operator_ok (AND, SImode, operands)"
7059 "*
7060 {
7061 switch (get_attr_type (insn))
7062 {
7063 case TYPE_IMOVX:
7064 {
7065 enum machine_mode mode;
7066
7067 if (GET_CODE (operands[2]) != CONST_INT)
7068 abort ();
7069 if (INTVAL (operands[2]) == 0xff)
7070 mode = QImode;
7071 else if (INTVAL (operands[2]) == 0xffff)
7072 mode = HImode;
7073 else
7074 abort ();
7075
7076 operands[1] = gen_lowpart (mode, operands[1]);
7077 if (mode == QImode)
7078 return \"movz{bl|x}\\t{%1,%0|%0, %1}\";
7079 else
7080 return \"movz{wl|x}\\t{%1,%0|%0, %1}\";
7081 }
7082
7083 default:
7084 if (! rtx_equal_p (operands[0], operands[1]))
7085 abort ();
7086 return \"and{l}\\t{%2, %0|%0, %2}\";
7087 }
7088 }"
7089 [(set_attr "type" "alu,alu,imovx")
7090 (set_attr "length_immediate" "*,*,0")
7091 (set_attr "mode" "SI")])
7092
7093 (define_split
7094 [(set (match_operand:SI 0 "register_operand" "")
7095 (and:SI (match_dup 0)
7096 (const_int -65536)))
7097 (clobber (reg:CC 17))]
7098 "optimize_size"
7099 [(set (strict_low_part (match_dup 1)) (const_int 0))]
7100 "operands[1] = gen_lowpart (HImode, operands[0]);")
7101
7102 (define_split
7103 [(set (match_operand 0 "q_regs_operand" "")
7104 (and (match_dup 0)
7105 (const_int -256)))
7106 (clobber (reg:CC 17))]
7107 "(optimize_size || !TARGET_PARTIAL_REG_STALL)
7108 && (GET_MODE (operands[0]) == SImode || GET_MODE (operands[0]) == HImode)"
7109 [(set (strict_low_part (match_dup 1)) (const_int 0))]
7110 "operands[1] = gen_lowpart (QImode, operands[0]);")
7111
7112 (define_split
7113 [(set (match_operand 0 "q_regs_operand" "")
7114 (and (match_dup 0)
7115 (const_int -65281)))
7116 (clobber (reg:CC 17))]
7117 "(optimize_size || !TARGET_PARTIAL_REG_STALL)
7118 && (GET_MODE (operands[0]) == SImode || GET_MODE (operands[0]) == HImode)"
7119 [(parallel [(set (zero_extract:SI (match_dup 0)
7120 (const_int 8)
7121 (const_int 8))
7122 (xor:SI
7123 (zero_extract:SI (match_dup 0)
7124 (const_int 8)
7125 (const_int 8))
7126 (zero_extract:SI (match_dup 0)
7127 (const_int 8)
7128 (const_int 8))))
7129 (clobber (reg:CC 17))])]
7130 "operands[0] = gen_lowpart (SImode, operands[0]);")
7131
7132 (define_insn "*andsi_2"
7133 [(set (reg 17)
7134 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
7135 (match_operand:SI 2 "general_operand" "rim,ri"))
7136 (const_int 0)))
7137 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
7138 (and:SI (match_dup 1) (match_dup 2)))]
7139 "ix86_match_ccmode (insn, CCNOmode)
7140 && ix86_binary_operator_ok (AND, SImode, operands)"
7141 "and{l}\\t{%2, %0|%0, %2}"
7142 [(set_attr "type" "alu")
7143 (set_attr "mode" "SI")])
7144
7145 (define_expand "andhi3"
7146 [(set (match_operand:HI 0 "nonimmediate_operand" "")
7147 (and:HI (match_operand:HI 1 "nonimmediate_operand" "")
7148 (match_operand:HI 2 "general_operand" "")))
7149 (clobber (reg:CC 17))]
7150 "TARGET_HIMODE_MATH"
7151 "ix86_expand_binary_operator (AND, HImode, operands); DONE;")
7152
7153 (define_insn "*andhi_1"
7154 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
7155 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
7156 (match_operand:HI 2 "general_operand" "ri,rm,L")))
7157 (clobber (reg:CC 17))]
7158 "ix86_binary_operator_ok (AND, HImode, operands)"
7159 "*
7160 {
7161 switch (get_attr_type (insn))
7162 {
7163 case TYPE_IMOVX:
7164 if (GET_CODE (operands[2]) != CONST_INT)
7165 abort ();
7166 if (INTVAL (operands[2]) == 0xff)
7167 return \"movz{bl|x}\\t{%b1, %k0|%k0, %b1}\";
7168 abort ();
7169
7170 default:
7171 if (! rtx_equal_p (operands[0], operands[1]))
7172 abort ();
7173
7174 return \"and{w}\\t{%2, %0|%0, %2}\";
7175 }
7176 }"
7177 [(set_attr "type" "alu,alu,imovx")
7178 (set_attr "length_immediate" "*,*,0")
7179 (set_attr "mode" "HI,HI,SI")])
7180
7181 (define_insn "*andhi_2"
7182 [(set (reg 17)
7183 (compare (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
7184 (match_operand:HI 2 "general_operand" "rim,ri"))
7185 (const_int 0)))
7186 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
7187 (and:HI (match_dup 1) (match_dup 2)))]
7188 "ix86_match_ccmode (insn, CCNOmode)
7189 && ix86_binary_operator_ok (AND, HImode, operands)"
7190 "and{w}\\t{%2, %0|%0, %2}"
7191 [(set_attr "type" "alu")
7192 (set_attr "mode" "HI")])
7193
7194 (define_expand "andqi3"
7195 [(set (match_operand:QI 0 "nonimmediate_operand" "")
7196 (and:QI (match_operand:QI 1 "nonimmediate_operand" "")
7197 (match_operand:QI 2 "general_operand" "")))
7198 (clobber (reg:CC 17))]
7199 "TARGET_QIMODE_MATH"
7200 "ix86_expand_binary_operator (AND, QImode, operands); DONE;")
7201
7202 ;; %%% Potential partial reg stall on alternative 2. What to do?
7203 (define_insn "*andqi_1"
7204 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
7205 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7206 (match_operand:QI 2 "general_operand" "qi,qmi,ri")))
7207 (clobber (reg:CC 17))]
7208 "ix86_binary_operator_ok (AND, QImode, operands)"
7209 "@
7210 and{b}\\t{%2, %0|%0, %2}
7211 and{b}\\t{%2, %0|%0, %2}
7212 and{l}\\t{%k2, %k0|%k0, %k2}"
7213 [(set_attr "type" "alu")
7214 (set_attr "mode" "QI,QI,SI")])
7215
7216 (define_insn "*andqi_1_slp"
7217 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
7218 (and:QI (match_dup 0)
7219 (match_operand:QI 1 "general_operand" "qi,qmi")))
7220 (clobber (reg:CC 17))]
7221 ""
7222 "and{b}\\t{%1, %0|%0, %1}"
7223 [(set_attr "type" "alu1")
7224 (set_attr "mode" "QI")])
7225
7226 (define_insn "*andqi_2"
7227 [(set (reg 17)
7228 (compare (and:QI
7229 (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7230 (match_operand:QI 2 "general_operand" "qim,qi,i"))
7231 (const_int 0)))
7232 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
7233 (and:QI (match_dup 1) (match_dup 2)))]
7234 "ix86_match_ccmode (insn, CCNOmode)
7235 && ix86_binary_operator_ok (AND, QImode, operands)"
7236 "*
7237 {
7238 if (which_alternative == 2)
7239 {
7240 if (GET_CODE (operands[2]) == CONST_INT
7241 && (INTVAL (operands[2]) & 0xffffff00))
7242 operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
7243 return \"and{l}\\t{%2, %k0|%k0, %2}\";
7244 }
7245 return \"and{b}\\t{%2, %0|%0, %2}\";
7246 }"
7247 [(set_attr "type" "alu")
7248 (set_attr "mode" "QI,QI,SI")])
7249
7250 (define_insn "*andqi_2_slp"
7251 [(set (reg 17)
7252 (compare (and:QI
7253 (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
7254 (match_operand:QI 1 "nonimmediate_operand" "qmi,qi"))
7255 (const_int 0)))
7256 (set (strict_low_part (match_dup 0))
7257 (and:QI (match_dup 0) (match_dup 1)))]
7258 "ix86_match_ccmode (insn, CCNOmode)"
7259 "and{b}\\t{%1, %0|%0, %1}"
7260 [(set_attr "type" "alu1")
7261 (set_attr "mode" "QI")])
7262
7263 ;; ??? A bug in recog prevents it from recognizing a const_int as an
7264 ;; operand to zero_extend in andqi_ext_1. It was checking explicitly
7265 ;; for a QImode operand, which of course failed.
7266
7267 (define_insn "andqi_ext_0"
7268 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7269 (const_int 8)
7270 (const_int 8))
7271 (and:SI
7272 (zero_extract:SI
7273 (match_operand 1 "ext_register_operand" "0")
7274 (const_int 8)
7275 (const_int 8))
7276 (match_operand 2 "const_int_operand" "n")))
7277 (clobber (reg:CC 17))]
7278 "(unsigned HOST_WIDE_INT)INTVAL (operands[2]) <= 0xff"
7279 "and{b}\\t{%2, %h0|%h0, %2}"
7280 [(set_attr "type" "alu")
7281 (set_attr "length_immediate" "1")
7282 (set_attr "mode" "QI")])
7283
7284 ;; Generated by peephole translating test to and. This shows up
7285 ;; often in fp comparisons.
7286
7287 (define_insn "*andqi_ext_0_cc"
7288 [(set (reg 17)
7289 (compare
7290 (and:SI
7291 (zero_extract:SI
7292 (match_operand 1 "ext_register_operand" "0")
7293 (const_int 8)
7294 (const_int 8))
7295 (match_operand 2 "const_int_operand" "n"))
7296 (const_int 0)))
7297 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7298 (const_int 8)
7299 (const_int 8))
7300 (and:SI
7301 (zero_extract:SI
7302 (match_dup 1)
7303 (const_int 8)
7304 (const_int 8))
7305 (match_dup 2)))]
7306 "ix86_match_ccmode (insn, CCNOmode)
7307 && (unsigned HOST_WIDE_INT)INTVAL (operands[2]) <= 0xff"
7308 "and{b}\\t{%2, %h0|%h0, %2}"
7309 [(set_attr "type" "alu")
7310 (set_attr "length_immediate" "1")
7311 (set_attr "mode" "QI")])
7312
7313 (define_insn "*andqi_ext_1"
7314 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7315 (const_int 8)
7316 (const_int 8))
7317 (and:SI
7318 (zero_extract:SI
7319 (match_operand 1 "ext_register_operand" "0")
7320 (const_int 8)
7321 (const_int 8))
7322 (zero_extend:SI
7323 (match_operand:QI 2 "general_operand" "Qm"))))
7324 (clobber (reg:CC 17))]
7325 "!TARGET_64BIT"
7326 "and{b}\\t{%2, %h0|%h0, %2}"
7327 [(set_attr "type" "alu")
7328 (set_attr "length_immediate" "0")
7329 (set_attr "mode" "QI")])
7330
7331 (define_insn "*andqi_ext_1_rex64"
7332 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7333 (const_int 8)
7334 (const_int 8))
7335 (and:SI
7336 (zero_extract:SI
7337 (match_operand 1 "ext_register_operand" "0")
7338 (const_int 8)
7339 (const_int 8))
7340 (zero_extend:SI
7341 (match_operand:QI 2 "ext_register_operand" "Q"))))
7342 (clobber (reg:CC 17))]
7343 "TARGET_64BIT"
7344 "and{b}\\t{%2, %h0|%h0, %2}"
7345 [(set_attr "type" "alu")
7346 (set_attr "length_immediate" "0")
7347 (set_attr "mode" "QI")])
7348
7349 (define_insn "*andqi_ext_2"
7350 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7351 (const_int 8)
7352 (const_int 8))
7353 (and:SI
7354 (zero_extract:SI
7355 (match_operand 1 "ext_register_operand" "%0")
7356 (const_int 8)
7357 (const_int 8))
7358 (zero_extract:SI
7359 (match_operand 2 "ext_register_operand" "Q")
7360 (const_int 8)
7361 (const_int 8))))
7362 (clobber (reg:CC 17))]
7363 ""
7364 "and{b}\\t{%h2, %h0|%h0, %h2}"
7365 [(set_attr "type" "alu")
7366 (set_attr "length_immediate" "0")
7367 (set_attr "mode" "QI")])
7368 \f
7369 ;; Logical inclusive OR instructions
7370
7371 ;; %%% This used to optimize known byte-wide and operations to memory.
7372 ;; If this is considered useful, it should be done with splitters.
7373
7374 (define_expand "iorsi3"
7375 [(set (match_operand:SI 0 "nonimmediate_operand" "")
7376 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "")
7377 (match_operand:SI 2 "general_operand" "")))
7378 (clobber (reg:CC 17))]
7379 ""
7380 "ix86_expand_binary_operator (IOR, SImode, operands); DONE;")
7381
7382 (define_insn "*iorsi_1"
7383 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7384 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
7385 (match_operand:SI 2 "general_operand" "ri,rmi")))
7386 (clobber (reg:CC 17))]
7387 "ix86_binary_operator_ok (IOR, SImode, operands)"
7388 "or{l}\\t{%2, %0|%0, %2}"
7389 [(set_attr "type" "alu")
7390 (set_attr "mode" "SI")])
7391
7392 (define_insn "*iorsi_2"
7393 [(set (reg 17)
7394 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
7395 (match_operand:SI 2 "general_operand" "rim,ri"))
7396 (const_int 0)))
7397 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
7398 (ior:SI (match_dup 1) (match_dup 2)))]
7399 "ix86_match_ccmode (insn, CCNOmode)
7400 && ix86_binary_operator_ok (IOR, SImode, operands)"
7401 "or{l}\\t{%2, %0|%0, %2}"
7402 [(set_attr "type" "alu")
7403 (set_attr "mode" "SI")])
7404
7405 (define_insn "*iorsi_3"
7406 [(set (reg 17)
7407 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
7408 (match_operand:SI 2 "general_operand" "rim"))
7409 (const_int 0)))
7410 (clobber (match_scratch:SI 0 "=r"))]
7411 "ix86_match_ccmode (insn, CCNOmode)
7412 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7413 "or{l}\\t{%2, %0|%0, %2}"
7414 [(set_attr "type" "alu")
7415 (set_attr "mode" "SI")])
7416
7417 (define_expand "iorhi3"
7418 [(set (match_operand:HI 0 "nonimmediate_operand" "")
7419 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "")
7420 (match_operand:HI 2 "general_operand" "")))
7421 (clobber (reg:CC 17))]
7422 "TARGET_HIMODE_MATH"
7423 "ix86_expand_binary_operator (IOR, HImode, operands); DONE;")
7424
7425 (define_insn "*iorhi_1"
7426 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
7427 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
7428 (match_operand:HI 2 "general_operand" "rmi,ri")))
7429 (clobber (reg:CC 17))]
7430 "ix86_binary_operator_ok (IOR, HImode, operands)"
7431 "or{w}\\t{%2, %0|%0, %2}"
7432 [(set_attr "type" "alu")
7433 (set_attr "mode" "HI")])
7434
7435 (define_insn "*iorhi_2"
7436 [(set (reg 17)
7437 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
7438 (match_operand:HI 2 "general_operand" "rim,ri"))
7439 (const_int 0)))
7440 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
7441 (ior:HI (match_dup 1) (match_dup 2)))]
7442 "ix86_match_ccmode (insn, CCNOmode)
7443 && ix86_binary_operator_ok (IOR, HImode, operands)"
7444 "or{w}\\t{%2, %0|%0, %2}"
7445 [(set_attr "type" "alu")
7446 (set_attr "mode" "HI")])
7447
7448 (define_insn "*iorhi_3"
7449 [(set (reg 17)
7450 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
7451 (match_operand:HI 2 "general_operand" "rim"))
7452 (const_int 0)))
7453 (clobber (match_scratch:HI 0 "=r"))]
7454 "ix86_match_ccmode (insn, CCNOmode)
7455 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7456 "or{w}\\t{%2, %0|%0, %2}"
7457 [(set_attr "type" "alu")
7458 (set_attr "mode" "HI")])
7459
7460 (define_expand "iorqi3"
7461 [(set (match_operand:QI 0 "nonimmediate_operand" "")
7462 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "")
7463 (match_operand:QI 2 "general_operand" "")))
7464 (clobber (reg:CC 17))]
7465 "TARGET_QIMODE_MATH"
7466 "ix86_expand_binary_operator (IOR, QImode, operands); DONE;")
7467
7468 ;; %%% Potential partial reg stall on alternative 2. What to do?
7469 (define_insn "*iorqi_1"
7470 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
7471 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7472 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
7473 (clobber (reg:CC 17))]
7474 "ix86_binary_operator_ok (IOR, QImode, operands)"
7475 "@
7476 or{b}\\t{%2, %0|%0, %2}
7477 or{b}\\t{%2, %0|%0, %2}
7478 or{l}\\t{%k2, %k0|%k0, %k2}"
7479 [(set_attr "type" "alu")
7480 (set_attr "mode" "QI,QI,SI")])
7481
7482 (define_insn "*iorqi_1_slp"
7483 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
7484 (ior:QI (match_dup 0)
7485 (match_operand:QI 1 "general_operand" "qmi,qi")))
7486 (clobber (reg:CC 17))]
7487 ""
7488 "or{b}\\t{%1, %0|%0, %1}"
7489 [(set_attr "type" "alu1")
7490 (set_attr "mode" "QI")])
7491
7492 (define_insn "*iorqi_2"
7493 [(set (reg 17)
7494 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
7495 (match_operand:QI 2 "general_operand" "qim,qi"))
7496 (const_int 0)))
7497 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
7498 (ior:QI (match_dup 1) (match_dup 2)))]
7499 "ix86_match_ccmode (insn, CCNOmode)
7500 && ix86_binary_operator_ok (IOR, QImode, operands)"
7501 "or{b}\\t{%2, %0|%0, %2}"
7502 [(set_attr "type" "alu")
7503 (set_attr "mode" "QI")])
7504
7505 (define_insn "*iorqi_2_slp"
7506 [(set (reg 17)
7507 (compare (ior:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
7508 (match_operand:QI 1 "general_operand" "qim,qi"))
7509 (const_int 0)))
7510 (set (strict_low_part (match_dup 0))
7511 (ior:QI (match_dup 0) (match_dup 1)))]
7512 "ix86_match_ccmode (insn, CCNOmode)"
7513 "or{b}\\t{%1, %0|%0, %1}"
7514 [(set_attr "type" "alu1")
7515 (set_attr "mode" "QI")])
7516
7517 (define_insn "*iorqi_3"
7518 [(set (reg 17)
7519 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
7520 (match_operand:QI 2 "general_operand" "qim"))
7521 (const_int 0)))
7522 (clobber (match_scratch:QI 0 "=q"))]
7523 "ix86_match_ccmode (insn, CCNOmode)
7524 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7525 "or{b}\\t{%2, %0|%0, %2}"
7526 [(set_attr "type" "alu")
7527 (set_attr "mode" "QI")])
7528
7529 \f
7530 ;; Logical XOR instructions
7531
7532 ;; %%% This used to optimize known byte-wide and operations to memory.
7533 ;; If this is considered useful, it should be done with splitters.
7534
7535 (define_expand "xorsi3"
7536 [(set (match_operand:SI 0 "nonimmediate_operand" "")
7537 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "")
7538 (match_operand:SI 2 "general_operand" "")))
7539 (clobber (reg:CC 17))]
7540 ""
7541 "ix86_expand_binary_operator (XOR, SImode, operands); DONE;")
7542
7543 (define_insn "*xorsi_1"
7544 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
7545 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
7546 (match_operand:SI 2 "general_operand" "ri,rm")))
7547 (clobber (reg:CC 17))]
7548 "ix86_binary_operator_ok (XOR, SImode, operands)"
7549 "xor{l}\\t{%2, %0|%0, %2}"
7550 [(set_attr "type" "alu")
7551 (set_attr "mode" "SI")])
7552
7553 (define_insn "*xorsi_2"
7554 [(set (reg 17)
7555 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
7556 (match_operand:SI 2 "general_operand" "rim,ri"))
7557 (const_int 0)))
7558 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
7559 (xor:SI (match_dup 1) (match_dup 2)))]
7560 "ix86_match_ccmode (insn, CCNOmode)
7561 && ix86_binary_operator_ok (XOR, SImode, operands)"
7562 "xor{l}\\t{%2, %0|%0, %2}"
7563 [(set_attr "type" "alu")
7564 (set_attr "mode" "SI")])
7565
7566 (define_insn "*xorsi_3"
7567 [(set (reg 17)
7568 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
7569 (match_operand:SI 2 "general_operand" "rim"))
7570 (const_int 0)))
7571 (clobber (match_scratch:SI 0 "=r"))]
7572 "ix86_match_ccmode (insn, CCNOmode)
7573 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7574 "xor{l}\\t{%2, %0|%0, %2}"
7575 [(set_attr "type" "alu")
7576 (set_attr "mode" "SI")])
7577
7578 (define_expand "xorhi3"
7579 [(set (match_operand:HI 0 "nonimmediate_operand" "")
7580 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "")
7581 (match_operand:HI 2 "general_operand" "")))
7582 (clobber (reg:CC 17))]
7583 "TARGET_HIMODE_MATH"
7584 "ix86_expand_binary_operator (XOR, HImode, operands); DONE;")
7585
7586 (define_insn "*xorhi_1"
7587 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
7588 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
7589 (match_operand:HI 2 "general_operand" "rmi,ri")))
7590 (clobber (reg:CC 17))]
7591 "ix86_binary_operator_ok (XOR, HImode, operands)"
7592 "xor{w}\\t{%2, %0|%0, %2}"
7593 [(set_attr "type" "alu")
7594 (set_attr "mode" "HI")])
7595
7596 (define_insn "*xorhi_2"
7597 [(set (reg 17)
7598 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
7599 (match_operand:HI 2 "general_operand" "rim,ri"))
7600 (const_int 0)))
7601 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
7602 (xor:HI (match_dup 1) (match_dup 2)))]
7603 "ix86_match_ccmode (insn, CCNOmode)
7604 && ix86_binary_operator_ok (XOR, HImode, operands)"
7605 "xor{w}\\t{%2, %0|%0, %2}"
7606 [(set_attr "type" "alu")
7607 (set_attr "mode" "HI")])
7608
7609 (define_insn "*xorhi_3"
7610 [(set (reg 17)
7611 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
7612 (match_operand:HI 2 "general_operand" "rim"))
7613 (const_int 0)))
7614 (clobber (match_scratch:HI 0 "=r"))]
7615 "ix86_match_ccmode (insn, CCNOmode)
7616 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7617 "xor{w}\\t{%2, %0|%0, %2}"
7618 [(set_attr "type" "alu")
7619 (set_attr "mode" "HI")])
7620
7621 (define_expand "xorqi3"
7622 [(set (match_operand:QI 0 "nonimmediate_operand" "")
7623 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "")
7624 (match_operand:QI 2 "general_operand" "")))
7625 (clobber (reg:CC 17))]
7626 "TARGET_QIMODE_MATH"
7627 "ix86_expand_binary_operator (XOR, QImode, operands); DONE;")
7628
7629 ;; %%% Potential partial reg stall on alternative 2. What to do?
7630 (define_insn "*xorqi_1"
7631 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
7632 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
7633 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
7634 (clobber (reg:CC 17))]
7635 "ix86_binary_operator_ok (XOR, QImode, operands)"
7636 "@
7637 xor{b}\\t{%2, %0|%0, %2}
7638 xor{b}\\t{%2, %0|%0, %2}
7639 xor{l}\\t{%k2, %k0|%k0, %k2}"
7640 [(set_attr "type" "alu")
7641 (set_attr "mode" "QI,QI,SI")])
7642
7643 (define_insn "*xorqi_ext_1"
7644 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7645 (const_int 8)
7646 (const_int 8))
7647 (xor:SI
7648 (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
7649 (const_int 8)
7650 (const_int 8))
7651 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
7652 (const_int 8)
7653 (const_int 8))))
7654 (clobber (reg:CC 17))]
7655 ""
7656 "xor{b}\\t{%h2, %h0|%h0, %h2}"
7657 [(set_attr "type" "alu")
7658 (set_attr "length_immediate" "0")
7659 (set_attr "mode" "QI")])
7660
7661 (define_insn "*xorqi_cc_1"
7662 [(set (reg 17)
7663 (compare
7664 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
7665 (match_operand:QI 2 "general_operand" "qim,qi"))
7666 (const_int 0)))
7667 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
7668 (xor:QI (match_dup 1) (match_dup 2)))]
7669 "ix86_match_ccmode (insn, CCNOmode)
7670 && ix86_binary_operator_ok (XOR, QImode, operands)"
7671 "xor{b}\\t{%2, %0|%0, %2}"
7672 [(set_attr "type" "alu")
7673 (set_attr "mode" "QI")])
7674
7675 (define_insn "*xorqi_cc_2"
7676 [(set (reg 17)
7677 (compare
7678 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
7679 (match_operand:QI 2 "general_operand" "qim"))
7680 (const_int 0)))
7681 (clobber (match_scratch:QI 0 "=q"))]
7682 "ix86_match_ccmode (insn, CCNOmode)
7683 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7684 "xor{b}\\t{%2, %0|%0, %2}"
7685 [(set_attr "type" "alu")
7686 (set_attr "mode" "QI")])
7687
7688 (define_insn "*xorqi_cc_ext_1"
7689 [(set (reg 17)
7690 (compare
7691 (xor:SI
7692 (zero_extract:SI
7693 (match_operand 1 "ext_register_operand" "0")
7694 (const_int 8)
7695 (const_int 8))
7696 (match_operand:QI 2 "general_operand" "qmn"))
7697 (const_int 0)))
7698 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
7699 (const_int 8)
7700 (const_int 8))
7701 (xor:SI
7702 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
7703 (match_dup 2)))]
7704 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7705 "xor{b}\\t{%2, %h0|%h0, %2}"
7706 [(set_attr "type" "alu")
7707 (set_attr "mode" "QI")])
7708
7709 (define_insn "*xorqi_cc_ext_1_rex64"
7710 [(set (reg 17)
7711 (compare
7712 (xor:SI
7713 (zero_extract:SI
7714 (match_operand 1 "ext_register_operand" "0")
7715 (const_int 8)
7716 (const_int 8))
7717 (match_operand:QI 2 "nonmemory_operand" "Qn"))
7718 (const_int 0)))
7719 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
7720 (const_int 8)
7721 (const_int 8))
7722 (xor:SI
7723 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
7724 (match_dup 2)))]
7725 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7726 "xor{b}\\t{%2, %h0|%h0, %2}"
7727 [(set_attr "type" "alu")
7728 (set_attr "mode" "QI")])
7729
7730 (define_expand "xorqi_cc_ext_1"
7731 [(parallel [
7732 (set (reg:CCNO 17)
7733 (compare:CCNO
7734 (xor:SI
7735 (zero_extract:SI
7736 (match_operand 1 "ext_register_operand" "")
7737 (const_int 8)
7738 (const_int 8))
7739 (match_operand:QI 2 "general_operand" ""))
7740 (const_int 0)))
7741 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
7742 (const_int 8)
7743 (const_int 8))
7744 (xor:SI
7745 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
7746 (match_dup 2)))])]
7747 ""
7748 "")
7749 \f
7750 ;; Negation instructions
7751
7752 ;; %%% define_expand from the very first?
7753
7754 (define_expand "negdi2"
7755 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
7756 (neg:DI (match_operand:DI 1 "nonimmediate_operand" "")))
7757 (clobber (reg:CC 17))])]
7758 ""
7759 "ix86_expand_unary_operator (NEG, DImode, operands); DONE;")
7760
7761 (define_insn "*negdi2_1"
7762 [(set (match_operand:DI 0 "nonimmediate_operand" "=ro")
7763 (neg:DI (match_operand:DI 1 "general_operand" "0")))
7764 (clobber (reg:CC 17))]
7765 "!TARGET_64BIT
7766 && ix86_unary_operator_ok (NEG, DImode, operands)"
7767 "#")
7768
7769 (define_split
7770 [(set (match_operand:DI 0 "nonimmediate_operand" "")
7771 (neg:DI (match_operand:DI 1 "general_operand" "")))
7772 (clobber (reg:CC 17))]
7773 "reload_completed
7774 && !TARGET_64BIT"
7775 [(parallel
7776 [(set (reg:CCZ 17)
7777 (compare:CCZ (neg:SI (match_dup 2)) (const_int 0)))
7778 (set (match_dup 0) (neg:SI (match_dup 2)))])
7779 (parallel
7780 [(set (match_dup 1)
7781 (plus:SI (plus:SI (ltu:SI (reg:CC 17) (const_int 0))
7782 (match_dup 3))
7783 (const_int 0)))
7784 (clobber (reg:CC 17))])
7785 (parallel
7786 [(set (match_dup 1)
7787 (neg:SI (match_dup 1)))
7788 (clobber (reg:CC 17))])]
7789 "split_di (operands+1, 1, operands+2, operands+3);
7790 split_di (operands+0, 1, operands+0, operands+1);")
7791
7792 (define_expand "negsi2"
7793 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
7794 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "")))
7795 (clobber (reg:CC 17))])]
7796 ""
7797 "ix86_expand_unary_operator (NEG, SImode, operands); DONE;")
7798
7799 (define_insn "*negsi2_1"
7800 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
7801 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0")))
7802 (clobber (reg:CC 17))]
7803 "ix86_unary_operator_ok (NEG, SImode, operands)"
7804 "neg{l}\\t%0"
7805 [(set_attr "type" "negnot")
7806 (set_attr "mode" "SI")])
7807
7808 ;; The problem with neg is that it does not perform (compare x 0),
7809 ;; it really performs (compare 0 x), which leaves us with the zero
7810 ;; flag being the only useful item.
7811
7812 (define_insn "*negsi2_cmpz"
7813 [(set (reg:CCZ 17)
7814 (compare:CCZ (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
7815 (const_int 0)))
7816 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
7817 (neg:SI (match_dup 1)))]
7818 "ix86_unary_operator_ok (NEG, SImode, operands)"
7819 "neg{l}\\t%0"
7820 [(set_attr "type" "negnot")
7821 (set_attr "mode" "SI")])
7822
7823 (define_expand "neghi2"
7824 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
7825 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "")))
7826 (clobber (reg:CC 17))])]
7827 "TARGET_HIMODE_MATH"
7828 "ix86_expand_unary_operator (NEG, HImode, operands); DONE;")
7829
7830 (define_insn "*neghi2_1"
7831 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
7832 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0")))
7833 (clobber (reg:CC 17))]
7834 "ix86_unary_operator_ok (NEG, HImode, operands)"
7835 "neg{w}\\t%0"
7836 [(set_attr "type" "negnot")
7837 (set_attr "mode" "HI")])
7838
7839 (define_insn "*neghi2_cmpz"
7840 [(set (reg:CCZ 17)
7841 (compare:CCZ (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
7842 (const_int 0)))
7843 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
7844 (neg:HI (match_dup 1)))]
7845 "ix86_unary_operator_ok (NEG, HImode, operands)"
7846 "neg{w}\\t%0"
7847 [(set_attr "type" "negnot")
7848 (set_attr "mode" "HI")])
7849
7850 (define_expand "negqi2"
7851 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
7852 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "")))
7853 (clobber (reg:CC 17))])]
7854 "TARGET_QIMODE_MATH"
7855 "ix86_expand_unary_operator (NEG, QImode, operands); DONE;")
7856
7857 (define_insn "*negqi2_1"
7858 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
7859 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0")))
7860 (clobber (reg:CC 17))]
7861 "ix86_unary_operator_ok (NEG, QImode, operands)"
7862 "neg{b}\\t%0"
7863 [(set_attr "type" "negnot")
7864 (set_attr "mode" "QI")])
7865
7866 (define_insn "*negqi2_cmpz"
7867 [(set (reg:CCZ 17)
7868 (compare:CCZ (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
7869 (const_int 0)))
7870 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
7871 (neg:QI (match_dup 1)))]
7872 "ix86_unary_operator_ok (NEG, QImode, operands)"
7873 "neg{b}\\t%0"
7874 [(set_attr "type" "negnot")
7875 (set_attr "mode" "QI")])
7876
7877 ;; Changing of sign for FP values is doable using integer unit too.
7878
7879 (define_expand "negsf2"
7880 [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
7881 (neg:SF (match_operand:SF 1 "nonimmediate_operand" "")))
7882 (clobber (reg:CC 17))])]
7883 "TARGET_80387"
7884 "ix86_expand_unary_operator (NEG, SFmode, operands); DONE;")
7885
7886 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
7887 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
7888 ;; to itself.
7889 (define_insn "*negsf2_if"
7890 [(set (match_operand:SF 0 "nonimmediate_operand" "=f#r,rm#f")
7891 (neg:SF (match_operand:SF 1 "nonimmediate_operand" "0,0")))
7892 (clobber (reg:CC 17))]
7893 "TARGET_80387 && ix86_unary_operator_ok (NEG, SFmode, operands)"
7894 "#")
7895
7896 (define_split
7897 [(set (match_operand:SF 0 "register_operand" "")
7898 (neg:SF (match_operand:SF 1 "register_operand" "")))
7899 (clobber (reg:CC 17))]
7900 "TARGET_80387 && FP_REGNO_P (REGNO (operands[0])) && reload_completed"
7901 [(set (match_dup 0)
7902 (neg:SF (match_dup 1)))]
7903 "")
7904
7905 (define_split
7906 [(set (match_operand:SF 0 "register_operand" "")
7907 (neg:SF (match_operand:SF 1 "register_operand" "")))
7908 (clobber (reg:CC 17))]
7909 "TARGET_80387 && reload_completed && !FP_REGNO_P (REGNO (operands[0]))"
7910 [(parallel [(set (match_dup 0) (xor:SI (match_dup 0) (match_dup 1)))
7911 (clobber (reg:CC 17))])]
7912 "operands[1] = GEN_INT (0x80000000);
7913 operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]));")
7914
7915 (define_split
7916 [(set (match_operand 0 "memory_operand" "")
7917 (neg (match_operand 1 "memory_operand" "")))
7918 (clobber (reg:CC 17))]
7919 "TARGET_80387 && reload_completed && FLOAT_MODE_P (GET_MODE (operands[0]))"
7920 [(parallel [(set (match_dup 0) (xor:QI (match_dup 0) (match_dup 1)))
7921 (clobber (reg:CC 17))])]
7922 "
7923 {
7924 int size = GET_MODE_SIZE (GET_MODE (operands[1]));
7925
7926 /* XFmode's size is 12, but only 10 bytes are used. */
7927 if (size == 12)
7928 size = 10;
7929 operands[0] = gen_rtx_MEM (QImode, XEXP (operands[0], 0));
7930 operands[0] = adj_offsettable_operand (operands[0], size - 1);
7931 operands[1] = GEN_INT (0x80);
7932 }")
7933
7934 (define_expand "negdf2"
7935 [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
7936 (neg:DF (match_operand:DF 1 "nonimmediate_operand" "")))
7937 (clobber (reg:CC 17))])]
7938 "TARGET_80387"
7939 "ix86_expand_unary_operator (NEG, DFmode, operands); DONE;")
7940
7941 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
7942 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
7943 ;; to itself.
7944 (define_insn "*negdf2_if"
7945 [(set (match_operand:DF 0 "nonimmediate_operand" "=f#r,rm#f")
7946 (neg:DF (match_operand:DF 1 "nonimmediate_operand" "0,0")))
7947 (clobber (reg:CC 17))]
7948 "TARGET_80387 && ix86_unary_operator_ok (NEG, DFmode, operands)"
7949 "#")
7950
7951 (define_split
7952 [(set (match_operand:DF 0 "register_operand" "")
7953 (neg:DF (match_operand:DF 1 "register_operand" "")))
7954 (clobber (reg:CC 17))]
7955 "TARGET_80387 && FP_REGNO_P (REGNO (operands[0])) && reload_completed"
7956 [(set (match_dup 0)
7957 (neg:DF (match_dup 1)))]
7958 "")
7959
7960 (define_split
7961 [(set (match_operand:DF 0 "register_operand" "")
7962 (neg:DF (match_operand:DF 1 "register_operand" "")))
7963 (clobber (reg:CC 17))]
7964 "TARGET_80387 && reload_completed && !FP_REGNO_P (REGNO (operands[0]))"
7965 [(parallel [(set (match_dup 3) (xor:SI (match_dup 3) (match_dup 4)))
7966 (clobber (reg:CC 17))])]
7967 "operands[4] = GEN_INT (0x80000000);
7968 split_di (operands+0, 1, operands+2, operands+3);")
7969
7970 (define_expand "negxf2"
7971 [(parallel [(set (match_operand:XF 0 "nonimmediate_operand" "")
7972 (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))
7973 (clobber (reg:CC 17))])]
7974 "TARGET_80387 && !TARGET_64BIT"
7975 "ix86_expand_unary_operator (NEG, XFmode, operands); DONE;")
7976
7977 (define_expand "negtf2"
7978 [(parallel [(set (match_operand:TF 0 "nonimmediate_operand" "")
7979 (neg:TF (match_operand:TF 1 "nonimmediate_operand" "")))
7980 (clobber (reg:CC 17))])]
7981 "TARGET_80387"
7982 "ix86_expand_unary_operator (NEG, TFmode, operands); DONE;")
7983
7984 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
7985 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
7986 ;; to itself.
7987 (define_insn "*negxf2_if"
7988 [(set (match_operand:XF 0 "nonimmediate_operand" "=f#r,rm#f")
7989 (neg:XF (match_operand:XF 1 "nonimmediate_operand" "0,0")))
7990 (clobber (reg:CC 17))]
7991 "TARGET_80387 && !TARGET_64BIT
7992 && ix86_unary_operator_ok (NEG, XFmode, operands)"
7993 "#")
7994
7995 (define_split
7996 [(set (match_operand:XF 0 "register_operand" "")
7997 (neg:XF (match_operand:XF 1 "register_operand" "")))
7998 (clobber (reg:CC 17))]
7999 "TARGET_80387 && FP_REGNO_P (REGNO (operands[0])) && reload_completed"
8000 [(set (match_dup 0)
8001 (neg:XF (match_dup 1)))]
8002 "")
8003
8004 (define_split
8005 [(set (match_operand:XF 0 "register_operand" "")
8006 (neg:XF (match_operand:XF 1 "register_operand" "")))
8007 (clobber (reg:CC 17))]
8008 "TARGET_80387 && reload_completed && !FP_REGNO_P (REGNO (operands[0]))"
8009 [(parallel [(set (match_dup 0) (xor:SI (match_dup 0) (match_dup 1)))
8010 (clobber (reg:CC 17))])]
8011 "operands[1] = GEN_INT (0x8000);
8012 operands[0] = gen_rtx_REG (SImode, true_regnum (operands[0]) + 2);")
8013
8014 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
8015 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
8016 ;; to itself.
8017 (define_insn "*negtf2_if"
8018 [(set (match_operand:TF 0 "nonimmediate_operand" "=f#r,rm#f")
8019 (neg:TF (match_operand:TF 1 "nonimmediate_operand" "0,0")))
8020 (clobber (reg:CC 17))]
8021 "TARGET_80387 && ix86_unary_operator_ok (NEG, TFmode, operands)"
8022 "#")
8023
8024 (define_split
8025 [(set (match_operand:TF 0 "register_operand" "")
8026 (neg:TF (match_operand:TF 1 "register_operand" "")))
8027 (clobber (reg:CC 17))]
8028 "TARGET_80387 && FP_REGNO_P (REGNO (operands[0])) && reload_completed"
8029 [(set (match_dup 0)
8030 (neg:TF (match_dup 1)))]
8031 "")
8032
8033 (define_split
8034 [(set (match_operand:TF 0 "register_operand" "")
8035 (neg:TF (match_operand:TF 1 "register_operand" "")))
8036 (clobber (reg:CC 17))]
8037 "TARGET_80387 && reload_completed && !FP_REGNO_P (REGNO (operands[0]))"
8038 [(parallel [(set (match_dup 0) (xor:SI (match_dup 0) (match_dup 1)))
8039 (clobber (reg:CC 17))])]
8040 "operands[1] = GEN_INT (0x8000);
8041 operands[0] = gen_rtx_REG (SImode, true_regnum (operands[0]) + 2);")
8042
8043 ;; Conditionize these after reload. If they matches before reload, we
8044 ;; lose the clobber and ability to use integer instructions.
8045
8046 (define_insn "*negsf2_1"
8047 [(set (match_operand:SF 0 "register_operand" "=f")
8048 (neg:SF (match_operand:SF 1 "register_operand" "0")))]
8049 "TARGET_80387 && reload_completed"
8050 "fchs"
8051 [(set_attr "type" "fsgn")
8052 (set_attr "mode" "SF")
8053 (set_attr "ppro_uops" "few")])
8054
8055 (define_insn "*negdf2_1"
8056 [(set (match_operand:DF 0 "register_operand" "=f")
8057 (neg:DF (match_operand:DF 1 "register_operand" "0")))]
8058 "TARGET_80387 && reload_completed"
8059 "fchs"
8060 [(set_attr "type" "fsgn")
8061 (set_attr "mode" "DF")
8062 (set_attr "ppro_uops" "few")])
8063
8064 (define_insn "*negextendsfdf2"
8065 [(set (match_operand:DF 0 "register_operand" "=f")
8066 (neg:DF (float_extend:DF
8067 (match_operand:SF 1 "register_operand" "0"))))]
8068 "TARGET_80387"
8069 "fchs"
8070 [(set_attr "type" "fsgn")
8071 (set_attr "mode" "DF")
8072 (set_attr "ppro_uops" "few")])
8073
8074 (define_insn "*negxf2_1"
8075 [(set (match_operand:XF 0 "register_operand" "=f")
8076 (neg:XF (match_operand:XF 1 "register_operand" "0")))]
8077 "TARGET_80387 && !TARGET_64BIT && reload_completed"
8078 "fchs"
8079 [(set_attr "type" "fsgn")
8080 (set_attr "mode" "XF")
8081 (set_attr "ppro_uops" "few")])
8082
8083 (define_insn "*negextenddfxf2"
8084 [(set (match_operand:XF 0 "register_operand" "=f")
8085 (neg:XF (float_extend:XF
8086 (match_operand:DF 1 "register_operand" "0"))))]
8087 "TARGET_80387 && !TARGET_64BIT"
8088 "fchs"
8089 [(set_attr "type" "fsgn")
8090 (set_attr "mode" "XF")
8091 (set_attr "ppro_uops" "few")])
8092
8093 (define_insn "*negextendsfxf2"
8094 [(set (match_operand:XF 0 "register_operand" "=f")
8095 (neg:XF (float_extend:XF
8096 (match_operand:SF 1 "register_operand" "0"))))]
8097 "TARGET_80387 && !TARGET_64BIT"
8098 "fchs"
8099 [(set_attr "type" "fsgn")
8100 (set_attr "mode" "XF")
8101 (set_attr "ppro_uops" "few")])
8102
8103 (define_insn "*negtf2_1"
8104 [(set (match_operand:TF 0 "register_operand" "=f")
8105 (neg:TF (match_operand:TF 1 "register_operand" "0")))]
8106 "TARGET_80387 && reload_completed"
8107 "fchs"
8108 [(set_attr "type" "fsgn")
8109 (set_attr "mode" "XF")
8110 (set_attr "ppro_uops" "few")])
8111
8112 (define_insn "*negextenddftf2"
8113 [(set (match_operand:TF 0 "register_operand" "=f")
8114 (neg:TF (float_extend:TF
8115 (match_operand:DF 1 "register_operand" "0"))))]
8116 "TARGET_80387"
8117 "fchs"
8118 [(set_attr "type" "fsgn")
8119 (set_attr "mode" "XF")
8120 (set_attr "ppro_uops" "few")])
8121
8122 (define_insn "*negextendsftf2"
8123 [(set (match_operand:TF 0 "register_operand" "=f")
8124 (neg:TF (float_extend:TF
8125 (match_operand:SF 1 "register_operand" "0"))))]
8126 "TARGET_80387"
8127 "fchs"
8128 [(set_attr "type" "fsgn")
8129 (set_attr "mode" "XF")
8130 (set_attr "ppro_uops" "few")])
8131 \f
8132 ;; Absolute value instructions
8133
8134 (define_expand "abssf2"
8135 [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
8136 (neg:SF (match_operand:SF 1 "nonimmediate_operand" "")))
8137 (clobber (reg:CC 17))])]
8138 "TARGET_80387"
8139 "if (TARGET_SSE)
8140 {
8141 /* In case operand is in memory, we will not use SSE. */
8142 if (memory_operand (operands[0], VOIDmode)
8143 && rtx_equal_p (operands[0], operands[1]))
8144 emit_insn (gen_abssf2_memory (operands[0], operands[1]));
8145 else
8146 {
8147 /* Using SSE is tricky, since we need bitwise negation of -0
8148 in register. */
8149 rtx reg = gen_reg_rtx (SFmode);
8150 emit_move_insn (reg, gen_lowpart (SFmode, GEN_INT (0x80000000)));
8151 emit_insn (gen_abssf2_ifs (operands[0], operands[1], reg));
8152 }
8153 DONE;
8154 }
8155 ix86_expand_unary_operator (ABS, SFmode, operands); DONE;")
8156
8157 (define_insn "abssf2_memory"
8158 [(set (match_operand:SF 0 "memory_operand" "=m")
8159 (abs:SF (match_operand:SF 1 "memory_operand" "0")))
8160 (clobber (reg:CC 17))]
8161 "ix86_unary_operator_ok (ABS, SFmode, operands)"
8162 "#")
8163
8164 (define_insn "abssf2_ifs"
8165 [(set (match_operand:SF 0 "nonimmediate_operand" "=x#fr,f#xr,r#xf")
8166 (abs:SF (match_operand:SF 1 "nonimmediate_operand" "x,0,0")))
8167 (use (match_operand:SF 2 "nonmemory_operand" "*0#x,*X#x,*X#x"))
8168 (clobber (reg:CC 17))]
8169 "TARGET_SSE"
8170 "#")
8171
8172 (define_split
8173 [(set (match_operand:SF 0 "memory_operand" "")
8174 (abs:SF (match_operand:SF 1 "memory_operand" "")))
8175 (use (match_operand:SF 2 "" ""))
8176 (clobber (reg:CC 17))]
8177 ""
8178 [(parallel [(set (match_dup 0)
8179 (abs:SF (match_dup 1)))
8180 (clobber (reg:CC 17))])])
8181
8182 (define_split
8183 [(set (match_operand:SF 0 "register_operand" "")
8184 (abs:SF (match_operand:SF 1 "register_operand" "")))
8185 (use (match_operand:SF 2 "" ""))
8186 (clobber (reg:CC 17))]
8187 "reload_completed && !SSE_REG_P (operands[0])"
8188 [(parallel [(set (match_dup 0)
8189 (abs:SF (match_dup 1)))
8190 (clobber (reg:CC 17))])])
8191
8192 (define_split
8193 [(set (match_operand:SF 0 "register_operand" "")
8194 (abs:SF (match_operand:SF 1 "register_operand" "")))
8195 (use (match_operand:SF 2 "register_operand" ""))
8196 (clobber (reg:CC 17))]
8197 "reload_completed && SSE_REG_P (operands[0])"
8198 [(set (subreg:TI (match_dup 0) 0)
8199 (and:TI (not:TI (subreg:TI (match_dup 2) 0))
8200 (subreg:TI (match_dup 1) 0)))])
8201
8202 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
8203 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
8204 ;; to itself.
8205 (define_insn "*abssf2_if"
8206 [(set (match_operand:SF 0 "nonimmediate_operand" "=f#r,rm#f")
8207 (abs:SF (match_operand:SF 1 "nonimmediate_operand" "0,0")))
8208 (clobber (reg:CC 17))]
8209 "TARGET_80387 && ix86_unary_operator_ok (ABS, SFmode, operands) && !TARGET_SSE"
8210 "#")
8211
8212 (define_split
8213 [(set (match_operand:SF 0 "register_operand" "")
8214 (abs:SF (match_operand:SF 1 "register_operand" "")))
8215 (clobber (reg:CC 17))]
8216 "TARGET_80387 && FP_REGNO_P (REGNO (operands[0]))"
8217 [(set (match_dup 0)
8218 (abs:SF (match_dup 1)))]
8219 "")
8220
8221 (define_split
8222 [(set (match_operand:SF 0 "register_operand" "")
8223 (abs:SF (match_operand:SF 1 "register_operand" "")))
8224 (clobber (reg:CC 17))]
8225 "TARGET_80387 && reload_completed && !FP_REGNO_P (REGNO (operands[0]))"
8226 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (match_dup 1)))
8227 (clobber (reg:CC 17))])]
8228 "operands[1] = GEN_INT (~0x80000000);
8229 operands[0] = gen_rtx_REG (SImode, REGNO (operands[0]));")
8230
8231 (define_split
8232 [(set (match_operand 0 "memory_operand" "")
8233 (abs (match_operand 1 "memory_operand" "")))
8234 (clobber (reg:CC 17))]
8235 "TARGET_80387 && reload_completed && FLOAT_MODE_P (GET_MODE (operands[0]))"
8236 [(parallel [(set (match_dup 0) (and:QI (match_dup 0) (match_dup 1)))
8237 (clobber (reg:CC 17))])]
8238 "
8239 {
8240 int size = GET_MODE_SIZE (GET_MODE (operands[1]));
8241
8242 /* XFmode's size is 12, but only 10 bytes are used. */
8243 if (size == 12)
8244 size = 10;
8245 operands[0] = gen_rtx_MEM (QImode, XEXP (operands[0], 0));
8246 operands[0] = adj_offsettable_operand (operands[0], size - 1);
8247 operands[1] = GEN_INT (~0x80);
8248 }")
8249
8250 (define_expand "absdf2"
8251 [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
8252 (neg:DF (match_operand:DF 1 "nonimmediate_operand" "")))
8253 (clobber (reg:CC 17))])]
8254 "TARGET_80387"
8255 "if (TARGET_SSE2)
8256 {
8257 /* In case operand is in memory, we will not use SSE. */
8258 if (memory_operand (operands[0], VOIDmode)
8259 && rtx_equal_p (operands[0], operands[1]))
8260 emit_insn (gen_absdf2_memory (operands[0], operands[1]));
8261 else
8262 {
8263 /* Using SSE is tricky, since we need bitwise negation of -0
8264 in register. */
8265 rtx reg = gen_reg_rtx (DFmode);
8266 #if HOST_BITS_PER_WIDE_INT >= 64
8267 rtx imm = GEN_INT (0x80000000);
8268 #else
8269 rtx imm = immed_double_const (0, 0x80000000, DImode);
8270 #endif
8271 emit_move_insn (reg, gen_lowpart (DFmode, imm));
8272 emit_insn (gen_absdf2_ifs (operands[0], operands[1], reg));
8273 }
8274 DONE;
8275 }
8276 ix86_expand_unary_operator (ABS, DFmode, operands); DONE;")
8277
8278 (define_insn "absdf2_memory"
8279 [(set (match_operand:DF 0 "memory_operand" "=m")
8280 (abs:DF (match_operand:DF 1 "memory_operand" "0")))
8281 (clobber (reg:CC 17))]
8282 "ix86_unary_operator_ok (ABS, DFmode, operands)"
8283 "#")
8284
8285 (define_insn "absdf2_ifs"
8286 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y#fr,f#Yr,r#Yf")
8287 (abs:DF (match_operand:DF 1 "nonimmediate_operand" "Y,0,0")))
8288 (use (match_operand:DF 2 "nonmemory_operand" "*0#Y,*X#Y,*X#Y"))
8289 (clobber (reg:CC 17))]
8290 "TARGET_SSE2"
8291 "#")
8292
8293 (define_split
8294 [(set (match_operand:DF 0 "memory_operand" "")
8295 (abs:DF (match_operand:DF 1 "memory_operand" "")))
8296 (use (match_operand:DF 2 "" ""))
8297 (clobber (reg:CC 17))]
8298 ""
8299 [(parallel [(set (match_dup 0)
8300 (abs:DF (match_dup 1)))
8301 (clobber (reg:CC 17))])])
8302
8303 (define_split
8304 [(set (match_operand:DF 0 "register_operand" "")
8305 (abs:DF (match_operand:DF 1 "register_operand" "")))
8306 (use (match_operand:DF 2 "" ""))
8307 (clobber (reg:CC 17))]
8308 "reload_completed && !SSE_REG_P (operands[0])"
8309 [(parallel [(set (match_dup 0)
8310 (abs:DF (match_dup 1)))
8311 (clobber (reg:CC 17))])])
8312
8313 (define_split
8314 [(set (match_operand:DF 0 "register_operand" "")
8315 (abs:DF (match_operand:DF 1 "register_operand" "")))
8316 (use (match_operand:DF 2 "register_operand" ""))
8317 (clobber (reg:CC 17))]
8318 "reload_completed && SSE_REG_P (operands[0])"
8319 [(set (subreg:TI (match_dup 0) 0)
8320 (and:TI (not:TI (subreg:TI (match_dup 2) 0))
8321 (subreg:TI (match_dup 1) 0)))])
8322
8323
8324 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
8325 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
8326 ;; to itself.
8327 (define_insn "*absdf2_if"
8328 [(set (match_operand:DF 0 "nonimmediate_operand" "=f#r,rm#f")
8329 (abs:DF (match_operand:DF 1 "nonimmediate_operand" "0,0")))
8330 (clobber (reg:CC 17))]
8331 "TARGET_80387 && ix86_unary_operator_ok (ABS, DFmode, operands)"
8332 "#")
8333
8334 (define_split
8335 [(set (match_operand:DF 0 "register_operand" "")
8336 (abs:DF (match_operand:DF 1 "register_operand" "")))
8337 (clobber (reg:CC 17))]
8338 "TARGET_80387 && FP_REGNO_P (REGNO (operands[0])) && reload_completed"
8339 [(set (match_dup 0)
8340 (abs:DF (match_dup 1)))]
8341 "")
8342
8343 (define_split
8344 [(set (match_operand:DF 0 "register_operand" "")
8345 (abs:DF (match_operand:DF 1 "register_operand" "")))
8346 (clobber (reg:CC 17))]
8347 "TARGET_80387 && reload_completed && !FP_REGNO_P (REGNO (operands[0]))"
8348 [(parallel [(set (match_dup 3) (and:SI (match_dup 3) (match_dup 4)))
8349 (clobber (reg:CC 17))])]
8350 "operands[4] = GEN_INT (~0x80000000);
8351 split_di (operands+0, 1, operands+2, operands+3);")
8352
8353 (define_expand "absxf2"
8354 [(parallel [(set (match_operand:XF 0 "nonimmediate_operand" "")
8355 (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))
8356 (clobber (reg:CC 17))])]
8357 "TARGET_80387 && !TARGET_64BIT"
8358 "ix86_expand_unary_operator (ABS, XFmode, operands); DONE;")
8359
8360 (define_expand "abstf2"
8361 [(parallel [(set (match_operand:TF 0 "nonimmediate_operand" "")
8362 (neg:TF (match_operand:TF 1 "nonimmediate_operand" "")))
8363 (clobber (reg:CC 17))])]
8364 "TARGET_80387"
8365 "ix86_expand_unary_operator (ABS, TFmode, operands); DONE;")
8366
8367 ;; Keep 'f' and 'r' in separate alternatives to avoid reload problems
8368 ;; because of secondary memory needed to reload from class FLOAT_INT_REGS
8369 ;; to itself.
8370 (define_insn "*absxf2_if"
8371 [(set (match_operand:XF 0 "nonimmediate_operand" "=f#r,rm#f")
8372 (abs:XF (match_operand:XF 1 "nonimmediate_operand" "0,0")))
8373 (clobber (reg:CC 17))]
8374 "TARGET_80387 && !TARGET_64BIT
8375 && ix86_unary_operator_ok (ABS, XFmode, operands)"
8376 "#")
8377
8378 (define_split
8379 [(set (match_operand:XF 0 "register_operand" "")
8380 (abs:XF (match_operand:XF 1 "register_operand" "")))
8381 (clobber (reg:CC 17))]
8382 "TARGET_80387 && FP_REGNO_P (REGNO (operands[0])) && reload_completed"
8383 [(set (match_dup 0)
8384 (abs:XF (match_dup 1)))]
8385 "")
8386
8387 (define_split
8388 [(set (match_operand:XF 0 "register_operand" "")
8389 (abs:XF (match_operand:XF 1 "register_operand" "")))
8390 (clobber (reg:CC 17))]
8391 "TARGET_80387 && reload_completed && !FP_REGNO_P (REGNO (operands[0]))"
8392 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (match_dup 1)))
8393 (clobber (reg:CC 17))])]
8394 "operands[1] = GEN_INT (~0x8000);
8395 operands[0] = gen_rtx_REG (SImode, true_regnum (operands[0]) + 2);")
8396
8397 (define_insn "*abstf2_if"
8398 [(set (match_operand:TF 0 "nonimmediate_operand" "=f#r,rm#f")
8399 (abs:TF (match_operand:TF 1 "nonimmediate_operand" "0,0")))
8400 (clobber (reg:CC 17))]
8401 "TARGET_80387 && ix86_unary_operator_ok (ABS, TFmode, operands)"
8402 "#")
8403
8404 (define_split
8405 [(set (match_operand:TF 0 "register_operand" "")
8406 (abs:TF (match_operand:TF 1 "register_operand" "")))
8407 (clobber (reg:CC 17))]
8408 "TARGET_80387 && FP_REGNO_P (REGNO (operands[0])) && reload_completed"
8409 [(set (match_dup 0)
8410 (abs:TF (match_dup 1)))]
8411 "")
8412
8413 (define_split
8414 [(set (match_operand:TF 0 "register_operand" "")
8415 (abs:TF (match_operand:TF 1 "register_operand" "")))
8416 (clobber (reg:CC 17))]
8417 "TARGET_80387 && reload_completed && !FP_REGNO_P (REGNO (operands[0]))"
8418 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (match_dup 1)))
8419 (clobber (reg:CC 17))])]
8420 "operands[1] = GEN_INT (~0x8000);
8421 operands[0] = gen_rtx_REG (SImode, true_regnum (operands[0]) + 2);")
8422
8423 (define_insn "*abssf2_1"
8424 [(set (match_operand:SF 0 "register_operand" "=f")
8425 (abs:SF (match_operand:SF 1 "register_operand" "0")))]
8426 "TARGET_80387 && reload_completed"
8427 "fabs"
8428 [(set_attr "type" "fsgn")
8429 (set_attr "mode" "SF")])
8430
8431 (define_insn "*absdf2_1"
8432 [(set (match_operand:DF 0 "register_operand" "=f")
8433 (abs:DF (match_operand:DF 1 "register_operand" "0")))]
8434 "TARGET_80387 && reload_completed"
8435 "fabs"
8436 [(set_attr "type" "fsgn")
8437 (set_attr "mode" "DF")])
8438
8439 (define_insn "*absextendsfdf2"
8440 [(set (match_operand:DF 0 "register_operand" "=f")
8441 (abs:DF (float_extend:DF
8442 (match_operand:SF 1 "register_operand" "0"))))]
8443 "TARGET_80387"
8444 "fabs"
8445 [(set_attr "type" "fsgn")
8446 (set_attr "mode" "DF")])
8447
8448 (define_insn "*absxf2_1"
8449 [(set (match_operand:XF 0 "register_operand" "=f")
8450 (abs:XF (match_operand:XF 1 "register_operand" "0")))]
8451 "TARGET_80387 && !TARGET_64BIT && reload_completed"
8452 "fabs"
8453 [(set_attr "type" "fsgn")
8454 (set_attr "mode" "DF")])
8455
8456 (define_insn "*absextenddfxf2"
8457 [(set (match_operand:XF 0 "register_operand" "=f")
8458 (abs:XF (float_extend:XF
8459 (match_operand:DF 1 "register_operand" "0"))))]
8460 "TARGET_80387 && !TARGET_64BIT"
8461 "fabs"
8462 [(set_attr "type" "fsgn")
8463 (set_attr "mode" "XF")])
8464
8465 (define_insn "*absextendsfxf2"
8466 [(set (match_operand:XF 0 "register_operand" "=f")
8467 (abs:XF (float_extend:XF
8468 (match_operand:SF 1 "register_operand" "0"))))]
8469 "TARGET_80387 && !TARGET_64BIT"
8470 "fabs"
8471 [(set_attr "type" "fsgn")
8472 (set_attr "mode" "XF")])
8473
8474 (define_insn "*abstf2_1"
8475 [(set (match_operand:TF 0 "register_operand" "=f")
8476 (abs:TF (match_operand:TF 1 "register_operand" "0")))]
8477 "TARGET_80387 && reload_completed"
8478 "fabs"
8479 [(set_attr "type" "fsgn")
8480 (set_attr "mode" "DF")])
8481
8482 (define_insn "*absextenddftf2"
8483 [(set (match_operand:TF 0 "register_operand" "=f")
8484 (abs:TF (float_extend:TF
8485 (match_operand:DF 1 "register_operand" "0"))))]
8486 "TARGET_80387"
8487 "fabs"
8488 [(set_attr "type" "fsgn")
8489 (set_attr "mode" "XF")])
8490
8491 (define_insn "*absextendsftf2"
8492 [(set (match_operand:TF 0 "register_operand" "=f")
8493 (abs:TF (float_extend:TF
8494 (match_operand:SF 1 "register_operand" "0"))))]
8495 "TARGET_80387"
8496 "fabs"
8497 [(set_attr "type" "fsgn")
8498 (set_attr "mode" "XF")])
8499 \f
8500 ;; One complement instructions
8501
8502 (define_expand "one_cmplsi2"
8503 [(set (match_operand:SI 0 "nonimmediate_operand" "")
8504 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
8505 ""
8506 "ix86_expand_unary_operator (NOT, SImode, operands); DONE;")
8507
8508 (define_insn "*one_cmplsi2_1"
8509 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
8510 (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))]
8511 "ix86_unary_operator_ok (NOT, SImode, operands)"
8512 "not{l}\\t%0"
8513 [(set_attr "type" "negnot")
8514 (set_attr "mode" "SI")])
8515
8516 (define_insn "*one_cmplsi2_2"
8517 [(set (reg 17)
8518 (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
8519 (const_int 0)))
8520 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
8521 (not:SI (match_dup 1)))]
8522 "ix86_match_ccmode (insn, CCNOmode)
8523 && ix86_unary_operator_ok (NOT, SImode, operands)"
8524 "#"
8525 [(set_attr "type" "alu1")
8526 (set_attr "mode" "SI")])
8527
8528 (define_split
8529 [(set (reg 17)
8530 (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" ""))
8531 (const_int 0)))
8532 (set (match_operand:SI 0 "nonimmediate_operand" "")
8533 (not:SI (match_dup 1)))]
8534 "ix86_match_ccmode (insn, CCNOmode)"
8535 [(parallel [(set (reg:CCNO 17)
8536 (compare:CCNO (xor:SI (match_dup 1) (const_int -1))
8537 (const_int 0)))
8538 (set (match_dup 0)
8539 (xor:SI (match_dup 1) (const_int -1)))])]
8540 "")
8541
8542 (define_expand "one_cmplhi2"
8543 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8544 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
8545 "TARGET_HIMODE_MATH"
8546 "ix86_expand_unary_operator (NOT, HImode, operands); DONE;")
8547
8548 (define_insn "*one_cmplhi2_1"
8549 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
8550 (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))]
8551 "ix86_unary_operator_ok (NOT, HImode, operands)"
8552 "not{w}\\t%0"
8553 [(set_attr "type" "negnot")
8554 (set_attr "mode" "HI")])
8555
8556 (define_insn "*one_cmplhi2_2"
8557 [(set (reg 17)
8558 (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
8559 (const_int 0)))
8560 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
8561 (not:HI (match_dup 1)))]
8562 "ix86_match_ccmode (insn, CCNOmode)
8563 && ix86_unary_operator_ok (NEG, HImode, operands)"
8564 "#"
8565 [(set_attr "type" "alu1")
8566 (set_attr "mode" "HI")])
8567
8568 (define_split
8569 [(set (reg 17)
8570 (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" ""))
8571 (const_int 0)))
8572 (set (match_operand:HI 0 "nonimmediate_operand" "")
8573 (not:HI (match_dup 1)))]
8574 "ix86_match_ccmode (insn, CCNOmode)"
8575 [(parallel [(set (reg:CCNO 17)
8576 (compare:CCNO (xor:HI (match_dup 1) (const_int -1))
8577 (const_int 0)))
8578 (set (match_dup 0)
8579 (xor:HI (match_dup 1) (const_int -1)))])]
8580 "")
8581
8582 ;; %%% Potential partial reg stall on alternative 1. What to do?
8583 (define_expand "one_cmplqi2"
8584 [(set (match_operand:QI 0 "nonimmediate_operand" "")
8585 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
8586 "TARGET_QIMODE_MATH"
8587 "ix86_expand_unary_operator (NOT, QImode, operands); DONE;")
8588
8589 (define_insn "*one_cmplqi2_1"
8590 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
8591 (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
8592 "ix86_unary_operator_ok (NOT, QImode, operands)"
8593 "@
8594 not{b}\\t%0
8595 not{l}\\t%k0"
8596 [(set_attr "type" "negnot")
8597 (set_attr "mode" "QI,SI")])
8598
8599 (define_insn "*one_cmplqi2_2"
8600 [(set (reg 17)
8601 (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
8602 (const_int 0)))
8603 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
8604 (not:QI (match_dup 1)))]
8605 "ix86_match_ccmode (insn, CCNOmode)
8606 && ix86_unary_operator_ok (NOT, QImode, operands)"
8607 "#"
8608 [(set_attr "type" "alu1")
8609 (set_attr "mode" "QI")])
8610
8611 (define_split
8612 [(set (reg 17)
8613 (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" ""))
8614 (const_int 0)))
8615 (set (match_operand:QI 0 "nonimmediate_operand" "")
8616 (not:QI (match_dup 1)))]
8617 "ix86_match_ccmode (insn, CCNOmode)"
8618 [(parallel [(set (reg:CCNO 17)
8619 (compare:CCNO (xor:QI (match_dup 1) (const_int -1))
8620 (const_int 0)))
8621 (set (match_dup 0)
8622 (xor:QI (match_dup 1) (const_int -1)))])]
8623 "")
8624 \f
8625 ;; Arithmetic shift instructions
8626
8627 ;; DImode shifts are implemented using the i386 "shift double" opcode,
8628 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem". If the shift count
8629 ;; is variable, then the count is in %cl and the "imm" operand is dropped
8630 ;; from the assembler input.
8631 ;;
8632 ;; This instruction shifts the target reg/mem as usual, but instead of
8633 ;; shifting in zeros, bits are shifted in from reg operand. If the insn
8634 ;; is a left shift double, bits are taken from the high order bits of
8635 ;; reg, else if the insn is a shift right double, bits are taken from the
8636 ;; low order bits of reg. So if %eax is "1234" and %edx is "5678",
8637 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
8638 ;;
8639 ;; Since sh[lr]d does not change the `reg' operand, that is done
8640 ;; separately, making all shifts emit pairs of shift double and normal
8641 ;; shift. Since sh[lr]d does not shift more than 31 bits, and we wish to
8642 ;; support a 63 bit shift, each shift where the count is in a reg expands
8643 ;; to a pair of shifts, a branch, a shift by 32 and a label.
8644 ;;
8645 ;; If the shift count is a constant, we need never emit more than one
8646 ;; shift pair, instead using moves and sign extension for counts greater
8647 ;; than 31.
8648
8649 (define_expand "ashldi3"
8650 [(parallel [(set (match_operand:DI 0 "register_operand" "")
8651 (ashift:DI (match_operand:DI 1 "register_operand" "")
8652 (match_operand:QI 2 "nonmemory_operand" "")))
8653 (clobber (reg:CC 17))])]
8654 ""
8655 "
8656 {
8657 if (!TARGET_64BIT && TARGET_CMOVE && ! immediate_operand (operands[2], QImode))
8658 {
8659 emit_insn (gen_ashldi3_1 (operands[0], operands[1], operands[2]));
8660 DONE;
8661 }
8662 ix86_expand_binary_operator (ASHIFT, DImode, operands); DONE;
8663 }")
8664
8665 (define_insn "ashldi3_1"
8666 [(set (match_operand:DI 0 "register_operand" "=r")
8667 (ashift:DI (match_operand:DI 1 "register_operand" "0")
8668 (match_operand:QI 2 "nonmemory_operand" "Jc")))
8669 (clobber (match_scratch:SI 3 "=&r"))
8670 (clobber (reg:CC 17))]
8671 "TARGET_CMOVE"
8672 "#"
8673 [(set_attr "type" "multi")])
8674
8675 (define_insn "*ashldi3_2"
8676 [(set (match_operand:DI 0 "register_operand" "=r")
8677 (ashift:DI (match_operand:DI 1 "register_operand" "0")
8678 (match_operand:QI 2 "nonmemory_operand" "Jc")))
8679 (clobber (reg:CC 17))]
8680 ""
8681 "#"
8682 [(set_attr "type" "multi")])
8683
8684 (define_split
8685 [(set (match_operand:DI 0 "register_operand" "")
8686 (ashift:DI (match_operand:DI 1 "register_operand" "")
8687 (match_operand:QI 2 "nonmemory_operand" "")))
8688 (clobber (match_scratch:SI 3 ""))
8689 (clobber (reg:CC 17))]
8690 "TARGET_CMOVE && reload_completed"
8691 [(const_int 0)]
8692 "ix86_split_ashldi (operands, operands[3]); DONE;")
8693
8694 (define_split
8695 [(set (match_operand:DI 0 "register_operand" "")
8696 (ashift:DI (match_operand:DI 1 "register_operand" "")
8697 (match_operand:QI 2 "nonmemory_operand" "")))
8698 (clobber (reg:CC 17))]
8699 "reload_completed"
8700 [(const_int 0)]
8701 "ix86_split_ashldi (operands, NULL_RTX); DONE;")
8702
8703 (define_insn "x86_shld_1"
8704 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
8705 (ior:SI (ashift:SI (match_dup 0)
8706 (match_operand:QI 2 "nonmemory_operand" "I,c"))
8707 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
8708 (minus:QI (const_int 32) (match_dup 2)))))
8709 (clobber (reg:CC 17))]
8710 ""
8711 "@
8712 shld{l}\\t{%2, %1, %0|%0, %1, %2}
8713 shld{l}\\t{%s2%1, %0|%0, %1, %2}"
8714 [(set_attr "type" "ishift")
8715 (set_attr "prefix_0f" "1")
8716 (set_attr "mode" "SI")
8717 (set_attr "pent_pair" "np")
8718 (set_attr "athlon_decode" "vector")
8719 (set_attr "ppro_uops" "few")])
8720
8721 (define_expand "x86_shift_adj_1"
8722 [(set (reg:CCZ 17)
8723 (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
8724 (const_int 32))
8725 (const_int 0)))
8726 (set (match_operand:SI 0 "register_operand" "")
8727 (if_then_else:SI (ne (reg:CCZ 17) (const_int 0))
8728 (match_operand:SI 1 "register_operand" "")
8729 (match_dup 0)))
8730 (set (match_dup 1)
8731 (if_then_else:SI (ne (reg:CCZ 17) (const_int 0))
8732 (match_operand:SI 3 "register_operand" "r")
8733 (match_dup 1)))]
8734 "TARGET_CMOVE"
8735 "")
8736
8737 (define_expand "x86_shift_adj_2"
8738 [(use (match_operand:SI 0 "register_operand" ""))
8739 (use (match_operand:SI 1 "register_operand" ""))
8740 (use (match_operand:QI 2 "register_operand" ""))]
8741 ""
8742 "
8743 {
8744 rtx label = gen_label_rtx ();
8745 rtx tmp;
8746
8747 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
8748
8749 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
8750 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
8751 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
8752 gen_rtx_LABEL_REF (VOIDmode, label),
8753 pc_rtx);
8754 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
8755 JUMP_LABEL (tmp) = label;
8756
8757 emit_move_insn (operands[0], operands[1]);
8758 emit_move_insn (operands[1], const0_rtx);
8759
8760 emit_label (label);
8761 LABEL_NUSES (label) = 1;
8762
8763 DONE;
8764 }")
8765
8766 (define_expand "ashlsi3"
8767 [(set (match_operand:SI 0 "nonimmediate_operand" "")
8768 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
8769 (match_operand:QI 2 "nonmemory_operand" "")))
8770 (clobber (reg:CC 17))]
8771 ""
8772 "ix86_expand_binary_operator (ASHIFT, SImode, operands); DONE;")
8773
8774 (define_insn "*ashlsi3_1"
8775 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
8776 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,r")
8777 (match_operand:QI 2 "nonmemory_operand" "cI,M")))
8778 (clobber (reg:CC 17))]
8779 "ix86_binary_operator_ok (ASHIFT, SImode, operands)"
8780 "*
8781 {
8782 switch (get_attr_type (insn))
8783 {
8784 case TYPE_ALU:
8785 if (operands[2] != const1_rtx)
8786 abort ();
8787 if (!rtx_equal_p (operands[0], operands[1]))
8788 abort ();
8789 return \"add{l}\\t{%0, %0|%0, %0}\";
8790
8791 case TYPE_LEA:
8792 return \"#\";
8793
8794 default:
8795 if (REG_P (operands[2]))
8796 return \"sal{l}\\t{%b2, %0|%0, %b2}\";
8797 else if (GET_CODE (operands[2]) == CONST_INT
8798 && INTVAL (operands[2]) == 1
8799 && (TARGET_PENTIUM || TARGET_PENTIUMPRO))
8800 return \"sal{l}\\t%0\";
8801 else
8802 return \"sal{l}\\t{%2, %0|%0, %2}\";
8803 }
8804 }"
8805 [(set (attr "type")
8806 (cond [(eq_attr "alternative" "1")
8807 (const_string "lea")
8808 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
8809 (const_int 0))
8810 (match_operand 0 "register_operand" ""))
8811 (match_operand 2 "const1_operand" ""))
8812 (const_string "alu")
8813 ]
8814 (const_string "ishift")))
8815 (set_attr "mode" "SI")])
8816
8817 ;; Convert lea to the lea pattern to avoid flags dependency.
8818 (define_split
8819 [(set (match_operand 0 "register_operand" "")
8820 (ashift (match_operand 1 "register_operand" "")
8821 (match_operand:QI 2 "const_int_operand" "")))
8822 (clobber (reg:CC 17))]
8823 "reload_completed
8824 && true_regnum (operands[0]) != true_regnum (operands[1])"
8825 [(const_int 0)]
8826 "
8827 {
8828 rtx pat;
8829 operands[0] = gen_lowpart (SImode, operands[0]);
8830 operands[1] = gen_lowpart (Pmode, operands[1]);
8831 operands[2] = GEN_INT (1 << INTVAL (operands[2]));
8832 pat = gen_rtx_MULT (Pmode, operands[1], operands[2]);
8833 if (Pmode != SImode)
8834 pat = gen_rtx_SUBREG (SImode, pat, 0);
8835 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
8836 DONE;
8837 }")
8838
8839 ;; This pattern can't accept a variable shift count, since shifts by
8840 ;; zero don't affect the flags. We assume that shifts by constant
8841 ;; zero are optimized away.
8842 (define_insn "*ashlsi3_cmp"
8843 [(set (reg 17)
8844 (compare
8845 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
8846 (match_operand:QI 2 "immediate_operand" "I"))
8847 (const_int 0)))
8848 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
8849 (ashift:SI (match_dup 1) (match_dup 2)))]
8850 "ix86_match_ccmode (insn, CCGOCmode)
8851 && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
8852 "*
8853 {
8854 switch (get_attr_type (insn))
8855 {
8856 case TYPE_ALU:
8857 if (operands[2] != const1_rtx)
8858 abort ();
8859 return \"add{l}\\t{%0, %0|%0, %0}\";
8860
8861 default:
8862 if (REG_P (operands[2]))
8863 return \"sal{l}\\t{%b2, %0|%0, %b2}\";
8864 else if (GET_CODE (operands[2]) == CONST_INT
8865 && INTVAL (operands[2]) == 1
8866 && (TARGET_PENTIUM || TARGET_PENTIUMPRO))
8867 return \"sal{l}\\t%0\";
8868 else
8869 return \"sal{l}\\t{%2, %0|%0, %2}\";
8870 }
8871 }"
8872 [(set (attr "type")
8873 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
8874 (const_int 0))
8875 (match_operand 0 "register_operand" ""))
8876 (match_operand 2 "const1_operand" ""))
8877 (const_string "alu")
8878 ]
8879 (const_string "ishift")))
8880 (set_attr "mode" "SI")])
8881
8882 (define_expand "ashlhi3"
8883 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8884 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "")
8885 (match_operand:QI 2 "nonmemory_operand" "")))
8886 (clobber (reg:CC 17))]
8887 "TARGET_HIMODE_MATH"
8888 "ix86_expand_binary_operator (ASHIFT, HImode, operands); DONE;")
8889
8890 (define_insn "*ashlhi3_1_lea"
8891 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
8892 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,r")
8893 (match_operand:QI 2 "nonmemory_operand" "cI,M")))
8894 (clobber (reg:CC 17))]
8895 "!TARGET_PARTIAL_REG_STALL
8896 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
8897 "*
8898 {
8899 switch (get_attr_type (insn))
8900 {
8901 case TYPE_LEA:
8902 return \"#\";
8903 case TYPE_ALU:
8904 if (operands[2] != const1_rtx)
8905 abort ();
8906 return \"add{w}\\t{%0, %0|%0, %0}\";
8907
8908 default:
8909 if (REG_P (operands[2]))
8910 return \"sal{w}\\t{%b2, %0|%0, %b2}\";
8911 else if (GET_CODE (operands[2]) == CONST_INT
8912 && INTVAL (operands[2]) == 1
8913 && (TARGET_PENTIUM || TARGET_PENTIUMPRO))
8914 return \"sal{w}\\t%0\";
8915 else
8916 return \"sal{w}\\t{%2, %0|%0, %2}\";
8917 }
8918 }"
8919 [(set (attr "type")
8920 (cond [(eq_attr "alternative" "1")
8921 (const_string "lea")
8922 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
8923 (const_int 0))
8924 (match_operand 0 "register_operand" ""))
8925 (match_operand 2 "const1_operand" ""))
8926 (const_string "alu")
8927 ]
8928 (const_string "ishift")))
8929 (set_attr "mode" "HI,SI")])
8930
8931 (define_insn "*ashlhi3_1"
8932 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
8933 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
8934 (match_operand:QI 2 "nonmemory_operand" "cI")))
8935 (clobber (reg:CC 17))]
8936 "TARGET_PARTIAL_REG_STALL
8937 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
8938 "*
8939 {
8940 switch (get_attr_type (insn))
8941 {
8942 case TYPE_ALU:
8943 if (operands[2] != const1_rtx)
8944 abort ();
8945 return \"add{w}\\t{%0, %0|%0, %0}\";
8946
8947 default:
8948 if (REG_P (operands[2]))
8949 return \"sal{w}\\t{%b2, %0|%0, %b2}\";
8950 else if (GET_CODE (operands[2]) == CONST_INT
8951 && INTVAL (operands[2]) == 1
8952 && (TARGET_PENTIUM || TARGET_PENTIUMPRO))
8953 return \"sal{w}\\t%0\";
8954 else
8955 return \"sal{w}\\t{%2, %0|%0, %2}\";
8956 }
8957 }"
8958 [(set (attr "type")
8959 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
8960 (const_int 0))
8961 (match_operand 0 "register_operand" ""))
8962 (match_operand 2 "const1_operand" ""))
8963 (const_string "alu")
8964 ]
8965 (const_string "ishift")))
8966 (set_attr "mode" "HI")])
8967
8968 ;; This pattern can't accept a variable shift count, since shifts by
8969 ;; zero don't affect the flags. We assume that shifts by constant
8970 ;; zero are optimized away.
8971 (define_insn "*ashlhi3_cmp"
8972 [(set (reg 17)
8973 (compare
8974 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
8975 (match_operand:QI 2 "immediate_operand" "I"))
8976 (const_int 0)))
8977 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
8978 (ashift:HI (match_dup 1) (match_dup 2)))]
8979 "ix86_match_ccmode (insn, CCGOCmode)
8980 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
8981 "*
8982 {
8983 switch (get_attr_type (insn))
8984 {
8985 case TYPE_ALU:
8986 if (operands[2] != const1_rtx)
8987 abort ();
8988 return \"add{w}\\t{%0, %0|%0, %0}\";
8989
8990 default:
8991 if (REG_P (operands[2]))
8992 return \"sal{w}\\t{%b2, %0|%0, %b2}\";
8993 else if (GET_CODE (operands[2]) == CONST_INT
8994 && INTVAL (operands[2]) == 1
8995 && (TARGET_PENTIUM || TARGET_PENTIUMPRO))
8996 return \"sal{w}\\t%0\";
8997 else
8998 return \"sal{w}\\t{%2, %0|%0, %2}\";
8999 }
9000 }"
9001 [(set (attr "type")
9002 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
9003 (const_int 0))
9004 (match_operand 0 "register_operand" ""))
9005 (match_operand 2 "const1_operand" ""))
9006 (const_string "alu")
9007 ]
9008 (const_string "ishift")))
9009 (set_attr "mode" "HI")])
9010
9011 (define_expand "ashlqi3"
9012 [(set (match_operand:QI 0 "nonimmediate_operand" "")
9013 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "")
9014 (match_operand:QI 2 "nonmemory_operand" "")))
9015 (clobber (reg:CC 17))]
9016 "TARGET_QIMODE_MATH"
9017 "ix86_expand_binary_operator (ASHIFT, QImode, operands); DONE;")
9018
9019 ;; %%% Potential partial reg stall on alternative 2. What to do?
9020
9021 (define_insn "*ashlqi3_1_lea"
9022 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r")
9023 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,r")
9024 (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
9025 (clobber (reg:CC 17))]
9026 "!TARGET_PARTIAL_REG_STALL
9027 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
9028 "*
9029 {
9030 switch (get_attr_type (insn))
9031 {
9032 case TYPE_LEA:
9033 return \"#\";
9034 case TYPE_ALU:
9035 if (operands[2] != const1_rtx)
9036 abort ();
9037 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
9038 return \"add{l}\\t{%k0, %k0|%k0, %k0}\";
9039 else
9040 return \"add{b}\\t{%0, %0|%0, %0}\";
9041
9042 default:
9043 if (REG_P (operands[2]))
9044 {
9045 if (get_attr_mode (insn) == MODE_SI)
9046 return \"sal{l}\\t{%b2, %k0|%k0, %b2}\";
9047 else
9048 return \"sal{b}\\t{%b2, %0|%0, %b2}\";
9049 }
9050 else if (GET_CODE (operands[2]) == CONST_INT
9051 && INTVAL (operands[2]) == 1
9052 && (TARGET_PENTIUM || TARGET_PENTIUMPRO))
9053 {
9054 if (get_attr_mode (insn) == MODE_SI)
9055 return \"sal{l}\\t%0\";
9056 else
9057 return \"sal{b}\\t%0\";
9058 }
9059 else
9060 {
9061 if (get_attr_mode (insn) == MODE_SI)
9062 return \"sal{l}\\t{%2, %k0|%k0, %2}\";
9063 else
9064 return \"sal{b}\\t{%2, %0|%0, %2}\";
9065 }
9066 }
9067 }"
9068 [(set (attr "type")
9069 (cond [(eq_attr "alternative" "2")
9070 (const_string "lea")
9071 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
9072 (const_int 0))
9073 (match_operand 0 "register_operand" ""))
9074 (match_operand 2 "const1_operand" ""))
9075 (const_string "alu")
9076 ]
9077 (const_string "ishift")))
9078 (set_attr "mode" "QI,SI,SI")])
9079
9080 (define_insn "*ashlqi3_1"
9081 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
9082 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
9083 (match_operand:QI 2 "nonmemory_operand" "cI,cI")))
9084 (clobber (reg:CC 17))]
9085 "TARGET_PARTIAL_REG_STALL
9086 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
9087 "*
9088 {
9089 switch (get_attr_type (insn))
9090 {
9091 case TYPE_ALU:
9092 if (operands[2] != const1_rtx)
9093 abort ();
9094 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
9095 return \"add{l}\\t{%k0, %k0|%k0, %k0}\";
9096 else
9097 return \"add{b}\\t{%0, %0|%0, %0}\";
9098
9099 default:
9100 if (REG_P (operands[2]))
9101 {
9102 if (get_attr_mode (insn) == MODE_SI)
9103 return \"sal{l}\\t{%b2, %k0|%k0, %b2}\";
9104 else
9105 return \"sal{b}\\t{%b2, %0|%0, %b2}\";
9106 }
9107 else if (GET_CODE (operands[2]) == CONST_INT
9108 && INTVAL (operands[2]) == 1
9109 && (TARGET_PENTIUM || TARGET_PENTIUMPRO))
9110 {
9111 if (get_attr_mode (insn) == MODE_SI)
9112 return \"sal{l}\\t%0\";
9113 else
9114 return \"sal{b}\\t%0\";
9115 }
9116 else
9117 {
9118 if (get_attr_mode (insn) == MODE_SI)
9119 return \"sal{l}\\t{%2, %k0|%k0, %2}\";
9120 else
9121 return \"sal{b}\\t{%2, %0|%0, %2}\";
9122 }
9123 }
9124 }"
9125 [(set (attr "type")
9126 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
9127 (const_int 0))
9128 (match_operand 0 "register_operand" ""))
9129 (match_operand 2 "const1_operand" ""))
9130 (const_string "alu")
9131 ]
9132 (const_string "ishift")))
9133 (set_attr "mode" "QI,SI")])
9134
9135 ;; This pattern can't accept a variable shift count, since shifts by
9136 ;; zero don't affect the flags. We assume that shifts by constant
9137 ;; zero are optimized away.
9138 (define_insn "*ashlqi3_cmp"
9139 [(set (reg 17)
9140 (compare
9141 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
9142 (match_operand:QI 2 "immediate_operand" "I"))
9143 (const_int 0)))
9144 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9145 (ashift:QI (match_dup 1) (match_dup 2)))]
9146 "ix86_match_ccmode (insn, CCGOCmode)
9147 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
9148 "*
9149 {
9150 switch (get_attr_type (insn))
9151 {
9152 case TYPE_ALU:
9153 if (operands[2] != const1_rtx)
9154 abort ();
9155 return \"add{b}\\t{%0, %0|%0, %0}\";
9156
9157 default:
9158 if (REG_P (operands[2]))
9159 return \"sal{b}\\t{%b2, %0|%0, %b2}\";
9160 else if (GET_CODE (operands[2]) == CONST_INT
9161 && INTVAL (operands[2]) == 1
9162 && (TARGET_PENTIUM || TARGET_PENTIUMPRO))
9163 return \"sal{b}\\t%0\";
9164 else
9165 return \"sal{b}\\t{%2, %0|%0, %2}\";
9166 }
9167 }"
9168 [(set (attr "type")
9169 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
9170 (const_int 0))
9171 (match_operand 0 "register_operand" ""))
9172 (match_operand 2 "const1_operand" ""))
9173 (const_string "alu")
9174 ]
9175 (const_string "ishift")))
9176 (set_attr "mode" "QI")])
9177
9178 ;; See comment above `ashldi3' about how this works.
9179
9180 (define_expand "ashrdi3"
9181 [(parallel [(set (match_operand:DI 0 "register_operand" "=r")
9182 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
9183 (match_operand:QI 2 "nonmemory_operand" "Jc")))
9184 (clobber (reg:CC 17))])]
9185 ""
9186 "
9187 {
9188 if (TARGET_CMOVE && ! immediate_operand (operands[2], QImode))
9189 {
9190 emit_insn (gen_ashrdi3_1 (operands[0], operands[1], operands[2]));
9191 DONE;
9192 }
9193 }")
9194
9195 (define_insn "ashrdi3_1"
9196 [(set (match_operand:DI 0 "register_operand" "=r")
9197 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
9198 (match_operand:QI 2 "nonmemory_operand" "Jc")))
9199 (clobber (match_scratch:SI 3 "=&r"))
9200 (clobber (reg:CC 17))]
9201 "TARGET_CMOVE"
9202 "#"
9203 [(set_attr "type" "multi")])
9204
9205 (define_insn "*ashrdi3_2"
9206 [(set (match_operand:DI 0 "register_operand" "=r")
9207 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
9208 (match_operand:QI 2 "nonmemory_operand" "Jc")))
9209 (clobber (reg:CC 17))]
9210 ""
9211 "#"
9212 [(set_attr "type" "multi")])
9213
9214 (define_split
9215 [(set (match_operand:DI 0 "register_operand" "")
9216 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
9217 (match_operand:QI 2 "nonmemory_operand" "")))
9218 (clobber (match_scratch:SI 3 ""))
9219 (clobber (reg:CC 17))]
9220 "TARGET_CMOVE && reload_completed"
9221 [(const_int 0)]
9222 "ix86_split_ashrdi (operands, operands[3]); DONE;")
9223
9224 (define_split
9225 [(set (match_operand:DI 0 "register_operand" "")
9226 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
9227 (match_operand:QI 2 "nonmemory_operand" "")))
9228 (clobber (reg:CC 17))]
9229 "reload_completed"
9230 [(const_int 0)]
9231 "ix86_split_ashrdi (operands, NULL_RTX); DONE;")
9232
9233 (define_insn "x86_shrd_1"
9234 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
9235 (ior:SI (ashiftrt:SI (match_dup 0)
9236 (match_operand:QI 2 "nonmemory_operand" "I,c"))
9237 (ashift:SI (match_operand:SI 1 "register_operand" "r,r")
9238 (minus:QI (const_int 32) (match_dup 2)))))
9239 (clobber (reg:CC 17))]
9240 ""
9241 "@
9242 shrd{l}\\t{%2, %1, %0|%0, %1, %2}
9243 shrd{l}\\t{%s2%1, %0|%0, %1, %2}"
9244 [(set_attr "type" "ishift")
9245 (set_attr "prefix_0f" "1")
9246 (set_attr "pent_pair" "np")
9247 (set_attr "ppro_uops" "few")
9248 (set_attr "mode" "SI")])
9249
9250 (define_expand "x86_shift_adj_3"
9251 [(use (match_operand:SI 0 "register_operand" ""))
9252 (use (match_operand:SI 1 "register_operand" ""))
9253 (use (match_operand:QI 2 "register_operand" ""))]
9254 ""
9255 "
9256 {
9257 rtx label = gen_label_rtx ();
9258 rtx tmp;
9259
9260 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
9261
9262 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
9263 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
9264 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
9265 gen_rtx_LABEL_REF (VOIDmode, label),
9266 pc_rtx);
9267 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
9268 JUMP_LABEL (tmp) = label;
9269
9270 emit_move_insn (operands[0], operands[1]);
9271 emit_insn (gen_ashrsi3_31 (operands[1], operands[1], GEN_INT (31)));
9272
9273 emit_label (label);
9274 LABEL_NUSES (label) = 1;
9275
9276 DONE;
9277 }")
9278
9279 (define_insn "ashrsi3_31"
9280 [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
9281 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
9282 (match_operand:SI 2 "const_int_operand" "i,i")))
9283 (clobber (reg:CC 17))]
9284 "INTVAL (operands[2]) == 31 && (TARGET_USE_CLTD || optimize_size)
9285 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
9286 "@
9287 {cltd|cdq}
9288 sar{l}\\t{%2, %0|%0, %2}"
9289 [(set_attr "type" "imovx,ishift")
9290 (set_attr "prefix_0f" "0,*")
9291 (set_attr "length_immediate" "0,*")
9292 (set_attr "modrm" "0,1")
9293 (set_attr "mode" "SI")])
9294
9295 (define_expand "ashrsi3"
9296 [(set (match_operand:SI 0 "nonimmediate_operand" "")
9297 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
9298 (match_operand:QI 2 "nonmemory_operand" "")))
9299 (clobber (reg:CC 17))]
9300 ""
9301 "ix86_expand_binary_operator (ASHIFTRT, SImode, operands); DONE;")
9302
9303 (define_insn "*ashrsi3_1_one_bit"
9304 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9305 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
9306 (match_operand:QI 2 "const_int_1_operand" "")))
9307 (clobber (reg:CC 17))]
9308 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
9309 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9310 "sar{l}\\t%0"
9311 [(set_attr "type" "ishift")
9312 (set (attr "length")
9313 (if_then_else (match_operand:SI 0 "register_operand" "")
9314 (const_string "2")
9315 (const_string "*")))])
9316
9317 (define_insn "*ashrsi3_1"
9318 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
9319 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
9320 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9321 (clobber (reg:CC 17))]
9322 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
9323 "@
9324 sar{l}\\t{%2, %0|%0, %2}
9325 sar{l}\\t{%b2, %0|%0, %b2}"
9326 [(set_attr "type" "ishift")
9327 (set_attr "mode" "SI")])
9328
9329 ;; This pattern can't accept a variable shift count, since shifts by
9330 ;; zero don't affect the flags. We assume that shifts by constant
9331 ;; zero are optimized away.
9332 (define_insn "*ashrsi3_one_bit_cmp"
9333 [(set (reg 17)
9334 (compare
9335 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
9336 (match_operand:QI 2 "const_int_1_operand" ""))
9337 (const_int 0)))
9338 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9339 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
9340 "ix86_match_ccmode (insn, CCGOCmode)
9341 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)
9342 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
9343 "sar{l}\\t%0"
9344 [(set_attr "type" "ishift")
9345 (set (attr "length")
9346 (if_then_else (match_operand:SI 0 "register_operand" "")
9347 (const_string "2")
9348 (const_string "*")))])
9349
9350 ;; This pattern can't accept a variable shift count, since shifts by
9351 ;; zero don't affect the flags. We assume that shifts by constant
9352 ;; zero are optimized away.
9353 (define_insn "*ashrsi3_cmp"
9354 [(set (reg 17)
9355 (compare
9356 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
9357 (match_operand:QI 2 "immediate_operand" "I"))
9358 (const_int 0)))
9359 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9360 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
9361 "ix86_match_ccmode (insn, CCGOCmode)
9362 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
9363 "sar{l}\\t{%2, %0|%0, %2}"
9364 [(set_attr "type" "ishift")
9365 (set_attr "mode" "SI")])
9366
9367 (define_expand "ashrhi3"
9368 [(set (match_operand:HI 0 "nonimmediate_operand" "")
9369 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
9370 (match_operand:QI 2 "nonmemory_operand" "")))
9371 (clobber (reg:CC 17))]
9372 "TARGET_HIMODE_MATH"
9373 "ix86_expand_binary_operator (ASHIFTRT, HImode, operands); DONE;")
9374
9375 (define_insn "*ashrhi3_1_one_bit"
9376 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9377 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
9378 (match_operand:QI 2 "const_int_1_operand" "")))
9379 (clobber (reg:CC 17))]
9380 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)
9381 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9382 "sar{w}\\t%0"
9383 [(set_attr "type" "ishift")
9384 (set (attr "length")
9385 (if_then_else (match_operand 0 "register_operand" "")
9386 (const_string "2")
9387 (const_string "*")))])
9388
9389 (define_insn "*ashrhi3_1"
9390 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
9391 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
9392 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9393 (clobber (reg:CC 17))]
9394 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
9395 "@
9396 sar{w}\\t{%2, %0|%0, %2}
9397 sar{w}\\t{%b2, %0|%0, %b2}"
9398 [(set_attr "type" "ishift")
9399 (set_attr "mode" "HI")])
9400
9401 ;; This pattern can't accept a variable shift count, since shifts by
9402 ;; zero don't affect the flags. We assume that shifts by constant
9403 ;; zero are optimized away.
9404 (define_insn "*ashrhi3_one_bit_cmp"
9405 [(set (reg 17)
9406 (compare
9407 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
9408 (match_operand:QI 2 "const_int_1_operand" ""))
9409 (const_int 0)))
9410 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9411 (ashiftrt:HI (match_dup 1) (match_dup 2)))]
9412 "ix86_match_ccmode (insn, CCGOCmode)
9413 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)
9414 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
9415 "sar{w}\\t%0"
9416 [(set_attr "type" "ishift")
9417 (set (attr "length")
9418 (if_then_else (match_operand 0 "register_operand" "")
9419 (const_string "2")
9420 (const_string "*")))])
9421
9422 ;; This pattern can't accept a variable shift count, since shifts by
9423 ;; zero don't affect the flags. We assume that shifts by constant
9424 ;; zero are optimized away.
9425 (define_insn "*ashrhi3_cmp"
9426 [(set (reg 17)
9427 (compare
9428 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
9429 (match_operand:QI 2 "immediate_operand" "I"))
9430 (const_int 0)))
9431 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9432 (ashiftrt:HI (match_dup 1) (match_dup 2)))]
9433 "ix86_match_ccmode (insn, CCGOCmode)
9434 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
9435 "sar{w}\\t{%2, %0|%0, %2}"
9436 [(set_attr "type" "ishift")
9437 (set_attr "mode" "HI")])
9438
9439 (define_expand "ashrqi3"
9440 [(set (match_operand:QI 0 "nonimmediate_operand" "")
9441 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
9442 (match_operand:QI 2 "nonmemory_operand" "")))
9443 (clobber (reg:CC 17))]
9444 "TARGET_QIMODE_MATH"
9445 "ix86_expand_binary_operator (ASHIFTRT, QImode, operands); DONE;")
9446
9447 (define_insn "*ashrqi3_1_one_bit"
9448 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9449 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
9450 (match_operand:QI 2 "const_int_1_operand" "")))
9451 (clobber (reg:CC 17))]
9452 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
9453 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9454 "sar{b}\\t%0"
9455 [(set_attr "type" "ishift")
9456 (set (attr "length")
9457 (if_then_else (match_operand 0 "register_operand" "")
9458 (const_string "2")
9459 (const_string "*")))])
9460
9461 (define_insn "*ashrqi3_1"
9462 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
9463 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
9464 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9465 (clobber (reg:CC 17))]
9466 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
9467 "@
9468 sar{b}\\t{%2, %0|%0, %2}
9469 sar{b}\\t{%b2, %0|%0, %b2}"
9470 [(set_attr "type" "ishift")
9471 (set_attr "mode" "QI")])
9472
9473 ;; This pattern can't accept a variable shift count, since shifts by
9474 ;; zero don't affect the flags. We assume that shifts by constant
9475 ;; zero are optimized away.
9476 (define_insn "*ashrqi3_one_bit_cmp"
9477 [(set (reg 17)
9478 (compare
9479 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
9480 (match_operand:QI 2 "const_int_1_operand" "I"))
9481 (const_int 0)))
9482 (set (match_operand:QI 0 "nonimmediate_operand" "=rm")
9483 (ashiftrt:QI (match_dup 1) (match_dup 2)))]
9484 "ix86_match_ccmode (insn, CCGOCmode)
9485 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)
9486 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
9487 "sar{b}\\t%0"
9488 [(set_attr "type" "ishift")
9489 (set (attr "length")
9490 (if_then_else (match_operand 0 "register_operand" "")
9491 (const_string "2")
9492 (const_string "*")))])
9493
9494 ;; This pattern can't accept a variable shift count, since shifts by
9495 ;; zero don't affect the flags. We assume that shifts by constant
9496 ;; zero are optimized away.
9497 (define_insn "*ashrqi3_cmp"
9498 [(set (reg 17)
9499 (compare
9500 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
9501 (match_operand:QI 2 "immediate_operand" "I"))
9502 (const_int 0)))
9503 (set (match_operand:QI 0 "nonimmediate_operand" "=rm")
9504 (ashiftrt:QI (match_dup 1) (match_dup 2)))]
9505 "ix86_match_ccmode (insn, CCGOCmode)
9506 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
9507 "sar{b}\\t{%2, %0|%0, %2}"
9508 [(set_attr "type" "ishift")
9509 (set_attr "mode" "QI")])
9510 \f
9511 ;; Logical shift instructions
9512
9513 ;; See comment above `ashldi3' about how this works.
9514
9515 (define_expand "lshrdi3"
9516 [(parallel [(set (match_operand:DI 0 "register_operand" "=r")
9517 (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
9518 (match_operand:QI 2 "nonmemory_operand" "Jc")))
9519 (clobber (reg:CC 17))])]
9520 ""
9521 "
9522 {
9523 if (TARGET_CMOVE && ! immediate_operand (operands[2], QImode))
9524 {
9525 emit_insn (gen_lshrdi3_1 (operands[0], operands[1], operands[2]));
9526 DONE;
9527 }
9528 }")
9529
9530 (define_insn "lshrdi3_1"
9531 [(set (match_operand:DI 0 "register_operand" "=r")
9532 (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
9533 (match_operand:QI 2 "nonmemory_operand" "Jc")))
9534 (clobber (match_scratch:SI 3 "=&r"))
9535 (clobber (reg:CC 17))]
9536 "!TARGET_64BIT && TARGET_CMOVE"
9537 "#"
9538 [(set_attr "type" "multi")])
9539
9540 (define_insn "*lshrdi3_2"
9541 [(set (match_operand:DI 0 "register_operand" "=r")
9542 (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
9543 (match_operand:QI 2 "nonmemory_operand" "Jc")))
9544 (clobber (reg:CC 17))]
9545 "!TARGET_64BIT"
9546 "#"
9547 [(set_attr "type" "multi")])
9548
9549 (define_split
9550 [(set (match_operand:DI 0 "register_operand" "")
9551 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
9552 (match_operand:QI 2 "nonmemory_operand" "")))
9553 (clobber (match_scratch:SI 3 ""))
9554 (clobber (reg:CC 17))]
9555 "!TARGET_64BIT && TARGET_CMOVE && reload_completed"
9556 [(const_int 0)]
9557 "ix86_split_lshrdi (operands, operands[3]); DONE;")
9558
9559 (define_split
9560 [(set (match_operand:DI 0 "register_operand" "")
9561 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
9562 (match_operand:QI 2 "nonmemory_operand" "")))
9563 (clobber (reg:CC 17))]
9564 "!TARGET_64BIT && reload_completed"
9565 [(const_int 0)]
9566 "ix86_split_lshrdi (operands, NULL_RTX); DONE;")
9567
9568 (define_expand "lshrsi3"
9569 [(set (match_operand:SI 0 "nonimmediate_operand" "")
9570 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
9571 (match_operand:QI 2 "nonmemory_operand" "")))
9572 (clobber (reg:CC 17))]
9573 ""
9574 "ix86_expand_binary_operator (LSHIFTRT, SImode, operands); DONE;")
9575
9576 (define_insn "*lshrsi3_1_one_bit"
9577 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9578 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
9579 (match_operand:QI 2 "const_int_1_operand" "")))
9580 (clobber (reg:CC 17))]
9581 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
9582 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9583 "shr{l}\\t%0"
9584 [(set_attr "type" "ishift")
9585 (set (attr "length")
9586 (if_then_else (match_operand:SI 0 "register_operand" "")
9587 (const_string "2")
9588 (const_string "*")))])
9589
9590 (define_insn "*lshrsi3_1"
9591 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
9592 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
9593 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9594 (clobber (reg:CC 17))]
9595 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
9596 "@
9597 shr{l}\\t{%2, %0|%0, %2}
9598 shr{l}\\t{%b2, %0|%0, %b2}"
9599 [(set_attr "type" "ishift")
9600 (set_attr "mode" "SI")])
9601
9602 ;; This pattern can't accept a variable shift count, since shifts by
9603 ;; zero don't affect the flags. We assume that shifts by constant
9604 ;; zero are optimized away.
9605 (define_insn "*lshrsi3_one_bit_cmp"
9606 [(set (reg 17)
9607 (compare
9608 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
9609 (match_operand:QI 2 "const_int_1_operand" ""))
9610 (const_int 0)))
9611 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9612 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
9613 "ix86_match_ccmode (insn, CCGOCmode)
9614 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)
9615 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
9616 "shr{l}\\t%0"
9617 [(set_attr "type" "ishift")
9618 (set (attr "length")
9619 (if_then_else (match_operand:SI 0 "register_operand" "")
9620 (const_string "2")
9621 (const_string "*")))])
9622
9623 ;; This pattern can't accept a variable shift count, since shifts by
9624 ;; zero don't affect the flags. We assume that shifts by constant
9625 ;; zero are optimized away.
9626 (define_insn "*lshrsi3_cmp"
9627 [(set (reg 17)
9628 (compare
9629 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
9630 (match_operand:QI 2 "immediate_operand" "I"))
9631 (const_int 0)))
9632 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9633 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
9634 "ix86_match_ccmode (insn, CCGOCmode)
9635 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
9636 "shr{l}\\t{%2, %0|%0, %2}"
9637 [(set_attr "type" "ishift")
9638 (set_attr "mode" "SI")])
9639
9640 (define_expand "lshrhi3"
9641 [(set (match_operand:HI 0 "nonimmediate_operand" "")
9642 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
9643 (match_operand:QI 2 "nonmemory_operand" "")))
9644 (clobber (reg:CC 17))]
9645 "TARGET_HIMODE_MATH"
9646 "ix86_expand_binary_operator (LSHIFTRT, HImode, operands); DONE;")
9647
9648 (define_insn "*lshrhi3_1_one_bit"
9649 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9650 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
9651 (match_operand:QI 2 "const_int_1_operand" "")))
9652 (clobber (reg:CC 17))]
9653 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
9654 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9655 "shr{w}\\t%0"
9656 [(set_attr "type" "ishift")
9657 (set (attr "length")
9658 (if_then_else (match_operand 0 "register_operand" "")
9659 (const_string "2")
9660 (const_string "*")))])
9661
9662 (define_insn "*lshrhi3_1"
9663 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
9664 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
9665 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9666 (clobber (reg:CC 17))]
9667 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
9668 "@
9669 shr{w}\\t{%2, %0|%0, %2}
9670 shr{w}\\t{%b2, %0|%0, %b2}"
9671 [(set_attr "type" "ishift")
9672 (set_attr "mode" "HI")])
9673
9674 ;; This pattern can't accept a variable shift count, since shifts by
9675 ;; zero don't affect the flags. We assume that shifts by constant
9676 ;; zero are optimized away.
9677 (define_insn "*lshrhi3_one_bit_cmp"
9678 [(set (reg 17)
9679 (compare
9680 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
9681 (match_operand:QI 2 "const_int_1_operand" ""))
9682 (const_int 0)))
9683 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9684 (lshiftrt:HI (match_dup 1) (match_dup 2)))]
9685 "ix86_match_ccmode (insn, CCGOCmode)
9686 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)
9687 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
9688 "shr{w}\\t%0"
9689 [(set_attr "type" "ishift")
9690 (set (attr "length")
9691 (if_then_else (match_operand:SI 0 "register_operand" "")
9692 (const_string "2")
9693 (const_string "*")))])
9694
9695 ;; This pattern can't accept a variable shift count, since shifts by
9696 ;; zero don't affect the flags. We assume that shifts by constant
9697 ;; zero are optimized away.
9698 (define_insn "*lshrhi3_cmp"
9699 [(set (reg 17)
9700 (compare
9701 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
9702 (match_operand:QI 2 "immediate_operand" "I"))
9703 (const_int 0)))
9704 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9705 (lshiftrt:HI (match_dup 1) (match_dup 2)))]
9706 "ix86_match_ccmode (insn, CCGOCmode)
9707 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
9708 "shr{w}\\t{%2, %0|%0, %2}"
9709 [(set_attr "type" "ishift")
9710 (set_attr "mode" "HI")])
9711
9712 (define_expand "lshrqi3"
9713 [(set (match_operand:QI 0 "nonimmediate_operand" "")
9714 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
9715 (match_operand:QI 2 "nonmemory_operand" "")))
9716 (clobber (reg:CC 17))]
9717 "TARGET_QIMODE_MATH"
9718 "ix86_expand_binary_operator (LSHIFTRT, QImode, operands); DONE;")
9719
9720 (define_insn "*lshrqi3_1_one_bit"
9721 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9722 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
9723 (match_operand:QI 2 "const_int_1_operand" "")))
9724 (clobber (reg:CC 17))]
9725 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)
9726 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9727 "shr{b}\\t%0"
9728 [(set_attr "type" "ishift")
9729 (set (attr "length")
9730 (if_then_else (match_operand 0 "register_operand" "")
9731 (const_string "2")
9732 (const_string "*")))])
9733
9734 (define_insn "*lshrqi3_1"
9735 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
9736 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
9737 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9738 (clobber (reg:CC 17))]
9739 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
9740 "@
9741 shr{b}\\t{%2, %0|%0, %2}
9742 shr{b}\\t{%b2, %0|%0, %b2}"
9743 [(set_attr "type" "ishift")
9744 (set_attr "mode" "QI")])
9745
9746 ;; This pattern can't accept a variable shift count, since shifts by
9747 ;; zero don't affect the flags. We assume that shifts by constant
9748 ;; zero are optimized away.
9749 (define_insn "*lshrqi2_one_bit_cmp"
9750 [(set (reg 17)
9751 (compare
9752 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
9753 (match_operand:QI 2 "const_int_1_operand" ""))
9754 (const_int 0)))
9755 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9756 (lshiftrt:QI (match_dup 1) (match_dup 2)))]
9757 "ix86_match_ccmode (insn, CCGOCmode)
9758 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)
9759 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
9760 "shr{b}\\t%0"
9761 [(set_attr "type" "ishift")
9762 (set (attr "length")
9763 (if_then_else (match_operand:SI 0 "register_operand" "")
9764 (const_string "2")
9765 (const_string "*")))])
9766
9767 ;; This pattern can't accept a variable shift count, since shifts by
9768 ;; zero don't affect the flags. We assume that shifts by constant
9769 ;; zero are optimized away.
9770 (define_insn "*lshrqi2_cmp"
9771 [(set (reg 17)
9772 (compare
9773 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
9774 (match_operand:QI 2 "immediate_operand" "I"))
9775 (const_int 0)))
9776 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9777 (lshiftrt:QI (match_dup 1) (match_dup 2)))]
9778 "ix86_match_ccmode (insn, CCGOCmode)
9779 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
9780 "shr{b}\\t{%2, %0|%0, %2}"
9781 [(set_attr "type" "ishift")
9782 (set_attr "mode" "QI")])
9783 \f
9784 ;; Rotate instructions
9785
9786 (define_expand "rotlsi3"
9787 [(set (match_operand:SI 0 "nonimmediate_operand" "")
9788 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
9789 (match_operand:QI 2 "nonmemory_operand" "")))
9790 (clobber (reg:CC 17))]
9791 ""
9792 "ix86_expand_binary_operator (ROTATE, SImode, operands); DONE;")
9793
9794 (define_insn "*rotlsi3_1_one_bit"
9795 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9796 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0")
9797 (match_operand:QI 2 "const_int_1_operand" "")))
9798 (clobber (reg:CC 17))]
9799 "ix86_binary_operator_ok (ROTATE, SImode, operands)
9800 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9801 "rol{l}\\t%0"
9802 [(set_attr "type" "ishift")
9803 (set (attr "length")
9804 (if_then_else (match_operand:SI 0 "register_operand" "")
9805 (const_string "2")
9806 (const_string "*")))])
9807
9808 (define_insn "*rotlsi3_1"
9809 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
9810 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
9811 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9812 (clobber (reg:CC 17))]
9813 "ix86_binary_operator_ok (ROTATE, SImode, operands)"
9814 "@
9815 rol{l}\\t{%2, %0|%0, %2}
9816 rol{l}\\t{%b2, %0|%0, %b2}"
9817 [(set_attr "type" "ishift")
9818 (set_attr "mode" "SI")])
9819
9820 (define_expand "rotlhi3"
9821 [(set (match_operand:HI 0 "nonimmediate_operand" "")
9822 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "")
9823 (match_operand:QI 2 "nonmemory_operand" "")))
9824 (clobber (reg:CC 17))]
9825 "TARGET_HIMODE_MATH"
9826 "ix86_expand_binary_operator (ROTATE, HImode, operands); DONE;")
9827
9828 (define_insn "*rotlhi3_1_one_bit"
9829 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9830 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0")
9831 (match_operand:QI 2 "const_int_1_operand" "")))
9832 (clobber (reg:CC 17))]
9833 "ix86_binary_operator_ok (ROTATE, HImode, operands)
9834 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9835 "rol{w}\\t%0"
9836 [(set_attr "type" "ishift")
9837 (set (attr "length")
9838 (if_then_else (match_operand 0 "register_operand" "")
9839 (const_string "2")
9840 (const_string "*")))])
9841
9842 (define_insn "*rotlhi3_1"
9843 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
9844 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
9845 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9846 (clobber (reg:CC 17))]
9847 "ix86_binary_operator_ok (ROTATE, HImode, operands)"
9848 "@
9849 rol{w}\\t{%2, %0|%0, %2}
9850 rol{w}\\t{%b2, %0|%0, %b2}"
9851 [(set_attr "type" "ishift")
9852 (set_attr "mode" "HI")])
9853
9854 (define_expand "rotlqi3"
9855 [(set (match_operand:QI 0 "nonimmediate_operand" "")
9856 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "")
9857 (match_operand:QI 2 "nonmemory_operand" "")))
9858 (clobber (reg:CC 17))]
9859 "TARGET_QIMODE_MATH"
9860 "ix86_expand_binary_operator (ROTATE, QImode, operands); DONE;")
9861
9862 (define_insn "*rotlqi3_1_one_bit"
9863 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9864 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0")
9865 (match_operand:QI 2 "const_int_1_operand" "")))
9866 (clobber (reg:CC 17))]
9867 "ix86_binary_operator_ok (ROTATE, QImode, operands)
9868 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9869 "rol{b}\\t%0"
9870 [(set_attr "type" "ishift")
9871 (set (attr "length")
9872 (if_then_else (match_operand 0 "register_operand" "")
9873 (const_string "2")
9874 (const_string "*")))])
9875
9876 (define_insn "*rotlqi3_1"
9877 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
9878 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
9879 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9880 (clobber (reg:CC 17))]
9881 "ix86_binary_operator_ok (ROTATE, QImode, operands)"
9882 "@
9883 rol{b}\\t{%2, %0|%0, %2}
9884 rol{b}\\t{%b2, %0|%0, %b2}"
9885 [(set_attr "type" "ishift")
9886 (set_attr "mode" "QI")])
9887
9888 (define_expand "rotrsi3"
9889 [(set (match_operand:SI 0 "nonimmediate_operand" "")
9890 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
9891 (match_operand:QI 2 "nonmemory_operand" "")))
9892 (clobber (reg:CC 17))]
9893 ""
9894 "ix86_expand_binary_operator (ROTATERT, SImode, operands); DONE;")
9895
9896 (define_insn "*rotrsi3_1_one_bit"
9897 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9898 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0")
9899 (match_operand:QI 2 "const_int_1_operand" "")))
9900 (clobber (reg:CC 17))]
9901 "ix86_binary_operator_ok (ROTATERT, SImode, operands)
9902 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9903 "ror{l}\\t%0"
9904 [(set_attr "type" "ishift")
9905 (set (attr "length")
9906 (if_then_else (match_operand:SI 0 "register_operand" "")
9907 (const_string "2")
9908 (const_string "*")))])
9909
9910 (define_insn "*rotrsi3_1"
9911 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
9912 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
9913 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9914 (clobber (reg:CC 17))]
9915 "ix86_binary_operator_ok (ROTATERT, SImode, operands)"
9916 "@
9917 ror{l}\\t{%2, %0|%0, %2}
9918 ror{l}\\t{%b2, %0|%0, %b2}"
9919 [(set_attr "type" "ishift")
9920 (set_attr "mode" "SI")])
9921
9922 (define_expand "rotrhi3"
9923 [(set (match_operand:HI 0 "nonimmediate_operand" "")
9924 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "")
9925 (match_operand:QI 2 "nonmemory_operand" "")))
9926 (clobber (reg:CC 17))]
9927 "TARGET_HIMODE_MATH"
9928 "ix86_expand_binary_operator (ROTATERT, HImode, operands); DONE;")
9929
9930 (define_insn "*rotrhi3_one_bit"
9931 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9932 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0")
9933 (match_operand:QI 2 "const_int_1_operand" "")))
9934 (clobber (reg:CC 17))]
9935 "ix86_binary_operator_ok (ROTATERT, HImode, operands)
9936 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9937 "ror{w}\\t%0"
9938 [(set_attr "type" "ishift")
9939 (set (attr "length")
9940 (if_then_else (match_operand 0 "register_operand" "")
9941 (const_string "2")
9942 (const_string "*")))])
9943
9944 (define_insn "*rotrhi3"
9945 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
9946 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
9947 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9948 (clobber (reg:CC 17))]
9949 "ix86_binary_operator_ok (ROTATERT, HImode, operands)"
9950 "@
9951 ror{w}\\t{%2, %0|%0, %2}
9952 ror{w}\\t{%b2, %0|%0, %b2}"
9953 [(set_attr "type" "ishift")
9954 (set_attr "mode" "HI")])
9955
9956 (define_expand "rotrqi3"
9957 [(set (match_operand:QI 0 "nonimmediate_operand" "")
9958 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "")
9959 (match_operand:QI 2 "nonmemory_operand" "")))
9960 (clobber (reg:CC 17))]
9961 "TARGET_QIMODE_MATH"
9962 "ix86_expand_binary_operator (ROTATERT, QImode, operands); DONE;")
9963
9964 (define_insn "*rotrqi3_1_one_bit"
9965 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9966 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0")
9967 (match_operand:QI 2 "const_int_1_operand" "")))
9968 (clobber (reg:CC 17))]
9969 "ix86_binary_operator_ok (ROTATERT, QImode, operands)
9970 && (TARGET_PENTIUM || TARGET_PENTIUMPRO)"
9971 "ror{b}\\t%0"
9972 [(set_attr "type" "ishift")
9973 (set (attr "length")
9974 (if_then_else (match_operand 0 "register_operand" "")
9975 (const_string "2")
9976 (const_string "*")))])
9977
9978 (define_insn "*rotrqi3_1"
9979 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
9980 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
9981 (match_operand:QI 2 "nonmemory_operand" "I,c")))
9982 (clobber (reg:CC 17))]
9983 "ix86_binary_operator_ok (ROTATERT, QImode, operands)"
9984 "@
9985 ror{b}\\t{%2, %0|%0, %2}
9986 ror{b}\\t{%b2, %0|%0, %b2}"
9987 [(set_attr "type" "ishift")
9988 (set_attr "mode" "QI")])
9989 \f
9990 ;; Bit set / bit test instructions
9991
9992 (define_expand "extv"
9993 [(set (match_operand:SI 0 "register_operand" "")
9994 (sign_extract:SI (match_operand:SI 1 "register_operand" "")
9995 (match_operand:SI 2 "immediate_operand" "")
9996 (match_operand:SI 3 "immediate_operand" "")))]
9997 ""
9998 "
9999 {
10000 /* Handle extractions from %ah et al. */
10001 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
10002 FAIL;
10003
10004 /* From mips.md: extract_bit_field doesn't verify that our source
10005 matches the predicate, so check it again here. */
10006 if (! register_operand (operands[1], VOIDmode))
10007 FAIL;
10008 }")
10009
10010 (define_expand "extzv"
10011 [(set (match_operand:SI 0 "register_operand" "")
10012 (zero_extract:SI (match_operand 1 "ext_register_operand" "")
10013 (match_operand:SI 2 "immediate_operand" "")
10014 (match_operand:SI 3 "immediate_operand" "")))]
10015 ""
10016 "
10017 {
10018 /* Handle extractions from %ah et al. */
10019 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
10020 FAIL;
10021
10022 /* From mips.md: extract_bit_field doesn't verify that our source
10023 matches the predicate, so check it again here. */
10024 if (! register_operand (operands[1], VOIDmode))
10025 FAIL;
10026 }")
10027
10028 (define_expand "insv"
10029 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
10030 (match_operand:SI 1 "immediate_operand" "")
10031 (match_operand:SI 2 "immediate_operand" ""))
10032 (match_operand:SI 3 "register_operand" ""))]
10033 ""
10034 "
10035 {
10036 /* Handle extractions from %ah et al. */
10037 if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
10038 FAIL;
10039
10040 /* From mips.md: insert_bit_field doesn't verify that our source
10041 matches the predicate, so check it again here. */
10042 if (! register_operand (operands[0], VOIDmode))
10043 FAIL;
10044 }")
10045
10046 ;; %%% bts, btr, btc, bt.
10047 \f
10048 ;; Store-flag instructions.
10049
10050 ;; For all sCOND expanders, also expand the compare or test insn that
10051 ;; generates cc0. Generate an equality comparison if `seq' or `sne'.
10052
10053 ;; %%% Do the expansion to SImode. If PII, do things the xor+setcc way
10054 ;; to avoid partial register stalls. Otherwise do things the setcc+movzx
10055 ;; way, which can later delete the movzx if only QImode is needed.
10056
10057 (define_expand "seq"
10058 [(set (match_operand:SI 0 "register_operand" "")
10059 (eq:SI (reg:CC 17) (const_int 0)))]
10060 ""
10061 "if (ix86_expand_setcc (EQ, operands[0])) DONE; else FAIL;")
10062
10063 (define_expand "sne"
10064 [(set (match_operand:SI 0 "register_operand" "")
10065 (ne:SI (reg:CC 17) (const_int 0)))]
10066 ""
10067 "if (ix86_expand_setcc (NE, operands[0])) DONE; else FAIL;")
10068
10069 (define_expand "sgt"
10070 [(set (match_operand:SI 0 "register_operand" "")
10071 (gt:SI (reg:CC 17) (const_int 0)))]
10072 ""
10073 "if (ix86_expand_setcc (GT, operands[0])) DONE; else FAIL;")
10074
10075 (define_expand "sgtu"
10076 [(set (match_operand:SI 0 "register_operand" "")
10077 (gtu:SI (reg:CC 17) (const_int 0)))]
10078 ""
10079 "if (ix86_expand_setcc (GTU, operands[0])) DONE; else FAIL;")
10080
10081 (define_expand "slt"
10082 [(set (match_operand:SI 0 "register_operand" "")
10083 (lt:SI (reg:CC 17) (const_int 0)))]
10084 ""
10085 "if (ix86_expand_setcc (LT, operands[0])) DONE; else FAIL;")
10086
10087 (define_expand "sltu"
10088 [(set (match_operand:SI 0 "register_operand" "")
10089 (ltu:SI (reg:CC 17) (const_int 0)))]
10090 ""
10091 "if (ix86_expand_setcc (LTU, operands[0])) DONE; else FAIL;")
10092
10093 (define_expand "sge"
10094 [(set (match_operand:SI 0 "register_operand" "")
10095 (ge:SI (reg:CC 17) (const_int 0)))]
10096 ""
10097 "if (ix86_expand_setcc (GE, operands[0])) DONE; else FAIL;")
10098
10099 (define_expand "sgeu"
10100 [(set (match_operand:SI 0 "register_operand" "")
10101 (geu:SI (reg:CC 17) (const_int 0)))]
10102 ""
10103 "if (ix86_expand_setcc (GEU, operands[0])) DONE; else FAIL;")
10104
10105 (define_expand "sle"
10106 [(set (match_operand:SI 0 "register_operand" "")
10107 (le:SI (reg:CC 17) (const_int 0)))]
10108 ""
10109 "if (ix86_expand_setcc (LE, operands[0])) DONE; else FAIL;")
10110
10111 (define_expand "sleu"
10112 [(set (match_operand:SI 0 "register_operand" "")
10113 (leu:SI (reg:CC 17) (const_int 0)))]
10114 ""
10115 "if (ix86_expand_setcc (LEU, operands[0])) DONE; else FAIL;")
10116
10117 (define_expand "sunordered"
10118 [(set (match_operand:SI 0 "register_operand" "")
10119 (unordered:SI (reg:CC 17) (const_int 0)))]
10120 "TARGET_80387 || TARGET_SSE"
10121 "if (ix86_expand_setcc (UNORDERED, operands[0])) DONE; else FAIL;")
10122
10123 (define_expand "sordered"
10124 [(set (match_operand:SI 0 "register_operand" "")
10125 (ordered:SI (reg:CC 17) (const_int 0)))]
10126 "TARGET_80387"
10127 "if (ix86_expand_setcc (ORDERED, operands[0])) DONE; else FAIL;")
10128
10129 (define_expand "suneq"
10130 [(set (match_operand:SI 0 "register_operand" "")
10131 (uneq:SI (reg:CC 17) (const_int 0)))]
10132 "TARGET_80387 || TARGET_SSE"
10133 "if (ix86_expand_setcc (UNEQ, operands[0])) DONE; else FAIL;")
10134
10135 (define_expand "sunge"
10136 [(set (match_operand:SI 0 "register_operand" "")
10137 (unge:SI (reg:CC 17) (const_int 0)))]
10138 "TARGET_80387 || TARGET_SSE"
10139 "if (ix86_expand_setcc (UNGE, operands[0])) DONE; else FAIL;")
10140
10141 (define_expand "sungt"
10142 [(set (match_operand:SI 0 "register_operand" "")
10143 (ungt:SI (reg:CC 17) (const_int 0)))]
10144 "TARGET_80387 || TARGET_SSE"
10145 "if (ix86_expand_setcc (UNGT, operands[0])) DONE; else FAIL;")
10146
10147 (define_expand "sunle"
10148 [(set (match_operand:SI 0 "register_operand" "")
10149 (unle:SI (reg:CC 17) (const_int 0)))]
10150 "TARGET_80387 || TARGET_SSE"
10151 "if (ix86_expand_setcc (UNLE, operands[0])) DONE; else FAIL;")
10152
10153 (define_expand "sunlt"
10154 [(set (match_operand:SI 0 "register_operand" "")
10155 (unlt:SI (reg:CC 17) (const_int 0)))]
10156 "TARGET_80387 || TARGET_SSE"
10157 "if (ix86_expand_setcc (UNLT, operands[0])) DONE; else FAIL;")
10158
10159 (define_expand "sltgt"
10160 [(set (match_operand:SI 0 "register_operand" "")
10161 (ltgt:SI (reg:CC 17) (const_int 0)))]
10162 "TARGET_80387 || TARGET_SSE"
10163 "if (ix86_expand_setcc (LTGT, operands[0])) DONE; else FAIL;")
10164
10165 (define_insn "*setcc_1"
10166 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10167 (match_operator:QI 1 "ix86_comparison_operator"
10168 [(reg 17) (const_int 0)]))]
10169 ""
10170 "set%C1\\t%0"
10171 [(set_attr "type" "setcc")
10172 (set_attr "mode" "QI")])
10173
10174 (define_insn "setcc_2"
10175 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
10176 (match_operator:QI 1 "ix86_comparison_operator"
10177 [(reg 17) (const_int 0)]))]
10178 ""
10179 "set%C1\\t%0"
10180 [(set_attr "type" "setcc")
10181 (set_attr "mode" "QI")])
10182
10183 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
10184 ;; subsequent logical operations are used to imitate conditional moves.
10185 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
10186 ;; it directly. Futher holding this value in pseudo register might bring
10187 ;; problem in implicit normalization in spill code.
10188 ;; So we don't define FLOAT_STORE_FLAG_VALUE and create these
10189 ;; instructions after reload by splitting the conditional move patterns.
10190
10191 (define_insn "*sse_setccsf"
10192 [(set (match_operand:SF 0 "register_operand" "=x")
10193 (match_operator:SF 1 "sse_comparison_operator"
10194 [(match_operand:SF 2 "register_operand" "0")
10195 (match_operand:SF 3 "nonimmediate_operand" "xm")]))]
10196 "TARGET_SSE && reload_completed"
10197 "cmp%D1ss\\t{%3, %0|%0, %3}"
10198 [(set_attr "type" "sse")
10199 (set_attr "mode" "SF")])
10200
10201 (define_insn "*sse_setccdf"
10202 [(set (match_operand:DF 0 "register_operand" "=Y")
10203 (match_operator:DF 1 "sse_comparison_operator"
10204 [(match_operand:DF 2 "register_operand" "0")
10205 (match_operand:DF 3 "nonimmediate_operand" "Ym")]))]
10206 "TARGET_SSE2 && reload_completed"
10207 "cmp%D1sd\\t{%3, %0|%0, %3}"
10208 [(set_attr "type" "sse")
10209 (set_attr "mode" "DF")])
10210 \f
10211 ;; Basic conditional jump instructions.
10212 ;; We ignore the overflow flag for signed branch instructions.
10213
10214 ;; For all bCOND expanders, also expand the compare or test insn that
10215 ;; generates reg 17. Generate an equality comparison if `beq' or `bne'.
10216
10217 (define_expand "beq"
10218 [(set (pc)
10219 (if_then_else (match_dup 1)
10220 (label_ref (match_operand 0 "" ""))
10221 (pc)))]
10222 ""
10223 "ix86_expand_branch (EQ, operands[0]); DONE;")
10224
10225 (define_expand "bne"
10226 [(set (pc)
10227 (if_then_else (match_dup 1)
10228 (label_ref (match_operand 0 "" ""))
10229 (pc)))]
10230 ""
10231 "ix86_expand_branch (NE, operands[0]); DONE;")
10232
10233 (define_expand "bgt"
10234 [(set (pc)
10235 (if_then_else (match_dup 1)
10236 (label_ref (match_operand 0 "" ""))
10237 (pc)))]
10238 ""
10239 "ix86_expand_branch (GT, operands[0]); DONE;")
10240
10241 (define_expand "bgtu"
10242 [(set (pc)
10243 (if_then_else (match_dup 1)
10244 (label_ref (match_operand 0 "" ""))
10245 (pc)))]
10246 ""
10247 "ix86_expand_branch (GTU, operands[0]); DONE;")
10248
10249 (define_expand "blt"
10250 [(set (pc)
10251 (if_then_else (match_dup 1)
10252 (label_ref (match_operand 0 "" ""))
10253 (pc)))]
10254 ""
10255 "ix86_expand_branch (LT, operands[0]); DONE;")
10256
10257 (define_expand "bltu"
10258 [(set (pc)
10259 (if_then_else (match_dup 1)
10260 (label_ref (match_operand 0 "" ""))
10261 (pc)))]
10262 ""
10263 "ix86_expand_branch (LTU, operands[0]); DONE;")
10264
10265 (define_expand "bge"
10266 [(set (pc)
10267 (if_then_else (match_dup 1)
10268 (label_ref (match_operand 0 "" ""))
10269 (pc)))]
10270 ""
10271 "ix86_expand_branch (GE, operands[0]); DONE;")
10272
10273 (define_expand "bgeu"
10274 [(set (pc)
10275 (if_then_else (match_dup 1)
10276 (label_ref (match_operand 0 "" ""))
10277 (pc)))]
10278 ""
10279 "ix86_expand_branch (GEU, operands[0]); DONE;")
10280
10281 (define_expand "ble"
10282 [(set (pc)
10283 (if_then_else (match_dup 1)
10284 (label_ref (match_operand 0 "" ""))
10285 (pc)))]
10286 ""
10287 "ix86_expand_branch (LE, operands[0]); DONE;")
10288
10289 (define_expand "bleu"
10290 [(set (pc)
10291 (if_then_else (match_dup 1)
10292 (label_ref (match_operand 0 "" ""))
10293 (pc)))]
10294 ""
10295 "ix86_expand_branch (LEU, operands[0]); DONE;")
10296
10297 (define_expand "bunordered"
10298 [(set (pc)
10299 (if_then_else (match_dup 1)
10300 (label_ref (match_operand 0 "" ""))
10301 (pc)))]
10302 "TARGET_80387 || TARGET_SSE"
10303 "ix86_expand_branch (UNORDERED, operands[0]); DONE;")
10304
10305 (define_expand "bordered"
10306 [(set (pc)
10307 (if_then_else (match_dup 1)
10308 (label_ref (match_operand 0 "" ""))
10309 (pc)))]
10310 "TARGET_80387 || TARGET_SSE"
10311 "ix86_expand_branch (ORDERED, operands[0]); DONE;")
10312
10313 (define_expand "buneq"
10314 [(set (pc)
10315 (if_then_else (match_dup 1)
10316 (label_ref (match_operand 0 "" ""))
10317 (pc)))]
10318 "TARGET_80387 || TARGET_SSE"
10319 "ix86_expand_branch (UNEQ, operands[0]); DONE;")
10320
10321 (define_expand "bunge"
10322 [(set (pc)
10323 (if_then_else (match_dup 1)
10324 (label_ref (match_operand 0 "" ""))
10325 (pc)))]
10326 "TARGET_80387 || TARGET_SSE"
10327 "ix86_expand_branch (UNGE, operands[0]); DONE;")
10328
10329 (define_expand "bungt"
10330 [(set (pc)
10331 (if_then_else (match_dup 1)
10332 (label_ref (match_operand 0 "" ""))
10333 (pc)))]
10334 "TARGET_80387 || TARGET_SSE"
10335 "ix86_expand_branch (UNGT, operands[0]); DONE;")
10336
10337 (define_expand "bunle"
10338 [(set (pc)
10339 (if_then_else (match_dup 1)
10340 (label_ref (match_operand 0 "" ""))
10341 (pc)))]
10342 "TARGET_80387 || TARGET_SSE"
10343 "ix86_expand_branch (UNLE, operands[0]); DONE;")
10344
10345 (define_expand "bunlt"
10346 [(set (pc)
10347 (if_then_else (match_dup 1)
10348 (label_ref (match_operand 0 "" ""))
10349 (pc)))]
10350 "TARGET_80387 || TARGET_SSE"
10351 "ix86_expand_branch (UNLT, operands[0]); DONE;")
10352
10353 (define_expand "bltgt"
10354 [(set (pc)
10355 (if_then_else (match_dup 1)
10356 (label_ref (match_operand 0 "" ""))
10357 (pc)))]
10358 "TARGET_80387 || TARGET_SSE"
10359 "ix86_expand_branch (LTGT, operands[0]); DONE;")
10360
10361 (define_insn "*jcc_1"
10362 [(set (pc)
10363 (if_then_else (match_operator 1 "ix86_comparison_operator"
10364 [(reg 17) (const_int 0)])
10365 (label_ref (match_operand 0 "" ""))
10366 (pc)))]
10367 ""
10368 "j%C1\\t%l0"
10369 [(set_attr "type" "ibr")
10370 (set (attr "prefix_0f")
10371 (if_then_else (and (ge (minus (match_dup 0) (pc))
10372 (const_int -128))
10373 (lt (minus (match_dup 0) (pc))
10374 (const_int 124)))
10375 (const_int 0)
10376 (const_int 1)))])
10377
10378 (define_insn "*jcc_2"
10379 [(set (pc)
10380 (if_then_else (match_operator 1 "ix86_comparison_operator"
10381 [(reg 17) (const_int 0)])
10382 (pc)
10383 (label_ref (match_operand 0 "" ""))))]
10384 ""
10385 "j%c1\\t%l0"
10386 [(set_attr "type" "ibr")
10387 (set (attr "prefix_0f")
10388 (if_then_else (and (ge (minus (match_dup 0) (pc))
10389 (const_int -128))
10390 (lt (minus (match_dup 0) (pc))
10391 (const_int 124)))
10392 (const_int 0)
10393 (const_int 1)))])
10394
10395 ;; Define combination compare-and-branch fp compare instructions to use
10396 ;; during early optimization. Splitting the operation apart early makes
10397 ;; for bad code when we want to reverse the operation.
10398
10399 (define_insn "*fp_jcc_1"
10400 [(set (pc)
10401 (if_then_else (match_operator 0 "comparison_operator"
10402 [(match_operand 1 "register_operand" "f")
10403 (match_operand 2 "register_operand" "f")])
10404 (label_ref (match_operand 3 "" ""))
10405 (pc)))
10406 (clobber (reg:CCFP 18))
10407 (clobber (reg:CCFP 17))]
10408 "TARGET_CMOVE && TARGET_80387
10409 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
10410 && FLOAT_MODE_P (GET_MODE (operands[1]))
10411 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
10412 "#")
10413
10414 (define_insn "*fp_jcc_1_sse"
10415 [(set (pc)
10416 (if_then_else (match_operator 0 "comparison_operator"
10417 [(match_operand 1 "register_operand" "f#x,x#f")
10418 (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
10419 (label_ref (match_operand 3 "" ""))
10420 (pc)))
10421 (clobber (reg:CCFP 18))
10422 (clobber (reg:CCFP 17))]
10423 "TARGET_80387
10424 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
10425 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
10426 "#")
10427
10428 (define_insn "*fp_jcc_1_sse_only"
10429 [(set (pc)
10430 (if_then_else (match_operator 0 "comparison_operator"
10431 [(match_operand 1 "register_operand" "x")
10432 (match_operand 2 "nonimmediate_operand" "xm")])
10433 (label_ref (match_operand 3 "" ""))
10434 (pc)))
10435 (clobber (reg:CCFP 18))
10436 (clobber (reg:CCFP 17))]
10437 "SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
10438 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
10439 "#")
10440
10441 (define_insn "*fp_jcc_2"
10442 [(set (pc)
10443 (if_then_else (match_operator 0 "comparison_operator"
10444 [(match_operand 1 "register_operand" "f")
10445 (match_operand 2 "register_operand" "f")])
10446 (pc)
10447 (label_ref (match_operand 3 "" ""))))
10448 (clobber (reg:CCFP 18))
10449 (clobber (reg:CCFP 17))]
10450 "TARGET_CMOVE && TARGET_80387
10451 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
10452 && FLOAT_MODE_P (GET_MODE (operands[1]))
10453 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
10454 "#")
10455
10456 (define_insn "*fp_jcc_2_sse"
10457 [(set (pc)
10458 (if_then_else (match_operator 0 "comparison_operator"
10459 [(match_operand 1 "register_operand" "f#x,x#f")
10460 (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
10461 (pc)
10462 (label_ref (match_operand 3 "" ""))))
10463 (clobber (reg:CCFP 18))
10464 (clobber (reg:CCFP 17))]
10465 "TARGET_80387
10466 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
10467 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
10468 "#")
10469
10470 (define_insn "*fp_jcc_2_sse_only"
10471 [(set (pc)
10472 (if_then_else (match_operator 0 "comparison_operator"
10473 [(match_operand 1 "register_operand" "x")
10474 (match_operand 2 "nonimmediate_operand" "xm")])
10475 (pc)
10476 (label_ref (match_operand 3 "" ""))))
10477 (clobber (reg:CCFP 18))
10478 (clobber (reg:CCFP 17))]
10479 "SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
10480 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
10481 "#")
10482
10483 (define_insn "*fp_jcc_3"
10484 [(set (pc)
10485 (if_then_else (match_operator 0 "comparison_operator"
10486 [(match_operand 1 "register_operand" "f")
10487 (match_operand 2 "nonimmediate_operand" "fm")])
10488 (label_ref (match_operand 3 "" ""))
10489 (pc)))
10490 (clobber (reg:CCFP 18))
10491 (clobber (reg:CCFP 17))
10492 (clobber (match_scratch:HI 4 "=a"))]
10493 "TARGET_80387
10494 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
10495 && GET_MODE (operands[1]) == GET_MODE (operands[2])
10496 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
10497 && SELECT_CC_MODE (GET_CODE (operands[0]),
10498 operands[1], operands[2]) == CCFPmode"
10499 "#")
10500
10501 (define_insn "*fp_jcc_4"
10502 [(set (pc)
10503 (if_then_else (match_operator 0 "comparison_operator"
10504 [(match_operand 1 "register_operand" "f")
10505 (match_operand 2 "nonimmediate_operand" "fm")])
10506 (pc)
10507 (label_ref (match_operand 3 "" ""))))
10508 (clobber (reg:CCFP 18))
10509 (clobber (reg:CCFP 17))
10510 (clobber (match_scratch:HI 4 "=a"))]
10511 "TARGET_80387
10512 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
10513 && GET_MODE (operands[1]) == GET_MODE (operands[2])
10514 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
10515 && SELECT_CC_MODE (GET_CODE (operands[0]),
10516 operands[1], operands[2]) == CCFPmode"
10517 "#")
10518
10519 (define_insn "*fp_jcc_5"
10520 [(set (pc)
10521 (if_then_else (match_operator 0 "comparison_operator"
10522 [(match_operand 1 "register_operand" "f")
10523 (match_operand 2 "register_operand" "f")])
10524 (label_ref (match_operand 3 "" ""))
10525 (pc)))
10526 (clobber (reg:CCFP 18))
10527 (clobber (reg:CCFP 17))
10528 (clobber (match_scratch:HI 4 "=a"))]
10529 "TARGET_80387
10530 && FLOAT_MODE_P (GET_MODE (operands[1]))
10531 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
10532 "#")
10533
10534 (define_insn "*fp_jcc_6"
10535 [(set (pc)
10536 (if_then_else (match_operator 0 "comparison_operator"
10537 [(match_operand 1 "register_operand" "f")
10538 (match_operand 2 "register_operand" "f")])
10539 (pc)
10540 (label_ref (match_operand 3 "" ""))))
10541 (clobber (reg:CCFP 18))
10542 (clobber (reg:CCFP 17))
10543 (clobber (match_scratch:HI 4 "=a"))]
10544 "TARGET_80387
10545 && FLOAT_MODE_P (GET_MODE (operands[1]))
10546 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
10547 "#")
10548
10549 (define_split
10550 [(set (pc)
10551 (if_then_else (match_operator 0 "comparison_operator"
10552 [(match_operand 1 "register_operand" "")
10553 (match_operand 2 "nonimmediate_operand" "")])
10554 (match_operand 3 "" "")
10555 (match_operand 4 "" "")))
10556 (clobber (reg:CCFP 18))
10557 (clobber (reg:CCFP 17))]
10558 "reload_completed"
10559 [(const_int 0)]
10560 "
10561 {
10562 ix86_split_fp_branch (operands[0], operands[1], operands[2],
10563 operands[3], operands[4], NULL_RTX);
10564 DONE;
10565 }")
10566
10567 (define_split
10568 [(set (pc)
10569 (if_then_else (match_operator 0 "comparison_operator"
10570 [(match_operand 1 "register_operand" "")
10571 (match_operand 2 "nonimmediate_operand" "")])
10572 (match_operand 3 "" "")
10573 (match_operand 4 "" "")))
10574 (clobber (reg:CCFP 18))
10575 (clobber (reg:CCFP 17))
10576 (clobber (match_scratch:HI 5 "=a"))]
10577 "reload_completed"
10578 [(set (pc)
10579 (if_then_else (match_dup 6)
10580 (match_dup 3)
10581 (match_dup 4)))]
10582 "
10583 {
10584 ix86_split_fp_branch (operands[0], operands[1], operands[2],
10585 operands[3], operands[4], operands[5]);
10586 DONE;
10587 }")
10588 \f
10589 ;; Unconditional and other jump instructions
10590
10591 (define_insn "jump"
10592 [(set (pc)
10593 (label_ref (match_operand 0 "" "")))]
10594 ""
10595 "jmp\\t%l0"
10596 [(set_attr "type" "ibr")])
10597
10598 (define_insn "indirect_jump"
10599 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))]
10600 ""
10601 "jmp\\t%A0"
10602 [(set_attr "type" "ibr")
10603 (set_attr "length_immediate" "0")])
10604
10605 (define_insn "tablejump"
10606 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))
10607 (use (label_ref (match_operand 1 "" "")))]
10608 "! flag_pic"
10609 "jmp\\t%A0"
10610 [(set_attr "type" "ibr")
10611 (set_attr "length_immediate" "0")])
10612
10613 ;; Implement switch statements when generating PIC code. Switches are
10614 ;; implemented by `tablejump' when not using -fpic.
10615 ;;
10616 ;; Emit code here to do the range checking and make the index zero based.
10617 ;;
10618 ;; Each entry in the "addr_diff_vec" looks like this as the result of the
10619 ;; two rules below:
10620 ;;
10621 ;; .long _GLOBAL_OFFSET_TABLE_+[.-.L2]
10622 ;;
10623 ;; 1. An expression involving an external reference may only use the
10624 ;; addition operator, and only with an assembly-time constant.
10625 ;; The example above satisfies this because ".-.L2" is a constant.
10626 ;;
10627 ;; 2. The symbol _GLOBAL_OFFSET_TABLE_ is magic, and at link time is
10628 ;; given the value of "GOT - .", where GOT is the actual address of
10629 ;; the Global Offset Table. Therefore, the .long above actually
10630 ;; stores the value "( GOT - . ) + [ . - .L2 ]", or "GOT - .L2". The
10631 ;; expression "GOT - .L2" by itself would generate an error from as(1).
10632 ;;
10633 ;; The pattern below emits code that looks like this:
10634 ;;
10635 ;; movl %ebx,reg
10636 ;; subl TABLE@GOTOFF(%ebx,index,4),reg
10637 ;; jmp reg
10638 ;;
10639 ;; The addr_diff_vec contents may be directly referenced with @GOTOFF, since
10640 ;; the addr_diff_vec is known to be part of this module.
10641 ;;
10642 ;; The subl above calculates "GOT - (( GOT - . ) + [ . - .L2 ])", which
10643 ;; evaluates to just ".L2".
10644
10645 (define_expand "casesi"
10646 [(set (match_dup 5)
10647 (match_operand:SI 0 "general_operand" ""))
10648 (parallel [(set (match_dup 6)
10649 (minus:SI (match_dup 5)
10650 (match_operand:SI 1 "general_operand" "")))
10651 (clobber (reg:CC 17))])
10652 (set (reg:CC 17)
10653 (compare:CC (match_dup 6)
10654 (match_operand:SI 2 "general_operand" "")))
10655 (set (pc)
10656 (if_then_else (gtu (reg:CC 17)
10657 (const_int 0))
10658 (label_ref (match_operand 4 "" ""))
10659 (pc)))
10660 (parallel
10661 [(set (match_dup 7)
10662 (minus:SI (match_dup 8)
10663 (mem:SI (plus:SI (plus:SI (mult:SI (match_dup 6) (const_int 4))
10664 (match_dup 8))
10665 (const (unspec [(label_ref (match_operand 3 "" ""))] 7))))))
10666 (clobber (reg:CC 17))])
10667 (parallel [(set (pc) (match_dup 7))
10668 (use (label_ref (match_dup 3)))])]
10669 "flag_pic"
10670 "
10671 {
10672 operands[5] = gen_reg_rtx (SImode);
10673 operands[6] = gen_reg_rtx (SImode);
10674 operands[7] = gen_reg_rtx (SImode);
10675 operands[8] = pic_offset_table_rtx;
10676 current_function_uses_pic_offset_table = 1;
10677 }")
10678
10679 (define_insn "*tablejump_pic"
10680 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))
10681 (use (label_ref (match_operand 1 "" "")))]
10682 ""
10683 "jmp\\t%A0"
10684 [(set_attr "type" "ibr")
10685 (set_attr "length_immediate" "0")])
10686 \f
10687 ;; Loop instruction
10688 ;;
10689 ;; This is all complicated by the fact that since this is a jump insn
10690 ;; we must handle our own reloads.
10691
10692 (define_expand "doloop_end"
10693 [(use (match_operand 0 "" "")) ; loop pseudo
10694 (use (match_operand 1 "" "")) ; iterations; zero if unknown
10695 (use (match_operand 2 "" "")) ; max iterations
10696 (use (match_operand 3 "" "")) ; loop level
10697 (use (match_operand 4 "" ""))] ; label
10698 "TARGET_USE_LOOP && !TARGET_64BIT"
10699 "
10700 {
10701 /* Only use cloop on innermost loops. */
10702 if (INTVAL (operands[3]) > 1)
10703 FAIL;
10704 if (GET_MODE (operands[0]) != SImode)
10705 FAIL;
10706 emit_jump_insn (gen_doloop_end_internal (operands[4], operands[0],
10707 operands[0]));
10708 DONE;
10709 }")
10710
10711 (define_insn "doloop_end_internal"
10712 [(set (pc)
10713 (if_then_else (ne (match_operand:SI 1 "register_operand" "c,?*r,?*r")
10714 (const_int 1))
10715 (label_ref (match_operand 0 "" ""))
10716 (pc)))
10717 (set (match_operand:SI 2 "register_operand" "=1,1,*m*r")
10718 (plus:SI (match_dup 1)
10719 (const_int -1)))
10720 (clobber (match_scratch:SI 3 "=X,X,r"))
10721 (clobber (reg:CC 17))]
10722 "TARGET_USE_LOOP && !TARGET_64BIT"
10723 "*
10724 {
10725 if (which_alternative != 0)
10726 return \"#\";
10727 if (get_attr_length (insn) == 2)
10728 return \"loop\\t%l0\";
10729 else
10730 return \"dec{l}\\t%1\;jne\\t%l0\";
10731 }"
10732 [(set_attr "ppro_uops" "many")
10733 (set (attr "type")
10734 (if_then_else (and (eq_attr "alternative" "0")
10735 (and (ge (minus (match_dup 0) (pc))
10736 (const_int -128))
10737 (lt (minus (match_dup 0) (pc))
10738 (const_int 124))))
10739 (const_string "ibr")
10740 (const_string "multi")))])
10741
10742 (define_split
10743 [(set (pc)
10744 (if_then_else (ne (match_operand:SI 1 "register_operand" "")
10745 (const_int 1))
10746 (match_operand 0 "" "")
10747 (pc)))
10748 (set (match_dup 1)
10749 (plus:SI (match_dup 1)
10750 (const_int -1)))
10751 (clobber (match_scratch:SI 2 ""))
10752 (clobber (reg:CC 17))]
10753 "TARGET_USE_LOOP && !TARGET_64BIT
10754 && reload_completed
10755 && REGNO (operands[1]) != 2"
10756 [(parallel [(set (reg:CCZ 17)
10757 (compare:CCZ (plus:SI (match_dup 1) (const_int -1))
10758 (const_int 0)))
10759 (set (match_dup 1) (plus:SI (match_dup 1) (const_int -1)))])
10760 (set (pc) (if_then_else (ne (reg:CCZ 17) (const_int 0))
10761 (match_dup 0)
10762 (pc)))]
10763 "")
10764
10765 (define_split
10766 [(set (pc)
10767 (if_then_else (ne (match_operand:SI 1 "register_operand" "")
10768 (const_int 1))
10769 (match_operand 0 "" "")
10770 (pc)))
10771 (set (match_operand:SI 2 "nonimmediate_operand" "")
10772 (plus:SI (match_dup 1)
10773 (const_int -1)))
10774 (clobber (match_scratch:SI 3 ""))
10775 (clobber (reg:CC 17))]
10776 "TARGET_USE_LOOP && !TARGET_64BIT
10777 && reload_completed
10778 && (! REG_P (operands[2])
10779 || ! rtx_equal_p (operands[1], operands[2]))"
10780 [(set (match_dup 3) (match_dup 1))
10781 (parallel [(set (reg:CCZ 17)
10782 (compare:CCZ (plus:SI (match_dup 3) (const_int -1))
10783 (const_int 0)))
10784 (set (match_dup 3) (plus:SI (match_dup 3) (const_int -1)))])
10785 (set (match_dup 2) (match_dup 3))
10786 (set (pc) (if_then_else (ne (reg:CCZ 17) (const_int 0))
10787 (match_dup 0)
10788 (pc)))]
10789 "")
10790 \f
10791 ;; Call instructions.
10792
10793 ;; The predicates normally associated with named expanders are not properly
10794 ;; checked for calls. This is a bug in the generic code, but it isn't that
10795 ;; easy to fix. Ignore it for now and be prepared to fix things up.
10796
10797 ;; Call subroutine returning no value.
10798
10799 (define_expand "call_pop"
10800 [(parallel [(call (match_operand:QI 0 "" "")
10801 (match_operand:SI 1 "" ""))
10802 (set (reg:SI 7)
10803 (plus:SI (reg:SI 7)
10804 (match_operand:SI 3 "" "")))])]
10805 "!TARGET_64BIT"
10806 "
10807 {
10808 if (operands[3] == const0_rtx)
10809 {
10810 emit_insn (gen_call (operands[0], operands[1]));
10811 DONE;
10812 }
10813 /* Static functions and indirect calls don't need
10814 current_function_uses_pic_offset_table. */
10815 if (flag_pic
10816 && GET_CODE (XEXP (operands[0], 0)) == SYMBOL_REF
10817 && ! SYMBOL_REF_FLAG (XEXP (operands[0], 0)))
10818 current_function_uses_pic_offset_table = 1;
10819 if (! call_insn_operand (XEXP (operands[0], 0), Pmode))
10820 XEXP (operands[0], 0) = copy_to_mode_reg (Pmode, XEXP (operands[0], 0));
10821 if (TARGET_64BIT)
10822 abort();
10823 }")
10824
10825 (define_insn "*call_pop_0"
10826 [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" ""))
10827 (match_operand:SI 1 "" ""))
10828 (set (reg:SI 7) (plus:SI (reg:SI 7)
10829 (match_operand:SI 2 "immediate_operand" "")))]
10830 "!TARGET_64BIT"
10831 "*
10832 {
10833 if (SIBLING_CALL_P (insn))
10834 return \"jmp\\t%P0\";
10835 else
10836 return \"call\\t%P0\";
10837 }"
10838 [(set_attr "type" "call")])
10839
10840 (define_insn "*call_pop_1"
10841 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
10842 (match_operand:SI 1 "" ""))
10843 (set (reg:SI 7) (plus:SI (reg:SI 7)
10844 (match_operand:SI 2 "immediate_operand" "i")))]
10845 "!TARGET_64BIT"
10846 "*
10847 {
10848 if (constant_call_address_operand (operands[0], Pmode))
10849 {
10850 if (SIBLING_CALL_P (insn))
10851 return \"jmp\\t%P0\";
10852 else
10853 return \"call\\t%P0\";
10854 }
10855 if (SIBLING_CALL_P (insn))
10856 return \"jmp\\t%A0\";
10857 else
10858 return \"call\\t%A0\";
10859 }"
10860 [(set_attr "type" "call")])
10861
10862 (define_expand "call"
10863 [(call (match_operand:QI 0 "" "")
10864 (match_operand:SI 1 "" ""))]
10865 ;; Operand 1 not used on the i386.
10866 ""
10867 "
10868 {
10869 /* Static functions and indirect calls don't need
10870 current_function_uses_pic_offset_table. */
10871 if (flag_pic
10872 && GET_CODE (XEXP (operands[0], 0)) == SYMBOL_REF
10873 && ! SYMBOL_REF_FLAG (XEXP (operands[0], 0)))
10874 current_function_uses_pic_offset_table = 1;
10875 if (! call_insn_operand (XEXP (operands[0], 0), Pmode))
10876 XEXP (operands[0], 0) = copy_to_mode_reg (Pmode, XEXP (operands[0], 0));
10877 }")
10878
10879 (define_insn "*call_0"
10880 [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" ""))
10881 (match_operand:SI 1 "" ""))]
10882 ""
10883 "*
10884 {
10885 if (SIBLING_CALL_P (insn))
10886 return \"jmp\\t%P0\";
10887 else
10888 return \"call\\t%P0\";
10889 }"
10890 [(set_attr "type" "call")])
10891
10892 (define_insn "*call_1"
10893 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
10894 (match_operand:SI 1 "" ""))]
10895 ""
10896 "*
10897 {
10898 if (constant_call_address_operand (operands[0], QImode))
10899 {
10900 if (SIBLING_CALL_P (insn))
10901 return \"jmp\\t%P0\";
10902 else
10903 return \"call\\t%P0\";
10904 }
10905 if (SIBLING_CALL_P (insn))
10906 return \"jmp\\t%A0\";
10907 else
10908 return \"call\\t%A0\";
10909 }"
10910 [(set_attr "type" "call")])
10911
10912 ;; Call subroutine, returning value in operand 0
10913 ;; (which must be a hard register).
10914
10915 (define_expand "call_value_pop"
10916 [(parallel [(set (match_operand 0 "" "")
10917 (call (match_operand:QI 1 "" "")
10918 (match_operand:SI 2 "" "")))
10919 (set (reg:SI 7)
10920 (plus:SI (reg:SI 7)
10921 (match_operand:SI 4 "" "")))])]
10922 "!TARGET_64BIT"
10923 "
10924 {
10925 if (operands[4] == const0_rtx)
10926 {
10927 emit_insn (gen_call_value (operands[0], operands[1], operands[2]));
10928 DONE;
10929 }
10930 /* Static functions and indirect calls don't need
10931 current_function_uses_pic_offset_table. */
10932 if (flag_pic
10933 && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
10934 && ! SYMBOL_REF_FLAG (XEXP (operands[1], 0)))
10935 current_function_uses_pic_offset_table = 1;
10936 if (! call_insn_operand (XEXP (operands[1], 0), Pmode))
10937 XEXP (operands[1], 0) = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
10938 }")
10939
10940 (define_expand "call_value"
10941 [(set (match_operand 0 "" "")
10942 (call (match_operand:QI 1 "" "")
10943 (match_operand:SI 2 "" "")))]
10944 ;; Operand 2 not used on the i386.
10945 ""
10946 "
10947 {
10948 /* Static functions and indirect calls don't need
10949 current_function_uses_pic_offset_table. */
10950 if (flag_pic
10951 && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
10952 && ! SYMBOL_REF_FLAG (XEXP (operands[1], 0)))
10953 current_function_uses_pic_offset_table = 1;
10954 if (! call_insn_operand (XEXP (operands[1], 0), Pmode))
10955 XEXP (operands[1], 0) = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
10956 }")
10957
10958 ;; Call subroutine returning any type.
10959
10960 (define_expand "untyped_call"
10961 [(parallel [(call (match_operand 0 "" "")
10962 (const_int 0))
10963 (match_operand 1 "" "")
10964 (match_operand 2 "" "")])]
10965 ""
10966 "
10967 {
10968 int i;
10969
10970 /* In order to give reg-stack an easier job in validating two
10971 coprocessor registers as containing a possible return value,
10972 simply pretend the untyped call returns a complex long double
10973 value. */
10974
10975 emit_call_insn (TARGET_80387
10976 ? gen_call_value (gen_rtx_REG (XCmode, FIRST_FLOAT_REG),
10977 operands[0], const0_rtx)
10978 : gen_call (operands[0], const0_rtx));
10979
10980 for (i = 0; i < XVECLEN (operands[2], 0); i++)
10981 {
10982 rtx set = XVECEXP (operands[2], 0, i);
10983 emit_move_insn (SET_DEST (set), SET_SRC (set));
10984 }
10985
10986 /* The optimizer does not know that the call sets the function value
10987 registers we stored in the result block. We avoid problems by
10988 claiming that all hard registers are used and clobbered at this
10989 point. */
10990 emit_insn (gen_blockage ());
10991
10992 DONE;
10993 }")
10994 \f
10995 ;; Prologue and epilogue instructions
10996
10997 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
10998 ;; all of memory. This blocks insns from being moved across this point.
10999
11000 (define_insn "blockage"
11001 [(unspec_volatile [(const_int 0)] 0)]
11002 ""
11003 ""
11004 [(set_attr "length" "0")])
11005
11006 ;; Insn emitted into the body of a function to return from a function.
11007 ;; This is only done if the function's epilogue is known to be simple.
11008 ;; See comments for ix86_can_use_return_insn_p in i386.c.
11009
11010 (define_expand "return"
11011 [(return)]
11012 "ix86_can_use_return_insn_p ()"
11013 "
11014 {
11015 if (current_function_pops_args)
11016 {
11017 rtx popc = GEN_INT (current_function_pops_args);
11018 emit_jump_insn (gen_return_pop_internal (popc));
11019 DONE;
11020 }
11021 }")
11022
11023 (define_insn "return_internal"
11024 [(return)]
11025 "reload_completed"
11026 "ret"
11027 [(set_attr "length" "1")
11028 (set_attr "length_immediate" "0")
11029 (set_attr "modrm" "0")])
11030
11031 (define_insn "return_pop_internal"
11032 [(return)
11033 (use (match_operand:SI 0 "const_int_operand" ""))]
11034 "reload_completed"
11035 "ret\\t%0"
11036 [(set_attr "length" "3")
11037 (set_attr "length_immediate" "2")
11038 (set_attr "modrm" "0")])
11039
11040 (define_insn "return_indirect_internal"
11041 [(return)
11042 (use (match_operand:SI 0 "register_operand" "r"))]
11043 "reload_completed"
11044 "jmp\\t%A0"
11045 [(set_attr "type" "ibr")
11046 (set_attr "length_immediate" "0")])
11047
11048 (define_insn "nop"
11049 [(const_int 0)]
11050 ""
11051 "nop"
11052 [(set_attr "length" "1")
11053 (set_attr "length_immediate" "0")
11054 (set_attr "modrm" "0")
11055 (set_attr "ppro_uops" "one")])
11056
11057 (define_expand "prologue"
11058 [(const_int 1)]
11059 ""
11060 "ix86_expand_prologue (); DONE;")
11061
11062 (define_insn "prologue_set_got"
11063 [(set (match_operand:SI 0 "register_operand" "=r")
11064 (unspec_volatile:SI
11065 [(plus:SI (match_dup 0)
11066 (plus:SI (match_operand:SI 1 "symbolic_operand" "")
11067 (minus:SI (pc) (match_operand 2 "" ""))))] 1))
11068 (clobber (reg:CC 17))]
11069 ""
11070 "*
11071 {
11072 if (GET_CODE (operands[2]) == LABEL_REF)
11073 operands[2] = XEXP (operands[2], 0);
11074 if (TARGET_DEEP_BRANCH_PREDICTION)
11075 return \"add{l}\\t{%1, %0|%0, %1}\";
11076 else
11077 return \"add{l}\\t{%1+[.-%X2], %0|%0, %a1+(.-%X2)}\";
11078 }"
11079 [(set_attr "type" "alu")
11080 ; Since this insn may have two constant operands, we must set the
11081 ; length manually.
11082 (set_attr "length_immediate" "4")
11083 (set_attr "mode" "SI")])
11084
11085 (define_insn "prologue_get_pc"
11086 [(set (match_operand:SI 0 "register_operand" "=r")
11087 (unspec_volatile:SI [(plus:SI (pc) (match_operand 1 "" ""))] 2))]
11088 "!TARGET_64BIT"
11089 "*
11090 {
11091 if (GET_CODE (operands[1]) == LABEL_REF)
11092 operands[1] = XEXP (operands[1], 0);
11093 output_asm_insn (\"call\\t%X1\", operands);
11094 if (! TARGET_DEEP_BRANCH_PREDICTION)
11095 {
11096 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"L\",
11097 CODE_LABEL_NUMBER (operands[1]));
11098 }
11099 RET;
11100 }"
11101 [(set_attr "type" "multi")])
11102
11103 (define_expand "epilogue"
11104 [(const_int 1)]
11105 ""
11106 "ix86_expand_epilogue (1); DONE;")
11107
11108 (define_expand "sibcall_epilogue"
11109 [(const_int 1)]
11110 ""
11111 "ix86_expand_epilogue (0); DONE;")
11112
11113 (define_insn "leave"
11114 [(set (reg:SI 7) (reg:SI 6))
11115 (set (reg:SI 6) (mem:SI (pre_dec:SI (reg:SI 7))))]
11116 "!TARGET_64BIT"
11117 "leave"
11118 [(set_attr "length_immediate" "0")
11119 (set_attr "length" "1")
11120 (set_attr "modrm" "0")
11121 (set_attr "modrm" "0")
11122 (set_attr "athlon_decode" "vector")
11123 (set_attr "ppro_uops" "few")])
11124 \f
11125 (define_expand "ffssi2"
11126 [(set (match_operand:SI 0 "nonimmediate_operand" "")
11127 (ffs:SI (match_operand:SI 1 "general_operand" "")))]
11128 ""
11129 "
11130 {
11131 rtx out = gen_reg_rtx (SImode), tmp = gen_reg_rtx (SImode);
11132 rtx in = operands[1];
11133
11134 if (TARGET_CMOVE)
11135 {
11136 emit_move_insn (tmp, constm1_rtx);
11137 emit_insn (gen_ffssi_1 (out, in));
11138 emit_insn (gen_rtx_SET (VOIDmode, out,
11139 gen_rtx_IF_THEN_ELSE (SImode,
11140 gen_rtx_EQ (VOIDmode, gen_rtx_REG (CCZmode, FLAGS_REG),
11141 const0_rtx),
11142 tmp,
11143 out)));
11144 emit_insn (gen_addsi3 (out, out, const1_rtx));
11145 emit_move_insn (operands[0], out);
11146 }
11147
11148 /* Pentium bsf instruction is extremly slow. The following code is
11149 recommended by the Intel Optimizing Manual as a reasonable replacement:
11150 TEST EAX,EAX
11151 JZ SHORT BS2
11152 XOR ECX,ECX
11153 MOV DWORD PTR [TEMP+4],ECX
11154 SUB ECX,EAX
11155 AND EAX,ECX
11156 MOV DWORD PTR [TEMP],EAX
11157 FILD QWORD PTR [TEMP]
11158 FSTP QWORD PTR [TEMP]
11159 WAIT ; WAIT only needed for compatibility with
11160 ; earlier processors
11161 MOV ECX, DWORD PTR [TEMP+4]
11162 SHR ECX,20
11163 SUB ECX,3FFH
11164 TEST EAX,EAX ; clear zero flag
11165 BS2:
11166 Following piece of code expand ffs to similar beast.
11167 */
11168
11169 else if (TARGET_PENTIUM && !optimize_size && TARGET_80387)
11170 {
11171 rtx label = gen_label_rtx ();
11172 rtx lo, hi;
11173 rtx mem = assign_386_stack_local (DImode, 0);
11174 rtx fptmp = gen_reg_rtx (DFmode);
11175 split_di (&mem, 1, &lo, &hi);
11176
11177 emit_move_insn (out, const0_rtx);
11178
11179 emit_cmp_and_jump_insns (in, const0_rtx, EQ, 0, SImode, 1, 0, label);
11180
11181 emit_move_insn (hi, out);
11182 emit_insn (gen_subsi3 (out, out, in));
11183 emit_insn (gen_andsi3 (out, out, in));
11184 emit_move_insn (lo, out);
11185 emit_insn (gen_floatdidf2 (fptmp,mem));
11186 emit_move_insn (gen_rtx_MEM (DFmode, XEXP (mem, 0)), fptmp);
11187 emit_move_insn (out, hi);
11188 emit_insn (gen_lshrsi3 (out, out, GEN_INT (20)));
11189 emit_insn (gen_subsi3 (out, out, GEN_INT (0x3ff - 1)));
11190
11191 emit_label (label);
11192 LABEL_NUSES (label) = 1;
11193
11194 emit_move_insn (operands[0], out);
11195 }
11196 else
11197 {
11198 emit_move_insn (tmp, const0_rtx);
11199 emit_insn (gen_ffssi_1 (out, in));
11200 emit_insn (gen_rtx_SET (VOIDmode,
11201 gen_rtx_STRICT_LOW_PART (VOIDmode, gen_lowpart (QImode, tmp)),
11202 gen_rtx_EQ (QImode, gen_rtx_REG (CCZmode, FLAGS_REG),
11203 const0_rtx)));
11204 emit_insn (gen_negsi2 (tmp, tmp));
11205 emit_insn (gen_iorsi3 (out, out, tmp));
11206 emit_insn (gen_addsi3 (out, out, const1_rtx));
11207 emit_move_insn (operands[0], out);
11208 }
11209 DONE;
11210 }")
11211
11212 (define_insn "ffssi_1"
11213 [(set (reg:CCZ 17)
11214 (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "rm")
11215 (const_int 0)))
11216 (set (match_operand:SI 0 "register_operand" "=r")
11217 (unspec:SI [(match_dup 1)] 5))]
11218 ""
11219 "bsf{l}\\t{%1, %0|%0, %1}"
11220 [(set_attr "prefix_0f" "1")
11221 (set_attr "ppro_uops" "few")])
11222
11223 ;; ffshi2 is not useful -- 4 word prefix ops are needed, which is larger
11224 ;; and slower than the two-byte movzx insn needed to do the work in SImode.
11225 \f
11226 ;; These patterns match the binary 387 instructions for addM3, subM3,
11227 ;; mulM3 and divM3. There are three patterns for each of DFmode and
11228 ;; SFmode. The first is the normal insn, the second the same insn but
11229 ;; with one operand a conversion, and the third the same insn but with
11230 ;; the other operand a conversion. The conversion may be SFmode or
11231 ;; SImode if the target mode DFmode, but only SImode if the target mode
11232 ;; is SFmode.
11233
11234 ;; Gcc is slightly more smart about handling normal two address instructions
11235 ;; so use special patterns for add and mull.
11236 (define_insn "*fop_sf_comm"
11237 [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
11238 (match_operator:SF 3 "binary_fp_operator"
11239 [(match_operand:SF 1 "register_operand" "%0,0")
11240 (match_operand:SF 2 "nonimmediate_operand" "fm#x,xm#f")]))]
11241 "TARGET_80387 && (!TARGET_SSE || TARGET_MIX_SSE_I387)
11242 && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'"
11243 "* return output_387_binary_op (insn, operands);"
11244 [(set (attr "type")
11245 (if_then_else (eq_attr "alternative" "1")
11246 (const_string "sse")
11247 (if_then_else (match_operand:SF 3 "mult_operator" "")
11248 (const_string "fmul")
11249 (const_string "fop"))))
11250 (set_attr "mode" "SF")])
11251
11252 (define_insn "*fop_sf_comm_sse"
11253 [(set (match_operand:SF 0 "register_operand" "=x")
11254 (match_operator:SF 3 "binary_fp_operator"
11255 [(match_operand:SF 1 "register_operand" "%0")
11256 (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
11257 "TARGET_SSE && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'"
11258 "* return output_387_binary_op (insn, operands);"
11259 [(set_attr "type" "sse")
11260 (set_attr "mode" "SF")])
11261
11262 (define_insn "*fop_df_comm"
11263 [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
11264 (match_operator:DF 3 "binary_fp_operator"
11265 [(match_operand:DF 1 "register_operand" "%0,0")
11266 (match_operand:DF 2 "nonimmediate_operand" "fm#Y,Ym#f")]))]
11267 "TARGET_80387 && (!TARGET_SSE2 || TARGET_MIX_SSE_I387)
11268 && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'"
11269 "* return output_387_binary_op (insn, operands);"
11270 [(set (attr "type")
11271 (if_then_else (eq_attr "alternative" "1")
11272 (const_string "sse")
11273 (if_then_else (match_operand:SF 3 "mult_operator" "")
11274 (const_string "fmul")
11275 (const_string "fop"))))
11276 (set_attr "mode" "DF")])
11277
11278 (define_insn "*fop_df_comm_sse"
11279 [(set (match_operand:DF 0 "register_operand" "=Y")
11280 (match_operator:DF 3 "binary_fp_operator"
11281 [(match_operand:DF 1 "register_operand" "%0")
11282 (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
11283 "TARGET_SSE2
11284 && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'"
11285 "* return output_387_binary_op (insn, operands);"
11286 [(set_attr "type" "sse")
11287 (set_attr "mode" "DF")])
11288
11289 (define_insn "*fop_xf_comm"
11290 [(set (match_operand:XF 0 "register_operand" "=f")
11291 (match_operator:XF 3 "binary_fp_operator"
11292 [(match_operand:XF 1 "register_operand" "%0")
11293 (match_operand:XF 2 "register_operand" "f")]))]
11294 "TARGET_80387 && !TARGET_64BIT
11295 && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'"
11296 "* return output_387_binary_op (insn, operands);"
11297 [(set (attr "type")
11298 (if_then_else (match_operand:XF 3 "mult_operator" "")
11299 (const_string "fmul")
11300 (const_string "fop")))
11301 (set_attr "mode" "XF")])
11302
11303 (define_insn "*fop_tf_comm"
11304 [(set (match_operand:TF 0 "register_operand" "=f")
11305 (match_operator:TF 3 "binary_fp_operator"
11306 [(match_operand:TF 1 "register_operand" "%0")
11307 (match_operand:TF 2 "register_operand" "f")]))]
11308 "TARGET_80387 && GET_RTX_CLASS (GET_CODE (operands[3])) == 'c'"
11309 "* return output_387_binary_op (insn, operands);"
11310 [(set (attr "type")
11311 (if_then_else (match_operand:TF 3 "mult_operator" "")
11312 (const_string "fmul")
11313 (const_string "fop")))
11314 (set_attr "mode" "XF")])
11315
11316 (define_insn "*fop_sf_1"
11317 [(set (match_operand:SF 0 "register_operand" "=f,f,x")
11318 (match_operator:SF 3 "binary_fp_operator"
11319 [(match_operand:SF 1 "nonimmediate_operand" "0,fm,0")
11320 (match_operand:SF 2 "nonimmediate_operand" "fm,0,xm#f")]))]
11321 "TARGET_80387 && (!TARGET_SSE || TARGET_MIX_SSE_I387)
11322 && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'
11323 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
11324 "* return output_387_binary_op (insn, operands);"
11325 [(set (attr "type")
11326 (cond [(eq_attr "alternative" "2")
11327 (const_string "sse")
11328 (match_operand:SF 3 "mult_operator" "")
11329 (const_string "fmul")
11330 (match_operand:SF 3 "div_operator" "")
11331 (const_string "fdiv")
11332 ]
11333 (const_string "fop")))
11334 (set_attr "mode" "SF")])
11335
11336 (define_insn "*fop_sf_1_sse"
11337 [(set (match_operand:SF 0 "register_operand" "=x")
11338 (match_operator:SF 3 "binary_fp_operator"
11339 [(match_operand:SF 1 "register_operand" "0")
11340 (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
11341 "TARGET_SSE
11342 && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'"
11343 "* return output_387_binary_op (insn, operands);"
11344 [(set_attr "type" "sse")
11345 (set_attr "mode" "SF")])
11346
11347 ;; ??? Add SSE splitters for these!
11348 (define_insn "*fop_sf_2"
11349 [(set (match_operand:SF 0 "register_operand" "=f,f")
11350 (match_operator:SF 3 "binary_fp_operator"
11351 [(float:SF (match_operand:SI 1 "nonimmediate_operand" "m,?r"))
11352 (match_operand:SF 2 "register_operand" "0,0")]))]
11353 "TARGET_80387 && TARGET_USE_FIOP && !TARGET_SSE"
11354 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
11355 [(set (attr "type")
11356 (cond [(match_operand:SF 3 "mult_operator" "")
11357 (const_string "fmul")
11358 (match_operand:SF 3 "div_operator" "")
11359 (const_string "fdiv")
11360 ]
11361 (const_string "fop")))
11362 (set_attr "fp_int_src" "true")
11363 (set_attr "ppro_uops" "many")
11364 (set_attr "mode" "SI")])
11365
11366 (define_insn "*fop_sf_3"
11367 [(set (match_operand:SF 0 "register_operand" "=f,f")
11368 (match_operator:SF 3 "binary_fp_operator"
11369 [(match_operand:SF 1 "register_operand" "0,0")
11370 (float:SF (match_operand:SI 2 "nonimmediate_operand" "m,?r"))]))]
11371 "TARGET_80387 && TARGET_USE_FIOP && !TARGET_SSE"
11372 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
11373 [(set (attr "type")
11374 (cond [(match_operand:SF 3 "mult_operator" "")
11375 (const_string "fmul")
11376 (match_operand:SF 3 "div_operator" "")
11377 (const_string "fdiv")
11378 ]
11379 (const_string "fop")))
11380 (set_attr "fp_int_src" "true")
11381 (set_attr "ppro_uops" "many")
11382 (set_attr "mode" "SI")])
11383
11384 (define_insn "*fop_df_1"
11385 [(set (match_operand:DF 0 "register_operand" "=f#Y,f#Y,Y#f")
11386 (match_operator:DF 3 "binary_fp_operator"
11387 [(match_operand:DF 1 "nonimmediate_operand" "0,fm,0")
11388 (match_operand:DF 2 "nonimmediate_operand" "fm,0,Ym#f")]))]
11389 "TARGET_80387 && (!TARGET_SSE2 || TARGET_MIX_SSE_I387)
11390 && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'
11391 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
11392 "* return output_387_binary_op (insn, operands);"
11393 [(set (attr "type")
11394 (cond [(eq_attr "alternative" "2")
11395 (const_string "sse")
11396 (match_operand:DF 3 "mult_operator" "")
11397 (const_string "fmul")
11398 (match_operand:DF 3 "div_operator" "")
11399 (const_string "fdiv")
11400 ]
11401 (const_string "fop")))
11402 (set_attr "mode" "DF")])
11403
11404 (define_insn "*fop_df_1_sse"
11405 [(set (match_operand:DF 0 "register_operand" "=Y")
11406 (match_operator:DF 3 "binary_fp_operator"
11407 [(match_operand:DF 1 "register_operand" "0")
11408 (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
11409 "TARGET_SSE
11410 && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'"
11411 "* return output_387_binary_op (insn, operands);"
11412 [(set_attr "type" "sse")])
11413
11414 ;; ??? Add SSE splitters for these!
11415 (define_insn "*fop_df_2"
11416 [(set (match_operand:DF 0 "register_operand" "=f,f")
11417 (match_operator:DF 3 "binary_fp_operator"
11418 [(float:DF (match_operand:SI 1 "nonimmediate_operand" "m,?r"))
11419 (match_operand:DF 2 "register_operand" "0,0")]))]
11420 "TARGET_80387 && TARGET_USE_FIOP && !TARGET_SSE2"
11421 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
11422 [(set (attr "type")
11423 (cond [(match_operand:DF 3 "mult_operator" "")
11424 (const_string "fmul")
11425 (match_operand:DF 3 "div_operator" "")
11426 (const_string "fdiv")
11427 ]
11428 (const_string "fop")))
11429 (set_attr "fp_int_src" "true")
11430 (set_attr "ppro_uops" "many")
11431 (set_attr "mode" "SI")])
11432
11433 (define_insn "*fop_df_3"
11434 [(set (match_operand:DF 0 "register_operand" "=f,f")
11435 (match_operator:DF 3 "binary_fp_operator"
11436 [(match_operand:DF 1 "register_operand" "0,0")
11437 (float:DF (match_operand:SI 2 "nonimmediate_operand" "m,?r"))]))]
11438 "TARGET_80387 && TARGET_USE_FIOP && !TARGET_SSE2"
11439 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
11440 [(set (attr "type")
11441 (cond [(match_operand:DF 3 "mult_operator" "")
11442 (const_string "fmul")
11443 (match_operand:DF 3 "div_operator" "")
11444 (const_string "fdiv")
11445 ]
11446 (const_string "fop")))
11447 (set_attr "fp_int_src" "true")
11448 (set_attr "ppro_uops" "many")
11449 (set_attr "mode" "SI")])
11450
11451 (define_insn "*fop_df_4"
11452 [(set (match_operand:DF 0 "register_operand" "=f,f")
11453 (match_operator:DF 3 "binary_fp_operator"
11454 [(float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
11455 (match_operand:DF 2 "register_operand" "0,f")]))]
11456 "TARGET_80387
11457 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
11458 "* return output_387_binary_op (insn, operands);"
11459 [(set (attr "type")
11460 (cond [(match_operand:DF 3 "mult_operator" "")
11461 (const_string "fmul")
11462 (match_operand:DF 3 "div_operator" "")
11463 (const_string "fdiv")
11464 ]
11465 (const_string "fop")))
11466 (set_attr "mode" "SF")])
11467
11468 (define_insn "*fop_df_5"
11469 [(set (match_operand:DF 0 "register_operand" "=f,f")
11470 (match_operator:DF 3 "binary_fp_operator"
11471 [(match_operand:DF 1 "register_operand" "0,f")
11472 (float_extend:DF
11473 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
11474 "TARGET_80387 && !TARGET_SSE2"
11475 "* return output_387_binary_op (insn, operands);"
11476 [(set (attr "type")
11477 (cond [(match_operand:DF 3 "mult_operator" "")
11478 (const_string "fmul")
11479 (match_operand:DF 3 "div_operator" "")
11480 (const_string "fdiv")
11481 ]
11482 (const_string "fop")))
11483 (set_attr "mode" "SF")])
11484
11485 (define_insn "*fop_xf_1"
11486 [(set (match_operand:XF 0 "register_operand" "=f,f")
11487 (match_operator:XF 3 "binary_fp_operator"
11488 [(match_operand:XF 1 "register_operand" "0,f")
11489 (match_operand:XF 2 "register_operand" "f,0")]))]
11490 "TARGET_80387 && !TARGET_64BIT
11491 && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'"
11492 "* return output_387_binary_op (insn, operands);"
11493 [(set (attr "type")
11494 (cond [(match_operand:XF 3 "mult_operator" "")
11495 (const_string "fmul")
11496 (match_operand:XF 3 "div_operator" "")
11497 (const_string "fdiv")
11498 ]
11499 (const_string "fop")))
11500 (set_attr "mode" "XF")])
11501
11502 (define_insn "*fop_tf_1"
11503 [(set (match_operand:TF 0 "register_operand" "=f,f")
11504 (match_operator:TF 3 "binary_fp_operator"
11505 [(match_operand:TF 1 "register_operand" "0,f")
11506 (match_operand:TF 2 "register_operand" "f,0")]))]
11507 "TARGET_80387
11508 && GET_RTX_CLASS (GET_CODE (operands[3])) != 'c'"
11509 "* return output_387_binary_op (insn, operands);"
11510 [(set (attr "type")
11511 (cond [(match_operand:TF 3 "mult_operator" "")
11512 (const_string "fmul")
11513 (match_operand:TF 3 "div_operator" "")
11514 (const_string "fdiv")
11515 ]
11516 (const_string "fop")))
11517 (set_attr "mode" "XF")])
11518
11519 (define_insn "*fop_xf_2"
11520 [(set (match_operand:XF 0 "register_operand" "=f,f")
11521 (match_operator:XF 3 "binary_fp_operator"
11522 [(float:XF (match_operand:SI 1 "nonimmediate_operand" "m,?r"))
11523 (match_operand:XF 2 "register_operand" "0,0")]))]
11524 "TARGET_80387 && !TARGET_64BIT && TARGET_USE_FIOP"
11525 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
11526 [(set (attr "type")
11527 (cond [(match_operand:XF 3 "mult_operator" "")
11528 (const_string "fmul")
11529 (match_operand:XF 3 "div_operator" "")
11530 (const_string "fdiv")
11531 ]
11532 (const_string "fop")))
11533 (set_attr "fp_int_src" "true")
11534 (set_attr "mode" "SI")
11535 (set_attr "ppro_uops" "many")])
11536
11537 (define_insn "*fop_tf_2"
11538 [(set (match_operand:TF 0 "register_operand" "=f,f")
11539 (match_operator:TF 3 "binary_fp_operator"
11540 [(float:TF (match_operand:SI 1 "nonimmediate_operand" "m,?r"))
11541 (match_operand:TF 2 "register_operand" "0,0")]))]
11542 "TARGET_80387 && TARGET_USE_FIOP"
11543 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
11544 [(set (attr "type")
11545 (cond [(match_operand:TF 3 "mult_operator" "")
11546 (const_string "fmul")
11547 (match_operand:TF 3 "div_operator" "")
11548 (const_string "fdiv")
11549 ]
11550 (const_string "fop")))
11551 (set_attr "fp_int_src" "true")
11552 (set_attr "mode" "SI")
11553 (set_attr "ppro_uops" "many")])
11554
11555 (define_insn "*fop_xf_3"
11556 [(set (match_operand:XF 0 "register_operand" "=f,f")
11557 (match_operator:XF 3 "binary_fp_operator"
11558 [(match_operand:XF 1 "register_operand" "0,0")
11559 (float:XF (match_operand:SI 2 "nonimmediate_operand" "m,?r"))]))]
11560 "TARGET_80387 && !TARGET_64BIT && TARGET_USE_FIOP"
11561 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
11562 [(set (attr "type")
11563 (cond [(match_operand:XF 3 "mult_operator" "")
11564 (const_string "fmul")
11565 (match_operand:XF 3 "div_operator" "")
11566 (const_string "fdiv")
11567 ]
11568 (const_string "fop")))
11569 (set_attr "fp_int_src" "true")
11570 (set_attr "mode" "SI")
11571 (set_attr "ppro_uops" "many")])
11572
11573 (define_insn "*fop_tf_3"
11574 [(set (match_operand:TF 0 "register_operand" "=f,f")
11575 (match_operator:TF 3 "binary_fp_operator"
11576 [(match_operand:TF 1 "register_operand" "0,0")
11577 (float:TF (match_operand:SI 2 "nonimmediate_operand" "m,?r"))]))]
11578 "TARGET_80387 && TARGET_USE_FIOP"
11579 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
11580 [(set (attr "type")
11581 (cond [(match_operand:TF 3 "mult_operator" "")
11582 (const_string "fmul")
11583 (match_operand:TF 3 "div_operator" "")
11584 (const_string "fdiv")
11585 ]
11586 (const_string "fop")))
11587 (set_attr "fp_int_src" "true")
11588 (set_attr "mode" "SI")
11589 (set_attr "ppro_uops" "many")])
11590
11591 (define_insn "*fop_xf_4"
11592 [(set (match_operand:XF 0 "register_operand" "=f,f")
11593 (match_operator:XF 3 "binary_fp_operator"
11594 [(float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
11595 (match_operand:XF 2 "register_operand" "0,f")]))]
11596 "TARGET_80387 && !TARGET_64BIT"
11597 "* return output_387_binary_op (insn, operands);"
11598 [(set (attr "type")
11599 (cond [(match_operand:XF 3 "mult_operator" "")
11600 (const_string "fmul")
11601 (match_operand:XF 3 "div_operator" "")
11602 (const_string "fdiv")
11603 ]
11604 (const_string "fop")))
11605 (set_attr "mode" "SF")])
11606
11607 (define_insn "*fop_tf_4"
11608 [(set (match_operand:TF 0 "register_operand" "=f,f")
11609 (match_operator:TF 3 "binary_fp_operator"
11610 [(float_extend:TF (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
11611 (match_operand:TF 2 "register_operand" "0,f")]))]
11612 "TARGET_80387"
11613 "* return output_387_binary_op (insn, operands);"
11614 [(set (attr "type")
11615 (cond [(match_operand:TF 3 "mult_operator" "")
11616 (const_string "fmul")
11617 (match_operand:TF 3 "div_operator" "")
11618 (const_string "fdiv")
11619 ]
11620 (const_string "fop")))
11621 (set_attr "mode" "SF")])
11622
11623 (define_insn "*fop_xf_5"
11624 [(set (match_operand:XF 0 "register_operand" "=f,f")
11625 (match_operator:XF 3 "binary_fp_operator"
11626 [(match_operand:XF 1 "register_operand" "0,f")
11627 (float_extend:XF
11628 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
11629 "TARGET_80387 && !TARGET_64BIT"
11630 "* return output_387_binary_op (insn, operands);"
11631 [(set (attr "type")
11632 (cond [(match_operand:XF 3 "mult_operator" "")
11633 (const_string "fmul")
11634 (match_operand:XF 3 "div_operator" "")
11635 (const_string "fdiv")
11636 ]
11637 (const_string "fop")))
11638 (set_attr "mode" "SF")])
11639
11640 (define_insn "*fop_tf_5"
11641 [(set (match_operand:TF 0 "register_operand" "=f,f")
11642 (match_operator:TF 3 "binary_fp_operator"
11643 [(match_operand:TF 1 "register_operand" "0,f")
11644 (float_extend:TF
11645 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
11646 "TARGET_80387"
11647 "* return output_387_binary_op (insn, operands);"
11648 [(set (attr "type")
11649 (cond [(match_operand:TF 3 "mult_operator" "")
11650 (const_string "fmul")
11651 (match_operand:TF 3 "div_operator" "")
11652 (const_string "fdiv")
11653 ]
11654 (const_string "fop")))
11655 (set_attr "mode" "SF")])
11656
11657 (define_insn "*fop_xf_6"
11658 [(set (match_operand:XF 0 "register_operand" "=f,f")
11659 (match_operator:XF 3 "binary_fp_operator"
11660 [(float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "fm,0"))
11661 (match_operand:XF 2 "register_operand" "0,f")]))]
11662 "TARGET_80387 && !TARGET_64BIT"
11663 "* return output_387_binary_op (insn, operands);"
11664 [(set (attr "type")
11665 (cond [(match_operand:XF 3 "mult_operator" "")
11666 (const_string "fmul")
11667 (match_operand:XF 3 "div_operator" "")
11668 (const_string "fdiv")
11669 ]
11670 (const_string "fop")))
11671 (set_attr "mode" "DF")])
11672
11673 (define_insn "*fop_tf_6"
11674 [(set (match_operand:TF 0 "register_operand" "=f,f")
11675 (match_operator:TF 3 "binary_fp_operator"
11676 [(float_extend:TF (match_operand:DF 1 "nonimmediate_operand" "fm,0"))
11677 (match_operand:TF 2 "register_operand" "0,f")]))]
11678 "TARGET_80387"
11679 "* return output_387_binary_op (insn, operands);"
11680 [(set (attr "type")
11681 (cond [(match_operand:TF 3 "mult_operator" "")
11682 (const_string "fmul")
11683 (match_operand:TF 3 "div_operator" "")
11684 (const_string "fdiv")
11685 ]
11686 (const_string "fop")))
11687 (set_attr "mode" "DF")])
11688
11689 (define_insn "*fop_xf_7"
11690 [(set (match_operand:XF 0 "register_operand" "=f,f")
11691 (match_operator:XF 3 "binary_fp_operator"
11692 [(match_operand:XF 1 "register_operand" "0,f")
11693 (float_extend:XF
11694 (match_operand:DF 2 "nonimmediate_operand" "fm,0"))]))]
11695 "TARGET_80387 && !TARGET_64BIT"
11696 "* return output_387_binary_op (insn, operands);"
11697 [(set (attr "type")
11698 (cond [(match_operand:XF 3 "mult_operator" "")
11699 (const_string "fmul")
11700 (match_operand:XF 3 "div_operator" "")
11701 (const_string "fdiv")
11702 ]
11703 (const_string "fop")))
11704 (set_attr "mode" "DF")])
11705
11706 (define_insn "*fop_tf_7"
11707 [(set (match_operand:TF 0 "register_operand" "=f,f")
11708 (match_operator:TF 3 "binary_fp_operator"
11709 [(match_operand:TF 1 "register_operand" "0,f")
11710 (float_extend:TF
11711 (match_operand:DF 2 "nonimmediate_operand" "fm,0"))]))]
11712 "TARGET_80387"
11713 "* return output_387_binary_op (insn, operands);"
11714 [(set (attr "type")
11715 (cond [(match_operand:TF 3 "mult_operator" "")
11716 (const_string "fmul")
11717 (match_operand:TF 3 "div_operator" "")
11718 (const_string "fdiv")
11719 ]
11720 (const_string "fop")))
11721 (set_attr "mode" "DF")])
11722
11723 (define_split
11724 [(set (match_operand 0 "register_operand" "")
11725 (match_operator 3 "binary_fp_operator"
11726 [(float (match_operand:SI 1 "register_operand" ""))
11727 (match_operand 2 "register_operand" "")]))]
11728 "TARGET_80387 && reload_completed
11729 && FLOAT_MODE_P (GET_MODE (operands[0]))"
11730 [(const_int 0)]
11731 "
11732 {
11733 operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
11734 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
11735 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
11736 gen_rtx_fmt_ee (GET_CODE (operands[3]),
11737 GET_MODE (operands[3]),
11738 operands[4],
11739 operands[2])));
11740 ix86_free_from_memory (GET_MODE (operands[1]));
11741 DONE;
11742 }")
11743
11744 (define_split
11745 [(set (match_operand 0 "register_operand" "")
11746 (match_operator 3 "binary_fp_operator"
11747 [(match_operand 1 "register_operand" "")
11748 (float (match_operand:SI 2 "register_operand" ""))]))]
11749 "TARGET_80387 && reload_completed
11750 && FLOAT_MODE_P (GET_MODE (operands[0]))"
11751 [(const_int 0)]
11752 "
11753 {
11754 operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
11755 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
11756 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
11757 gen_rtx_fmt_ee (GET_CODE (operands[3]),
11758 GET_MODE (operands[3]),
11759 operands[1],
11760 operands[4])));
11761 ix86_free_from_memory (GET_MODE (operands[2]));
11762 DONE;
11763 }")
11764 \f
11765 ;; FPU special functions.
11766
11767 (define_expand "sqrtsf2"
11768 [(set (match_operand:SF 0 "register_operand" "")
11769 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
11770 "(! TARGET_NO_FANCY_MATH_387 && TARGET_80387) || TARGET_SSE"
11771 "
11772 {
11773 if (!TARGET_SSE)
11774 operands[1] = force_reg (SFmode, operands[1]);
11775 }")
11776
11777 (define_insn "sqrtsf2_1"
11778 [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
11779 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "0#x,xm#f")))]
11780 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11781 && (TARGET_SSE && TARGET_MIX_SSE_I387)"
11782 "@
11783 fsqrt
11784 sqrtss\\t{%1, %0|%0, %1}"
11785 [(set_attr "type" "fpspc,sse")
11786 (set_attr "mode" "SF,SF")
11787 (set_attr "athlon_decode" "direct,*")])
11788
11789 (define_insn "sqrtsf2_1_sse_only"
11790 [(set (match_operand:SF 0 "register_operand" "=x")
11791 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
11792 "TARGET_SSE && (!TARGET_80387 || !TARGET_MIX_SSE_I387)"
11793 "sqrtss\\t{%1, %0|%0, %1}"
11794 [(set_attr "type" "sse")
11795 (set_attr "mode" "SF")
11796 (set_attr "athlon_decode" "*")])
11797
11798 (define_insn "sqrtsf2_i387"
11799 [(set (match_operand:SF 0 "register_operand" "=f")
11800 (sqrt:SF (match_operand:SF 1 "register_operand" "0")))]
11801 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11802 && (!TARGET_SSE && !TARGET_MIX_SSE_I387)"
11803 "fsqrt"
11804 [(set_attr "type" "fpspc")
11805 (set_attr "mode" "SF")
11806 (set_attr "athlon_decode" "direct")])
11807
11808 (define_expand "sqrtdf2"
11809 [(set (match_operand:DF 0 "register_operand" "")
11810 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
11811 "(! TARGET_NO_FANCY_MATH_387 && TARGET_80387) || TARGET_SSE2"
11812 "
11813 {
11814 if (!TARGET_SSE2)
11815 operands[1] = force_reg (SFmode, operands[1]);
11816 }")
11817
11818 (define_insn "sqrtdf2_1"
11819 [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
11820 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "0#Y,Ym#f")))]
11821 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11822 && (TARGET_SSE2 && TARGET_MIX_SSE_I387)"
11823 "@
11824 fsqrt
11825 sqrtsd\\t{%1, %0|%0, %1}"
11826 [(set_attr "type" "fpspc,sse")
11827 (set_attr "mode" "DF,DF")
11828 (set_attr "athlon_decode" "direct,*")])
11829
11830 (define_insn "sqrtdf2_1_sse_only"
11831 [(set (match_operand:DF 0 "register_operand" "=Y")
11832 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
11833 "TARGET_SSE2 && (!TARGET_80387 || !TARGET_MIX_SSE_I387)"
11834 "sqrtsd\\t{%1, %0|%0, %1}"
11835 [(set_attr "type" "sse")
11836 (set_attr "mode" "DF")
11837 (set_attr "athlon_decode" "*")])
11838
11839 (define_insn "sqrtdf2_i387"
11840 [(set (match_operand:DF 0 "register_operand" "=f")
11841 (sqrt:DF (match_operand:DF 1 "register_operand" "0")))]
11842 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11843 && (!TARGET_SSE2 && !TARGET_MIX_SSE_I387)"
11844 "fsqrt"
11845 [(set_attr "type" "fpspc")
11846 (set_attr "mode" "DF")
11847 (set_attr "athlon_decode" "direct")])
11848
11849 (define_insn "*sqrtextendsfdf2"
11850 [(set (match_operand:DF 0 "register_operand" "=f")
11851 (sqrt:DF (float_extend:DF
11852 (match_operand:SF 1 "register_operand" "0"))))]
11853 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 && !TARGET_SSE2"
11854 "fsqrt"
11855 [(set_attr "type" "fpspc")
11856 (set_attr "mode" "DF")
11857 (set_attr "athlon_decode" "direct")])
11858
11859 (define_insn "sqrtxf2"
11860 [(set (match_operand:XF 0 "register_operand" "=f")
11861 (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
11862 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 && !TARGET_64BIT
11863 && (TARGET_IEEE_FP || flag_unsafe_math_optimizations) "
11864 "fsqrt"
11865 [(set_attr "type" "fpspc")
11866 (set_attr "mode" "XF")
11867 (set_attr "athlon_decode" "direct")])
11868
11869 (define_insn "sqrttf2"
11870 [(set (match_operand:TF 0 "register_operand" "=f")
11871 (sqrt:TF (match_operand:TF 1 "register_operand" "0")))]
11872 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11873 && (TARGET_IEEE_FP || flag_unsafe_math_optimizations) "
11874 "fsqrt"
11875 [(set_attr "type" "fpspc")
11876 (set_attr "mode" "XF")
11877 (set_attr "athlon_decode" "direct")])
11878
11879 (define_insn "*sqrtextenddfxf2"
11880 [(set (match_operand:XF 0 "register_operand" "=f")
11881 (sqrt:XF (float_extend:XF
11882 (match_operand:DF 1 "register_operand" "0"))))]
11883 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 && !TARGET_64BIT"
11884 "fsqrt"
11885 [(set_attr "type" "fpspc")
11886 (set_attr "mode" "XF")
11887 (set_attr "athlon_decode" "direct")])
11888
11889 (define_insn "*sqrtextenddftf2"
11890 [(set (match_operand:TF 0 "register_operand" "=f")
11891 (sqrt:TF (float_extend:TF
11892 (match_operand:DF 1 "register_operand" "0"))))]
11893 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387"
11894 "fsqrt"
11895 [(set_attr "type" "fpspc")
11896 (set_attr "mode" "XF")
11897 (set_attr "athlon_decode" "direct")])
11898
11899 (define_insn "*sqrtextendsfxf2"
11900 [(set (match_operand:XF 0 "register_operand" "=f")
11901 (sqrt:XF (float_extend:XF
11902 (match_operand:SF 1 "register_operand" "0"))))]
11903 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 && !TARGET_64BIT"
11904 "fsqrt"
11905 [(set_attr "type" "fpspc")
11906 (set_attr "mode" "XF")
11907 (set_attr "athlon_decode" "direct")])
11908
11909 (define_insn "*sqrtextendsftf2"
11910 [(set (match_operand:TF 0 "register_operand" "=f")
11911 (sqrt:TF (float_extend:TF
11912 (match_operand:SF 1 "register_operand" "0"))))]
11913 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387"
11914 "fsqrt"
11915 [(set_attr "type" "fpspc")
11916 (set_attr "mode" "XF")
11917 (set_attr "athlon_decode" "direct")])
11918
11919 (define_insn "sindf2"
11920 [(set (match_operand:DF 0 "register_operand" "=f")
11921 (unspec:DF [(match_operand:DF 1 "register_operand" "0")] 1))]
11922 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11923 && flag_unsafe_math_optimizations"
11924 "fsin"
11925 [(set_attr "type" "fpspc")
11926 (set_attr "mode" "DF")])
11927
11928 (define_insn "sinsf2"
11929 [(set (match_operand:SF 0 "register_operand" "=f")
11930 (unspec:SF [(match_operand:SF 1 "register_operand" "0")] 1))]
11931 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11932 && flag_unsafe_math_optimizations"
11933 "fsin"
11934 [(set_attr "type" "fpspc")
11935 (set_attr "mode" "SF")])
11936
11937 (define_insn "*sinextendsfdf2"
11938 [(set (match_operand:DF 0 "register_operand" "=f")
11939 (unspec:DF [(float_extend:DF
11940 (match_operand:SF 1 "register_operand" "0"))] 1))]
11941 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11942 && flag_unsafe_math_optimizations"
11943 "fsin"
11944 [(set_attr "type" "fpspc")
11945 (set_attr "mode" "DF")])
11946
11947 (define_insn "sinxf2"
11948 [(set (match_operand:XF 0 "register_operand" "=f")
11949 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 1))]
11950 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387 && !TARGET_64BIT
11951 && flag_unsafe_math_optimizations"
11952 "fsin"
11953 [(set_attr "type" "fpspc")
11954 (set_attr "mode" "XF")])
11955
11956 (define_insn "sintf2"
11957 [(set (match_operand:TF 0 "register_operand" "=f")
11958 (unspec:TF [(match_operand:TF 1 "register_operand" "0")] 1))]
11959 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11960 && flag_unsafe_math_optimizations"
11961 "fsin"
11962 [(set_attr "type" "fpspc")
11963 (set_attr "mode" "XF")])
11964
11965 (define_insn "cosdf2"
11966 [(set (match_operand:DF 0 "register_operand" "=f")
11967 (unspec:DF [(match_operand:DF 1 "register_operand" "0")] 2))]
11968 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11969 && flag_unsafe_math_optimizations"
11970 "fcos"
11971 [(set_attr "type" "fpspc")
11972 (set_attr "mode" "DF")])
11973
11974 (define_insn "cossf2"
11975 [(set (match_operand:SF 0 "register_operand" "=f")
11976 (unspec:SF [(match_operand:SF 1 "register_operand" "0")] 2))]
11977 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11978 && flag_unsafe_math_optimizations"
11979 "fcos"
11980 [(set_attr "type" "fpspc")
11981 (set_attr "mode" "SF")])
11982
11983 (define_insn "*cosextendsfdf2"
11984 [(set (match_operand:DF 0 "register_operand" "=f")
11985 (unspec:DF [(float_extend:DF
11986 (match_operand:SF 1 "register_operand" "0"))] 2))]
11987 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11988 && flag_unsafe_math_optimizations"
11989 "fcos"
11990 [(set_attr "type" "fpspc")
11991 (set_attr "mode" "DF")])
11992
11993 (define_insn "cosxf2"
11994 [(set (match_operand:XF 0 "register_operand" "=f")
11995 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] 2))]
11996 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
11997 && flag_unsafe_math_optimizations"
11998 "fcos"
11999 [(set_attr "type" "fpspc")
12000 (set_attr "mode" "XF")])
12001
12002 (define_insn "costf2"
12003 [(set (match_operand:TF 0 "register_operand" "=f")
12004 (unspec:TF [(match_operand:TF 1 "register_operand" "0")] 2))]
12005 "! TARGET_NO_FANCY_MATH_387 && TARGET_80387
12006 && flag_unsafe_math_optimizations"
12007 "fcos"
12008 [(set_attr "type" "fpspc")
12009 (set_attr "mode" "XF")])
12010 \f
12011 ;; Block operation instructions
12012
12013 (define_insn "cld"
12014 [(set (reg:SI 19) (const_int 0))]
12015 ""
12016 "cld"
12017 [(set_attr "type" "cld")])
12018
12019 (define_expand "movstrsi"
12020 [(use (match_operand:BLK 0 "memory_operand" ""))
12021 (use (match_operand:BLK 1 "memory_operand" ""))
12022 (use (match_operand:SI 2 "nonmemory_operand" ""))
12023 (use (match_operand:SI 3 "const_int_operand" ""))]
12024 ""
12025 "
12026 {
12027 rtx srcreg, destreg, countreg;
12028 int align = 0;
12029 int count = -1;
12030 rtx insns;
12031
12032 start_sequence ();
12033
12034 if (GET_CODE (operands[3]) == CONST_INT)
12035 align = INTVAL (operands[3]);
12036
12037 /* This simple hack avoids all inlining code and simplifies code bellow. */
12038 if (!TARGET_ALIGN_STRINGOPS)
12039 align = 32;
12040
12041 if (GET_CODE (operands[2]) == CONST_INT)
12042 count = INTVAL (operands[2]);
12043
12044 destreg = copy_to_mode_reg (Pmode, XEXP (operands[0], 0));
12045 srcreg = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
12046
12047 emit_insn (gen_cld ());
12048
12049 /* When optimizing for size emit simple rep ; movsb instruction for
12050 counts not divisible by 4. */
12051
12052 if ((!optimize || optimize_size)
12053 && (count < 0 || (count & 0x03)))
12054 {
12055 countreg = copy_to_mode_reg (SImode, operands[2]);
12056 emit_insn (gen_rep_movqi (destreg, srcreg, countreg,
12057 destreg, srcreg, countreg));
12058 }
12059
12060 /* For constant aligned (or small unaligned) copies use rep movsl
12061 followed by code copying the rest. For PentiumPro ensure 8 byte
12062 alignment to allow rep movsl acceleration. */
12063
12064 else if (count >= 0
12065 && (align >= 8
12066 || (!TARGET_PENTIUMPRO && align >= 4)
12067 || optimize_size || count < 64))
12068 {
12069 if (count & ~0x03)
12070 {
12071 countreg = copy_to_mode_reg (SImode,
12072 GEN_INT ((count >> 2)
12073 & 0x3fffffff));
12074 emit_insn (gen_rep_movsi (destreg, srcreg, countreg,
12075 destreg, srcreg, countreg));
12076 }
12077 if (count & 0x02)
12078 emit_insn (gen_strmovhi (destreg, srcreg));
12079 if (count & 0x01)
12080 emit_insn (gen_strmovqi (destreg, srcreg));
12081 }
12082 /* The generic code based on the glibc implementation:
12083 - align destination to 4 bytes (8 byte alignment is used for PentiumPro
12084 allowing accelerated copying there)
12085 - copy the data using rep movsl
12086 - copy the rest. */
12087 else
12088 {
12089 rtx countreg2;
12090 rtx label = NULL;
12091
12092 /* In case we don't know anything about the alignment, default to
12093 library version, since it is usually equally fast and result in
12094 shorter code. */
12095 if (!TARGET_INLINE_ALL_STRINGOPS && align < 4)
12096 {
12097 end_sequence ();
12098 FAIL;
12099 }
12100
12101 if (TARGET_SINGLE_STRINGOP)
12102 emit_insn (gen_cld ());
12103
12104 countreg2 = gen_reg_rtx (SImode);
12105 countreg = copy_to_mode_reg (SImode, operands[2]);
12106
12107 /* We don't use loops to align destination and to copy parts smaller
12108 than 4 bytes, because gcc is able to optimize such code better (in
12109 the case the destination or the count really is aligned, gcc is often
12110 able to predict the branches) and also it is friendlier to the
12111 hardware branch prediction.
12112
12113 Using loops is benefical for generic case, because we can
12114 handle small counts using the loops. Many CPUs (such as Athlon)
12115 have large REP prefix setup costs.
12116
12117 This is quite costy. Maybe we can revisit this decision later or
12118 add some customizability to this code. */
12119
12120 if (count < 0
12121 && align < (TARGET_PENTIUMPRO && (count < 0 || count >= 260) ? 8 : 4))
12122 {
12123 label = gen_label_rtx ();
12124 emit_cmp_and_jump_insns (countreg, GEN_INT (3),
12125 LEU, 0, SImode, 1, 0, label);
12126 }
12127 if (align <= 1)
12128 {
12129 rtx label = gen_label_rtx ();
12130 rtx tmpcount = gen_reg_rtx (SImode);
12131 emit_insn (gen_andsi3 (tmpcount, destreg, GEN_INT (1)));
12132 emit_cmp_and_jump_insns (tmpcount, GEN_INT (0), EQ, 0,
12133 SImode, 1, 0, label);
12134 emit_insn (gen_strmovqi (destreg, srcreg));
12135 emit_insn (gen_addsi3 (countreg, countreg, constm1_rtx));
12136 emit_label (label);
12137 LABEL_NUSES (label) = 1;
12138 }
12139 if (align <= 2)
12140 {
12141 rtx label = gen_label_rtx ();
12142 rtx tmpcount = gen_reg_rtx (SImode);
12143 emit_insn (gen_andsi3 (tmpcount, destreg, GEN_INT (2)));
12144 emit_cmp_and_jump_insns (tmpcount, GEN_INT (0), EQ, 0,
12145 SImode, 1, 0, label);
12146 emit_insn (gen_strmovhi (destreg, srcreg));
12147 emit_insn (gen_addsi3 (countreg, countreg, GEN_INT (-2)));
12148 emit_label (label);
12149 LABEL_NUSES (label) = 1;
12150 }
12151 if (align <= 4 && TARGET_PENTIUMPRO && (count < 1 || count >= 260))
12152 {
12153 rtx label = gen_label_rtx ();
12154 rtx tmpcount = gen_reg_rtx (SImode);
12155 emit_insn (gen_andsi3 (tmpcount, destreg, GEN_INT (4)));
12156 emit_cmp_and_jump_insns (tmpcount, GEN_INT (0), EQ, 0,
12157 SImode, 1, 0, label);
12158 emit_insn (gen_strmovsi (destreg, srcreg));
12159 emit_insn (gen_addsi3 (countreg, countreg, GEN_INT (-4)));
12160 emit_label (label);
12161 LABEL_NUSES (label) = 1;
12162 }
12163
12164 if (!TARGET_SINGLE_STRINGOP)
12165 emit_insn (gen_cld());
12166 emit_insn (gen_lshrsi3 (countreg2, countreg, GEN_INT (2)));
12167 emit_insn (gen_rep_movsi (destreg, srcreg, countreg2,
12168 destreg, srcreg, countreg2));
12169
12170 if (label)
12171 {
12172 emit_label (label);
12173 LABEL_NUSES (label) = 1;
12174 }
12175 if (align > 2 && count > 0 && (count & 2))
12176 emit_insn (gen_strmovhi (destreg, srcreg));
12177 if (align <= 2 || count < 0)
12178 {
12179 rtx label = gen_label_rtx ();
12180 rtx tmpcount = gen_reg_rtx (SImode);
12181 emit_insn (gen_andsi3 (tmpcount, countreg, GEN_INT (2)));
12182 emit_cmp_and_jump_insns (tmpcount, GEN_INT (0), EQ, 0,
12183 SImode, 1, 0, label);
12184 emit_insn (gen_strmovhi (destreg, srcreg));
12185 emit_label (label);
12186 LABEL_NUSES (label) = 1;
12187 }
12188 if (align > 1 && count > 0 && (count & 1))
12189 emit_insn (gen_strmovsi (destreg, srcreg));
12190 if (align <= 1 || count < 0)
12191 {
12192 rtx label = gen_label_rtx ();
12193 rtx tmpcount = gen_reg_rtx (SImode);
12194 emit_insn (gen_andsi3 (tmpcount, countreg, GEN_INT (1)));
12195 emit_cmp_and_jump_insns (tmpcount, GEN_INT (0), EQ, 0,
12196 SImode, 1, 0, label);
12197 emit_insn (gen_strmovqi (destreg, srcreg));
12198 emit_label (label);
12199 LABEL_NUSES (label) = 1;
12200 }
12201 }
12202
12203 insns = get_insns ();
12204 end_sequence ();
12205
12206 ix86_set_move_mem_attrs (insns, operands[0], operands[1], destreg, srcreg);
12207 emit_insns (insns);
12208 DONE;
12209 }")
12210
12211 ;; Most CPUs don't like single string operations
12212 ;; Handle this case here to simplify previous expander.
12213
12214 (define_expand "strmovsi"
12215 [(set (match_dup 2)
12216 (mem:SI (match_operand:SI 1 "register_operand" "")))
12217 (set (mem:SI (match_operand:SI 0 "register_operand" ""))
12218 (match_dup 2))
12219 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 4)))
12220 (clobber (reg:CC 17))])
12221 (parallel [(set (match_dup 1) (plus:SI (match_dup 1) (const_int 4)))
12222 (clobber (reg:CC 17))])]
12223 ""
12224 "
12225 {
12226 if (TARGET_SINGLE_STRINGOP || optimize_size)
12227 {
12228 emit_insn (gen_strmovsi_1 (operands[0], operands[1], operands[0],
12229 operands[1]));
12230 DONE;
12231 }
12232 else
12233 operands[2] = gen_reg_rtx (SImode);
12234 }")
12235
12236 (define_expand "strmovhi"
12237 [(set (match_dup 2)
12238 (mem:HI (match_operand:SI 1 "register_operand" "")))
12239 (set (mem:HI (match_operand:SI 0 "register_operand" ""))
12240 (match_dup 2))
12241 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 2)))
12242 (clobber (reg:CC 17))])
12243 (parallel [(set (match_dup 1) (plus:SI (match_dup 1) (const_int 2)))
12244 (clobber (reg:CC 17))])]
12245 ""
12246 "
12247 {
12248 if (TARGET_SINGLE_STRINGOP || optimize_size)
12249 {
12250 emit_insn (gen_strmovhi_1 (operands[0], operands[1], operands[0],
12251 operands[1]));
12252 DONE;
12253 }
12254 else
12255 operands[2] = gen_reg_rtx (HImode);
12256 }")
12257
12258 (define_expand "strmovqi"
12259 [(set (match_dup 2)
12260 (mem:QI (match_operand:SI 1 "register_operand" "")))
12261 (set (mem:QI (match_operand:SI 0 "register_operand" ""))
12262 (match_dup 2))
12263 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
12264 (clobber (reg:CC 17))])
12265 (parallel [(set (match_dup 1) (plus:SI (match_dup 1) (const_int 1)))
12266 (clobber (reg:CC 17))])]
12267 ""
12268 "
12269 {
12270 if (TARGET_SINGLE_STRINGOP || optimize_size)
12271 {
12272 emit_insn (gen_strmovqi_1 (operands[0], operands[1], operands[0],
12273 operands[1]));
12274 DONE;
12275 }
12276 else
12277 operands[2] = gen_reg_rtx (QImode);
12278 }")
12279
12280 (define_insn "strmovsi_1"
12281 [(set (mem:SI (match_operand:SI 2 "register_operand" "0"))
12282 (mem:SI (match_operand:SI 3 "register_operand" "1")))
12283 (set (match_operand:SI 0 "register_operand" "=D")
12284 (plus:SI (match_dup 2)
12285 (const_int 4)))
12286 (set (match_operand:SI 1 "register_operand" "=S")
12287 (plus:SI (match_dup 3)
12288 (const_int 4)))
12289 (use (reg:SI 19))]
12290 "TARGET_SINGLE_STRINGOP || optimize_size"
12291 "movsl"
12292 [(set_attr "type" "str")
12293 (set_attr "mode" "SI")
12294 (set_attr "memory" "both")])
12295
12296 (define_insn "strmovhi_1"
12297 [(set (mem:HI (match_operand:SI 2 "register_operand" "0"))
12298 (mem:HI (match_operand:SI 3 "register_operand" "1")))
12299 (set (match_operand:SI 0 "register_operand" "=D")
12300 (plus:SI (match_dup 2)
12301 (const_int 2)))
12302 (set (match_operand:SI 1 "register_operand" "=S")
12303 (plus:SI (match_dup 3)
12304 (const_int 2)))
12305 (use (reg:SI 19))]
12306 "TARGET_SINGLE_STRINGOP || optimize_size"
12307 "movsw"
12308 [(set_attr "type" "str")
12309 (set_attr "memory" "both")
12310 (set_attr "mode" "HI")])
12311
12312 (define_insn "strmovqi_1"
12313 [(set (mem:QI (match_operand:SI 2 "register_operand" "0"))
12314 (mem:QI (match_operand:SI 3 "register_operand" "1")))
12315 (set (match_operand:SI 0 "register_operand" "=D")
12316 (plus:SI (match_dup 2)
12317 (const_int 1)))
12318 (set (match_operand:SI 1 "register_operand" "=S")
12319 (plus:SI (match_dup 3)
12320 (const_int 1)))
12321 (use (reg:SI 19))]
12322 "TARGET_SINGLE_STRINGOP || optimize_size"
12323 "movsb"
12324 [(set_attr "type" "str")
12325 (set_attr "memory" "both")
12326 (set_attr "mode" "QI")])
12327
12328 (define_insn "rep_movsi"
12329 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
12330 (set (match_operand:SI 0 "register_operand" "=D")
12331 (plus:SI (ashift:SI (match_operand:SI 5 "register_operand" "2")
12332 (const_int 2))
12333 (match_operand:SI 3 "register_operand" "0")))
12334 (set (match_operand:SI 1 "register_operand" "=S")
12335 (plus:SI (ashift:SI (match_dup 5) (const_int 2))
12336 (match_operand:SI 4 "register_operand" "1")))
12337 (set (mem:BLK (match_dup 3))
12338 (mem:BLK (match_dup 4)))
12339 (use (match_dup 5))
12340 (use (reg:SI 19))]
12341 ""
12342 "rep\;movsl|rep movsd"
12343 [(set_attr "type" "str")
12344 (set_attr "prefix_rep" "1")
12345 (set_attr "memory" "both")
12346 (set_attr "mode" "SI")])
12347
12348 (define_insn "rep_movqi"
12349 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
12350 (set (match_operand:SI 0 "register_operand" "=D")
12351 (plus:SI (match_operand:SI 3 "register_operand" "0")
12352 (match_operand:SI 5 "register_operand" "2")))
12353 (set (match_operand:SI 1 "register_operand" "=S")
12354 (plus:SI (match_operand:SI 4 "register_operand" "1") (match_dup 5)))
12355 (set (mem:BLK (match_dup 3))
12356 (mem:BLK (match_dup 4)))
12357 (use (match_dup 5))
12358 (use (reg:SI 19))]
12359 ""
12360 "rep\;movsb|rep movsb"
12361 [(set_attr "type" "str")
12362 (set_attr "prefix_rep" "1")
12363 (set_attr "memory" "both")
12364 (set_attr "mode" "SI")])
12365
12366 (define_expand "clrstrsi"
12367 [(use (match_operand:BLK 0 "memory_operand" ""))
12368 (use (match_operand:SI 1 "nonmemory_operand" ""))
12369 (use (match_operand:SI 2 "const_int_operand" ""))]
12370 ""
12371 "
12372 {
12373 /* See comments in movstr expanders. The code is mostly identical. */
12374
12375 rtx destreg, zeroreg, countreg;
12376 int align = 0;
12377 int count = -1;
12378 rtx insns;
12379
12380 start_sequence ();
12381
12382 if (GET_CODE (operands[2]) == CONST_INT)
12383 align = INTVAL (operands[2]);
12384
12385 /* This simple hack avoids all inlining code and simplifies code bellow. */
12386 if (!TARGET_ALIGN_STRINGOPS)
12387 align = 32;
12388
12389 if (GET_CODE (operands[1]) == CONST_INT)
12390 count = INTVAL (operands[1]);
12391
12392 destreg = copy_to_mode_reg (Pmode, XEXP (operands[0], 0));
12393
12394 emit_insn (gen_cld ());
12395
12396 /* When optimizing for size emit simple rep ; movsb instruction for
12397 counts not divisible by 4. */
12398
12399 if ((!optimize || optimize_size)
12400 && (count < 0 || (count & 0x03)))
12401 {
12402 countreg = copy_to_mode_reg (SImode, operands[1]);
12403 zeroreg = copy_to_mode_reg (QImode, const0_rtx);
12404 emit_insn (gen_rep_stosqi (destreg, countreg, zeroreg,
12405 destreg, countreg));
12406 }
12407 else if (count >= 0
12408 && (align >= 8
12409 || (!TARGET_PENTIUMPRO && align >= 4)
12410 || optimize_size || count < 64))
12411 {
12412 zeroreg = copy_to_mode_reg (SImode, const0_rtx);
12413 if (INTVAL (operands[1]) & ~0x03)
12414 {
12415 countreg = copy_to_mode_reg (SImode,
12416 GEN_INT ((INTVAL (operands[1]) >> 2)
12417 & 0x3fffffff));
12418 emit_insn (gen_rep_stossi (destreg, countreg, zeroreg,
12419 destreg, countreg));
12420 }
12421 if (INTVAL (operands[1]) & 0x02)
12422 emit_insn (gen_strsethi (destreg,
12423 gen_rtx_SUBREG (HImode, zeroreg, 0)));
12424 if (INTVAL (operands[1]) & 0x01)
12425 emit_insn (gen_strsetqi (destreg,
12426 gen_rtx_SUBREG (QImode, zeroreg, 0)));
12427 }
12428 else
12429 {
12430 rtx countreg2;
12431 rtx label = NULL;
12432
12433 /* In case we don't know anything about the alignment, default to
12434 library version, since it is usually equally fast and result in
12435 shorter code. */
12436 if (!TARGET_INLINE_ALL_STRINGOPS && align < 4)
12437 {
12438 end_sequence ();
12439 FAIL;
12440 }
12441
12442 if (TARGET_SINGLE_STRINGOP)
12443 emit_insn (gen_cld ());
12444
12445 countreg2 = gen_reg_rtx (SImode);
12446 countreg = copy_to_mode_reg (SImode, operands[1]);
12447 zeroreg = copy_to_mode_reg (SImode, const0_rtx);
12448
12449 if (count < 0
12450 && align < (TARGET_PENTIUMPRO && (count < 0 || count >= 260) ? 8 : 4))
12451 {
12452 label = gen_label_rtx ();
12453 emit_cmp_and_jump_insns (countreg, GEN_INT (3),
12454 LEU, 0, SImode, 1, 0, label);
12455 }
12456 if (align <= 1)
12457 {
12458 rtx label = gen_label_rtx ();
12459 rtx tmpcount = gen_reg_rtx (SImode);
12460 emit_insn (gen_andsi3 (tmpcount, destreg, GEN_INT (1)));
12461 emit_cmp_and_jump_insns (tmpcount, GEN_INT (0), EQ, 0,
12462 SImode, 1, 0, label);
12463 emit_insn (gen_strsetqi (destreg,
12464 gen_rtx_SUBREG (QImode, zeroreg, 0)));
12465 emit_insn (gen_addsi3 (countreg, countreg, constm1_rtx));
12466 emit_label (label);
12467 LABEL_NUSES (label) = 1;
12468 }
12469 if (align <= 2)
12470 {
12471 rtx label = gen_label_rtx ();
12472 rtx tmpcount = gen_reg_rtx (SImode);
12473 emit_insn (gen_andsi3 (tmpcount, destreg, GEN_INT (2)));
12474 emit_cmp_and_jump_insns (tmpcount, GEN_INT (0), EQ, 0,
12475 SImode, 1, 0, label);
12476 emit_insn (gen_strsethi (destreg,
12477 gen_rtx_SUBREG (HImode, zeroreg, 0)));
12478 emit_insn (gen_addsi3 (countreg, countreg, GEN_INT (-2)));
12479 emit_label (label);
12480 LABEL_NUSES (label) = 1;
12481 }
12482 if (align <= 4 && TARGET_PENTIUMPRO && (count < 1 || count >= 260))
12483 {
12484 rtx label = gen_label_rtx ();
12485 rtx tmpcount = gen_reg_rtx (SImode);
12486 emit_insn (gen_andsi3 (tmpcount, destreg, GEN_INT (4)));
12487 emit_cmp_and_jump_insns (tmpcount, GEN_INT (0), EQ, 0,
12488 SImode, 1, 0, label);
12489 emit_insn (gen_strsetsi (destreg, zeroreg));
12490 emit_insn (gen_addsi3 (countreg, countreg, GEN_INT (-4)));
12491 emit_label (label);
12492 LABEL_NUSES (label) = 1;
12493 }
12494
12495 if (!TARGET_SINGLE_STRINGOP)
12496 emit_insn (gen_cld());
12497 emit_insn (gen_lshrsi3 (countreg2, countreg, GEN_INT (2)));
12498 emit_insn (gen_rep_stossi (destreg, countreg2, zeroreg,
12499 destreg, countreg2));
12500
12501 if (label)
12502 {
12503 emit_label (label);
12504 LABEL_NUSES (label) = 1;
12505 }
12506 if (align > 2 && count > 0 && (count & 2))
12507 emit_insn (gen_strsethi (destreg,
12508 gen_rtx_SUBREG (HImode, zeroreg, 0)));
12509 if (align <= 2 || count < 0)
12510 {
12511 rtx label = gen_label_rtx ();
12512 rtx tmpcount = gen_reg_rtx (SImode);
12513 emit_insn (gen_andsi3 (tmpcount, countreg, GEN_INT (2)));
12514 emit_cmp_and_jump_insns (tmpcount, GEN_INT (0), EQ, 0,
12515 SImode, 1, 0, label);
12516 emit_insn (gen_strsethi (destreg,
12517 gen_rtx_SUBREG (HImode, zeroreg, 0)));
12518 emit_label (label);
12519 LABEL_NUSES (label) = 1;
12520 }
12521 if (align > 1 && count > 0 && (count & 1))
12522 emit_insn (gen_strsetqi (destreg,
12523 gen_rtx_SUBREG (QImode, zeroreg, 0)));
12524 if (align <= 1 || count < 0)
12525 {
12526 rtx label = gen_label_rtx ();
12527 rtx tmpcount = gen_reg_rtx (SImode);
12528 emit_insn (gen_andsi3 (tmpcount, countreg, GEN_INT (1)));
12529 emit_cmp_and_jump_insns (tmpcount, GEN_INT (0), EQ, 0,
12530 SImode, 1, 0, label);
12531 emit_insn (gen_strsetqi (destreg,
12532 gen_rtx_SUBREG (QImode, zeroreg, 0)));
12533 emit_label (label);
12534 LABEL_NUSES (label) = 1;
12535 }
12536 }
12537
12538 insns = get_insns ();
12539 end_sequence ();
12540
12541 ix86_set_move_mem_attrs (insns, operands[0], operands[0], destreg, destreg);
12542 emit_insns (insns);
12543
12544 DONE;
12545 }")
12546
12547 ;; Most CPUs don't like single string operations
12548 ;; Handle this case here to simplify previous expander.
12549
12550 (define_expand "strsetsi"
12551 [(set (mem:SI (match_operand:SI 0 "register_operand" ""))
12552 (match_operand:SI 1 "register_operand" ""))
12553 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 4)))
12554 (clobber (reg:CC 17))])]
12555 ""
12556 "
12557 {
12558 if (TARGET_SINGLE_STRINGOP || optimize_size)
12559 {
12560 emit_insn (gen_strsetsi_1 (operands[0], operands[0], operands[1]));
12561 DONE;
12562 }
12563 }")
12564
12565 (define_expand "strsethi"
12566 [(set (mem:HI (match_operand:SI 0 "register_operand" ""))
12567 (match_operand:HI 1 "register_operand" ""))
12568 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 2)))
12569 (clobber (reg:CC 17))])]
12570 ""
12571 "
12572 {
12573 if (TARGET_SINGLE_STRINGOP || optimize_size)
12574 {
12575 emit_insn (gen_strsethi_1 (operands[0], operands[0], operands[1]));
12576 DONE;
12577 }
12578 }")
12579
12580 (define_expand "strsetqi"
12581 [(set (mem:QI (match_operand:SI 0 "register_operand" ""))
12582 (match_operand:QI 1 "register_operand" ""))
12583 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
12584 (clobber (reg:CC 17))])]
12585 ""
12586 "
12587 {
12588 if (TARGET_SINGLE_STRINGOP || optimize_size)
12589 {
12590 emit_insn (gen_strsetqi_1 (operands[0], operands[0], operands[1]));
12591 DONE;
12592 }
12593 }")
12594
12595 (define_insn "strsetsi_1"
12596 [(set (mem:SI (match_operand:SI 1 "register_operand" "0"))
12597 (match_operand:SI 2 "register_operand" "a"))
12598 (set (match_operand:SI 0 "register_operand" "=D")
12599 (plus:SI (match_dup 1)
12600 (const_int 4)))
12601 (use (reg:SI 19))]
12602 "TARGET_SINGLE_STRINGOP || optimize_size"
12603 "stosl"
12604 [(set_attr "type" "str")
12605 (set_attr "memory" "store")
12606 (set_attr "mode" "SI")])
12607
12608 (define_insn "strsethi_1"
12609 [(set (mem:HI (match_operand:SI 1 "register_operand" "0"))
12610 (match_operand:HI 2 "register_operand" "a"))
12611 (set (match_operand:SI 0 "register_operand" "=D")
12612 (plus:SI (match_dup 1)
12613 (const_int 2)))
12614 (use (reg:SI 19))]
12615 "TARGET_SINGLE_STRINGOP || optimize_size"
12616 "stosw"
12617 [(set_attr "type" "str")
12618 (set_attr "memory" "store")
12619 (set_attr "mode" "HI")])
12620
12621 (define_insn "strsetqi_1"
12622 [(set (mem:QI (match_operand:SI 1 "register_operand" "0"))
12623 (match_operand:QI 2 "register_operand" "a"))
12624 (set (match_operand:SI 0 "register_operand" "=D")
12625 (plus:SI (match_dup 1)
12626 (const_int 1)))
12627 (use (reg:SI 19))]
12628 "TARGET_SINGLE_STRINGOP || optimize_size"
12629 "stosb"
12630 [(set_attr "type" "str")
12631 (set_attr "memory" "store")
12632 (set_attr "mode" "QI")])
12633
12634 (define_insn "rep_stossi"
12635 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
12636 (set (match_operand:SI 0 "register_operand" "=D")
12637 (plus:SI (ashift:SI (match_operand:SI 4 "register_operand" "1")
12638 (const_int 2))
12639 (match_operand:SI 3 "register_operand" "0")))
12640 (set (mem:BLK (match_dup 3))
12641 (const_int 0))
12642 (use (match_operand:SI 2 "register_operand" "a"))
12643 (use (match_dup 4))
12644 (use (reg:SI 19))]
12645 ""
12646 "rep\;stosl|rep stosd"
12647 [(set_attr "type" "str")
12648 (set_attr "prefix_rep" "1")
12649 (set_attr "memory" "store")
12650 (set_attr "mode" "SI")])
12651
12652 (define_insn "rep_stosqi"
12653 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
12654 (set (match_operand:SI 0 "register_operand" "=D")
12655 (plus:SI (match_operand:SI 3 "register_operand" "0")
12656 (match_operand:SI 4 "register_operand" "1")))
12657 (set (mem:BLK (match_dup 3))
12658 (const_int 0))
12659 (use (match_operand:QI 2 "register_operand" "a"))
12660 (use (match_dup 4))
12661 (use (reg:SI 19))]
12662 ""
12663 "rep\;stosb|rep stosb"
12664 [(set_attr "type" "str")
12665 (set_attr "prefix_rep" "1")
12666 (set_attr "memory" "store")
12667 (set_attr "mode" "QI")])
12668
12669 (define_expand "cmpstrsi"
12670 [(set (match_operand:SI 0 "register_operand" "")
12671 (compare:SI (match_operand:BLK 1 "general_operand" "")
12672 (match_operand:BLK 2 "general_operand" "")))
12673 (use (match_operand:SI 3 "general_operand" ""))
12674 (use (match_operand:SI 4 "immediate_operand" ""))]
12675 ""
12676 "
12677 {
12678 rtx addr1, addr2, out, outlow, count, countreg, align;
12679
12680 out = operands[0];
12681 if (GET_CODE (out) != REG)
12682 out = gen_reg_rtx (SImode);
12683
12684 addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
12685 addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
12686
12687 count = operands[3];
12688 countreg = copy_to_mode_reg (SImode, count);
12689
12690 /* %%% Iff we are testing strict equality, we can use known alignment
12691 to good advantage. This may be possible with combine, particularly
12692 once cc0 is dead. */
12693 align = operands[4];
12694
12695 emit_insn (gen_cld ());
12696 if (GET_CODE (count) == CONST_INT)
12697 {
12698 if (INTVAL (count) == 0)
12699 {
12700 emit_move_insn (operands[0], const0_rtx);
12701 DONE;
12702 }
12703 emit_insn (gen_cmpstrsi_nz_1 (addr1, addr2, countreg, align,
12704 addr1, addr2, countreg));
12705 }
12706 else
12707 {
12708 emit_insn (gen_cmpsi_1 (countreg, countreg));
12709 emit_insn (gen_cmpstrsi_1 (addr1, addr2, countreg, align,
12710 addr1, addr2, countreg));
12711 }
12712
12713 outlow = gen_lowpart (QImode, out);
12714 emit_insn (gen_cmpintqi (outlow));
12715 emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
12716
12717 if (operands[0] != out)
12718 emit_move_insn (operands[0], out);
12719
12720 DONE;
12721 }")
12722
12723 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
12724
12725 (define_expand "cmpintqi"
12726 [(set (match_dup 1)
12727 (gtu:QI (reg:CC 17) (const_int 0)))
12728 (set (match_dup 2)
12729 (ltu:QI (reg:CC 17) (const_int 0)))
12730 (parallel [(set (match_operand:QI 0 "register_operand" "")
12731 (minus:QI (match_dup 1)
12732 (match_dup 2)))
12733 (clobber (reg:CC 17))])]
12734 ""
12735 "operands[1] = gen_reg_rtx (QImode);
12736 operands[2] = gen_reg_rtx (QImode);")
12737
12738 ;; memcmp recognizers. The `cmpsb' opcode does nothing if the count is
12739 ;; zero. Emit extra code to make sure that a zero-length compare is EQ.
12740
12741 (define_insn "cmpstrsi_nz_1"
12742 [(set (reg:CC 17)
12743 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
12744 (mem:BLK (match_operand:SI 5 "register_operand" "1"))))
12745 (use (match_operand:SI 6 "register_operand" "2"))
12746 (use (match_operand:SI 3 "immediate_operand" "i"))
12747 (use (reg:SI 19))
12748 (clobber (match_operand:SI 0 "register_operand" "=S"))
12749 (clobber (match_operand:SI 1 "register_operand" "=D"))
12750 (clobber (match_operand:SI 2 "register_operand" "=c"))]
12751 ""
12752 "repz{\;| }cmpsb"
12753 [(set_attr "type" "str")
12754 (set_attr "mode" "QI")
12755 (set_attr "prefix_rep" "1")])
12756
12757 ;; The same, but the count is not known to not be zero.
12758
12759 (define_insn "cmpstrsi_1"
12760 [(set (reg:CC 17)
12761 (if_then_else:CC (ne (match_operand:SI 6 "register_operand" "2")
12762 (const_int 0))
12763 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
12764 (mem:BLK (match_operand:SI 5 "register_operand" "1")))
12765 (const_int 0)))
12766 (use (match_operand:SI 3 "immediate_operand" "i"))
12767 (use (reg:CC 17))
12768 (use (reg:SI 19))
12769 (clobber (match_operand:SI 0 "register_operand" "=S"))
12770 (clobber (match_operand:SI 1 "register_operand" "=D"))
12771 (clobber (match_operand:SI 2 "register_operand" "=c"))]
12772 ""
12773 "repz{\;| }cmpsb"
12774 [(set_attr "type" "str")
12775 (set_attr "mode" "QI")
12776 (set_attr "prefix_rep" "1")])
12777
12778 (define_expand "strlensi"
12779 [(set (match_operand:SI 0 "register_operand" "")
12780 (unspec:SI [(match_operand:BLK 1 "general_operand" "")
12781 (match_operand:QI 2 "immediate_operand" "")
12782 (match_operand:SI 3 "immediate_operand" "")] 0))]
12783 ""
12784 "
12785 {
12786 rtx out, addr, scratch1, scratch2, scratch3;
12787 rtx eoschar = operands[2];
12788 rtx align = operands[3];
12789
12790 /* The generic case of strlen expander is long. Avoid it's
12791 expanding unless TARGET_INLINE_ALL_STRINGOPS. */
12792
12793 if (TARGET_UNROLL_STRLEN && eoschar == const0_rtx && optimize > 1
12794 && !TARGET_INLINE_ALL_STRINGOPS
12795 && !optimize_size
12796 && (GET_CODE (align) != CONST_INT || INTVAL (align) < 4))
12797 FAIL;
12798
12799 out = operands[0];
12800 addr = force_reg (Pmode, XEXP (operands[1], 0));
12801 scratch1 = gen_reg_rtx (SImode);
12802
12803 if (TARGET_UNROLL_STRLEN && eoschar == const0_rtx && optimize > 1
12804 && !optimize_size)
12805 {
12806 /* Well it seems that some optimizer does not combine a call like
12807 foo(strlen(bar), strlen(bar));
12808 when the move and the subtraction is done here. It does calculate
12809 the length just once when these instructions are done inside of
12810 output_strlen_unroll(). But I think since &bar[strlen(bar)] is
12811 often used and I use one fewer register for the lifetime of
12812 output_strlen_unroll() this is better. */
12813
12814 if (GET_CODE (align) != CONST_INT || INTVAL (align) < 4)
12815 emit_move_insn (scratch1, addr);
12816
12817 emit_move_insn (out, addr);
12818
12819 ix86_expand_strlensi_unroll_1 (out, align, scratch1);
12820
12821 /* strlensi_unroll_1 returns the address of the zero at the end of
12822 the string, like memchr(), so compute the length by subtracting
12823 the start address. */
12824 emit_insn (gen_subsi3 (out, out, addr));
12825 }
12826 else
12827 {
12828 scratch2 = gen_reg_rtx (SImode);
12829 scratch3 = gen_reg_rtx (SImode);
12830
12831 emit_move_insn (scratch3, addr);
12832
12833 emit_insn (gen_cld ());
12834 emit_insn (gen_strlensi_1 (scratch1, scratch3, eoschar,
12835 align, constm1_rtx, scratch3));
12836 emit_insn (gen_one_cmplsi2 (scratch2, scratch1));
12837 emit_insn (gen_addsi3 (out, scratch2, constm1_rtx));
12838 }
12839 DONE;
12840 }")
12841
12842 (define_insn "strlensi_1"
12843 [(set (match_operand:SI 0 "register_operand" "=&c")
12844 (unspec:SI [(mem:BLK (match_operand:SI 5 "register_operand" "1"))
12845 (match_operand:QI 2 "general_operand" "a")
12846 (match_operand:SI 3 "immediate_operand" "i")
12847 (match_operand:SI 4 "immediate_operand" "0")] 0))
12848 (use (reg:SI 19))
12849 (clobber (match_operand:SI 1 "register_operand" "=D"))
12850 (clobber (reg:CC 17))]
12851 ""
12852 "repnz{\;| }scasb"
12853 [(set_attr "type" "str")
12854 (set_attr "mode" "QI")
12855 (set_attr "prefix_rep" "1")])
12856 \f
12857 ;; Conditional move instructions.
12858
12859 (define_expand "movsicc"
12860 [(set (match_operand:SI 0 "register_operand" "")
12861 (if_then_else:SI (match_operand 1 "comparison_operator" "")
12862 (match_operand:SI 2 "general_operand" "")
12863 (match_operand:SI 3 "general_operand" "")))]
12864 ""
12865 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
12866
12867 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
12868 ;; the register first winds up with `sbbl $0,reg', which is also weird.
12869 ;; So just document what we're doing explicitly.
12870
12871 (define_insn "x86_movsicc_0_m1"
12872 [(set (match_operand:SI 0 "register_operand" "=r")
12873 (if_then_else:SI (ltu (reg:CC 17) (const_int 0))
12874 (const_int -1)
12875 (const_int 0)))
12876 (clobber (reg:CC 17))]
12877 ""
12878 "sbb{l}\\t%0, %0"
12879 ; Since we don't have the proper number of operands for an alu insn,
12880 ; fill in all the blanks.
12881 [(set_attr "type" "alu")
12882 (set_attr "memory" "none")
12883 (set_attr "imm_disp" "false")
12884 (set_attr "mode" "SI")
12885 (set_attr "length_immediate" "0")])
12886
12887 (define_insn "*movsicc_noc"
12888 [(set (match_operand:SI 0 "register_operand" "=r,r")
12889 (if_then_else:SI (match_operator 1 "ix86_comparison_operator"
12890 [(reg 17) (const_int 0)])
12891 (match_operand:SI 2 "nonimmediate_operand" "rm,0")
12892 (match_operand:SI 3 "nonimmediate_operand" "0,rm")))]
12893 "TARGET_CMOVE
12894 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
12895 "@
12896 cmov%C1\\t{%2, %0|%0, %2}
12897 cmov%c1\\t{%3, %0|%0, %3}"
12898 [(set_attr "type" "icmov")
12899 (set_attr "mode" "SI")])
12900
12901 (define_expand "movhicc"
12902 [(set (match_operand:HI 0 "register_operand" "")
12903 (if_then_else:HI (match_operand 1 "comparison_operator" "")
12904 (match_operand:HI 2 "nonimmediate_operand" "")
12905 (match_operand:HI 3 "nonimmediate_operand" "")))]
12906 "TARGET_CMOVE && TARGET_HIMODE_MATH"
12907 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
12908
12909 (define_insn "*movhicc_noc"
12910 [(set (match_operand:HI 0 "register_operand" "=r,r")
12911 (if_then_else:HI (match_operator 1 "ix86_comparison_operator"
12912 [(reg 17) (const_int 0)])
12913 (match_operand:HI 2 "nonimmediate_operand" "rm,0")
12914 (match_operand:HI 3 "nonimmediate_operand" "0,rm")))]
12915 "TARGET_CMOVE
12916 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
12917 "@
12918 cmov%C1\\t{%2, %0|%0, %2}
12919 cmov%c1\\t{%3, %0|%0, %3}"
12920 [(set_attr "type" "icmov")
12921 (set_attr "mode" "HI")])
12922
12923 (define_expand "movsfcc"
12924 [(set (match_operand:SF 0 "register_operand" "")
12925 (if_then_else:SF (match_operand 1 "comparison_operator" "")
12926 (match_operand:SF 2 "register_operand" "")
12927 (match_operand:SF 3 "register_operand" "")))]
12928 "TARGET_CMOVE"
12929 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
12930
12931 (define_insn "*movsfcc_1"
12932 [(set (match_operand:SF 0 "register_operand" "=f,f,r,r")
12933 (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
12934 [(reg 17) (const_int 0)])
12935 (match_operand:SF 2 "nonimmediate_operand" "f,0,rm,0")
12936 (match_operand:SF 3 "nonimmediate_operand" "0,f,0,rm")))]
12937 "TARGET_CMOVE
12938 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
12939 "@
12940 fcmov%F1\\t{%2, %0|%0, %2}
12941 fcmov%f1\\t{%3, %0|%0, %3}
12942 cmov%C1\\t{%2, %0|%0, %2}
12943 cmov%c1\\t{%3, %0|%0, %3}"
12944 [(set_attr "type" "fcmov,fcmov,icmov,icmov")
12945 (set_attr "mode" "SF,SF,SI,SI")])
12946
12947 (define_expand "movdfcc"
12948 [(set (match_operand:DF 0 "register_operand" "")
12949 (if_then_else:DF (match_operand 1 "comparison_operator" "")
12950 (match_operand:DF 2 "register_operand" "")
12951 (match_operand:DF 3 "register_operand" "")))]
12952 "TARGET_CMOVE"
12953 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
12954
12955 (define_insn "*movdfcc_1"
12956 [(set (match_operand:DF 0 "register_operand" "=f,f,&r,&r")
12957 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
12958 [(reg 17) (const_int 0)])
12959 (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
12960 (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
12961 "TARGET_CMOVE && !TARGET_64BIT
12962 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
12963 "@
12964 fcmov%F1\\t{%2, %0|%0, %2}
12965 fcmov%f1\\t{%3, %0|%0, %3}
12966 #
12967 #"
12968 [(set_attr "type" "fcmov,fcmov,multi,multi")
12969 (set_attr "mode" "DF")])
12970
12971 (define_insn "*movdfcc_1_rex64"
12972 [(set (match_operand:DF 0 "register_operand" "=f,f,&r,&r")
12973 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
12974 [(reg 17) (const_int 0)])
12975 (match_operand:DF 2 "nonimmediate_operand" "f,0,rm,0")
12976 (match_operand:DF 3 "nonimmediate_operand" "0,f,0,rm")))]
12977 "TARGET_CMOVE && TARGET_64BIT
12978 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
12979 "@
12980 fcmov%F1\\t{%2, %0|%0, %2}
12981 fcmov%f1\\t{%3, %0|%0, %3}
12982 cmov%C1\\t{%2, %0|%0, %2}
12983 cmov%c1\\t{%3, %0|%0, %3}"
12984 [(set_attr "type" "fcmov,fcmov,icmov,icmov")
12985 (set_attr "mode" "DF")])
12986
12987 (define_split
12988 [(set (match_operand:DF 0 "register_operand" "")
12989 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
12990 [(match_operand 4 "" "") (const_int 0)])
12991 (match_operand:DF 2 "nonimmediate_operand" "")
12992 (match_operand:DF 3 "nonimmediate_operand" "")))]
12993 "!ANY_FP_REG_P (operands[0]) && reload_completed && !TARGET_64BIT"
12994 [(set (match_dup 2)
12995 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
12996 (match_dup 5)
12997 (match_dup 7)))
12998 (set (match_dup 3)
12999 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
13000 (match_dup 6)
13001 (match_dup 8)))]
13002 "split_di (operands+2, 1, operands+5, operands+6);
13003 split_di (operands+3, 1, operands+7, operands+8);
13004 split_di (operands, 1, operands+2, operands+3);")
13005
13006 (define_expand "movxfcc"
13007 [(set (match_operand:XF 0 "register_operand" "")
13008 (if_then_else:XF (match_operand 1 "comparison_operator" "")
13009 (match_operand:XF 2 "register_operand" "")
13010 (match_operand:XF 3 "register_operand" "")))]
13011 "TARGET_CMOVE && !TARGET_64BIT"
13012 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
13013
13014 (define_expand "movtfcc"
13015 [(set (match_operand:TF 0 "register_operand" "")
13016 (if_then_else:TF (match_operand 1 "comparison_operator" "")
13017 (match_operand:TF 2 "register_operand" "")
13018 (match_operand:TF 3 "register_operand" "")))]
13019 "TARGET_CMOVE"
13020 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
13021
13022 (define_insn "*movxfcc_1"
13023 [(set (match_operand:XF 0 "register_operand" "=f,f")
13024 (if_then_else:XF (match_operator 1 "fcmov_comparison_operator"
13025 [(reg 17) (const_int 0)])
13026 (match_operand:XF 2 "register_operand" "f,0")
13027 (match_operand:XF 3 "register_operand" "0,f")))]
13028 "TARGET_CMOVE && !TARGET_64BIT"
13029 "@
13030 fcmov%F1\\t{%2, %0|%0, %2}
13031 fcmov%f1\\t{%3, %0|%0, %3}"
13032 [(set_attr "type" "fcmov")
13033 (set_attr "mode" "XF")])
13034
13035 (define_insn "*movtfcc_1"
13036 [(set (match_operand:TF 0 "register_operand" "=f,f")
13037 (if_then_else:TF (match_operator 1 "fcmov_comparison_operator"
13038 [(reg 17) (const_int 0)])
13039 (match_operand:TF 2 "register_operand" "f,0")
13040 (match_operand:TF 3 "register_operand" "0,f")))]
13041 "TARGET_CMOVE"
13042 "@
13043 fcmov%F1\\t{%2, %0|%0, %2}
13044 fcmov%f1\\t{%3, %0|%0, %3}"
13045 [(set_attr "type" "fcmov")
13046 (set_attr "mode" "XF")])
13047
13048 (define_expand "minsf3"
13049 [(parallel [
13050 (set (match_operand:SF 0 "register_operand" "")
13051 (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "")
13052 (match_operand:SF 2 "nonimmediate_operand" ""))
13053 (match_dup 1)
13054 (match_dup 2)))
13055 (clobber (reg:CC 17))])]
13056 "TARGET_SSE"
13057 "")
13058
13059 (define_insn "*minsf"
13060 [(set (match_operand:SF 0 "register_operand" "=x#f,f#x,f#x")
13061 (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "0,0,f#x")
13062 (match_operand:SF 2 "nonimmediate_operand" "xm#f,f#x,0"))
13063 (match_dup 1)
13064 (match_dup 2)))
13065 (clobber (reg:CC 17))]
13066 "TARGET_SSE && TARGET_IEEE_FP"
13067 "#")
13068
13069 (define_insn "*minsf_nonieee"
13070 [(set (match_operand:SF 0 "register_operand" "=x#f,f#x")
13071 (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "%0,0")
13072 (match_operand:SF 2 "nonimmediate_operand" "xm#f,fm#x"))
13073 (match_dup 1)
13074 (match_dup 2)))
13075 (clobber (reg:CC 17))]
13076 "TARGET_SSE && !TARGET_IEEE_FP"
13077 "#")
13078
13079 (define_split
13080 [(set (match_operand:SF 0 "register_operand" "")
13081 (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "")
13082 (match_operand:SF 2 "nonimmediate_operand" ""))
13083 (match_dup 1)
13084 (match_dup 2)))
13085 (clobber (reg:CC 17))]
13086 "SSE_REG_P (operands[0]) && reload_completed"
13087 [(set (match_dup 0)
13088 (if_then_else:SF (lt (match_dup 1)
13089 (match_dup 2))
13090 (match_dup 1)
13091 (match_dup 2)))])
13092
13093 ;; We can't represent the LT test directly. Do this by swapping the operands.
13094 (define_split
13095 [(set (match_operand:SF 0 "register_operand" "")
13096 (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "")
13097 (match_operand:SF 2 "register_operand" ""))
13098 (match_dup 1)
13099 (match_dup 2)))
13100 (clobber (reg:CC 17))]
13101 "FP_REG_P (operands[0]) && reload_completed"
13102 [(set (reg:CCFP 17)
13103 (compare:CCFP (match_dup 2)
13104 (match_dup 1)))
13105 (set (match_dup 0)
13106 (if_then_else:SF (ge (reg:CCFP 17) (const_int 0))
13107 (match_dup 1)
13108 (match_dup 2)))])
13109
13110 (define_insn "*minsf_sse"
13111 [(set (match_operand:SF 0 "register_operand" "=x")
13112 (if_then_else:SF (lt (match_operand:SF 1 "register_operand" "0")
13113 (match_operand:SF 2 "nonimmediate_operand" "xm"))
13114 (match_dup 1)
13115 (match_dup 2)))]
13116 "TARGET_SSE && reload_completed"
13117 "minss\\t{%2, %0|%0, %2}"
13118 [(set_attr "type" "sse")
13119 (set_attr "mode" "SF")])
13120
13121 (define_expand "mindf3"
13122 [(parallel [
13123 (set (match_operand:DF 0 "register_operand" "")
13124 (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "")
13125 (match_operand:DF 2 "nonimmediate_operand" ""))
13126 (match_dup 1)
13127 (match_dup 2)))
13128 (clobber (reg:CC 17))])]
13129 "TARGET_SSE2"
13130 "#")
13131
13132 (define_insn "*mindf"
13133 [(set (match_operand:DF 0 "register_operand" "=Y#f,f#Y,f#Y")
13134 (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "0,0,f#Y")
13135 (match_operand:DF 2 "nonimmediate_operand" "Ym#f,f#Y,0"))
13136 (match_dup 1)
13137 (match_dup 2)))
13138 (clobber (reg:CC 17))]
13139 "TARGET_SSE2 && TARGET_IEEE_FP"
13140 "#")
13141
13142 (define_insn "*mindf_nonieee"
13143 [(set (match_operand:DF 0 "register_operand" "=Y#f,f#Y")
13144 (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "%0,0")
13145 (match_operand:DF 2 "nonimmediate_operand" "Ym#f,fm#Y"))
13146 (match_dup 1)
13147 (match_dup 2)))
13148 (clobber (reg:CC 17))]
13149 "TARGET_SSE2 && !TARGET_IEEE_FP"
13150 "#")
13151
13152 (define_split
13153 [(set (match_operand:DF 0 "register_operand" "")
13154 (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "")
13155 (match_operand:DF 2 "nonimmediate_operand" ""))
13156 (match_dup 1)
13157 (match_dup 2)))
13158 (clobber (reg:CC 17))]
13159 "SSE_REG_P (operands[0]) && reload_completed"
13160 [(set (match_dup 0)
13161 (if_then_else:DF (lt (match_dup 1)
13162 (match_dup 2))
13163 (match_dup 1)
13164 (match_dup 2)))])
13165
13166 ;; We can't represent the LT test directly. Do this by swapping the operands.
13167 (define_split
13168 [(set (match_operand:DF 0 "register_operand" "")
13169 (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "")
13170 (match_operand:DF 2 "register_operand" ""))
13171 (match_dup 1)
13172 (match_dup 2)))
13173 (clobber (reg:CC 17))]
13174 "FP_REG_P (operands[0]) && reload_completed"
13175 [(set (reg:CCFP 17)
13176 (compare:CCFP (match_dup 2)
13177 (match_dup 2)))
13178 (set (match_dup 0)
13179 (if_then_else:DF (ge (reg:CCFP 17) (const_int 0))
13180 (match_dup 1)
13181 (match_dup 2)))])
13182
13183 (define_insn "*mindf_sse"
13184 [(set (match_operand:DF 0 "register_operand" "=Y")
13185 (if_then_else:DF (lt (match_operand:DF 1 "register_operand" "0")
13186 (match_operand:DF 2 "nonimmediate_operand" "Ym"))
13187 (match_dup 1)
13188 (match_dup 2)))]
13189 "TARGET_SSE2 && reload_completed"
13190 "minsd\\t{%2, %0|%0, %2}"
13191 [(set_attr "type" "sse")
13192 (set_attr "mode" "DF")])
13193
13194 (define_expand "maxsf3"
13195 [(parallel [
13196 (set (match_operand:SF 0 "register_operand" "")
13197 (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "")
13198 (match_operand:SF 2 "nonimmediate_operand" ""))
13199 (match_dup 1)
13200 (match_dup 2)))
13201 (clobber (reg:CC 17))])]
13202 "TARGET_SSE"
13203 "#")
13204
13205 (define_insn "*maxsf"
13206 [(set (match_operand:SF 0 "register_operand" "=x#f,f#x,f#x")
13207 (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "0,0,f#x")
13208 (match_operand:SF 2 "nonimmediate_operand" "xm#f,fm#x,0"))
13209 (match_dup 1)
13210 (match_dup 2)))
13211 (clobber (reg:CC 17))]
13212 "TARGET_SSE && TARGET_IEEE_FP"
13213 "#")
13214
13215 (define_insn "*maxsf_nonieee"
13216 [(set (match_operand:SF 0 "register_operand" "=x#f,f#x")
13217 (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "%0,0")
13218 (match_operand:SF 2 "nonimmediate_operand" "xm#f,fm#x"))
13219 (match_dup 1)
13220 (match_dup 2)))
13221 (clobber (reg:CC 17))]
13222 "TARGET_SSE && !TARGET_IEEE_FP"
13223 "#")
13224
13225 (define_split
13226 [(set (match_operand:SF 0 "register_operand" "")
13227 (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "")
13228 (match_operand:SF 2 "nonimmediate_operand" ""))
13229 (match_dup 1)
13230 (match_dup 2)))
13231 (clobber (reg:CC 17))]
13232 "SSE_REG_P (operands[0]) && reload_completed"
13233 [(set (match_dup 0)
13234 (if_then_else:SF (gt (match_dup 1)
13235 (match_dup 2))
13236 (match_dup 1)
13237 (match_dup 2)))])
13238
13239 (define_split
13240 [(set (match_operand:SF 0 "register_operand" "")
13241 (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "")
13242 (match_operand:SF 2 "register_operand" ""))
13243 (match_dup 1)
13244 (match_dup 2)))
13245 (clobber (reg:CC 17))]
13246 "FP_REG_P (operands[0]) && reload_completed"
13247 [(set (reg:CCFP 17)
13248 (compare:CCFP (match_dup 1)
13249 (match_dup 2)))
13250 (set (match_dup 0)
13251 (if_then_else:SF (gt (reg:CCFP 17) (const_int 0))
13252 (match_dup 1)
13253 (match_dup 2)))])
13254
13255 (define_insn "*maxsf_sse"
13256 [(set (match_operand:SF 0 "register_operand" "=x")
13257 (if_then_else:SF (gt (match_operand:SF 1 "register_operand" "0")
13258 (match_operand:SF 2 "nonimmediate_operand" "xm"))
13259 (match_dup 1)
13260 (match_dup 2)))]
13261 "TARGET_SSE && reload_completed"
13262 "maxss\\t{%2, %0|%0, %2}"
13263 [(set_attr "type" "sse")
13264 (set_attr "mode" "SF")])
13265
13266 (define_expand "maxdf3"
13267 [(parallel [
13268 (set (match_operand:DF 0 "register_operand" "")
13269 (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "")
13270 (match_operand:DF 2 "nonimmediate_operand" ""))
13271 (match_dup 1)
13272 (match_dup 2)))
13273 (clobber (reg:CC 17))])]
13274 "TARGET_SSE2"
13275 "#")
13276
13277 (define_insn "*maxdf"
13278 [(set (match_operand:DF 0 "register_operand" "=Y#f,f#Y,f#Y")
13279 (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "0,0,f#Y")
13280 (match_operand:DF 2 "nonimmediate_operand" "Ym#f,fm#Y,0"))
13281 (match_dup 1)
13282 (match_dup 2)))
13283 (clobber (reg:CC 17))]
13284 "TARGET_SSE2 && TARGET_IEEE_FP"
13285 "#")
13286
13287 (define_insn "*maxdf_nonieee"
13288 [(set (match_operand:DF 0 "register_operand" "=Y#f,f#Y")
13289 (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "%0,0")
13290 (match_operand:DF 2 "nonimmediate_operand" "Ym#f,fm#Y"))
13291 (match_dup 1)
13292 (match_dup 2)))
13293 (clobber (reg:CC 17))]
13294 "TARGET_SSE2 && !TARGET_IEEE_FP"
13295 "#")
13296
13297 (define_split
13298 [(set (match_operand:DF 0 "register_operand" "")
13299 (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "")
13300 (match_operand:DF 2 "nonimmediate_operand" ""))
13301 (match_dup 1)
13302 (match_dup 2)))
13303 (clobber (reg:CC 17))]
13304 "SSE_REG_P (operands[0]) && reload_completed"
13305 [(set (match_dup 0)
13306 (if_then_else:DF (gt (match_dup 1)
13307 (match_dup 2))
13308 (match_dup 1)
13309 (match_dup 2)))])
13310
13311 (define_split
13312 [(set (match_operand:DF 0 "register_operand" "")
13313 (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "")
13314 (match_operand:DF 2 "register_operand" ""))
13315 (match_dup 1)
13316 (match_dup 2)))
13317 (clobber (reg:CC 17))]
13318 "FP_REG_P (operands[0]) && reload_completed"
13319 [(set (reg:CCFP 17)
13320 (compare:CCFP (match_dup 1)
13321 (match_dup 2)))
13322 (set (match_dup 0)
13323 (if_then_else:DF (gt (reg:CCFP 17) (const_int 0))
13324 (match_dup 1)
13325 (match_dup 2)))])
13326
13327 (define_insn "*maxdf_sse"
13328 [(set (match_operand:DF 0 "register_operand" "=Y")
13329 (if_then_else:DF (gt (match_operand:DF 1 "register_operand" "0")
13330 (match_operand:DF 2 "nonimmediate_operand" "Ym"))
13331 (match_dup 1)
13332 (match_dup 2)))]
13333 "TARGET_SSE2 && reload_completed"
13334 "maxsd\\t{%2, %0|%0, %2}"
13335 [(set_attr "type" "sse")
13336 (set_attr "mode" "DF")])
13337 \f
13338 ;; Misc patterns (?)
13339
13340 ;; This pattern exists to put a dependancy on all ebp-based memory accesses.
13341 ;; Otherwise there will be nothing to keep
13342 ;;
13343 ;; [(set (reg ebp) (reg esp))]
13344 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
13345 ;; (clobber (eflags)]
13346 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
13347 ;;
13348 ;; in proper program order.
13349
13350 (define_insn "pro_epilogue_adjust_stack"
13351 [(set (match_operand:SI 0 "register_operand" "=r,r")
13352 (plus:SI (match_operand:SI 1 "register_operand" "0,r")
13353 (match_operand:SI 2 "immediate_operand" "i,i")))
13354 (set (match_operand:SI 3 "register_operand" "+r,r")
13355 (match_dup 3))
13356 (clobber (reg:CC 17))]
13357 ""
13358 "*
13359 {
13360 switch (get_attr_type (insn))
13361 {
13362 case TYPE_IMOV:
13363 return \"mov{l}\\t{%1, %0|%0, %1}\";
13364
13365 case TYPE_ALU:
13366 if (GET_CODE (operands[2]) == CONST_INT
13367 && (INTVAL (operands[2]) == 128
13368 || (INTVAL (operands[2]) < 0
13369 && INTVAL (operands[2]) != -128)))
13370 {
13371 operands[2] = GEN_INT (-INTVAL (operands[2]));
13372 return \"sub{l}\\t{%2, %0|%0, %2}\";
13373 }
13374 return \"add{l}\\t{%2, %0|%0, %2}\";
13375
13376 case TYPE_LEA:
13377 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
13378 return \"lea{l}\\t{%a2, %0|%0, %a2}\";
13379
13380 default:
13381 abort ();
13382 }
13383 }"
13384 [(set (attr "type")
13385 (cond [(eq_attr "alternative" "0")
13386 (const_string "alu")
13387 (match_operand:SI 2 "const0_operand" "")
13388 (const_string "imov")
13389 ]
13390 (const_string "lea")))
13391 (set_attr "mode" "SI")])
13392
13393 ;; Placeholder for the conditional moves. This one is split eighter to SSE
13394 ;; based moves emulation or to usual cmove sequence. Little bit unfortunate
13395 ;; fact is that compares supported by the cmp??ss instructions are exactly
13396 ;; swapped of those supported by cmove sequence.
13397 ;; The EQ/NE comparisons also needs bit care, since they are not directly
13398 ;; supported by i387 comparisons and we do need to emit two conditional moves
13399 ;; in tandem.
13400
13401 (define_insn "sse_movsfcc"
13402 [(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")
13403 (if_then_else:SF (match_operator 1 "sse_comparison_operator"
13404 [(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")
13405 (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")])
13406 (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")
13407 (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")))
13408 (clobber (match_scratch:SF 6 "=2,&4,X,X,X,X,X,X,X,X"))
13409 (clobber (reg:CC 17))]
13410 "TARGET_SSE
13411 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)
13412 && (!TARGET_IEEE_FP
13413 || (GET_CODE (operands[1]) != EQ && GET_CODE (operands[1]) != NE))"
13414 "#")
13415
13416 (define_insn "sse_movsfcc_eq"
13417 [(set (match_operand:SF 0 "register_operand" "=&x#rf,x#rf,?f#xr,?f#xr,?r#xf,?r#xf")
13418 (if_then_else:SF (eq (match_operand:SF 3 "nonimmediate_operand" "%0#fx,x#fx,f#x,xm#f,f#x,xm#f")
13419 (match_operand:SF 4 "nonimmediate_operand" "xm#f,xm#f,f#x,x#f,f#x,x#f"))
13420 (match_operand:SF 1 "nonimmediate_operand" "x#fr,0#fr,0#fx,0#fx,0#rx,0#rx")
13421 (match_operand:SF 2 "nonimmediate_operand" "x#fr,x#fr,f#fx,f#fx,rm#rx,rm#rx")))
13422 (clobber (match_scratch:SF 5 "=1,&4,X,X,X,X"))
13423 (clobber (reg:CC 17))]
13424 "TARGET_SSE
13425 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
13426 "#")
13427
13428 (define_insn "sse_movdfcc"
13429 [(set (match_operand:DF 0 "register_operand" "=&x#rf,x#rf,?f#xr,?f#xr,?f#xr,?f#xr,?r#xf,?r#xf,?r#xf,?r#xf")
13430 (if_then_else:DF (match_operator 1 "sse_comparison_operator"
13431 [(match_operand:DF 4 "nonimmediate_operand" "0#fx,x#fx,f#x,f#x,xm#f,xm#f,f#x,f#x,xm#f,xm#f")
13432 (match_operand:DF 5 "nonimmediate_operand" "xm#f,xm#f,f#x,f#x,x#f,x#f,f#x,f#x,x#f,x#f")])
13433 (match_operand:DF 2 "nonimmediate_operand" "x#fr,0#fr,f#fx,0#fx,f#fx,0#fx,rm#rx,0#rx,rm#rx,0#rx")
13434 (match_operand:DF 3 "nonimmediate_operand" "x#fr,x#fr,0#fx,f#fx,0#fx,f#fx,0#fx,rm#rx,0#rx,rm#rx")))
13435 (clobber (match_scratch:DF 6 "=2,&4,X,X,X,X,X,X,X,X"))
13436 (clobber (reg:CC 17))]
13437 "TARGET_SSE2
13438 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)
13439 && (!TARGET_IEEE_FP
13440 || (GET_CODE (operands[1]) != EQ && GET_CODE (operands[1]) != NE))"
13441 "#")
13442
13443 (define_insn "sse_movdfcc_eq"
13444 [(set (match_operand:DF 0 "register_operand" "=&x#rf,x#rf,?f#xr,?f#xr,?r#xf,?r#xf")
13445 (if_then_else:DF (eq (match_operand:DF 3 "nonimmediate_operand" "%0#fx,x#fx,f#x,xm#f,f#x,xm#f")
13446 (match_operand:DF 4 "nonimmediate_operand" "xm#f,xm#f,f#x,x#f,f#x,x#f"))
13447 (match_operand:DF 1 "nonimmediate_operand" "x#fr,0#fr,0#fx,0#fx,0#rx,0#rx")
13448 (match_operand:DF 2 "nonimmediate_operand" "x#fr,x#fr,f#fx,f#fx,rm#rx,rm#rx")))
13449 (clobber (match_scratch:DF 5 "=1,&3,X,X,X,X"))
13450 (clobber (reg:CC 17))]
13451 "TARGET_SSE
13452 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
13453 "#")
13454
13455 ;; For non-sse moves just expand the usual cmove sequence.
13456 (define_split
13457 [(set (match_operand 0 "register_operand" "")
13458 (if_then_else (match_operator 1 "comparison_operator"
13459 [(match_operand 4 "nonimmediate_operand" "")
13460 (match_operand 5 "register_operand" "")])
13461 (match_operand 2 "nonimmediate_operand" "")
13462 (match_operand 3 "nonimmediate_operand" "")))
13463 (clobber (match_operand 6 "" ""))
13464 (clobber (reg:CC 17))]
13465 "!SSE_REG_P (operands[0]) && reload_completed
13466 && VALID_SSE_REG_MODE (GET_MODE (operands[0]))"
13467 [(const_int 0)]
13468 "
13469 {
13470 ix86_compare_op0 = operands[5];
13471 ix86_compare_op1 = operands[4];
13472 operands[1] = gen_rtx_fmt_ee (swap_condition (GET_CODE (operands[1])),
13473 VOIDmode, operands[5], operands[4]);
13474 ix86_expand_fp_movcc (operands);
13475 DONE;
13476 }")
13477
13478 ;; Split SSE based conditional move into seqence:
13479 ;; cmpCC op0, op4 - set op0 to 0 or ffffffff depending on the comparison
13480 ;; and op2, op0 - zero op2 if comparison was false
13481 ;; nand op0, op3 - load op3 to op0 if comparison was false
13482 ;; or op2, op0 - get the non-zero one into the result.
13483 (define_split
13484 [(set (match_operand 0 "register_operand" "")
13485 (if_then_else (match_operator 1 "sse_comparison_operator"
13486 [(match_operand 4 "register_operand" "")
13487 (match_operand 5 "nonimmediate_operand" "")])
13488 (match_operand 2 "register_operand" "")
13489 (match_operand 3 "register_operand" "")))
13490 (clobber (match_operand 6 "" ""))
13491 (clobber (reg:CC 17))]
13492 "SSE_REG_P (operands[0]) && reload_completed"
13493 [(set (match_dup 4) (match_op_dup 1 [(match_dup 4) (match_dup 5)]))
13494 (set (subreg:TI (match_dup 2) 0) (and:TI (subreg:TI (match_dup 2) 0)
13495 (subreg:TI (match_dup 0) 0)))
13496 (set (subreg:TI (match_dup 4) 0) (and:TI (not:TI (subreg:TI (match_dup 0) 0))
13497 (subreg:TI (match_dup 3) 0)))
13498 (set (subreg:TI (match_dup 0) 0) (ior:TI (subreg:TI (match_dup 6) 0)
13499 (subreg:TI (match_dup 7) 0)))]
13500 "
13501 {
13502 PUT_MODE (operands[1], GET_MODE (operands[0]));
13503 if (rtx_equal_p (operands[0], operands[4]))
13504 operands[6] = operands[4], operands[7] = operands[2];
13505 else
13506 operands[6] = operands[2], operands[7] = operands[0];
13507 }")
13508
13509 ;; Special case of conditional move we can handle effectivly.
13510 ;; Do not brother with the integer/floating point case, since these are
13511 ;; bot considerably slower, unlike in the generic case.
13512 (define_insn "*sse_movsfcc_const0_1"
13513 [(set (match_operand:SF 0 "register_operand" "=x")
13514 (if_then_else:SF (match_operator 1 "sse_comparison_operator"
13515 [(match_operand:SF 4 "register_operand" "0")
13516 (match_operand:SF 5 "nonimmediate_operand" "xm")])
13517 (match_operand:SF 2 "register_operand" "x")
13518 (match_operand:SF 3 "const0_operand" "X")))]
13519 "TARGET_SSE"
13520 "#")
13521
13522 (define_insn "*sse_movsfcc_const0_2"
13523 [(set (match_operand:SF 0 "register_operand" "=x")
13524 (if_then_else:SF (match_operator 1 "sse_comparison_operator"
13525 [(match_operand:SF 4 "register_operand" "0")
13526 (match_operand:SF 5 "nonimmediate_operand" "xm")])
13527 (match_operand:SF 2 "const0_operand" "x")
13528 (match_operand:SF 3 "register_operand" "X")))]
13529 "TARGET_SSE"
13530 "#")
13531
13532 (define_insn "*sse_movsfcc_const0_3"
13533 [(set (match_operand:SF 0 "register_operand" "=x")
13534 (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
13535 [(match_operand:SF 4 "nonimmediate_operand" "xm")
13536 (match_operand:SF 5 "register_operand" "0")])
13537 (match_operand:SF 2 "register_operand" "x")
13538 (match_operand:SF 3 "const0_operand" "X")))]
13539 "TARGET_SSE"
13540 "#")
13541
13542 (define_insn "*sse_movsfcc_const0_4"
13543 [(set (match_operand:SF 0 "register_operand" "=x")
13544 (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
13545 [(match_operand:SF 4 "nonimmediate_operand" "xm")
13546 (match_operand:SF 5 "register_operand" "0")])
13547 (match_operand:SF 2 "const0_operand" "x")
13548 (match_operand:SF 3 "register_operand" "X")))]
13549 "TARGET_SSE"
13550 "#")
13551
13552 (define_insn "*sse_movdfcc_const0_1"
13553 [(set (match_operand:SF 0 "register_operand" "=x")
13554 (if_then_else:SF (match_operator 1 "sse_comparison_operator"
13555 [(match_operand:SF 4 "register_operand" "0")
13556 (match_operand:SF 5 "nonimmediate_operand" "xm")])
13557 (match_operand:SF 2 "register_operand" "x")
13558 (match_operand:SF 3 "const0_operand" "X")))]
13559 "TARGET_SSE2"
13560 "#")
13561
13562 (define_insn "*sse_movdfcc_const0_2"
13563 [(set (match_operand:SF 0 "register_operand" "=x")
13564 (if_then_else:SF (match_operator 1 "sse_comparison_operator"
13565 [(match_operand:SF 4 "register_operand" "0")
13566 (match_operand:SF 5 "nonimmediate_operand" "xm")])
13567 (match_operand:SF 2 "const0_operand" "x")
13568 (match_operand:SF 3 "register_operand" "X")))]
13569 "TARGET_SSE2"
13570 "#")
13571
13572 (define_insn "*sse_movdfcc_const0_3"
13573 [(set (match_operand:SF 0 "register_operand" "=x")
13574 (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
13575 [(match_operand:SF 4 "nonimmediate_operand" "xm")
13576 (match_operand:SF 5 "register_operand" "0")])
13577 (match_operand:SF 2 "register_operand" "x")
13578 (match_operand:SF 3 "const0_operand" "X")))]
13579 "TARGET_SSE2"
13580 "#")
13581
13582 (define_insn "*sse_movdfcc_const0_4"
13583 [(set (match_operand:SF 0 "register_operand" "=x")
13584 (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
13585 [(match_operand:SF 4 "nonimmediate_operand" "xm")
13586 (match_operand:SF 5 "register_operand" "0")])
13587 (match_operand:SF 2 "const0_operand" "x")
13588 (match_operand:SF 3 "register_operand" "X")))]
13589 "TARGET_SSE2"
13590 "#")
13591
13592 (define_split
13593 [(set (match_operand 0 "register_operand" "")
13594 (if_then_else (match_operator 1 "comparison_operator"
13595 [(match_operand 4 "register_operand" "")
13596 (match_operand 5 "nonimmediate_operand" "")])
13597 (match_operand 2 "nonmemory_operand" "")
13598 (match_operand 3 "nonmemory_operand" "")))]
13599 "SSE_REG_P (operands[0]) && reload_completed
13600 && (const0_operand (operands[2], GET_MODE (operands[0]))
13601 || const0_operand (operands[3], GET_MODE (operands[0])))"
13602 [(set (match_dup 0) (match_op_dup 1 [(match_dup 0) (match_dup 5)]))
13603 (set (subreg:TI (match_dup 0) 0) (and:TI (match_dup 6)
13604 (subreg:TI (match_dup 7) 0)))]
13605 "
13606 {
13607 PUT_MODE (operands[1], GET_MODE (operands[0]));
13608 if (!sse_comparison_operator (operands[1], VOIDmode))
13609 {
13610 rtx tmp = operands[5];
13611 operands[5] = operands[4];
13612 operands[4] = tmp;
13613 PUT_CODE (operands[1], swap_condition (GET_CODE (operands[1])));
13614 }
13615 if (const0_operand (operands[2], GET_MODE (operands[0])))
13616 {
13617 operands[7] = operands[3];
13618 operands[6] = gen_rtx_NOT (TImode, gen_rtx_SUBREG (TImode, operands[0],
13619 0));
13620 }
13621 else
13622 {
13623 operands[7] = operands[2];
13624 operands[6] = gen_rtx_SUBREG (TImode, operands[0], 0);
13625 }
13626 }")
13627
13628 (define_insn "allocate_stack_worker"
13629 [(unspec:SI [(match_operand:SI 0 "register_operand" "a")] 3)
13630 (set (reg:SI 7) (minus:SI (reg:SI 7) (match_dup 0)))
13631 (clobber (match_dup 0))
13632 (clobber (reg:CC 17))]
13633 "TARGET_STACK_PROBE"
13634 "call\\t__alloca"
13635 [(set_attr "type" "multi")
13636 (set_attr "length" "5")])
13637
13638 (define_expand "allocate_stack"
13639 [(parallel [(set (match_operand:SI 0 "register_operand" "=r")
13640 (minus:SI (reg:SI 7)
13641 (match_operand:SI 1 "general_operand" "")))
13642 (clobber (reg:CC 17))])
13643 (parallel [(set (reg:SI 7)
13644 (minus:SI (reg:SI 7) (match_dup 1)))
13645 (clobber (reg:CC 17))])]
13646 "TARGET_STACK_PROBE"
13647 "
13648 {
13649 #ifdef CHECK_STACK_LIMIT
13650 if (GET_CODE (operands[1]) == CONST_INT
13651 && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
13652 emit_insn (gen_subsi3 (stack_pointer_rtx, stack_pointer_rtx,
13653 operands[1]));
13654 else
13655 #endif
13656 emit_insn (gen_allocate_stack_worker (copy_to_mode_reg (SImode,
13657 operands[1])));
13658
13659 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
13660 DONE;
13661 }")
13662
13663 (define_expand "exception_receiver"
13664 [(const_int 0)]
13665 "flag_pic"
13666 "
13667 {
13668 load_pic_register ();
13669 DONE;
13670 }")
13671
13672 (define_expand "builtin_setjmp_receiver"
13673 [(label_ref (match_operand 0 "" ""))]
13674 "flag_pic"
13675 "
13676 {
13677 load_pic_register ();
13678 DONE;
13679 }")
13680 \f
13681 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
13682
13683 (define_split
13684 [(set (match_operand 0 "register_operand" "")
13685 (match_operator 3 "promotable_binary_operator"
13686 [(match_operand 1 "register_operand" "")
13687 (match_operand 2 "aligned_operand" "")]))
13688 (clobber (reg:CC 17))]
13689 "! TARGET_PARTIAL_REG_STALL && reload_completed
13690 && ((GET_MODE (operands[0]) == HImode
13691 && (!optimize_size || GET_CODE (operands[2]) != CONST_INT
13692 || CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')))
13693 || (GET_MODE (operands[0]) == QImode
13694 && (TARGET_PROMOTE_QImode || optimize_size)))"
13695 [(parallel [(set (match_dup 0)
13696 (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
13697 (clobber (reg:CC 17))])]
13698 "operands[0] = gen_lowpart (SImode, operands[0]);
13699 operands[1] = gen_lowpart (SImode, operands[1]);
13700 if (GET_CODE (operands[3]) != ASHIFT)
13701 operands[2] = gen_lowpart (SImode, operands[2]);
13702 PUT_MODE (operands[3], SImode);")
13703
13704 (define_split
13705 [(set (reg 17)
13706 (compare (and (match_operand 1 "aligned_operand" "")
13707 (match_operand 2 "const_int_operand" ""))
13708 (const_int 0)))
13709 (set (match_operand 0 "register_operand" "")
13710 (and (match_dup 1) (match_dup 2)))]
13711 "! TARGET_PARTIAL_REG_STALL && reload_completed
13712 && ix86_match_ccmode (insn, CCNOmode)
13713 && (GET_MODE (operands[0]) == HImode
13714 || (GET_MODE (operands[0]) == QImode
13715 && (TARGET_PROMOTE_QImode || optimize_size)))"
13716 [(parallel [(set (reg:CCNO 17)
13717 (compare:CCNO (and:SI (match_dup 1) (match_dup 2))
13718 (const_int 0)))
13719 (set (match_dup 0)
13720 (and:SI (match_dup 1) (match_dup 2)))])]
13721 "operands[2]
13722 = GEN_INT (INTVAL (operands[2]) & GET_MODE_MASK (GET_MODE (operands[0])));
13723 operands[0] = gen_lowpart (SImode, operands[0]);
13724 operands[1] = gen_lowpart (SImode, operands[1]);")
13725
13726 (define_split
13727 [(set (reg 17)
13728 (compare (and (match_operand 0 "aligned_operand" "")
13729 (match_operand 1 "const_int_operand" ""))
13730 (const_int 0)))]
13731 "! TARGET_PARTIAL_REG_STALL && reload_completed
13732 && ix86_match_ccmode (insn, CCNOmode)
13733 && (GET_MODE (operands[0]) == HImode
13734 || (GET_MODE (operands[0]) == QImode
13735 && (TARGET_PROMOTE_QImode || optimize_size)))"
13736 [(set (reg:CCNO 17)
13737 (compare:CCNO (and:SI (match_dup 0) (match_dup 1))
13738 (const_int 0)))]
13739 "operands[1]
13740 = GEN_INT (INTVAL (operands[1]) & GET_MODE_MASK (GET_MODE (operands[0])));
13741 operands[0] = gen_lowpart (SImode, operands[0]);")
13742
13743 (define_split
13744 [(set (match_operand 0 "register_operand" "")
13745 (neg (match_operand 1 "register_operand" "")))
13746 (clobber (reg:CC 17))]
13747 "! TARGET_PARTIAL_REG_STALL && reload_completed
13748 && (GET_MODE (operands[0]) == HImode
13749 || (GET_MODE (operands[0]) == QImode
13750 && (TARGET_PROMOTE_QImode || optimize_size)))"
13751 [(parallel [(set (match_dup 0)
13752 (neg:SI (match_dup 1)))
13753 (clobber (reg:CC 17))])]
13754 "operands[0] = gen_lowpart (SImode, operands[0]);
13755 operands[1] = gen_lowpart (SImode, operands[1]);")
13756
13757 (define_split
13758 [(set (match_operand 0 "register_operand" "")
13759 (not (match_operand 1 "register_operand" "")))]
13760 "! TARGET_PARTIAL_REG_STALL && reload_completed
13761 && (GET_MODE (operands[0]) == HImode
13762 || (GET_MODE (operands[0]) == QImode
13763 && (TARGET_PROMOTE_QImode || optimize_size)))"
13764 [(set (match_dup 0)
13765 (not:SI (match_dup 1)))]
13766 "operands[0] = gen_lowpart (SImode, operands[0]);
13767 operands[1] = gen_lowpart (SImode, operands[1]);")
13768
13769 (define_split
13770 [(set (match_operand 0 "register_operand" "")
13771 (if_then_else (match_operator 1 "comparison_operator"
13772 [(reg 17) (const_int 0)])
13773 (match_operand 2 "register_operand" "")
13774 (match_operand 3 "register_operand" "")))]
13775 "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE
13776 && (GET_MODE (operands[0]) == HImode
13777 || (GET_MODE (operands[0]) == QImode
13778 && (TARGET_PROMOTE_QImode || optimize_size)))"
13779 [(set (match_dup 0)
13780 (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
13781 "operands[0] = gen_lowpart (SImode, operands[0]);
13782 operands[2] = gen_lowpart (SImode, operands[2]);
13783 operands[3] = gen_lowpart (SImode, operands[3]);")
13784
13785 \f
13786 ;; RTL Peephole optimizations, run before sched2. These primarily look to
13787 ;; transform a complex memory operation into two memory to register operations.
13788
13789 ;; Don't push memory operands
13790 (define_peephole2
13791 [(set (match_operand:SI 0 "push_operand" "")
13792 (match_operand:SI 1 "memory_operand" ""))
13793 (match_scratch:SI 2 "r")]
13794 "! optimize_size && ! TARGET_PUSH_MEMORY"
13795 [(set (match_dup 2) (match_dup 1))
13796 (set (match_dup 0) (match_dup 2))]
13797 "")
13798
13799 ;; We need to handle SFmode only, because DFmode and XFmode is split to
13800 ;; SImode pushes.
13801 (define_peephole2
13802 [(set (match_operand:SF 0 "push_operand" "")
13803 (match_operand:SF 1 "memory_operand" ""))
13804 (match_scratch:SF 2 "r")]
13805 "! optimize_size && ! TARGET_PUSH_MEMORY"
13806 [(set (match_dup 2) (match_dup 1))
13807 (set (match_dup 0) (match_dup 2))]
13808 "")
13809
13810 (define_peephole2
13811 [(set (match_operand:HI 0 "push_operand" "")
13812 (match_operand:HI 1 "memory_operand" ""))
13813 (match_scratch:HI 2 "r")]
13814 "! optimize_size && ! TARGET_PUSH_MEMORY"
13815 [(set (match_dup 2) (match_dup 1))
13816 (set (match_dup 0) (match_dup 2))]
13817 "")
13818
13819 (define_peephole2
13820 [(set (match_operand:QI 0 "push_operand" "")
13821 (match_operand:QI 1 "memory_operand" ""))
13822 (match_scratch:QI 2 "q")]
13823 "! optimize_size && ! TARGET_PUSH_MEMORY"
13824 [(set (match_dup 2) (match_dup 1))
13825 (set (match_dup 0) (match_dup 2))]
13826 "")
13827
13828 ;; Don't move an immediate directly to memory when the instruction
13829 ;; gets too big.
13830 (define_peephole2
13831 [(match_scratch:SI 1 "r")
13832 (set (match_operand:SI 0 "memory_operand" "")
13833 (const_int 0))]
13834 "! optimize_size
13835 && ! TARGET_USE_MOV0
13836 && TARGET_SPLIT_LONG_MOVES
13837 && get_attr_length (insn) >= ix86_cost->large_insn
13838 && peep2_regno_dead_p (0, FLAGS_REG)"
13839 [(parallel [(set (match_dup 1) (const_int 0))
13840 (clobber (reg:CC 17))])
13841 (set (match_dup 0) (match_dup 1))]
13842 "")
13843
13844 (define_peephole2
13845 [(match_scratch:HI 1 "r")
13846 (set (match_operand:HI 0 "memory_operand" "")
13847 (const_int 0))]
13848 "! optimize_size
13849 && ! TARGET_USE_MOV0
13850 && TARGET_SPLIT_LONG_MOVES
13851 && get_attr_length (insn) >= ix86_cost->large_insn
13852 && peep2_regno_dead_p (0, FLAGS_REG)"
13853 [(parallel [(set (match_dup 2) (const_int 0))
13854 (clobber (reg:CC 17))])
13855 (set (match_dup 0) (match_dup 1))]
13856 "operands[2] = gen_rtx_REG (SImode, true_regnum (operands[1]));")
13857
13858 (define_peephole2
13859 [(match_scratch:QI 1 "q")
13860 (set (match_operand:QI 0 "memory_operand" "")
13861 (const_int 0))]
13862 "! optimize_size
13863 && ! TARGET_USE_MOV0
13864 && TARGET_SPLIT_LONG_MOVES
13865 && get_attr_length (insn) >= ix86_cost->large_insn
13866 && peep2_regno_dead_p (0, FLAGS_REG)"
13867 [(parallel [(set (match_dup 2) (const_int 0))
13868 (clobber (reg:CC 17))])
13869 (set (match_dup 0) (match_dup 1))]
13870 "operands[2] = gen_rtx_REG (SImode, true_regnum (operands[1]));")
13871
13872 (define_peephole2
13873 [(match_scratch:SI 2 "r")
13874 (set (match_operand:SI 0 "memory_operand" "")
13875 (match_operand:SI 1 "immediate_operand" ""))]
13876 "! optimize_size
13877 && get_attr_length (insn) >= ix86_cost->large_insn
13878 && TARGET_SPLIT_LONG_MOVES"
13879 [(set (match_dup 2) (match_dup 1))
13880 (set (match_dup 0) (match_dup 2))]
13881 "")
13882
13883 (define_peephole2
13884 [(match_scratch:HI 2 "r")
13885 (set (match_operand:HI 0 "memory_operand" "")
13886 (match_operand:HI 1 "immediate_operand" ""))]
13887 "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
13888 && TARGET_SPLIT_LONG_MOVES"
13889 [(set (match_dup 2) (match_dup 1))
13890 (set (match_dup 0) (match_dup 2))]
13891 "")
13892
13893 (define_peephole2
13894 [(match_scratch:QI 2 "q")
13895 (set (match_operand:QI 0 "memory_operand" "")
13896 (match_operand:QI 1 "immediate_operand" ""))]
13897 "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
13898 && TARGET_SPLIT_LONG_MOVES"
13899 [(set (match_dup 2) (match_dup 1))
13900 (set (match_dup 0) (match_dup 2))]
13901 "")
13902
13903 ;; Don't compare memory with zero, load and use a test instead.
13904 (define_peephole2
13905 [(set (reg 17)
13906 (compare (match_operand:SI 0 "memory_operand" "")
13907 (const_int 0)))
13908 (match_scratch:SI 3 "r")]
13909 "ix86_match_ccmode (insn, CCNOmode) && ! optimize_size"
13910 [(set (match_dup 3) (match_dup 0))
13911 (set (reg:CCNO 17) (compare:CCNO (match_dup 3) (const_int 0)))]
13912 "")
13913
13914 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer.
13915 ;; Don't split NOTs with a displacement operand, because resulting XOR
13916 ;; will not be pariable anyway.
13917 ;;
13918 ;; On AMD K6, NOT is vector decoded with memory operand that can not be
13919 ;; represented using a modRM byte. The XOR replacement is long decoded,
13920 ;; so this split helps here as well.
13921 ;;
13922 ;; Note: Can't do this as a regular split because we can't get proper
13923 ;; lifetime information then.
13924
13925 (define_peephole2
13926 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
13927 (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))]
13928 "!optimize_size
13929 && peep2_regno_dead_p (0, FLAGS_REG)
13930 && ((TARGET_PENTIUM
13931 && (GET_CODE (operands[0]) != MEM
13932 || !memory_displacement_operand (operands[0], SImode)))
13933 || (TARGET_K6 && long_memory_operand (operands[0], SImode)))"
13934 [(parallel [(set (match_dup 0)
13935 (xor:SI (match_dup 1) (const_int -1)))
13936 (clobber (reg:CC 17))])]
13937 "")
13938
13939 (define_peephole2
13940 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
13941 (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))]
13942 "!optimize_size
13943 && peep2_regno_dead_p (0, FLAGS_REG)
13944 && ((TARGET_PENTIUM
13945 && (GET_CODE (operands[0]) != MEM
13946 || !memory_displacement_operand (operands[0], HImode)))
13947 || (TARGET_K6 && long_memory_operand (operands[0], HImode)))"
13948 [(parallel [(set (match_dup 0)
13949 (xor:HI (match_dup 1) (const_int -1)))
13950 (clobber (reg:CC 17))])]
13951 "")
13952
13953 (define_peephole2
13954 [(set (match_operand:QI 0 "nonimmediate_operand" "=rm")
13955 (not:QI (match_operand:QI 1 "nonimmediate_operand" "0")))]
13956 "!optimize_size
13957 && peep2_regno_dead_p (0, FLAGS_REG)
13958 && ((TARGET_PENTIUM
13959 && (GET_CODE (operands[0]) != MEM
13960 || !memory_displacement_operand (operands[0], QImode)))
13961 || (TARGET_K6 && long_memory_operand (operands[0], QImode)))"
13962 [(parallel [(set (match_dup 0)
13963 (xor:QI (match_dup 1) (const_int -1)))
13964 (clobber (reg:CC 17))])]
13965 "")
13966
13967 ;; Non pairable "test imm, reg" instructions can be translated to
13968 ;; "and imm, reg" if reg dies. The "and" form is also shorter (one
13969 ;; byte opcode instead of two, have a short form for byte operands),
13970 ;; so do it for other CPUs as well. Given that the value was dead,
13971 ;; this should not create any new dependancies. Pass on the sub-word
13972 ;; versions if we're concerned about partial register stalls.
13973
13974 (define_peephole2
13975 [(set (reg 17)
13976 (compare (and:SI (match_operand:SI 0 "register_operand" "")
13977 (match_operand:SI 1 "immediate_operand" ""))
13978 (const_int 0)))]
13979 "ix86_match_ccmode (insn, CCNOmode)
13980 && (true_regnum (operands[0]) != 0
13981 || CONST_OK_FOR_LETTER_P (INTVAL (operands[1]), 'K'))
13982 && find_regno_note (insn, REG_DEAD, true_regnum (operands[0]))"
13983 [(parallel
13984 [(set (reg:CCNO 17)
13985 (compare:CCNO (and:SI (match_dup 0)
13986 (match_dup 1))
13987 (const_int 0)))
13988 (set (match_dup 0)
13989 (and:SI (match_dup 0) (match_dup 1)))])]
13990 "")
13991
13992 ;; We don't need to handle HImode case, because it will be promoted to SImode
13993 ;; on ! TARGET_PARTIAL_REG_STALL
13994
13995 (define_peephole2
13996 [(set (reg 17)
13997 (compare (and:QI (match_operand:QI 0 "register_operand" "")
13998 (match_operand:QI 1 "immediate_operand" ""))
13999 (const_int 0)))]
14000 "! TARGET_PARTIAL_REG_STALL
14001 && ix86_match_ccmode (insn, CCNOmode)
14002 && true_regnum (operands[0]) != 0
14003 && find_regno_note (insn, REG_DEAD, true_regnum (operands[0]))"
14004 [(parallel
14005 [(set (reg:CCNO 17)
14006 (compare:CCNO (and:QI (match_dup 0)
14007 (match_dup 1))
14008 (const_int 0)))
14009 (set (match_dup 0)
14010 (and:QI (match_dup 0) (match_dup 1)))])]
14011 "")
14012
14013 (define_peephole2
14014 [(set (reg 17)
14015 (compare
14016 (and:SI
14017 (zero_extract:SI
14018 (match_operand 0 "ext_register_operand" "q")
14019 (const_int 8)
14020 (const_int 8))
14021 (match_operand 1 "const_int_operand" "n"))
14022 (const_int 0)))]
14023 "! TARGET_PARTIAL_REG_STALL
14024 && ix86_match_ccmode (insn, CCNOmode)
14025 && true_regnum (operands[0]) != 0
14026 && find_regno_note (insn, REG_DEAD, true_regnum (operands[0]))"
14027 [(parallel [(set (reg:CCNO 17)
14028 (compare:CCNO
14029 (and:SI
14030 (zero_extract:SI
14031 (match_dup 0)
14032 (const_int 8)
14033 (const_int 8))
14034 (match_dup 1))
14035 (const_int 0)))
14036 (set (zero_extract:SI (match_dup 0)
14037 (const_int 8)
14038 (const_int 8))
14039 (and:SI
14040 (zero_extract:SI
14041 (match_dup 0)
14042 (const_int 8)
14043 (const_int 8))
14044 (match_dup 1)))])]
14045 "")
14046
14047 ;; Don't do logical operations with memory inputs.
14048 (define_peephole2
14049 [(match_scratch:SI 2 "r")
14050 (parallel [(set (match_operand:SI 0 "register_operand" "")
14051 (match_operator:SI 3 "arith_or_logical_operator"
14052 [(match_dup 0)
14053 (match_operand:SI 1 "memory_operand" "")]))
14054 (clobber (reg:CC 17))])]
14055 "! optimize_size && ! TARGET_READ_MODIFY"
14056 [(set (match_dup 2) (match_dup 1))
14057 (parallel [(set (match_dup 0)
14058 (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
14059 (clobber (reg:CC 17))])]
14060 "")
14061
14062 (define_peephole2
14063 [(match_scratch:SI 2 "r")
14064 (parallel [(set (match_operand:SI 0 "register_operand" "")
14065 (match_operator:SI 3 "arith_or_logical_operator"
14066 [(match_operand:SI 1 "memory_operand" "")
14067 (match_dup 0)]))
14068 (clobber (reg:CC 17))])]
14069 "! optimize_size && ! TARGET_READ_MODIFY"
14070 [(set (match_dup 2) (match_dup 1))
14071 (parallel [(set (match_dup 0)
14072 (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
14073 (clobber (reg:CC 17))])]
14074 "")
14075
14076 ; Don't do logical operations with memory outputs
14077 ;
14078 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
14079 ; instruction into two 1-uop insns plus a 2-uop insn. That last has
14080 ; the same decoder scheduling characteristics as the original.
14081
14082 (define_peephole2
14083 [(match_scratch:SI 2 "r")
14084 (parallel [(set (match_operand:SI 0 "memory_operand" "")
14085 (match_operator:SI 3 "arith_or_logical_operator"
14086 [(match_dup 0)
14087 (match_operand:SI 1 "nonmemory_operand" "")]))
14088 (clobber (reg:CC 17))])]
14089 "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
14090 [(set (match_dup 2) (match_dup 0))
14091 (parallel [(set (match_dup 2)
14092 (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
14093 (clobber (reg:CC 17))])
14094 (set (match_dup 0) (match_dup 2))]
14095 "")
14096
14097 (define_peephole2
14098 [(match_scratch:SI 2 "r")
14099 (parallel [(set (match_operand:SI 0 "memory_operand" "")
14100 (match_operator:SI 3 "arith_or_logical_operator"
14101 [(match_operand:SI 1 "nonmemory_operand" "")
14102 (match_dup 0)]))
14103 (clobber (reg:CC 17))])]
14104 "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
14105 [(set (match_dup 2) (match_dup 0))
14106 (parallel [(set (match_dup 2)
14107 (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
14108 (clobber (reg:CC 17))])
14109 (set (match_dup 0) (match_dup 2))]
14110 "")
14111
14112 ;; Attempt to always use XOR for zeroing registers.
14113 (define_peephole2
14114 [(set (match_operand 0 "register_operand" "")
14115 (const_int 0))]
14116 "(GET_MODE (operands[0]) == QImode
14117 || GET_MODE (operands[0]) == HImode
14118 || GET_MODE (operands[0]) == SImode)
14119 && (! TARGET_USE_MOV0 || optimize_size)
14120 && peep2_regno_dead_p (0, FLAGS_REG)"
14121 [(parallel [(set (match_dup 0) (const_int 0))
14122 (clobber (reg:CC 17))])]
14123 "operands[0] = gen_rtx_REG (SImode, true_regnum (operands[0]));")
14124
14125 (define_peephole2
14126 [(set (strict_low_part (match_operand 0 "register_operand" ""))
14127 (const_int 0))]
14128 "(GET_MODE (operands[0]) == QImode
14129 || GET_MODE (operands[0]) == HImode)
14130 && (! TARGET_USE_MOV0 || optimize_size)
14131 && peep2_regno_dead_p (0, FLAGS_REG)"
14132 [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
14133 (clobber (reg:CC 17))])])
14134
14135 ;; For HI and SI modes, or $-1,reg is smaller than mov $-1,reg.
14136 (define_peephole2
14137 [(set (match_operand 0 "register_operand" "")
14138 (const_int -1))]
14139 "(GET_MODE (operands[0]) == HImode
14140 || GET_MODE (operands[0]) == SImode)
14141 && (optimize_size || TARGET_PENTIUM)
14142 && peep2_regno_dead_p (0, FLAGS_REG)"
14143 [(parallel [(set (match_dup 0) (const_int -1))
14144 (clobber (reg:CC 17))])]
14145 "operands[0] = gen_rtx_REG (SImode, true_regnum (operands[0]));")
14146
14147 ;; Attempt to convert simple leas to adds. These can be created by
14148 ;; move expanders.
14149 (define_peephole2
14150 [(set (match_operand:SI 0 "register_operand" "")
14151 (plus:SI (match_dup 0)
14152 (match_operand:SI 1 "nonmemory_operand" "")))]
14153 "peep2_regno_dead_p (0, FLAGS_REG)"
14154 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
14155 (clobber (reg:CC 17))])]
14156 "")
14157
14158 (define_peephole2
14159 [(set (match_operand:SI 0 "register_operand" "")
14160 (mult:SI (match_dup 0)
14161 (match_operand:SI 1 "immediate_operand" "")))]
14162 "exact_log2 (INTVAL (operands[1])) >= 0
14163 && peep2_regno_dead_p (0, FLAGS_REG)"
14164 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
14165 (clobber (reg:CC 17))])]
14166 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
14167
14168 ;; The ESP adjustments can be done by the push and pop instructions. Resulting
14169 ;; code is shorter, since push is only 1 byte, while add imm, %esp 3 bytes. On
14170 ;; many CPUs it is also faster, since special hardware to avoid esp
14171 ;; dependancies is present.
14172
14173 ;; While some of these converisons may be done using splitters, we use peepholes
14174 ;; in order to allow combine_stack_adjustments pass to see nonobfuscated RTL.
14175
14176 ;; Convert prologue esp substractions to push.
14177 ;; We need register to push. In order to keep verify_flow_info happy we have
14178 ;; two choices
14179 ;; - use scratch and clobber it in order to avoid dependencies
14180 ;; - use already live register
14181 ;; We can't use the second way right now, since there is no reliable way how to
14182 ;; verify that given register is live. First choice will also most likely in
14183 ;; fewer dependencies. On the place of esp adjustments it is very likely that
14184 ;; call clobbered registers are dead. We may want to use base pointer as an
14185 ;; alternative when no register is available later.
14186
14187 (define_peephole2
14188 [(match_scratch:SI 0 "r")
14189 (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -4)))
14190 (set (reg:SI 6) (reg:SI 6))
14191 (clobber (reg:CC 17))])]
14192 "optimize_size || !TARGET_SUB_ESP_4"
14193 [(clobber (match_dup 0))
14194 (parallel [(set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))
14195 (set (reg:SI 6) (reg:SI 6))])])
14196
14197 (define_peephole2
14198 [(match_scratch:SI 0 "r")
14199 (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
14200 (set (reg:SI 6) (reg:SI 6))
14201 (clobber (reg:CC 17))])]
14202 "optimize_size || !TARGET_SUB_ESP_8"
14203 [(clobber (match_dup 0))
14204 (set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))
14205 (parallel [(set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))
14206 (set (reg:SI 6) (reg:SI 6))])])
14207
14208 ;; Convert esp substractions to push.
14209 (define_peephole2
14210 [(match_scratch:SI 0 "r")
14211 (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -4)))
14212 (clobber (reg:CC 17))])]
14213 "optimize_size || !TARGET_SUB_ESP_4"
14214 [(clobber (match_dup 0))
14215 (set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))])
14216
14217 (define_peephole2
14218 [(match_scratch:SI 0 "r")
14219 (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
14220 (clobber (reg:CC 17))])]
14221 "optimize_size || !TARGET_SUB_ESP_8"
14222 [(clobber (match_dup 0))
14223 (set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))
14224 (set (mem:SI (pre_dec:SI (reg:SI 7))) (match_dup 0))])
14225
14226 ;; Convert epilogue deallocator to pop.
14227 (define_peephole2
14228 [(match_scratch:SI 0 "r")
14229 (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))
14230 (set (reg:SI 6) (reg:SI 6))
14231 (clobber (reg:CC 17))])]
14232 "optimize_size || !TARGET_ADD_ESP_4"
14233 [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
14234 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))
14235 (set (reg:SI 6) (reg:SI 6))])]
14236 "")
14237
14238 ;; Two pops case is tricky, since pop causes dependency on destination register.
14239 ;; We use two registers if available.
14240 (define_peephole2
14241 [(match_scratch:SI 0 "r")
14242 (match_scratch:SI 1 "r")
14243 (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 8)))
14244 (set (reg:SI 6) (reg:SI 6))
14245 (clobber (reg:CC 17))])]
14246 "optimize_size || !TARGET_ADD_ESP_8"
14247 [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
14248 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))
14249 (set (reg:SI 6) (reg:SI 6))])
14250 (parallel [(set (match_dup 1) (mem:SI (reg:SI 7)))
14251 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
14252 "")
14253
14254 (define_peephole2
14255 [(match_scratch:SI 0 "r")
14256 (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 8)))
14257 (set (reg:SI 6) (reg:SI 6))
14258 (clobber (reg:CC 17))])]
14259 "optimize_size"
14260 [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
14261 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))
14262 (set (reg:SI 6) (reg:SI 6))])
14263 (parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
14264 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
14265 "")
14266
14267 ;; Convert esp additions to pop.
14268 (define_peephole2
14269 [(match_scratch:SI 0 "r")
14270 (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))
14271 (clobber (reg:CC 17))])]
14272 ""
14273 [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
14274 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
14275 "")
14276
14277 ;; Two pops case is tricky, since pop causes dependency on destination register.
14278 ;; We use two registers if available.
14279 (define_peephole2
14280 [(match_scratch:SI 0 "r")
14281 (match_scratch:SI 1 "r")
14282 (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 8)))
14283 (clobber (reg:CC 17))])]
14284 ""
14285 [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
14286 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])
14287 (parallel [(set (match_dup 1) (mem:SI (reg:SI 7)))
14288 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
14289 "")
14290
14291 (define_peephole2
14292 [(match_scratch:SI 0 "r")
14293 (parallel [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 8)))
14294 (clobber (reg:CC 17))])]
14295 "optimize_size"
14296 [(parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
14297 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])
14298 (parallel [(set (match_dup 0) (mem:SI (reg:SI 7)))
14299 (set (reg:SI 7) (plus:SI (reg:SI 7) (const_int 4)))])]
14300 "")
14301 \f
14302 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
14303 ;; required and register dies.
14304 (define_peephole2
14305 [(set (reg 17)
14306 (compare (match_operand:SI 0 "register_operand" "")
14307 (match_operand:SI 1 "incdec_operand" "")))]
14308 "ix86_match_ccmode (insn, CCGCmode)
14309 && find_regno_note (insn, REG_DEAD, true_regnum (operands[0]))"
14310 [(parallel [(set (reg:CCGC 17)
14311 (compare:CCGC (match_dup 0)
14312 (match_dup 1)))
14313 (clobber (match_dup 0))])]
14314 "")
14315
14316 (define_peephole2
14317 [(set (reg 17)
14318 (compare (match_operand:HI 0 "register_operand" "")
14319 (match_operand:HI 1 "incdec_operand" "")))]
14320 "ix86_match_ccmode (insn, CCGCmode)
14321 && find_regno_note (insn, REG_DEAD, true_regnum (operands[0]))"
14322 [(parallel [(set (reg:CCGC 17)
14323 (compare:CCGC (match_dup 0)
14324 (match_dup 1)))
14325 (clobber (match_dup 0))])]
14326 "")
14327
14328 (define_peephole2
14329 [(set (reg 17)
14330 (compare (match_operand:QI 0 "register_operand" "")
14331 (match_operand:QI 1 "incdec_operand" "")))]
14332 "ix86_match_ccmode (insn, CCGCmode)
14333 && find_regno_note (insn, REG_DEAD, true_regnum (operands[0]))"
14334 [(parallel [(set (reg:CCGC 17)
14335 (compare:CCGC (match_dup 0)
14336 (match_dup 1)))
14337 (clobber (match_dup 0))])]
14338 "")
14339
14340 ;; Convert compares with 128 to shorter add -128
14341 (define_peephole2
14342 [(set (reg 17)
14343 (compare (match_operand:SI 0 "register_operand" "")
14344 (const_int 128)))]
14345 "ix86_match_ccmode (insn, CCGCmode)
14346 && find_regno_note (insn, REG_DEAD, true_regnum (operands[0]))"
14347 [(parallel [(set (reg:CCGC 17)
14348 (compare:CCGC (match_dup 0)
14349 (const_int 128)))
14350 (clobber (match_dup 0))])]
14351 "")
14352
14353 (define_peephole2
14354 [(set (reg 17)
14355 (compare (match_operand:HI 0 "register_operand" "")
14356 (const_int 128)))]
14357 "ix86_match_ccmode (insn, CCGCmode)
14358 && find_regno_note (insn, REG_DEAD, true_regnum (operands[0]))"
14359 [(parallel [(set (reg:CCGC 17)
14360 (compare:CCGC (match_dup 0)
14361 (const_int 128)))
14362 (clobber (match_dup 0))])]
14363 "")
14364 \f
14365 ;; Call-value patterns last so that the wildcard operand does not
14366 ;; disrupt insn-recog's switch tables.
14367
14368 (define_insn "*call_value_pop_0"
14369 [(set (match_operand 0 "" "")
14370 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
14371 (match_operand:SI 2 "" "")))
14372 (set (reg:SI 7) (plus:SI (reg:SI 7)
14373 (match_operand:SI 3 "immediate_operand" "")))]
14374 "!TARGET_64BIT"
14375 "*
14376 {
14377 if (SIBLING_CALL_P (insn))
14378 return \"jmp\\t%P1\";
14379 else
14380 return \"call\\t%P1\";
14381 }"
14382 [(set_attr "type" "callv")])
14383
14384 (define_insn "*call_value_pop_1"
14385 [(set (match_operand 0 "" "")
14386 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
14387 (match_operand:SI 2 "" "")))
14388 (set (reg:SI 7) (plus:SI (reg:SI 7)
14389 (match_operand:SI 3 "immediate_operand" "i")))]
14390 "!TARGET_64BIT"
14391 "*
14392 {
14393 if (constant_call_address_operand (operands[1], QImode))
14394 {
14395 if (SIBLING_CALL_P (insn))
14396 return \"jmp\\t%P1\";
14397 else
14398 return \"call\\t%P1\";
14399 }
14400 if (SIBLING_CALL_P (insn))
14401 return \"jmp\\t%A1\";
14402 else
14403 return \"call\\t%A1\";
14404 }"
14405 [(set_attr "type" "callv")])
14406
14407 (define_insn "*call_value_0"
14408 [(set (match_operand 0 "" "")
14409 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
14410 (match_operand:SI 2 "" "")))]
14411 ""
14412 "*
14413 {
14414 if (SIBLING_CALL_P (insn))
14415 return \"jmp\\t%P1\";
14416 else
14417 return \"call\\t%P1\";
14418 }"
14419 [(set_attr "type" "callv")])
14420
14421 (define_insn "*call_value_1"
14422 [(set (match_operand 0 "" "")
14423 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
14424 (match_operand:SI 2 "" "")))]
14425 ""
14426 "*
14427 {
14428 if (constant_call_address_operand (operands[1], QImode))
14429 {
14430 if (SIBLING_CALL_P (insn))
14431 return \"jmp\\t%P1\";
14432 else
14433 return \"call\\t%P1\";
14434 }
14435 if (SIBLING_CALL_P (insn))
14436 return \"jmp\\t%A1\";
14437 else
14438 return \"call\\t%A1\";
14439 }"
14440 [(set_attr "type" "callv")])
14441 \f
14442 (define_insn "trap"
14443 [(trap_if (const_int 1) (const_int 5))]
14444 ""
14445 "int\\t$5")
14446
14447 ;;; ix86 doesn't have conditional trap instructions, but we fake them
14448 ;;; for the sake of bounds checking. By emitting bounds checks as
14449 ;;; conditional traps rather than as conditional jumps around
14450 ;;; unconditional traps we avoid introducing spurious basic-block
14451 ;;; boundaries and facilitate elimination of redundant checks. In
14452 ;;; honor of the too-inflexible-for-BPs `bound' instruction, we use
14453 ;;; interrupt 5.
14454 ;;;
14455 ;;; FIXME: Static branch prediction rules for ix86 are such that
14456 ;;; forward conditional branches predict as untaken. As implemented
14457 ;;; below, pseudo conditional traps violate that rule. We should use
14458 ;;; .pushsection/.popsection to place all of the `int 5's in a special
14459 ;;; section loaded at the end of the text segment and branch forward
14460 ;;; there on bounds-failure, and then jump back immediately (in case
14461 ;;; the system chooses to ignore bounds violations, or to report
14462 ;;; violations and continue execution).
14463
14464 (define_expand "conditional_trap"
14465 [(trap_if (match_operator 0 "comparison_operator"
14466 [(match_dup 2) (const_int 0)])
14467 (match_operand 1 "const_int_operand" ""))]
14468 ""
14469 "
14470 {
14471 emit_insn (gen_rtx_TRAP_IF (VOIDmode,
14472 ix86_expand_compare (GET_CODE (operands[0]),
14473 NULL_PTR, NULL_PTR),
14474 operands[1]));
14475 DONE;
14476 }")
14477
14478 (define_insn ""
14479 [(trap_if (match_operator 0 "comparison_operator"
14480 [(reg 17) (const_int 0)])
14481 (match_operand 1 "const_int_operand" ""))]
14482 ""
14483 "*
14484 {
14485 operands[2] = gen_label_rtx ();
14486 output_asm_insn (\"j%c0\\t%l2\; int\\t%1\", operands);
14487 ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, \"L\",
14488 CODE_LABEL_NUMBER (operands[2]));
14489 RET;
14490 }")
14491
14492 ;; Pentium III SIMD instructions.
14493
14494 ;; Moves for SSE/MMX regs.
14495
14496 (define_insn "movv4sf_internal"
14497 [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,m")
14498 (match_operand:V4SF 1 "general_operand" "xm,x"))]
14499 "TARGET_SSE"
14500 ;; @@@ let's try to use movaps here.
14501 "movaps\\t{%1, %0|%0, %1}"
14502 [(set_attr "type" "sse")])
14503
14504 (define_insn "movv4si_internal"
14505 [(set (match_operand:V4SI 0 "nonimmediate_operand" "=x,m")
14506 (match_operand:V4SI 1 "general_operand" "xm,x"))]
14507 "TARGET_SSE"
14508 ;; @@@ let's try to use movaps here.
14509 "movaps\\t{%1, %0|%0, %1}"
14510 [(set_attr "type" "sse")])
14511
14512 (define_insn "movv8qi_internal"
14513 [(set (match_operand:V8QI 0 "nonimmediate_operand" "=y,m")
14514 (match_operand:V8QI 1 "general_operand" "ym,y"))]
14515 "TARGET_MMX"
14516 "movq\\t{%1, %0|%0, %1}"
14517 [(set_attr "type" "mmx")])
14518
14519 (define_insn "movv4hi_internal"
14520 [(set (match_operand:V4HI 0 "nonimmediate_operand" "=y,m")
14521 (match_operand:V4HI 1 "general_operand" "ym,y"))]
14522 "TARGET_MMX"
14523 "movq\\t{%1, %0|%0, %1}"
14524 [(set_attr "type" "mmx")])
14525
14526 (define_insn "movv2si_internal"
14527 [(set (match_operand:V2SI 0 "nonimmediate_operand" "=y,m")
14528 (match_operand:V2SI 1 "general_operand" "ym,y"))]
14529 "TARGET_MMX"
14530 "movq\\t{%1, %0|%0, %1}"
14531 [(set_attr "type" "mmx")])
14532
14533 (define_expand "movti"
14534 [(set (match_operand:TI 0 "general_operand" "")
14535 (match_operand:TI 1 "general_operand" ""))]
14536 "TARGET_SSE"
14537 "
14538 {
14539 /* For constants other than zero into memory. We do not know how the
14540 instructions used to build constants modify the upper 64 bits
14541 of the register, once we have that information we may be able
14542 to handle some of them more efficiently. */
14543 if ((reload_in_progress | reload_completed) == 0
14544 && register_operand (operands[0], TImode)
14545 && CONSTANT_P (operands[1]))
14546 {
14547 rtx addr = gen_reg_rtx (Pmode);
14548
14549 emit_move_insn (addr, XEXP (force_const_mem (TImode, operands[1]), 0));
14550 operands[1] = gen_rtx_MEM (TImode, addr);
14551 }
14552
14553 /* Make operand1 a register if it isn't already. */
14554 if ((reload_in_progress | reload_completed) == 0
14555 && !register_operand (operands[0], TImode)
14556 && !register_operand (operands[1], TImode)
14557 && operands[1] != CONST0_RTX (TImode))
14558 {
14559 rtx temp = force_reg (TImode, operands[1]);
14560 emit_move_insn (operands[0], temp);
14561 DONE;
14562 }
14563 }")
14564
14565 (define_expand "movv4sf"
14566 [(set (match_operand:V4SF 0 "general_operand" "")
14567 (match_operand:V4SF 1 "general_operand" ""))]
14568 "TARGET_SSE"
14569 "
14570 {
14571 /* For constants other than zero into memory. We do not know how the
14572 instructions used to build constants modify the upper 64 bits
14573 of the register, once we have that information we may be able
14574 to handle some of them more efficiently. */
14575 if ((reload_in_progress | reload_completed) == 0
14576 && register_operand (operands[0], V4SFmode)
14577 && CONSTANT_P (operands[1]))
14578 {
14579 rtx addr = gen_reg_rtx (Pmode);
14580
14581 emit_move_insn (addr, XEXP (force_const_mem (V4SFmode, operands[1]), 0));
14582 operands[1] = gen_rtx_MEM (V4SFmode, addr);
14583 }
14584
14585 /* Make operand1 a register if it isn't already. */
14586 if ((reload_in_progress | reload_completed) == 0
14587 && !register_operand (operands[0], V4SFmode)
14588 && !register_operand (operands[1], V4SFmode)
14589 && operands[1] != CONST0_RTX (V4SFmode))
14590 {
14591 rtx temp = force_reg (V4SFmode, operands[1]);
14592 emit_move_insn (operands[0], temp);
14593 DONE;
14594 }
14595 }")
14596
14597 (define_expand "movv4si"
14598 [(set (match_operand:V4SI 0 "general_operand" "")
14599 (match_operand:V4SI 1 "general_operand" ""))]
14600 "TARGET_MMX"
14601 "
14602 {
14603 /* For constants other than zero into memory. We do not know how the
14604 instructions used to build constants modify the upper 64 bits
14605 of the register, once we have that information we may be able
14606 to handle some of them more efficiently. */
14607 if ((reload_in_progress | reload_completed) == 0
14608 && register_operand (operands[0], V4SImode)
14609 && CONSTANT_P (operands[1]))
14610 {
14611 rtx addr = gen_reg_rtx (Pmode);
14612
14613 emit_move_insn (addr, XEXP (force_const_mem (V4SImode, operands[1]), 0));
14614 operands[1] = gen_rtx_MEM (V4SImode, addr);
14615 }
14616
14617 /* Make operand1 a register if it isn't already. */
14618 if ((reload_in_progress | reload_completed) == 0
14619 && !register_operand (operands[0], V4SImode)
14620 && !register_operand (operands[1], V4SImode)
14621 && operands[1] != CONST0_RTX (V4SImode))
14622 {
14623 rtx temp = force_reg (V4SImode, operands[1]);
14624 emit_move_insn (operands[0], temp);
14625 DONE;
14626 }
14627 }")
14628
14629 (define_expand "movv2si"
14630 [(set (match_operand:V2SI 0 "general_operand" "")
14631 (match_operand:V2SI 1 "general_operand" ""))]
14632 "TARGET_MMX"
14633 "
14634 {
14635 /* For constants other than zero into memory. We do not know how the
14636 instructions used to build constants modify the upper 64 bits
14637 of the register, once we have that information we may be able
14638 to handle some of them more efficiently. */
14639 if ((reload_in_progress | reload_completed) == 0
14640 && register_operand (operands[0], V2SImode)
14641 && CONSTANT_P (operands[1]))
14642 {
14643 rtx addr = gen_reg_rtx (Pmode);
14644
14645 emit_move_insn (addr, XEXP (force_const_mem (V2SImode, operands[1]), 0));
14646 operands[1] = gen_rtx_MEM (V2SImode, addr);
14647 }
14648
14649 /* Make operand1 a register if it isn't already. */
14650 if ((reload_in_progress | reload_completed) == 0
14651 && !register_operand (operands[0], V2SImode)
14652 && !register_operand (operands[1], V2SImode)
14653 && operands[1] != CONST0_RTX (V2SImode))
14654 {
14655 rtx temp = force_reg (V2SImode, operands[1]);
14656 emit_move_insn (operands[0], temp);
14657 DONE;
14658 }
14659 }")
14660
14661 (define_expand "movv4hi"
14662 [(set (match_operand:V4HI 0 "general_operand" "")
14663 (match_operand:V4HI 1 "general_operand" ""))]
14664 "TARGET_MMX"
14665 "
14666 {
14667 /* For constants other than zero into memory. We do not know how the
14668 instructions used to build constants modify the upper 64 bits
14669 of the register, once we have that information we may be able
14670 to handle some of them more efficiently. */
14671 if ((reload_in_progress | reload_completed) == 0
14672 && register_operand (operands[0], V4HImode)
14673 && CONSTANT_P (operands[1]))
14674 {
14675 rtx addr = gen_reg_rtx (Pmode);
14676
14677 emit_move_insn (addr, XEXP (force_const_mem (V4HImode, operands[1]), 0));
14678 operands[1] = gen_rtx_MEM (V4HImode, addr);
14679 }
14680
14681 /* Make operand1 a register if it isn't already. */
14682 if ((reload_in_progress | reload_completed) == 0
14683 && !register_operand (operands[0], V4HImode)
14684 && !register_operand (operands[1], V4HImode)
14685 && operands[1] != CONST0_RTX (V4HImode))
14686 {
14687 rtx temp = force_reg (V4HImode, operands[1]);
14688 emit_move_insn (operands[0], temp);
14689 DONE;
14690 }
14691 }")
14692
14693 (define_expand "movv8qi"
14694 [(set (match_operand:V8QI 0 "general_operand" "")
14695 (match_operand:V8QI 1 "general_operand" ""))]
14696 "TARGET_MMX"
14697 "
14698 {
14699 /* For constants other than zero into memory. We do not know how the
14700 instructions used to build constants modify the upper 64 bits
14701 of the register, once we have that information we may be able
14702 to handle some of them more efficiently. */
14703 if ((reload_in_progress | reload_completed) == 0
14704 && register_operand (operands[0], V8QImode)
14705 && CONSTANT_P (operands[1]))
14706 {
14707 rtx addr = gen_reg_rtx (Pmode);
14708
14709 emit_move_insn (addr, XEXP (force_const_mem (V8QImode, operands[1]), 0));
14710 operands[1] = gen_rtx_MEM (V8QImode, addr);
14711 }
14712
14713 /* Make operand1 a register if it isn't already. */
14714 if ((reload_in_progress | reload_completed) == 0
14715 && !register_operand (operands[0], V8QImode)
14716 && !register_operand (operands[1], V8QImode)
14717 && operands[1] != CONST0_RTX (V8QImode))
14718 {
14719 rtx temp = force_reg (V8QImode, operands[1]);
14720 emit_move_insn (operands[0], temp);
14721 DONE;
14722 }
14723 }")
14724
14725 (define_insn_and_split "*pushti"
14726 [(set (match_operand:TI 0 "push_operand" "=<")
14727 (match_operand:TI 1 "nonmemory_operand" "x"))]
14728 "TARGET_SSE"
14729 "#"
14730 ""
14731 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -16)))
14732 (set (mem:TI (reg:SI 7)) (match_dup 1))]
14733 ""
14734 [(set_attr "type" "sse")])
14735
14736 (define_insn_and_split "*pushv4sf"
14737 [(set (match_operand:V4SF 0 "push_operand" "=<")
14738 (match_operand:V4SF 1 "nonmemory_operand" "x"))]
14739 "TARGET_SSE"
14740 "#"
14741 ""
14742 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -16)))
14743 (set (mem:V4SF (reg:SI 7)) (match_dup 1))]
14744 ""
14745 [(set_attr "type" "sse")])
14746
14747 (define_insn_and_split "*pushv4si"
14748 [(set (match_operand:V4SI 0 "push_operand" "=<")
14749 (match_operand:V4SI 1 "nonmemory_operand" "x"))]
14750 "TARGET_SSE"
14751 "#"
14752 ""
14753 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -16)))
14754 (set (mem:V4SI (reg:SI 7)) (match_dup 1))]
14755 ""
14756 [(set_attr "type" "sse")])
14757
14758 (define_insn_and_split "*pushv2si"
14759 [(set (match_operand:V2SI 0 "push_operand" "=<")
14760 (match_operand:V2SI 1 "nonmemory_operand" "y"))]
14761 "TARGET_MMX"
14762 "#"
14763 ""
14764 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
14765 (set (mem:V2SI (reg:SI 7)) (match_dup 1))]
14766 ""
14767 [(set_attr "type" "mmx")])
14768
14769 (define_insn_and_split "*pushv4hi"
14770 [(set (match_operand:V4HI 0 "push_operand" "=<")
14771 (match_operand:V4HI 1 "nonmemory_operand" "y"))]
14772 "TARGET_MMX"
14773 "#"
14774 ""
14775 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
14776 (set (mem:V4HI (reg:SI 7)) (match_dup 1))]
14777 ""
14778 [(set_attr "type" "mmx")])
14779
14780 (define_insn_and_split "*pushv8qi"
14781 [(set (match_operand:V8QI 0 "push_operand" "=<")
14782 (match_operand:V8QI 1 "nonmemory_operand" "y"))]
14783 "TARGET_MMX"
14784 "#"
14785 ""
14786 [(set (reg:SI 7) (plus:SI (reg:SI 7) (const_int -8)))
14787 (set (mem:V8QI (reg:SI 7)) (match_dup 1))]
14788 ""
14789 [(set_attr "type" "mmx")])
14790
14791 (define_insn "movti_internal"
14792 [(set (match_operand:TI 0 "nonimmediate_operand" "=x,m")
14793 (match_operand:TI 1 "general_operand" "xm,x"))]
14794 "TARGET_SSE"
14795 "@
14796 movaps\\t{%1, %0|%0, %1}
14797 movaps\\t{%1, %0|%0, %1}"
14798 [(set_attr "type" "sse")])
14799
14800 ;; These two patterns are useful for specifying exactly whether to use
14801 ;; movaps or movups
14802 (define_insn "sse_movaps"
14803 [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,m")
14804 (unspec:V4SF [(match_operand:V4SF 1 "general_operand" "xm,x")] 38))]
14805 "TARGET_SSE"
14806 "@
14807 movaps\\t{%1, %0|%0, %1}
14808 movaps\\t{%1, %0|%0, %1}"
14809 [(set_attr "type" "sse")])
14810
14811 (define_insn "sse_movups"
14812 [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,m")
14813 (unspec:V4SF [(match_operand:V4SF 1 "general_operand" "xm,x")] 39))]
14814 "TARGET_SSE"
14815 "@
14816 movups\\t{%1, %0|%0, %1}
14817 movups\\t{%1, %0|%0, %1}"
14818 [(set_attr "type" "sse")])
14819
14820
14821 ;; SSE Strange Moves.
14822
14823 (define_insn "sse_movmskps"
14824 [(set (match_operand:SI 0 "register_operand" "=r")
14825 (unspec:SI [(match_operand:V4SF 1 "register_operand" "x")] 33))]
14826 "TARGET_SSE"
14827 "movmskps\\t{%1, %0|%0, %1}"
14828 [(set_attr "type" "sse")])
14829
14830 (define_insn "mmx_pmovmskb"
14831 [(set (match_operand:SI 0 "register_operand" "=r")
14832 (unspec:SI [(match_operand:V8QI 1 "register_operand" "y")] 33))]
14833 "TARGET_SSE"
14834 "pmovmskb\\t{%1, %0|%0, %1}"
14835 [(set_attr "type" "sse")])
14836
14837 (define_insn "mmx_maskmovq"
14838 [(set (mem:V8QI (match_operand:SI 0 "register_operand" "D"))
14839 (unspec:V8QI [(match_operand:V8QI 1 "register_operand" "y")
14840 (match_operand:V8QI 2 "register_operand" "y")] 32))]
14841 "TARGET_SSE"
14842 ;; @@@ check ordering of operands in intel/nonintel syntax
14843 "maskmovq\\t{%2, %1|%1, %2}"
14844 [(set_attr "type" "sse")])
14845
14846 (define_insn "sse_movntv4sf"
14847 [(set (match_operand:V4SF 0 "memory_operand" "=m")
14848 (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "x")] 34))]
14849 "TARGET_SSE"
14850 "movntps\\t{%1, %0|%0, %1}"
14851 [(set_attr "type" "sse")])
14852
14853 (define_insn "sse_movntdi"
14854 [(set (match_operand:DI 0 "memory_operand" "=m")
14855 (unspec:DI [(match_operand:DI 1 "register_operand" "y")] 34))]
14856 "TARGET_SSE"
14857 "movntq\\t{%1, %0|%0, %1}"
14858 [(set_attr "type" "sse")])
14859
14860 (define_insn "sse_movhlps"
14861 [(set (match_operand:V4SF 0 "register_operand" "=x")
14862 (vec_merge:V4SF
14863 (match_operand:V4SF 1 "register_operand" "0")
14864 (vec_select:V4SF (match_operand:V4SF 2 "register_operand" "x")
14865 (parallel [(const_int 2)
14866 (const_int 3)
14867 (const_int 0)
14868 (const_int 1)]))
14869 (const_int 3)))]
14870 "TARGET_SSE"
14871 "movhlps\\t{%2, %0|%0, %2}"
14872 [(set_attr "type" "sse")])
14873
14874 (define_insn "sse_movlhps"
14875 [(set (match_operand:V4SF 0 "register_operand" "=x")
14876 (vec_merge:V4SF
14877 (match_operand:V4SF 1 "register_operand" "0")
14878 (vec_select:V4SF (match_operand:V4SF 2 "register_operand" "x")
14879 (parallel [(const_int 2)
14880 (const_int 3)
14881 (const_int 0)
14882 (const_int 1)]))
14883 (const_int 12)))]
14884 "TARGET_SSE"
14885 "movlhps\\t{%2, %0|%0, %2}"
14886 [(set_attr "type" "sse")])
14887
14888 (define_insn "sse_movhps"
14889 [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,m")
14890 (vec_merge:V4SF
14891 (match_operand:V4SF 1 "nonimmediate_operand" "0,0")
14892 (match_operand:V4SF 2 "nonimmediate_operand" "m,x")
14893 (const_int 12)))]
14894 "TARGET_SSE && (GET_CODE (operands[1]) == MEM || GET_CODE (operands[2]) == MEM)"
14895 "movhps\\t{%2, %0|%0, %2}"
14896 [(set_attr "type" "sse")])
14897
14898 (define_insn "sse_movlps"
14899 [(set (match_operand:V4SF 0 "nonimmediate_operand" "=x,m")
14900 (vec_merge:V4SF
14901 (match_operand:V4SF 1 "nonimmediate_operand" "0,0")
14902 (match_operand:V4SF 2 "nonimmediate_operand" "m,x")
14903 (const_int 3)))]
14904 "TARGET_SSE && (GET_CODE (operands[1]) == MEM || GET_CODE (operands[2]) == MEM)"
14905 "movlps\\t{%2, %0|%0, %2}"
14906 [(set_attr "type" "sse")])
14907
14908 (define_insn "sse_loadss"
14909 [(set (match_operand:V4SF 0 "register_operand" "=x")
14910 (vec_merge:V4SF
14911 (match_operand:V4SF 1 "memory_operand" "m")
14912 (vec_duplicate:V4SF (float:SF (const_int 0)))
14913 (const_int 1)))]
14914 "TARGET_SSE"
14915 "movss\\t{%1, %0|%0, %1}"
14916 [(set_attr "type" "sse")])
14917
14918 (define_insn "sse_movss"
14919 [(set (match_operand:V4SF 0 "register_operand" "=x")
14920 (vec_merge:V4SF
14921 (match_operand:V4SF 1 "register_operand" "0")
14922 (match_operand:V4SF 2 "register_operand" "x")
14923 (const_int 1)))]
14924 "TARGET_SSE"
14925 "movss\\t{%2, %0|%0, %2}"
14926 [(set_attr "type" "sse")])
14927
14928 (define_insn "sse_storess"
14929 [(set (match_operand:SF 0 "memory_operand" "=m")
14930 (vec_select:SF
14931 (match_operand:V4SF 1 "register_operand" "x")
14932 (parallel [(const_int 0)])))]
14933 "TARGET_SSE"
14934 "movss\\t{%1, %0|%0, %1}"
14935 [(set_attr "type" "sse")])
14936
14937 (define_insn "sse_shufps"
14938 [(set (match_operand:V4SF 0 "register_operand" "=x")
14939 (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "0")
14940 (match_operand:V4SF 2 "nonimmediate_operand" "xm")
14941 (match_operand:SI 3 "immediate_operand" "i")] 41))]
14942 "TARGET_SSE"
14943 ;; @@@ check operand order for intel/nonintel syntax
14944 "shufps\\t{%3, %2, %0|%0, %2, %3}"
14945 [(set_attr "type" "sse")])
14946
14947
14948 ;; SSE arithmetic
14949
14950 (define_insn "addv4sf3"
14951 [(set (match_operand:V4SF 0 "register_operand" "=x")
14952 (plus:V4SF (match_operand:V4SF 1 "register_operand" "0")
14953 (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
14954 "TARGET_SSE"
14955 "addps\\t{%2, %0|%0, %2}"
14956 [(set_attr "type" "sse")])
14957
14958 (define_insn "vmaddv4sf3"
14959 [(set (match_operand:V4SF 0 "register_operand" "=x")
14960 (vec_merge:V4SF (plus:V4SF (match_operand:V4SF 1 "register_operand" "0")
14961 (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
14962 (match_dup 1)
14963 (const_int 1)))]
14964 "TARGET_SSE"
14965 "addss\\t{%2, %0|%0, %2}"
14966 [(set_attr "type" "sse")])
14967
14968 (define_insn "subv4sf3"
14969 [(set (match_operand:V4SF 0 "register_operand" "=x")
14970 (minus:V4SF (match_operand:V4SF 1 "register_operand" "0")
14971 (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
14972 "TARGET_SSE"
14973 "subps\\t{%2, %0|%0, %2}"
14974 [(set_attr "type" "sse")])
14975
14976 (define_insn "vmsubv4sf3"
14977 [(set (match_operand:V4SF 0 "register_operand" "=x")
14978 (vec_merge:V4SF (minus:V4SF (match_operand:V4SF 1 "register_operand" "0")
14979 (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
14980 (match_dup 1)
14981 (const_int 1)))]
14982 "TARGET_SSE"
14983 "subss\\t{%2, %0|%0, %2}"
14984 [(set_attr "type" "sse")])
14985
14986 (define_insn "mulv4sf3"
14987 [(set (match_operand:V4SF 0 "register_operand" "=x")
14988 (mult:V4SF (match_operand:V4SF 1 "register_operand" "0")
14989 (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
14990 "TARGET_SSE"
14991 "mulps\\t{%2, %0|%0, %2}"
14992 [(set_attr "type" "sse")])
14993
14994 (define_insn "vmmulv4sf3"
14995 [(set (match_operand:V4SF 0 "register_operand" "=x")
14996 (vec_merge:V4SF (mult:V4SF (match_operand:V4SF 1 "register_operand" "0")
14997 (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
14998 (match_dup 1)
14999 (const_int 1)))]
15000 "TARGET_SSE"
15001 "mulss\\t{%2, %0|%0, %2}"
15002 [(set_attr "type" "sse")])
15003
15004 (define_insn "divv4sf3"
15005 [(set (match_operand:V4SF 0 "register_operand" "=x")
15006 (div:V4SF (match_operand:V4SF 1 "register_operand" "0")
15007 (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
15008 "TARGET_SSE"
15009 "divps\\t{%2, %0|%0, %2}"
15010 [(set_attr "type" "sse")])
15011
15012 (define_insn "vmdivv4sf3"
15013 [(set (match_operand:V4SF 0 "register_operand" "=x")
15014 (vec_merge:V4SF (div:V4SF (match_operand:V4SF 1 "register_operand" "0")
15015 (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
15016 (match_dup 1)
15017 (const_int 1)))]
15018 "TARGET_SSE"
15019 "divss\\t{%2, %0|%0, %2}"
15020 [(set_attr "type" "sse")])
15021
15022
15023 ;; SSE square root/reciprocal
15024
15025 (define_insn "rcpv4sf2"
15026 [(set (match_operand:V4SF 0 "register_operand" "=x")
15027 (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "xm")] 42))]
15028 "TARGET_SSE"
15029 "rcpps\\t{%1, %0|%0, %1}"
15030 [(set_attr "type" "sse")])
15031
15032 (define_insn "vmrcpv4sf2"
15033 [(set (match_operand:V4SF 0 "register_operand" "=x")
15034 (vec_merge:V4SF (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "xm")] 42)
15035 (match_operand:V4SF 2 "register_operand" "0")
15036 (const_int 1)))]
15037 "TARGET_SSE"
15038 "rcpss\\t{%1, %0|%0, %1}"
15039 [(set_attr "type" "sse")])
15040
15041 (define_insn "rsqrtv4sf2"
15042 [(set (match_operand:V4SF 0 "register_operand" "=x")
15043 (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "xm")] 43))]
15044 "TARGET_SSE"
15045 "rsqrtps\\t{%1, %0|%0, %1}"
15046 [(set_attr "type" "sse")])
15047
15048 (define_insn "vmrsqrtv4sf2"
15049 [(set (match_operand:V4SF 0 "register_operand" "=x")
15050 (vec_merge:V4SF (unspec:V4SF [(match_operand:V4SF 1 "register_operand" "xm")] 43)
15051 (match_operand:V4SF 2 "register_operand" "0")
15052 (const_int 1)))]
15053 "TARGET_SSE"
15054 "rsqrtss\\t{%1, %0|%0, %1}"
15055 [(set_attr "type" "sse")])
15056
15057 (define_insn "sqrtv4sf2"
15058 [(set (match_operand:V4SF 0 "register_operand" "=x")
15059 (sqrt:V4SF (match_operand:V4SF 1 "register_operand" "xm")))]
15060 "TARGET_SSE"
15061 "sqrtps\\t{%1, %0|%0, %1}"
15062 [(set_attr "type" "sse")])
15063
15064 (define_insn "vmsqrtv4sf2"
15065 [(set (match_operand:V4SF 0 "register_operand" "=x")
15066 (vec_merge:V4SF (sqrt:V4SF (match_operand:V4SF 1 "register_operand" "xm"))
15067 (match_operand:V4SF 2 "register_operand" "0")
15068 (const_int 1)))]
15069 "TARGET_SSE"
15070 "sqrtss\\t{%1, %0|%0, %1}"
15071 [(set_attr "type" "sse")])
15072
15073
15074 ;; SSE logical operations.
15075
15076 ;; These are not called andti3 etc. because we really really don't want
15077 ;; the compiler to widen DImode ands to TImode ands and then try to move
15078 ;; into DImode subregs of SSE registers, and them together, and move out
15079 ;; of DImode subregs again!
15080
15081 (define_insn "*sse_andti3_df_1"
15082 [(set (subreg:TI (match_operand:DF 0 "register_operand" "=Y") 0)
15083 (and:TI (subreg:TI (match_operand:DF 1 "register_operand" "%0") 0)
15084 (subreg:TI (match_operand:DF 2 "register_operand" "Y") 0)))]
15085 "TARGET_SSE2"
15086 "andpd\\t{%2, %0|%0, %2}"
15087 [(set_attr "type" "sse")])
15088
15089 (define_insn "*sse_andti3_df_2"
15090 [(set (subreg:TI (match_operand:DF 0 "register_operand" "=Y") 0)
15091 (and:TI (subreg:TI (match_operand:DF 1 "register_operand" "0") 0)
15092 (match_operand:TI 2 "nonimmediate_operand" "Ym")))]
15093 "TARGET_SSE2"
15094 "andpd\\t{%2, %0|%0, %2}"
15095 [(set_attr "type" "sse")])
15096
15097 (define_insn "*sse_andti3_sf_1"
15098 [(set (subreg:TI (match_operand:SF 0 "register_operand" "=x") 0)
15099 (and:TI (subreg:TI (match_operand:SF 1 "register_operand" "%0") 0)
15100 (subreg:TI (match_operand:SF 2 "register_operand" "x") 0)))]
15101 "TARGET_SSE"
15102 "andps\\t{%2, %0|%0, %2}"
15103 [(set_attr "type" "sse")])
15104
15105 (define_insn "*sse_andti3_sf_2"
15106 [(set (subreg:TI (match_operand:SF 0 "register_operand" "=x") 0)
15107 (and:TI (subreg:TI (match_operand:SF 1 "register_operand" "0") 0)
15108 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15109 "TARGET_SSE"
15110 "andps\\t{%2, %0|%0, %2}"
15111 [(set_attr "type" "sse")])
15112
15113 (define_insn "sse_andti3"
15114 [(set (match_operand:TI 0 "register_operand" "=x")
15115 (and:TI (match_operand:TI 1 "register_operand" "%0")
15116 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15117 "TARGET_SSE && !TARGET_SSE2"
15118 "andps\\t{%2, %0|%0, %2}"
15119 [(set_attr "type" "sse")])
15120
15121 (define_insn "*sse_andti3_sse2"
15122 [(set (match_operand:TI 0 "register_operand" "=x")
15123 (and:TI (match_operand:TI 1 "register_operand" "%0")
15124 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15125 "TARGET_SSE2"
15126 "pand\\t{%2, %0|%0, %2}"
15127 [(set_attr "type" "sse")])
15128
15129 (define_insn "*sse_nandti3_df"
15130 [(set (subreg:TI (match_operand:DF 0 "register_operand" "=Y") 0)
15131 (and:TI (not:TI (subreg:TI (match_operand:DF 1 "register_operand" "0") 0))
15132 (match_operand:TI 2 "nonimmediate_operand" "Ym")))]
15133 "TARGET_SSE2"
15134 "andnpd\\t{%2, %0|%0, %2}"
15135 [(set_attr "type" "sse")])
15136
15137 (define_insn "*sse_nandti3_sf"
15138 [(set (subreg:TI (match_operand:SF 0 "register_operand" "=x") 0)
15139 (and:TI (not:TI (subreg:TI (match_operand:SF 1 "register_operand" "0") 0))
15140 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15141 "TARGET_SSE"
15142 "andnps\\t{%2, %0|%0, %2}"
15143 [(set_attr "type" "sse")])
15144
15145 (define_insn "sse_nandti3"
15146 [(set (match_operand:TI 0 "register_operand" "=x")
15147 (and:TI (not:TI (match_operand:TI 1 "register_operand" "0"))
15148 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15149 "TARGET_SSE && !TARGET_SSE2"
15150 "andnps\\t{%2, %0|%0, %2}"
15151 [(set_attr "type" "sse")])
15152
15153 (define_insn "*sse_nandti3_sse2"
15154 [(set (match_operand:TI 0 "register_operand" "=x")
15155 (and:TI (not:TI (match_operand:TI 1 "register_operand" "0"))
15156 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15157 "TARGET_SSE2"
15158 "pnand\\t{%2, %0|%0, %2}"
15159 [(set_attr "type" "sse")])
15160
15161 (define_insn "*sse_iorti3_df_1"
15162 [(set (subreg:TI (match_operand:DF 0 "register_operand" "=Y") 0)
15163 (ior:TI (subreg:TI (match_operand:DF 1 "register_operand" "%0") 0)
15164 (subreg:TI (match_operand:DF 2 "register_operand" "Y") 0)))]
15165 "TARGET_SSE2"
15166 "orpd\\t{%2, %0|%0, %2}"
15167 [(set_attr "type" "sse")])
15168
15169 (define_insn "*sse_iorti3_df_2"
15170 [(set (subreg:TI (match_operand:DF 0 "register_operand" "=Y") 0)
15171 (ior:TI (subreg:TI (match_operand:DF 1 "register_operand" "0") 0)
15172 (match_operand:TI 2 "nonimmediate_operand" "Ym")))]
15173 "TARGET_SSE2"
15174 "orpd\\t{%2, %0|%0, %2}"
15175 [(set_attr "type" "sse")])
15176
15177 (define_insn "*sse_iorti3_sf_1"
15178 [(set (subreg:TI (match_operand:SF 0 "register_operand" "=x") 0)
15179 (ior:TI (subreg:TI (match_operand:SF 1 "register_operand" "%0") 0)
15180 (subreg:TI (match_operand:SF 2 "register_operand" "x") 0)))]
15181 "TARGET_SSE"
15182 "orps\\t{%2, %0|%0, %2}"
15183 [(set_attr "type" "sse")])
15184
15185 (define_insn "*sse_iorti3_sf_2"
15186 [(set (subreg:TI (match_operand:SF 0 "register_operand" "=x") 0)
15187 (ior:TI (subreg:TI (match_operand:SF 1 "register_operand" "0") 0)
15188 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15189 "TARGET_SSE"
15190 "orps\\t{%2, %0|%0, %2}"
15191 [(set_attr "type" "sse")])
15192
15193 (define_insn "sse_iorti3"
15194 [(set (match_operand:TI 0 "register_operand" "=x")
15195 (ior:TI (match_operand:TI 1 "register_operand" "%0")
15196 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15197 "TARGET_SSE && !TARGET_SSE2"
15198 "orps\\t{%2, %0|%0, %2}"
15199 [(set_attr "type" "sse")])
15200
15201 (define_insn "*sse_iorti3_sse2"
15202 [(set (match_operand:TI 0 "register_operand" "=x")
15203 (ior:TI (match_operand:TI 1 "register_operand" "%0")
15204 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15205 "TARGET_SSE2"
15206 "por\\t{%2, %0|%0, %2}"
15207 [(set_attr "type" "sse")])
15208
15209 (define_insn "*sse_xorti3_df_1"
15210 [(set (subreg:TI (match_operand:DF 0 "register_operand" "=Y") 0)
15211 (xor:TI (subreg:TI (match_operand:DF 1 "register_operand" "%0") 0)
15212 (subreg:TI (match_operand:DF 2 "register_operand" "Y") 0)))]
15213 "TARGET_SSE2"
15214 "xorpd\\t{%2, %0|%0, %2}"
15215 [(set_attr "type" "sse")])
15216
15217 (define_insn "*sse_xorti3_df_2"
15218 [(set (subreg:TI (match_operand:DF 0 "register_operand" "=Y") 0)
15219 (xor:TI (subreg:TI (match_operand:DF 1 "register_operand" "0") 0)
15220 (match_operand:TI 2 "nonimmediate_operand" "Ym")))]
15221 "TARGET_SSE2"
15222 "xorpd\\t{%2, %0|%0, %2}"
15223 [(set_attr "type" "sse")])
15224
15225 (define_insn "*sse_xorti3_sf_1"
15226 [(set (subreg:TI (match_operand:SF 0 "register_operand" "=x") 0)
15227 (xor:TI (subreg:TI (match_operand:SF 1 "register_operand" "%0") 0)
15228 (subreg:TI (match_operand:SF 2 "register_operand" "x") 0)))]
15229 "TARGET_SSE"
15230 "xorps\\t{%2, %0|%0, %2}"
15231 [(set_attr "type" "sse")])
15232
15233 (define_insn "*sse_xorti3_sf_2"
15234 [(set (subreg:TI (match_operand:SF 0 "register_operand" "=x") 0)
15235 (xor:TI (subreg:TI (match_operand:SF 1 "register_operand" "0") 0)
15236 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15237 "TARGET_SSE"
15238 "xorps\\t{%2, %0|%0, %2}"
15239 [(set_attr "type" "sse")])
15240
15241 (define_insn "sse_xorti3"
15242 [(set (match_operand:TI 0 "register_operand" "=x")
15243 (xor:TI (match_operand:TI 1 "register_operand" "%0")
15244 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15245 "TARGET_SSE && !TARGET_SSE2"
15246 "xorps\\t{%2, %0|%0, %2}"
15247 [(set_attr "type" "sse")])
15248
15249 (define_insn "*sse_xorti3_sse2"
15250 [(set (match_operand:TI 0 "register_operand" "=x")
15251 (xor:TI (match_operand:TI 1 "register_operand" "%0")
15252 (match_operand:TI 2 "nonimmediate_operand" "xm")))]
15253 "TARGET_SSE2"
15254 "pxor\\t{%2, %0|%0, %2}"
15255 [(set_attr "type" "sse")])
15256
15257 ;; Use xor, but don't show input operands so they aren't live before
15258 ;; this insn.
15259 (define_insn "sse_clrti"
15260 [(set (match_operand:TI 0 "register_operand" "=x")
15261 (unspec:TI [(const_int 0)] 45))]
15262 "TARGET_SSE"
15263 "xorps\\t{%0, %0|%0, %0}"
15264 [(set_attr "type" "sse")])
15265
15266
15267 ;; SSE mask-generating compares
15268
15269 (define_insn "maskcmpv4sf3"
15270 [(set (match_operand:V4SI 0 "register_operand" "=x")
15271 (match_operator:V4SI 3 "sse_comparison_operator"
15272 [(match_operand:V4SF 1 "register_operand" "0")
15273 (match_operand:V4SF 2 "nonimmediate_operand" "x")]))]
15274 "TARGET_SSE"
15275 "cmp%D3ps\\t{%2, %0|%0, %2}"
15276 [(set_attr "type" "sse")])
15277
15278 (define_insn "maskncmpv4sf3"
15279 [(set (match_operand:V4SI 0 "register_operand" "=x")
15280 (not:V4SI
15281 (match_operator:V4SI 3 "sse_comparison_operator"
15282 [(match_operand:V4SF 1 "register_operand" "0")
15283 (match_operand:V4SF 2 "nonimmediate_operand" "x")])))]
15284 "TARGET_SSE"
15285 "cmpn%D3ps\\t{%2, %0|%0, %2}"
15286 [(set_attr "type" "sse")])
15287
15288 (define_insn "vmmaskcmpv4sf3"
15289 [(set (match_operand:V4SI 0 "register_operand" "=x")
15290 (vec_merge:V4SI
15291 (match_operator:V4SI 3 "sse_comparison_operator"
15292 [(match_operand:V4SF 1 "register_operand" "0")
15293 (match_operand:V4SF 2 "nonimmediate_operand" "x")])
15294 (match_dup 1)
15295 (const_int 1)))]
15296 "TARGET_SSE"
15297 "cmp%D3ss\\t{%2, %0|%0, %2}"
15298 [(set_attr "type" "sse")])
15299
15300 (define_insn "vmmaskncmpv4sf3"
15301 [(set (match_operand:V4SI 0 "register_operand" "=x")
15302 (vec_merge:V4SI
15303 (not:V4SI
15304 (match_operator:V4SI 3 "sse_comparison_operator"
15305 [(match_operand:V4SF 1 "register_operand" "0")
15306 (match_operand:V4SF 2 "nonimmediate_operand" "x")]))
15307 (subreg:V4SI (match_dup 1) 0)
15308 (const_int 1)))]
15309 "TARGET_SSE"
15310 "cmp%D3ss\\t{%2, %0|%0, %2}"
15311 [(set_attr "type" "sse")])
15312
15313 (define_insn "sse_comi"
15314 [(set (reg:CCFP 17)
15315 (match_operator:CCFP 2 "sse_comparison_operator"
15316 [(vec_select:SF
15317 (match_operand:V4SF 0 "register_operand" "x")
15318 (parallel [(const_int 0)]))
15319 (vec_select:SF
15320 (match_operand:V4SF 1 "register_operand" "x")
15321 (parallel [(const_int 0)]))]))]
15322 "TARGET_SSE"
15323 "comiss\\t{%2, %0|%0, %2}"
15324 [(set_attr "type" "sse")])
15325
15326 (define_insn "sse_ucomi"
15327 [(set (reg:CCFPU 17)
15328 (match_operator:CCFPU 2 "sse_comparison_operator"
15329 [(vec_select:SF
15330 (match_operand:V4SF 0 "register_operand" "x")
15331 (parallel [(const_int 0)]))
15332 (vec_select:SF
15333 (match_operand:V4SF 1 "register_operand" "x")
15334 (parallel [(const_int 0)]))]))]
15335 "TARGET_SSE"
15336 "ucomiss\\t{%2, %0|%0, %2}"
15337 [(set_attr "type" "sse")])
15338
15339
15340 ;; SSE unpack
15341
15342 (define_insn "sse_unpckhps"
15343 [(set (match_operand:V4SF 0 "register_operand" "=x")
15344 (vec_merge:V4SF
15345 (vec_select:V4SF (match_operand:V4SF 1 "register_operand" "0")
15346 (parallel [(const_int 2)
15347 (const_int 0)
15348 (const_int 3)
15349 (const_int 1)]))
15350 (vec_select:V8QI (match_operand:V8QI 2 "register_operand" "x")
15351 (parallel [(const_int 0)
15352 (const_int 2)
15353 (const_int 1)
15354 (const_int 3)]))
15355 (const_int 5)))]
15356 "TARGET_SSE"
15357 "unpckhps\\t{%2, %0|%0, %2}"
15358 [(set_attr "type" "sse")])
15359
15360 (define_insn "sse_unpcklps"
15361 [(set (match_operand:V4SF 0 "register_operand" "=x")
15362 (vec_merge:V4SF
15363 (vec_select:V4SF (match_operand:V4SF 1 "register_operand" "0")
15364 (parallel [(const_int 0)
15365 (const_int 2)
15366 (const_int 1)
15367 (const_int 3)]))
15368 (vec_select:V8QI (match_operand:V8QI 2 "register_operand" "x")
15369 (parallel [(const_int 2)
15370 (const_int 0)
15371 (const_int 3)
15372 (const_int 1)]))
15373 (const_int 5)))]
15374 "TARGET_SSE"
15375 "unpcklps\\t{%2, %0|%0, %2}"
15376 [(set_attr "type" "sse")])
15377
15378
15379 ;; SSE min/max
15380
15381 (define_insn "smaxv4sf3"
15382 [(set (match_operand:V4SF 0 "register_operand" "=x")
15383 (smax:V4SF (match_operand:V4SF 1 "register_operand" "0")
15384 (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
15385 "TARGET_SSE"
15386 "maxps\\t{%2, %0|%0, %2}"
15387 [(set_attr "type" "sse")])
15388
15389 (define_insn "vmsmaxv4sf3"
15390 [(set (match_operand:V4SF 0 "register_operand" "=x")
15391 (vec_merge:V4SF (smax:V4SF (match_operand:V4SF 1 "register_operand" "0")
15392 (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
15393 (match_dup 1)
15394 (const_int 1)))]
15395 "TARGET_SSE"
15396 "maxss\\t{%2, %0|%0, %2}"
15397 [(set_attr "type" "sse")])
15398
15399 (define_insn "sminv4sf3"
15400 [(set (match_operand:V4SF 0 "register_operand" "=x")
15401 (smin:V4SF (match_operand:V4SF 1 "register_operand" "0")
15402 (match_operand:V4SF 2 "nonimmediate_operand" "xm")))]
15403 "TARGET_SSE"
15404 "minps\\t{%2, %0|%0, %2}"
15405 [(set_attr "type" "sse")])
15406
15407 (define_insn "vmsminv4sf3"
15408 [(set (match_operand:V4SF 0 "register_operand" "=x")
15409 (vec_merge:V4SF (smin:V4SF (match_operand:V4SF 1 "register_operand" "0")
15410 (match_operand:V4SF 2 "nonimmediate_operand" "xm"))
15411 (match_dup 1)
15412 (const_int 1)))]
15413 "TARGET_SSE"
15414 "minss\\t{%2, %0|%0, %2}"
15415 [(set_attr "type" "sse")])
15416
15417
15418 ;; SSE <-> integer/MMX conversions
15419
15420 (define_insn "cvtpi2ps"
15421 [(set (match_operand:V4SF 0 "register_operand" "=x")
15422 (vec_merge:V4SF (match_operand:V4SF 1 "register_operand" "0")
15423 (vec_duplicate:V4SF
15424 (float:V2SF (match_operand:V2SI 2 "register_operand" "ym")))
15425 (const_int 12)))]
15426 "TARGET_SSE"
15427 "cvtpi2ps\\t{%2, %0|%0, %2}"
15428 [(set_attr "type" "sse")])
15429
15430 (define_insn "cvtps2pi"
15431 [(set (match_operand:V2SI 0 "register_operand" "=y")
15432 (vec_select:V2SI (fix:V4SI (match_operand:V4SF 1 "register_operand" "xm"))
15433 (parallel
15434 [(const_int 0)
15435 (const_int 1)])))]
15436 "TARGET_SSE"
15437 "cvtps2pi\\t{%1, %0|%0, %1}"
15438 [(set_attr "type" "sse")])
15439
15440 (define_insn "cvttps2pi"
15441 [(set (match_operand:V2SI 0 "register_operand" "=y")
15442 (vec_select:V2SI (unspec:V4SI [(match_operand:V4SF 1 "register_operand" "xm")] 30)
15443 (parallel
15444 [(const_int 0)
15445 (const_int 1)])))]
15446 "TARGET_SSE"
15447 "cvttps2pi\\t{%1, %0|%0, %1}"
15448 [(set_attr "type" "sse")])
15449
15450 (define_insn "cvtsi2ss"
15451 [(set (match_operand:V4SF 0 "register_operand" "=x")
15452 (vec_merge:V4SF (match_operand:V4SF 1 "register_operand" "0")
15453 (vec_duplicate:V4SF
15454 (float:SF (match_operand:SI 2 "register_operand" "rm")))
15455 (const_int 15)))]
15456 "TARGET_SSE"
15457 "cvtsi2ss\\t{%2, %0|%0, %2}"
15458 [(set_attr "type" "sse")])
15459
15460 (define_insn "cvtss2si"
15461 [(set (match_operand:SI 0 "register_operand" "=y")
15462 (vec_select:SI (fix:V4SI (match_operand:V4SF 1 "register_operand" "xm"))
15463 (parallel [(const_int 0)])))]
15464 "TARGET_SSE"
15465 "cvtss2si\\t{%1, %0|%0, %1}"
15466 [(set_attr "type" "sse")])
15467
15468 (define_insn "cvttss2si"
15469 [(set (match_operand:SI 0 "register_operand" "=y")
15470 (vec_select:SI (unspec:V4SI [(match_operand:V4SF 1 "register_operand" "xm")] 30)
15471 (parallel [(const_int 0)])))]
15472 "TARGET_SSE"
15473 "cvttss2si\\t{%1, %0|%0, %1}"
15474 [(set_attr "type" "sse")])
15475
15476
15477 ;; MMX insns
15478
15479 ;; MMX arithmetic
15480
15481 (define_insn "addv8qi3"
15482 [(set (match_operand:V8QI 0 "register_operand" "=y")
15483 (plus:V8QI (match_operand:V8QI 1 "register_operand" "0")
15484 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
15485 "TARGET_MMX"
15486 "paddb\\t{%2, %0|%0, %2}"
15487 [(set_attr "type" "mmx")])
15488
15489 (define_insn "addv4hi3"
15490 [(set (match_operand:V4HI 0 "register_operand" "=y")
15491 (plus:V4HI (match_operand:V4HI 1 "register_operand" "0")
15492 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15493 "TARGET_MMX"
15494 "paddw\\t{%2, %0|%0, %2}"
15495 [(set_attr "type" "mmx")])
15496
15497 (define_insn "addv2si3"
15498 [(set (match_operand:V2SI 0 "register_operand" "=y")
15499 (plus:V2SI (match_operand:V2SI 1 "register_operand" "0")
15500 (match_operand:V2SI 2 "nonimmediate_operand" "ym")))]
15501 "TARGET_MMX"
15502 "paddd\\t{%2, %0|%0, %2}"
15503 [(set_attr "type" "mmx")])
15504
15505 (define_insn "ssaddv8qi3"
15506 [(set (match_operand:V8QI 0 "register_operand" "=y")
15507 (ss_plus:V8QI (match_operand:V8QI 1 "register_operand" "0")
15508 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
15509 "TARGET_MMX"
15510 "paddsb\\t{%2, %0|%0, %2}"
15511 [(set_attr "type" "mmx")])
15512
15513 (define_insn "ssaddv4hi3"
15514 [(set (match_operand:V4HI 0 "register_operand" "=y")
15515 (ss_plus:V4HI (match_operand:V4HI 1 "register_operand" "0")
15516 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15517 "TARGET_MMX"
15518 "paddsw\\t{%2, %0|%0, %2}"
15519 [(set_attr "type" "mmx")])
15520
15521 (define_insn "usaddv8qi3"
15522 [(set (match_operand:V8QI 0 "register_operand" "=y")
15523 (us_plus:V8QI (match_operand:V8QI 1 "register_operand" "0")
15524 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
15525 "TARGET_MMX"
15526 "paddusb\\t{%2, %0|%0, %2}"
15527 [(set_attr "type" "mmx")])
15528
15529 (define_insn "usaddv4hi3"
15530 [(set (match_operand:V4HI 0 "register_operand" "=y")
15531 (us_plus:V4HI (match_operand:V4HI 1 "register_operand" "0")
15532 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15533 "TARGET_MMX"
15534 "paddusw\\t{%2, %0|%0, %2}"
15535 [(set_attr "type" "mmx")])
15536
15537 (define_insn "subv8qi3"
15538 [(set (match_operand:V8QI 0 "register_operand" "=y")
15539 (minus:V8QI (match_operand:V8QI 1 "register_operand" "0")
15540 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
15541 "TARGET_MMX"
15542 "psubb\\t{%2, %0|%0, %2}"
15543 [(set_attr "type" "mmx")])
15544
15545 (define_insn "subv4hi3"
15546 [(set (match_operand:V4HI 0 "register_operand" "=y")
15547 (minus:V4HI (match_operand:V4HI 1 "register_operand" "0")
15548 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15549 "TARGET_MMX"
15550 "psubw\\t{%2, %0|%0, %2}"
15551 [(set_attr "type" "mmx")])
15552
15553 (define_insn "subv2si3"
15554 [(set (match_operand:V2SI 0 "register_operand" "=y")
15555 (minus:V2SI (match_operand:V2SI 1 "register_operand" "0")
15556 (match_operand:V2SI 2 "nonimmediate_operand" "ym")))]
15557 "TARGET_MMX"
15558 "psubd\\t{%2, %0|%0, %2}"
15559 [(set_attr "type" "mmx")])
15560
15561 (define_insn "sssubv8qi3"
15562 [(set (match_operand:V8QI 0 "register_operand" "=y")
15563 (ss_minus:V8QI (match_operand:V8QI 1 "register_operand" "0")
15564 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
15565 "TARGET_MMX"
15566 "psubsb\\t{%2, %0|%0, %2}"
15567 [(set_attr "type" "mmx")])
15568
15569 (define_insn "sssubv4hi3"
15570 [(set (match_operand:V4HI 0 "register_operand" "=y")
15571 (ss_minus:V4HI (match_operand:V4HI 1 "register_operand" "0")
15572 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15573 "TARGET_MMX"
15574 "psubsw\\t{%2, %0|%0, %2}"
15575 [(set_attr "type" "mmx")])
15576
15577 (define_insn "ussubv8qi3"
15578 [(set (match_operand:V8QI 0 "register_operand" "=y")
15579 (us_minus:V8QI (match_operand:V8QI 1 "register_operand" "0")
15580 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
15581 "TARGET_MMX"
15582 "psubusb\\t{%2, %0|%0, %2}"
15583 [(set_attr "type" "mmx")])
15584
15585 (define_insn "ussubv4hi3"
15586 [(set (match_operand:V4HI 0 "register_operand" "=y")
15587 (us_minus:V4HI (match_operand:V4HI 1 "register_operand" "0")
15588 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15589 "TARGET_MMX"
15590 "psubusw\\t{%2, %0|%0, %2}"
15591 [(set_attr "type" "mmx")])
15592
15593 (define_insn "mulv4hi3"
15594 [(set (match_operand:V4HI 0 "register_operand" "=y")
15595 (mult:V4HI (match_operand:V4HI 1 "register_operand" "0")
15596 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15597 "TARGET_MMX"
15598 "pmullw\\t{%2, %0|%0, %2}"
15599 [(set_attr "type" "mmx")])
15600
15601 (define_insn "smulv4hi3_highpart"
15602 [(set (match_operand:V4HI 0 "register_operand" "=y")
15603 (truncate:V4HI
15604 (lshiftrt:V4SI
15605 (mult:V4SI (sign_extend:V4SI (match_operand:V4HI 1 "register_operand" "0"))
15606 (sign_extend:V4SI (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
15607 (const_int 16))))]
15608 "TARGET_MMX"
15609 "pmulhw\\t{%2, %0|%0, %2}"
15610 [(set_attr "type" "mmx")])
15611
15612 (define_insn "umulv4hi3_highpart"
15613 [(set (match_operand:V4HI 0 "register_operand" "=y")
15614 (truncate:V4HI
15615 (lshiftrt:V4SI
15616 (mult:V4SI (zero_extend:V4SI (match_operand:V4HI 1 "register_operand" "0"))
15617 (zero_extend:V4SI (match_operand:V4HI 2 "nonimmediate_operand" "ym")))
15618 (const_int 16))))]
15619 "TARGET_MMX"
15620 "pmulhuw\\t{%2, %0|%0, %2}"
15621 [(set_attr "type" "mmx")])
15622
15623 (define_insn "mmx_pmaddwd"
15624 [(set (match_operand:V2SI 0 "register_operand" "=y")
15625 (plus:V2SI
15626 (mult:V2SI
15627 (sign_extend:V2SI (vec_select:V2HI (match_operand:V4HI 1 "register_operand" "0")
15628 (parallel [(const_int 0)
15629 (const_int 2)])))
15630 (sign_extend:V2SI (vec_select:V2HI (match_operand:V4HI 2 "nonimmediate_operand" "ym")
15631 (parallel [(const_int 0)
15632 (const_int 2)]))))
15633 (mult:V2SI
15634 (sign_extend:V2SI (vec_select:V2HI (match_dup 1)
15635 (parallel [(const_int 1)
15636 (const_int 3)])))
15637 (sign_extend:V2SI (vec_select:V2HI (match_dup 2)
15638 (parallel [(const_int 1)
15639 (const_int 3)]))))))]
15640 "TARGET_MMX"
15641 "pmaddwd\\t{%2, %0|%0, %2}"
15642 [(set_attr "type" "mmx")])
15643
15644
15645 ;; MMX logical operations
15646 ;; Note we don't want to declare these as regular iordi3 insns to prevent
15647 ;; normal code that also wants to use the FPU from getting broken.
15648 ;; The UNSPECs are there to prevent the combiner from getting overly clever.
15649 (define_insn "mmx_iordi3"
15650 [(set (match_operand:DI 0 "register_operand" "=y")
15651 (unspec:DI
15652 [(ior:DI (match_operand:DI 1 "register_operand" "0")
15653 (match_operand:DI 2 "nonimmediate_operand" "ym"))] 45))]
15654 "TARGET_MMX"
15655 "por\\t{%2, %0|%0, %2}"
15656 [(set_attr "type" "mmx")])
15657
15658 (define_insn "mmx_xordi3"
15659 [(set (match_operand:DI 0 "register_operand" "=y")
15660 (unspec:DI
15661 [(xor:DI (match_operand:DI 1 "register_operand" "0")
15662 (match_operand:DI 2 "nonimmediate_operand" "ym"))] 45))]
15663 "TARGET_MMX"
15664 "pxor\\t{%2, %0|%0, %2}"
15665 [(set_attr "type" "mmx")])
15666
15667 ;; Same as pxor, but don't show input operands so that we don't think
15668 ;; they are live.
15669 (define_insn "mmx_clrdi"
15670 [(set (match_operand:DI 0 "register_operand" "=y")
15671 (unspec:DI [(const_int 0)] 45))]
15672 "TARGET_MMX"
15673 "pxor\\t{%0, %0|%0, %0}"
15674 [(set_attr "type" "mmx")])
15675
15676 (define_insn "mmx_anddi3"
15677 [(set (match_operand:DI 0 "register_operand" "=y")
15678 (unspec:DI
15679 [(and:DI (match_operand:DI 1 "register_operand" "0")
15680 (match_operand:DI 2 "nonimmediate_operand" "ym"))] 45))]
15681 "TARGET_MMX"
15682 "pand\\t{%2, %0|%0, %2}"
15683 [(set_attr "type" "mmx")])
15684
15685 (define_insn "mmx_nanddi3"
15686 [(set (match_operand:DI 0 "register_operand" "=y")
15687 (unspec:DI
15688 [(and:DI (not:DI (match_operand:DI 1 "register_operand" "0"))
15689 (match_operand:DI 2 "nonimmediate_operand" "ym"))] 45))]
15690 "TARGET_MMX"
15691 "pandn\\t{%2, %0|%0, %2}"
15692 [(set_attr "type" "mmx")])
15693
15694
15695 ;; MMX unsigned averages/sum of absolute differences
15696
15697 (define_insn "mmx_uavgv8qi3"
15698 [(set (match_operand:V8QI 0 "register_operand" "=y")
15699 (ashiftrt:V8QI
15700 (plus:V8QI (plus:V8QI
15701 (match_operand:V8QI 1 "register_operand" "0")
15702 (match_operand:V8QI 2 "nonimmediate_operand" "ym"))
15703 (vec_const:V8QI (parallel [(const_int 1)
15704 (const_int 1)
15705 (const_int 1)
15706 (const_int 1)
15707 (const_int 1)
15708 (const_int 1)
15709 (const_int 1)
15710 (const_int 1)])))
15711 (const_int 1)))]
15712 "TARGET_SSE"
15713 "pavgb\\t{%2, %0|%0, %2}"
15714 [(set_attr "type" "sse")])
15715
15716 (define_insn "mmx_uavgv4hi3"
15717 [(set (match_operand:V4HI 0 "register_operand" "=y")
15718 (ashiftrt:V4HI
15719 (plus:V4HI (plus:V4HI
15720 (match_operand:V4HI 1 "register_operand" "0")
15721 (match_operand:V4HI 2 "nonimmediate_operand" "ym"))
15722 (vec_const:V4HI (parallel [(const_int 1)
15723 (const_int 1)
15724 (const_int 1)
15725 (const_int 1)])))
15726 (const_int 1)))]
15727 "TARGET_SSE"
15728 "pavgw\\t{%2, %0|%0, %2}"
15729 [(set_attr "type" "sse")])
15730
15731 (define_insn "mmx_psadbw"
15732 [(set (match_operand:V8QI 0 "register_operand" "=y")
15733 (abs:V8QI (minus:V8QI (match_operand:V8QI 1 "register_operand" "0")
15734 (match_operand:V8QI 2 "nonimmediate_operand" "ym"))))]
15735 "TARGET_SSE"
15736 "psadbw\\t{%2, %0|%0, %2}"
15737 [(set_attr "type" "sse")])
15738
15739
15740 ;; MMX insert/extract/shuffle
15741
15742 (define_insn "mmx_pinsrw"
15743 [(set (match_operand:V4HI 0 "register_operand" "=y")
15744 (vec_merge:V4HI (match_operand:V4HI 1 "register_operand" "0")
15745 (vec_duplicate:V4HI
15746 (truncate:HI (match_operand:SI 2 "nonimmediate_operand" "rm")))
15747 (match_operand:SI 3 "immediate_operand" "i")))]
15748 "TARGET_SSE"
15749 "pinsrw\\t{%3, %2, %0|%0, %2, %3}"
15750 [(set_attr "type" "sse")])
15751
15752 (define_insn "mmx_pextrw"
15753 [(set (match_operand:SI 0 "register_operand" "=r")
15754 (zero_extend:SI (vec_select:HI (match_operand:V4HI 1 "register_operand" "y")
15755 (parallel
15756 [(match_operand:SI 2 "immediate_operand" "i")]))))]
15757 "TARGET_SSE"
15758 "pextrw\\t{%2, %1, %0|%0, %1, %2}"
15759 [(set_attr "type" "sse")])
15760
15761 (define_insn "mmx_pshufw"
15762 [(set (match_operand:V4HI 0 "register_operand" "=y")
15763 (unspec:V4HI [(match_operand:V4HI 1 "register_operand" "0")
15764 (match_operand:V4HI 2 "nonimmediate_operand" "ym")
15765 (match_operand:SI 3 "immediate_operand" "i")] 41))]
15766 "TARGET_SSE"
15767 "pshufw\\t{%3, %2, %0|%0, %2, %3}"
15768 [(set_attr "type" "sse")])
15769
15770
15771 ;; MMX mask-generating comparisons
15772
15773 (define_insn "eqv8qi3"
15774 [(set (match_operand:V8QI 0 "register_operand" "=y")
15775 (eq:V8QI (match_operand:V8QI 1 "register_operand" "0")
15776 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
15777 "TARGET_MMX"
15778 "pcmpeqb\\t{%2, %0|%0, %2}"
15779 [(set_attr "type" "mmx")])
15780
15781 (define_insn "eqv4hi3"
15782 [(set (match_operand:V4HI 0 "register_operand" "=y")
15783 (eq:V4HI (match_operand:V4HI 1 "register_operand" "0")
15784 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15785 "TARGET_MMX"
15786 "pcmpeqw\\t{%2, %0|%0, %2}"
15787 [(set_attr "type" "mmx")])
15788
15789 (define_insn "eqv2si3"
15790 [(set (match_operand:V2SI 0 "register_operand" "=y")
15791 (eq:V2SI (match_operand:V2SI 1 "register_operand" "0")
15792 (match_operand:V2SI 2 "nonimmediate_operand" "ym")))]
15793 "TARGET_MMX"
15794 "pcmpeqd\\t{%2, %0|%0, %2}"
15795 [(set_attr "type" "mmx")])
15796
15797 (define_insn "gtv8qi3"
15798 [(set (match_operand:V8QI 0 "register_operand" "=y")
15799 (gt:V8QI (match_operand:V8QI 1 "register_operand" "0")
15800 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
15801 "TARGET_MMX"
15802 "pcmpgtb\\t{%2, %0|%0, %2}"
15803 [(set_attr "type" "mmx")])
15804
15805 (define_insn "gtv4hi3"
15806 [(set (match_operand:V4HI 0 "register_operand" "=y")
15807 (gt:V4HI (match_operand:V4HI 1 "register_operand" "0")
15808 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15809 "TARGET_MMX"
15810 "pcmpgtw\\t{%2, %0|%0, %2}"
15811 [(set_attr "type" "mmx")])
15812
15813 (define_insn "gtv2si3"
15814 [(set (match_operand:V2SI 0 "register_operand" "=y")
15815 (gt:V2SI (match_operand:V2SI 1 "register_operand" "0")
15816 (match_operand:V2SI 2 "nonimmediate_operand" "ym")))]
15817 "TARGET_MMX"
15818 "pcmpgtd\\t{%2, %0|%0, %2}"
15819 [(set_attr "type" "mmx")])
15820
15821
15822 ;; MMX max/min insns
15823
15824 (define_insn "umaxv8qi3"
15825 [(set (match_operand:V8QI 0 "register_operand" "=y")
15826 (umax:V8QI (match_operand:V8QI 1 "register_operand" "0")
15827 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
15828 "TARGET_SSE"
15829 "pmaxub\\t{%2, %0|%0, %2}"
15830 [(set_attr "type" "sse")])
15831
15832 (define_insn "smaxv4hi3"
15833 [(set (match_operand:V4HI 0 "register_operand" "=y")
15834 (smax:V4HI (match_operand:V4HI 1 "register_operand" "0")
15835 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15836 "TARGET_SSE"
15837 "pmaxsw\\t{%2, %0|%0, %2}"
15838 [(set_attr "type" "sse")])
15839
15840 (define_insn "uminv8qi3"
15841 [(set (match_operand:V8QI 0 "register_operand" "=y")
15842 (umin:V8QI (match_operand:V8QI 1 "register_operand" "0")
15843 (match_operand:V8QI 2 "nonimmediate_operand" "ym")))]
15844 "TARGET_SSE"
15845 "pminub\\t{%2, %0|%0, %2}"
15846 [(set_attr "type" "sse")])
15847
15848 (define_insn "sminv4hi3"
15849 [(set (match_operand:V4HI 0 "register_operand" "=y")
15850 (smin:V4HI (match_operand:V4HI 1 "register_operand" "0")
15851 (match_operand:V4HI 2 "nonimmediate_operand" "ym")))]
15852 "TARGET_SSE"
15853 "pminsw\\t{%2, %0|%0, %2}"
15854 [(set_attr "type" "sse")])
15855
15856
15857 ;; MMX shifts
15858
15859 (define_insn "ashrv4hi3"
15860 [(set (match_operand:V4HI 0 "register_operand" "=y")
15861 (ashiftrt:V4HI (match_operand:V4HI 1 "register_operand" "0")
15862 (match_operand:DI 2 "nonmemory_operand" "yi")))]
15863 "TARGET_MMX"
15864 "psraw\\t{%2, %0|%0, %2}"
15865 [(set_attr "type" "mmx")])
15866
15867 (define_insn "ashrv2si3"
15868 [(set (match_operand:V2SI 0 "register_operand" "=y")
15869 (ashiftrt:V2SI (match_operand:V2SI 1 "register_operand" "0")
15870 (match_operand:DI 2 "nonmemory_operand" "yi")))]
15871 "TARGET_MMX"
15872 "psrad\\t{%2, %0|%0, %2}"
15873 [(set_attr "type" "mmx")])
15874
15875 (define_insn "lshrv4hi3"
15876 [(set (match_operand:V4HI 0 "register_operand" "=y")
15877 (lshiftrt:V4HI (match_operand:V4HI 1 "register_operand" "0")
15878 (match_operand:DI 2 "nonmemory_operand" "yi")))]
15879 "TARGET_MMX"
15880 "psrlw\\t{%2, %0|%0, %2}"
15881 [(set_attr "type" "mmx")])
15882
15883 (define_insn "lshrv2si3"
15884 [(set (match_operand:V2SI 0 "register_operand" "=y")
15885 (lshiftrt:V2SI (match_operand:V2SI 1 "register_operand" "0")
15886 (match_operand:DI 2 "nonmemory_operand" "yi")))]
15887 "TARGET_MMX"
15888 "psrld\\t{%2, %0|%0, %2}"
15889 [(set_attr "type" "mmx")])
15890
15891 ;; See logical MMX insns.
15892 (define_insn "mmx_lshrdi3"
15893 [(set (match_operand:DI 0 "register_operand" "=y")
15894 (unspec:DI
15895 [(lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
15896 (match_operand:DI 2 "nonmemory_operand" "yi"))] 45))]
15897 "TARGET_MMX"
15898 "psrlq\\t{%2, %0|%0, %2}"
15899 [(set_attr "type" "mmx")])
15900
15901 (define_insn "ashlv4hi3"
15902 [(set (match_operand:V4HI 0 "register_operand" "=y")
15903 (ashift:V4HI (match_operand:V4HI 1 "register_operand" "0")
15904 (match_operand:DI 2 "nonmemory_operand" "yi")))]
15905 "TARGET_MMX"
15906 "psllw\\t{%2, %0|%0, %2}"
15907 [(set_attr "type" "mmx")])
15908
15909 (define_insn "ashlv2si3"
15910 [(set (match_operand:V2SI 0 "register_operand" "=y")
15911 (ashift:V2SI (match_operand:V2SI 1 "register_operand" "0")
15912 (match_operand:DI 2 "nonmemory_operand" "yi")))]
15913 "TARGET_MMX"
15914 "pslld\\t{%2, %0|%0, %2}"
15915 [(set_attr "type" "mmx")])
15916
15917 ;; See logical MMX insns.
15918 (define_insn "mmx_ashldi3"
15919 [(set (match_operand:DI 0 "register_operand" "=y")
15920 (unspec:DI
15921 [(ashift:DI (match_operand:DI 1 "register_operand" "0")
15922 (match_operand:DI 2 "nonmemory_operand" "yi"))] 45))]
15923 "TARGET_MMX"
15924 "psllq\\t{%2, %0|%0, %2}"
15925 [(set_attr "type" "mmx")])
15926
15927
15928 ;; MMX pack/unpack insns.
15929
15930 (define_insn "mmx_packsswb"
15931 [(set (match_operand:V8QI 0 "register_operand" "=y")
15932 (vec_concat:V8QI
15933 (ss_truncate:V4QI (match_operand:V4HI 1 "register_operand" "0"))
15934 (ss_truncate:V4QI (match_operand:V4HI 2 "register_operand" "y"))))]
15935 "TARGET_MMX"
15936 "packsswb\\t{%2, %0|%0, %2}"
15937 [(set_attr "type" "mmx")])
15938
15939 (define_insn "mmx_packssdw"
15940 [(set (match_operand:V4HI 0 "register_operand" "=y")
15941 (vec_concat:V4HI
15942 (ss_truncate:V2HI (match_operand:V2SI 1 "register_operand" "0"))
15943 (ss_truncate:V2HI (match_operand:V2SI 2 "register_operand" "y"))))]
15944 "TARGET_MMX"
15945 "packssdw\\t{%2, %0|%0, %2}"
15946 [(set_attr "type" "mmx")])
15947
15948 (define_insn "mmx_packuswb"
15949 [(set (match_operand:V8QI 0 "register_operand" "=y")
15950 (vec_concat:V8QI
15951 (us_truncate:V4QI (match_operand:V4HI 1 "register_operand" "0"))
15952 (us_truncate:V4QI (match_operand:V4HI 2 "register_operand" "y"))))]
15953 "TARGET_MMX"
15954 "packuswb\\t{%2, %0|%0, %2}"
15955 [(set_attr "type" "mmx")])
15956
15957 (define_insn "mmx_punpckhbw"
15958 [(set (match_operand:V8QI 0 "register_operand" "=y")
15959 (vec_merge:V8QI
15960 (vec_select:V8QI (match_operand:V8QI 1 "register_operand" "0")
15961 (parallel [(const_int 4)
15962 (const_int 0)
15963 (const_int 5)
15964 (const_int 1)
15965 (const_int 6)
15966 (const_int 2)
15967 (const_int 7)
15968 (const_int 3)]))
15969 (vec_select:V8QI (match_operand:V8QI 2 "register_operand" "y")
15970 (parallel [(const_int 0)
15971 (const_int 4)
15972 (const_int 1)
15973 (const_int 5)
15974 (const_int 2)
15975 (const_int 6)
15976 (const_int 3)
15977 (const_int 7)]))
15978 (const_int 85)))]
15979 "TARGET_MMX"
15980 "punpckhbw\\t{%2, %0|%0, %2}"
15981 [(set_attr "type" "mmx")])
15982
15983 (define_insn "mmx_punpckhwd"
15984 [(set (match_operand:V4HI 0 "register_operand" "=y")
15985 (vec_merge:V4HI
15986 (vec_select:V4HI (match_operand:V4HI 1 "register_operand" "0")
15987 (parallel [(const_int 0)
15988 (const_int 2)
15989 (const_int 1)
15990 (const_int 3)]))
15991 (vec_select:V4HI (match_operand:V4HI 2 "register_operand" "y")
15992 (parallel [(const_int 2)
15993 (const_int 0)
15994 (const_int 3)
15995 (const_int 1)]))
15996 (const_int 5)))]
15997 "TARGET_MMX"
15998 "punpckhwd\\t{%2, %0|%0, %2}"
15999 [(set_attr "type" "mmx")])
16000
16001 (define_insn "mmx_punpckhdq"
16002 [(set (match_operand:V2SI 0 "register_operand" "=y")
16003 (vec_merge:V2SI
16004 (vec_select:V2SI (match_operand:V2SI 1 "register_operand" "0")
16005 (parallel [(const_int 0)
16006 (const_int 1)]))
16007 (vec_select:V2SI (match_operand:V2SI 2 "register_operand" "y")
16008 (parallel [(const_int 1)
16009 (const_int 0)]))
16010 (const_int 1)))]
16011 "TARGET_MMX"
16012 "punpckhdq\\t{%2, %0|%0, %2}"
16013 [(set_attr "type" "mmx")])
16014
16015 (define_insn "mmx_punpcklbw"
16016 [(set (match_operand:V8QI 0 "register_operand" "=y")
16017 (vec_merge:V8QI
16018 (vec_select:V8QI (match_operand:V8QI 1 "register_operand" "0")
16019 (parallel [(const_int 0)
16020 (const_int 4)
16021 (const_int 1)
16022 (const_int 5)
16023 (const_int 2)
16024 (const_int 6)
16025 (const_int 3)
16026 (const_int 7)]))
16027 (vec_select:V8QI (match_operand:V8QI 2 "register_operand" "y")
16028 (parallel [(const_int 4)
16029 (const_int 0)
16030 (const_int 5)
16031 (const_int 1)
16032 (const_int 6)
16033 (const_int 2)
16034 (const_int 7)
16035 (const_int 3)]))
16036 (const_int 85)))]
16037 "TARGET_MMX"
16038 "punpcklbw\\t{%2, %0|%0, %2}"
16039 [(set_attr "type" "mmx")])
16040
16041 (define_insn "mmx_punpcklwd"
16042 [(set (match_operand:V4HI 0 "register_operand" "=y")
16043 (vec_merge:V4HI
16044 (vec_select:V4HI (match_operand:V4HI 1 "register_operand" "0")
16045 (parallel [(const_int 2)
16046 (const_int 0)
16047 (const_int 3)
16048 (const_int 1)]))
16049 (vec_select:V4HI (match_operand:V4HI 2 "register_operand" "y")
16050 (parallel [(const_int 0)
16051 (const_int 2)
16052 (const_int 1)
16053 (const_int 3)]))
16054 (const_int 5)))]
16055 "TARGET_MMX"
16056 "punpcklwd\\t{%2, %0|%0, %2}"
16057 [(set_attr "type" "mmx")])
16058
16059 (define_insn "mmx_punpckldq"
16060 [(set (match_operand:V2SI 0 "register_operand" "=y")
16061 (vec_merge:V2SI
16062 (vec_select:V2SI (match_operand:V2SI 1 "register_operand" "0")
16063 (parallel [(const_int 1)
16064 (const_int 0)]))
16065 (vec_select:V2SI (match_operand:V2SI 2 "register_operand" "y")
16066 (parallel [(const_int 0)
16067 (const_int 1)]))
16068 (const_int 1)))]
16069 "TARGET_MMX"
16070 "punpckldq\\t{%2, %0|%0, %2}"
16071 [(set_attr "type" "mmx")])
16072
16073
16074 ;; Miscellaneous stuff
16075
16076 (define_insn "emms"
16077 [(unspec_volatile [(const_int 0)] 31)
16078 (clobber (reg:XF 8))
16079 (clobber (reg:XF 9))
16080 (clobber (reg:XF 10))
16081 (clobber (reg:XF 11))
16082 (clobber (reg:XF 12))
16083 (clobber (reg:XF 13))
16084 (clobber (reg:XF 14))
16085 (clobber (reg:XF 15))
16086 (clobber (reg:DI 29))
16087 (clobber (reg:DI 30))
16088 (clobber (reg:DI 31))
16089 (clobber (reg:DI 32))
16090 (clobber (reg:DI 33))
16091 (clobber (reg:DI 34))
16092 (clobber (reg:DI 35))
16093 (clobber (reg:DI 36))]
16094 "TARGET_MMX"
16095 "emms"
16096 [(set_attr "type" "mmx")
16097 (set_attr "memory" "unknown")])
16098
16099 (define_insn "ldmxcsr"
16100 [(unspec_volatile [(match_operand:SI 0 "memory_operand" "m")] 37)]
16101 "TARGET_MMX"
16102 "ldmxcsr\\t%0"
16103 [(set_attr "type" "mmx")])
16104
16105 (define_insn "stmxcsr"
16106 [(set (match_operand:SI 0 "memory_operand" "=m")
16107 (unspec_volatile:SI [(const_int 0)] 40))]
16108 "TARGET_MMX"
16109 "stmxcsr\\t%0"
16110 [(set_attr "type" "mmx")])
16111
16112 (define_expand "sfence"
16113 [(set (match_dup 0)
16114 (unspec:BLK [(match_dup 0)] 44))]
16115 "TARGET_SSE"
16116 "
16117 {
16118 operands[0] = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (Pmode));
16119 MEM_VOLATILE_P (operands[0]) = 1;
16120 }")
16121
16122 (define_insn "*sfence_insn"
16123 [(set (match_operand:BLK 0 "" "")
16124 (unspec:BLK [(match_dup 0)] 44))]
16125 "TARGET_SSE"
16126 "sfence"
16127 [(set_attr "type" "sse")
16128 (set_attr "memory" "unknown")])
16129
16130 (define_insn "prefetch"
16131 [(unspec [(match_operand:SI 0 "address_operand" "p")
16132 (match_operand:SI 1 "immediate_operand" "n")] 35)]
16133 "TARGET_SSE"
16134 "*
16135 {
16136 switch (INTVAL (operands[1]))
16137 {
16138 case 0:
16139 return \"prefetchnta\\t%a0\";
16140 case 1:
16141 return \"prefetcht0\\t%a0\";
16142 case 2:
16143 return \"prefetcht1\\t%a0\";
16144 case 3:
16145 return \"prefetcht2\\t%a0\";
16146 default:
16147 abort ();
16148 }
16149 }"
16150 [(set_attr "type" "sse")])
16151