1 ;; GCC machine description for IA-32 and x86-64.
2 ;; Copyright (C) 1988, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
3 ;; 2001, 2002, 2003, 2004, 2005
4 ;; Free Software Foundation, Inc.
5 ;; Mostly by William Schelter.
6 ;; x86_64 support added by Jan Hubicka
8 ;; This file is part of GCC.
10 ;; GCC is free software; you can redistribute it and/or modify
11 ;; it under the terms of the GNU General Public License as published by
12 ;; the Free Software Foundation; either version 2, or (at your option)
15 ;; GCC is distributed in the hope that it will be useful,
16 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 ;; GNU General Public License for more details.
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GCC; see the file COPYING. If not, write to
22 ;; the Free Software Foundation, 51 Franklin Street, Fifth Floor,
23 ;; Boston, MA 02110-1301, USA. */
25 ;; The original PO technology requires these to be ordered by speed,
26 ;; so that assigner will pick the fastest.
28 ;; See file "rtl.def" for documentation on define_insn, match_*, et. al.
30 ;; Macro REG_CLASS_FROM_LETTER in file i386.h defines the register
31 ;; constraint letters.
33 ;; The special asm out single letter directives following a '%' are:
34 ;; 'z' mov%z1 would be movl, movw, or movb depending on the mode of
36 ;; 'L' Print the opcode suffix for a 32-bit integer opcode.
37 ;; 'W' Print the opcode suffix for a 16-bit integer opcode.
38 ;; 'B' Print the opcode suffix for an 8-bit integer opcode.
39 ;; 'Q' Print the opcode suffix for a 64-bit float opcode.
40 ;; 'S' Print the opcode suffix for a 32-bit float opcode.
41 ;; 'T' Print the opcode suffix for an 80-bit extended real XFmode float opcode.
42 ;; 'J' Print the appropriate jump operand.
44 ;; 'b' Print the QImode name of the register for the indicated operand.
45 ;; %b0 would print %al if operands[0] is reg 0.
46 ;; 'w' Likewise, print the HImode name of the register.
47 ;; 'k' Likewise, print the SImode name of the register.
48 ;; 'h' Print the QImode name for a "high" register, either ah, bh, ch or dh.
49 ;; 'y' Print "st(0)" instead of "st" as a register.
54 [; Relocation specifiers
66 (UNSPEC_STACK_ALLOC 11)
68 (UNSPEC_SSE_PROLOGUE_SAVE 13)
75 (UNSPEC_TLS_LD_BASE 18)
77 ; Other random patterns
87 ; For SSE/MMX support:
88 (UNSPEC_FIX_NOTRUNC 30)
96 (UNSPEC_NOP 38) ; prevents combiner cleverness
107 ; Generic math support
109 (UNSPEC_IEEE_MIN 51) ; not commutative
110 (UNSPEC_IEEE_MAX 52) ; not commutative
123 (UNSPEC_FRNDINT_FLOOR 70)
124 (UNSPEC_FRNDINT_CEIL 71)
125 (UNSPEC_FRNDINT_TRUNC 72)
126 (UNSPEC_FRNDINT_MASK_PM 73)
127 (UNSPEC_FIST_FLOOR 74)
128 (UNSPEC_FIST_CEIL 75)
130 ; x87 Double output FP
131 (UNSPEC_SINCOS_COS 80)
132 (UNSPEC_SINCOS_SIN 81)
135 (UNSPEC_XTRACT_FRACT 84)
136 (UNSPEC_XTRACT_EXP 85)
137 (UNSPEC_FSCALE_FRACT 86)
138 (UNSPEC_FSCALE_EXP 87)
147 (UNSPEC_SP_TLS_SET 102)
148 (UNSPEC_SP_TLS_TEST 103)
152 [(UNSPECV_BLOCKAGE 0)
153 (UNSPECV_STACK_PROBE 1)
162 (UNSPECV_CMPXCHG_1 10)
163 (UNSPECV_CMPXCHG_2 11)
168 ;; Registers by name.
177 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
180 ;; In C guard expressions, put expressions which may be compile-time
181 ;; constants first. This allows for better optimization. For
182 ;; example, write "TARGET_64BIT && reload_completed", not
183 ;; "reload_completed && TARGET_64BIT".
186 ;; Processor type. This attribute must exactly match the processor_type
187 ;; enumeration in i386.h.
188 (define_attr "cpu" "i386,i486,pentium,pentiumpro,k6,athlon,pentium4,k8,nocona"
189 (const (symbol_ref "ix86_tune")))
191 ;; A basic instruction type. Refinements due to arguments to be
192 ;; provided in other attributes.
195 alu,alu1,negnot,imov,imovx,lea,
196 incdec,ishift,ishift1,rotate,rotate1,imul,idiv,
197 icmp,test,ibr,setcc,icmov,
198 push,pop,call,callv,leave,
200 fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint,
201 sselog,sselog1,sseiadd,sseishft,sseimul,
202 sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv,
203 mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft"
204 (const_string "other"))
206 ;; Main data type used by the insn
208 "unknown,none,QI,HI,SI,DI,SF,DF,XF,TI,V4SF,V2DF,V2SF,V1DF"
209 (const_string "unknown"))
211 ;; The CPU unit operations uses.
212 (define_attr "unit" "integer,i387,sse,mmx,unknown"
213 (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint")
214 (const_string "i387")
215 (eq_attr "type" "sselog,sselog1,sseiadd,sseishft,sseimul,
216 sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv")
218 (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft")
220 (eq_attr "type" "other")
221 (const_string "unknown")]
222 (const_string "integer")))
224 ;; The (bounding maximum) length of an instruction immediate.
225 (define_attr "length_immediate" ""
226 (cond [(eq_attr "type" "incdec,setcc,icmov,str,cld,lea,other,multi,idiv,leave")
228 (eq_attr "unit" "i387,sse,mmx")
230 (eq_attr "type" "alu,alu1,negnot,imovx,ishift,rotate,ishift1,rotate1,
232 (symbol_ref "ix86_attr_length_immediate_default(insn,1)")
233 (eq_attr "type" "imov,test")
234 (symbol_ref "ix86_attr_length_immediate_default(insn,0)")
235 (eq_attr "type" "call")
236 (if_then_else (match_operand 0 "constant_call_address_operand" "")
239 (eq_attr "type" "callv")
240 (if_then_else (match_operand 1 "constant_call_address_operand" "")
243 ;; We don't know the size before shorten_branches. Expect
244 ;; the instruction to fit for better scheduling.
245 (eq_attr "type" "ibr")
248 (symbol_ref "/* Update immediate_length and other attributes! */
249 gcc_unreachable (),1")))
251 ;; The (bounding maximum) length of an instruction address.
252 (define_attr "length_address" ""
253 (cond [(eq_attr "type" "str,cld,other,multi,fxch")
255 (and (eq_attr "type" "call")
256 (match_operand 0 "constant_call_address_operand" ""))
258 (and (eq_attr "type" "callv")
259 (match_operand 1 "constant_call_address_operand" ""))
262 (symbol_ref "ix86_attr_length_address_default (insn)")))
264 ;; Set when length prefix is used.
265 (define_attr "prefix_data16" ""
266 (if_then_else (ior (eq_attr "mode" "HI")
267 (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF")))
271 ;; Set when string REP prefix is used.
272 (define_attr "prefix_rep" ""
273 (if_then_else (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF"))
277 ;; Set when 0f opcode prefix is used.
278 (define_attr "prefix_0f" ""
280 (ior (eq_attr "type" "imovx,setcc,icmov")
281 (eq_attr "unit" "sse,mmx"))
285 ;; Set when REX opcode prefix is used.
286 (define_attr "prefix_rex" ""
287 (cond [(and (eq_attr "mode" "DI")
288 (eq_attr "type" "!push,pop,call,callv,leave,ibr"))
290 (and (eq_attr "mode" "QI")
291 (ne (symbol_ref "x86_extended_QIreg_mentioned_p (insn)")
294 (ne (symbol_ref "x86_extended_reg_mentioned_p (insn)")
300 ;; Set when modrm byte is used.
301 (define_attr "modrm" ""
302 (cond [(eq_attr "type" "str,cld,leave")
304 (eq_attr "unit" "i387")
306 (and (eq_attr "type" "incdec")
307 (ior (match_operand:SI 1 "register_operand" "")
308 (match_operand:HI 1 "register_operand" "")))
310 (and (eq_attr "type" "push")
311 (not (match_operand 1 "memory_operand" "")))
313 (and (eq_attr "type" "pop")
314 (not (match_operand 0 "memory_operand" "")))
316 (and (eq_attr "type" "imov")
317 (ior (and (match_operand 0 "register_operand" "")
318 (match_operand 1 "immediate_operand" ""))
319 (ior (and (match_operand 0 "ax_reg_operand" "")
320 (match_operand 1 "memory_displacement_only_operand" ""))
321 (and (match_operand 0 "memory_displacement_only_operand" "")
322 (match_operand 1 "ax_reg_operand" "")))))
324 (and (eq_attr "type" "call")
325 (match_operand 0 "constant_call_address_operand" ""))
327 (and (eq_attr "type" "callv")
328 (match_operand 1 "constant_call_address_operand" ""))
333 ;; The (bounding maximum) length of an instruction in bytes.
334 ;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences.
335 ;; Later we may want to split them and compute proper length as for
337 (define_attr "length" ""
338 (cond [(eq_attr "type" "other,multi,fistp,frndint")
340 (eq_attr "type" "fcmp")
342 (eq_attr "unit" "i387")
344 (plus (attr "prefix_data16")
345 (attr "length_address")))]
346 (plus (plus (attr "modrm")
347 (plus (attr "prefix_0f")
348 (plus (attr "prefix_rex")
350 (plus (attr "prefix_rep")
351 (plus (attr "prefix_data16")
352 (plus (attr "length_immediate")
353 (attr "length_address")))))))
355 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
356 ;; `store' if there is a simple memory reference therein, or `unknown'
357 ;; if the instruction is complex.
359 (define_attr "memory" "none,load,store,both,unknown"
360 (cond [(eq_attr "type" "other,multi,str")
361 (const_string "unknown")
362 (eq_attr "type" "lea,fcmov,fpspc,cld")
363 (const_string "none")
364 (eq_attr "type" "fistp,leave")
365 (const_string "both")
366 (eq_attr "type" "frndint")
367 (const_string "load")
368 (eq_attr "type" "push")
369 (if_then_else (match_operand 1 "memory_operand" "")
370 (const_string "both")
371 (const_string "store"))
372 (eq_attr "type" "pop")
373 (if_then_else (match_operand 0 "memory_operand" "")
374 (const_string "both")
375 (const_string "load"))
376 (eq_attr "type" "setcc")
377 (if_then_else (match_operand 0 "memory_operand" "")
378 (const_string "store")
379 (const_string "none"))
380 (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp")
381 (if_then_else (ior (match_operand 0 "memory_operand" "")
382 (match_operand 1 "memory_operand" ""))
383 (const_string "load")
384 (const_string "none"))
385 (eq_attr "type" "ibr")
386 (if_then_else (match_operand 0 "memory_operand" "")
387 (const_string "load")
388 (const_string "none"))
389 (eq_attr "type" "call")
390 (if_then_else (match_operand 0 "constant_call_address_operand" "")
391 (const_string "none")
392 (const_string "load"))
393 (eq_attr "type" "callv")
394 (if_then_else (match_operand 1 "constant_call_address_operand" "")
395 (const_string "none")
396 (const_string "load"))
397 (and (eq_attr "type" "alu1,negnot,ishift1,sselog1")
398 (match_operand 1 "memory_operand" ""))
399 (const_string "both")
400 (and (match_operand 0 "memory_operand" "")
401 (match_operand 1 "memory_operand" ""))
402 (const_string "both")
403 (match_operand 0 "memory_operand" "")
404 (const_string "store")
405 (match_operand 1 "memory_operand" "")
406 (const_string "load")
408 "!alu1,negnot,ishift1,
409 imov,imovx,icmp,test,
411 sse,ssemov,ssecmp,ssecomi,ssecvt,sseicvt,sselog1,
412 mmx,mmxmov,mmxcmp,mmxcvt")
413 (match_operand 2 "memory_operand" ""))
414 (const_string "load")
415 (and (eq_attr "type" "icmov")
416 (match_operand 3 "memory_operand" ""))
417 (const_string "load")
419 (const_string "none")))
421 ;; Indicates if an instruction has both an immediate and a displacement.
423 (define_attr "imm_disp" "false,true,unknown"
424 (cond [(eq_attr "type" "other,multi")
425 (const_string "unknown")
426 (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1")
427 (and (match_operand 0 "memory_displacement_operand" "")
428 (match_operand 1 "immediate_operand" "")))
429 (const_string "true")
430 (and (eq_attr "type" "alu,ishift,rotate,imul,idiv")
431 (and (match_operand 0 "memory_displacement_operand" "")
432 (match_operand 2 "immediate_operand" "")))
433 (const_string "true")
435 (const_string "false")))
437 ;; Indicates if an FP operation has an integer source.
439 (define_attr "fp_int_src" "false,true"
440 (const_string "false"))
442 ;; Defines rounding mode of an FP operation.
444 (define_attr "i387_cw" "trunc,floor,ceil,mask_pm,uninitialized,any"
445 (const_string "any"))
447 ;; Describe a user's asm statement.
448 (define_asm_attributes
449 [(set_attr "length" "128")
450 (set_attr "type" "multi")])
452 ;; All x87 floating point modes
453 (define_mode_macro X87MODEF [SF DF XF])
455 ;; All integer modes handled by x87 fisttp operator.
456 (define_mode_macro X87MODEI [HI SI DI])
458 ;; All integer modes handled by integer x87 operators.
459 (define_mode_macro X87MODEI12 [HI SI])
461 ;; All SSE floating point modes
462 (define_mode_macro SSEMODEF [SF DF])
464 ;; All integer modes handled by SSE cvtts?2si* operators.
465 (define_mode_macro SSEMODEI24 [SI DI])
468 ;; Scheduling descriptions
470 (include "pentium.md")
473 (include "athlon.md")
476 ;; Operand and operator predicates
478 (include "predicates.md")
481 ;; Compare instructions.
483 ;; All compare insns have expanders that save the operands away without
484 ;; actually generating RTL. The bCOND or sCOND (emitted immediately
485 ;; after the cmp) will actually emit the cmpM.
487 (define_expand "cmpti"
488 [(set (reg:CC FLAGS_REG)
489 (compare:CC (match_operand:TI 0 "nonimmediate_operand" "")
490 (match_operand:TI 1 "x86_64_general_operand" "")))]
493 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
494 operands[0] = force_reg (TImode, operands[0]);
495 ix86_compare_op0 = operands[0];
496 ix86_compare_op1 = operands[1];
500 (define_expand "cmpdi"
501 [(set (reg:CC FLAGS_REG)
502 (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
503 (match_operand:DI 1 "x86_64_general_operand" "")))]
506 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
507 operands[0] = force_reg (DImode, operands[0]);
508 ix86_compare_op0 = operands[0];
509 ix86_compare_op1 = operands[1];
513 (define_expand "cmpsi"
514 [(set (reg:CC FLAGS_REG)
515 (compare:CC (match_operand:SI 0 "cmpsi_operand" "")
516 (match_operand:SI 1 "general_operand" "")))]
519 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
520 operands[0] = force_reg (SImode, operands[0]);
521 ix86_compare_op0 = operands[0];
522 ix86_compare_op1 = operands[1];
526 (define_expand "cmphi"
527 [(set (reg:CC FLAGS_REG)
528 (compare:CC (match_operand:HI 0 "nonimmediate_operand" "")
529 (match_operand:HI 1 "general_operand" "")))]
532 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
533 operands[0] = force_reg (HImode, operands[0]);
534 ix86_compare_op0 = operands[0];
535 ix86_compare_op1 = operands[1];
539 (define_expand "cmpqi"
540 [(set (reg:CC FLAGS_REG)
541 (compare:CC (match_operand:QI 0 "nonimmediate_operand" "")
542 (match_operand:QI 1 "general_operand" "")))]
545 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
546 operands[0] = force_reg (QImode, operands[0]);
547 ix86_compare_op0 = operands[0];
548 ix86_compare_op1 = operands[1];
552 (define_insn "cmpdi_ccno_1_rex64"
553 [(set (reg FLAGS_REG)
554 (compare (match_operand:DI 0 "nonimmediate_operand" "r,?mr")
555 (match_operand:DI 1 "const0_operand" "n,n")))]
556 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
558 test{q}\t{%0, %0|%0, %0}
559 cmp{q}\t{%1, %0|%0, %1}"
560 [(set_attr "type" "test,icmp")
561 (set_attr "length_immediate" "0,1")
562 (set_attr "mode" "DI")])
564 (define_insn "*cmpdi_minus_1_rex64"
565 [(set (reg FLAGS_REG)
566 (compare (minus:DI (match_operand:DI 0 "nonimmediate_operand" "rm,r")
567 (match_operand:DI 1 "x86_64_general_operand" "re,mr"))
569 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)"
570 "cmp{q}\t{%1, %0|%0, %1}"
571 [(set_attr "type" "icmp")
572 (set_attr "mode" "DI")])
574 (define_expand "cmpdi_1_rex64"
575 [(set (reg:CC FLAGS_REG)
576 (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
577 (match_operand:DI 1 "general_operand" "")))]
581 (define_insn "cmpdi_1_insn_rex64"
582 [(set (reg FLAGS_REG)
583 (compare (match_operand:DI 0 "nonimmediate_operand" "mr,r")
584 (match_operand:DI 1 "x86_64_general_operand" "re,mr")))]
585 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
586 "cmp{q}\t{%1, %0|%0, %1}"
587 [(set_attr "type" "icmp")
588 (set_attr "mode" "DI")])
591 (define_insn "*cmpsi_ccno_1"
592 [(set (reg FLAGS_REG)
593 (compare (match_operand:SI 0 "nonimmediate_operand" "r,?mr")
594 (match_operand:SI 1 "const0_operand" "n,n")))]
595 "ix86_match_ccmode (insn, CCNOmode)"
597 test{l}\t{%0, %0|%0, %0}
598 cmp{l}\t{%1, %0|%0, %1}"
599 [(set_attr "type" "test,icmp")
600 (set_attr "length_immediate" "0,1")
601 (set_attr "mode" "SI")])
603 (define_insn "*cmpsi_minus_1"
604 [(set (reg FLAGS_REG)
605 (compare (minus:SI (match_operand:SI 0 "nonimmediate_operand" "rm,r")
606 (match_operand:SI 1 "general_operand" "ri,mr"))
608 "ix86_match_ccmode (insn, CCGOCmode)"
609 "cmp{l}\t{%1, %0|%0, %1}"
610 [(set_attr "type" "icmp")
611 (set_attr "mode" "SI")])
613 (define_expand "cmpsi_1"
614 [(set (reg:CC FLAGS_REG)
615 (compare:CC (match_operand:SI 0 "nonimmediate_operand" "rm,r")
616 (match_operand:SI 1 "general_operand" "ri,mr")))]
620 (define_insn "*cmpsi_1_insn"
621 [(set (reg FLAGS_REG)
622 (compare (match_operand:SI 0 "nonimmediate_operand" "rm,r")
623 (match_operand:SI 1 "general_operand" "ri,mr")))]
624 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
625 && ix86_match_ccmode (insn, CCmode)"
626 "cmp{l}\t{%1, %0|%0, %1}"
627 [(set_attr "type" "icmp")
628 (set_attr "mode" "SI")])
630 (define_insn "*cmphi_ccno_1"
631 [(set (reg FLAGS_REG)
632 (compare (match_operand:HI 0 "nonimmediate_operand" "r,?mr")
633 (match_operand:HI 1 "const0_operand" "n,n")))]
634 "ix86_match_ccmode (insn, CCNOmode)"
636 test{w}\t{%0, %0|%0, %0}
637 cmp{w}\t{%1, %0|%0, %1}"
638 [(set_attr "type" "test,icmp")
639 (set_attr "length_immediate" "0,1")
640 (set_attr "mode" "HI")])
642 (define_insn "*cmphi_minus_1"
643 [(set (reg FLAGS_REG)
644 (compare (minus:HI (match_operand:HI 0 "nonimmediate_operand" "rm,r")
645 (match_operand:HI 1 "general_operand" "ri,mr"))
647 "ix86_match_ccmode (insn, CCGOCmode)"
648 "cmp{w}\t{%1, %0|%0, %1}"
649 [(set_attr "type" "icmp")
650 (set_attr "mode" "HI")])
652 (define_insn "*cmphi_1"
653 [(set (reg FLAGS_REG)
654 (compare (match_operand:HI 0 "nonimmediate_operand" "rm,r")
655 (match_operand:HI 1 "general_operand" "ri,mr")))]
656 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
657 && ix86_match_ccmode (insn, CCmode)"
658 "cmp{w}\t{%1, %0|%0, %1}"
659 [(set_attr "type" "icmp")
660 (set_attr "mode" "HI")])
662 (define_insn "*cmpqi_ccno_1"
663 [(set (reg FLAGS_REG)
664 (compare (match_operand:QI 0 "nonimmediate_operand" "q,?mq")
665 (match_operand:QI 1 "const0_operand" "n,n")))]
666 "ix86_match_ccmode (insn, CCNOmode)"
668 test{b}\t{%0, %0|%0, %0}
669 cmp{b}\t{$0, %0|%0, 0}"
670 [(set_attr "type" "test,icmp")
671 (set_attr "length_immediate" "0,1")
672 (set_attr "mode" "QI")])
674 (define_insn "*cmpqi_1"
675 [(set (reg FLAGS_REG)
676 (compare (match_operand:QI 0 "nonimmediate_operand" "qm,q")
677 (match_operand:QI 1 "general_operand" "qi,mq")))]
678 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
679 && ix86_match_ccmode (insn, CCmode)"
680 "cmp{b}\t{%1, %0|%0, %1}"
681 [(set_attr "type" "icmp")
682 (set_attr "mode" "QI")])
684 (define_insn "*cmpqi_minus_1"
685 [(set (reg FLAGS_REG)
686 (compare (minus:QI (match_operand:QI 0 "nonimmediate_operand" "qm,q")
687 (match_operand:QI 1 "general_operand" "qi,mq"))
689 "ix86_match_ccmode (insn, CCGOCmode)"
690 "cmp{b}\t{%1, %0|%0, %1}"
691 [(set_attr "type" "icmp")
692 (set_attr "mode" "QI")])
694 (define_insn "*cmpqi_ext_1"
695 [(set (reg FLAGS_REG)
697 (match_operand:QI 0 "general_operand" "Qm")
700 (match_operand 1 "ext_register_operand" "Q")
703 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
704 "cmp{b}\t{%h1, %0|%0, %h1}"
705 [(set_attr "type" "icmp")
706 (set_attr "mode" "QI")])
708 (define_insn "*cmpqi_ext_1_rex64"
709 [(set (reg FLAGS_REG)
711 (match_operand:QI 0 "register_operand" "Q")
714 (match_operand 1 "ext_register_operand" "Q")
717 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
718 "cmp{b}\t{%h1, %0|%0, %h1}"
719 [(set_attr "type" "icmp")
720 (set_attr "mode" "QI")])
722 (define_insn "*cmpqi_ext_2"
723 [(set (reg FLAGS_REG)
727 (match_operand 0 "ext_register_operand" "Q")
730 (match_operand:QI 1 "const0_operand" "n")))]
731 "ix86_match_ccmode (insn, CCNOmode)"
733 [(set_attr "type" "test")
734 (set_attr "length_immediate" "0")
735 (set_attr "mode" "QI")])
737 (define_expand "cmpqi_ext_3"
738 [(set (reg:CC FLAGS_REG)
742 (match_operand 0 "ext_register_operand" "")
745 (match_operand:QI 1 "general_operand" "")))]
749 (define_insn "cmpqi_ext_3_insn"
750 [(set (reg FLAGS_REG)
754 (match_operand 0 "ext_register_operand" "Q")
757 (match_operand:QI 1 "general_operand" "Qmn")))]
758 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
759 "cmp{b}\t{%1, %h0|%h0, %1}"
760 [(set_attr "type" "icmp")
761 (set_attr "mode" "QI")])
763 (define_insn "cmpqi_ext_3_insn_rex64"
764 [(set (reg FLAGS_REG)
768 (match_operand 0 "ext_register_operand" "Q")
771 (match_operand:QI 1 "nonmemory_operand" "Qn")))]
772 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
773 "cmp{b}\t{%1, %h0|%h0, %1}"
774 [(set_attr "type" "icmp")
775 (set_attr "mode" "QI")])
777 (define_insn "*cmpqi_ext_4"
778 [(set (reg FLAGS_REG)
782 (match_operand 0 "ext_register_operand" "Q")
787 (match_operand 1 "ext_register_operand" "Q")
790 "ix86_match_ccmode (insn, CCmode)"
791 "cmp{b}\t{%h1, %h0|%h0, %h1}"
792 [(set_attr "type" "icmp")
793 (set_attr "mode" "QI")])
795 ;; These implement float point compares.
796 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
797 ;; which would allow mix and match FP modes on the compares. Which is what
798 ;; the old patterns did, but with many more of them.
800 (define_expand "cmpxf"
801 [(set (reg:CC FLAGS_REG)
802 (compare:CC (match_operand:XF 0 "nonmemory_operand" "")
803 (match_operand:XF 1 "nonmemory_operand" "")))]
806 ix86_compare_op0 = operands[0];
807 ix86_compare_op1 = operands[1];
811 (define_expand "cmpdf"
812 [(set (reg:CC FLAGS_REG)
813 (compare:CC (match_operand:DF 0 "cmp_fp_expander_operand" "")
814 (match_operand:DF 1 "cmp_fp_expander_operand" "")))]
815 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
817 ix86_compare_op0 = operands[0];
818 ix86_compare_op1 = operands[1];
822 (define_expand "cmpsf"
823 [(set (reg:CC FLAGS_REG)
824 (compare:CC (match_operand:SF 0 "cmp_fp_expander_operand" "")
825 (match_operand:SF 1 "cmp_fp_expander_operand" "")))]
826 "TARGET_80387 || TARGET_SSE_MATH"
828 ix86_compare_op0 = operands[0];
829 ix86_compare_op1 = operands[1];
833 ;; FP compares, step 1:
834 ;; Set the FP condition codes.
836 ;; CCFPmode compare with exceptions
837 ;; CCFPUmode compare with no exceptions
839 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
840 ;; used to manage the reg stack popping would not be preserved.
842 (define_insn "*cmpfp_0"
843 [(set (match_operand:HI 0 "register_operand" "=a")
846 (match_operand 1 "register_operand" "f")
847 (match_operand 2 "const0_operand" "X"))]
850 && FLOAT_MODE_P (GET_MODE (operands[1]))
851 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
852 "* return output_fp_compare (insn, operands, 0, 0);"
853 [(set_attr "type" "multi")
854 (set_attr "unit" "i387")
856 (cond [(match_operand:SF 1 "" "")
858 (match_operand:DF 1 "" "")
861 (const_string "XF")))])
863 (define_insn "*cmpfp_sf"
864 [(set (match_operand:HI 0 "register_operand" "=a")
867 (match_operand:SF 1 "register_operand" "f")
868 (match_operand:SF 2 "nonimmediate_operand" "fm"))]
871 "* return output_fp_compare (insn, operands, 0, 0);"
872 [(set_attr "type" "multi")
873 (set_attr "unit" "i387")
874 (set_attr "mode" "SF")])
876 (define_insn "*cmpfp_df"
877 [(set (match_operand:HI 0 "register_operand" "=a")
880 (match_operand:DF 1 "register_operand" "f")
881 (match_operand:DF 2 "nonimmediate_operand" "fm"))]
884 "* return output_fp_compare (insn, operands, 0, 0);"
885 [(set_attr "type" "multi")
886 (set_attr "unit" "i387")
887 (set_attr "mode" "DF")])
889 (define_insn "*cmpfp_xf"
890 [(set (match_operand:HI 0 "register_operand" "=a")
893 (match_operand:XF 1 "register_operand" "f")
894 (match_operand:XF 2 "register_operand" "f"))]
897 "* return output_fp_compare (insn, operands, 0, 0);"
898 [(set_attr "type" "multi")
899 (set_attr "unit" "i387")
900 (set_attr "mode" "XF")])
902 (define_insn "*cmpfp_u"
903 [(set (match_operand:HI 0 "register_operand" "=a")
906 (match_operand 1 "register_operand" "f")
907 (match_operand 2 "register_operand" "f"))]
910 && FLOAT_MODE_P (GET_MODE (operands[1]))
911 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
912 "* return output_fp_compare (insn, operands, 0, 1);"
913 [(set_attr "type" "multi")
914 (set_attr "unit" "i387")
916 (cond [(match_operand:SF 1 "" "")
918 (match_operand:DF 1 "" "")
921 (const_string "XF")))])
923 (define_insn "*cmpfp_<mode>"
924 [(set (match_operand:HI 0 "register_operand" "=a")
927 (match_operand 1 "register_operand" "f")
928 (match_operator 3 "float_operator"
929 [(match_operand:X87MODEI12 2 "memory_operand" "m")]))]
931 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
932 && FLOAT_MODE_P (GET_MODE (operands[1]))
933 && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
934 "* return output_fp_compare (insn, operands, 0, 0);"
935 [(set_attr "type" "multi")
936 (set_attr "unit" "i387")
937 (set_attr "fp_int_src" "true")
938 (set_attr "mode" "<MODE>")])
940 ;; FP compares, step 2
941 ;; Move the fpsw to ax.
943 (define_insn "x86_fnstsw_1"
944 [(set (match_operand:HI 0 "register_operand" "=a")
945 (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))]
948 [(set_attr "length" "2")
949 (set_attr "mode" "SI")
950 (set_attr "unit" "i387")])
952 ;; FP compares, step 3
953 ;; Get ax into flags, general case.
955 (define_insn "x86_sahf_1"
956 [(set (reg:CC FLAGS_REG)
957 (unspec:CC [(match_operand:HI 0 "register_operand" "a")] UNSPEC_SAHF))]
960 [(set_attr "length" "1")
961 (set_attr "athlon_decode" "vector")
962 (set_attr "mode" "SI")])
964 ;; Pentium Pro can do steps 1 through 3 in one go.
966 (define_insn "*cmpfp_i_mixed"
967 [(set (reg:CCFP FLAGS_REG)
968 (compare:CCFP (match_operand 0 "register_operand" "f#x,x#f")
969 (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
971 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
972 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
973 "* return output_fp_compare (insn, operands, 1, 0);"
974 [(set_attr "type" "fcmp,ssecomi")
976 (if_then_else (match_operand:SF 1 "" "")
978 (const_string "DF")))
979 (set_attr "athlon_decode" "vector")])
981 (define_insn "*cmpfp_i_sse"
982 [(set (reg:CCFP FLAGS_REG)
983 (compare:CCFP (match_operand 0 "register_operand" "x")
984 (match_operand 1 "nonimmediate_operand" "xm")))]
986 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
987 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
988 "* return output_fp_compare (insn, operands, 1, 0);"
989 [(set_attr "type" "ssecomi")
991 (if_then_else (match_operand:SF 1 "" "")
993 (const_string "DF")))
994 (set_attr "athlon_decode" "vector")])
996 (define_insn "*cmpfp_i_i387"
997 [(set (reg:CCFP FLAGS_REG)
998 (compare:CCFP (match_operand 0 "register_operand" "f")
999 (match_operand 1 "register_operand" "f")))]
1000 "TARGET_80387 && TARGET_CMOVE
1001 && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0])))
1002 && FLOAT_MODE_P (GET_MODE (operands[0]))
1003 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1004 "* return output_fp_compare (insn, operands, 1, 0);"
1005 [(set_attr "type" "fcmp")
1007 (cond [(match_operand:SF 1 "" "")
1009 (match_operand:DF 1 "" "")
1012 (const_string "XF")))
1013 (set_attr "athlon_decode" "vector")])
1015 (define_insn "*cmpfp_iu_mixed"
1016 [(set (reg:CCFPU FLAGS_REG)
1017 (compare:CCFPU (match_operand 0 "register_operand" "f#x,x#f")
1018 (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
1019 "TARGET_MIX_SSE_I387
1020 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1021 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1022 "* return output_fp_compare (insn, operands, 1, 1);"
1023 [(set_attr "type" "fcmp,ssecomi")
1025 (if_then_else (match_operand:SF 1 "" "")
1027 (const_string "DF")))
1028 (set_attr "athlon_decode" "vector")])
1030 (define_insn "*cmpfp_iu_sse"
1031 [(set (reg:CCFPU FLAGS_REG)
1032 (compare:CCFPU (match_operand 0 "register_operand" "x")
1033 (match_operand 1 "nonimmediate_operand" "xm")))]
1035 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1036 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1037 "* return output_fp_compare (insn, operands, 1, 1);"
1038 [(set_attr "type" "ssecomi")
1040 (if_then_else (match_operand:SF 1 "" "")
1042 (const_string "DF")))
1043 (set_attr "athlon_decode" "vector")])
1045 (define_insn "*cmpfp_iu_387"
1046 [(set (reg:CCFPU FLAGS_REG)
1047 (compare:CCFPU (match_operand 0 "register_operand" "f")
1048 (match_operand 1 "register_operand" "f")))]
1049 "TARGET_80387 && TARGET_CMOVE
1050 && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0])))
1051 && FLOAT_MODE_P (GET_MODE (operands[0]))
1052 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1053 "* return output_fp_compare (insn, operands, 1, 1);"
1054 [(set_attr "type" "fcmp")
1056 (cond [(match_operand:SF 1 "" "")
1058 (match_operand:DF 1 "" "")
1061 (const_string "XF")))
1062 (set_attr "athlon_decode" "vector")])
1064 ;; Move instructions.
1066 ;; General case of fullword move.
1068 (define_expand "movsi"
1069 [(set (match_operand:SI 0 "nonimmediate_operand" "")
1070 (match_operand:SI 1 "general_operand" ""))]
1072 "ix86_expand_move (SImode, operands); DONE;")
1074 ;; Push/pop instructions. They are separate since autoinc/dec is not a
1077 ;; %%% We don't use a post-inc memory reference because x86 is not a
1078 ;; general AUTO_INC_DEC host, which impacts how it is treated in flow.
1079 ;; Changing this impacts compiler performance on other non-AUTO_INC_DEC
1080 ;; targets without our curiosities, and it is just as easy to represent
1081 ;; this differently.
1083 (define_insn "*pushsi2"
1084 [(set (match_operand:SI 0 "push_operand" "=<")
1085 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1088 [(set_attr "type" "push")
1089 (set_attr "mode" "SI")])
1091 ;; For 64BIT abi we always round up to 8 bytes.
1092 (define_insn "*pushsi2_rex64"
1093 [(set (match_operand:SI 0 "push_operand" "=X")
1094 (match_operand:SI 1 "nonmemory_no_elim_operand" "ri"))]
1097 [(set_attr "type" "push")
1098 (set_attr "mode" "SI")])
1100 (define_insn "*pushsi2_prologue"
1101 [(set (match_operand:SI 0 "push_operand" "=<")
1102 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))
1103 (clobber (mem:BLK (scratch)))]
1106 [(set_attr "type" "push")
1107 (set_attr "mode" "SI")])
1109 (define_insn "*popsi1_epilogue"
1110 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1111 (mem:SI (reg:SI SP_REG)))
1112 (set (reg:SI SP_REG)
1113 (plus:SI (reg:SI SP_REG) (const_int 4)))
1114 (clobber (mem:BLK (scratch)))]
1117 [(set_attr "type" "pop")
1118 (set_attr "mode" "SI")])
1120 (define_insn "popsi1"
1121 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1122 (mem:SI (reg:SI SP_REG)))
1123 (set (reg:SI SP_REG)
1124 (plus:SI (reg:SI SP_REG) (const_int 4)))]
1127 [(set_attr "type" "pop")
1128 (set_attr "mode" "SI")])
1130 (define_insn "*movsi_xor"
1131 [(set (match_operand:SI 0 "register_operand" "=r")
1132 (match_operand:SI 1 "const0_operand" "i"))
1133 (clobber (reg:CC FLAGS_REG))]
1134 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1135 "xor{l}\t{%0, %0|%0, %0}"
1136 [(set_attr "type" "alu1")
1137 (set_attr "mode" "SI")
1138 (set_attr "length_immediate" "0")])
1140 (define_insn "*movsi_or"
1141 [(set (match_operand:SI 0 "register_operand" "=r")
1142 (match_operand:SI 1 "immediate_operand" "i"))
1143 (clobber (reg:CC FLAGS_REG))]
1145 && operands[1] == constm1_rtx
1146 && (TARGET_PENTIUM || optimize_size)"
1148 operands[1] = constm1_rtx;
1149 return "or{l}\t{%1, %0|%0, %1}";
1151 [(set_attr "type" "alu1")
1152 (set_attr "mode" "SI")
1153 (set_attr "length_immediate" "1")])
1155 (define_insn "*movsi_1"
1156 [(set (match_operand:SI 0 "nonimmediate_operand"
1157 "=r ,m ,*y,*y,?rm,?*y,*x,*x,?r,m ,?*Y,*x")
1158 (match_operand:SI 1 "general_operand"
1159 "rinm,rin,C ,*y,*y ,rm ,C ,*x,*Y,*x,r ,m "))]
1160 "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1162 switch (get_attr_type (insn))
1165 if (get_attr_mode (insn) == MODE_TI)
1166 return "pxor\t%0, %0";
1167 return "xorps\t%0, %0";
1170 switch (get_attr_mode (insn))
1173 return "movdqa\t{%1, %0|%0, %1}";
1175 return "movaps\t{%1, %0|%0, %1}";
1177 return "movd\t{%1, %0|%0, %1}";
1179 return "movss\t{%1, %0|%0, %1}";
1185 return "pxor\t%0, %0";
1188 if (get_attr_mode (insn) == MODE_DI)
1189 return "movq\t{%1, %0|%0, %1}";
1190 return "movd\t{%1, %0|%0, %1}";
1193 return "lea{l}\t{%1, %0|%0, %1}";
1196 gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
1197 return "mov{l}\t{%1, %0|%0, %1}";
1201 (cond [(eq_attr "alternative" "2")
1202 (const_string "mmxadd")
1203 (eq_attr "alternative" "3,4,5")
1204 (const_string "mmxmov")
1205 (eq_attr "alternative" "6")
1206 (const_string "sselog1")
1207 (eq_attr "alternative" "7,8,9,10,11")
1208 (const_string "ssemov")
1209 (match_operand:DI 1 "pic_32bit_operand" "")
1210 (const_string "lea")
1212 (const_string "imov")))
1214 (cond [(eq_attr "alternative" "2,3")
1216 (eq_attr "alternative" "6,7")
1218 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
1219 (const_string "V4SF")
1220 (const_string "TI"))
1221 (and (eq_attr "alternative" "8,9,10,11")
1222 (eq (symbol_ref "TARGET_SSE2") (const_int 0)))
1225 (const_string "SI")))])
1227 ;; Stores and loads of ax to arbitrary constant address.
1228 ;; We fake an second form of instruction to force reload to load address
1229 ;; into register when rax is not available
1230 (define_insn "*movabssi_1_rex64"
1231 [(set (mem:SI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1232 (match_operand:SI 1 "nonmemory_operand" "a,er"))]
1233 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1235 movabs{l}\t{%1, %P0|%P0, %1}
1236 mov{l}\t{%1, %a0|%a0, %1}"
1237 [(set_attr "type" "imov")
1238 (set_attr "modrm" "0,*")
1239 (set_attr "length_address" "8,0")
1240 (set_attr "length_immediate" "0,*")
1241 (set_attr "memory" "store")
1242 (set_attr "mode" "SI")])
1244 (define_insn "*movabssi_2_rex64"
1245 [(set (match_operand:SI 0 "register_operand" "=a,r")
1246 (mem:SI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1247 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1249 movabs{l}\t{%P1, %0|%0, %P1}
1250 mov{l}\t{%a1, %0|%0, %a1}"
1251 [(set_attr "type" "imov")
1252 (set_attr "modrm" "0,*")
1253 (set_attr "length_address" "8,0")
1254 (set_attr "length_immediate" "0")
1255 (set_attr "memory" "load")
1256 (set_attr "mode" "SI")])
1258 (define_insn "*swapsi"
1259 [(set (match_operand:SI 0 "register_operand" "+r")
1260 (match_operand:SI 1 "register_operand" "+r"))
1265 [(set_attr "type" "imov")
1266 (set_attr "mode" "SI")
1267 (set_attr "pent_pair" "np")
1268 (set_attr "athlon_decode" "vector")])
1270 (define_expand "movhi"
1271 [(set (match_operand:HI 0 "nonimmediate_operand" "")
1272 (match_operand:HI 1 "general_operand" ""))]
1274 "ix86_expand_move (HImode, operands); DONE;")
1276 (define_insn "*pushhi2"
1277 [(set (match_operand:HI 0 "push_operand" "=<,<")
1278 (match_operand:HI 1 "general_no_elim_operand" "n,r*m"))]
1281 push{w}\t{|WORD PTR }%1
1283 [(set_attr "type" "push")
1284 (set_attr "mode" "HI")])
1286 ;; For 64BIT abi we always round up to 8 bytes.
1287 (define_insn "*pushhi2_rex64"
1288 [(set (match_operand:HI 0 "push_operand" "=X")
1289 (match_operand:HI 1 "nonmemory_no_elim_operand" "ri"))]
1292 [(set_attr "type" "push")
1293 (set_attr "mode" "QI")])
1295 (define_insn "*movhi_1"
1296 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
1297 (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
1298 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1300 switch (get_attr_type (insn))
1303 /* movzwl is faster than movw on p2 due to partial word stalls,
1304 though not as fast as an aligned movl. */
1305 return "movz{wl|x}\t{%1, %k0|%k0, %1}";
1307 if (get_attr_mode (insn) == MODE_SI)
1308 return "mov{l}\t{%k1, %k0|%k0, %k1}";
1310 return "mov{w}\t{%1, %0|%0, %1}";
1314 (cond [(ne (symbol_ref "optimize_size") (const_int 0))
1315 (const_string "imov")
1316 (and (eq_attr "alternative" "0")
1317 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1319 (eq (symbol_ref "TARGET_HIMODE_MATH")
1321 (const_string "imov")
1322 (and (eq_attr "alternative" "1,2")
1323 (match_operand:HI 1 "aligned_operand" ""))
1324 (const_string "imov")
1325 (and (ne (symbol_ref "TARGET_MOVX")
1327 (eq_attr "alternative" "0,2"))
1328 (const_string "imovx")
1330 (const_string "imov")))
1332 (cond [(eq_attr "type" "imovx")
1334 (and (eq_attr "alternative" "1,2")
1335 (match_operand:HI 1 "aligned_operand" ""))
1337 (and (eq_attr "alternative" "0")
1338 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1340 (eq (symbol_ref "TARGET_HIMODE_MATH")
1344 (const_string "HI")))])
1346 ;; Stores and loads of ax to arbitrary constant address.
1347 ;; We fake an second form of instruction to force reload to load address
1348 ;; into register when rax is not available
1349 (define_insn "*movabshi_1_rex64"
1350 [(set (mem:HI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1351 (match_operand:HI 1 "nonmemory_operand" "a,er"))]
1352 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1354 movabs{w}\t{%1, %P0|%P0, %1}
1355 mov{w}\t{%1, %a0|%a0, %1}"
1356 [(set_attr "type" "imov")
1357 (set_attr "modrm" "0,*")
1358 (set_attr "length_address" "8,0")
1359 (set_attr "length_immediate" "0,*")
1360 (set_attr "memory" "store")
1361 (set_attr "mode" "HI")])
1363 (define_insn "*movabshi_2_rex64"
1364 [(set (match_operand:HI 0 "register_operand" "=a,r")
1365 (mem:HI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1366 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1368 movabs{w}\t{%P1, %0|%0, %P1}
1369 mov{w}\t{%a1, %0|%0, %a1}"
1370 [(set_attr "type" "imov")
1371 (set_attr "modrm" "0,*")
1372 (set_attr "length_address" "8,0")
1373 (set_attr "length_immediate" "0")
1374 (set_attr "memory" "load")
1375 (set_attr "mode" "HI")])
1377 (define_insn "*swaphi_1"
1378 [(set (match_operand:HI 0 "register_operand" "+r")
1379 (match_operand:HI 1 "register_operand" "+r"))
1382 "!TARGET_PARTIAL_REG_STALL || optimize_size"
1384 [(set_attr "type" "imov")
1385 (set_attr "mode" "SI")
1386 (set_attr "pent_pair" "np")
1387 (set_attr "athlon_decode" "vector")])
1389 (define_insn "*swaphi_2"
1390 [(set (match_operand:HI 0 "register_operand" "+r")
1391 (match_operand:HI 1 "register_operand" "+r"))
1394 "TARGET_PARTIAL_REG_STALL"
1396 [(set_attr "type" "imov")
1397 (set_attr "mode" "HI")
1398 (set_attr "pent_pair" "np")
1399 (set_attr "athlon_decode" "vector")])
1401 (define_expand "movstricthi"
1402 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" ""))
1403 (match_operand:HI 1 "general_operand" ""))]
1404 "! TARGET_PARTIAL_REG_STALL || optimize_size"
1406 /* Don't generate memory->memory moves, go through a register */
1407 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1408 operands[1] = force_reg (HImode, operands[1]);
1411 (define_insn "*movstricthi_1"
1412 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+rm,r"))
1413 (match_operand:HI 1 "general_operand" "rn,m"))]
1414 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1415 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1416 "mov{w}\t{%1, %0|%0, %1}"
1417 [(set_attr "type" "imov")
1418 (set_attr "mode" "HI")])
1420 (define_insn "*movstricthi_xor"
1421 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
1422 (match_operand:HI 1 "const0_operand" "i"))
1423 (clobber (reg:CC FLAGS_REG))]
1425 && ((!TARGET_USE_MOV0 && !TARGET_PARTIAL_REG_STALL) || optimize_size)"
1426 "xor{w}\t{%0, %0|%0, %0}"
1427 [(set_attr "type" "alu1")
1428 (set_attr "mode" "HI")
1429 (set_attr "length_immediate" "0")])
1431 (define_expand "movqi"
1432 [(set (match_operand:QI 0 "nonimmediate_operand" "")
1433 (match_operand:QI 1 "general_operand" ""))]
1435 "ix86_expand_move (QImode, operands); DONE;")
1437 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1438 ;; "push a byte". But actually we use pushw, which has the effect
1439 ;; of rounding the amount pushed up to a halfword.
1441 (define_insn "*pushqi2"
1442 [(set (match_operand:QI 0 "push_operand" "=X,X")
1443 (match_operand:QI 1 "nonmemory_no_elim_operand" "n,r"))]
1446 push{w}\t{|word ptr }%1
1448 [(set_attr "type" "push")
1449 (set_attr "mode" "HI")])
1451 ;; For 64BIT abi we always round up to 8 bytes.
1452 (define_insn "*pushqi2_rex64"
1453 [(set (match_operand:QI 0 "push_operand" "=X")
1454 (match_operand:QI 1 "nonmemory_no_elim_operand" "qi"))]
1457 [(set_attr "type" "push")
1458 (set_attr "mode" "QI")])
1460 ;; Situation is quite tricky about when to choose full sized (SImode) move
1461 ;; over QImode moves. For Q_REG -> Q_REG move we use full size only for
1462 ;; partial register dependency machines (such as AMD Athlon), where QImode
1463 ;; moves issue extra dependency and for partial register stalls machines
1464 ;; that don't use QImode patterns (and QImode move cause stall on the next
1467 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
1468 ;; register stall machines with, where we use QImode instructions, since
1469 ;; partial register stall can be caused there. Then we use movzx.
1470 (define_insn "*movqi_1"
1471 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
1472 (match_operand:QI 1 "general_operand" " q,qn,qm,q,rn,m ,qn"))]
1473 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1475 switch (get_attr_type (insn))
1478 gcc_assert (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM);
1479 return "movz{bl|x}\t{%1, %k0|%k0, %1}";
1481 if (get_attr_mode (insn) == MODE_SI)
1482 return "mov{l}\t{%k1, %k0|%k0, %k1}";
1484 return "mov{b}\t{%1, %0|%0, %1}";
1488 (cond [(eq_attr "alternative" "5")
1489 (const_string "imovx")
1490 (ne (symbol_ref "optimize_size") (const_int 0))
1491 (const_string "imov")
1492 (and (eq_attr "alternative" "3")
1493 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1495 (eq (symbol_ref "TARGET_QIMODE_MATH")
1497 (const_string "imov")
1498 (eq_attr "alternative" "3")
1499 (const_string "imovx")
1500 (and (ne (symbol_ref "TARGET_MOVX")
1502 (eq_attr "alternative" "2"))
1503 (const_string "imovx")
1505 (const_string "imov")))
1507 (cond [(eq_attr "alternative" "3,4,5")
1509 (eq_attr "alternative" "6")
1511 (eq_attr "type" "imovx")
1513 (and (eq_attr "type" "imov")
1514 (and (eq_attr "alternative" "0,1")
1515 (ne (symbol_ref "TARGET_PARTIAL_REG_DEPENDENCY")
1518 ;; Avoid partial register stalls when not using QImode arithmetic
1519 (and (eq_attr "type" "imov")
1520 (and (eq_attr "alternative" "0,1")
1521 (and (ne (symbol_ref "TARGET_PARTIAL_REG_STALL")
1523 (eq (symbol_ref "TARGET_QIMODE_MATH")
1527 (const_string "QI")))])
1529 (define_expand "reload_outqi"
1530 [(parallel [(match_operand:QI 0 "" "=m")
1531 (match_operand:QI 1 "register_operand" "r")
1532 (match_operand:QI 2 "register_operand" "=&q")])]
1536 op0 = operands[0]; op1 = operands[1]; op2 = operands[2];
1538 gcc_assert (!reg_overlap_mentioned_p (op2, op0));
1539 if (! q_regs_operand (op1, QImode))
1541 emit_insn (gen_movqi (op2, op1));
1544 emit_insn (gen_movqi (op0, op1));
1548 (define_insn "*swapqi_1"
1549 [(set (match_operand:QI 0 "register_operand" "+r")
1550 (match_operand:QI 1 "register_operand" "+r"))
1553 "!TARGET_PARTIAL_REG_STALL || optimize_size"
1555 [(set_attr "type" "imov")
1556 (set_attr "mode" "SI")
1557 (set_attr "pent_pair" "np")
1558 (set_attr "athlon_decode" "vector")])
1560 (define_insn "*swapqi_2"
1561 [(set (match_operand:QI 0 "register_operand" "+q")
1562 (match_operand:QI 1 "register_operand" "+q"))
1565 "TARGET_PARTIAL_REG_STALL"
1567 [(set_attr "type" "imov")
1568 (set_attr "mode" "QI")
1569 (set_attr "pent_pair" "np")
1570 (set_attr "athlon_decode" "vector")])
1572 (define_expand "movstrictqi"
1573 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
1574 (match_operand:QI 1 "general_operand" ""))]
1575 "! TARGET_PARTIAL_REG_STALL || optimize_size"
1577 /* Don't generate memory->memory moves, go through a register. */
1578 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1579 operands[1] = force_reg (QImode, operands[1]);
1582 (define_insn "*movstrictqi_1"
1583 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
1584 (match_operand:QI 1 "general_operand" "*qn,m"))]
1585 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1586 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1587 "mov{b}\t{%1, %0|%0, %1}"
1588 [(set_attr "type" "imov")
1589 (set_attr "mode" "QI")])
1591 (define_insn "*movstrictqi_xor"
1592 [(set (strict_low_part (match_operand:QI 0 "q_regs_operand" "+q"))
1593 (match_operand:QI 1 "const0_operand" "i"))
1594 (clobber (reg:CC FLAGS_REG))]
1595 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1596 "xor{b}\t{%0, %0|%0, %0}"
1597 [(set_attr "type" "alu1")
1598 (set_attr "mode" "QI")
1599 (set_attr "length_immediate" "0")])
1601 (define_insn "*movsi_extv_1"
1602 [(set (match_operand:SI 0 "register_operand" "=R")
1603 (sign_extract:SI (match_operand 1 "ext_register_operand" "Q")
1607 "movs{bl|x}\t{%h1, %0|%0, %h1}"
1608 [(set_attr "type" "imovx")
1609 (set_attr "mode" "SI")])
1611 (define_insn "*movhi_extv_1"
1612 [(set (match_operand:HI 0 "register_operand" "=R")
1613 (sign_extract:HI (match_operand 1 "ext_register_operand" "Q")
1617 "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
1618 [(set_attr "type" "imovx")
1619 (set_attr "mode" "SI")])
1621 (define_insn "*movqi_extv_1"
1622 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
1623 (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1628 switch (get_attr_type (insn))
1631 return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1633 return "mov{b}\t{%h1, %0|%0, %h1}";
1637 (if_then_else (and (match_operand:QI 0 "register_operand" "")
1638 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1639 (ne (symbol_ref "TARGET_MOVX")
1641 (const_string "imovx")
1642 (const_string "imov")))
1644 (if_then_else (eq_attr "type" "imovx")
1646 (const_string "QI")))])
1648 (define_insn "*movqi_extv_1_rex64"
1649 [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1650 (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1655 switch (get_attr_type (insn))
1658 return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1660 return "mov{b}\t{%h1, %0|%0, %h1}";
1664 (if_then_else (and (match_operand:QI 0 "register_operand" "")
1665 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1666 (ne (symbol_ref "TARGET_MOVX")
1668 (const_string "imovx")
1669 (const_string "imov")))
1671 (if_then_else (eq_attr "type" "imovx")
1673 (const_string "QI")))])
1675 ;; Stores and loads of ax to arbitrary constant address.
1676 ;; We fake an second form of instruction to force reload to load address
1677 ;; into register when rax is not available
1678 (define_insn "*movabsqi_1_rex64"
1679 [(set (mem:QI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1680 (match_operand:QI 1 "nonmemory_operand" "a,er"))]
1681 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1683 movabs{b}\t{%1, %P0|%P0, %1}
1684 mov{b}\t{%1, %a0|%a0, %1}"
1685 [(set_attr "type" "imov")
1686 (set_attr "modrm" "0,*")
1687 (set_attr "length_address" "8,0")
1688 (set_attr "length_immediate" "0,*")
1689 (set_attr "memory" "store")
1690 (set_attr "mode" "QI")])
1692 (define_insn "*movabsqi_2_rex64"
1693 [(set (match_operand:QI 0 "register_operand" "=a,r")
1694 (mem:QI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1695 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1697 movabs{b}\t{%P1, %0|%0, %P1}
1698 mov{b}\t{%a1, %0|%0, %a1}"
1699 [(set_attr "type" "imov")
1700 (set_attr "modrm" "0,*")
1701 (set_attr "length_address" "8,0")
1702 (set_attr "length_immediate" "0")
1703 (set_attr "memory" "load")
1704 (set_attr "mode" "QI")])
1706 (define_insn "*movdi_extzv_1"
1707 [(set (match_operand:DI 0 "register_operand" "=R")
1708 (zero_extract:DI (match_operand 1 "ext_register_operand" "Q")
1712 "movz{bl|x}\t{%h1, %k0|%k0, %h1}"
1713 [(set_attr "type" "imovx")
1714 (set_attr "mode" "DI")])
1716 (define_insn "*movsi_extzv_1"
1717 [(set (match_operand:SI 0 "register_operand" "=R")
1718 (zero_extract:SI (match_operand 1 "ext_register_operand" "Q")
1722 "movz{bl|x}\t{%h1, %0|%0, %h1}"
1723 [(set_attr "type" "imovx")
1724 (set_attr "mode" "SI")])
1726 (define_insn "*movqi_extzv_2"
1727 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
1728 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1733 switch (get_attr_type (insn))
1736 return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1738 return "mov{b}\t{%h1, %0|%0, %h1}";
1742 (if_then_else (and (match_operand:QI 0 "register_operand" "")
1743 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1744 (ne (symbol_ref "TARGET_MOVX")
1746 (const_string "imovx")
1747 (const_string "imov")))
1749 (if_then_else (eq_attr "type" "imovx")
1751 (const_string "QI")))])
1753 (define_insn "*movqi_extzv_2_rex64"
1754 [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1755 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1760 switch (get_attr_type (insn))
1763 return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1765 return "mov{b}\t{%h1, %0|%0, %h1}";
1769 (if_then_else (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1770 (ne (symbol_ref "TARGET_MOVX")
1772 (const_string "imovx")
1773 (const_string "imov")))
1775 (if_then_else (eq_attr "type" "imovx")
1777 (const_string "QI")))])
1779 (define_insn "movsi_insv_1"
1780 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
1783 (match_operand:SI 1 "general_operand" "Qmn"))]
1785 "mov{b}\t{%b1, %h0|%h0, %b1}"
1786 [(set_attr "type" "imov")
1787 (set_attr "mode" "QI")])
1789 (define_insn "movdi_insv_1_rex64"
1790 [(set (zero_extract:DI (match_operand 0 "ext_register_operand" "+Q")
1793 (match_operand:DI 1 "nonmemory_operand" "Qn"))]
1795 "mov{b}\t{%b1, %h0|%h0, %b1}"
1796 [(set_attr "type" "imov")
1797 (set_attr "mode" "QI")])
1799 (define_insn "*movqi_insv_2"
1800 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
1803 (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
1806 "mov{b}\t{%h1, %h0|%h0, %h1}"
1807 [(set_attr "type" "imov")
1808 (set_attr "mode" "QI")])
1810 (define_expand "movdi"
1811 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1812 (match_operand:DI 1 "general_operand" ""))]
1814 "ix86_expand_move (DImode, operands); DONE;")
1816 (define_insn "*pushdi"
1817 [(set (match_operand:DI 0 "push_operand" "=<")
1818 (match_operand:DI 1 "general_no_elim_operand" "riF*m"))]
1822 (define_insn "*pushdi2_rex64"
1823 [(set (match_operand:DI 0 "push_operand" "=<,!<")
1824 (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
1829 [(set_attr "type" "push,multi")
1830 (set_attr "mode" "DI")])
1832 ;; Convert impossible pushes of immediate to existing instructions.
1833 ;; First try to get scratch register and go through it. In case this
1834 ;; fails, push sign extended lower part first and then overwrite
1835 ;; upper part by 32bit move.
1837 [(match_scratch:DI 2 "r")
1838 (set (match_operand:DI 0 "push_operand" "")
1839 (match_operand:DI 1 "immediate_operand" ""))]
1840 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1841 && !x86_64_immediate_operand (operands[1], DImode)"
1842 [(set (match_dup 2) (match_dup 1))
1843 (set (match_dup 0) (match_dup 2))]
1846 ;; We need to define this as both peepholer and splitter for case
1847 ;; peephole2 pass is not run.
1848 ;; "&& 1" is needed to keep it from matching the previous pattern.
1850 [(set (match_operand:DI 0 "push_operand" "")
1851 (match_operand:DI 1 "immediate_operand" ""))]
1852 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1853 && !x86_64_immediate_operand (operands[1], DImode) && 1"
1854 [(set (match_dup 0) (match_dup 1))
1855 (set (match_dup 2) (match_dup 3))]
1856 "split_di (operands + 1, 1, operands + 2, operands + 3);
1857 operands[1] = gen_lowpart (DImode, operands[2]);
1858 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1863 [(set (match_operand:DI 0 "push_operand" "")
1864 (match_operand:DI 1 "immediate_operand" ""))]
1865 "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
1866 ? flow2_completed : reload_completed)
1867 && !symbolic_operand (operands[1], DImode)
1868 && !x86_64_immediate_operand (operands[1], DImode)"
1869 [(set (match_dup 0) (match_dup 1))
1870 (set (match_dup 2) (match_dup 3))]
1871 "split_di (operands + 1, 1, operands + 2, operands + 3);
1872 operands[1] = gen_lowpart (DImode, operands[2]);
1873 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1877 (define_insn "*pushdi2_prologue_rex64"
1878 [(set (match_operand:DI 0 "push_operand" "=<")
1879 (match_operand:DI 1 "general_no_elim_operand" "re*m"))
1880 (clobber (mem:BLK (scratch)))]
1883 [(set_attr "type" "push")
1884 (set_attr "mode" "DI")])
1886 (define_insn "*popdi1_epilogue_rex64"
1887 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
1888 (mem:DI (reg:DI SP_REG)))
1889 (set (reg:DI SP_REG)
1890 (plus:DI (reg:DI SP_REG) (const_int 8)))
1891 (clobber (mem:BLK (scratch)))]
1894 [(set_attr "type" "pop")
1895 (set_attr "mode" "DI")])
1897 (define_insn "popdi1"
1898 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
1899 (mem:DI (reg:DI SP_REG)))
1900 (set (reg:DI SP_REG)
1901 (plus:DI (reg:DI SP_REG) (const_int 8)))]
1904 [(set_attr "type" "pop")
1905 (set_attr "mode" "DI")])
1907 (define_insn "*movdi_xor_rex64"
1908 [(set (match_operand:DI 0 "register_operand" "=r")
1909 (match_operand:DI 1 "const0_operand" "i"))
1910 (clobber (reg:CC FLAGS_REG))]
1911 "TARGET_64BIT && (!TARGET_USE_MOV0 || optimize_size)
1912 && reload_completed"
1913 "xor{l}\t{%k0, %k0|%k0, %k0}"
1914 [(set_attr "type" "alu1")
1915 (set_attr "mode" "SI")
1916 (set_attr "length_immediate" "0")])
1918 (define_insn "*movdi_or_rex64"
1919 [(set (match_operand:DI 0 "register_operand" "=r")
1920 (match_operand:DI 1 "const_int_operand" "i"))
1921 (clobber (reg:CC FLAGS_REG))]
1922 "TARGET_64BIT && (TARGET_PENTIUM || optimize_size)
1924 && operands[1] == constm1_rtx"
1926 operands[1] = constm1_rtx;
1927 return "or{q}\t{%1, %0|%0, %1}";
1929 [(set_attr "type" "alu1")
1930 (set_attr "mode" "DI")
1931 (set_attr "length_immediate" "1")])
1933 (define_insn "*movdi_2"
1934 [(set (match_operand:DI 0 "nonimmediate_operand"
1935 "=r ,o ,*y,m*y,*y,*Y,m ,*Y,*Y,*x,m ,*x,*x")
1936 (match_operand:DI 1 "general_operand"
1937 "riFo,riF,C ,*y ,m ,C ,*Y,*Y,m ,C ,*x,*x,m "))]
1938 "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1943 movq\t{%1, %0|%0, %1}
1944 movq\t{%1, %0|%0, %1}
1946 movq\t{%1, %0|%0, %1}
1947 movdqa\t{%1, %0|%0, %1}
1948 movq\t{%1, %0|%0, %1}
1950 movlps\t{%1, %0|%0, %1}
1951 movaps\t{%1, %0|%0, %1}
1952 movlps\t{%1, %0|%0, %1}"
1953 [(set_attr "type" "*,*,mmx,mmxmov,mmxmov,sselog1,ssemov,ssemov,ssemov,sselog1,ssemov,ssemov,ssemov")
1954 (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF")])
1957 [(set (match_operand:DI 0 "push_operand" "")
1958 (match_operand:DI 1 "general_operand" ""))]
1959 "!TARGET_64BIT && reload_completed
1960 && (! MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
1962 "ix86_split_long_move (operands); DONE;")
1964 ;; %%% This multiword shite has got to go.
1966 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1967 (match_operand:DI 1 "general_operand" ""))]
1968 "!TARGET_64BIT && reload_completed
1969 && (!MMX_REG_P (operands[0]) && !SSE_REG_P (operands[0]))
1970 && (!MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
1972 "ix86_split_long_move (operands); DONE;")
1974 (define_insn "*movdi_1_rex64"
1975 [(set (match_operand:DI 0 "nonimmediate_operand"
1976 "=r,r ,r,m ,!m,*y,*y,?rm,?*y,*x,*x,?rm,?*x,?*x,?*y")
1977 (match_operand:DI 1 "general_operand"
1978 "Z ,rem,i,re,n ,C ,*y,*y ,rm ,C ,*x,*x ,rm ,*y ,*x"))]
1979 "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1981 switch (get_attr_type (insn))
1984 if (which_alternative == 13)
1985 return "movq2dq\t{%1, %0|%0, %1}";
1987 return "movdq2q\t{%1, %0|%0, %1}";
1989 if (get_attr_mode (insn) == MODE_TI)
1990 return "movdqa\t{%1, %0|%0, %1}";
1993 /* Moves from and into integer register is done using movd opcode with
1995 if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
1996 return "movd\t{%1, %0|%0, %1}";
1997 return "movq\t{%1, %0|%0, %1}";
2000 return "pxor\t%0, %0";
2004 return "lea{q}\t{%a1, %0|%0, %a1}";
2006 gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
2007 if (get_attr_mode (insn) == MODE_SI)
2008 return "mov{l}\t{%k1, %k0|%k0, %k1}";
2009 else if (which_alternative == 2)
2010 return "movabs{q}\t{%1, %0|%0, %1}";
2012 return "mov{q}\t{%1, %0|%0, %1}";
2016 (cond [(eq_attr "alternative" "5")
2017 (const_string "mmxadd")
2018 (eq_attr "alternative" "6,7,8")
2019 (const_string "mmxmov")
2020 (eq_attr "alternative" "9")
2021 (const_string "sselog1")
2022 (eq_attr "alternative" "10,11,12")
2023 (const_string "ssemov")
2024 (eq_attr "alternative" "13,14")
2025 (const_string "ssecvt")
2026 (eq_attr "alternative" "4")
2027 (const_string "multi")
2028 (match_operand:DI 1 "pic_32bit_operand" "")
2029 (const_string "lea")
2031 (const_string "imov")))
2032 (set_attr "modrm" "*,0,0,*,*,*,*,*,*,*,*,*,*,*,*")
2033 (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*,*,*,*,*,*,*")
2034 (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,TI,TI,DI,DI,DI,DI")])
2036 ;; Stores and loads of ax to arbitrary constant address.
2037 ;; We fake an second form of instruction to force reload to load address
2038 ;; into register when rax is not available
2039 (define_insn "*movabsdi_1_rex64"
2040 [(set (mem:DI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2041 (match_operand:DI 1 "nonmemory_operand" "a,er"))]
2042 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
2044 movabs{q}\t{%1, %P0|%P0, %1}
2045 mov{q}\t{%1, %a0|%a0, %1}"
2046 [(set_attr "type" "imov")
2047 (set_attr "modrm" "0,*")
2048 (set_attr "length_address" "8,0")
2049 (set_attr "length_immediate" "0,*")
2050 (set_attr "memory" "store")
2051 (set_attr "mode" "DI")])
2053 (define_insn "*movabsdi_2_rex64"
2054 [(set (match_operand:DI 0 "register_operand" "=a,r")
2055 (mem:DI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2056 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
2058 movabs{q}\t{%P1, %0|%0, %P1}
2059 mov{q}\t{%a1, %0|%0, %a1}"
2060 [(set_attr "type" "imov")
2061 (set_attr "modrm" "0,*")
2062 (set_attr "length_address" "8,0")
2063 (set_attr "length_immediate" "0")
2064 (set_attr "memory" "load")
2065 (set_attr "mode" "DI")])
2067 ;; Convert impossible stores of immediate to existing instructions.
2068 ;; First try to get scratch register and go through it. In case this
2069 ;; fails, move by 32bit parts.
2071 [(match_scratch:DI 2 "r")
2072 (set (match_operand:DI 0 "memory_operand" "")
2073 (match_operand:DI 1 "immediate_operand" ""))]
2074 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2075 && !x86_64_immediate_operand (operands[1], DImode)"
2076 [(set (match_dup 2) (match_dup 1))
2077 (set (match_dup 0) (match_dup 2))]
2080 ;; We need to define this as both peepholer and splitter for case
2081 ;; peephole2 pass is not run.
2082 ;; "&& 1" is needed to keep it from matching the previous pattern.
2084 [(set (match_operand:DI 0 "memory_operand" "")
2085 (match_operand:DI 1 "immediate_operand" ""))]
2086 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2087 && !x86_64_immediate_operand (operands[1], DImode) && 1"
2088 [(set (match_dup 2) (match_dup 3))
2089 (set (match_dup 4) (match_dup 5))]
2090 "split_di (operands, 2, operands + 2, operands + 4);")
2093 [(set (match_operand:DI 0 "memory_operand" "")
2094 (match_operand:DI 1 "immediate_operand" ""))]
2095 "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2096 ? flow2_completed : reload_completed)
2097 && !symbolic_operand (operands[1], DImode)
2098 && !x86_64_immediate_operand (operands[1], DImode)"
2099 [(set (match_dup 2) (match_dup 3))
2100 (set (match_dup 4) (match_dup 5))]
2101 "split_di (operands, 2, operands + 2, operands + 4);")
2103 (define_insn "*swapdi_rex64"
2104 [(set (match_operand:DI 0 "register_operand" "+r")
2105 (match_operand:DI 1 "register_operand" "+r"))
2110 [(set_attr "type" "imov")
2111 (set_attr "mode" "DI")
2112 (set_attr "pent_pair" "np")
2113 (set_attr "athlon_decode" "vector")])
2115 (define_expand "movti"
2116 [(set (match_operand:TI 0 "nonimmediate_operand" "")
2117 (match_operand:TI 1 "nonimmediate_operand" ""))]
2118 "TARGET_SSE || TARGET_64BIT"
2121 ix86_expand_move (TImode, operands);
2123 ix86_expand_vector_move (TImode, operands);
2127 (define_insn "*movti_internal"
2128 [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
2129 (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
2130 "TARGET_SSE && !TARGET_64BIT
2131 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2133 switch (which_alternative)
2136 if (get_attr_mode (insn) == MODE_V4SF)
2137 return "xorps\t%0, %0";
2139 return "pxor\t%0, %0";
2142 if (get_attr_mode (insn) == MODE_V4SF)
2143 return "movaps\t{%1, %0|%0, %1}";
2145 return "movdqa\t{%1, %0|%0, %1}";
2150 [(set_attr "type" "ssemov,ssemov,ssemov")
2152 (cond [(eq (symbol_ref "TARGET_SSE2") (const_int 0))
2153 (const_string "V4SF")
2155 (eq_attr "alternative" "0,1")
2157 (ne (symbol_ref "optimize_size")
2159 (const_string "V4SF")
2160 (const_string "TI"))
2161 (eq_attr "alternative" "2")
2163 (ne (symbol_ref "optimize_size")
2165 (const_string "V4SF")
2166 (const_string "TI"))]
2167 (const_string "TI")))])
2169 (define_insn "*movti_rex64"
2170 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o,x,x,xm")
2171 (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
2173 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2175 switch (which_alternative)
2181 if (get_attr_mode (insn) == MODE_V4SF)
2182 return "xorps\t%0, %0";
2184 return "pxor\t%0, %0";
2187 if (get_attr_mode (insn) == MODE_V4SF)
2188 return "movaps\t{%1, %0|%0, %1}";
2190 return "movdqa\t{%1, %0|%0, %1}";
2195 [(set_attr "type" "*,*,ssemov,ssemov,ssemov")
2197 (cond [(eq_attr "alternative" "2,3")
2199 (ne (symbol_ref "optimize_size")
2201 (const_string "V4SF")
2202 (const_string "TI"))
2203 (eq_attr "alternative" "4")
2205 (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2207 (ne (symbol_ref "optimize_size")
2209 (const_string "V4SF")
2210 (const_string "TI"))]
2211 (const_string "DI")))])
2214 [(set (match_operand:TI 0 "nonimmediate_operand" "")
2215 (match_operand:TI 1 "general_operand" ""))]
2216 "reload_completed && !SSE_REG_P (operands[0])
2217 && !SSE_REG_P (operands[1])"
2219 "ix86_split_long_move (operands); DONE;")
2221 (define_expand "movsf"
2222 [(set (match_operand:SF 0 "nonimmediate_operand" "")
2223 (match_operand:SF 1 "general_operand" ""))]
2225 "ix86_expand_move (SFmode, operands); DONE;")
2227 (define_insn "*pushsf"
2228 [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2229 (match_operand:SF 1 "general_no_elim_operand" "f#rx,rFm#fx,x#rf"))]
2232 /* Anything else should be already split before reg-stack. */
2233 gcc_assert (which_alternative == 1);
2234 return "push{l}\t%1";
2236 [(set_attr "type" "multi,push,multi")
2237 (set_attr "unit" "i387,*,*")
2238 (set_attr "mode" "SF,SI,SF")])
2240 (define_insn "*pushsf_rex64"
2241 [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2242 (match_operand:SF 1 "nonmemory_no_elim_operand" "f#rx,rF#fx,x#rf"))]
2245 /* Anything else should be already split before reg-stack. */
2246 gcc_assert (which_alternative == 1);
2247 return "push{q}\t%q1";
2249 [(set_attr "type" "multi,push,multi")
2250 (set_attr "unit" "i387,*,*")
2251 (set_attr "mode" "SF,DI,SF")])
2254 [(set (match_operand:SF 0 "push_operand" "")
2255 (match_operand:SF 1 "memory_operand" ""))]
2257 && GET_CODE (operands[1]) == MEM
2258 && constant_pool_reference_p (operands[1])"
2261 "operands[1] = avoid_constant_pool_reference (operands[1]);")
2264 ;; %%% Kill this when call knows how to work this out.
2266 [(set (match_operand:SF 0 "push_operand" "")
2267 (match_operand:SF 1 "any_fp_register_operand" ""))]
2269 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
2270 (set (mem:SF (reg:SI SP_REG)) (match_dup 1))])
2273 [(set (match_operand:SF 0 "push_operand" "")
2274 (match_operand:SF 1 "any_fp_register_operand" ""))]
2276 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2277 (set (mem:SF (reg:DI SP_REG)) (match_dup 1))])
2279 (define_insn "*movsf_1"
2280 [(set (match_operand:SF 0 "nonimmediate_operand"
2281 "=f#xr,m ,f#xr,r#xf ,m ,x#rf,x#rf,x#rf ,m ,!*y,!rm,!*y")
2282 (match_operand:SF 1 "general_operand"
2283 "fm#rx,f#rx,G ,rmF#fx,Fr#fx,C ,x ,xm#rf,x#rf,rm ,*y ,*y"))]
2284 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2285 && (reload_in_progress || reload_completed
2286 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2287 || GET_CODE (operands[1]) != CONST_DOUBLE
2288 || memory_operand (operands[0], SFmode))"
2290 switch (which_alternative)
2293 return output_387_reg_move (insn, operands);
2296 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2297 return "fstp%z0\t%y0";
2299 return "fst%z0\t%y0";
2302 return standard_80387_constant_opcode (operands[1]);
2306 return "mov{l}\t{%1, %0|%0, %1}";
2308 if (get_attr_mode (insn) == MODE_TI)
2309 return "pxor\t%0, %0";
2311 return "xorps\t%0, %0";
2313 if (get_attr_mode (insn) == MODE_V4SF)
2314 return "movaps\t{%1, %0|%0, %1}";
2316 return "movss\t{%1, %0|%0, %1}";
2319 return "movss\t{%1, %0|%0, %1}";
2323 return "movd\t{%1, %0|%0, %1}";
2326 return "movq\t{%1, %0|%0, %1}";
2332 [(set_attr "type" "fmov,fmov,fmov,imov,imov,ssemov,ssemov,ssemov,ssemov,mmxmov,mmxmov,mmxmov")
2334 (cond [(eq_attr "alternative" "3,4,9,10")
2336 (eq_attr "alternative" "5")
2338 (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2340 (ne (symbol_ref "TARGET_SSE2")
2342 (eq (symbol_ref "optimize_size")
2345 (const_string "V4SF"))
2346 /* For architectures resolving dependencies on
2347 whole SSE registers use APS move to break dependency
2348 chains, otherwise use short move to avoid extra work.
2350 Do the same for architectures resolving dependencies on
2351 the parts. While in DF mode it is better to always handle
2352 just register parts, the SF mode is different due to lack
2353 of instructions to load just part of the register. It is
2354 better to maintain the whole registers in single format
2355 to avoid problems on using packed logical operations. */
2356 (eq_attr "alternative" "6")
2358 (ior (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2360 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2362 (const_string "V4SF")
2363 (const_string "SF"))
2364 (eq_attr "alternative" "11")
2365 (const_string "DI")]
2366 (const_string "SF")))])
2368 (define_insn "*swapsf"
2369 [(set (match_operand:SF 0 "fp_register_operand" "+f")
2370 (match_operand:SF 1 "fp_register_operand" "+f"))
2373 "reload_completed || TARGET_80387"
2375 if (STACK_TOP_P (operands[0]))
2380 [(set_attr "type" "fxch")
2381 (set_attr "mode" "SF")])
2383 (define_expand "movdf"
2384 [(set (match_operand:DF 0 "nonimmediate_operand" "")
2385 (match_operand:DF 1 "general_operand" ""))]
2387 "ix86_expand_move (DFmode, operands); DONE;")
2389 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2390 ;; Size of pushdf using integer instructions is 2+2*memory operand size
2391 ;; On the average, pushdf using integers can be still shorter. Allow this
2392 ;; pattern for optimize_size too.
2394 (define_insn "*pushdf_nointeger"
2395 [(set (match_operand:DF 0 "push_operand" "=<,<,<,<")
2396 (match_operand:DF 1 "general_no_elim_operand" "f#Y,Fo#fY,*r#fY,Y#f"))]
2397 "!TARGET_64BIT && !TARGET_INTEGER_DFMODE_MOVES"
2399 /* This insn should be already split before reg-stack. */
2402 [(set_attr "type" "multi")
2403 (set_attr "unit" "i387,*,*,*")
2404 (set_attr "mode" "DF,SI,SI,DF")])
2406 (define_insn "*pushdf_integer"
2407 [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2408 (match_operand:DF 1 "general_no_elim_operand" "f#rY,rFo#fY,Y#rf"))]
2409 "TARGET_64BIT || TARGET_INTEGER_DFMODE_MOVES"
2411 /* This insn should be already split before reg-stack. */
2414 [(set_attr "type" "multi")
2415 (set_attr "unit" "i387,*,*")
2416 (set_attr "mode" "DF,SI,DF")])
2418 ;; %%% Kill this when call knows how to work this out.
2420 [(set (match_operand:DF 0 "push_operand" "")
2421 (match_operand:DF 1 "any_fp_register_operand" ""))]
2422 "!TARGET_64BIT && reload_completed"
2423 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
2424 (set (mem:DF (reg:SI SP_REG)) (match_dup 1))]
2428 [(set (match_operand:DF 0 "push_operand" "")
2429 (match_operand:DF 1 "any_fp_register_operand" ""))]
2430 "TARGET_64BIT && reload_completed"
2431 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2432 (set (mem:DF (reg:DI SP_REG)) (match_dup 1))]
2436 [(set (match_operand:DF 0 "push_operand" "")
2437 (match_operand:DF 1 "general_operand" ""))]
2440 "ix86_split_long_move (operands); DONE;")
2442 ;; Moving is usually shorter when only FP registers are used. This separate
2443 ;; movdf pattern avoids the use of integer registers for FP operations
2444 ;; when optimizing for size.
2446 (define_insn "*movdf_nointeger"
2447 [(set (match_operand:DF 0 "nonimmediate_operand"
2448 "=f#Y,m ,f#Y,*r ,o ,Y*x#f,Y*x#f,Y*x#f ,m ")
2449 (match_operand:DF 1 "general_operand"
2450 "fm#Y,f#Y,G ,*roF,F*r,C ,Y*x#f,HmY*x#f,Y*x#f"))]
2451 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2452 && ((optimize_size || !TARGET_INTEGER_DFMODE_MOVES) && !TARGET_64BIT)
2453 && (reload_in_progress || reload_completed
2454 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2455 || GET_CODE (operands[1]) != CONST_DOUBLE
2456 || memory_operand (operands[0], DFmode))"
2458 switch (which_alternative)
2461 return output_387_reg_move (insn, operands);
2464 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2465 return "fstp%z0\t%y0";
2467 return "fst%z0\t%y0";
2470 return standard_80387_constant_opcode (operands[1]);
2476 switch (get_attr_mode (insn))
2479 return "xorps\t%0, %0";
2481 return "xorpd\t%0, %0";
2483 return "pxor\t%0, %0";
2490 switch (get_attr_mode (insn))
2493 return "movaps\t{%1, %0|%0, %1}";
2495 return "movapd\t{%1, %0|%0, %1}";
2497 return "movdqa\t{%1, %0|%0, %1}";
2499 return "movq\t{%1, %0|%0, %1}";
2501 return "movsd\t{%1, %0|%0, %1}";
2503 return "movlpd\t{%1, %0|%0, %1}";
2505 return "movlps\t{%1, %0|%0, %1}";
2514 [(set_attr "type" "fmov,fmov,fmov,multi,multi,ssemov,ssemov,ssemov,ssemov")
2516 (cond [(eq_attr "alternative" "0,1,2")
2518 (eq_attr "alternative" "3,4")
2521 /* For SSE1, we have many fewer alternatives. */
2522 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2523 (cond [(eq_attr "alternative" "5,6")
2524 (const_string "V4SF")
2526 (const_string "V2SF"))
2528 /* xorps is one byte shorter. */
2529 (eq_attr "alternative" "5")
2530 (cond [(ne (symbol_ref "optimize_size")
2532 (const_string "V4SF")
2533 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2537 (const_string "V2DF"))
2539 /* For architectures resolving dependencies on
2540 whole SSE registers use APD move to break dependency
2541 chains, otherwise use short move to avoid extra work.
2543 movaps encodes one byte shorter. */
2544 (eq_attr "alternative" "6")
2546 [(ne (symbol_ref "optimize_size")
2548 (const_string "V4SF")
2549 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2551 (const_string "V2DF")
2553 (const_string "DF"))
2554 /* For architectures resolving dependencies on register
2555 parts we may avoid extra work to zero out upper part
2557 (eq_attr "alternative" "7")
2559 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2561 (const_string "V1DF")
2562 (const_string "DF"))
2564 (const_string "DF")))])
2566 (define_insn "*movdf_integer"
2567 [(set (match_operand:DF 0 "nonimmediate_operand"
2568 "=f#Yr,m ,f#Yr,r#Yf ,o ,Y*x#rf,Y*x#rf,Y*x#rf,m")
2569 (match_operand:DF 1 "general_operand"
2570 "fm#Yr,f#Yr,G ,roF#Yf,Fr#Yf,C ,Y*x#rf,m ,Y*x#rf"))]
2571 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2572 && ((!optimize_size && TARGET_INTEGER_DFMODE_MOVES) || TARGET_64BIT)
2573 && (reload_in_progress || reload_completed
2574 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2575 || GET_CODE (operands[1]) != CONST_DOUBLE
2576 || memory_operand (operands[0], DFmode))"
2578 switch (which_alternative)
2581 return output_387_reg_move (insn, operands);
2584 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2585 return "fstp%z0\t%y0";
2587 return "fst%z0\t%y0";
2590 return standard_80387_constant_opcode (operands[1]);
2597 switch (get_attr_mode (insn))
2600 return "xorps\t%0, %0";
2602 return "xorpd\t%0, %0";
2604 return "pxor\t%0, %0";
2611 switch (get_attr_mode (insn))
2614 return "movaps\t{%1, %0|%0, %1}";
2616 return "movapd\t{%1, %0|%0, %1}";
2618 return "movdqa\t{%1, %0|%0, %1}";
2620 return "movq\t{%1, %0|%0, %1}";
2622 return "movsd\t{%1, %0|%0, %1}";
2624 return "movlpd\t{%1, %0|%0, %1}";
2626 return "movlps\t{%1, %0|%0, %1}";
2635 [(set_attr "type" "fmov,fmov,fmov,multi,multi,ssemov,ssemov,ssemov,ssemov")
2637 (cond [(eq_attr "alternative" "0,1,2")
2639 (eq_attr "alternative" "3,4")
2642 /* For SSE1, we have many fewer alternatives. */
2643 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2644 (cond [(eq_attr "alternative" "5,6")
2645 (const_string "V4SF")
2647 (const_string "V2SF"))
2649 /* xorps is one byte shorter. */
2650 (eq_attr "alternative" "5")
2651 (cond [(ne (symbol_ref "optimize_size")
2653 (const_string "V4SF")
2654 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2658 (const_string "V2DF"))
2660 /* For architectures resolving dependencies on
2661 whole SSE registers use APD move to break dependency
2662 chains, otherwise use short move to avoid extra work.
2664 movaps encodes one byte shorter. */
2665 (eq_attr "alternative" "6")
2667 [(ne (symbol_ref "optimize_size")
2669 (const_string "V4SF")
2670 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2672 (const_string "V2DF")
2674 (const_string "DF"))
2675 /* For architectures resolving dependencies on register
2676 parts we may avoid extra work to zero out upper part
2678 (eq_attr "alternative" "7")
2680 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2682 (const_string "V1DF")
2683 (const_string "DF"))
2685 (const_string "DF")))])
2688 [(set (match_operand:DF 0 "nonimmediate_operand" "")
2689 (match_operand:DF 1 "general_operand" ""))]
2691 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2692 && ! (ANY_FP_REG_P (operands[0]) ||
2693 (GET_CODE (operands[0]) == SUBREG
2694 && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2695 && ! (ANY_FP_REG_P (operands[1]) ||
2696 (GET_CODE (operands[1]) == SUBREG
2697 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2699 "ix86_split_long_move (operands); DONE;")
2701 (define_insn "*swapdf"
2702 [(set (match_operand:DF 0 "fp_register_operand" "+f")
2703 (match_operand:DF 1 "fp_register_operand" "+f"))
2706 "reload_completed || TARGET_80387"
2708 if (STACK_TOP_P (operands[0]))
2713 [(set_attr "type" "fxch")
2714 (set_attr "mode" "DF")])
2716 (define_expand "movxf"
2717 [(set (match_operand:XF 0 "nonimmediate_operand" "")
2718 (match_operand:XF 1 "general_operand" ""))]
2720 "ix86_expand_move (XFmode, operands); DONE;")
2722 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2723 ;; Size of pushdf using integer instructions is 3+3*memory operand size
2724 ;; Pushing using integer instructions is longer except for constants
2725 ;; and direct memory references.
2726 ;; (assuming that any given constant is pushed only once, but this ought to be
2727 ;; handled elsewhere).
2729 (define_insn "*pushxf_nointeger"
2730 [(set (match_operand:XF 0 "push_operand" "=X,X,X")
2731 (match_operand:XF 1 "general_no_elim_operand" "f,Fo,*r"))]
2734 /* This insn should be already split before reg-stack. */
2737 [(set_attr "type" "multi")
2738 (set_attr "unit" "i387,*,*")
2739 (set_attr "mode" "XF,SI,SI")])
2741 (define_insn "*pushxf_integer"
2742 [(set (match_operand:XF 0 "push_operand" "=<,<")
2743 (match_operand:XF 1 "general_no_elim_operand" "f#r,ro#f"))]
2746 /* This insn should be already split before reg-stack. */
2749 [(set_attr "type" "multi")
2750 (set_attr "unit" "i387,*")
2751 (set_attr "mode" "XF,SI")])
2754 [(set (match_operand 0 "push_operand" "")
2755 (match_operand 1 "general_operand" ""))]
2757 && (GET_MODE (operands[0]) == XFmode
2758 || GET_MODE (operands[0]) == DFmode)
2759 && !ANY_FP_REG_P (operands[1])"
2761 "ix86_split_long_move (operands); DONE;")
2764 [(set (match_operand:XF 0 "push_operand" "")
2765 (match_operand:XF 1 "any_fp_register_operand" ""))]
2767 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
2768 (set (mem:XF (reg:SI SP_REG)) (match_dup 1))]
2769 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
2772 [(set (match_operand:XF 0 "push_operand" "")
2773 (match_operand:XF 1 "any_fp_register_operand" ""))]
2775 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
2776 (set (mem:XF (reg:DI SP_REG)) (match_dup 1))]
2777 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
2779 ;; Do not use integer registers when optimizing for size
2780 (define_insn "*movxf_nointeger"
2781 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,*r,o")
2782 (match_operand:XF 1 "general_operand" "fm,f,G,*roF,F*r"))]
2784 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2785 && (reload_in_progress || reload_completed
2786 || GET_CODE (operands[1]) != CONST_DOUBLE
2787 || memory_operand (operands[0], XFmode))"
2789 switch (which_alternative)
2792 return output_387_reg_move (insn, operands);
2795 /* There is no non-popping store to memory for XFmode. So if
2796 we need one, follow the store with a load. */
2797 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2798 return "fstp%z0\t%y0\;fld%z0\t%y0";
2800 return "fstp%z0\t%y0";
2803 return standard_80387_constant_opcode (operands[1]);
2811 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2812 (set_attr "mode" "XF,XF,XF,SI,SI")])
2814 (define_insn "*movxf_integer"
2815 [(set (match_operand:XF 0 "nonimmediate_operand" "=f#r,m,f#r,r#f,o")
2816 (match_operand:XF 1 "general_operand" "fm#r,f#r,G,roF#f,Fr#f"))]
2818 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2819 && (reload_in_progress || reload_completed
2820 || GET_CODE (operands[1]) != CONST_DOUBLE
2821 || memory_operand (operands[0], XFmode))"
2823 switch (which_alternative)
2826 return output_387_reg_move (insn, operands);
2829 /* There is no non-popping store to memory for XFmode. So if
2830 we need one, follow the store with a load. */
2831 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2832 return "fstp%z0\t%y0\;fld%z0\t%y0";
2834 return "fstp%z0\t%y0";
2837 return standard_80387_constant_opcode (operands[1]);
2846 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2847 (set_attr "mode" "XF,XF,XF,SI,SI")])
2850 [(set (match_operand 0 "nonimmediate_operand" "")
2851 (match_operand 1 "general_operand" ""))]
2853 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2854 && GET_MODE (operands[0]) == XFmode
2855 && ! (ANY_FP_REG_P (operands[0]) ||
2856 (GET_CODE (operands[0]) == SUBREG
2857 && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2858 && ! (ANY_FP_REG_P (operands[1]) ||
2859 (GET_CODE (operands[1]) == SUBREG
2860 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2862 "ix86_split_long_move (operands); DONE;")
2865 [(set (match_operand 0 "register_operand" "")
2866 (match_operand 1 "memory_operand" ""))]
2868 && GET_CODE (operands[1]) == MEM
2869 && (GET_MODE (operands[0]) == XFmode
2870 || GET_MODE (operands[0]) == SFmode || GET_MODE (operands[0]) == DFmode)
2871 && constant_pool_reference_p (operands[1])"
2872 [(set (match_dup 0) (match_dup 1))]
2874 rtx c = avoid_constant_pool_reference (operands[1]);
2875 rtx r = operands[0];
2877 if (GET_CODE (r) == SUBREG)
2882 if (!standard_sse_constant_p (c))
2885 else if (FP_REG_P (r))
2887 if (!standard_80387_constant_p (c))
2890 else if (MMX_REG_P (r))
2896 (define_insn "swapxf"
2897 [(set (match_operand:XF 0 "register_operand" "+f")
2898 (match_operand:XF 1 "register_operand" "+f"))
2903 if (STACK_TOP_P (operands[0]))
2908 [(set_attr "type" "fxch")
2909 (set_attr "mode" "XF")])
2911 (define_expand "movtf"
2912 [(set (match_operand:TF 0 "nonimmediate_operand" "")
2913 (match_operand:TF 1 "nonimmediate_operand" ""))]
2916 ix86_expand_move (TFmode, operands);
2920 (define_insn "*movtf_internal"
2921 [(set (match_operand:TF 0 "nonimmediate_operand" "=r,o,x,x,xm")
2922 (match_operand:TF 1 "general_operand" "riFo,riF,C,xm,x"))]
2924 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2926 switch (which_alternative)
2932 if (get_attr_mode (insn) == MODE_V4SF)
2933 return "xorps\t%0, %0";
2935 return "pxor\t%0, %0";
2938 if (get_attr_mode (insn) == MODE_V4SF)
2939 return "movaps\t{%1, %0|%0, %1}";
2941 return "movdqa\t{%1, %0|%0, %1}";
2946 [(set_attr "type" "*,*,ssemov,ssemov,ssemov")
2948 (cond [(eq_attr "alternative" "2,3")
2950 (ne (symbol_ref "optimize_size")
2952 (const_string "V4SF")
2953 (const_string "TI"))
2954 (eq_attr "alternative" "4")
2956 (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2958 (ne (symbol_ref "optimize_size")
2960 (const_string "V4SF")
2961 (const_string "TI"))]
2962 (const_string "DI")))])
2965 [(set (match_operand:TF 0 "nonimmediate_operand" "")
2966 (match_operand:TF 1 "general_operand" ""))]
2967 "reload_completed && !SSE_REG_P (operands[0])
2968 && !SSE_REG_P (operands[1])"
2970 "ix86_split_long_move (operands); DONE;")
2972 ;; Zero extension instructions
2974 (define_expand "zero_extendhisi2"
2975 [(set (match_operand:SI 0 "register_operand" "")
2976 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
2979 if (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
2981 operands[1] = force_reg (HImode, operands[1]);
2982 emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
2987 (define_insn "zero_extendhisi2_and"
2988 [(set (match_operand:SI 0 "register_operand" "=r")
2989 (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
2990 (clobber (reg:CC FLAGS_REG))]
2991 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
2993 [(set_attr "type" "alu1")
2994 (set_attr "mode" "SI")])
2997 [(set (match_operand:SI 0 "register_operand" "")
2998 (zero_extend:SI (match_operand:HI 1 "register_operand" "")))
2999 (clobber (reg:CC FLAGS_REG))]
3000 "reload_completed && TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3001 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
3002 (clobber (reg:CC FLAGS_REG))])]
3005 (define_insn "*zero_extendhisi2_movzwl"
3006 [(set (match_operand:SI 0 "register_operand" "=r")
3007 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3008 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3009 "movz{wl|x}\t{%1, %0|%0, %1}"
3010 [(set_attr "type" "imovx")
3011 (set_attr "mode" "SI")])
3013 (define_expand "zero_extendqihi2"
3015 [(set (match_operand:HI 0 "register_operand" "")
3016 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3017 (clobber (reg:CC FLAGS_REG))])]
3021 (define_insn "*zero_extendqihi2_and"
3022 [(set (match_operand:HI 0 "register_operand" "=r,?&q")
3023 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3024 (clobber (reg:CC FLAGS_REG))]
3025 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3027 [(set_attr "type" "alu1")
3028 (set_attr "mode" "HI")])
3030 (define_insn "*zero_extendqihi2_movzbw_and"
3031 [(set (match_operand:HI 0 "register_operand" "=r,r")
3032 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3033 (clobber (reg:CC FLAGS_REG))]
3034 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3036 [(set_attr "type" "imovx,alu1")
3037 (set_attr "mode" "HI")])
3039 ; zero extend to SImode here to avoid partial register stalls
3040 (define_insn "*zero_extendqihi2_movzbl"
3041 [(set (match_operand:HI 0 "register_operand" "=r")
3042 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3043 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3044 "movz{bl|x}\t{%1, %k0|%k0, %k1}"
3045 [(set_attr "type" "imovx")
3046 (set_attr "mode" "SI")])
3048 ;; For the movzbw case strip only the clobber
3050 [(set (match_operand:HI 0 "register_operand" "")
3051 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3052 (clobber (reg:CC FLAGS_REG))]
3054 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3055 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3056 [(set (match_operand:HI 0 "register_operand" "")
3057 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))])
3059 ;; When source and destination does not overlap, clear destination
3060 ;; first and then do the movb
3062 [(set (match_operand:HI 0 "register_operand" "")
3063 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3064 (clobber (reg:CC FLAGS_REG))]
3066 && ANY_QI_REG_P (operands[0])
3067 && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3068 && !reg_overlap_mentioned_p (operands[0], operands[1])"
3069 [(set (match_dup 0) (const_int 0))
3070 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3071 "operands[2] = gen_lowpart (QImode, operands[0]);")
3073 ;; Rest is handled by single and.
3075 [(set (match_operand:HI 0 "register_operand" "")
3076 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))
3077 (clobber (reg:CC FLAGS_REG))]
3079 && true_regnum (operands[0]) == true_regnum (operands[1])"
3080 [(parallel [(set (match_dup 0) (and:HI (match_dup 0) (const_int 255)))
3081 (clobber (reg:CC FLAGS_REG))])]
3084 (define_expand "zero_extendqisi2"
3086 [(set (match_operand:SI 0 "register_operand" "")
3087 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3088 (clobber (reg:CC FLAGS_REG))])]
3092 (define_insn "*zero_extendqisi2_and"
3093 [(set (match_operand:SI 0 "register_operand" "=r,?&q")
3094 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3095 (clobber (reg:CC FLAGS_REG))]
3096 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3098 [(set_attr "type" "alu1")
3099 (set_attr "mode" "SI")])
3101 (define_insn "*zero_extendqisi2_movzbw_and"
3102 [(set (match_operand:SI 0 "register_operand" "=r,r")
3103 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3104 (clobber (reg:CC FLAGS_REG))]
3105 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3107 [(set_attr "type" "imovx,alu1")
3108 (set_attr "mode" "SI")])
3110 (define_insn "*zero_extendqisi2_movzbw"
3111 [(set (match_operand:SI 0 "register_operand" "=r")
3112 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3113 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3114 "movz{bl|x}\t{%1, %0|%0, %1}"
3115 [(set_attr "type" "imovx")
3116 (set_attr "mode" "SI")])
3118 ;; For the movzbl case strip only the clobber
3120 [(set (match_operand:SI 0 "register_operand" "")
3121 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3122 (clobber (reg:CC FLAGS_REG))]
3124 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3125 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3127 (zero_extend:SI (match_dup 1)))])
3129 ;; When source and destination does not overlap, clear destination
3130 ;; first and then do the movb
3132 [(set (match_operand:SI 0 "register_operand" "")
3133 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3134 (clobber (reg:CC FLAGS_REG))]
3136 && ANY_QI_REG_P (operands[0])
3137 && (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM)
3138 && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3139 && !reg_overlap_mentioned_p (operands[0], operands[1])"
3140 [(set (match_dup 0) (const_int 0))
3141 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3142 "operands[2] = gen_lowpart (QImode, operands[0]);")
3144 ;; Rest is handled by single and.
3146 [(set (match_operand:SI 0 "register_operand" "")
3147 (zero_extend:SI (match_operand:QI 1 "register_operand" "")))
3148 (clobber (reg:CC FLAGS_REG))]
3150 && true_regnum (operands[0]) == true_regnum (operands[1])"
3151 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 255)))
3152 (clobber (reg:CC FLAGS_REG))])]
3155 ;; %%% Kill me once multi-word ops are sane.
3156 (define_expand "zero_extendsidi2"
3157 [(set (match_operand:DI 0 "register_operand" "=r")
3158 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm")))]
3162 emit_insn (gen_zero_extendsidi2_32 (operands[0], operands[1]));
3167 (define_insn "zero_extendsidi2_32"
3168 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?*o,?*y,?*Y")
3169 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "0,rm,r,rm,rm")))
3170 (clobber (reg:CC FLAGS_REG))]
3176 movd\t{%1, %0|%0, %1}
3177 movd\t{%1, %0|%0, %1}"
3178 [(set_attr "mode" "SI,SI,SI,DI,TI")
3179 (set_attr "type" "multi,multi,multi,mmxmov,ssemov")])
3181 (define_insn "zero_extendsidi2_rex64"
3182 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,?*y,?*Y")
3183 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm,0,rm,rm")))]
3186 mov\t{%k1, %k0|%k0, %k1}
3188 movd\t{%1, %0|%0, %1}
3189 movd\t{%1, %0|%0, %1}"
3190 [(set_attr "type" "imovx,imov,mmxmov,ssemov")
3191 (set_attr "mode" "SI,DI,SI,SI")])
3194 [(set (match_operand:DI 0 "memory_operand" "")
3195 (zero_extend:DI (match_dup 0)))]
3197 [(set (match_dup 4) (const_int 0))]
3198 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3201 [(set (match_operand:DI 0 "register_operand" "")
3202 (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3203 (clobber (reg:CC FLAGS_REG))]
3204 "!TARGET_64BIT && reload_completed
3205 && true_regnum (operands[0]) == true_regnum (operands[1])"
3206 [(set (match_dup 4) (const_int 0))]
3207 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3210 [(set (match_operand:DI 0 "nonimmediate_operand" "")
3211 (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3212 (clobber (reg:CC FLAGS_REG))]
3213 "!TARGET_64BIT && reload_completed
3214 && !SSE_REG_P (operands[0]) && !MMX_REG_P (operands[0])"
3215 [(set (match_dup 3) (match_dup 1))
3216 (set (match_dup 4) (const_int 0))]
3217 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3219 (define_insn "zero_extendhidi2"
3220 [(set (match_operand:DI 0 "register_operand" "=r")
3221 (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3223 "movz{wl|x}\t{%1, %k0|%k0, %1}"
3224 [(set_attr "type" "imovx")
3225 (set_attr "mode" "DI")])
3227 (define_insn "zero_extendqidi2"
3228 [(set (match_operand:DI 0 "register_operand" "=r")
3229 (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "rm")))]
3231 "movz{bl|x}\t{%1, %k0|%k0, %1}"
3232 [(set_attr "type" "imovx")
3233 (set_attr "mode" "DI")])
3235 ;; Sign extension instructions
3237 (define_expand "extendsidi2"
3238 [(parallel [(set (match_operand:DI 0 "register_operand" "")
3239 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3240 (clobber (reg:CC FLAGS_REG))
3241 (clobber (match_scratch:SI 2 ""))])]
3246 emit_insn (gen_extendsidi2_rex64 (operands[0], operands[1]));
3251 (define_insn "*extendsidi2_1"
3252 [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3253 (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3254 (clobber (reg:CC FLAGS_REG))
3255 (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3259 (define_insn "extendsidi2_rex64"
3260 [(set (match_operand:DI 0 "register_operand" "=*a,r")
3261 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3265 movs{lq|x}\t{%1,%0|%0, %1}"
3266 [(set_attr "type" "imovx")
3267 (set_attr "mode" "DI")
3268 (set_attr "prefix_0f" "0")
3269 (set_attr "modrm" "0,1")])
3271 (define_insn "extendhidi2"
3272 [(set (match_operand:DI 0 "register_operand" "=r")
3273 (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3275 "movs{wq|x}\t{%1,%0|%0, %1}"
3276 [(set_attr "type" "imovx")
3277 (set_attr "mode" "DI")])
3279 (define_insn "extendqidi2"
3280 [(set (match_operand:DI 0 "register_operand" "=r")
3281 (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3283 "movs{bq|x}\t{%1,%0|%0, %1}"
3284 [(set_attr "type" "imovx")
3285 (set_attr "mode" "DI")])
3287 ;; Extend to memory case when source register does die.
3289 [(set (match_operand:DI 0 "memory_operand" "")
3290 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3291 (clobber (reg:CC FLAGS_REG))
3292 (clobber (match_operand:SI 2 "register_operand" ""))]
3294 && dead_or_set_p (insn, operands[1])
3295 && !reg_mentioned_p (operands[1], operands[0]))"
3296 [(set (match_dup 3) (match_dup 1))
3297 (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3298 (clobber (reg:CC FLAGS_REG))])
3299 (set (match_dup 4) (match_dup 1))]
3300 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3302 ;; Extend to memory case when source register does not die.
3304 [(set (match_operand:DI 0 "memory_operand" "")
3305 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3306 (clobber (reg:CC FLAGS_REG))
3307 (clobber (match_operand:SI 2 "register_operand" ""))]
3311 split_di (&operands[0], 1, &operands[3], &operands[4]);
3313 emit_move_insn (operands[3], operands[1]);
3315 /* Generate a cltd if possible and doing so it profitable. */
3316 if (true_regnum (operands[1]) == 0
3317 && true_regnum (operands[2]) == 1
3318 && (optimize_size || TARGET_USE_CLTD))
3320 emit_insn (gen_ashrsi3_31 (operands[2], operands[1], GEN_INT (31)));
3324 emit_move_insn (operands[2], operands[1]);
3325 emit_insn (gen_ashrsi3_31 (operands[2], operands[2], GEN_INT (31)));
3327 emit_move_insn (operands[4], operands[2]);
3331 ;; Extend to register case. Optimize case where source and destination
3332 ;; registers match and cases where we can use cltd.
3334 [(set (match_operand:DI 0 "register_operand" "")
3335 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3336 (clobber (reg:CC FLAGS_REG))
3337 (clobber (match_scratch:SI 2 ""))]
3341 split_di (&operands[0], 1, &operands[3], &operands[4]);
3343 if (true_regnum (operands[3]) != true_regnum (operands[1]))
3344 emit_move_insn (operands[3], operands[1]);
3346 /* Generate a cltd if possible and doing so it profitable. */
3347 if (true_regnum (operands[3]) == 0
3348 && (optimize_size || TARGET_USE_CLTD))
3350 emit_insn (gen_ashrsi3_31 (operands[4], operands[3], GEN_INT (31)));
3354 if (true_regnum (operands[4]) != true_regnum (operands[1]))
3355 emit_move_insn (operands[4], operands[1]);
3357 emit_insn (gen_ashrsi3_31 (operands[4], operands[4], GEN_INT (31)));
3361 (define_insn "extendhisi2"
3362 [(set (match_operand:SI 0 "register_operand" "=*a,r")
3363 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3366 switch (get_attr_prefix_0f (insn))
3369 return "{cwtl|cwde}";
3371 return "movs{wl|x}\t{%1,%0|%0, %1}";
3374 [(set_attr "type" "imovx")
3375 (set_attr "mode" "SI")
3376 (set (attr "prefix_0f")
3377 ;; movsx is short decodable while cwtl is vector decoded.
3378 (if_then_else (and (eq_attr "cpu" "!k6")
3379 (eq_attr "alternative" "0"))
3381 (const_string "1")))
3383 (if_then_else (eq_attr "prefix_0f" "0")
3385 (const_string "1")))])
3387 (define_insn "*extendhisi2_zext"
3388 [(set (match_operand:DI 0 "register_operand" "=*a,r")
3390 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3393 switch (get_attr_prefix_0f (insn))
3396 return "{cwtl|cwde}";
3398 return "movs{wl|x}\t{%1,%k0|%k0, %1}";
3401 [(set_attr "type" "imovx")
3402 (set_attr "mode" "SI")
3403 (set (attr "prefix_0f")
3404 ;; movsx is short decodable while cwtl is vector decoded.
3405 (if_then_else (and (eq_attr "cpu" "!k6")
3406 (eq_attr "alternative" "0"))
3408 (const_string "1")))
3410 (if_then_else (eq_attr "prefix_0f" "0")
3412 (const_string "1")))])
3414 (define_insn "extendqihi2"
3415 [(set (match_operand:HI 0 "register_operand" "=*a,r")
3416 (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3419 switch (get_attr_prefix_0f (insn))
3422 return "{cbtw|cbw}";
3424 return "movs{bw|x}\t{%1,%0|%0, %1}";
3427 [(set_attr "type" "imovx")
3428 (set_attr "mode" "HI")
3429 (set (attr "prefix_0f")
3430 ;; movsx is short decodable while cwtl is vector decoded.
3431 (if_then_else (and (eq_attr "cpu" "!k6")
3432 (eq_attr "alternative" "0"))
3434 (const_string "1")))
3436 (if_then_else (eq_attr "prefix_0f" "0")
3438 (const_string "1")))])
3440 (define_insn "extendqisi2"
3441 [(set (match_operand:SI 0 "register_operand" "=r")
3442 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3444 "movs{bl|x}\t{%1,%0|%0, %1}"
3445 [(set_attr "type" "imovx")
3446 (set_attr "mode" "SI")])
3448 (define_insn "*extendqisi2_zext"
3449 [(set (match_operand:DI 0 "register_operand" "=r")
3451 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3453 "movs{bl|x}\t{%1,%k0|%k0, %1}"
3454 [(set_attr "type" "imovx")
3455 (set_attr "mode" "SI")])
3457 ;; Conversions between float and double.
3459 ;; These are all no-ops in the model used for the 80387. So just
3462 ;; %%% Kill these when call knows how to work out a DFmode push earlier.
3463 (define_insn "*dummy_extendsfdf2"
3464 [(set (match_operand:DF 0 "push_operand" "=<")
3465 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fY")))]
3470 [(set (match_operand:DF 0 "push_operand" "")
3471 (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3473 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
3474 (set (mem:DF (reg:SI SP_REG)) (float_extend:DF (match_dup 1)))])
3477 [(set (match_operand:DF 0 "push_operand" "")
3478 (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3480 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
3481 (set (mem:DF (reg:DI SP_REG)) (float_extend:DF (match_dup 1)))])
3483 (define_insn "*dummy_extendsfxf2"
3484 [(set (match_operand:XF 0 "push_operand" "=<")
3485 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "f")))]
3490 [(set (match_operand:XF 0 "push_operand" "")
3491 (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3493 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3494 (set (mem:XF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))]
3495 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3498 [(set (match_operand:XF 0 "push_operand" "")
3499 (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3501 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3502 (set (mem:DF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))]
3503 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3506 [(set (match_operand:XF 0 "push_operand" "")
3507 (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3509 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3510 (set (mem:DF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))]
3511 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3514 [(set (match_operand:XF 0 "push_operand" "")
3515 (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3517 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3518 (set (mem:XF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))]
3519 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3521 (define_expand "extendsfdf2"
3522 [(set (match_operand:DF 0 "nonimmediate_operand" "")
3523 (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
3524 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3526 /* ??? Needed for compress_float_constant since all fp constants
3527 are LEGITIMATE_CONSTANT_P. */
3528 if (GET_CODE (operands[1]) == CONST_DOUBLE)
3529 operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3530 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3531 operands[1] = force_reg (SFmode, operands[1]);
3534 (define_insn "*extendsfdf2_mixed"
3535 [(set (match_operand:DF 0 "nonimmediate_operand" "=f#Y,m#fY,Y#f")
3536 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm#Y,f#Y,mY#f")))]
3537 "TARGET_SSE2 && TARGET_MIX_SSE_I387
3538 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3540 switch (which_alternative)
3543 return output_387_reg_move (insn, operands);
3546 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3547 return "fstp%z0\t%y0";
3549 return "fst%z0\t%y0";
3552 return "cvtss2sd\t{%1, %0|%0, %1}";
3558 [(set_attr "type" "fmov,fmov,ssecvt")
3559 (set_attr "mode" "SF,XF,DF")])
3561 (define_insn "*extendsfdf2_sse"
3562 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y")
3563 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "mY")))]
3564 "TARGET_SSE2 && TARGET_SSE_MATH
3565 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3566 "cvtss2sd\t{%1, %0|%0, %1}"
3567 [(set_attr "type" "ssecvt")
3568 (set_attr "mode" "DF")])
3570 (define_insn "*extendsfdf2_i387"
3571 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
3572 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3574 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3576 switch (which_alternative)
3579 return output_387_reg_move (insn, operands);
3582 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3583 return "fstp%z0\t%y0";
3585 return "fst%z0\t%y0";
3591 [(set_attr "type" "fmov")
3592 (set_attr "mode" "SF,XF")])
3594 (define_expand "extendsfxf2"
3595 [(set (match_operand:XF 0 "nonimmediate_operand" "")
3596 (float_extend:XF (match_operand:SF 1 "general_operand" "")))]
3599 /* ??? Needed for compress_float_constant since all fp constants
3600 are LEGITIMATE_CONSTANT_P. */
3601 if (GET_CODE (operands[1]) == CONST_DOUBLE)
3602 operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3603 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3604 operands[1] = force_reg (SFmode, operands[1]);
3607 (define_insn "*extendsfxf2_i387"
3608 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3609 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3611 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3613 switch (which_alternative)
3616 return output_387_reg_move (insn, operands);
3619 /* There is no non-popping store to memory for XFmode. So if
3620 we need one, follow the store with a load. */
3621 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3622 return "fstp%z0\t%y0";
3624 return "fstp%z0\t%y0\n\tfld%z0\t%y0";
3630 [(set_attr "type" "fmov")
3631 (set_attr "mode" "SF,XF")])
3633 (define_expand "extenddfxf2"
3634 [(set (match_operand:XF 0 "nonimmediate_operand" "")
3635 (float_extend:XF (match_operand:DF 1 "general_operand" "")))]
3638 /* ??? Needed for compress_float_constant since all fp constants
3639 are LEGITIMATE_CONSTANT_P. */
3640 if (GET_CODE (operands[1]) == CONST_DOUBLE)
3641 operands[1] = validize_mem (force_const_mem (DFmode, operands[1]));
3642 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3643 operands[1] = force_reg (DFmode, operands[1]);
3646 (define_insn "*extenddfxf2_i387"
3647 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3648 (float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "fm,f")))]
3650 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3652 switch (which_alternative)
3655 return output_387_reg_move (insn, operands);
3658 /* There is no non-popping store to memory for XFmode. So if
3659 we need one, follow the store with a load. */
3660 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3661 return "fstp%z0\t%y0\n\tfld%z0\t%y0";
3663 return "fstp%z0\t%y0";
3669 [(set_attr "type" "fmov")
3670 (set_attr "mode" "DF,XF")])
3672 ;; %%% This seems bad bad news.
3673 ;; This cannot output into an f-reg because there is no way to be sure
3674 ;; of truncating in that case. Otherwise this is just like a simple move
3675 ;; insn. So we pretend we can output to a reg in order to get better
3676 ;; register preferencing, but we really use a stack slot.
3678 ;; Conversion from DFmode to SFmode.
3680 (define_expand "truncdfsf2"
3681 [(set (match_operand:SF 0 "nonimmediate_operand" "")
3683 (match_operand:DF 1 "nonimmediate_operand" "")))]
3684 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3686 if (MEM_P (operands[0]) && MEM_P (operands[1]))
3687 operands[1] = force_reg (DFmode, operands[1]);
3689 if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387)
3691 else if (flag_unsafe_math_optimizations)
3695 rtx temp = assign_386_stack_local (SFmode, SLOT_TEMP);
3696 emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp));
3701 (define_expand "truncdfsf2_with_temp"
3702 [(parallel [(set (match_operand:SF 0 "" "")
3703 (float_truncate:SF (match_operand:DF 1 "" "")))
3704 (clobber (match_operand:SF 2 "" ""))])]
3707 (define_insn "*truncdfsf_fast_mixed"
3708 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,f,Y")
3710 (match_operand:DF 1 "nonimmediate_operand" "f ,f,Ym")))]
3711 "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations"
3713 switch (which_alternative)
3716 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3717 return "fstp%z0\t%y0";
3719 return "fst%z0\t%y0";
3721 return output_387_reg_move (insn, operands);
3723 return "cvtsd2ss\t{%1, %0|%0, %1}";
3728 [(set_attr "type" "fmov,fmov,ssecvt")
3729 (set_attr "mode" "SF")])
3731 ;; Yes, this one doesn't depend on flag_unsafe_math_optimizations,
3732 ;; because nothing we do here is unsafe.
3733 (define_insn "*truncdfsf_fast_sse"
3734 [(set (match_operand:SF 0 "nonimmediate_operand" "=Y")
3736 (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
3737 "TARGET_SSE2 && TARGET_SSE_MATH"
3738 "cvtsd2ss\t{%1, %0|%0, %1}"
3739 [(set_attr "type" "ssecvt")
3740 (set_attr "mode" "SF")])
3742 (define_insn "*truncdfsf_fast_i387"
3743 [(set (match_operand:SF 0 "nonimmediate_operand" "=fm")
3745 (match_operand:DF 1 "nonimmediate_operand" "f")))]
3746 "TARGET_80387 && flag_unsafe_math_optimizations"
3747 "* return output_387_reg_move (insn, operands);"
3748 [(set_attr "type" "fmov")
3749 (set_attr "mode" "SF")])
3751 (define_insn "*truncdfsf_mixed"
3752 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r,Y")
3754 (match_operand:DF 1 "nonimmediate_operand" "f ,f ,Ym")))
3755 (clobber (match_operand:SF 2 "memory_operand" "=X,m ,X"))]
3756 "TARGET_MIX_SSE_I387"
3758 switch (which_alternative)
3761 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3762 return "fstp%z0\t%y0";
3764 return "fst%z0\t%y0";
3768 return "cvtsd2ss\t{%1, %0|%0, %1}";
3773 [(set_attr "type" "fmov,multi,ssecvt")
3774 (set_attr "unit" "*,i387,*")
3775 (set_attr "mode" "SF")])
3777 (define_insn "*truncdfsf_i387"
3778 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r")
3780 (match_operand:DF 1 "nonimmediate_operand" "f,f")))
3781 (clobber (match_operand:SF 2 "memory_operand" "=X,m"))]
3784 switch (which_alternative)
3787 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3788 return "fstp%z0\t%y0";
3790 return "fst%z0\t%y0";
3797 [(set_attr "type" "fmov,multi")
3798 (set_attr "unit" "*,i387")
3799 (set_attr "mode" "SF")])
3801 (define_insn "*truncdfsf2_i387_1"
3802 [(set (match_operand:SF 0 "memory_operand" "=m")
3804 (match_operand:DF 1 "register_operand" "f")))]
3806 && !(TARGET_SSE2 && TARGET_SSE_MATH)
3807 && !TARGET_MIX_SSE_I387"
3809 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3810 return "fstp%z0\t%y0";
3812 return "fst%z0\t%y0";
3814 [(set_attr "type" "fmov")
3815 (set_attr "mode" "SF")])
3818 [(set (match_operand:SF 0 "register_operand" "")
3820 (match_operand:DF 1 "fp_register_operand" "")))
3821 (clobber (match_operand 2 "" ""))]
3823 [(set (match_dup 2) (match_dup 1))
3824 (set (match_dup 0) (match_dup 2))]
3826 operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1]));
3829 ;; Conversion from XFmode to SFmode.
3831 (define_expand "truncxfsf2"
3832 [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
3834 (match_operand:XF 1 "register_operand" "")))
3835 (clobber (match_dup 2))])]
3838 if (flag_unsafe_math_optimizations)
3840 rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SFmode);
3841 emit_insn (gen_truncxfsf2_i387_noop (reg, operands[1]));
3842 if (reg != operands[0])
3843 emit_move_insn (operands[0], reg);
3847 operands[2] = assign_386_stack_local (SFmode, SLOT_TEMP);
3850 (define_insn "*truncxfsf2_mixed"
3851 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f#rx,?r#fx,?x#rf")
3853 (match_operand:XF 1 "register_operand" "f,f,f,f")))
3854 (clobber (match_operand:SF 2 "memory_operand" "=X,m,m,m"))]
3855 "TARGET_MIX_SSE_I387"
3857 gcc_assert (!which_alternative);
3858 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3859 return "fstp%z0\t%y0";
3861 return "fst%z0\t%y0";
3863 [(set_attr "type" "fmov,multi,multi,multi")
3864 (set_attr "unit" "*,i387,i387,i387")
3865 (set_attr "mode" "SF")])
3867 (define_insn "truncxfsf2_i387_noop"
3868 [(set (match_operand:SF 0 "register_operand" "=f")
3869 (float_truncate:SF (match_operand:XF 1 "register_operand" "f")))]
3870 "TARGET_80387 && flag_unsafe_math_optimizations"
3872 return output_387_reg_move (insn, operands);
3874 [(set_attr "type" "fmov")
3875 (set_attr "mode" "SF")])
3877 (define_insn "*truncxfsf2_i387"
3878 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f#r,?r#f")
3880 (match_operand:XF 1 "register_operand" "f,f,f")))
3881 (clobber (match_operand:SF 2 "memory_operand" "=X,m,m"))]
3884 gcc_assert (!which_alternative);
3885 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3886 return "fstp%z0\t%y0";
3888 return "fst%z0\t%y0";
3890 [(set_attr "type" "fmov,multi,multi")
3891 (set_attr "unit" "*,i387,i387")
3892 (set_attr "mode" "SF")])
3894 (define_insn "*truncxfsf2_i387_1"
3895 [(set (match_operand:SF 0 "memory_operand" "=m")
3897 (match_operand:XF 1 "register_operand" "f")))]
3900 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3901 return "fstp%z0\t%y0";
3903 return "fst%z0\t%y0";
3905 [(set_attr "type" "fmov")
3906 (set_attr "mode" "SF")])
3909 [(set (match_operand:SF 0 "register_operand" "")
3911 (match_operand:XF 1 "register_operand" "")))
3912 (clobber (match_operand:SF 2 "memory_operand" ""))]
3913 "TARGET_80387 && reload_completed"
3914 [(set (match_dup 2) (float_truncate:SF (match_dup 1)))
3915 (set (match_dup 0) (match_dup 2))]
3919 [(set (match_operand:SF 0 "memory_operand" "")
3921 (match_operand:XF 1 "register_operand" "")))
3922 (clobber (match_operand:SF 2 "memory_operand" ""))]
3924 [(set (match_dup 0) (float_truncate:SF (match_dup 1)))]
3927 ;; Conversion from XFmode to DFmode.
3929 (define_expand "truncxfdf2"
3930 [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
3932 (match_operand:XF 1 "register_operand" "")))
3933 (clobber (match_dup 2))])]
3936 if (flag_unsafe_math_optimizations)
3938 rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DFmode);
3939 emit_insn (gen_truncxfdf2_i387_noop (reg, operands[1]));
3940 if (reg != operands[0])
3941 emit_move_insn (operands[0], reg);
3945 operands[2] = assign_386_stack_local (DFmode, SLOT_TEMP);
3948 (define_insn "*truncxfdf2_mixed"
3949 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f#rY,?r#fY,?Y#rf")
3951 (match_operand:XF 1 "register_operand" "f,f,f,f")))
3952 (clobber (match_operand:DF 2 "memory_operand" "=X,m,m,m"))]
3953 "TARGET_SSE2 && TARGET_MIX_SSE_I387"
3955 gcc_assert (!which_alternative);
3956 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3957 return "fstp%z0\t%y0";
3959 return "fst%z0\t%y0";
3961 [(set_attr "type" "fmov,multi,multi,multi")
3962 (set_attr "unit" "*,i387,i387,i387")
3963 (set_attr "mode" "DF")])
3965 (define_insn "truncxfdf2_i387_noop"
3966 [(set (match_operand:DF 0 "register_operand" "=f")
3967 (float_truncate:DF (match_operand:XF 1 "register_operand" "f")))]
3968 "TARGET_80387 && flag_unsafe_math_optimizations"
3970 return output_387_reg_move (insn, operands);
3972 [(set_attr "type" "fmov")
3973 (set_attr "mode" "DF")])
3975 (define_insn "*truncxfdf2_i387"
3976 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f#r,?r#f")
3978 (match_operand:XF 1 "register_operand" "f,f,f")))
3979 (clobber (match_operand:DF 2 "memory_operand" "=X,m,m"))]
3982 gcc_assert (!which_alternative);
3983 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3984 return "fstp%z0\t%y0";
3986 return "fst%z0\t%y0";
3988 [(set_attr "type" "fmov,multi,multi")
3989 (set_attr "unit" "*,i387,i387")
3990 (set_attr "mode" "DF")])
3992 (define_insn "*truncxfdf2_i387_1"
3993 [(set (match_operand:DF 0 "memory_operand" "=m")
3995 (match_operand:XF 1 "register_operand" "f")))]
3998 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3999 return "fstp%z0\t%y0";
4001 return "fst%z0\t%y0";
4003 [(set_attr "type" "fmov")
4004 (set_attr "mode" "DF")])
4007 [(set (match_operand:DF 0 "register_operand" "")
4009 (match_operand:XF 1 "register_operand" "")))
4010 (clobber (match_operand:DF 2 "memory_operand" ""))]
4011 "TARGET_80387 && reload_completed"
4012 [(set (match_dup 2) (float_truncate:DF (match_dup 1)))
4013 (set (match_dup 0) (match_dup 2))]
4017 [(set (match_operand:DF 0 "memory_operand" "")
4019 (match_operand:XF 1 "register_operand" "")))
4020 (clobber (match_operand:DF 2 "memory_operand" ""))]
4022 [(set (match_dup 0) (float_truncate:DF (match_dup 1)))]
4025 ;; Signed conversion to DImode.
4027 (define_expand "fix_truncxfdi2"
4028 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4029 (fix:DI (match_operand:XF 1 "register_operand" "")))
4030 (clobber (reg:CC FLAGS_REG))])]
4035 emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4040 (define_expand "fix_trunc<mode>di2"
4041 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4042 (fix:DI (match_operand:SSEMODEF 1 "register_operand" "")))
4043 (clobber (reg:CC FLAGS_REG))])]
4044 "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))"
4047 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4049 emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4052 if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))
4054 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4055 emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1]));
4056 if (out != operands[0])
4057 emit_move_insn (operands[0], out);
4062 ;; Signed conversion to SImode.
4064 (define_expand "fix_truncxfsi2"
4065 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4066 (fix:SI (match_operand:XF 1 "register_operand" "")))
4067 (clobber (reg:CC FLAGS_REG))])]
4072 emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4077 (define_expand "fix_trunc<mode>si2"
4078 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4079 (fix:SI (match_operand:SSEMODEF 1 "register_operand" "")))
4080 (clobber (reg:CC FLAGS_REG))])]
4081 "TARGET_80387 || SSE_FLOAT_MODE_P (<MODE>mode)"
4084 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4086 emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4089 if (SSE_FLOAT_MODE_P (<MODE>mode))
4091 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4092 emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1]));
4093 if (out != operands[0])
4094 emit_move_insn (operands[0], out);
4099 ;; Signed conversion to HImode.
4101 (define_expand "fix_trunc<mode>hi2"
4102 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4103 (fix:HI (match_operand:X87MODEF 1 "register_operand" "")))
4104 (clobber (reg:CC FLAGS_REG))])]
4106 && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))"
4110 emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1]));
4115 ;; When SSE is available, it is always faster to use it!
4116 (define_insn "fix_truncsfdi_sse"
4117 [(set (match_operand:DI 0 "register_operand" "=r,r")
4118 (fix:DI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))]
4119 "TARGET_64BIT && TARGET_SSE && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4120 "cvttss2si{q}\t{%1, %0|%0, %1}"
4121 [(set_attr "type" "sseicvt")
4122 (set_attr "mode" "SF")
4123 (set_attr "athlon_decode" "double,vector")])
4125 (define_insn "fix_truncdfdi_sse"
4126 [(set (match_operand:DI 0 "register_operand" "=r,r")
4127 (fix:DI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))]
4128 "TARGET_64BIT && TARGET_SSE2 && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4129 "cvttsd2si{q}\t{%1, %0|%0, %1}"
4130 [(set_attr "type" "sseicvt")
4131 (set_attr "mode" "DF")
4132 (set_attr "athlon_decode" "double,vector")])
4134 (define_insn "fix_truncsfsi_sse"
4135 [(set (match_operand:SI 0 "register_operand" "=r,r")
4136 (fix:SI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))]
4137 "TARGET_SSE && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4138 "cvttss2si\t{%1, %0|%0, %1}"
4139 [(set_attr "type" "sseicvt")
4140 (set_attr "mode" "DF")
4141 (set_attr "athlon_decode" "double,vector")])
4143 (define_insn "fix_truncdfsi_sse"
4144 [(set (match_operand:SI 0 "register_operand" "=r,r")
4145 (fix:SI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))]
4146 "TARGET_SSE2 && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4147 "cvttsd2si\t{%1, %0|%0, %1}"
4148 [(set_attr "type" "sseicvt")
4149 (set_attr "mode" "DF")
4150 (set_attr "athlon_decode" "double,vector")])
4152 ;; Avoid vector decoded forms of the instruction.
4154 [(match_scratch:DF 2 "Y")
4155 (set (match_operand:SSEMODEI24 0 "register_operand" "")
4156 (fix:SSEMODEI24 (match_operand:DF 1 "memory_operand" "")))]
4157 "TARGET_K8 && !optimize_size"
4158 [(set (match_dup 2) (match_dup 1))
4159 (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4163 [(match_scratch:SF 2 "x")
4164 (set (match_operand:SSEMODEI24 0 "register_operand" "")
4165 (fix:SSEMODEI24 (match_operand:SF 1 "memory_operand" "")))]
4166 "TARGET_K8 && !optimize_size"
4167 [(set (match_dup 2) (match_dup 1))
4168 (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4171 (define_insn_and_split "fix_trunc<mode>_fisttp_i387_1"
4172 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4173 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))]
4175 && FLOAT_MODE_P (GET_MODE (operands[1]))
4176 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4177 && (TARGET_64BIT || <MODE>mode != DImode))
4179 && !(reload_completed || reload_in_progress)"
4184 if (memory_operand (operands[0], VOIDmode))
4185 emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1]));
4188 operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4189 emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0],
4195 [(set_attr "type" "fisttp")
4196 (set_attr "mode" "<MODE>")])
4198 (define_insn "fix_trunc<mode>_i387_fisttp"
4199 [(set (match_operand:X87MODEI 0 "memory_operand" "=m")
4200 (fix:X87MODEI (match_operand 1 "register_operand" "f")))
4201 (clobber (match_scratch:XF 2 "=&1f"))]
4203 && FLOAT_MODE_P (GET_MODE (operands[1]))
4204 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4205 && (TARGET_64BIT || <MODE>mode != DImode))
4206 && TARGET_SSE_MATH)"
4207 "* return output_fix_trunc (insn, operands, 1);"
4208 [(set_attr "type" "fisttp")
4209 (set_attr "mode" "<MODE>")])
4211 (define_insn "fix_trunc<mode>_i387_fisttp_with_temp"
4212 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4213 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
4214 (clobber (match_operand:X87MODEI 2 "memory_operand" "=m,m"))
4215 (clobber (match_scratch:XF 3 "=&1f,&1f"))]
4217 && FLOAT_MODE_P (GET_MODE (operands[1]))
4218 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4219 && (TARGET_64BIT || <MODE>mode != DImode))
4220 && TARGET_SSE_MATH)"
4222 [(set_attr "type" "fisttp")
4223 (set_attr "mode" "<MODE>")])
4226 [(set (match_operand:X87MODEI 0 "register_operand" "")
4227 (fix:X87MODEI (match_operand 1 "register_operand" "")))
4228 (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4229 (clobber (match_scratch 3 ""))]
4231 [(parallel [(set (match_dup 2) (fix:X87MODEI (match_dup 1)))
4232 (clobber (match_dup 3))])
4233 (set (match_dup 0) (match_dup 2))]
4237 [(set (match_operand:X87MODEI 0 "memory_operand" "")
4238 (fix:X87MODEI (match_operand 1 "register_operand" "")))
4239 (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4240 (clobber (match_scratch 3 ""))]
4242 [(parallel [(set (match_dup 0) (fix:X87MODEI (match_dup 1)))
4243 (clobber (match_dup 3))])]
4246 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4247 ;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control
4248 ;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG
4249 ;; clobbering insns can be used. Look at emit_i387_cw_initialization ()
4250 ;; function in i386.c.
4251 (define_insn_and_split "*fix_trunc<mode>_i387_1"
4252 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4253 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
4254 (clobber (reg:CC FLAGS_REG))]
4255 "TARGET_80387 && !TARGET_FISTTP
4256 && FLOAT_MODE_P (GET_MODE (operands[1]))
4257 && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4258 && (TARGET_64BIT || <MODE>mode != DImode))
4259 && !(reload_completed || reload_in_progress)"
4264 ix86_optimize_mode_switching[I387_TRUNC] = 1;
4266 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
4267 operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
4268 if (memory_operand (operands[0], VOIDmode))
4269 emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1],
4270 operands[2], operands[3]));
4273 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4274 emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1],
4275 operands[2], operands[3],
4280 [(set_attr "type" "fistp")
4281 (set_attr "i387_cw" "trunc")
4282 (set_attr "mode" "<MODE>")])
4284 (define_insn "fix_truncdi_i387"
4285 [(set (match_operand:DI 0 "memory_operand" "=m")
4286 (fix:DI (match_operand 1 "register_operand" "f")))
4287 (use (match_operand:HI 2 "memory_operand" "m"))
4288 (use (match_operand:HI 3 "memory_operand" "m"))
4289 (clobber (match_scratch:XF 4 "=&1f"))]
4290 "TARGET_80387 && !TARGET_FISTTP
4291 && FLOAT_MODE_P (GET_MODE (operands[1]))
4292 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4293 "* return output_fix_trunc (insn, operands, 0);"
4294 [(set_attr "type" "fistp")
4295 (set_attr "i387_cw" "trunc")
4296 (set_attr "mode" "DI")])
4298 (define_insn "fix_truncdi_i387_with_temp"
4299 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4300 (fix:DI (match_operand 1 "register_operand" "f,f")))
4301 (use (match_operand:HI 2 "memory_operand" "m,m"))
4302 (use (match_operand:HI 3 "memory_operand" "m,m"))
4303 (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
4304 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
4305 "TARGET_80387 && !TARGET_FISTTP
4306 && FLOAT_MODE_P (GET_MODE (operands[1]))
4307 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4309 [(set_attr "type" "fistp")
4310 (set_attr "i387_cw" "trunc")
4311 (set_attr "mode" "DI")])
4314 [(set (match_operand:DI 0 "register_operand" "")
4315 (fix:DI (match_operand 1 "register_operand" "")))
4316 (use (match_operand:HI 2 "memory_operand" ""))
4317 (use (match_operand:HI 3 "memory_operand" ""))
4318 (clobber (match_operand:DI 4 "memory_operand" ""))
4319 (clobber (match_scratch 5 ""))]
4321 [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
4324 (clobber (match_dup 5))])
4325 (set (match_dup 0) (match_dup 4))]
4329 [(set (match_operand:DI 0 "memory_operand" "")
4330 (fix:DI (match_operand 1 "register_operand" "")))
4331 (use (match_operand:HI 2 "memory_operand" ""))
4332 (use (match_operand:HI 3 "memory_operand" ""))
4333 (clobber (match_operand:DI 4 "memory_operand" ""))
4334 (clobber (match_scratch 5 ""))]
4336 [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
4339 (clobber (match_dup 5))])]
4342 (define_insn "fix_trunc<mode>_i387"
4343 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
4344 (fix:X87MODEI12 (match_operand 1 "register_operand" "f")))
4345 (use (match_operand:HI 2 "memory_operand" "m"))
4346 (use (match_operand:HI 3 "memory_operand" "m"))]
4347 "TARGET_80387 && !TARGET_FISTTP
4348 && FLOAT_MODE_P (GET_MODE (operands[1]))
4349 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4350 "* return output_fix_trunc (insn, operands, 0);"
4351 [(set_attr "type" "fistp")
4352 (set_attr "i387_cw" "trunc")
4353 (set_attr "mode" "<MODE>")])
4355 (define_insn "fix_trunc<mode>_i387_with_temp"
4356 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
4357 (fix:X87MODEI12 (match_operand 1 "register_operand" "f,f")))
4358 (use (match_operand:HI 2 "memory_operand" "m,m"))
4359 (use (match_operand:HI 3 "memory_operand" "m,m"))
4360 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
4361 "TARGET_80387 && !TARGET_FISTTP
4362 && FLOAT_MODE_P (GET_MODE (operands[1]))
4363 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4365 [(set_attr "type" "fistp")
4366 (set_attr "i387_cw" "trunc")
4367 (set_attr "mode" "<MODE>")])
4370 [(set (match_operand:X87MODEI12 0 "register_operand" "")
4371 (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4372 (use (match_operand:HI 2 "memory_operand" ""))
4373 (use (match_operand:HI 3 "memory_operand" ""))
4374 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4376 [(parallel [(set (match_dup 4) (fix:X87MODEI12 (match_dup 1)))
4378 (use (match_dup 3))])
4379 (set (match_dup 0) (match_dup 4))]
4383 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
4384 (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4385 (use (match_operand:HI 2 "memory_operand" ""))
4386 (use (match_operand:HI 3 "memory_operand" ""))
4387 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4389 [(parallel [(set (match_dup 0) (fix:X87MODEI12 (match_dup 1)))
4391 (use (match_dup 3))])]
4394 (define_insn "x86_fnstcw_1"
4395 [(set (match_operand:HI 0 "memory_operand" "=m")
4396 (unspec:HI [(reg:HI FPSR_REG)] UNSPEC_FSTCW))]
4399 [(set_attr "length" "2")
4400 (set_attr "mode" "HI")
4401 (set_attr "unit" "i387")])
4403 (define_insn "x86_fldcw_1"
4404 [(set (reg:HI FPSR_REG)
4405 (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
4408 [(set_attr "length" "2")
4409 (set_attr "mode" "HI")
4410 (set_attr "unit" "i387")
4411 (set_attr "athlon_decode" "vector")])
4413 ;; Conversion between fixed point and floating point.
4415 ;; Even though we only accept memory inputs, the backend _really_
4416 ;; wants to be able to do this between registers.
4418 (define_expand "floathisf2"
4419 [(set (match_operand:SF 0 "register_operand" "")
4420 (float:SF (match_operand:HI 1 "nonimmediate_operand" "")))]
4421 "TARGET_80387 || TARGET_SSE_MATH"
4423 if (TARGET_SSE_MATH)
4425 emit_insn (gen_floatsisf2 (operands[0],
4426 convert_to_mode (SImode, operands[1], 0)));
4431 (define_insn "*floathisf2_i387"
4432 [(set (match_operand:SF 0 "register_operand" "=f,f")
4433 (float:SF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4434 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
4438 [(set_attr "type" "fmov,multi")
4439 (set_attr "mode" "SF")
4440 (set_attr "unit" "*,i387")
4441 (set_attr "fp_int_src" "true")])
4443 (define_expand "floatsisf2"
4444 [(set (match_operand:SF 0 "register_operand" "")
4445 (float:SF (match_operand:SI 1 "nonimmediate_operand" "")))]
4446 "TARGET_80387 || TARGET_SSE_MATH"
4449 (define_insn "*floatsisf2_mixed"
4450 [(set (match_operand:SF 0 "register_operand" "=f#x,?f#x,x#f,x#f")
4451 (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))]
4452 "TARGET_MIX_SSE_I387"
4456 cvtsi2ss\t{%1, %0|%0, %1}
4457 cvtsi2ss\t{%1, %0|%0, %1}"
4458 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4459 (set_attr "mode" "SF")
4460 (set_attr "unit" "*,i387,*,*")
4461 (set_attr "athlon_decode" "*,*,vector,double")
4462 (set_attr "fp_int_src" "true")])
4464 (define_insn "*floatsisf2_sse"
4465 [(set (match_operand:SF 0 "register_operand" "=x,x")
4466 (float:SF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))]
4468 "cvtsi2ss\t{%1, %0|%0, %1}"
4469 [(set_attr "type" "sseicvt")
4470 (set_attr "mode" "SF")
4471 (set_attr "athlon_decode" "vector,double")
4472 (set_attr "fp_int_src" "true")])
4474 (define_insn "*floatsisf2_i387"
4475 [(set (match_operand:SF 0 "register_operand" "=f,f")
4476 (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4481 [(set_attr "type" "fmov,multi")
4482 (set_attr "mode" "SF")
4483 (set_attr "unit" "*,i387")
4484 (set_attr "fp_int_src" "true")])
4486 (define_expand "floatdisf2"
4487 [(set (match_operand:SF 0 "register_operand" "")
4488 (float:SF (match_operand:DI 1 "nonimmediate_operand" "")))]
4489 "TARGET_80387 || (TARGET_64BIT && TARGET_SSE_MATH)"
4492 (define_insn "*floatdisf2_mixed"
4493 [(set (match_operand:SF 0 "register_operand" "=f#x,?f#x,x#f,x#f")
4494 (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))]
4495 "TARGET_64BIT && TARGET_MIX_SSE_I387"
4499 cvtsi2ss{q}\t{%1, %0|%0, %1}
4500 cvtsi2ss{q}\t{%1, %0|%0, %1}"
4501 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4502 (set_attr "mode" "SF")
4503 (set_attr "unit" "*,i387,*,*")
4504 (set_attr "athlon_decode" "*,*,vector,double")
4505 (set_attr "fp_int_src" "true")])
4507 (define_insn "*floatdisf2_sse"
4508 [(set (match_operand:SF 0 "register_operand" "=x,x")
4509 (float:SF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))]
4510 "TARGET_64BIT && TARGET_SSE_MATH"
4511 "cvtsi2ss{q}\t{%1, %0|%0, %1}"
4512 [(set_attr "type" "sseicvt")
4513 (set_attr "mode" "SF")
4514 (set_attr "athlon_decode" "vector,double")
4515 (set_attr "fp_int_src" "true")])
4517 (define_insn "*floatdisf2_i387"
4518 [(set (match_operand:SF 0 "register_operand" "=f,f")
4519 (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4524 [(set_attr "type" "fmov,multi")
4525 (set_attr "mode" "SF")
4526 (set_attr "unit" "*,i387")
4527 (set_attr "fp_int_src" "true")])
4529 (define_expand "floathidf2"
4530 [(set (match_operand:DF 0 "register_operand" "")
4531 (float:DF (match_operand:HI 1 "nonimmediate_operand" "")))]
4532 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4534 if (TARGET_SSE2 && TARGET_SSE_MATH)
4536 emit_insn (gen_floatsidf2 (operands[0],
4537 convert_to_mode (SImode, operands[1], 0)));
4542 (define_insn "*floathidf2_i387"
4543 [(set (match_operand:DF 0 "register_operand" "=f,f")
4544 (float:DF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4545 "TARGET_80387 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)"
4549 [(set_attr "type" "fmov,multi")
4550 (set_attr "mode" "DF")
4551 (set_attr "unit" "*,i387")
4552 (set_attr "fp_int_src" "true")])
4554 (define_expand "floatsidf2"
4555 [(set (match_operand:DF 0 "register_operand" "")
4556 (float:DF (match_operand:SI 1 "nonimmediate_operand" "")))]
4557 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4560 (define_insn "*floatsidf2_mixed"
4561 [(set (match_operand:DF 0 "register_operand" "=f#Y,?f#Y,Y#f,Y#f")
4562 (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))]
4563 "TARGET_SSE2 && TARGET_MIX_SSE_I387"
4567 cvtsi2sd\t{%1, %0|%0, %1}
4568 cvtsi2sd\t{%1, %0|%0, %1}"
4569 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4570 (set_attr "mode" "DF")
4571 (set_attr "unit" "*,i387,*,*")
4572 (set_attr "athlon_decode" "*,*,double,direct")
4573 (set_attr "fp_int_src" "true")])
4575 (define_insn "*floatsidf2_sse"
4576 [(set (match_operand:DF 0 "register_operand" "=Y,Y")
4577 (float:DF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))]
4578 "TARGET_SSE2 && TARGET_SSE_MATH"
4579 "cvtsi2sd\t{%1, %0|%0, %1}"
4580 [(set_attr "type" "sseicvt")
4581 (set_attr "mode" "DF")
4582 (set_attr "athlon_decode" "double,direct")
4583 (set_attr "fp_int_src" "true")])
4585 (define_insn "*floatsidf2_i387"
4586 [(set (match_operand:DF 0 "register_operand" "=f,f")
4587 (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4592 [(set_attr "type" "fmov,multi")
4593 (set_attr "mode" "DF")
4594 (set_attr "unit" "*,i387")
4595 (set_attr "fp_int_src" "true")])
4597 (define_expand "floatdidf2"
4598 [(set (match_operand:DF 0 "register_operand" "")
4599 (float:DF (match_operand:DI 1 "nonimmediate_operand" "")))]
4600 "TARGET_80387 || (TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH)"
4603 (define_insn "*floatdidf2_mixed"
4604 [(set (match_operand:DF 0 "register_operand" "=f#Y,?f#Y,Y#f,Y#f")
4605 (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))]
4606 "TARGET_64BIT && TARGET_SSE2 && TARGET_MIX_SSE_I387"
4610 cvtsi2sd{q}\t{%1, %0|%0, %1}
4611 cvtsi2sd{q}\t{%1, %0|%0, %1}"
4612 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4613 (set_attr "mode" "DF")
4614 (set_attr "unit" "*,i387,*,*")
4615 (set_attr "athlon_decode" "*,*,double,direct")
4616 (set_attr "fp_int_src" "true")])
4618 (define_insn "*floatdidf2_sse"
4619 [(set (match_operand:DF 0 "register_operand" "=Y,Y")
4620 (float:DF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))]
4621 "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4622 "cvtsi2sd{q}\t{%1, %0|%0, %1}"
4623 [(set_attr "type" "sseicvt")
4624 (set_attr "mode" "DF")
4625 (set_attr "athlon_decode" "double,direct")
4626 (set_attr "fp_int_src" "true")])
4628 (define_insn "*floatdidf2_i387"
4629 [(set (match_operand:DF 0 "register_operand" "=f,f")
4630 (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4635 [(set_attr "type" "fmov,multi")
4636 (set_attr "mode" "DF")
4637 (set_attr "unit" "*,i387")
4638 (set_attr "fp_int_src" "true")])
4640 (define_insn "floathixf2"
4641 [(set (match_operand:XF 0 "register_operand" "=f,f")
4642 (float:XF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4647 [(set_attr "type" "fmov,multi")
4648 (set_attr "mode" "XF")
4649 (set_attr "unit" "*,i387")
4650 (set_attr "fp_int_src" "true")])
4652 (define_insn "floatsixf2"
4653 [(set (match_operand:XF 0 "register_operand" "=f,f")
4654 (float:XF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4659 [(set_attr "type" "fmov,multi")
4660 (set_attr "mode" "XF")
4661 (set_attr "unit" "*,i387")
4662 (set_attr "fp_int_src" "true")])
4664 (define_insn "floatdixf2"
4665 [(set (match_operand:XF 0 "register_operand" "=f,f")
4666 (float:XF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4671 [(set_attr "type" "fmov,multi")
4672 (set_attr "mode" "XF")
4673 (set_attr "unit" "*,i387")
4674 (set_attr "fp_int_src" "true")])
4676 ;; %%% Kill these when reload knows how to do it.
4678 [(set (match_operand 0 "fp_register_operand" "")
4679 (float (match_operand 1 "register_operand" "")))]
4682 && FLOAT_MODE_P (GET_MODE (operands[0]))"
4685 operands[2] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
4686 operands[2] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[2]);
4687 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[2]));
4688 ix86_free_from_memory (GET_MODE (operands[1]));
4692 (define_expand "floatunssisf2"
4693 [(use (match_operand:SF 0 "register_operand" ""))
4694 (use (match_operand:SI 1 "register_operand" ""))]
4695 "!TARGET_64BIT && TARGET_SSE_MATH"
4696 "x86_emit_floatuns (operands); DONE;")
4698 (define_expand "floatunsdisf2"
4699 [(use (match_operand:SF 0 "register_operand" ""))
4700 (use (match_operand:DI 1 "register_operand" ""))]
4701 "TARGET_64BIT && TARGET_SSE_MATH"
4702 "x86_emit_floatuns (operands); DONE;")
4704 (define_expand "floatunsdidf2"
4705 [(use (match_operand:DF 0 "register_operand" ""))
4706 (use (match_operand:DI 1 "register_operand" ""))]
4707 "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4708 "x86_emit_floatuns (operands); DONE;")
4710 ;; SSE extract/set expanders
4715 ;; %%% splits for addditi3
4717 (define_expand "addti3"
4718 [(set (match_operand:TI 0 "nonimmediate_operand" "")
4719 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
4720 (match_operand:TI 2 "x86_64_general_operand" "")))
4721 (clobber (reg:CC FLAGS_REG))]
4723 "ix86_expand_binary_operator (PLUS, TImode, operands); DONE;")
4725 (define_insn "*addti3_1"
4726 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o")
4727 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0,0")
4728 (match_operand:TI 2 "general_operand" "roiF,riF")))
4729 (clobber (reg:CC FLAGS_REG))]
4730 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, TImode, operands)"
4734 [(set (match_operand:TI 0 "nonimmediate_operand" "")
4735 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
4736 (match_operand:TI 2 "general_operand" "")))
4737 (clobber (reg:CC FLAGS_REG))]
4738 "TARGET_64BIT && reload_completed"
4739 [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
4741 (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))])
4742 (parallel [(set (match_dup 3)
4743 (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
4746 (clobber (reg:CC FLAGS_REG))])]
4747 "split_ti (operands+0, 1, operands+0, operands+3);
4748 split_ti (operands+1, 1, operands+1, operands+4);
4749 split_ti (operands+2, 1, operands+2, operands+5);")
4751 ;; %%% splits for addsidi3
4752 ; [(set (match_operand:DI 0 "nonimmediate_operand" "")
4753 ; (plus:DI (match_operand:DI 1 "general_operand" "")
4754 ; (zero_extend:DI (match_operand:SI 2 "general_operand" ""))))]
4756 (define_expand "adddi3"
4757 [(set (match_operand:DI 0 "nonimmediate_operand" "")
4758 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4759 (match_operand:DI 2 "x86_64_general_operand" "")))
4760 (clobber (reg:CC FLAGS_REG))]
4762 "ix86_expand_binary_operator (PLUS, DImode, operands); DONE;")
4764 (define_insn "*adddi3_1"
4765 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
4766 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
4767 (match_operand:DI 2 "general_operand" "roiF,riF")))
4768 (clobber (reg:CC FLAGS_REG))]
4769 "!TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4773 [(set (match_operand:DI 0 "nonimmediate_operand" "")
4774 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4775 (match_operand:DI 2 "general_operand" "")))
4776 (clobber (reg:CC FLAGS_REG))]
4777 "!TARGET_64BIT && reload_completed"
4778 [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
4780 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))])
4781 (parallel [(set (match_dup 3)
4782 (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
4785 (clobber (reg:CC FLAGS_REG))])]
4786 "split_di (operands+0, 1, operands+0, operands+3);
4787 split_di (operands+1, 1, operands+1, operands+4);
4788 split_di (operands+2, 1, operands+2, operands+5);")
4790 (define_insn "adddi3_carry_rex64"
4791 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
4792 (plus:DI (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
4793 (match_operand:DI 1 "nonimmediate_operand" "%0,0"))
4794 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
4795 (clobber (reg:CC FLAGS_REG))]
4796 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4797 "adc{q}\t{%2, %0|%0, %2}"
4798 [(set_attr "type" "alu")
4799 (set_attr "pent_pair" "pu")
4800 (set_attr "mode" "DI")])
4802 (define_insn "*adddi3_cc_rex64"
4803 [(set (reg:CC FLAGS_REG)
4804 (unspec:CC [(match_operand:DI 1 "nonimmediate_operand" "%0,0")
4805 (match_operand:DI 2 "x86_64_general_operand" "re,rm")]
4807 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
4808 (plus:DI (match_dup 1) (match_dup 2)))]
4809 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4810 "add{q}\t{%2, %0|%0, %2}"
4811 [(set_attr "type" "alu")
4812 (set_attr "mode" "DI")])
4814 (define_insn "addqi3_carry"
4815 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
4816 (plus:QI (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
4817 (match_operand:QI 1 "nonimmediate_operand" "%0,0"))
4818 (match_operand:QI 2 "general_operand" "qi,qm")))
4819 (clobber (reg:CC FLAGS_REG))]
4820 "ix86_binary_operator_ok (PLUS, QImode, operands)"
4821 "adc{b}\t{%2, %0|%0, %2}"
4822 [(set_attr "type" "alu")
4823 (set_attr "pent_pair" "pu")
4824 (set_attr "mode" "QI")])
4826 (define_insn "addhi3_carry"
4827 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
4828 (plus:HI (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
4829 (match_operand:HI 1 "nonimmediate_operand" "%0,0"))
4830 (match_operand:HI 2 "general_operand" "ri,rm")))
4831 (clobber (reg:CC FLAGS_REG))]
4832 "ix86_binary_operator_ok (PLUS, HImode, operands)"
4833 "adc{w}\t{%2, %0|%0, %2}"
4834 [(set_attr "type" "alu")
4835 (set_attr "pent_pair" "pu")
4836 (set_attr "mode" "HI")])
4838 (define_insn "addsi3_carry"
4839 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
4840 (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
4841 (match_operand:SI 1 "nonimmediate_operand" "%0,0"))
4842 (match_operand:SI 2 "general_operand" "ri,rm")))
4843 (clobber (reg:CC FLAGS_REG))]
4844 "ix86_binary_operator_ok (PLUS, SImode, operands)"
4845 "adc{l}\t{%2, %0|%0, %2}"
4846 [(set_attr "type" "alu")
4847 (set_attr "pent_pair" "pu")
4848 (set_attr "mode" "SI")])
4850 (define_insn "*addsi3_carry_zext"
4851 [(set (match_operand:DI 0 "register_operand" "=r")
4853 (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
4854 (match_operand:SI 1 "nonimmediate_operand" "%0"))
4855 (match_operand:SI 2 "general_operand" "rim"))))
4856 (clobber (reg:CC FLAGS_REG))]
4857 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
4858 "adc{l}\t{%2, %k0|%k0, %2}"
4859 [(set_attr "type" "alu")
4860 (set_attr "pent_pair" "pu")
4861 (set_attr "mode" "SI")])
4863 (define_insn "*addsi3_cc"
4864 [(set (reg:CC FLAGS_REG)
4865 (unspec:CC [(match_operand:SI 1 "nonimmediate_operand" "%0,0")
4866 (match_operand:SI 2 "general_operand" "ri,rm")]
4868 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
4869 (plus:SI (match_dup 1) (match_dup 2)))]
4870 "ix86_binary_operator_ok (PLUS, SImode, operands)"
4871 "add{l}\t{%2, %0|%0, %2}"
4872 [(set_attr "type" "alu")
4873 (set_attr "mode" "SI")])
4875 (define_insn "addqi3_cc"
4876 [(set (reg:CC FLAGS_REG)
4877 (unspec:CC [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
4878 (match_operand:QI 2 "general_operand" "qi,qm")]
4880 (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
4881 (plus:QI (match_dup 1) (match_dup 2)))]
4882 "ix86_binary_operator_ok (PLUS, QImode, operands)"
4883 "add{b}\t{%2, %0|%0, %2}"
4884 [(set_attr "type" "alu")
4885 (set_attr "mode" "QI")])
4887 (define_expand "addsi3"
4888 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4889 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
4890 (match_operand:SI 2 "general_operand" "")))
4891 (clobber (reg:CC FLAGS_REG))])]
4893 "ix86_expand_binary_operator (PLUS, SImode, operands); DONE;")
4895 (define_insn "*lea_1"
4896 [(set (match_operand:SI 0 "register_operand" "=r")
4897 (match_operand:SI 1 "no_seg_address_operand" "p"))]
4899 "lea{l}\t{%a1, %0|%0, %a1}"
4900 [(set_attr "type" "lea")
4901 (set_attr "mode" "SI")])
4903 (define_insn "*lea_1_rex64"
4904 [(set (match_operand:SI 0 "register_operand" "=r")
4905 (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0))]
4907 "lea{l}\t{%a1, %0|%0, %a1}"
4908 [(set_attr "type" "lea")
4909 (set_attr "mode" "SI")])
4911 (define_insn "*lea_1_zext"
4912 [(set (match_operand:DI 0 "register_operand" "=r")
4914 (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0)))]
4916 "lea{l}\t{%a1, %k0|%k0, %a1}"
4917 [(set_attr "type" "lea")
4918 (set_attr "mode" "SI")])
4920 (define_insn "*lea_2_rex64"
4921 [(set (match_operand:DI 0 "register_operand" "=r")
4922 (match_operand:DI 1 "no_seg_address_operand" "p"))]
4924 "lea{q}\t{%a1, %0|%0, %a1}"
4925 [(set_attr "type" "lea")
4926 (set_attr "mode" "DI")])
4928 ;; The lea patterns for non-Pmodes needs to be matched by several
4929 ;; insns converted to real lea by splitters.
4931 (define_insn_and_split "*lea_general_1"
4932 [(set (match_operand 0 "register_operand" "=r")
4933 (plus (plus (match_operand 1 "index_register_operand" "l")
4934 (match_operand 2 "register_operand" "r"))
4935 (match_operand 3 "immediate_operand" "i")))]
4936 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
4937 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
4938 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
4939 && GET_MODE (operands[0]) == GET_MODE (operands[1])
4940 && GET_MODE (operands[0]) == GET_MODE (operands[2])
4941 && (GET_MODE (operands[0]) == GET_MODE (operands[3])
4942 || GET_MODE (operands[3]) == VOIDmode)"
4944 "&& reload_completed"
4948 operands[0] = gen_lowpart (SImode, operands[0]);
4949 operands[1] = gen_lowpart (Pmode, operands[1]);
4950 operands[2] = gen_lowpart (Pmode, operands[2]);
4951 operands[3] = gen_lowpart (Pmode, operands[3]);
4952 pat = gen_rtx_PLUS (Pmode, gen_rtx_PLUS (Pmode, operands[1], operands[2]),
4954 if (Pmode != SImode)
4955 pat = gen_rtx_SUBREG (SImode, pat, 0);
4956 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
4959 [(set_attr "type" "lea")
4960 (set_attr "mode" "SI")])
4962 (define_insn_and_split "*lea_general_1_zext"
4963 [(set (match_operand:DI 0 "register_operand" "=r")
4965 (plus:SI (plus:SI (match_operand:SI 1 "index_register_operand" "l")
4966 (match_operand:SI 2 "register_operand" "r"))
4967 (match_operand:SI 3 "immediate_operand" "i"))))]
4970 "&& reload_completed"
4972 (zero_extend:DI (subreg:SI (plus:DI (plus:DI (match_dup 1)
4974 (match_dup 3)) 0)))]
4976 operands[1] = gen_lowpart (Pmode, operands[1]);
4977 operands[2] = gen_lowpart (Pmode, operands[2]);
4978 operands[3] = gen_lowpart (Pmode, operands[3]);
4980 [(set_attr "type" "lea")
4981 (set_attr "mode" "SI")])
4983 (define_insn_and_split "*lea_general_2"
4984 [(set (match_operand 0 "register_operand" "=r")
4985 (plus (mult (match_operand 1 "index_register_operand" "l")
4986 (match_operand 2 "const248_operand" "i"))
4987 (match_operand 3 "nonmemory_operand" "ri")))]
4988 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
4989 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
4990 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
4991 && GET_MODE (operands[0]) == GET_MODE (operands[1])
4992 && (GET_MODE (operands[0]) == GET_MODE (operands[3])
4993 || GET_MODE (operands[3]) == VOIDmode)"
4995 "&& reload_completed"
4999 operands[0] = gen_lowpart (SImode, operands[0]);
5000 operands[1] = gen_lowpart (Pmode, operands[1]);
5001 operands[3] = gen_lowpart (Pmode, operands[3]);
5002 pat = gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], operands[2]),
5004 if (Pmode != SImode)
5005 pat = gen_rtx_SUBREG (SImode, pat, 0);
5006 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5009 [(set_attr "type" "lea")
5010 (set_attr "mode" "SI")])
5012 (define_insn_and_split "*lea_general_2_zext"
5013 [(set (match_operand:DI 0 "register_operand" "=r")
5015 (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "l")
5016 (match_operand:SI 2 "const248_operand" "n"))
5017 (match_operand:SI 3 "nonmemory_operand" "ri"))))]
5020 "&& reload_completed"
5022 (zero_extend:DI (subreg:SI (plus:DI (mult:DI (match_dup 1)
5024 (match_dup 3)) 0)))]
5026 operands[1] = gen_lowpart (Pmode, operands[1]);
5027 operands[3] = gen_lowpart (Pmode, operands[3]);
5029 [(set_attr "type" "lea")
5030 (set_attr "mode" "SI")])
5032 (define_insn_and_split "*lea_general_3"
5033 [(set (match_operand 0 "register_operand" "=r")
5034 (plus (plus (mult (match_operand 1 "index_register_operand" "l")
5035 (match_operand 2 "const248_operand" "i"))
5036 (match_operand 3 "register_operand" "r"))
5037 (match_operand 4 "immediate_operand" "i")))]
5038 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5039 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5040 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5041 && GET_MODE (operands[0]) == GET_MODE (operands[1])
5042 && GET_MODE (operands[0]) == GET_MODE (operands[3])"
5044 "&& reload_completed"
5048 operands[0] = gen_lowpart (SImode, operands[0]);
5049 operands[1] = gen_lowpart (Pmode, operands[1]);
5050 operands[3] = gen_lowpart (Pmode, operands[3]);
5051 operands[4] = gen_lowpart (Pmode, operands[4]);
5052 pat = gen_rtx_PLUS (Pmode,
5053 gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1],
5057 if (Pmode != SImode)
5058 pat = gen_rtx_SUBREG (SImode, pat, 0);
5059 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5062 [(set_attr "type" "lea")
5063 (set_attr "mode" "SI")])
5065 (define_insn_and_split "*lea_general_3_zext"
5066 [(set (match_operand:DI 0 "register_operand" "=r")
5068 (plus:SI (plus:SI (mult:SI
5069 (match_operand:SI 1 "index_register_operand" "l")
5070 (match_operand:SI 2 "const248_operand" "n"))
5071 (match_operand:SI 3 "register_operand" "r"))
5072 (match_operand:SI 4 "immediate_operand" "i"))))]
5075 "&& reload_completed"
5077 (zero_extend:DI (subreg:SI (plus:DI (plus:DI (mult:DI (match_dup 1)
5080 (match_dup 4)) 0)))]
5082 operands[1] = gen_lowpart (Pmode, operands[1]);
5083 operands[3] = gen_lowpart (Pmode, operands[3]);
5084 operands[4] = gen_lowpart (Pmode, operands[4]);
5086 [(set_attr "type" "lea")
5087 (set_attr "mode" "SI")])
5089 (define_insn "*adddi_1_rex64"
5090 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r")
5091 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,r")
5092 (match_operand:DI 2 "x86_64_general_operand" "rme,re,le")))
5093 (clobber (reg:CC FLAGS_REG))]
5094 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5096 switch (get_attr_type (insn))
5099 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5100 return "lea{q}\t{%a2, %0|%0, %a2}";
5103 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5104 if (operands[2] == const1_rtx)
5105 return "inc{q}\t%0";
5108 gcc_assert (operands[2] == constm1_rtx);
5109 return "dec{q}\t%0";
5113 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5115 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5116 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5117 if (GET_CODE (operands[2]) == CONST_INT
5118 /* Avoid overflows. */
5119 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5120 && (INTVAL (operands[2]) == 128
5121 || (INTVAL (operands[2]) < 0
5122 && INTVAL (operands[2]) != -128)))
5124 operands[2] = GEN_INT (-INTVAL (operands[2]));
5125 return "sub{q}\t{%2, %0|%0, %2}";
5127 return "add{q}\t{%2, %0|%0, %2}";
5131 (cond [(eq_attr "alternative" "2")
5132 (const_string "lea")
5133 ; Current assemblers are broken and do not allow @GOTOFF in
5134 ; ought but a memory context.
5135 (match_operand:DI 2 "pic_symbolic_operand" "")
5136 (const_string "lea")
5137 (match_operand:DI 2 "incdec_operand" "")
5138 (const_string "incdec")
5140 (const_string "alu")))
5141 (set_attr "mode" "DI")])
5143 ;; Convert lea to the lea pattern to avoid flags dependency.
5145 [(set (match_operand:DI 0 "register_operand" "")
5146 (plus:DI (match_operand:DI 1 "register_operand" "")
5147 (match_operand:DI 2 "x86_64_nonmemory_operand" "")))
5148 (clobber (reg:CC FLAGS_REG))]
5149 "TARGET_64BIT && reload_completed
5150 && true_regnum (operands[0]) != true_regnum (operands[1])"
5152 (plus:DI (match_dup 1)
5156 (define_insn "*adddi_2_rex64"
5157 [(set (reg FLAGS_REG)
5159 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5160 (match_operand:DI 2 "x86_64_general_operand" "rme,re"))
5162 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
5163 (plus:DI (match_dup 1) (match_dup 2)))]
5164 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5165 && ix86_binary_operator_ok (PLUS, DImode, operands)
5166 /* Current assemblers are broken and do not allow @GOTOFF in
5167 ought but a memory context. */
5168 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5170 switch (get_attr_type (insn))
5173 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5174 if (operands[2] == const1_rtx)
5175 return "inc{q}\t%0";
5178 gcc_assert (operands[2] == constm1_rtx);
5179 return "dec{q}\t%0";
5183 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5184 /* ???? We ought to handle there the 32bit case too
5185 - do we need new constraint? */
5186 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5187 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5188 if (GET_CODE (operands[2]) == CONST_INT
5189 /* Avoid overflows. */
5190 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5191 && (INTVAL (operands[2]) == 128
5192 || (INTVAL (operands[2]) < 0
5193 && INTVAL (operands[2]) != -128)))
5195 operands[2] = GEN_INT (-INTVAL (operands[2]));
5196 return "sub{q}\t{%2, %0|%0, %2}";
5198 return "add{q}\t{%2, %0|%0, %2}";
5202 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5203 (const_string "incdec")
5204 (const_string "alu")))
5205 (set_attr "mode" "DI")])
5207 (define_insn "*adddi_3_rex64"
5208 [(set (reg FLAGS_REG)
5209 (compare (neg:DI (match_operand:DI 2 "x86_64_general_operand" "rme"))
5210 (match_operand:DI 1 "x86_64_general_operand" "%0")))
5211 (clobber (match_scratch:DI 0 "=r"))]
5213 && ix86_match_ccmode (insn, CCZmode)
5214 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5215 /* Current assemblers are broken and do not allow @GOTOFF in
5216 ought but a memory context. */
5217 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5219 switch (get_attr_type (insn))
5222 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5223 if (operands[2] == const1_rtx)
5224 return "inc{q}\t%0";
5227 gcc_assert (operands[2] == constm1_rtx);
5228 return "dec{q}\t%0";
5232 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5233 /* ???? We ought to handle there the 32bit case too
5234 - do we need new constraint? */
5235 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5236 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5237 if (GET_CODE (operands[2]) == CONST_INT
5238 /* Avoid overflows. */
5239 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5240 && (INTVAL (operands[2]) == 128
5241 || (INTVAL (operands[2]) < 0
5242 && INTVAL (operands[2]) != -128)))
5244 operands[2] = GEN_INT (-INTVAL (operands[2]));
5245 return "sub{q}\t{%2, %0|%0, %2}";
5247 return "add{q}\t{%2, %0|%0, %2}";
5251 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5252 (const_string "incdec")
5253 (const_string "alu")))
5254 (set_attr "mode" "DI")])
5256 ; For comparisons against 1, -1 and 128, we may generate better code
5257 ; by converting cmp to add, inc or dec as done by peephole2. This pattern
5258 ; is matched then. We can't accept general immediate, because for
5259 ; case of overflows, the result is messed up.
5260 ; This pattern also don't hold of 0x8000000000000000, since the value overflows
5262 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5263 ; only for comparisons not depending on it.
5264 (define_insn "*adddi_4_rex64"
5265 [(set (reg FLAGS_REG)
5266 (compare (match_operand:DI 1 "nonimmediate_operand" "0")
5267 (match_operand:DI 2 "x86_64_immediate_operand" "e")))
5268 (clobber (match_scratch:DI 0 "=rm"))]
5270 && ix86_match_ccmode (insn, CCGCmode)"
5272 switch (get_attr_type (insn))
5275 if (operands[2] == constm1_rtx)
5276 return "inc{q}\t%0";
5279 gcc_assert (operands[2] == const1_rtx);
5280 return "dec{q}\t%0";
5284 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5285 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5286 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5287 if ((INTVAL (operands[2]) == -128
5288 || (INTVAL (operands[2]) > 0
5289 && INTVAL (operands[2]) != 128))
5290 /* Avoid overflows. */
5291 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))))
5292 return "sub{q}\t{%2, %0|%0, %2}";
5293 operands[2] = GEN_INT (-INTVAL (operands[2]));
5294 return "add{q}\t{%2, %0|%0, %2}";
5298 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5299 (const_string "incdec")
5300 (const_string "alu")))
5301 (set_attr "mode" "DI")])
5303 (define_insn "*adddi_5_rex64"
5304 [(set (reg FLAGS_REG)
5306 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5307 (match_operand:DI 2 "x86_64_general_operand" "rme"))
5309 (clobber (match_scratch:DI 0 "=r"))]
5311 && ix86_match_ccmode (insn, CCGOCmode)
5312 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5313 /* Current assemblers are broken and do not allow @GOTOFF in
5314 ought but a memory context. */
5315 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5317 switch (get_attr_type (insn))
5320 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5321 if (operands[2] == const1_rtx)
5322 return "inc{q}\t%0";
5325 gcc_assert (operands[2] == constm1_rtx);
5326 return "dec{q}\t%0";
5330 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5331 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5332 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5333 if (GET_CODE (operands[2]) == CONST_INT
5334 /* Avoid overflows. */
5335 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5336 && (INTVAL (operands[2]) == 128
5337 || (INTVAL (operands[2]) < 0
5338 && INTVAL (operands[2]) != -128)))
5340 operands[2] = GEN_INT (-INTVAL (operands[2]));
5341 return "sub{q}\t{%2, %0|%0, %2}";
5343 return "add{q}\t{%2, %0|%0, %2}";
5347 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5348 (const_string "incdec")
5349 (const_string "alu")))
5350 (set_attr "mode" "DI")])
5353 (define_insn "*addsi_1"
5354 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,rm,r")
5355 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,r")
5356 (match_operand:SI 2 "general_operand" "rmni,rni,lni")))
5357 (clobber (reg:CC FLAGS_REG))]
5358 "ix86_binary_operator_ok (PLUS, SImode, operands)"
5360 switch (get_attr_type (insn))
5363 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5364 return "lea{l}\t{%a2, %0|%0, %a2}";
5367 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5368 if (operands[2] == const1_rtx)
5369 return "inc{l}\t%0";
5372 gcc_assert (operands[2] == constm1_rtx);
5373 return "dec{l}\t%0";
5377 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5379 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5380 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5381 if (GET_CODE (operands[2]) == CONST_INT
5382 && (INTVAL (operands[2]) == 128
5383 || (INTVAL (operands[2]) < 0
5384 && INTVAL (operands[2]) != -128)))
5386 operands[2] = GEN_INT (-INTVAL (operands[2]));
5387 return "sub{l}\t{%2, %0|%0, %2}";
5389 return "add{l}\t{%2, %0|%0, %2}";
5393 (cond [(eq_attr "alternative" "2")
5394 (const_string "lea")
5395 ; Current assemblers are broken and do not allow @GOTOFF in
5396 ; ought but a memory context.
5397 (match_operand:SI 2 "pic_symbolic_operand" "")
5398 (const_string "lea")
5399 (match_operand:SI 2 "incdec_operand" "")
5400 (const_string "incdec")
5402 (const_string "alu")))
5403 (set_attr "mode" "SI")])
5405 ;; Convert lea to the lea pattern to avoid flags dependency.
5407 [(set (match_operand 0 "register_operand" "")
5408 (plus (match_operand 1 "register_operand" "")
5409 (match_operand 2 "nonmemory_operand" "")))
5410 (clobber (reg:CC FLAGS_REG))]
5412 && true_regnum (operands[0]) != true_regnum (operands[1])"
5416 /* In -fPIC mode the constructs like (const (unspec [symbol_ref]))
5417 may confuse gen_lowpart. */
5418 if (GET_MODE (operands[0]) != Pmode)
5420 operands[1] = gen_lowpart (Pmode, operands[1]);
5421 operands[2] = gen_lowpart (Pmode, operands[2]);
5423 operands[0] = gen_lowpart (SImode, operands[0]);
5424 pat = gen_rtx_PLUS (Pmode, operands[1], operands[2]);
5425 if (Pmode != SImode)
5426 pat = gen_rtx_SUBREG (SImode, pat, 0);
5427 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5431 ;; It may seem that nonimmediate operand is proper one for operand 1.
5432 ;; The addsi_1 pattern allows nonimmediate operand at that place and
5433 ;; we take care in ix86_binary_operator_ok to not allow two memory
5434 ;; operands so proper swapping will be done in reload. This allow
5435 ;; patterns constructed from addsi_1 to match.
5436 (define_insn "addsi_1_zext"
5437 [(set (match_operand:DI 0 "register_operand" "=r,r")
5439 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r")
5440 (match_operand:SI 2 "general_operand" "rmni,lni"))))
5441 (clobber (reg:CC FLAGS_REG))]
5442 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5444 switch (get_attr_type (insn))
5447 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5448 return "lea{l}\t{%a2, %k0|%k0, %a2}";
5451 if (operands[2] == const1_rtx)
5452 return "inc{l}\t%k0";
5455 gcc_assert (operands[2] == constm1_rtx);
5456 return "dec{l}\t%k0";
5460 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5461 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5462 if (GET_CODE (operands[2]) == CONST_INT
5463 && (INTVAL (operands[2]) == 128
5464 || (INTVAL (operands[2]) < 0
5465 && INTVAL (operands[2]) != -128)))
5467 operands[2] = GEN_INT (-INTVAL (operands[2]));
5468 return "sub{l}\t{%2, %k0|%k0, %2}";
5470 return "add{l}\t{%2, %k0|%k0, %2}";
5474 (cond [(eq_attr "alternative" "1")
5475 (const_string "lea")
5476 ; Current assemblers are broken and do not allow @GOTOFF in
5477 ; ought but a memory context.
5478 (match_operand:SI 2 "pic_symbolic_operand" "")
5479 (const_string "lea")
5480 (match_operand:SI 2 "incdec_operand" "")
5481 (const_string "incdec")
5483 (const_string "alu")))
5484 (set_attr "mode" "SI")])
5486 ;; Convert lea to the lea pattern to avoid flags dependency.
5488 [(set (match_operand:DI 0 "register_operand" "")
5490 (plus:SI (match_operand:SI 1 "register_operand" "")
5491 (match_operand:SI 2 "nonmemory_operand" ""))))
5492 (clobber (reg:CC FLAGS_REG))]
5493 "TARGET_64BIT && reload_completed
5494 && true_regnum (operands[0]) != true_regnum (operands[1])"
5496 (zero_extend:DI (subreg:SI (plus:DI (match_dup 1) (match_dup 2)) 0)))]
5498 operands[1] = gen_lowpart (Pmode, operands[1]);
5499 operands[2] = gen_lowpart (Pmode, operands[2]);
5502 (define_insn "*addsi_2"
5503 [(set (reg FLAGS_REG)
5505 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
5506 (match_operand:SI 2 "general_operand" "rmni,rni"))
5508 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
5509 (plus:SI (match_dup 1) (match_dup 2)))]
5510 "ix86_match_ccmode (insn, CCGOCmode)
5511 && ix86_binary_operator_ok (PLUS, SImode, operands)
5512 /* Current assemblers are broken and do not allow @GOTOFF in
5513 ought but a memory context. */
5514 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5516 switch (get_attr_type (insn))
5519 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5520 if (operands[2] == const1_rtx)
5521 return "inc{l}\t%0";
5524 gcc_assert (operands[2] == constm1_rtx);
5525 return "dec{l}\t%0";
5529 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5530 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5531 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5532 if (GET_CODE (operands[2]) == CONST_INT
5533 && (INTVAL (operands[2]) == 128
5534 || (INTVAL (operands[2]) < 0
5535 && INTVAL (operands[2]) != -128)))
5537 operands[2] = GEN_INT (-INTVAL (operands[2]));
5538 return "sub{l}\t{%2, %0|%0, %2}";
5540 return "add{l}\t{%2, %0|%0, %2}";
5544 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5545 (const_string "incdec")
5546 (const_string "alu")))
5547 (set_attr "mode" "SI")])
5549 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5550 (define_insn "*addsi_2_zext"
5551 [(set (reg FLAGS_REG)
5553 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5554 (match_operand:SI 2 "general_operand" "rmni"))
5556 (set (match_operand:DI 0 "register_operand" "=r")
5557 (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5558 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5559 && ix86_binary_operator_ok (PLUS, SImode, operands)
5560 /* Current assemblers are broken and do not allow @GOTOFF in
5561 ought but a memory context. */
5562 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5564 switch (get_attr_type (insn))
5567 if (operands[2] == const1_rtx)
5568 return "inc{l}\t%k0";
5571 gcc_assert (operands[2] == constm1_rtx);
5572 return "dec{l}\t%k0";
5576 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5577 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5578 if (GET_CODE (operands[2]) == CONST_INT
5579 && (INTVAL (operands[2]) == 128
5580 || (INTVAL (operands[2]) < 0
5581 && INTVAL (operands[2]) != -128)))
5583 operands[2] = GEN_INT (-INTVAL (operands[2]));
5584 return "sub{l}\t{%2, %k0|%k0, %2}";
5586 return "add{l}\t{%2, %k0|%k0, %2}";
5590 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5591 (const_string "incdec")
5592 (const_string "alu")))
5593 (set_attr "mode" "SI")])
5595 (define_insn "*addsi_3"
5596 [(set (reg FLAGS_REG)
5597 (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5598 (match_operand:SI 1 "nonimmediate_operand" "%0")))
5599 (clobber (match_scratch:SI 0 "=r"))]
5600 "ix86_match_ccmode (insn, CCZmode)
5601 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5602 /* Current assemblers are broken and do not allow @GOTOFF in
5603 ought but a memory context. */
5604 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5606 switch (get_attr_type (insn))
5609 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5610 if (operands[2] == const1_rtx)
5611 return "inc{l}\t%0";
5614 gcc_assert (operands[2] == constm1_rtx);
5615 return "dec{l}\t%0";
5619 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5620 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5621 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5622 if (GET_CODE (operands[2]) == CONST_INT
5623 && (INTVAL (operands[2]) == 128
5624 || (INTVAL (operands[2]) < 0
5625 && INTVAL (operands[2]) != -128)))
5627 operands[2] = GEN_INT (-INTVAL (operands[2]));
5628 return "sub{l}\t{%2, %0|%0, %2}";
5630 return "add{l}\t{%2, %0|%0, %2}";
5634 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5635 (const_string "incdec")
5636 (const_string "alu")))
5637 (set_attr "mode" "SI")])
5639 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5640 (define_insn "*addsi_3_zext"
5641 [(set (reg FLAGS_REG)
5642 (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5643 (match_operand:SI 1 "nonimmediate_operand" "%0")))
5644 (set (match_operand:DI 0 "register_operand" "=r")
5645 (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5646 "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
5647 && ix86_binary_operator_ok (PLUS, SImode, operands)
5648 /* Current assemblers are broken and do not allow @GOTOFF in
5649 ought but a memory context. */
5650 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5652 switch (get_attr_type (insn))
5655 if (operands[2] == const1_rtx)
5656 return "inc{l}\t%k0";
5659 gcc_assert (operands[2] == constm1_rtx);
5660 return "dec{l}\t%k0";
5664 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5665 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5666 if (GET_CODE (operands[2]) == CONST_INT
5667 && (INTVAL (operands[2]) == 128
5668 || (INTVAL (operands[2]) < 0
5669 && INTVAL (operands[2]) != -128)))
5671 operands[2] = GEN_INT (-INTVAL (operands[2]));
5672 return "sub{l}\t{%2, %k0|%k0, %2}";
5674 return "add{l}\t{%2, %k0|%k0, %2}";
5678 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5679 (const_string "incdec")
5680 (const_string "alu")))
5681 (set_attr "mode" "SI")])
5683 ; For comparisons against 1, -1 and 128, we may generate better code
5684 ; by converting cmp to add, inc or dec as done by peephole2. This pattern
5685 ; is matched then. We can't accept general immediate, because for
5686 ; case of overflows, the result is messed up.
5687 ; This pattern also don't hold of 0x80000000, since the value overflows
5689 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5690 ; only for comparisons not depending on it.
5691 (define_insn "*addsi_4"
5692 [(set (reg FLAGS_REG)
5693 (compare (match_operand:SI 1 "nonimmediate_operand" "0")
5694 (match_operand:SI 2 "const_int_operand" "n")))
5695 (clobber (match_scratch:SI 0 "=rm"))]
5696 "ix86_match_ccmode (insn, CCGCmode)
5697 && (INTVAL (operands[2]) & 0xffffffff) != 0x80000000"
5699 switch (get_attr_type (insn))
5702 if (operands[2] == constm1_rtx)
5703 return "inc{l}\t%0";
5706 gcc_assert (operands[2] == const1_rtx);
5707 return "dec{l}\t%0";
5711 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5712 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5713 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5714 if ((INTVAL (operands[2]) == -128
5715 || (INTVAL (operands[2]) > 0
5716 && INTVAL (operands[2]) != 128)))
5717 return "sub{l}\t{%2, %0|%0, %2}";
5718 operands[2] = GEN_INT (-INTVAL (operands[2]));
5719 return "add{l}\t{%2, %0|%0, %2}";
5723 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5724 (const_string "incdec")
5725 (const_string "alu")))
5726 (set_attr "mode" "SI")])
5728 (define_insn "*addsi_5"
5729 [(set (reg FLAGS_REG)
5731 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5732 (match_operand:SI 2 "general_operand" "rmni"))
5734 (clobber (match_scratch:SI 0 "=r"))]
5735 "ix86_match_ccmode (insn, CCGOCmode)
5736 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5737 /* Current assemblers are broken and do not allow @GOTOFF in
5738 ought but a memory context. */
5739 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5741 switch (get_attr_type (insn))
5744 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5745 if (operands[2] == const1_rtx)
5746 return "inc{l}\t%0";
5749 gcc_assert (operands[2] == constm1_rtx);
5750 return "dec{l}\t%0";
5754 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5755 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5756 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5757 if (GET_CODE (operands[2]) == CONST_INT
5758 && (INTVAL (operands[2]) == 128
5759 || (INTVAL (operands[2]) < 0
5760 && INTVAL (operands[2]) != -128)))
5762 operands[2] = GEN_INT (-INTVAL (operands[2]));
5763 return "sub{l}\t{%2, %0|%0, %2}";
5765 return "add{l}\t{%2, %0|%0, %2}";
5769 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5770 (const_string "incdec")
5771 (const_string "alu")))
5772 (set_attr "mode" "SI")])
5774 (define_expand "addhi3"
5775 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
5776 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "")
5777 (match_operand:HI 2 "general_operand" "")))
5778 (clobber (reg:CC FLAGS_REG))])]
5779 "TARGET_HIMODE_MATH"
5780 "ix86_expand_binary_operator (PLUS, HImode, operands); DONE;")
5782 ;; %%% After Dave's SUBREG_BYTE stuff goes in, re-enable incb %ah
5783 ;; type optimizations enabled by define-splits. This is not important
5784 ;; for PII, and in fact harmful because of partial register stalls.
5786 (define_insn "*addhi_1_lea"
5787 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
5788 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r")
5789 (match_operand:HI 2 "general_operand" "ri,rm,lni")))
5790 (clobber (reg:CC FLAGS_REG))]
5791 "!TARGET_PARTIAL_REG_STALL
5792 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5794 switch (get_attr_type (insn))
5799 if (operands[2] == const1_rtx)
5800 return "inc{w}\t%0";
5803 gcc_assert (operands[2] == constm1_rtx);
5804 return "dec{w}\t%0";
5808 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5809 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5810 if (GET_CODE (operands[2]) == CONST_INT
5811 && (INTVAL (operands[2]) == 128
5812 || (INTVAL (operands[2]) < 0
5813 && INTVAL (operands[2]) != -128)))
5815 operands[2] = GEN_INT (-INTVAL (operands[2]));
5816 return "sub{w}\t{%2, %0|%0, %2}";
5818 return "add{w}\t{%2, %0|%0, %2}";
5822 (if_then_else (eq_attr "alternative" "2")
5823 (const_string "lea")
5824 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5825 (const_string "incdec")
5826 (const_string "alu"))))
5827 (set_attr "mode" "HI,HI,SI")])
5829 (define_insn "*addhi_1"
5830 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
5831 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
5832 (match_operand:HI 2 "general_operand" "ri,rm")))
5833 (clobber (reg:CC FLAGS_REG))]
5834 "TARGET_PARTIAL_REG_STALL
5835 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5837 switch (get_attr_type (insn))
5840 if (operands[2] == const1_rtx)
5841 return "inc{w}\t%0";
5844 gcc_assert (operands[2] == constm1_rtx);
5845 return "dec{w}\t%0";
5849 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5850 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5851 if (GET_CODE (operands[2]) == CONST_INT
5852 && (INTVAL (operands[2]) == 128
5853 || (INTVAL (operands[2]) < 0
5854 && INTVAL (operands[2]) != -128)))
5856 operands[2] = GEN_INT (-INTVAL (operands[2]));
5857 return "sub{w}\t{%2, %0|%0, %2}";
5859 return "add{w}\t{%2, %0|%0, %2}";
5863 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5864 (const_string "incdec")
5865 (const_string "alu")))
5866 (set_attr "mode" "HI")])
5868 (define_insn "*addhi_2"
5869 [(set (reg FLAGS_REG)
5871 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
5872 (match_operand:HI 2 "general_operand" "rmni,rni"))
5874 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
5875 (plus:HI (match_dup 1) (match_dup 2)))]
5876 "ix86_match_ccmode (insn, CCGOCmode)
5877 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5879 switch (get_attr_type (insn))
5882 if (operands[2] == const1_rtx)
5883 return "inc{w}\t%0";
5886 gcc_assert (operands[2] == constm1_rtx);
5887 return "dec{w}\t%0";
5891 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5892 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5893 if (GET_CODE (operands[2]) == CONST_INT
5894 && (INTVAL (operands[2]) == 128
5895 || (INTVAL (operands[2]) < 0
5896 && INTVAL (operands[2]) != -128)))
5898 operands[2] = GEN_INT (-INTVAL (operands[2]));
5899 return "sub{w}\t{%2, %0|%0, %2}";
5901 return "add{w}\t{%2, %0|%0, %2}";
5905 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5906 (const_string "incdec")
5907 (const_string "alu")))
5908 (set_attr "mode" "HI")])
5910 (define_insn "*addhi_3"
5911 [(set (reg FLAGS_REG)
5912 (compare (neg:HI (match_operand:HI 2 "general_operand" "rmni"))
5913 (match_operand:HI 1 "nonimmediate_operand" "%0")))
5914 (clobber (match_scratch:HI 0 "=r"))]
5915 "ix86_match_ccmode (insn, CCZmode)
5916 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5918 switch (get_attr_type (insn))
5921 if (operands[2] == const1_rtx)
5922 return "inc{w}\t%0";
5925 gcc_assert (operands[2] == constm1_rtx);
5926 return "dec{w}\t%0";
5930 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5931 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5932 if (GET_CODE (operands[2]) == CONST_INT
5933 && (INTVAL (operands[2]) == 128
5934 || (INTVAL (operands[2]) < 0
5935 && INTVAL (operands[2]) != -128)))
5937 operands[2] = GEN_INT (-INTVAL (operands[2]));
5938 return "sub{w}\t{%2, %0|%0, %2}";
5940 return "add{w}\t{%2, %0|%0, %2}";
5944 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5945 (const_string "incdec")
5946 (const_string "alu")))
5947 (set_attr "mode" "HI")])
5949 ; See comments above addsi_4 for details.
5950 (define_insn "*addhi_4"
5951 [(set (reg FLAGS_REG)
5952 (compare (match_operand:HI 1 "nonimmediate_operand" "0")
5953 (match_operand:HI 2 "const_int_operand" "n")))
5954 (clobber (match_scratch:HI 0 "=rm"))]
5955 "ix86_match_ccmode (insn, CCGCmode)
5956 && (INTVAL (operands[2]) & 0xffff) != 0x8000"
5958 switch (get_attr_type (insn))
5961 if (operands[2] == constm1_rtx)
5962 return "inc{w}\t%0";
5965 gcc_assert (operands[2] == const1_rtx);
5966 return "dec{w}\t%0";
5970 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5971 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5972 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5973 if ((INTVAL (operands[2]) == -128
5974 || (INTVAL (operands[2]) > 0
5975 && INTVAL (operands[2]) != 128)))
5976 return "sub{w}\t{%2, %0|%0, %2}";
5977 operands[2] = GEN_INT (-INTVAL (operands[2]));
5978 return "add{w}\t{%2, %0|%0, %2}";
5982 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5983 (const_string "incdec")
5984 (const_string "alu")))
5985 (set_attr "mode" "SI")])
5988 (define_insn "*addhi_5"
5989 [(set (reg FLAGS_REG)
5991 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
5992 (match_operand:HI 2 "general_operand" "rmni"))
5994 (clobber (match_scratch:HI 0 "=r"))]
5995 "ix86_match_ccmode (insn, CCGOCmode)
5996 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5998 switch (get_attr_type (insn))
6001 if (operands[2] == const1_rtx)
6002 return "inc{w}\t%0";
6005 gcc_assert (operands[2] == constm1_rtx);
6006 return "dec{w}\t%0";
6010 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6011 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6012 if (GET_CODE (operands[2]) == CONST_INT
6013 && (INTVAL (operands[2]) == 128
6014 || (INTVAL (operands[2]) < 0
6015 && INTVAL (operands[2]) != -128)))
6017 operands[2] = GEN_INT (-INTVAL (operands[2]));
6018 return "sub{w}\t{%2, %0|%0, %2}";
6020 return "add{w}\t{%2, %0|%0, %2}";
6024 (if_then_else (match_operand:HI 2 "incdec_operand" "")
6025 (const_string "incdec")
6026 (const_string "alu")))
6027 (set_attr "mode" "HI")])
6029 (define_expand "addqi3"
6030 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6031 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6032 (match_operand:QI 2 "general_operand" "")))
6033 (clobber (reg:CC FLAGS_REG))])]
6034 "TARGET_QIMODE_MATH"
6035 "ix86_expand_binary_operator (PLUS, QImode, operands); DONE;")
6037 ;; %%% Potential partial reg stall on alternative 2. What to do?
6038 (define_insn "*addqi_1_lea"
6039 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r,r")
6040 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,r")
6041 (match_operand:QI 2 "general_operand" "qn,qmn,rn,ln")))
6042 (clobber (reg:CC FLAGS_REG))]
6043 "!TARGET_PARTIAL_REG_STALL
6044 && ix86_binary_operator_ok (PLUS, QImode, operands)"
6046 int widen = (which_alternative == 2);
6047 switch (get_attr_type (insn))
6052 if (operands[2] == const1_rtx)
6053 return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6056 gcc_assert (operands[2] == constm1_rtx);
6057 return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6061 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6062 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6063 if (GET_CODE (operands[2]) == CONST_INT
6064 && (INTVAL (operands[2]) == 128
6065 || (INTVAL (operands[2]) < 0
6066 && INTVAL (operands[2]) != -128)))
6068 operands[2] = GEN_INT (-INTVAL (operands[2]));
6070 return "sub{l}\t{%2, %k0|%k0, %2}";
6072 return "sub{b}\t{%2, %0|%0, %2}";
6075 return "add{l}\t{%k2, %k0|%k0, %k2}";
6077 return "add{b}\t{%2, %0|%0, %2}";
6081 (if_then_else (eq_attr "alternative" "3")
6082 (const_string "lea")
6083 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6084 (const_string "incdec")
6085 (const_string "alu"))))
6086 (set_attr "mode" "QI,QI,SI,SI")])
6088 (define_insn "*addqi_1"
6089 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
6090 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
6091 (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
6092 (clobber (reg:CC FLAGS_REG))]
6093 "TARGET_PARTIAL_REG_STALL
6094 && ix86_binary_operator_ok (PLUS, QImode, operands)"
6096 int widen = (which_alternative == 2);
6097 switch (get_attr_type (insn))
6100 if (operands[2] == const1_rtx)
6101 return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6104 gcc_assert (operands[2] == constm1_rtx);
6105 return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6109 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6110 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6111 if (GET_CODE (operands[2]) == CONST_INT
6112 && (INTVAL (operands[2]) == 128
6113 || (INTVAL (operands[2]) < 0
6114 && INTVAL (operands[2]) != -128)))
6116 operands[2] = GEN_INT (-INTVAL (operands[2]));
6118 return "sub{l}\t{%2, %k0|%k0, %2}";
6120 return "sub{b}\t{%2, %0|%0, %2}";
6123 return "add{l}\t{%k2, %k0|%k0, %k2}";
6125 return "add{b}\t{%2, %0|%0, %2}";
6129 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6130 (const_string "incdec")
6131 (const_string "alu")))
6132 (set_attr "mode" "QI,QI,SI")])
6134 (define_insn "*addqi_1_slp"
6135 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6136 (plus:QI (match_dup 0)
6137 (match_operand:QI 1 "general_operand" "qn,qnm")))
6138 (clobber (reg:CC FLAGS_REG))]
6139 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6140 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
6142 switch (get_attr_type (insn))
6145 if (operands[1] == const1_rtx)
6146 return "inc{b}\t%0";
6149 gcc_assert (operands[1] == constm1_rtx);
6150 return "dec{b}\t%0";
6154 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. */
6155 if (GET_CODE (operands[1]) == CONST_INT
6156 && INTVAL (operands[1]) < 0)
6158 operands[1] = GEN_INT (-INTVAL (operands[1]));
6159 return "sub{b}\t{%1, %0|%0, %1}";
6161 return "add{b}\t{%1, %0|%0, %1}";
6165 (if_then_else (match_operand:QI 1 "incdec_operand" "")
6166 (const_string "incdec")
6167 (const_string "alu1")))
6168 (set (attr "memory")
6169 (if_then_else (match_operand 1 "memory_operand" "")
6170 (const_string "load")
6171 (const_string "none")))
6172 (set_attr "mode" "QI")])
6174 (define_insn "*addqi_2"
6175 [(set (reg FLAGS_REG)
6177 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
6178 (match_operand:QI 2 "general_operand" "qmni,qni"))
6180 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
6181 (plus:QI (match_dup 1) (match_dup 2)))]
6182 "ix86_match_ccmode (insn, CCGOCmode)
6183 && ix86_binary_operator_ok (PLUS, QImode, operands)"
6185 switch (get_attr_type (insn))
6188 if (operands[2] == const1_rtx)
6189 return "inc{b}\t%0";
6192 gcc_assert (operands[2] == constm1_rtx
6193 || (GET_CODE (operands[2]) == CONST_INT
6194 && INTVAL (operands[2]) == 255));
6195 return "dec{b}\t%0";
6199 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
6200 if (GET_CODE (operands[2]) == CONST_INT
6201 && INTVAL (operands[2]) < 0)
6203 operands[2] = GEN_INT (-INTVAL (operands[2]));
6204 return "sub{b}\t{%2, %0|%0, %2}";
6206 return "add{b}\t{%2, %0|%0, %2}";
6210 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6211 (const_string "incdec")
6212 (const_string "alu")))
6213 (set_attr "mode" "QI")])
6215 (define_insn "*addqi_3"
6216 [(set (reg FLAGS_REG)
6217 (compare (neg:QI (match_operand:QI 2 "general_operand" "qmni"))
6218 (match_operand:QI 1 "nonimmediate_operand" "%0")))
6219 (clobber (match_scratch:QI 0 "=q"))]
6220 "ix86_match_ccmode (insn, CCZmode)
6221 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6223 switch (get_attr_type (insn))
6226 if (operands[2] == const1_rtx)
6227 return "inc{b}\t%0";
6230 gcc_assert (operands[2] == constm1_rtx
6231 || (GET_CODE (operands[2]) == CONST_INT
6232 && INTVAL (operands[2]) == 255));
6233 return "dec{b}\t%0";
6237 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
6238 if (GET_CODE (operands[2]) == CONST_INT
6239 && INTVAL (operands[2]) < 0)
6241 operands[2] = GEN_INT (-INTVAL (operands[2]));
6242 return "sub{b}\t{%2, %0|%0, %2}";
6244 return "add{b}\t{%2, %0|%0, %2}";
6248 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6249 (const_string "incdec")
6250 (const_string "alu")))
6251 (set_attr "mode" "QI")])
6253 ; See comments above addsi_4 for details.
6254 (define_insn "*addqi_4"
6255 [(set (reg FLAGS_REG)
6256 (compare (match_operand:QI 1 "nonimmediate_operand" "0")
6257 (match_operand:QI 2 "const_int_operand" "n")))
6258 (clobber (match_scratch:QI 0 "=qm"))]
6259 "ix86_match_ccmode (insn, CCGCmode)
6260 && (INTVAL (operands[2]) & 0xff) != 0x80"
6262 switch (get_attr_type (insn))
6265 if (operands[2] == constm1_rtx
6266 || (GET_CODE (operands[2]) == CONST_INT
6267 && INTVAL (operands[2]) == 255))
6268 return "inc{b}\t%0";
6271 gcc_assert (operands[2] == const1_rtx);
6272 return "dec{b}\t%0";
6276 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6277 if (INTVAL (operands[2]) < 0)
6279 operands[2] = GEN_INT (-INTVAL (operands[2]));
6280 return "add{b}\t{%2, %0|%0, %2}";
6282 return "sub{b}\t{%2, %0|%0, %2}";
6286 (if_then_else (match_operand:HI 2 "incdec_operand" "")
6287 (const_string "incdec")
6288 (const_string "alu")))
6289 (set_attr "mode" "QI")])
6292 (define_insn "*addqi_5"
6293 [(set (reg FLAGS_REG)
6295 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6296 (match_operand:QI 2 "general_operand" "qmni"))
6298 (clobber (match_scratch:QI 0 "=q"))]
6299 "ix86_match_ccmode (insn, CCGOCmode)
6300 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6302 switch (get_attr_type (insn))
6305 if (operands[2] == const1_rtx)
6306 return "inc{b}\t%0";
6309 gcc_assert (operands[2] == constm1_rtx
6310 || (GET_CODE (operands[2]) == CONST_INT
6311 && INTVAL (operands[2]) == 255));
6312 return "dec{b}\t%0";
6316 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
6317 if (GET_CODE (operands[2]) == CONST_INT
6318 && INTVAL (operands[2]) < 0)
6320 operands[2] = GEN_INT (-INTVAL (operands[2]));
6321 return "sub{b}\t{%2, %0|%0, %2}";
6323 return "add{b}\t{%2, %0|%0, %2}";
6327 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6328 (const_string "incdec")
6329 (const_string "alu")))
6330 (set_attr "mode" "QI")])
6333 (define_insn "addqi_ext_1"
6334 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6339 (match_operand 1 "ext_register_operand" "0")
6342 (match_operand:QI 2 "general_operand" "Qmn")))
6343 (clobber (reg:CC FLAGS_REG))]
6346 switch (get_attr_type (insn))
6349 if (operands[2] == const1_rtx)
6350 return "inc{b}\t%h0";
6353 gcc_assert (operands[2] == constm1_rtx
6354 || (GET_CODE (operands[2]) == CONST_INT
6355 && INTVAL (operands[2]) == 255));
6356 return "dec{b}\t%h0";
6360 return "add{b}\t{%2, %h0|%h0, %2}";
6364 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6365 (const_string "incdec")
6366 (const_string "alu")))
6367 (set_attr "mode" "QI")])
6369 (define_insn "*addqi_ext_1_rex64"
6370 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6375 (match_operand 1 "ext_register_operand" "0")
6378 (match_operand:QI 2 "nonmemory_operand" "Qn")))
6379 (clobber (reg:CC FLAGS_REG))]
6382 switch (get_attr_type (insn))
6385 if (operands[2] == const1_rtx)
6386 return "inc{b}\t%h0";
6389 gcc_assert (operands[2] == constm1_rtx
6390 || (GET_CODE (operands[2]) == CONST_INT
6391 && INTVAL (operands[2]) == 255));
6392 return "dec{b}\t%h0";
6396 return "add{b}\t{%2, %h0|%h0, %2}";
6400 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6401 (const_string "incdec")
6402 (const_string "alu")))
6403 (set_attr "mode" "QI")])
6405 (define_insn "*addqi_ext_2"
6406 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6411 (match_operand 1 "ext_register_operand" "%0")
6415 (match_operand 2 "ext_register_operand" "Q")
6418 (clobber (reg:CC FLAGS_REG))]
6420 "add{b}\t{%h2, %h0|%h0, %h2}"
6421 [(set_attr "type" "alu")
6422 (set_attr "mode" "QI")])
6424 ;; The patterns that match these are at the end of this file.
6426 (define_expand "addxf3"
6427 [(set (match_operand:XF 0 "register_operand" "")
6428 (plus:XF (match_operand:XF 1 "register_operand" "")
6429 (match_operand:XF 2 "register_operand" "")))]
6433 (define_expand "adddf3"
6434 [(set (match_operand:DF 0 "register_operand" "")
6435 (plus:DF (match_operand:DF 1 "register_operand" "")
6436 (match_operand:DF 2 "nonimmediate_operand" "")))]
6437 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
6440 (define_expand "addsf3"
6441 [(set (match_operand:SF 0 "register_operand" "")
6442 (plus:SF (match_operand:SF 1 "register_operand" "")
6443 (match_operand:SF 2 "nonimmediate_operand" "")))]
6444 "TARGET_80387 || TARGET_SSE_MATH"
6447 ;; Subtract instructions
6449 ;; %%% splits for subditi3
6451 (define_expand "subti3"
6452 [(parallel [(set (match_operand:TI 0 "nonimmediate_operand" "")
6453 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "")
6454 (match_operand:TI 2 "x86_64_general_operand" "")))
6455 (clobber (reg:CC FLAGS_REG))])]
6457 "ix86_expand_binary_operator (MINUS, TImode, operands); DONE;")
6459 (define_insn "*subti3_1"
6460 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o")
6461 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "0,0")
6462 (match_operand:TI 2 "general_operand" "roiF,riF")))
6463 (clobber (reg:CC FLAGS_REG))]
6464 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, TImode, operands)"
6468 [(set (match_operand:TI 0 "nonimmediate_operand" "")
6469 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "")
6470 (match_operand:TI 2 "general_operand" "")))
6471 (clobber (reg:CC FLAGS_REG))]
6472 "TARGET_64BIT && reload_completed"
6473 [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
6474 (set (match_dup 0) (minus:DI (match_dup 1) (match_dup 2)))])
6475 (parallel [(set (match_dup 3)
6476 (minus:DI (match_dup 4)
6477 (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
6479 (clobber (reg:CC FLAGS_REG))])]
6480 "split_ti (operands+0, 1, operands+0, operands+3);
6481 split_ti (operands+1, 1, operands+1, operands+4);
6482 split_ti (operands+2, 1, operands+2, operands+5);")
6484 ;; %%% splits for subsidi3
6486 (define_expand "subdi3"
6487 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
6488 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6489 (match_operand:DI 2 "x86_64_general_operand" "")))
6490 (clobber (reg:CC FLAGS_REG))])]
6492 "ix86_expand_binary_operator (MINUS, DImode, operands); DONE;")
6494 (define_insn "*subdi3_1"
6495 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
6496 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6497 (match_operand:DI 2 "general_operand" "roiF,riF")))
6498 (clobber (reg:CC FLAGS_REG))]
6499 "!TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6503 [(set (match_operand:DI 0 "nonimmediate_operand" "")
6504 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6505 (match_operand:DI 2 "general_operand" "")))
6506 (clobber (reg:CC FLAGS_REG))]
6507 "!TARGET_64BIT && reload_completed"
6508 [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
6509 (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 2)))])
6510 (parallel [(set (match_dup 3)
6511 (minus:SI (match_dup 4)
6512 (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
6514 (clobber (reg:CC FLAGS_REG))])]
6515 "split_di (operands+0, 1, operands+0, operands+3);
6516 split_di (operands+1, 1, operands+1, operands+4);
6517 split_di (operands+2, 1, operands+2, operands+5);")
6519 (define_insn "subdi3_carry_rex64"
6520 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6521 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6522 (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
6523 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))))
6524 (clobber (reg:CC FLAGS_REG))]
6525 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6526 "sbb{q}\t{%2, %0|%0, %2}"
6527 [(set_attr "type" "alu")
6528 (set_attr "pent_pair" "pu")
6529 (set_attr "mode" "DI")])
6531 (define_insn "*subdi_1_rex64"
6532 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6533 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6534 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6535 (clobber (reg:CC FLAGS_REG))]
6536 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6537 "sub{q}\t{%2, %0|%0, %2}"
6538 [(set_attr "type" "alu")
6539 (set_attr "mode" "DI")])
6541 (define_insn "*subdi_2_rex64"
6542 [(set (reg FLAGS_REG)
6544 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6545 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))
6547 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6548 (minus:DI (match_dup 1) (match_dup 2)))]
6549 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6550 && ix86_binary_operator_ok (MINUS, DImode, operands)"
6551 "sub{q}\t{%2, %0|%0, %2}"
6552 [(set_attr "type" "alu")
6553 (set_attr "mode" "DI")])
6555 (define_insn "*subdi_3_rex63"
6556 [(set (reg FLAGS_REG)
6557 (compare (match_operand:DI 1 "nonimmediate_operand" "0,0")
6558 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6559 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6560 (minus:DI (match_dup 1) (match_dup 2)))]
6561 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6562 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6563 "sub{q}\t{%2, %0|%0, %2}"
6564 [(set_attr "type" "alu")
6565 (set_attr "mode" "DI")])
6567 (define_insn "subqi3_carry"
6568 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6569 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6570 (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
6571 (match_operand:QI 2 "general_operand" "qi,qm"))))
6572 (clobber (reg:CC FLAGS_REG))]
6573 "ix86_binary_operator_ok (MINUS, QImode, operands)"
6574 "sbb{b}\t{%2, %0|%0, %2}"
6575 [(set_attr "type" "alu")
6576 (set_attr "pent_pair" "pu")
6577 (set_attr "mode" "QI")])
6579 (define_insn "subhi3_carry"
6580 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6581 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6582 (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
6583 (match_operand:HI 2 "general_operand" "ri,rm"))))
6584 (clobber (reg:CC FLAGS_REG))]
6585 "ix86_binary_operator_ok (MINUS, HImode, operands)"
6586 "sbb{w}\t{%2, %0|%0, %2}"
6587 [(set_attr "type" "alu")
6588 (set_attr "pent_pair" "pu")
6589 (set_attr "mode" "HI")])
6591 (define_insn "subsi3_carry"
6592 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6593 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6594 (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6595 (match_operand:SI 2 "general_operand" "ri,rm"))))
6596 (clobber (reg:CC FLAGS_REG))]
6597 "ix86_binary_operator_ok (MINUS, SImode, operands)"
6598 "sbb{l}\t{%2, %0|%0, %2}"
6599 [(set_attr "type" "alu")
6600 (set_attr "pent_pair" "pu")
6601 (set_attr "mode" "SI")])
6603 (define_insn "subsi3_carry_zext"
6604 [(set (match_operand:DI 0 "register_operand" "=rm,r")
6606 (minus:SI (match_operand:SI 1 "register_operand" "0,0")
6607 (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6608 (match_operand:SI 2 "general_operand" "ri,rm")))))
6609 (clobber (reg:CC FLAGS_REG))]
6610 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6611 "sbb{l}\t{%2, %k0|%k0, %2}"
6612 [(set_attr "type" "alu")
6613 (set_attr "pent_pair" "pu")
6614 (set_attr "mode" "SI")])
6616 (define_expand "subsi3"
6617 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
6618 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "")
6619 (match_operand:SI 2 "general_operand" "")))
6620 (clobber (reg:CC FLAGS_REG))])]
6622 "ix86_expand_binary_operator (MINUS, SImode, operands); DONE;")
6624 (define_insn "*subsi_1"
6625 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6626 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6627 (match_operand:SI 2 "general_operand" "ri,rm")))
6628 (clobber (reg:CC FLAGS_REG))]
6629 "ix86_binary_operator_ok (MINUS, SImode, operands)"
6630 "sub{l}\t{%2, %0|%0, %2}"
6631 [(set_attr "type" "alu")
6632 (set_attr "mode" "SI")])
6634 (define_insn "*subsi_1_zext"
6635 [(set (match_operand:DI 0 "register_operand" "=r")
6637 (minus:SI (match_operand:SI 1 "register_operand" "0")
6638 (match_operand:SI 2 "general_operand" "rim"))))
6639 (clobber (reg:CC FLAGS_REG))]
6640 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6641 "sub{l}\t{%2, %k0|%k0, %2}"
6642 [(set_attr "type" "alu")
6643 (set_attr "mode" "SI")])
6645 (define_insn "*subsi_2"
6646 [(set (reg FLAGS_REG)
6648 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6649 (match_operand:SI 2 "general_operand" "ri,rm"))
6651 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6652 (minus:SI (match_dup 1) (match_dup 2)))]
6653 "ix86_match_ccmode (insn, CCGOCmode)
6654 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6655 "sub{l}\t{%2, %0|%0, %2}"
6656 [(set_attr "type" "alu")
6657 (set_attr "mode" "SI")])
6659 (define_insn "*subsi_2_zext"
6660 [(set (reg FLAGS_REG)
6662 (minus:SI (match_operand:SI 1 "register_operand" "0")
6663 (match_operand:SI 2 "general_operand" "rim"))
6665 (set (match_operand:DI 0 "register_operand" "=r")
6667 (minus:SI (match_dup 1)
6669 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6670 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6671 "sub{l}\t{%2, %k0|%k0, %2}"
6672 [(set_attr "type" "alu")
6673 (set_attr "mode" "SI")])
6675 (define_insn "*subsi_3"
6676 [(set (reg FLAGS_REG)
6677 (compare (match_operand:SI 1 "nonimmediate_operand" "0,0")
6678 (match_operand:SI 2 "general_operand" "ri,rm")))
6679 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6680 (minus:SI (match_dup 1) (match_dup 2)))]
6681 "ix86_match_ccmode (insn, CCmode)
6682 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6683 "sub{l}\t{%2, %0|%0, %2}"
6684 [(set_attr "type" "alu")
6685 (set_attr "mode" "SI")])
6687 (define_insn "*subsi_3_zext"
6688 [(set (reg FLAGS_REG)
6689 (compare (match_operand:SI 1 "register_operand" "0")
6690 (match_operand:SI 2 "general_operand" "rim")))
6691 (set (match_operand:DI 0 "register_operand" "=r")
6693 (minus:SI (match_dup 1)
6695 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6696 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6697 "sub{q}\t{%2, %0|%0, %2}"
6698 [(set_attr "type" "alu")
6699 (set_attr "mode" "DI")])
6701 (define_expand "subhi3"
6702 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
6703 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "")
6704 (match_operand:HI 2 "general_operand" "")))
6705 (clobber (reg:CC FLAGS_REG))])]
6706 "TARGET_HIMODE_MATH"
6707 "ix86_expand_binary_operator (MINUS, HImode, operands); DONE;")
6709 (define_insn "*subhi_1"
6710 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6711 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6712 (match_operand:HI 2 "general_operand" "ri,rm")))
6713 (clobber (reg:CC FLAGS_REG))]
6714 "ix86_binary_operator_ok (MINUS, HImode, operands)"
6715 "sub{w}\t{%2, %0|%0, %2}"
6716 [(set_attr "type" "alu")
6717 (set_attr "mode" "HI")])
6719 (define_insn "*subhi_2"
6720 [(set (reg FLAGS_REG)
6722 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6723 (match_operand:HI 2 "general_operand" "ri,rm"))
6725 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6726 (minus:HI (match_dup 1) (match_dup 2)))]
6727 "ix86_match_ccmode (insn, CCGOCmode)
6728 && ix86_binary_operator_ok (MINUS, HImode, operands)"
6729 "sub{w}\t{%2, %0|%0, %2}"
6730 [(set_attr "type" "alu")
6731 (set_attr "mode" "HI")])
6733 (define_insn "*subhi_3"
6734 [(set (reg FLAGS_REG)
6735 (compare (match_operand:HI 1 "nonimmediate_operand" "0,0")
6736 (match_operand:HI 2 "general_operand" "ri,rm")))
6737 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6738 (minus:HI (match_dup 1) (match_dup 2)))]
6739 "ix86_match_ccmode (insn, CCmode)
6740 && ix86_binary_operator_ok (MINUS, HImode, operands)"
6741 "sub{w}\t{%2, %0|%0, %2}"
6742 [(set_attr "type" "alu")
6743 (set_attr "mode" "HI")])
6745 (define_expand "subqi3"
6746 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6747 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6748 (match_operand:QI 2 "general_operand" "")))
6749 (clobber (reg:CC FLAGS_REG))])]
6750 "TARGET_QIMODE_MATH"
6751 "ix86_expand_binary_operator (MINUS, QImode, operands); DONE;")
6753 (define_insn "*subqi_1"
6754 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6755 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6756 (match_operand:QI 2 "general_operand" "qn,qmn")))
6757 (clobber (reg:CC FLAGS_REG))]
6758 "ix86_binary_operator_ok (MINUS, QImode, operands)"
6759 "sub{b}\t{%2, %0|%0, %2}"
6760 [(set_attr "type" "alu")
6761 (set_attr "mode" "QI")])
6763 (define_insn "*subqi_1_slp"
6764 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6765 (minus:QI (match_dup 0)
6766 (match_operand:QI 1 "general_operand" "qn,qmn")))
6767 (clobber (reg:CC FLAGS_REG))]
6768 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6769 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
6770 "sub{b}\t{%1, %0|%0, %1}"
6771 [(set_attr "type" "alu1")
6772 (set_attr "mode" "QI")])
6774 (define_insn "*subqi_2"
6775 [(set (reg FLAGS_REG)
6777 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6778 (match_operand:QI 2 "general_operand" "qi,qm"))
6780 (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6781 (minus:HI (match_dup 1) (match_dup 2)))]
6782 "ix86_match_ccmode (insn, CCGOCmode)
6783 && ix86_binary_operator_ok (MINUS, QImode, operands)"
6784 "sub{b}\t{%2, %0|%0, %2}"
6785 [(set_attr "type" "alu")
6786 (set_attr "mode" "QI")])
6788 (define_insn "*subqi_3"
6789 [(set (reg FLAGS_REG)
6790 (compare (match_operand:QI 1 "nonimmediate_operand" "0,0")
6791 (match_operand:QI 2 "general_operand" "qi,qm")))
6792 (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6793 (minus:HI (match_dup 1) (match_dup 2)))]
6794 "ix86_match_ccmode (insn, CCmode)
6795 && ix86_binary_operator_ok (MINUS, QImode, operands)"
6796 "sub{b}\t{%2, %0|%0, %2}"
6797 [(set_attr "type" "alu")
6798 (set_attr "mode" "QI")])
6800 ;; The patterns that match these are at the end of this file.
6802 (define_expand "subxf3"
6803 [(set (match_operand:XF 0 "register_operand" "")
6804 (minus:XF (match_operand:XF 1 "register_operand" "")
6805 (match_operand:XF 2 "register_operand" "")))]
6809 (define_expand "subdf3"
6810 [(set (match_operand:DF 0 "register_operand" "")
6811 (minus:DF (match_operand:DF 1 "register_operand" "")
6812 (match_operand:DF 2 "nonimmediate_operand" "")))]
6813 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
6816 (define_expand "subsf3"
6817 [(set (match_operand:SF 0 "register_operand" "")
6818 (minus:SF (match_operand:SF 1 "register_operand" "")
6819 (match_operand:SF 2 "nonimmediate_operand" "")))]
6820 "TARGET_80387 || TARGET_SSE_MATH"
6823 ;; Multiply instructions
6825 (define_expand "muldi3"
6826 [(parallel [(set (match_operand:DI 0 "register_operand" "")
6827 (mult:DI (match_operand:DI 1 "register_operand" "")
6828 (match_operand:DI 2 "x86_64_general_operand" "")))
6829 (clobber (reg:CC FLAGS_REG))])]
6833 (define_insn "*muldi3_1_rex64"
6834 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6835 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%rm,rm,0")
6836 (match_operand:DI 2 "x86_64_general_operand" "K,e,mr")))
6837 (clobber (reg:CC FLAGS_REG))]
6839 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6841 imul{q}\t{%2, %1, %0|%0, %1, %2}
6842 imul{q}\t{%2, %1, %0|%0, %1, %2}
6843 imul{q}\t{%2, %0|%0, %2}"
6844 [(set_attr "type" "imul")
6845 (set_attr "prefix_0f" "0,0,1")
6846 (set (attr "athlon_decode")
6847 (cond [(eq_attr "cpu" "athlon")
6848 (const_string "vector")
6849 (eq_attr "alternative" "1")
6850 (const_string "vector")
6851 (and (eq_attr "alternative" "2")
6852 (match_operand 1 "memory_operand" ""))
6853 (const_string "vector")]
6854 (const_string "direct")))
6855 (set_attr "mode" "DI")])
6857 (define_expand "mulsi3"
6858 [(parallel [(set (match_operand:SI 0 "register_operand" "")
6859 (mult:SI (match_operand:SI 1 "register_operand" "")
6860 (match_operand:SI 2 "general_operand" "")))
6861 (clobber (reg:CC FLAGS_REG))])]
6865 (define_insn "*mulsi3_1"
6866 [(set (match_operand:SI 0 "register_operand" "=r,r,r")
6867 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6868 (match_operand:SI 2 "general_operand" "K,i,mr")))
6869 (clobber (reg:CC FLAGS_REG))]
6870 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6872 imul{l}\t{%2, %1, %0|%0, %1, %2}
6873 imul{l}\t{%2, %1, %0|%0, %1, %2}
6874 imul{l}\t{%2, %0|%0, %2}"
6875 [(set_attr "type" "imul")
6876 (set_attr "prefix_0f" "0,0,1")
6877 (set (attr "athlon_decode")
6878 (cond [(eq_attr "cpu" "athlon")
6879 (const_string "vector")
6880 (eq_attr "alternative" "1")
6881 (const_string "vector")
6882 (and (eq_attr "alternative" "2")
6883 (match_operand 1 "memory_operand" ""))
6884 (const_string "vector")]
6885 (const_string "direct")))
6886 (set_attr "mode" "SI")])
6888 (define_insn "*mulsi3_1_zext"
6889 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6891 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6892 (match_operand:SI 2 "general_operand" "K,i,mr"))))
6893 (clobber (reg:CC FLAGS_REG))]
6895 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6897 imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6898 imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6899 imul{l}\t{%2, %k0|%k0, %2}"
6900 [(set_attr "type" "imul")
6901 (set_attr "prefix_0f" "0,0,1")
6902 (set (attr "athlon_decode")
6903 (cond [(eq_attr "cpu" "athlon")
6904 (const_string "vector")
6905 (eq_attr "alternative" "1")
6906 (const_string "vector")
6907 (and (eq_attr "alternative" "2")
6908 (match_operand 1 "memory_operand" ""))
6909 (const_string "vector")]
6910 (const_string "direct")))
6911 (set_attr "mode" "SI")])
6913 (define_expand "mulhi3"
6914 [(parallel [(set (match_operand:HI 0 "register_operand" "")
6915 (mult:HI (match_operand:HI 1 "register_operand" "")
6916 (match_operand:HI 2 "general_operand" "")))
6917 (clobber (reg:CC FLAGS_REG))])]
6918 "TARGET_HIMODE_MATH"
6921 (define_insn "*mulhi3_1"
6922 [(set (match_operand:HI 0 "register_operand" "=r,r,r")
6923 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
6924 (match_operand:HI 2 "general_operand" "K,i,mr")))
6925 (clobber (reg:CC FLAGS_REG))]
6926 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6928 imul{w}\t{%2, %1, %0|%0, %1, %2}
6929 imul{w}\t{%2, %1, %0|%0, %1, %2}
6930 imul{w}\t{%2, %0|%0, %2}"
6931 [(set_attr "type" "imul")
6932 (set_attr "prefix_0f" "0,0,1")
6933 (set (attr "athlon_decode")
6934 (cond [(eq_attr "cpu" "athlon")
6935 (const_string "vector")
6936 (eq_attr "alternative" "1,2")
6937 (const_string "vector")]
6938 (const_string "direct")))
6939 (set_attr "mode" "HI")])
6941 (define_expand "mulqi3"
6942 [(parallel [(set (match_operand:QI 0 "register_operand" "")
6943 (mult:QI (match_operand:QI 1 "nonimmediate_operand" "")
6944 (match_operand:QI 2 "register_operand" "")))
6945 (clobber (reg:CC FLAGS_REG))])]
6946 "TARGET_QIMODE_MATH"
6949 (define_insn "*mulqi3_1"
6950 [(set (match_operand:QI 0 "register_operand" "=a")
6951 (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6952 (match_operand:QI 2 "nonimmediate_operand" "qm")))
6953 (clobber (reg:CC FLAGS_REG))]
6955 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6957 [(set_attr "type" "imul")
6958 (set_attr "length_immediate" "0")
6959 (set (attr "athlon_decode")
6960 (if_then_else (eq_attr "cpu" "athlon")
6961 (const_string "vector")
6962 (const_string "direct")))
6963 (set_attr "mode" "QI")])
6965 (define_expand "umulqihi3"
6966 [(parallel [(set (match_operand:HI 0 "register_operand" "")
6967 (mult:HI (zero_extend:HI
6968 (match_operand:QI 1 "nonimmediate_operand" ""))
6970 (match_operand:QI 2 "register_operand" ""))))
6971 (clobber (reg:CC FLAGS_REG))])]
6972 "TARGET_QIMODE_MATH"
6975 (define_insn "*umulqihi3_1"
6976 [(set (match_operand:HI 0 "register_operand" "=a")
6977 (mult:HI (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
6978 (zero_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6979 (clobber (reg:CC FLAGS_REG))]
6981 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6983 [(set_attr "type" "imul")
6984 (set_attr "length_immediate" "0")
6985 (set (attr "athlon_decode")
6986 (if_then_else (eq_attr "cpu" "athlon")
6987 (const_string "vector")
6988 (const_string "direct")))
6989 (set_attr "mode" "QI")])
6991 (define_expand "mulqihi3"
6992 [(parallel [(set (match_operand:HI 0 "register_operand" "")
6993 (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))
6994 (sign_extend:HI (match_operand:QI 2 "register_operand" ""))))
6995 (clobber (reg:CC FLAGS_REG))])]
6996 "TARGET_QIMODE_MATH"
6999 (define_insn "*mulqihi3_insn"
7000 [(set (match_operand:HI 0 "register_operand" "=a")
7001 (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
7002 (sign_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
7003 (clobber (reg:CC FLAGS_REG))]
7005 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7007 [(set_attr "type" "imul")
7008 (set_attr "length_immediate" "0")
7009 (set (attr "athlon_decode")
7010 (if_then_else (eq_attr "cpu" "athlon")
7011 (const_string "vector")
7012 (const_string "direct")))
7013 (set_attr "mode" "QI")])
7015 (define_expand "umulditi3"
7016 [(parallel [(set (match_operand:TI 0 "register_operand" "")
7017 (mult:TI (zero_extend:TI
7018 (match_operand:DI 1 "nonimmediate_operand" ""))
7020 (match_operand:DI 2 "register_operand" ""))))
7021 (clobber (reg:CC FLAGS_REG))])]
7025 (define_insn "*umulditi3_insn"
7026 [(set (match_operand:TI 0 "register_operand" "=A")
7027 (mult:TI (zero_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
7028 (zero_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
7029 (clobber (reg:CC FLAGS_REG))]
7031 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7033 [(set_attr "type" "imul")
7034 (set_attr "length_immediate" "0")
7035 (set (attr "athlon_decode")
7036 (if_then_else (eq_attr "cpu" "athlon")
7037 (const_string "vector")
7038 (const_string "double")))
7039 (set_attr "mode" "DI")])
7041 ;; We can't use this pattern in 64bit mode, since it results in two separate 32bit registers
7042 (define_expand "umulsidi3"
7043 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7044 (mult:DI (zero_extend:DI
7045 (match_operand:SI 1 "nonimmediate_operand" ""))
7047 (match_operand:SI 2 "register_operand" ""))))
7048 (clobber (reg:CC FLAGS_REG))])]
7052 (define_insn "*umulsidi3_insn"
7053 [(set (match_operand:DI 0 "register_operand" "=A")
7054 (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7055 (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7056 (clobber (reg:CC FLAGS_REG))]
7058 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7060 [(set_attr "type" "imul")
7061 (set_attr "length_immediate" "0")
7062 (set (attr "athlon_decode")
7063 (if_then_else (eq_attr "cpu" "athlon")
7064 (const_string "vector")
7065 (const_string "double")))
7066 (set_attr "mode" "SI")])
7068 (define_expand "mulditi3"
7069 [(parallel [(set (match_operand:TI 0 "register_operand" "")
7070 (mult:TI (sign_extend:TI
7071 (match_operand:DI 1 "nonimmediate_operand" ""))
7073 (match_operand:DI 2 "register_operand" ""))))
7074 (clobber (reg:CC FLAGS_REG))])]
7078 (define_insn "*mulditi3_insn"
7079 [(set (match_operand:TI 0 "register_operand" "=A")
7080 (mult:TI (sign_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
7081 (sign_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
7082 (clobber (reg:CC FLAGS_REG))]
7084 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7086 [(set_attr "type" "imul")
7087 (set_attr "length_immediate" "0")
7088 (set (attr "athlon_decode")
7089 (if_then_else (eq_attr "cpu" "athlon")
7090 (const_string "vector")
7091 (const_string "double")))
7092 (set_attr "mode" "DI")])
7094 (define_expand "mulsidi3"
7095 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7096 (mult:DI (sign_extend:DI
7097 (match_operand:SI 1 "nonimmediate_operand" ""))
7099 (match_operand:SI 2 "register_operand" ""))))
7100 (clobber (reg:CC FLAGS_REG))])]
7104 (define_insn "*mulsidi3_insn"
7105 [(set (match_operand:DI 0 "register_operand" "=A")
7106 (mult:DI (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7107 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7108 (clobber (reg:CC FLAGS_REG))]
7110 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7112 [(set_attr "type" "imul")
7113 (set_attr "length_immediate" "0")
7114 (set (attr "athlon_decode")
7115 (if_then_else (eq_attr "cpu" "athlon")
7116 (const_string "vector")
7117 (const_string "double")))
7118 (set_attr "mode" "SI")])
7120 (define_expand "umuldi3_highpart"
7121 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7124 (mult:TI (zero_extend:TI
7125 (match_operand:DI 1 "nonimmediate_operand" ""))
7127 (match_operand:DI 2 "register_operand" "")))
7129 (clobber (match_scratch:DI 3 ""))
7130 (clobber (reg:CC FLAGS_REG))])]
7134 (define_insn "*umuldi3_highpart_rex64"
7135 [(set (match_operand:DI 0 "register_operand" "=d")
7138 (mult:TI (zero_extend:TI
7139 (match_operand:DI 1 "nonimmediate_operand" "%a"))
7141 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7143 (clobber (match_scratch:DI 3 "=1"))
7144 (clobber (reg:CC FLAGS_REG))]
7146 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7148 [(set_attr "type" "imul")
7149 (set_attr "length_immediate" "0")
7150 (set (attr "athlon_decode")
7151 (if_then_else (eq_attr "cpu" "athlon")
7152 (const_string "vector")
7153 (const_string "double")))
7154 (set_attr "mode" "DI")])
7156 (define_expand "umulsi3_highpart"
7157 [(parallel [(set (match_operand:SI 0 "register_operand" "")
7160 (mult:DI (zero_extend:DI
7161 (match_operand:SI 1 "nonimmediate_operand" ""))
7163 (match_operand:SI 2 "register_operand" "")))
7165 (clobber (match_scratch:SI 3 ""))
7166 (clobber (reg:CC FLAGS_REG))])]
7170 (define_insn "*umulsi3_highpart_insn"
7171 [(set (match_operand:SI 0 "register_operand" "=d")
7174 (mult:DI (zero_extend:DI
7175 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7177 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7179 (clobber (match_scratch:SI 3 "=1"))
7180 (clobber (reg:CC FLAGS_REG))]
7181 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7183 [(set_attr "type" "imul")
7184 (set_attr "length_immediate" "0")
7185 (set (attr "athlon_decode")
7186 (if_then_else (eq_attr "cpu" "athlon")
7187 (const_string "vector")
7188 (const_string "double")))
7189 (set_attr "mode" "SI")])
7191 (define_insn "*umulsi3_highpart_zext"
7192 [(set (match_operand:DI 0 "register_operand" "=d")
7193 (zero_extend:DI (truncate:SI
7195 (mult:DI (zero_extend:DI
7196 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7198 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7200 (clobber (match_scratch:SI 3 "=1"))
7201 (clobber (reg:CC FLAGS_REG))]
7203 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7205 [(set_attr "type" "imul")
7206 (set_attr "length_immediate" "0")
7207 (set (attr "athlon_decode")
7208 (if_then_else (eq_attr "cpu" "athlon")
7209 (const_string "vector")
7210 (const_string "double")))
7211 (set_attr "mode" "SI")])
7213 (define_expand "smuldi3_highpart"
7214 [(parallel [(set (match_operand:DI 0 "register_operand" "=d")
7217 (mult:TI (sign_extend:TI
7218 (match_operand:DI 1 "nonimmediate_operand" ""))
7220 (match_operand:DI 2 "register_operand" "")))
7222 (clobber (match_scratch:DI 3 ""))
7223 (clobber (reg:CC FLAGS_REG))])]
7227 (define_insn "*smuldi3_highpart_rex64"
7228 [(set (match_operand:DI 0 "register_operand" "=d")
7231 (mult:TI (sign_extend:TI
7232 (match_operand:DI 1 "nonimmediate_operand" "%a"))
7234 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7236 (clobber (match_scratch:DI 3 "=1"))
7237 (clobber (reg:CC FLAGS_REG))]
7239 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7241 [(set_attr "type" "imul")
7242 (set (attr "athlon_decode")
7243 (if_then_else (eq_attr "cpu" "athlon")
7244 (const_string "vector")
7245 (const_string "double")))
7246 (set_attr "mode" "DI")])
7248 (define_expand "smulsi3_highpart"
7249 [(parallel [(set (match_operand:SI 0 "register_operand" "")
7252 (mult:DI (sign_extend:DI
7253 (match_operand:SI 1 "nonimmediate_operand" ""))
7255 (match_operand:SI 2 "register_operand" "")))
7257 (clobber (match_scratch:SI 3 ""))
7258 (clobber (reg:CC FLAGS_REG))])]
7262 (define_insn "*smulsi3_highpart_insn"
7263 [(set (match_operand:SI 0 "register_operand" "=d")
7266 (mult:DI (sign_extend:DI
7267 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7269 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7271 (clobber (match_scratch:SI 3 "=1"))
7272 (clobber (reg:CC FLAGS_REG))]
7273 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7275 [(set_attr "type" "imul")
7276 (set (attr "athlon_decode")
7277 (if_then_else (eq_attr "cpu" "athlon")
7278 (const_string "vector")
7279 (const_string "double")))
7280 (set_attr "mode" "SI")])
7282 (define_insn "*smulsi3_highpart_zext"
7283 [(set (match_operand:DI 0 "register_operand" "=d")
7284 (zero_extend:DI (truncate:SI
7286 (mult:DI (sign_extend:DI
7287 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7289 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7291 (clobber (match_scratch:SI 3 "=1"))
7292 (clobber (reg:CC FLAGS_REG))]
7294 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7296 [(set_attr "type" "imul")
7297 (set (attr "athlon_decode")
7298 (if_then_else (eq_attr "cpu" "athlon")
7299 (const_string "vector")
7300 (const_string "double")))
7301 (set_attr "mode" "SI")])
7303 ;; The patterns that match these are at the end of this file.
7305 (define_expand "mulxf3"
7306 [(set (match_operand:XF 0 "register_operand" "")
7307 (mult:XF (match_operand:XF 1 "register_operand" "")
7308 (match_operand:XF 2 "register_operand" "")))]
7312 (define_expand "muldf3"
7313 [(set (match_operand:DF 0 "register_operand" "")
7314 (mult:DF (match_operand:DF 1 "register_operand" "")
7315 (match_operand:DF 2 "nonimmediate_operand" "")))]
7316 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
7319 (define_expand "mulsf3"
7320 [(set (match_operand:SF 0 "register_operand" "")
7321 (mult:SF (match_operand:SF 1 "register_operand" "")
7322 (match_operand:SF 2 "nonimmediate_operand" "")))]
7323 "TARGET_80387 || TARGET_SSE_MATH"
7326 ;; Divide instructions
7328 (define_insn "divqi3"
7329 [(set (match_operand:QI 0 "register_operand" "=a")
7330 (div:QI (match_operand:HI 1 "register_operand" "0")
7331 (match_operand:QI 2 "nonimmediate_operand" "qm")))
7332 (clobber (reg:CC FLAGS_REG))]
7333 "TARGET_QIMODE_MATH"
7335 [(set_attr "type" "idiv")
7336 (set_attr "mode" "QI")])
7338 (define_insn "udivqi3"
7339 [(set (match_operand:QI 0 "register_operand" "=a")
7340 (udiv:QI (match_operand:HI 1 "register_operand" "0")
7341 (match_operand:QI 2 "nonimmediate_operand" "qm")))
7342 (clobber (reg:CC FLAGS_REG))]
7343 "TARGET_QIMODE_MATH"
7345 [(set_attr "type" "idiv")
7346 (set_attr "mode" "QI")])
7348 ;; The patterns that match these are at the end of this file.
7350 (define_expand "divxf3"
7351 [(set (match_operand:XF 0 "register_operand" "")
7352 (div:XF (match_operand:XF 1 "register_operand" "")
7353 (match_operand:XF 2 "register_operand" "")))]
7357 (define_expand "divdf3"
7358 [(set (match_operand:DF 0 "register_operand" "")
7359 (div:DF (match_operand:DF 1 "register_operand" "")
7360 (match_operand:DF 2 "nonimmediate_operand" "")))]
7361 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
7364 (define_expand "divsf3"
7365 [(set (match_operand:SF 0 "register_operand" "")
7366 (div:SF (match_operand:SF 1 "register_operand" "")
7367 (match_operand:SF 2 "nonimmediate_operand" "")))]
7368 "TARGET_80387 || TARGET_SSE_MATH"
7371 ;; Remainder instructions.
7373 (define_expand "divmoddi4"
7374 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7375 (div:DI (match_operand:DI 1 "register_operand" "")
7376 (match_operand:DI 2 "nonimmediate_operand" "")))
7377 (set (match_operand:DI 3 "register_operand" "")
7378 (mod:DI (match_dup 1) (match_dup 2)))
7379 (clobber (reg:CC FLAGS_REG))])]
7383 ;; Allow to come the parameter in eax or edx to avoid extra moves.
7384 ;; Penalize eax case slightly because it results in worse scheduling
7386 (define_insn "*divmoddi4_nocltd_rex64"
7387 [(set (match_operand:DI 0 "register_operand" "=&a,?a")
7388 (div:DI (match_operand:DI 2 "register_operand" "1,0")
7389 (match_operand:DI 3 "nonimmediate_operand" "rm,rm")))
7390 (set (match_operand:DI 1 "register_operand" "=&d,&d")
7391 (mod:DI (match_dup 2) (match_dup 3)))
7392 (clobber (reg:CC FLAGS_REG))]
7393 "TARGET_64BIT && !optimize_size && !TARGET_USE_CLTD"
7395 [(set_attr "type" "multi")])
7397 (define_insn "*divmoddi4_cltd_rex64"
7398 [(set (match_operand:DI 0 "register_operand" "=a")
7399 (div:DI (match_operand:DI 2 "register_operand" "a")
7400 (match_operand:DI 3 "nonimmediate_operand" "rm")))
7401 (set (match_operand:DI 1 "register_operand" "=&d")
7402 (mod:DI (match_dup 2) (match_dup 3)))
7403 (clobber (reg:CC FLAGS_REG))]
7404 "TARGET_64BIT && (optimize_size || TARGET_USE_CLTD)"
7406 [(set_attr "type" "multi")])
7408 (define_insn "*divmoddi_noext_rex64"
7409 [(set (match_operand:DI 0 "register_operand" "=a")
7410 (div:DI (match_operand:DI 1 "register_operand" "0")
7411 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7412 (set (match_operand:DI 3 "register_operand" "=d")
7413 (mod:DI (match_dup 1) (match_dup 2)))
7414 (use (match_operand:DI 4 "register_operand" "3"))
7415 (clobber (reg:CC FLAGS_REG))]
7418 [(set_attr "type" "idiv")
7419 (set_attr "mode" "DI")])
7422 [(set (match_operand:DI 0 "register_operand" "")
7423 (div:DI (match_operand:DI 1 "register_operand" "")
7424 (match_operand:DI 2 "nonimmediate_operand" "")))
7425 (set (match_operand:DI 3 "register_operand" "")
7426 (mod:DI (match_dup 1) (match_dup 2)))
7427 (clobber (reg:CC FLAGS_REG))]
7428 "TARGET_64BIT && reload_completed"
7429 [(parallel [(set (match_dup 3)
7430 (ashiftrt:DI (match_dup 4) (const_int 63)))
7431 (clobber (reg:CC FLAGS_REG))])
7432 (parallel [(set (match_dup 0)
7433 (div:DI (reg:DI 0) (match_dup 2)))
7435 (mod:DI (reg:DI 0) (match_dup 2)))
7437 (clobber (reg:CC FLAGS_REG))])]
7439 /* Avoid use of cltd in favor of a mov+shift. */
7440 if (!TARGET_USE_CLTD && !optimize_size)
7442 if (true_regnum (operands[1]))
7443 emit_move_insn (operands[0], operands[1]);
7445 emit_move_insn (operands[3], operands[1]);
7446 operands[4] = operands[3];
7450 gcc_assert (!true_regnum (operands[1]));
7451 operands[4] = operands[1];
7456 (define_expand "divmodsi4"
7457 [(parallel [(set (match_operand:SI 0 "register_operand" "")
7458 (div:SI (match_operand:SI 1 "register_operand" "")
7459 (match_operand:SI 2 "nonimmediate_operand" "")))
7460 (set (match_operand:SI 3 "register_operand" "")
7461 (mod:SI (match_dup 1) (match_dup 2)))
7462 (clobber (reg:CC FLAGS_REG))])]
7466 ;; Allow to come the parameter in eax or edx to avoid extra moves.
7467 ;; Penalize eax case slightly because it results in worse scheduling
7469 (define_insn "*divmodsi4_nocltd"
7470 [(set (match_operand:SI 0 "register_operand" "=&a,?a")
7471 (div:SI (match_operand:SI 2 "register_operand" "1,0")
7472 (match_operand:SI 3 "nonimmediate_operand" "rm,rm")))
7473 (set (match_operand:SI 1 "register_operand" "=&d,&d")
7474 (mod:SI (match_dup 2) (match_dup 3)))
7475 (clobber (reg:CC FLAGS_REG))]
7476 "!optimize_size && !TARGET_USE_CLTD"
7478 [(set_attr "type" "multi")])
7480 (define_insn "*divmodsi4_cltd"
7481 [(set (match_operand:SI 0 "register_operand" "=a")
7482 (div:SI (match_operand:SI 2 "register_operand" "a")
7483 (match_operand:SI 3 "nonimmediate_operand" "rm")))
7484 (set (match_operand:SI 1 "register_operand" "=&d")
7485 (mod:SI (match_dup 2) (match_dup 3)))
7486 (clobber (reg:CC FLAGS_REG))]
7487 "optimize_size || TARGET_USE_CLTD"
7489 [(set_attr "type" "multi")])
7491 (define_insn "*divmodsi_noext"
7492 [(set (match_operand:SI 0 "register_operand" "=a")
7493 (div:SI (match_operand:SI 1 "register_operand" "0")
7494 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7495 (set (match_operand:SI 3 "register_operand" "=d")
7496 (mod:SI (match_dup 1) (match_dup 2)))
7497 (use (match_operand:SI 4 "register_operand" "3"))
7498 (clobber (reg:CC FLAGS_REG))]
7501 [(set_attr "type" "idiv")
7502 (set_attr "mode" "SI")])
7505 [(set (match_operand:SI 0 "register_operand" "")
7506 (div:SI (match_operand:SI 1 "register_operand" "")
7507 (match_operand:SI 2 "nonimmediate_operand" "")))
7508 (set (match_operand:SI 3 "register_operand" "")
7509 (mod:SI (match_dup 1) (match_dup 2)))
7510 (clobber (reg:CC FLAGS_REG))]
7512 [(parallel [(set (match_dup 3)
7513 (ashiftrt:SI (match_dup 4) (const_int 31)))
7514 (clobber (reg:CC FLAGS_REG))])
7515 (parallel [(set (match_dup 0)
7516 (div:SI (reg:SI 0) (match_dup 2)))
7518 (mod:SI (reg:SI 0) (match_dup 2)))
7520 (clobber (reg:CC FLAGS_REG))])]
7522 /* Avoid use of cltd in favor of a mov+shift. */
7523 if (!TARGET_USE_CLTD && !optimize_size)
7525 if (true_regnum (operands[1]))
7526 emit_move_insn (operands[0], operands[1]);
7528 emit_move_insn (operands[3], operands[1]);
7529 operands[4] = operands[3];
7533 gcc_assert (!true_regnum (operands[1]));
7534 operands[4] = operands[1];
7538 (define_insn "divmodhi4"
7539 [(set (match_operand:HI 0 "register_operand" "=a")
7540 (div:HI (match_operand:HI 1 "register_operand" "0")
7541 (match_operand:HI 2 "nonimmediate_operand" "rm")))
7542 (set (match_operand:HI 3 "register_operand" "=&d")
7543 (mod:HI (match_dup 1) (match_dup 2)))
7544 (clobber (reg:CC FLAGS_REG))]
7545 "TARGET_HIMODE_MATH"
7547 [(set_attr "type" "multi")
7548 (set_attr "length_immediate" "0")
7549 (set_attr "mode" "SI")])
7551 (define_insn "udivmoddi4"
7552 [(set (match_operand:DI 0 "register_operand" "=a")
7553 (udiv:DI (match_operand:DI 1 "register_operand" "0")
7554 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7555 (set (match_operand:DI 3 "register_operand" "=&d")
7556 (umod:DI (match_dup 1) (match_dup 2)))
7557 (clobber (reg:CC FLAGS_REG))]
7559 "xor{q}\t%3, %3\;div{q}\t%2"
7560 [(set_attr "type" "multi")
7561 (set_attr "length_immediate" "0")
7562 (set_attr "mode" "DI")])
7564 (define_insn "*udivmoddi4_noext"
7565 [(set (match_operand:DI 0 "register_operand" "=a")
7566 (udiv:DI (match_operand:DI 1 "register_operand" "0")
7567 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7568 (set (match_operand:DI 3 "register_operand" "=d")
7569 (umod:DI (match_dup 1) (match_dup 2)))
7571 (clobber (reg:CC FLAGS_REG))]
7574 [(set_attr "type" "idiv")
7575 (set_attr "mode" "DI")])
7578 [(set (match_operand:DI 0 "register_operand" "")
7579 (udiv:DI (match_operand:DI 1 "register_operand" "")
7580 (match_operand:DI 2 "nonimmediate_operand" "")))
7581 (set (match_operand:DI 3 "register_operand" "")
7582 (umod:DI (match_dup 1) (match_dup 2)))
7583 (clobber (reg:CC FLAGS_REG))]
7584 "TARGET_64BIT && reload_completed"
7585 [(set (match_dup 3) (const_int 0))
7586 (parallel [(set (match_dup 0)
7587 (udiv:DI (match_dup 1) (match_dup 2)))
7589 (umod:DI (match_dup 1) (match_dup 2)))
7591 (clobber (reg:CC FLAGS_REG))])]
7594 (define_insn "udivmodsi4"
7595 [(set (match_operand:SI 0 "register_operand" "=a")
7596 (udiv:SI (match_operand:SI 1 "register_operand" "0")
7597 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7598 (set (match_operand:SI 3 "register_operand" "=&d")
7599 (umod:SI (match_dup 1) (match_dup 2)))
7600 (clobber (reg:CC FLAGS_REG))]
7602 "xor{l}\t%3, %3\;div{l}\t%2"
7603 [(set_attr "type" "multi")
7604 (set_attr "length_immediate" "0")
7605 (set_attr "mode" "SI")])
7607 (define_insn "*udivmodsi4_noext"
7608 [(set (match_operand:SI 0 "register_operand" "=a")
7609 (udiv:SI (match_operand:SI 1 "register_operand" "0")
7610 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7611 (set (match_operand:SI 3 "register_operand" "=d")
7612 (umod:SI (match_dup 1) (match_dup 2)))
7614 (clobber (reg:CC FLAGS_REG))]
7617 [(set_attr "type" "idiv")
7618 (set_attr "mode" "SI")])
7621 [(set (match_operand:SI 0 "register_operand" "")
7622 (udiv:SI (match_operand:SI 1 "register_operand" "")
7623 (match_operand:SI 2 "nonimmediate_operand" "")))
7624 (set (match_operand:SI 3 "register_operand" "")
7625 (umod:SI (match_dup 1) (match_dup 2)))
7626 (clobber (reg:CC FLAGS_REG))]
7628 [(set (match_dup 3) (const_int 0))
7629 (parallel [(set (match_dup 0)
7630 (udiv:SI (match_dup 1) (match_dup 2)))
7632 (umod:SI (match_dup 1) (match_dup 2)))
7634 (clobber (reg:CC FLAGS_REG))])]
7637 (define_expand "udivmodhi4"
7638 [(set (match_dup 4) (const_int 0))
7639 (parallel [(set (match_operand:HI 0 "register_operand" "")
7640 (udiv:HI (match_operand:HI 1 "register_operand" "")
7641 (match_operand:HI 2 "nonimmediate_operand" "")))
7642 (set (match_operand:HI 3 "register_operand" "")
7643 (umod:HI (match_dup 1) (match_dup 2)))
7645 (clobber (reg:CC FLAGS_REG))])]
7646 "TARGET_HIMODE_MATH"
7647 "operands[4] = gen_reg_rtx (HImode);")
7649 (define_insn "*udivmodhi_noext"
7650 [(set (match_operand:HI 0 "register_operand" "=a")
7651 (udiv:HI (match_operand:HI 1 "register_operand" "0")
7652 (match_operand:HI 2 "nonimmediate_operand" "rm")))
7653 (set (match_operand:HI 3 "register_operand" "=d")
7654 (umod:HI (match_dup 1) (match_dup 2)))
7655 (use (match_operand:HI 4 "register_operand" "3"))
7656 (clobber (reg:CC FLAGS_REG))]
7659 [(set_attr "type" "idiv")
7660 (set_attr "mode" "HI")])
7662 ;; We cannot use div/idiv for double division, because it causes
7663 ;; "division by zero" on the overflow and that's not what we expect
7664 ;; from truncate. Because true (non truncating) double division is
7665 ;; never generated, we can't create this insn anyway.
7668 ; [(set (match_operand:SI 0 "register_operand" "=a")
7670 ; (udiv:DI (match_operand:DI 1 "register_operand" "A")
7672 ; (match_operand:SI 2 "nonimmediate_operand" "rm")))))
7673 ; (set (match_operand:SI 3 "register_operand" "=d")
7675 ; (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
7676 ; (clobber (reg:CC FLAGS_REG))]
7678 ; "div{l}\t{%2, %0|%0, %2}"
7679 ; [(set_attr "type" "idiv")])
7681 ;;- Logical AND instructions
7683 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
7684 ;; Note that this excludes ah.
7686 (define_insn "*testdi_1_rex64"
7687 [(set (reg FLAGS_REG)
7689 (and:DI (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
7690 (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
7692 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7693 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7695 test{l}\t{%k1, %k0|%k0, %k1}
7696 test{l}\t{%k1, %k0|%k0, %k1}
7697 test{q}\t{%1, %0|%0, %1}
7698 test{q}\t{%1, %0|%0, %1}
7699 test{q}\t{%1, %0|%0, %1}"
7700 [(set_attr "type" "test")
7701 (set_attr "modrm" "0,1,0,1,1")
7702 (set_attr "mode" "SI,SI,DI,DI,DI")
7703 (set_attr "pent_pair" "uv,np,uv,np,uv")])
7705 (define_insn "testsi_1"
7706 [(set (reg FLAGS_REG)
7708 (and:SI (match_operand:SI 0 "nonimmediate_operand" "%!*a,r,rm")
7709 (match_operand:SI 1 "general_operand" "in,in,rin"))
7711 "ix86_match_ccmode (insn, CCNOmode)
7712 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7713 "test{l}\t{%1, %0|%0, %1}"
7714 [(set_attr "type" "test")
7715 (set_attr "modrm" "0,1,1")
7716 (set_attr "mode" "SI")
7717 (set_attr "pent_pair" "uv,np,uv")])
7719 (define_expand "testsi_ccno_1"
7720 [(set (reg:CCNO FLAGS_REG)
7722 (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
7723 (match_operand:SI 1 "nonmemory_operand" ""))
7728 (define_insn "*testhi_1"
7729 [(set (reg FLAGS_REG)
7730 (compare (and:HI (match_operand:HI 0 "nonimmediate_operand" "%!*a,r,rm")
7731 (match_operand:HI 1 "general_operand" "n,n,rn"))
7733 "ix86_match_ccmode (insn, CCNOmode)
7734 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7735 "test{w}\t{%1, %0|%0, %1}"
7736 [(set_attr "type" "test")
7737 (set_attr "modrm" "0,1,1")
7738 (set_attr "mode" "HI")
7739 (set_attr "pent_pair" "uv,np,uv")])
7741 (define_expand "testqi_ccz_1"
7742 [(set (reg:CCZ FLAGS_REG)
7743 (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
7744 (match_operand:QI 1 "nonmemory_operand" ""))
7749 (define_insn "*testqi_1_maybe_si"
7750 [(set (reg FLAGS_REG)
7753 (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
7754 (match_operand:QI 1 "general_operand" "n,n,qn,n"))
7756 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
7757 && ix86_match_ccmode (insn,
7758 GET_CODE (operands[1]) == CONST_INT
7759 && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
7761 if (which_alternative == 3)
7763 if (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) < 0)
7764 operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
7765 return "test{l}\t{%1, %k0|%k0, %1}";
7767 return "test{b}\t{%1, %0|%0, %1}";
7769 [(set_attr "type" "test")
7770 (set_attr "modrm" "0,1,1,1")
7771 (set_attr "mode" "QI,QI,QI,SI")
7772 (set_attr "pent_pair" "uv,np,uv,np")])
7774 (define_insn "*testqi_1"
7775 [(set (reg FLAGS_REG)
7778 (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm")
7779 (match_operand:QI 1 "general_operand" "n,n,qn"))
7781 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
7782 && ix86_match_ccmode (insn, CCNOmode)"
7783 "test{b}\t{%1, %0|%0, %1}"
7784 [(set_attr "type" "test")
7785 (set_attr "modrm" "0,1,1")
7786 (set_attr "mode" "QI")
7787 (set_attr "pent_pair" "uv,np,uv")])
7789 (define_expand "testqi_ext_ccno_0"
7790 [(set (reg:CCNO FLAGS_REG)
7794 (match_operand 0 "ext_register_operand" "")
7797 (match_operand 1 "const_int_operand" ""))
7802 (define_insn "*testqi_ext_0"
7803 [(set (reg FLAGS_REG)
7807 (match_operand 0 "ext_register_operand" "Q")
7810 (match_operand 1 "const_int_operand" "n"))
7812 "ix86_match_ccmode (insn, CCNOmode)"
7813 "test{b}\t{%1, %h0|%h0, %1}"
7814 [(set_attr "type" "test")
7815 (set_attr "mode" "QI")
7816 (set_attr "length_immediate" "1")
7817 (set_attr "pent_pair" "np")])
7819 (define_insn "*testqi_ext_1"
7820 [(set (reg FLAGS_REG)
7824 (match_operand 0 "ext_register_operand" "Q")
7828 (match_operand:QI 1 "general_operand" "Qm")))
7830 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7831 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7832 "test{b}\t{%1, %h0|%h0, %1}"
7833 [(set_attr "type" "test")
7834 (set_attr "mode" "QI")])
7836 (define_insn "*testqi_ext_1_rex64"
7837 [(set (reg FLAGS_REG)
7841 (match_operand 0 "ext_register_operand" "Q")
7845 (match_operand:QI 1 "register_operand" "Q")))
7847 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7848 "test{b}\t{%1, %h0|%h0, %1}"
7849 [(set_attr "type" "test")
7850 (set_attr "mode" "QI")])
7852 (define_insn "*testqi_ext_2"
7853 [(set (reg FLAGS_REG)
7857 (match_operand 0 "ext_register_operand" "Q")
7861 (match_operand 1 "ext_register_operand" "Q")
7865 "ix86_match_ccmode (insn, CCNOmode)"
7866 "test{b}\t{%h1, %h0|%h0, %h1}"
7867 [(set_attr "type" "test")
7868 (set_attr "mode" "QI")])
7870 ;; Combine likes to form bit extractions for some tests. Humor it.
7871 (define_insn "*testqi_ext_3"
7872 [(set (reg FLAGS_REG)
7873 (compare (zero_extract:SI
7874 (match_operand 0 "nonimmediate_operand" "rm")
7875 (match_operand:SI 1 "const_int_operand" "")
7876 (match_operand:SI 2 "const_int_operand" ""))
7878 "ix86_match_ccmode (insn, CCNOmode)
7879 && (GET_MODE (operands[0]) == SImode
7880 || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
7881 || GET_MODE (operands[0]) == HImode
7882 || GET_MODE (operands[0]) == QImode)"
7885 (define_insn "*testqi_ext_3_rex64"
7886 [(set (reg FLAGS_REG)
7887 (compare (zero_extract:DI
7888 (match_operand 0 "nonimmediate_operand" "rm")
7889 (match_operand:DI 1 "const_int_operand" "")
7890 (match_operand:DI 2 "const_int_operand" ""))
7893 && ix86_match_ccmode (insn, CCNOmode)
7894 /* The code below cannot deal with constants outside HOST_WIDE_INT. */
7895 && INTVAL (operands[1]) + INTVAL (operands[2]) < HOST_BITS_PER_WIDE_INT
7896 /* Ensure that resulting mask is zero or sign extended operand. */
7897 && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7898 || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
7899 && INTVAL (operands[1]) > 32))
7900 && (GET_MODE (operands[0]) == SImode
7901 || GET_MODE (operands[0]) == DImode
7902 || GET_MODE (operands[0]) == HImode
7903 || GET_MODE (operands[0]) == QImode)"
7907 [(set (match_operand 0 "flags_reg_operand" "")
7908 (match_operator 1 "compare_operator"
7910 (match_operand 2 "nonimmediate_operand" "")
7911 (match_operand 3 "const_int_operand" "")
7912 (match_operand 4 "const_int_operand" ""))
7914 "ix86_match_ccmode (insn, CCNOmode)"
7915 [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
7917 rtx val = operands[2];
7918 HOST_WIDE_INT len = INTVAL (operands[3]);
7919 HOST_WIDE_INT pos = INTVAL (operands[4]);
7921 enum machine_mode mode, submode;
7923 mode = GET_MODE (val);
7924 if (GET_CODE (val) == MEM)
7926 /* ??? Combine likes to put non-volatile mem extractions in QImode
7927 no matter the size of the test. So find a mode that works. */
7928 if (! MEM_VOLATILE_P (val))
7930 mode = smallest_mode_for_size (pos + len, MODE_INT);
7931 val = adjust_address (val, mode, 0);
7934 else if (GET_CODE (val) == SUBREG
7935 && (submode = GET_MODE (SUBREG_REG (val)),
7936 GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
7937 && pos + len <= GET_MODE_BITSIZE (submode))
7939 /* Narrow a paradoxical subreg to prevent partial register stalls. */
7941 val = SUBREG_REG (val);
7943 else if (mode == HImode && pos + len <= 8)
7945 /* Small HImode tests can be converted to QImode. */
7947 val = gen_lowpart (QImode, val);
7950 mask = ((HOST_WIDE_INT)1 << (pos + len)) - 1;
7951 mask &= ~(((HOST_WIDE_INT)1 << pos) - 1);
7953 operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
7956 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
7957 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
7958 ;; this is relatively important trick.
7959 ;; Do the conversion only post-reload to avoid limiting of the register class
7962 [(set (match_operand 0 "flags_reg_operand" "")
7963 (match_operator 1 "compare_operator"
7964 [(and (match_operand 2 "register_operand" "")
7965 (match_operand 3 "const_int_operand" ""))
7968 && QI_REG_P (operands[2])
7969 && GET_MODE (operands[2]) != QImode
7970 && ((ix86_match_ccmode (insn, CCZmode)
7971 && !(INTVAL (operands[3]) & ~(255 << 8)))
7972 || (ix86_match_ccmode (insn, CCNOmode)
7973 && !(INTVAL (operands[3]) & ~(127 << 8))))"
7976 [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
7979 "operands[2] = gen_lowpart (SImode, operands[2]);
7980 operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);")
7983 [(set (match_operand 0 "flags_reg_operand" "")
7984 (match_operator 1 "compare_operator"
7985 [(and (match_operand 2 "nonimmediate_operand" "")
7986 (match_operand 3 "const_int_operand" ""))
7989 && GET_MODE (operands[2]) != QImode
7990 && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
7991 && ((ix86_match_ccmode (insn, CCZmode)
7992 && !(INTVAL (operands[3]) & ~255))
7993 || (ix86_match_ccmode (insn, CCNOmode)
7994 && !(INTVAL (operands[3]) & ~127)))"
7996 (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
7998 "operands[2] = gen_lowpart (QImode, operands[2]);
7999 operands[3] = gen_lowpart (QImode, operands[3]);")
8002 ;; %%% This used to optimize known byte-wide and operations to memory,
8003 ;; and sometimes to QImode registers. If this is considered useful,
8004 ;; it should be done with splitters.
8006 (define_expand "anddi3"
8007 [(set (match_operand:DI 0 "nonimmediate_operand" "")
8008 (and:DI (match_operand:DI 1 "nonimmediate_operand" "")
8009 (match_operand:DI 2 "x86_64_szext_general_operand" "")))
8010 (clobber (reg:CC FLAGS_REG))]
8012 "ix86_expand_binary_operator (AND, DImode, operands); DONE;")
8014 (define_insn "*anddi_1_rex64"
8015 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
8016 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
8017 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
8018 (clobber (reg:CC FLAGS_REG))]
8019 "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
8021 switch (get_attr_type (insn))
8025 enum machine_mode mode;
8027 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
8028 if (INTVAL (operands[2]) == 0xff)
8032 gcc_assert (INTVAL (operands[2]) == 0xffff);
8036 operands[1] = gen_lowpart (mode, operands[1]);
8038 return "movz{bq|x}\t{%1,%0|%0, %1}";
8040 return "movz{wq|x}\t{%1,%0|%0, %1}";
8044 gcc_assert (rtx_equal_p (operands[0], operands[1]));
8045 if (get_attr_mode (insn) == MODE_SI)
8046 return "and{l}\t{%k2, %k0|%k0, %k2}";
8048 return "and{q}\t{%2, %0|%0, %2}";
8051 [(set_attr "type" "alu,alu,alu,imovx")
8052 (set_attr "length_immediate" "*,*,*,0")
8053 (set_attr "mode" "SI,DI,DI,DI")])
8055 (define_insn "*anddi_2"
8056 [(set (reg FLAGS_REG)
8057 (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
8058 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
8060 (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
8061 (and:DI (match_dup 1) (match_dup 2)))]
8062 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8063 && ix86_binary_operator_ok (AND, DImode, operands)"
8065 and{l}\t{%k2, %k0|%k0, %k2}
8066 and{q}\t{%2, %0|%0, %2}
8067 and{q}\t{%2, %0|%0, %2}"
8068 [(set_attr "type" "alu")
8069 (set_attr "mode" "SI,DI,DI")])
8071 (define_expand "andsi3"
8072 [(set (match_operand:SI 0 "nonimmediate_operand" "")
8073 (and:SI (match_operand:SI 1 "nonimmediate_operand" "")
8074 (match_operand:SI 2 "general_operand" "")))
8075 (clobber (reg:CC FLAGS_REG))]
8077 "ix86_expand_binary_operator (AND, SImode, operands); DONE;")
8079 (define_insn "*andsi_1"
8080 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
8081 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
8082 (match_operand:SI 2 "general_operand" "ri,rm,L")))
8083 (clobber (reg:CC FLAGS_REG))]
8084 "ix86_binary_operator_ok (AND, SImode, operands)"
8086 switch (get_attr_type (insn))
8090 enum machine_mode mode;
8092 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
8093 if (INTVAL (operands[2]) == 0xff)
8097 gcc_assert (INTVAL (operands[2]) == 0xffff);
8101 operands[1] = gen_lowpart (mode, operands[1]);
8103 return "movz{bl|x}\t{%1,%0|%0, %1}";
8105 return "movz{wl|x}\t{%1,%0|%0, %1}";
8109 gcc_assert (rtx_equal_p (operands[0], operands[1]));
8110 return "and{l}\t{%2, %0|%0, %2}";
8113 [(set_attr "type" "alu,alu,imovx")
8114 (set_attr "length_immediate" "*,*,0")
8115 (set_attr "mode" "SI")])
8118 [(set (match_operand 0 "register_operand" "")
8120 (const_int -65536)))
8121 (clobber (reg:CC FLAGS_REG))]
8122 "optimize_size || (TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)"
8123 [(set (strict_low_part (match_dup 1)) (const_int 0))]
8124 "operands[1] = gen_lowpart (HImode, operands[0]);")
8127 [(set (match_operand 0 "ext_register_operand" "")
8130 (clobber (reg:CC FLAGS_REG))]
8131 "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8132 [(set (strict_low_part (match_dup 1)) (const_int 0))]
8133 "operands[1] = gen_lowpart (QImode, operands[0]);")
8136 [(set (match_operand 0 "ext_register_operand" "")
8138 (const_int -65281)))
8139 (clobber (reg:CC FLAGS_REG))]
8140 "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8141 [(parallel [(set (zero_extract:SI (match_dup 0)
8145 (zero_extract:SI (match_dup 0)
8148 (zero_extract:SI (match_dup 0)
8151 (clobber (reg:CC FLAGS_REG))])]
8152 "operands[0] = gen_lowpart (SImode, operands[0]);")
8154 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8155 (define_insn "*andsi_1_zext"
8156 [(set (match_operand:DI 0 "register_operand" "=r")
8158 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8159 (match_operand:SI 2 "general_operand" "rim"))))
8160 (clobber (reg:CC FLAGS_REG))]
8161 "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
8162 "and{l}\t{%2, %k0|%k0, %2}"
8163 [(set_attr "type" "alu")
8164 (set_attr "mode" "SI")])
8166 (define_insn "*andsi_2"
8167 [(set (reg FLAGS_REG)
8168 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8169 (match_operand:SI 2 "general_operand" "rim,ri"))
8171 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8172 (and:SI (match_dup 1) (match_dup 2)))]
8173 "ix86_match_ccmode (insn, CCNOmode)
8174 && ix86_binary_operator_ok (AND, SImode, operands)"
8175 "and{l}\t{%2, %0|%0, %2}"
8176 [(set_attr "type" "alu")
8177 (set_attr "mode" "SI")])
8179 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8180 (define_insn "*andsi_2_zext"
8181 [(set (reg FLAGS_REG)
8182 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8183 (match_operand:SI 2 "general_operand" "rim"))
8185 (set (match_operand:DI 0 "register_operand" "=r")
8186 (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
8187 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8188 && ix86_binary_operator_ok (AND, SImode, operands)"
8189 "and{l}\t{%2, %k0|%k0, %2}"
8190 [(set_attr "type" "alu")
8191 (set_attr "mode" "SI")])
8193 (define_expand "andhi3"
8194 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8195 (and:HI (match_operand:HI 1 "nonimmediate_operand" "")
8196 (match_operand:HI 2 "general_operand" "")))
8197 (clobber (reg:CC FLAGS_REG))]
8198 "TARGET_HIMODE_MATH"
8199 "ix86_expand_binary_operator (AND, HImode, operands); DONE;")
8201 (define_insn "*andhi_1"
8202 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
8203 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
8204 (match_operand:HI 2 "general_operand" "ri,rm,L")))
8205 (clobber (reg:CC FLAGS_REG))]
8206 "ix86_binary_operator_ok (AND, HImode, operands)"
8208 switch (get_attr_type (insn))
8211 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
8212 gcc_assert (INTVAL (operands[2]) == 0xff);
8213 return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
8216 gcc_assert (rtx_equal_p (operands[0], operands[1]));
8218 return "and{w}\t{%2, %0|%0, %2}";
8221 [(set_attr "type" "alu,alu,imovx")
8222 (set_attr "length_immediate" "*,*,0")
8223 (set_attr "mode" "HI,HI,SI")])
8225 (define_insn "*andhi_2"
8226 [(set (reg FLAGS_REG)
8227 (compare (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8228 (match_operand:HI 2 "general_operand" "rim,ri"))
8230 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8231 (and:HI (match_dup 1) (match_dup 2)))]
8232 "ix86_match_ccmode (insn, CCNOmode)
8233 && ix86_binary_operator_ok (AND, HImode, operands)"
8234 "and{w}\t{%2, %0|%0, %2}"
8235 [(set_attr "type" "alu")
8236 (set_attr "mode" "HI")])
8238 (define_expand "andqi3"
8239 [(set (match_operand:QI 0 "nonimmediate_operand" "")
8240 (and:QI (match_operand:QI 1 "nonimmediate_operand" "")
8241 (match_operand:QI 2 "general_operand" "")))
8242 (clobber (reg:CC FLAGS_REG))]
8243 "TARGET_QIMODE_MATH"
8244 "ix86_expand_binary_operator (AND, QImode, operands); DONE;")
8246 ;; %%% Potential partial reg stall on alternative 2. What to do?
8247 (define_insn "*andqi_1"
8248 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
8249 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8250 (match_operand:QI 2 "general_operand" "qi,qmi,ri")))
8251 (clobber (reg:CC FLAGS_REG))]
8252 "ix86_binary_operator_ok (AND, QImode, operands)"
8254 and{b}\t{%2, %0|%0, %2}
8255 and{b}\t{%2, %0|%0, %2}
8256 and{l}\t{%k2, %k0|%k0, %k2}"
8257 [(set_attr "type" "alu")
8258 (set_attr "mode" "QI,QI,SI")])
8260 (define_insn "*andqi_1_slp"
8261 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
8262 (and:QI (match_dup 0)
8263 (match_operand:QI 1 "general_operand" "qi,qmi")))
8264 (clobber (reg:CC FLAGS_REG))]
8265 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8266 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8267 "and{b}\t{%1, %0|%0, %1}"
8268 [(set_attr "type" "alu1")
8269 (set_attr "mode" "QI")])
8271 (define_insn "*andqi_2_maybe_si"
8272 [(set (reg FLAGS_REG)
8274 (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8275 (match_operand:QI 2 "general_operand" "qim,qi,i"))
8277 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
8278 (and:QI (match_dup 1) (match_dup 2)))]
8279 "ix86_binary_operator_ok (AND, QImode, operands)
8280 && ix86_match_ccmode (insn,
8281 GET_CODE (operands[2]) == CONST_INT
8282 && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
8284 if (which_alternative == 2)
8286 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
8287 operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
8288 return "and{l}\t{%2, %k0|%k0, %2}";
8290 return "and{b}\t{%2, %0|%0, %2}";
8292 [(set_attr "type" "alu")
8293 (set_attr "mode" "QI,QI,SI")])
8295 (define_insn "*andqi_2"
8296 [(set (reg FLAGS_REG)
8298 (match_operand:QI 1 "nonimmediate_operand" "%0,0")
8299 (match_operand:QI 2 "general_operand" "qim,qi"))
8301 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
8302 (and:QI (match_dup 1) (match_dup 2)))]
8303 "ix86_match_ccmode (insn, CCNOmode)
8304 && ix86_binary_operator_ok (AND, QImode, operands)"
8305 "and{b}\t{%2, %0|%0, %2}"
8306 [(set_attr "type" "alu")
8307 (set_attr "mode" "QI")])
8309 (define_insn "*andqi_2_slp"
8310 [(set (reg FLAGS_REG)
8312 (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8313 (match_operand:QI 1 "nonimmediate_operand" "qmi,qi"))
8315 (set (strict_low_part (match_dup 0))
8316 (and:QI (match_dup 0) (match_dup 1)))]
8317 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8318 && ix86_match_ccmode (insn, CCNOmode)
8319 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8320 "and{b}\t{%1, %0|%0, %1}"
8321 [(set_attr "type" "alu1")
8322 (set_attr "mode" "QI")])
8324 ;; ??? A bug in recog prevents it from recognizing a const_int as an
8325 ;; operand to zero_extend in andqi_ext_1. It was checking explicitly
8326 ;; for a QImode operand, which of course failed.
8328 (define_insn "andqi_ext_0"
8329 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8334 (match_operand 1 "ext_register_operand" "0")
8337 (match_operand 2 "const_int_operand" "n")))
8338 (clobber (reg:CC FLAGS_REG))]
8340 "and{b}\t{%2, %h0|%h0, %2}"
8341 [(set_attr "type" "alu")
8342 (set_attr "length_immediate" "1")
8343 (set_attr "mode" "QI")])
8345 ;; Generated by peephole translating test to and. This shows up
8346 ;; often in fp comparisons.
8348 (define_insn "*andqi_ext_0_cc"
8349 [(set (reg FLAGS_REG)
8353 (match_operand 1 "ext_register_operand" "0")
8356 (match_operand 2 "const_int_operand" "n"))
8358 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8367 "ix86_match_ccmode (insn, CCNOmode)"
8368 "and{b}\t{%2, %h0|%h0, %2}"
8369 [(set_attr "type" "alu")
8370 (set_attr "length_immediate" "1")
8371 (set_attr "mode" "QI")])
8373 (define_insn "*andqi_ext_1"
8374 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8379 (match_operand 1 "ext_register_operand" "0")
8383 (match_operand:QI 2 "general_operand" "Qm"))))
8384 (clobber (reg:CC FLAGS_REG))]
8386 "and{b}\t{%2, %h0|%h0, %2}"
8387 [(set_attr "type" "alu")
8388 (set_attr "length_immediate" "0")
8389 (set_attr "mode" "QI")])
8391 (define_insn "*andqi_ext_1_rex64"
8392 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8397 (match_operand 1 "ext_register_operand" "0")
8401 (match_operand 2 "ext_register_operand" "Q"))))
8402 (clobber (reg:CC FLAGS_REG))]
8404 "and{b}\t{%2, %h0|%h0, %2}"
8405 [(set_attr "type" "alu")
8406 (set_attr "length_immediate" "0")
8407 (set_attr "mode" "QI")])
8409 (define_insn "*andqi_ext_2"
8410 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8415 (match_operand 1 "ext_register_operand" "%0")
8419 (match_operand 2 "ext_register_operand" "Q")
8422 (clobber (reg:CC FLAGS_REG))]
8424 "and{b}\t{%h2, %h0|%h0, %h2}"
8425 [(set_attr "type" "alu")
8426 (set_attr "length_immediate" "0")
8427 (set_attr "mode" "QI")])
8429 ;; Convert wide AND instructions with immediate operand to shorter QImode
8430 ;; equivalents when possible.
8431 ;; Don't do the splitting with memory operands, since it introduces risk
8432 ;; of memory mismatch stalls. We may want to do the splitting for optimizing
8433 ;; for size, but that can (should?) be handled by generic code instead.
8435 [(set (match_operand 0 "register_operand" "")
8436 (and (match_operand 1 "register_operand" "")
8437 (match_operand 2 "const_int_operand" "")))
8438 (clobber (reg:CC FLAGS_REG))]
8440 && QI_REG_P (operands[0])
8441 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8442 && !(~INTVAL (operands[2]) & ~(255 << 8))
8443 && GET_MODE (operands[0]) != QImode"
8444 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8445 (and:SI (zero_extract:SI (match_dup 1)
8446 (const_int 8) (const_int 8))
8448 (clobber (reg:CC FLAGS_REG))])]
8449 "operands[0] = gen_lowpart (SImode, operands[0]);
8450 operands[1] = gen_lowpart (SImode, operands[1]);
8451 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8453 ;; Since AND can be encoded with sign extended immediate, this is only
8454 ;; profitable when 7th bit is not set.
8456 [(set (match_operand 0 "register_operand" "")
8457 (and (match_operand 1 "general_operand" "")
8458 (match_operand 2 "const_int_operand" "")))
8459 (clobber (reg:CC FLAGS_REG))]
8461 && ANY_QI_REG_P (operands[0])
8462 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8463 && !(~INTVAL (operands[2]) & ~255)
8464 && !(INTVAL (operands[2]) & 128)
8465 && GET_MODE (operands[0]) != QImode"
8466 [(parallel [(set (strict_low_part (match_dup 0))
8467 (and:QI (match_dup 1)
8469 (clobber (reg:CC FLAGS_REG))])]
8470 "operands[0] = gen_lowpart (QImode, operands[0]);
8471 operands[1] = gen_lowpart (QImode, operands[1]);
8472 operands[2] = gen_lowpart (QImode, operands[2]);")
8474 ;; Logical inclusive OR instructions
8476 ;; %%% This used to optimize known byte-wide and operations to memory.
8477 ;; If this is considered useful, it should be done with splitters.
8479 (define_expand "iordi3"
8480 [(set (match_operand:DI 0 "nonimmediate_operand" "")
8481 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "")
8482 (match_operand:DI 2 "x86_64_general_operand" "")))
8483 (clobber (reg:CC FLAGS_REG))]
8485 "ix86_expand_binary_operator (IOR, DImode, operands); DONE;")
8487 (define_insn "*iordi_1_rex64"
8488 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
8489 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8490 (match_operand:DI 2 "x86_64_general_operand" "re,rme")))
8491 (clobber (reg:CC FLAGS_REG))]
8493 && ix86_binary_operator_ok (IOR, DImode, operands)"
8494 "or{q}\t{%2, %0|%0, %2}"
8495 [(set_attr "type" "alu")
8496 (set_attr "mode" "DI")])
8498 (define_insn "*iordi_2_rex64"
8499 [(set (reg FLAGS_REG)
8500 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8501 (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
8503 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
8504 (ior:DI (match_dup 1) (match_dup 2)))]
8506 && ix86_match_ccmode (insn, CCNOmode)
8507 && ix86_binary_operator_ok (IOR, DImode, operands)"
8508 "or{q}\t{%2, %0|%0, %2}"
8509 [(set_attr "type" "alu")
8510 (set_attr "mode" "DI")])
8512 (define_insn "*iordi_3_rex64"
8513 [(set (reg FLAGS_REG)
8514 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
8515 (match_operand:DI 2 "x86_64_general_operand" "rem"))
8517 (clobber (match_scratch:DI 0 "=r"))]
8519 && ix86_match_ccmode (insn, CCNOmode)
8520 && ix86_binary_operator_ok (IOR, DImode, operands)"
8521 "or{q}\t{%2, %0|%0, %2}"
8522 [(set_attr "type" "alu")
8523 (set_attr "mode" "DI")])
8526 (define_expand "iorsi3"
8527 [(set (match_operand:SI 0 "nonimmediate_operand" "")
8528 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "")
8529 (match_operand:SI 2 "general_operand" "")))
8530 (clobber (reg:CC FLAGS_REG))]
8532 "ix86_expand_binary_operator (IOR, SImode, operands); DONE;")
8534 (define_insn "*iorsi_1"
8535 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
8536 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8537 (match_operand:SI 2 "general_operand" "ri,rmi")))
8538 (clobber (reg:CC FLAGS_REG))]
8539 "ix86_binary_operator_ok (IOR, SImode, operands)"
8540 "or{l}\t{%2, %0|%0, %2}"
8541 [(set_attr "type" "alu")
8542 (set_attr "mode" "SI")])
8544 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8545 (define_insn "*iorsi_1_zext"
8546 [(set (match_operand:DI 0 "register_operand" "=rm")
8548 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8549 (match_operand:SI 2 "general_operand" "rim"))))
8550 (clobber (reg:CC FLAGS_REG))]
8551 "TARGET_64BIT && ix86_binary_operator_ok (IOR, SImode, operands)"
8552 "or{l}\t{%2, %k0|%k0, %2}"
8553 [(set_attr "type" "alu")
8554 (set_attr "mode" "SI")])
8556 (define_insn "*iorsi_1_zext_imm"
8557 [(set (match_operand:DI 0 "register_operand" "=rm")
8558 (ior:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8559 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8560 (clobber (reg:CC FLAGS_REG))]
8562 "or{l}\t{%2, %k0|%k0, %2}"
8563 [(set_attr "type" "alu")
8564 (set_attr "mode" "SI")])
8566 (define_insn "*iorsi_2"
8567 [(set (reg FLAGS_REG)
8568 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8569 (match_operand:SI 2 "general_operand" "rim,ri"))
8571 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8572 (ior:SI (match_dup 1) (match_dup 2)))]
8573 "ix86_match_ccmode (insn, CCNOmode)
8574 && ix86_binary_operator_ok (IOR, SImode, operands)"
8575 "or{l}\t{%2, %0|%0, %2}"
8576 [(set_attr "type" "alu")
8577 (set_attr "mode" "SI")])
8579 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8580 ;; ??? Special case for immediate operand is missing - it is tricky.
8581 (define_insn "*iorsi_2_zext"
8582 [(set (reg FLAGS_REG)
8583 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8584 (match_operand:SI 2 "general_operand" "rim"))
8586 (set (match_operand:DI 0 "register_operand" "=r")
8587 (zero_extend:DI (ior:SI (match_dup 1) (match_dup 2))))]
8588 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8589 && ix86_binary_operator_ok (IOR, SImode, operands)"
8590 "or{l}\t{%2, %k0|%k0, %2}"
8591 [(set_attr "type" "alu")
8592 (set_attr "mode" "SI")])
8594 (define_insn "*iorsi_2_zext_imm"
8595 [(set (reg FLAGS_REG)
8596 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8597 (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
8599 (set (match_operand:DI 0 "register_operand" "=r")
8600 (ior:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8601 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8602 && ix86_binary_operator_ok (IOR, SImode, operands)"
8603 "or{l}\t{%2, %k0|%k0, %2}"
8604 [(set_attr "type" "alu")
8605 (set_attr "mode" "SI")])
8607 (define_insn "*iorsi_3"
8608 [(set (reg FLAGS_REG)
8609 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8610 (match_operand:SI 2 "general_operand" "rim"))
8612 (clobber (match_scratch:SI 0 "=r"))]
8613 "ix86_match_ccmode (insn, CCNOmode)
8614 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8615 "or{l}\t{%2, %0|%0, %2}"
8616 [(set_attr "type" "alu")
8617 (set_attr "mode" "SI")])
8619 (define_expand "iorhi3"
8620 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8621 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "")
8622 (match_operand:HI 2 "general_operand" "")))
8623 (clobber (reg:CC FLAGS_REG))]
8624 "TARGET_HIMODE_MATH"
8625 "ix86_expand_binary_operator (IOR, HImode, operands); DONE;")
8627 (define_insn "*iorhi_1"
8628 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
8629 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8630 (match_operand:HI 2 "general_operand" "rmi,ri")))
8631 (clobber (reg:CC FLAGS_REG))]
8632 "ix86_binary_operator_ok (IOR, HImode, operands)"
8633 "or{w}\t{%2, %0|%0, %2}"
8634 [(set_attr "type" "alu")
8635 (set_attr "mode" "HI")])
8637 (define_insn "*iorhi_2"
8638 [(set (reg FLAGS_REG)
8639 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8640 (match_operand:HI 2 "general_operand" "rim,ri"))
8642 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8643 (ior:HI (match_dup 1) (match_dup 2)))]
8644 "ix86_match_ccmode (insn, CCNOmode)
8645 && ix86_binary_operator_ok (IOR, HImode, operands)"
8646 "or{w}\t{%2, %0|%0, %2}"
8647 [(set_attr "type" "alu")
8648 (set_attr "mode" "HI")])
8650 (define_insn "*iorhi_3"
8651 [(set (reg FLAGS_REG)
8652 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
8653 (match_operand:HI 2 "general_operand" "rim"))
8655 (clobber (match_scratch:HI 0 "=r"))]
8656 "ix86_match_ccmode (insn, CCNOmode)
8657 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8658 "or{w}\t{%2, %0|%0, %2}"
8659 [(set_attr "type" "alu")
8660 (set_attr "mode" "HI")])
8662 (define_expand "iorqi3"
8663 [(set (match_operand:QI 0 "nonimmediate_operand" "")
8664 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "")
8665 (match_operand:QI 2 "general_operand" "")))
8666 (clobber (reg:CC FLAGS_REG))]
8667 "TARGET_QIMODE_MATH"
8668 "ix86_expand_binary_operator (IOR, QImode, operands); DONE;")
8670 ;; %%% Potential partial reg stall on alternative 2. What to do?
8671 (define_insn "*iorqi_1"
8672 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
8673 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8674 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
8675 (clobber (reg:CC FLAGS_REG))]
8676 "ix86_binary_operator_ok (IOR, QImode, operands)"
8678 or{b}\t{%2, %0|%0, %2}
8679 or{b}\t{%2, %0|%0, %2}
8680 or{l}\t{%k2, %k0|%k0, %k2}"
8681 [(set_attr "type" "alu")
8682 (set_attr "mode" "QI,QI,SI")])
8684 (define_insn "*iorqi_1_slp"
8685 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
8686 (ior:QI (match_dup 0)
8687 (match_operand:QI 1 "general_operand" "qmi,qi")))
8688 (clobber (reg:CC FLAGS_REG))]
8689 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8690 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8691 "or{b}\t{%1, %0|%0, %1}"
8692 [(set_attr "type" "alu1")
8693 (set_attr "mode" "QI")])
8695 (define_insn "*iorqi_2"
8696 [(set (reg FLAGS_REG)
8697 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
8698 (match_operand:QI 2 "general_operand" "qim,qi"))
8700 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
8701 (ior:QI (match_dup 1) (match_dup 2)))]
8702 "ix86_match_ccmode (insn, CCNOmode)
8703 && ix86_binary_operator_ok (IOR, QImode, operands)"
8704 "or{b}\t{%2, %0|%0, %2}"
8705 [(set_attr "type" "alu")
8706 (set_attr "mode" "QI")])
8708 (define_insn "*iorqi_2_slp"
8709 [(set (reg FLAGS_REG)
8710 (compare (ior:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8711 (match_operand:QI 1 "general_operand" "qim,qi"))
8713 (set (strict_low_part (match_dup 0))
8714 (ior:QI (match_dup 0) (match_dup 1)))]
8715 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8716 && ix86_match_ccmode (insn, CCNOmode)
8717 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8718 "or{b}\t{%1, %0|%0, %1}"
8719 [(set_attr "type" "alu1")
8720 (set_attr "mode" "QI")])
8722 (define_insn "*iorqi_3"
8723 [(set (reg FLAGS_REG)
8724 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
8725 (match_operand:QI 2 "general_operand" "qim"))
8727 (clobber (match_scratch:QI 0 "=q"))]
8728 "ix86_match_ccmode (insn, CCNOmode)
8729 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8730 "or{b}\t{%2, %0|%0, %2}"
8731 [(set_attr "type" "alu")
8732 (set_attr "mode" "QI")])
8734 (define_insn "iorqi_ext_0"
8735 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8740 (match_operand 1 "ext_register_operand" "0")
8743 (match_operand 2 "const_int_operand" "n")))
8744 (clobber (reg:CC FLAGS_REG))]
8745 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8746 "or{b}\t{%2, %h0|%h0, %2}"
8747 [(set_attr "type" "alu")
8748 (set_attr "length_immediate" "1")
8749 (set_attr "mode" "QI")])
8751 (define_insn "*iorqi_ext_1"
8752 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8757 (match_operand 1 "ext_register_operand" "0")
8761 (match_operand:QI 2 "general_operand" "Qm"))))
8762 (clobber (reg:CC FLAGS_REG))]
8764 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
8765 "or{b}\t{%2, %h0|%h0, %2}"
8766 [(set_attr "type" "alu")
8767 (set_attr "length_immediate" "0")
8768 (set_attr "mode" "QI")])
8770 (define_insn "*iorqi_ext_1_rex64"
8771 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8776 (match_operand 1 "ext_register_operand" "0")
8780 (match_operand 2 "ext_register_operand" "Q"))))
8781 (clobber (reg:CC FLAGS_REG))]
8783 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
8784 "or{b}\t{%2, %h0|%h0, %2}"
8785 [(set_attr "type" "alu")
8786 (set_attr "length_immediate" "0")
8787 (set_attr "mode" "QI")])
8789 (define_insn "*iorqi_ext_2"
8790 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8794 (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
8797 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
8800 (clobber (reg:CC FLAGS_REG))]
8801 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8802 "ior{b}\t{%h2, %h0|%h0, %h2}"
8803 [(set_attr "type" "alu")
8804 (set_attr "length_immediate" "0")
8805 (set_attr "mode" "QI")])
8808 [(set (match_operand 0 "register_operand" "")
8809 (ior (match_operand 1 "register_operand" "")
8810 (match_operand 2 "const_int_operand" "")))
8811 (clobber (reg:CC FLAGS_REG))]
8813 && QI_REG_P (operands[0])
8814 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8815 && !(INTVAL (operands[2]) & ~(255 << 8))
8816 && GET_MODE (operands[0]) != QImode"
8817 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8818 (ior:SI (zero_extract:SI (match_dup 1)
8819 (const_int 8) (const_int 8))
8821 (clobber (reg:CC FLAGS_REG))])]
8822 "operands[0] = gen_lowpart (SImode, operands[0]);
8823 operands[1] = gen_lowpart (SImode, operands[1]);
8824 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8826 ;; Since OR can be encoded with sign extended immediate, this is only
8827 ;; profitable when 7th bit is set.
8829 [(set (match_operand 0 "register_operand" "")
8830 (ior (match_operand 1 "general_operand" "")
8831 (match_operand 2 "const_int_operand" "")))
8832 (clobber (reg:CC FLAGS_REG))]
8834 && ANY_QI_REG_P (operands[0])
8835 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8836 && !(INTVAL (operands[2]) & ~255)
8837 && (INTVAL (operands[2]) & 128)
8838 && GET_MODE (operands[0]) != QImode"
8839 [(parallel [(set (strict_low_part (match_dup 0))
8840 (ior:QI (match_dup 1)
8842 (clobber (reg:CC FLAGS_REG))])]
8843 "operands[0] = gen_lowpart (QImode, operands[0]);
8844 operands[1] = gen_lowpart (QImode, operands[1]);
8845 operands[2] = gen_lowpart (QImode, operands[2]);")
8847 ;; Logical XOR instructions
8849 ;; %%% This used to optimize known byte-wide and operations to memory.
8850 ;; If this is considered useful, it should be done with splitters.
8852 (define_expand "xordi3"
8853 [(set (match_operand:DI 0 "nonimmediate_operand" "")
8854 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "")
8855 (match_operand:DI 2 "x86_64_general_operand" "")))
8856 (clobber (reg:CC FLAGS_REG))]
8858 "ix86_expand_binary_operator (XOR, DImode, operands); DONE;")
8860 (define_insn "*xordi_1_rex64"
8861 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
8862 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8863 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
8864 (clobber (reg:CC FLAGS_REG))]
8866 && ix86_binary_operator_ok (XOR, DImode, operands)"
8868 xor{q}\t{%2, %0|%0, %2}
8869 xor{q}\t{%2, %0|%0, %2}"
8870 [(set_attr "type" "alu")
8871 (set_attr "mode" "DI,DI")])
8873 (define_insn "*xordi_2_rex64"
8874 [(set (reg FLAGS_REG)
8875 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8876 (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
8878 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
8879 (xor:DI (match_dup 1) (match_dup 2)))]
8881 && ix86_match_ccmode (insn, CCNOmode)
8882 && ix86_binary_operator_ok (XOR, DImode, operands)"
8884 xor{q}\t{%2, %0|%0, %2}
8885 xor{q}\t{%2, %0|%0, %2}"
8886 [(set_attr "type" "alu")
8887 (set_attr "mode" "DI,DI")])
8889 (define_insn "*xordi_3_rex64"
8890 [(set (reg FLAGS_REG)
8891 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
8892 (match_operand:DI 2 "x86_64_general_operand" "rem"))
8894 (clobber (match_scratch:DI 0 "=r"))]
8896 && ix86_match_ccmode (insn, CCNOmode)
8897 && ix86_binary_operator_ok (XOR, DImode, operands)"
8898 "xor{q}\t{%2, %0|%0, %2}"
8899 [(set_attr "type" "alu")
8900 (set_attr "mode" "DI")])
8902 (define_expand "xorsi3"
8903 [(set (match_operand:SI 0 "nonimmediate_operand" "")
8904 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "")
8905 (match_operand:SI 2 "general_operand" "")))
8906 (clobber (reg:CC FLAGS_REG))]
8908 "ix86_expand_binary_operator (XOR, SImode, operands); DONE;")
8910 (define_insn "*xorsi_1"
8911 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
8912 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8913 (match_operand:SI 2 "general_operand" "ri,rm")))
8914 (clobber (reg:CC FLAGS_REG))]
8915 "ix86_binary_operator_ok (XOR, SImode, operands)"
8916 "xor{l}\t{%2, %0|%0, %2}"
8917 [(set_attr "type" "alu")
8918 (set_attr "mode" "SI")])
8920 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8921 ;; Add speccase for immediates
8922 (define_insn "*xorsi_1_zext"
8923 [(set (match_operand:DI 0 "register_operand" "=r")
8925 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8926 (match_operand:SI 2 "general_operand" "rim"))))
8927 (clobber (reg:CC FLAGS_REG))]
8928 "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
8929 "xor{l}\t{%2, %k0|%k0, %2}"
8930 [(set_attr "type" "alu")
8931 (set_attr "mode" "SI")])
8933 (define_insn "*xorsi_1_zext_imm"
8934 [(set (match_operand:DI 0 "register_operand" "=r")
8935 (xor:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8936 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8937 (clobber (reg:CC FLAGS_REG))]
8938 "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
8939 "xor{l}\t{%2, %k0|%k0, %2}"
8940 [(set_attr "type" "alu")
8941 (set_attr "mode" "SI")])
8943 (define_insn "*xorsi_2"
8944 [(set (reg FLAGS_REG)
8945 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8946 (match_operand:SI 2 "general_operand" "rim,ri"))
8948 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8949 (xor:SI (match_dup 1) (match_dup 2)))]
8950 "ix86_match_ccmode (insn, CCNOmode)
8951 && ix86_binary_operator_ok (XOR, SImode, operands)"
8952 "xor{l}\t{%2, %0|%0, %2}"
8953 [(set_attr "type" "alu")
8954 (set_attr "mode" "SI")])
8956 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8957 ;; ??? Special case for immediate operand is missing - it is tricky.
8958 (define_insn "*xorsi_2_zext"
8959 [(set (reg FLAGS_REG)
8960 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8961 (match_operand:SI 2 "general_operand" "rim"))
8963 (set (match_operand:DI 0 "register_operand" "=r")
8964 (zero_extend:DI (xor:SI (match_dup 1) (match_dup 2))))]
8965 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8966 && ix86_binary_operator_ok (XOR, SImode, operands)"
8967 "xor{l}\t{%2, %k0|%k0, %2}"
8968 [(set_attr "type" "alu")
8969 (set_attr "mode" "SI")])
8971 (define_insn "*xorsi_2_zext_imm"
8972 [(set (reg FLAGS_REG)
8973 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8974 (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
8976 (set (match_operand:DI 0 "register_operand" "=r")
8977 (xor:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8978 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8979 && ix86_binary_operator_ok (XOR, SImode, operands)"
8980 "xor{l}\t{%2, %k0|%k0, %2}"
8981 [(set_attr "type" "alu")
8982 (set_attr "mode" "SI")])
8984 (define_insn "*xorsi_3"
8985 [(set (reg FLAGS_REG)
8986 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8987 (match_operand:SI 2 "general_operand" "rim"))
8989 (clobber (match_scratch:SI 0 "=r"))]
8990 "ix86_match_ccmode (insn, CCNOmode)
8991 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8992 "xor{l}\t{%2, %0|%0, %2}"
8993 [(set_attr "type" "alu")
8994 (set_attr "mode" "SI")])
8996 (define_expand "xorhi3"
8997 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8998 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "")
8999 (match_operand:HI 2 "general_operand" "")))
9000 (clobber (reg:CC FLAGS_REG))]
9001 "TARGET_HIMODE_MATH"
9002 "ix86_expand_binary_operator (XOR, HImode, operands); DONE;")
9004 (define_insn "*xorhi_1"
9005 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
9006 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9007 (match_operand:HI 2 "general_operand" "rmi,ri")))
9008 (clobber (reg:CC FLAGS_REG))]
9009 "ix86_binary_operator_ok (XOR, HImode, operands)"
9010 "xor{w}\t{%2, %0|%0, %2}"
9011 [(set_attr "type" "alu")
9012 (set_attr "mode" "HI")])
9014 (define_insn "*xorhi_2"
9015 [(set (reg FLAGS_REG)
9016 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9017 (match_operand:HI 2 "general_operand" "rim,ri"))
9019 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
9020 (xor:HI (match_dup 1) (match_dup 2)))]
9021 "ix86_match_ccmode (insn, CCNOmode)
9022 && ix86_binary_operator_ok (XOR, HImode, operands)"
9023 "xor{w}\t{%2, %0|%0, %2}"
9024 [(set_attr "type" "alu")
9025 (set_attr "mode" "HI")])
9027 (define_insn "*xorhi_3"
9028 [(set (reg FLAGS_REG)
9029 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
9030 (match_operand:HI 2 "general_operand" "rim"))
9032 (clobber (match_scratch:HI 0 "=r"))]
9033 "ix86_match_ccmode (insn, CCNOmode)
9034 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
9035 "xor{w}\t{%2, %0|%0, %2}"
9036 [(set_attr "type" "alu")
9037 (set_attr "mode" "HI")])
9039 (define_expand "xorqi3"
9040 [(set (match_operand:QI 0 "nonimmediate_operand" "")
9041 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "")
9042 (match_operand:QI 2 "general_operand" "")))
9043 (clobber (reg:CC FLAGS_REG))]
9044 "TARGET_QIMODE_MATH"
9045 "ix86_expand_binary_operator (XOR, QImode, operands); DONE;")
9047 ;; %%% Potential partial reg stall on alternative 2. What to do?
9048 (define_insn "*xorqi_1"
9049 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
9050 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9051 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
9052 (clobber (reg:CC FLAGS_REG))]
9053 "ix86_binary_operator_ok (XOR, QImode, operands)"
9055 xor{b}\t{%2, %0|%0, %2}
9056 xor{b}\t{%2, %0|%0, %2}
9057 xor{l}\t{%k2, %k0|%k0, %k2}"
9058 [(set_attr "type" "alu")
9059 (set_attr "mode" "QI,QI,SI")])
9061 (define_insn "*xorqi_1_slp"
9062 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
9063 (xor:QI (match_dup 0)
9064 (match_operand:QI 1 "general_operand" "qi,qmi")))
9065 (clobber (reg:CC FLAGS_REG))]
9066 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9067 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
9068 "xor{b}\t{%1, %0|%0, %1}"
9069 [(set_attr "type" "alu1")
9070 (set_attr "mode" "QI")])
9072 (define_insn "xorqi_ext_0"
9073 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9078 (match_operand 1 "ext_register_operand" "0")
9081 (match_operand 2 "const_int_operand" "n")))
9082 (clobber (reg:CC FLAGS_REG))]
9083 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9084 "xor{b}\t{%2, %h0|%h0, %2}"
9085 [(set_attr "type" "alu")
9086 (set_attr "length_immediate" "1")
9087 (set_attr "mode" "QI")])
9089 (define_insn "*xorqi_ext_1"
9090 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9095 (match_operand 1 "ext_register_operand" "0")
9099 (match_operand:QI 2 "general_operand" "Qm"))))
9100 (clobber (reg:CC FLAGS_REG))]
9102 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9103 "xor{b}\t{%2, %h0|%h0, %2}"
9104 [(set_attr "type" "alu")
9105 (set_attr "length_immediate" "0")
9106 (set_attr "mode" "QI")])
9108 (define_insn "*xorqi_ext_1_rex64"
9109 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9114 (match_operand 1 "ext_register_operand" "0")
9118 (match_operand 2 "ext_register_operand" "Q"))))
9119 (clobber (reg:CC FLAGS_REG))]
9121 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9122 "xor{b}\t{%2, %h0|%h0, %2}"
9123 [(set_attr "type" "alu")
9124 (set_attr "length_immediate" "0")
9125 (set_attr "mode" "QI")])
9127 (define_insn "*xorqi_ext_2"
9128 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9132 (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
9135 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
9138 (clobber (reg:CC FLAGS_REG))]
9139 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9140 "xor{b}\t{%h2, %h0|%h0, %h2}"
9141 [(set_attr "type" "alu")
9142 (set_attr "length_immediate" "0")
9143 (set_attr "mode" "QI")])
9145 (define_insn "*xorqi_cc_1"
9146 [(set (reg FLAGS_REG)
9148 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9149 (match_operand:QI 2 "general_operand" "qim,qi"))
9151 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9152 (xor:QI (match_dup 1) (match_dup 2)))]
9153 "ix86_match_ccmode (insn, CCNOmode)
9154 && ix86_binary_operator_ok (XOR, QImode, operands)"
9155 "xor{b}\t{%2, %0|%0, %2}"
9156 [(set_attr "type" "alu")
9157 (set_attr "mode" "QI")])
9159 (define_insn "*xorqi_2_slp"
9160 [(set (reg FLAGS_REG)
9161 (compare (xor:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9162 (match_operand:QI 1 "general_operand" "qim,qi"))
9164 (set (strict_low_part (match_dup 0))
9165 (xor:QI (match_dup 0) (match_dup 1)))]
9166 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9167 && ix86_match_ccmode (insn, CCNOmode)
9168 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
9169 "xor{b}\t{%1, %0|%0, %1}"
9170 [(set_attr "type" "alu1")
9171 (set_attr "mode" "QI")])
9173 (define_insn "*xorqi_cc_2"
9174 [(set (reg FLAGS_REG)
9176 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
9177 (match_operand:QI 2 "general_operand" "qim"))
9179 (clobber (match_scratch:QI 0 "=q"))]
9180 "ix86_match_ccmode (insn, CCNOmode)
9181 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
9182 "xor{b}\t{%2, %0|%0, %2}"
9183 [(set_attr "type" "alu")
9184 (set_attr "mode" "QI")])
9186 (define_insn "*xorqi_cc_ext_1"
9187 [(set (reg FLAGS_REG)
9191 (match_operand 1 "ext_register_operand" "0")
9194 (match_operand:QI 2 "general_operand" "qmn"))
9196 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
9200 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9202 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9203 "xor{b}\t{%2, %h0|%h0, %2}"
9204 [(set_attr "type" "alu")
9205 (set_attr "mode" "QI")])
9207 (define_insn "*xorqi_cc_ext_1_rex64"
9208 [(set (reg FLAGS_REG)
9212 (match_operand 1 "ext_register_operand" "0")
9215 (match_operand:QI 2 "nonmemory_operand" "Qn"))
9217 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9221 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9223 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9224 "xor{b}\t{%2, %h0|%h0, %2}"
9225 [(set_attr "type" "alu")
9226 (set_attr "mode" "QI")])
9228 (define_expand "xorqi_cc_ext_1"
9230 (set (reg:CCNO FLAGS_REG)
9234 (match_operand 1 "ext_register_operand" "")
9237 (match_operand:QI 2 "general_operand" ""))
9239 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
9243 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9249 [(set (match_operand 0 "register_operand" "")
9250 (xor (match_operand 1 "register_operand" "")
9251 (match_operand 2 "const_int_operand" "")))
9252 (clobber (reg:CC FLAGS_REG))]
9254 && QI_REG_P (operands[0])
9255 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9256 && !(INTVAL (operands[2]) & ~(255 << 8))
9257 && GET_MODE (operands[0]) != QImode"
9258 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9259 (xor:SI (zero_extract:SI (match_dup 1)
9260 (const_int 8) (const_int 8))
9262 (clobber (reg:CC FLAGS_REG))])]
9263 "operands[0] = gen_lowpart (SImode, operands[0]);
9264 operands[1] = gen_lowpart (SImode, operands[1]);
9265 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9267 ;; Since XOR can be encoded with sign extended immediate, this is only
9268 ;; profitable when 7th bit is set.
9270 [(set (match_operand 0 "register_operand" "")
9271 (xor (match_operand 1 "general_operand" "")
9272 (match_operand 2 "const_int_operand" "")))
9273 (clobber (reg:CC FLAGS_REG))]
9275 && ANY_QI_REG_P (operands[0])
9276 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9277 && !(INTVAL (operands[2]) & ~255)
9278 && (INTVAL (operands[2]) & 128)
9279 && GET_MODE (operands[0]) != QImode"
9280 [(parallel [(set (strict_low_part (match_dup 0))
9281 (xor:QI (match_dup 1)
9283 (clobber (reg:CC FLAGS_REG))])]
9284 "operands[0] = gen_lowpart (QImode, operands[0]);
9285 operands[1] = gen_lowpart (QImode, operands[1]);
9286 operands[2] = gen_lowpart (QImode, operands[2]);")
9288 ;; Negation instructions
9290 (define_expand "negti2"
9291 [(parallel [(set (match_operand:TI 0 "nonimmediate_operand" "")
9292 (neg:TI (match_operand:TI 1 "nonimmediate_operand" "")))
9293 (clobber (reg:CC FLAGS_REG))])]
9295 "ix86_expand_unary_operator (NEG, TImode, operands); DONE;")
9297 (define_insn "*negti2_1"
9298 [(set (match_operand:TI 0 "nonimmediate_operand" "=ro")
9299 (neg:TI (match_operand:TI 1 "general_operand" "0")))
9300 (clobber (reg:CC FLAGS_REG))]
9302 && ix86_unary_operator_ok (NEG, TImode, operands)"
9306 [(set (match_operand:TI 0 "nonimmediate_operand" "")
9307 (neg:TI (match_operand:TI 1 "general_operand" "")))
9308 (clobber (reg:CC FLAGS_REG))]
9309 "TARGET_64BIT && reload_completed"
9311 [(set (reg:CCZ FLAGS_REG)
9312 (compare:CCZ (neg:DI (match_dup 2)) (const_int 0)))
9313 (set (match_dup 0) (neg:DI (match_dup 2)))])
9316 (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
9319 (clobber (reg:CC FLAGS_REG))])
9322 (neg:DI (match_dup 1)))
9323 (clobber (reg:CC FLAGS_REG))])]
9324 "split_ti (operands+1, 1, operands+2, operands+3);
9325 split_ti (operands+0, 1, operands+0, operands+1);")
9327 (define_expand "negdi2"
9328 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
9329 (neg:DI (match_operand:DI 1 "nonimmediate_operand" "")))
9330 (clobber (reg:CC FLAGS_REG))])]
9332 "ix86_expand_unary_operator (NEG, DImode, operands); DONE;")
9334 (define_insn "*negdi2_1"
9335 [(set (match_operand:DI 0 "nonimmediate_operand" "=ro")
9336 (neg:DI (match_operand:DI 1 "general_operand" "0")))
9337 (clobber (reg:CC FLAGS_REG))]
9339 && ix86_unary_operator_ok (NEG, DImode, operands)"
9343 [(set (match_operand:DI 0 "nonimmediate_operand" "")
9344 (neg:DI (match_operand:DI 1 "general_operand" "")))
9345 (clobber (reg:CC FLAGS_REG))]
9346 "!TARGET_64BIT && reload_completed"
9348 [(set (reg:CCZ FLAGS_REG)
9349 (compare:CCZ (neg:SI (match_dup 2)) (const_int 0)))
9350 (set (match_dup 0) (neg:SI (match_dup 2)))])
9353 (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
9356 (clobber (reg:CC FLAGS_REG))])
9359 (neg:SI (match_dup 1)))
9360 (clobber (reg:CC FLAGS_REG))])]
9361 "split_di (operands+1, 1, operands+2, operands+3);
9362 split_di (operands+0, 1, operands+0, operands+1);")
9364 (define_insn "*negdi2_1_rex64"
9365 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9366 (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0")))
9367 (clobber (reg:CC FLAGS_REG))]
9368 "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
9370 [(set_attr "type" "negnot")
9371 (set_attr "mode" "DI")])
9373 ;; The problem with neg is that it does not perform (compare x 0),
9374 ;; it really performs (compare 0 x), which leaves us with the zero
9375 ;; flag being the only useful item.
9377 (define_insn "*negdi2_cmpz_rex64"
9378 [(set (reg:CCZ FLAGS_REG)
9379 (compare:CCZ (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
9381 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9382 (neg:DI (match_dup 1)))]
9383 "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
9385 [(set_attr "type" "negnot")
9386 (set_attr "mode" "DI")])
9389 (define_expand "negsi2"
9390 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
9391 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "")))
9392 (clobber (reg:CC FLAGS_REG))])]
9394 "ix86_expand_unary_operator (NEG, SImode, operands); DONE;")
9396 (define_insn "*negsi2_1"
9397 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9398 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0")))
9399 (clobber (reg:CC FLAGS_REG))]
9400 "ix86_unary_operator_ok (NEG, SImode, operands)"
9402 [(set_attr "type" "negnot")
9403 (set_attr "mode" "SI")])
9405 ;; Combine is quite creative about this pattern.
9406 (define_insn "*negsi2_1_zext"
9407 [(set (match_operand:DI 0 "register_operand" "=r")
9408 (lshiftrt:DI (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
9411 (clobber (reg:CC FLAGS_REG))]
9412 "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
9414 [(set_attr "type" "negnot")
9415 (set_attr "mode" "SI")])
9417 ;; The problem with neg is that it does not perform (compare x 0),
9418 ;; it really performs (compare 0 x), which leaves us with the zero
9419 ;; flag being the only useful item.
9421 (define_insn "*negsi2_cmpz"
9422 [(set (reg:CCZ FLAGS_REG)
9423 (compare:CCZ (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
9425 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9426 (neg:SI (match_dup 1)))]
9427 "ix86_unary_operator_ok (NEG, SImode, operands)"
9429 [(set_attr "type" "negnot")
9430 (set_attr "mode" "SI")])
9432 (define_insn "*negsi2_cmpz_zext"
9433 [(set (reg:CCZ FLAGS_REG)
9434 (compare:CCZ (lshiftrt:DI
9436 (match_operand:DI 1 "register_operand" "0")
9440 (set (match_operand:DI 0 "register_operand" "=r")
9441 (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
9444 "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
9446 [(set_attr "type" "negnot")
9447 (set_attr "mode" "SI")])
9449 (define_expand "neghi2"
9450 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
9451 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "")))
9452 (clobber (reg:CC FLAGS_REG))])]
9453 "TARGET_HIMODE_MATH"
9454 "ix86_expand_unary_operator (NEG, HImode, operands); DONE;")
9456 (define_insn "*neghi2_1"
9457 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9458 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0")))
9459 (clobber (reg:CC FLAGS_REG))]
9460 "ix86_unary_operator_ok (NEG, HImode, operands)"
9462 [(set_attr "type" "negnot")
9463 (set_attr "mode" "HI")])
9465 (define_insn "*neghi2_cmpz"
9466 [(set (reg:CCZ FLAGS_REG)
9467 (compare:CCZ (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
9469 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9470 (neg:HI (match_dup 1)))]
9471 "ix86_unary_operator_ok (NEG, HImode, operands)"
9473 [(set_attr "type" "negnot")
9474 (set_attr "mode" "HI")])
9476 (define_expand "negqi2"
9477 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
9478 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "")))
9479 (clobber (reg:CC FLAGS_REG))])]
9480 "TARGET_QIMODE_MATH"
9481 "ix86_expand_unary_operator (NEG, QImode, operands); DONE;")
9483 (define_insn "*negqi2_1"
9484 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9485 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0")))
9486 (clobber (reg:CC FLAGS_REG))]
9487 "ix86_unary_operator_ok (NEG, QImode, operands)"
9489 [(set_attr "type" "negnot")
9490 (set_attr "mode" "QI")])
9492 (define_insn "*negqi2_cmpz"
9493 [(set (reg:CCZ FLAGS_REG)
9494 (compare:CCZ (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
9496 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9497 (neg:QI (match_dup 1)))]
9498 "ix86_unary_operator_ok (NEG, QImode, operands)"
9500 [(set_attr "type" "negnot")
9501 (set_attr "mode" "QI")])
9503 ;; Changing of sign for FP values is doable using integer unit too.
9505 (define_expand "negsf2"
9506 [(set (match_operand:SF 0 "nonimmediate_operand" "")
9507 (neg:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
9508 "TARGET_80387 || TARGET_SSE_MATH"
9509 "ix86_expand_fp_absneg_operator (NEG, SFmode, operands); DONE;")
9511 (define_expand "abssf2"
9512 [(set (match_operand:SF 0 "nonimmediate_operand" "")
9513 (abs:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
9514 "TARGET_80387 || TARGET_SSE_MATH"
9515 "ix86_expand_fp_absneg_operator (ABS, SFmode, operands); DONE;")
9517 (define_insn "*absnegsf2_mixed"
9518 [(set (match_operand:SF 0 "nonimmediate_operand" "=x#f,x#f,f#x,rm")
9519 (match_operator:SF 3 "absneg_operator"
9520 [(match_operand:SF 1 "nonimmediate_operand" "0 ,x#f,0 ,0")]))
9521 (use (match_operand:V4SF 2 "nonimmediate_operand" "xm ,0 ,X ,X"))
9522 (clobber (reg:CC FLAGS_REG))]
9523 "TARGET_SSE_MATH && TARGET_MIX_SSE_I387
9524 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9527 (define_insn "*absnegsf2_sse"
9528 [(set (match_operand:SF 0 "nonimmediate_operand" "=x,x,rm")
9529 (match_operator:SF 3 "absneg_operator"
9530 [(match_operand:SF 1 "nonimmediate_operand" "0 ,x,0")]))
9531 (use (match_operand:V4SF 2 "nonimmediate_operand" "xm,0,X"))
9532 (clobber (reg:CC FLAGS_REG))]
9534 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9537 (define_insn "*absnegsf2_i387"
9538 [(set (match_operand:SF 0 "nonimmediate_operand" "=f,rm")
9539 (match_operator:SF 3 "absneg_operator"
9540 [(match_operand:SF 1 "nonimmediate_operand" "0,0")]))
9541 (use (match_operand 2 "" ""))
9542 (clobber (reg:CC FLAGS_REG))]
9543 "TARGET_80387 && !TARGET_SSE_MATH
9544 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9547 (define_expand "copysignsf3"
9548 [(match_operand:SF 0 "register_operand" "")
9549 (match_operand:SF 1 "nonmemory_operand" "")
9550 (match_operand:SF 2 "register_operand" "")]
9553 ix86_expand_copysign (operands);
9557 (define_insn_and_split "copysignsf3_const"
9558 [(set (match_operand:SF 0 "register_operand" "=x")
9560 [(match_operand:V4SF 1 "vector_move_operand" "xmC")
9561 (match_operand:SF 2 "register_operand" "0")
9562 (match_operand:V4SF 3 "nonimmediate_operand" "xm")]
9566 "&& reload_completed"
9569 ix86_split_copysign_const (operands);
9573 (define_insn "copysignsf3_var"
9574 [(set (match_operand:SF 0 "register_operand" "=x, x, x, x,x")
9576 [(match_operand:SF 2 "register_operand" " x, 0, 0, x,x")
9577 (match_operand:SF 3 "register_operand" " 1, 1, x, 1,x")
9578 (match_operand:V4SF 4 "nonimmediate_operand" " X,xm,xm, 0,0")
9579 (match_operand:V4SF 5 "nonimmediate_operand" " 0,xm, 1,xm,1")]
9581 (clobber (match_scratch:V4SF 1 "=x, x, x, x,x"))]
9586 [(set (match_operand:SF 0 "register_operand" "")
9588 [(match_operand:SF 2 "register_operand" "")
9589 (match_operand:SF 3 "register_operand" "")
9590 (match_operand:V4SF 4 "" "")
9591 (match_operand:V4SF 5 "" "")]
9593 (clobber (match_scratch:V4SF 1 ""))]
9594 "TARGET_SSE_MATH && reload_completed"
9597 ix86_split_copysign_var (operands);
9601 (define_expand "negdf2"
9602 [(set (match_operand:DF 0 "nonimmediate_operand" "")
9603 (neg:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
9604 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
9605 "ix86_expand_fp_absneg_operator (NEG, DFmode, operands); DONE;")
9607 (define_expand "absdf2"
9608 [(set (match_operand:DF 0 "nonimmediate_operand" "")
9609 (abs:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
9610 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
9611 "ix86_expand_fp_absneg_operator (ABS, DFmode, operands); DONE;")
9613 (define_insn "*absnegdf2_mixed"
9614 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y#f,Y#f,f#Y,rm")
9615 (match_operator:DF 3 "absneg_operator"
9616 [(match_operand:DF 1 "nonimmediate_operand" "0 ,Y#f,0 ,0")]))
9617 (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym ,0 ,X ,X"))
9618 (clobber (reg:CC FLAGS_REG))]
9619 "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
9620 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9623 (define_insn "*absnegdf2_sse"
9624 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y,Y,rm")
9625 (match_operator:DF 3 "absneg_operator"
9626 [(match_operand:DF 1 "nonimmediate_operand" "0 ,Y,0")]))
9627 (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym,0,X"))
9628 (clobber (reg:CC FLAGS_REG))]
9629 "TARGET_SSE2 && TARGET_SSE_MATH
9630 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9633 (define_insn "*absnegdf2_i387"
9634 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,rm")
9635 (match_operator:DF 3 "absneg_operator"
9636 [(match_operand:DF 1 "nonimmediate_operand" "0,0")]))
9637 (use (match_operand 2 "" ""))
9638 (clobber (reg:CC FLAGS_REG))]
9639 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
9640 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9643 (define_expand "copysigndf3"
9644 [(match_operand:DF 0 "register_operand" "")
9645 (match_operand:DF 1 "nonmemory_operand" "")
9646 (match_operand:DF 2 "register_operand" "")]
9647 "TARGET_SSE2 && TARGET_SSE_MATH"
9649 ix86_expand_copysign (operands);
9653 (define_insn_and_split "copysigndf3_const"
9654 [(set (match_operand:DF 0 "register_operand" "=x")
9656 [(match_operand:V2DF 1 "vector_move_operand" "xmC")
9657 (match_operand:DF 2 "register_operand" "0")
9658 (match_operand:V2DF 3 "nonimmediate_operand" "xm")]
9660 "TARGET_SSE2 && TARGET_SSE_MATH"
9662 "&& reload_completed"
9665 ix86_split_copysign_const (operands);
9669 (define_insn "copysigndf3_var"
9670 [(set (match_operand:DF 0 "register_operand" "=x, x, x, x,x")
9672 [(match_operand:DF 2 "register_operand" " x, 0, 0, x,x")
9673 (match_operand:DF 3 "register_operand" " 1, 1, x, 1,x")
9674 (match_operand:V2DF 4 "nonimmediate_operand" " X,xm,xm, 0,0")
9675 (match_operand:V2DF 5 "nonimmediate_operand" " 0,xm, 1,xm,1")]
9677 (clobber (match_scratch:V2DF 1 "=x, x, x, x,x"))]
9678 "TARGET_SSE2 && TARGET_SSE_MATH"
9682 [(set (match_operand:DF 0 "register_operand" "")
9684 [(match_operand:DF 2 "register_operand" "")
9685 (match_operand:DF 3 "register_operand" "")
9686 (match_operand:V2DF 4 "" "")
9687 (match_operand:V2DF 5 "" "")]
9689 (clobber (match_scratch:V2DF 1 ""))]
9690 "TARGET_SSE2 && TARGET_SSE_MATH && reload_completed"
9693 ix86_split_copysign_var (operands);
9697 (define_expand "negxf2"
9698 [(set (match_operand:XF 0 "nonimmediate_operand" "")
9699 (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))]
9701 "ix86_expand_fp_absneg_operator (NEG, XFmode, operands); DONE;")
9703 (define_expand "absxf2"
9704 [(set (match_operand:XF 0 "nonimmediate_operand" "")
9705 (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))]
9707 "ix86_expand_fp_absneg_operator (ABS, XFmode, operands); DONE;")
9709 (define_insn "*absnegxf2_i387"
9710 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,?rm")
9711 (match_operator:XF 3 "absneg_operator"
9712 [(match_operand:XF 1 "nonimmediate_operand" "0,0")]))
9713 (use (match_operand 2 "" ""))
9714 (clobber (reg:CC FLAGS_REG))]
9716 && ix86_unary_operator_ok (GET_CODE (operands[3]), XFmode, operands)"
9719 ;; Splitters for fp abs and neg.
9722 [(set (match_operand 0 "fp_register_operand" "")
9723 (match_operator 1 "absneg_operator" [(match_dup 0)]))
9724 (use (match_operand 2 "" ""))
9725 (clobber (reg:CC FLAGS_REG))]
9727 [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))])
9730 [(set (match_operand 0 "register_operand" "")
9731 (match_operator 3 "absneg_operator"
9732 [(match_operand 1 "register_operand" "")]))
9733 (use (match_operand 2 "nonimmediate_operand" ""))
9734 (clobber (reg:CC FLAGS_REG))]
9735 "reload_completed && SSE_REG_P (operands[0])"
9736 [(set (match_dup 0) (match_dup 3))]
9738 enum machine_mode mode = GET_MODE (operands[0]);
9739 enum machine_mode vmode = GET_MODE (operands[2]);
9742 operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0);
9743 operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0);
9744 if (operands_match_p (operands[0], operands[2]))
9747 operands[1] = operands[2];
9750 if (GET_CODE (operands[3]) == ABS)
9751 tmp = gen_rtx_AND (vmode, operands[1], operands[2]);
9753 tmp = gen_rtx_XOR (vmode, operands[1], operands[2]);
9758 [(set (match_operand:SF 0 "register_operand" "")
9759 (match_operator:SF 1 "absneg_operator" [(match_dup 0)]))
9760 (use (match_operand:V4SF 2 "" ""))
9761 (clobber (reg:CC FLAGS_REG))]
9763 [(parallel [(set (match_dup 0) (match_dup 1))
9764 (clobber (reg:CC FLAGS_REG))])]
9767 operands[0] = gen_lowpart (SImode, operands[0]);
9768 if (GET_CODE (operands[1]) == ABS)
9770 tmp = gen_int_mode (0x7fffffff, SImode);
9771 tmp = gen_rtx_AND (SImode, operands[0], tmp);
9775 tmp = gen_int_mode (0x80000000, SImode);
9776 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9782 [(set (match_operand:DF 0 "register_operand" "")
9783 (match_operator:DF 1 "absneg_operator" [(match_dup 0)]))
9784 (use (match_operand 2 "" ""))
9785 (clobber (reg:CC FLAGS_REG))]
9787 [(parallel [(set (match_dup 0) (match_dup 1))
9788 (clobber (reg:CC FLAGS_REG))])]
9793 tmp = gen_lowpart (DImode, operands[0]);
9794 tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63));
9797 if (GET_CODE (operands[1]) == ABS)
9800 tmp = gen_rtx_NOT (DImode, tmp);
9804 operands[0] = gen_highpart (SImode, operands[0]);
9805 if (GET_CODE (operands[1]) == ABS)
9807 tmp = gen_int_mode (0x7fffffff, SImode);
9808 tmp = gen_rtx_AND (SImode, operands[0], tmp);
9812 tmp = gen_int_mode (0x80000000, SImode);
9813 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9820 [(set (match_operand:XF 0 "register_operand" "")
9821 (match_operator:XF 1 "absneg_operator" [(match_dup 0)]))
9822 (use (match_operand 2 "" ""))
9823 (clobber (reg:CC FLAGS_REG))]
9825 [(parallel [(set (match_dup 0) (match_dup 1))
9826 (clobber (reg:CC FLAGS_REG))])]
9829 operands[0] = gen_rtx_REG (SImode,
9830 true_regnum (operands[0])
9831 + (TARGET_64BIT ? 1 : 2));
9832 if (GET_CODE (operands[1]) == ABS)
9834 tmp = GEN_INT (0x7fff);
9835 tmp = gen_rtx_AND (SImode, operands[0], tmp);
9839 tmp = GEN_INT (0x8000);
9840 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9846 [(set (match_operand 0 "memory_operand" "")
9847 (match_operator 1 "absneg_operator" [(match_dup 0)]))
9848 (use (match_operand 2 "" ""))
9849 (clobber (reg:CC FLAGS_REG))]
9851 [(parallel [(set (match_dup 0) (match_dup 1))
9852 (clobber (reg:CC FLAGS_REG))])]
9854 enum machine_mode mode = GET_MODE (operands[0]);
9855 int size = mode == XFmode ? 10 : GET_MODE_SIZE (mode);
9858 operands[0] = adjust_address (operands[0], QImode, size - 1);
9859 if (GET_CODE (operands[1]) == ABS)
9861 tmp = gen_int_mode (0x7f, QImode);
9862 tmp = gen_rtx_AND (QImode, operands[0], tmp);
9866 tmp = gen_int_mode (0x80, QImode);
9867 tmp = gen_rtx_XOR (QImode, operands[0], tmp);
9872 ;; Conditionalize these after reload. If they match before reload, we
9873 ;; lose the clobber and ability to use integer instructions.
9875 (define_insn "*negsf2_1"
9876 [(set (match_operand:SF 0 "register_operand" "=f")
9877 (neg:SF (match_operand:SF 1 "register_operand" "0")))]
9878 "TARGET_80387 && reload_completed"
9880 [(set_attr "type" "fsgn")
9881 (set_attr "mode" "SF")])
9883 (define_insn "*negdf2_1"
9884 [(set (match_operand:DF 0 "register_operand" "=f")
9885 (neg:DF (match_operand:DF 1 "register_operand" "0")))]
9886 "TARGET_80387 && reload_completed"
9888 [(set_attr "type" "fsgn")
9889 (set_attr "mode" "DF")])
9891 (define_insn "*negxf2_1"
9892 [(set (match_operand:XF 0 "register_operand" "=f")
9893 (neg:XF (match_operand:XF 1 "register_operand" "0")))]
9894 "TARGET_80387 && reload_completed"
9896 [(set_attr "type" "fsgn")
9897 (set_attr "mode" "XF")])
9899 (define_insn "*abssf2_1"
9900 [(set (match_operand:SF 0 "register_operand" "=f")
9901 (abs:SF (match_operand:SF 1 "register_operand" "0")))]
9902 "TARGET_80387 && reload_completed"
9904 [(set_attr "type" "fsgn")
9905 (set_attr "mode" "SF")])
9907 (define_insn "*absdf2_1"
9908 [(set (match_operand:DF 0 "register_operand" "=f")
9909 (abs:DF (match_operand:DF 1 "register_operand" "0")))]
9910 "TARGET_80387 && reload_completed"
9912 [(set_attr "type" "fsgn")
9913 (set_attr "mode" "DF")])
9915 (define_insn "*absxf2_1"
9916 [(set (match_operand:XF 0 "register_operand" "=f")
9917 (abs:XF (match_operand:XF 1 "register_operand" "0")))]
9918 "TARGET_80387 && reload_completed"
9920 [(set_attr "type" "fsgn")
9921 (set_attr "mode" "DF")])
9923 (define_insn "*negextendsfdf2"
9924 [(set (match_operand:DF 0 "register_operand" "=f")
9925 (neg:DF (float_extend:DF
9926 (match_operand:SF 1 "register_operand" "0"))))]
9927 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
9929 [(set_attr "type" "fsgn")
9930 (set_attr "mode" "DF")])
9932 (define_insn "*negextenddfxf2"
9933 [(set (match_operand:XF 0 "register_operand" "=f")
9934 (neg:XF (float_extend:XF
9935 (match_operand:DF 1 "register_operand" "0"))))]
9938 [(set_attr "type" "fsgn")
9939 (set_attr "mode" "XF")])
9941 (define_insn "*negextendsfxf2"
9942 [(set (match_operand:XF 0 "register_operand" "=f")
9943 (neg:XF (float_extend:XF
9944 (match_operand:SF 1 "register_operand" "0"))))]
9947 [(set_attr "type" "fsgn")
9948 (set_attr "mode" "XF")])
9950 (define_insn "*absextendsfdf2"
9951 [(set (match_operand:DF 0 "register_operand" "=f")
9952 (abs:DF (float_extend:DF
9953 (match_operand:SF 1 "register_operand" "0"))))]
9954 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
9956 [(set_attr "type" "fsgn")
9957 (set_attr "mode" "DF")])
9959 (define_insn "*absextenddfxf2"
9960 [(set (match_operand:XF 0 "register_operand" "=f")
9961 (abs:XF (float_extend:XF
9962 (match_operand:DF 1 "register_operand" "0"))))]
9965 [(set_attr "type" "fsgn")
9966 (set_attr "mode" "XF")])
9968 (define_insn "*absextendsfxf2"
9969 [(set (match_operand:XF 0 "register_operand" "=f")
9970 (abs:XF (float_extend:XF
9971 (match_operand:SF 1 "register_operand" "0"))))]
9974 [(set_attr "type" "fsgn")
9975 (set_attr "mode" "XF")])
9977 ;; One complement instructions
9979 (define_expand "one_cmpldi2"
9980 [(set (match_operand:DI 0 "nonimmediate_operand" "")
9981 (not:DI (match_operand:DI 1 "nonimmediate_operand" "")))]
9983 "ix86_expand_unary_operator (NOT, DImode, operands); DONE;")
9985 (define_insn "*one_cmpldi2_1_rex64"
9986 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9987 (not:DI (match_operand:DI 1 "nonimmediate_operand" "0")))]
9988 "TARGET_64BIT && ix86_unary_operator_ok (NOT, DImode, operands)"
9990 [(set_attr "type" "negnot")
9991 (set_attr "mode" "DI")])
9993 (define_insn "*one_cmpldi2_2_rex64"
9994 [(set (reg FLAGS_REG)
9995 (compare (not:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
9997 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9998 (not:DI (match_dup 1)))]
9999 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10000 && ix86_unary_operator_ok (NOT, DImode, operands)"
10002 [(set_attr "type" "alu1")
10003 (set_attr "mode" "DI")])
10006 [(set (match_operand 0 "flags_reg_operand" "")
10007 (match_operator 2 "compare_operator"
10008 [(not:DI (match_operand:DI 3 "nonimmediate_operand" ""))
10010 (set (match_operand:DI 1 "nonimmediate_operand" "")
10011 (not:DI (match_dup 3)))]
10012 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
10013 [(parallel [(set (match_dup 0)
10015 [(xor:DI (match_dup 3) (const_int -1))
10018 (xor:DI (match_dup 3) (const_int -1)))])]
10021 (define_expand "one_cmplsi2"
10022 [(set (match_operand:SI 0 "nonimmediate_operand" "")
10023 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
10025 "ix86_expand_unary_operator (NOT, SImode, operands); DONE;")
10027 (define_insn "*one_cmplsi2_1"
10028 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10029 (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))]
10030 "ix86_unary_operator_ok (NOT, SImode, operands)"
10032 [(set_attr "type" "negnot")
10033 (set_attr "mode" "SI")])
10035 ;; ??? Currently never generated - xor is used instead.
10036 (define_insn "*one_cmplsi2_1_zext"
10037 [(set (match_operand:DI 0 "register_operand" "=r")
10038 (zero_extend:DI (not:SI (match_operand:SI 1 "register_operand" "0"))))]
10039 "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
10041 [(set_attr "type" "negnot")
10042 (set_attr "mode" "SI")])
10044 (define_insn "*one_cmplsi2_2"
10045 [(set (reg FLAGS_REG)
10046 (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
10048 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10049 (not:SI (match_dup 1)))]
10050 "ix86_match_ccmode (insn, CCNOmode)
10051 && ix86_unary_operator_ok (NOT, SImode, operands)"
10053 [(set_attr "type" "alu1")
10054 (set_attr "mode" "SI")])
10057 [(set (match_operand 0 "flags_reg_operand" "")
10058 (match_operator 2 "compare_operator"
10059 [(not:SI (match_operand:SI 3 "nonimmediate_operand" ""))
10061 (set (match_operand:SI 1 "nonimmediate_operand" "")
10062 (not:SI (match_dup 3)))]
10063 "ix86_match_ccmode (insn, CCNOmode)"
10064 [(parallel [(set (match_dup 0)
10065 (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
10068 (xor:SI (match_dup 3) (const_int -1)))])]
10071 ;; ??? Currently never generated - xor is used instead.
10072 (define_insn "*one_cmplsi2_2_zext"
10073 [(set (reg FLAGS_REG)
10074 (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
10076 (set (match_operand:DI 0 "register_operand" "=r")
10077 (zero_extend:DI (not:SI (match_dup 1))))]
10078 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10079 && ix86_unary_operator_ok (NOT, SImode, operands)"
10081 [(set_attr "type" "alu1")
10082 (set_attr "mode" "SI")])
10085 [(set (match_operand 0 "flags_reg_operand" "")
10086 (match_operator 2 "compare_operator"
10087 [(not:SI (match_operand:SI 3 "register_operand" ""))
10089 (set (match_operand:DI 1 "register_operand" "")
10090 (zero_extend:DI (not:SI (match_dup 3))))]
10091 "ix86_match_ccmode (insn, CCNOmode)"
10092 [(parallel [(set (match_dup 0)
10093 (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
10096 (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])]
10099 (define_expand "one_cmplhi2"
10100 [(set (match_operand:HI 0 "nonimmediate_operand" "")
10101 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
10102 "TARGET_HIMODE_MATH"
10103 "ix86_expand_unary_operator (NOT, HImode, operands); DONE;")
10105 (define_insn "*one_cmplhi2_1"
10106 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10107 (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))]
10108 "ix86_unary_operator_ok (NOT, HImode, operands)"
10110 [(set_attr "type" "negnot")
10111 (set_attr "mode" "HI")])
10113 (define_insn "*one_cmplhi2_2"
10114 [(set (reg FLAGS_REG)
10115 (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
10117 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10118 (not:HI (match_dup 1)))]
10119 "ix86_match_ccmode (insn, CCNOmode)
10120 && ix86_unary_operator_ok (NEG, HImode, operands)"
10122 [(set_attr "type" "alu1")
10123 (set_attr "mode" "HI")])
10126 [(set (match_operand 0 "flags_reg_operand" "")
10127 (match_operator 2 "compare_operator"
10128 [(not:HI (match_operand:HI 3 "nonimmediate_operand" ""))
10130 (set (match_operand:HI 1 "nonimmediate_operand" "")
10131 (not:HI (match_dup 3)))]
10132 "ix86_match_ccmode (insn, CCNOmode)"
10133 [(parallel [(set (match_dup 0)
10134 (match_op_dup 2 [(xor:HI (match_dup 3) (const_int -1))
10137 (xor:HI (match_dup 3) (const_int -1)))])]
10140 ;; %%% Potential partial reg stall on alternative 1. What to do?
10141 (define_expand "one_cmplqi2"
10142 [(set (match_operand:QI 0 "nonimmediate_operand" "")
10143 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
10144 "TARGET_QIMODE_MATH"
10145 "ix86_expand_unary_operator (NOT, QImode, operands); DONE;")
10147 (define_insn "*one_cmplqi2_1"
10148 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10149 (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
10150 "ix86_unary_operator_ok (NOT, QImode, operands)"
10154 [(set_attr "type" "negnot")
10155 (set_attr "mode" "QI,SI")])
10157 (define_insn "*one_cmplqi2_2"
10158 [(set (reg FLAGS_REG)
10159 (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
10161 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10162 (not:QI (match_dup 1)))]
10163 "ix86_match_ccmode (insn, CCNOmode)
10164 && ix86_unary_operator_ok (NOT, QImode, operands)"
10166 [(set_attr "type" "alu1")
10167 (set_attr "mode" "QI")])
10170 [(set (match_operand 0 "flags_reg_operand" "")
10171 (match_operator 2 "compare_operator"
10172 [(not:QI (match_operand:QI 3 "nonimmediate_operand" ""))
10174 (set (match_operand:QI 1 "nonimmediate_operand" "")
10175 (not:QI (match_dup 3)))]
10176 "ix86_match_ccmode (insn, CCNOmode)"
10177 [(parallel [(set (match_dup 0)
10178 (match_op_dup 2 [(xor:QI (match_dup 3) (const_int -1))
10181 (xor:QI (match_dup 3) (const_int -1)))])]
10184 ;; Arithmetic shift instructions
10186 ;; DImode shifts are implemented using the i386 "shift double" opcode,
10187 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem". If the shift count
10188 ;; is variable, then the count is in %cl and the "imm" operand is dropped
10189 ;; from the assembler input.
10191 ;; This instruction shifts the target reg/mem as usual, but instead of
10192 ;; shifting in zeros, bits are shifted in from reg operand. If the insn
10193 ;; is a left shift double, bits are taken from the high order bits of
10194 ;; reg, else if the insn is a shift right double, bits are taken from the
10195 ;; low order bits of reg. So if %eax is "1234" and %edx is "5678",
10196 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
10198 ;; Since sh[lr]d does not change the `reg' operand, that is done
10199 ;; separately, making all shifts emit pairs of shift double and normal
10200 ;; shift. Since sh[lr]d does not shift more than 31 bits, and we wish to
10201 ;; support a 63 bit shift, each shift where the count is in a reg expands
10202 ;; to a pair of shifts, a branch, a shift by 32 and a label.
10204 ;; If the shift count is a constant, we need never emit more than one
10205 ;; shift pair, instead using moves and sign extension for counts greater
10208 (define_expand "ashlti3"
10209 [(parallel [(set (match_operand:TI 0 "register_operand" "")
10210 (ashift:TI (match_operand:TI 1 "register_operand" "")
10211 (match_operand:QI 2 "nonmemory_operand" "")))
10212 (clobber (reg:CC FLAGS_REG))])]
10215 if (! immediate_operand (operands[2], QImode))
10217 emit_insn (gen_ashlti3_1 (operands[0], operands[1], operands[2]));
10220 ix86_expand_binary_operator (ASHIFT, TImode, operands);
10224 (define_insn "ashlti3_1"
10225 [(set (match_operand:TI 0 "register_operand" "=r")
10226 (ashift:TI (match_operand:TI 1 "register_operand" "0")
10227 (match_operand:QI 2 "register_operand" "c")))
10228 (clobber (match_scratch:DI 3 "=&r"))
10229 (clobber (reg:CC FLAGS_REG))]
10232 [(set_attr "type" "multi")])
10234 (define_insn "*ashlti3_2"
10235 [(set (match_operand:TI 0 "register_operand" "=r")
10236 (ashift:TI (match_operand:TI 1 "register_operand" "0")
10237 (match_operand:QI 2 "immediate_operand" "O")))
10238 (clobber (reg:CC FLAGS_REG))]
10241 [(set_attr "type" "multi")])
10244 [(set (match_operand:TI 0 "register_operand" "")
10245 (ashift:TI (match_operand:TI 1 "nonmemory_operand" "")
10246 (match_operand:QI 2 "register_operand" "")))
10247 (clobber (match_scratch:DI 3 ""))
10248 (clobber (reg:CC FLAGS_REG))]
10249 "TARGET_64BIT && reload_completed"
10251 "ix86_split_ashl (operands, operands[3], TImode); DONE;")
10254 [(set (match_operand:TI 0 "register_operand" "")
10255 (ashift:TI (match_operand:TI 1 "register_operand" "")
10256 (match_operand:QI 2 "immediate_operand" "")))
10257 (clobber (reg:CC FLAGS_REG))]
10258 "TARGET_64BIT && reload_completed"
10260 "ix86_split_ashl (operands, NULL_RTX, TImode); DONE;")
10262 (define_insn "x86_64_shld"
10263 [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m,r*m")
10264 (ior:DI (ashift:DI (match_dup 0)
10265 (match_operand:QI 2 "nonmemory_operand" "J,c"))
10266 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r,r")
10267 (minus:QI (const_int 64) (match_dup 2)))))
10268 (clobber (reg:CC FLAGS_REG))]
10271 shld{q}\t{%2, %1, %0|%0, %1, %2}
10272 shld{q}\t{%s2%1, %0|%0, %1, %2}"
10273 [(set_attr "type" "ishift")
10274 (set_attr "prefix_0f" "1")
10275 (set_attr "mode" "DI")
10276 (set_attr "athlon_decode" "vector")])
10278 (define_expand "x86_64_shift_adj"
10279 [(set (reg:CCZ FLAGS_REG)
10280 (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
10283 (set (match_operand:DI 0 "register_operand" "")
10284 (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10285 (match_operand:DI 1 "register_operand" "")
10288 (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10289 (match_operand:DI 3 "register_operand" "r")
10294 (define_expand "ashldi3"
10295 [(set (match_operand:DI 0 "shiftdi_operand" "")
10296 (ashift:DI (match_operand:DI 1 "ashldi_input_operand" "")
10297 (match_operand:QI 2 "nonmemory_operand" "")))]
10299 "ix86_expand_binary_operator (ASHIFT, DImode, operands); DONE;")
10301 (define_insn "*ashldi3_1_rex64"
10302 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
10303 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0,l")
10304 (match_operand:QI 2 "nonmemory_operand" "cJ,M")))
10305 (clobber (reg:CC FLAGS_REG))]
10306 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10308 switch (get_attr_type (insn))
10311 gcc_assert (operands[2] == const1_rtx);
10312 gcc_assert (rtx_equal_p (operands[0], operands[1]));
10313 return "add{q}\t{%0, %0|%0, %0}";
10316 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
10317 gcc_assert ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) <= 3);
10318 operands[1] = gen_rtx_MULT (DImode, operands[1],
10319 GEN_INT (1 << INTVAL (operands[2])));
10320 return "lea{q}\t{%a1, %0|%0, %a1}";
10323 if (REG_P (operands[2]))
10324 return "sal{q}\t{%b2, %0|%0, %b2}";
10325 else if (operands[2] == const1_rtx
10326 && (TARGET_SHIFT1 || optimize_size))
10327 return "sal{q}\t%0";
10329 return "sal{q}\t{%2, %0|%0, %2}";
10332 [(set (attr "type")
10333 (cond [(eq_attr "alternative" "1")
10334 (const_string "lea")
10335 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10337 (match_operand 0 "register_operand" ""))
10338 (match_operand 2 "const1_operand" ""))
10339 (const_string "alu")
10341 (const_string "ishift")))
10342 (set_attr "mode" "DI")])
10344 ;; Convert lea to the lea pattern to avoid flags dependency.
10346 [(set (match_operand:DI 0 "register_operand" "")
10347 (ashift:DI (match_operand:DI 1 "index_register_operand" "")
10348 (match_operand:QI 2 "immediate_operand" "")))
10349 (clobber (reg:CC FLAGS_REG))]
10350 "TARGET_64BIT && reload_completed
10351 && true_regnum (operands[0]) != true_regnum (operands[1])"
10352 [(set (match_dup 0)
10353 (mult:DI (match_dup 1)
10355 "operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);")
10357 ;; This pattern can't accept a variable shift count, since shifts by
10358 ;; zero don't affect the flags. We assume that shifts by constant
10359 ;; zero are optimized away.
10360 (define_insn "*ashldi3_cmp_rex64"
10361 [(set (reg FLAGS_REG)
10363 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10364 (match_operand:QI 2 "immediate_operand" "e"))
10366 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10367 (ashift:DI (match_dup 1) (match_dup 2)))]
10368 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10369 && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10371 switch (get_attr_type (insn))
10374 gcc_assert (operands[2] == const1_rtx);
10375 return "add{q}\t{%0, %0|%0, %0}";
10378 if (REG_P (operands[2]))
10379 return "sal{q}\t{%b2, %0|%0, %b2}";
10380 else if (operands[2] == const1_rtx
10381 && (TARGET_SHIFT1 || optimize_size))
10382 return "sal{q}\t%0";
10384 return "sal{q}\t{%2, %0|%0, %2}";
10387 [(set (attr "type")
10388 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10390 (match_operand 0 "register_operand" ""))
10391 (match_operand 2 "const1_operand" ""))
10392 (const_string "alu")
10394 (const_string "ishift")))
10395 (set_attr "mode" "DI")])
10397 (define_insn "*ashldi3_1"
10398 [(set (match_operand:DI 0 "register_operand" "=&r,r")
10399 (ashift:DI (match_operand:DI 1 "reg_or_pm1_operand" "n,0")
10400 (match_operand:QI 2 "nonmemory_operand" "Jc,Jc")))
10401 (clobber (reg:CC FLAGS_REG))]
10404 [(set_attr "type" "multi")])
10406 ;; By default we don't ask for a scratch register, because when DImode
10407 ;; values are manipulated, registers are already at a premium. But if
10408 ;; we have one handy, we won't turn it away.
10410 [(match_scratch:SI 3 "r")
10411 (parallel [(set (match_operand:DI 0 "register_operand" "")
10412 (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
10413 (match_operand:QI 2 "nonmemory_operand" "")))
10414 (clobber (reg:CC FLAGS_REG))])
10416 "!TARGET_64BIT && TARGET_CMOVE"
10418 "ix86_split_ashl (operands, operands[3], DImode); DONE;")
10421 [(set (match_operand:DI 0 "register_operand" "")
10422 (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
10423 (match_operand:QI 2 "nonmemory_operand" "")))
10424 (clobber (reg:CC FLAGS_REG))]
10425 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
10426 ? flow2_completed : reload_completed)"
10428 "ix86_split_ashl (operands, NULL_RTX, DImode); DONE;")
10430 (define_insn "x86_shld_1"
10431 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
10432 (ior:SI (ashift:SI (match_dup 0)
10433 (match_operand:QI 2 "nonmemory_operand" "I,c"))
10434 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
10435 (minus:QI (const_int 32) (match_dup 2)))))
10436 (clobber (reg:CC FLAGS_REG))]
10439 shld{l}\t{%2, %1, %0|%0, %1, %2}
10440 shld{l}\t{%s2%1, %0|%0, %1, %2}"
10441 [(set_attr "type" "ishift")
10442 (set_attr "prefix_0f" "1")
10443 (set_attr "mode" "SI")
10444 (set_attr "pent_pair" "np")
10445 (set_attr "athlon_decode" "vector")])
10447 (define_expand "x86_shift_adj_1"
10448 [(set (reg:CCZ FLAGS_REG)
10449 (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
10452 (set (match_operand:SI 0 "register_operand" "")
10453 (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10454 (match_operand:SI 1 "register_operand" "")
10457 (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10458 (match_operand:SI 3 "register_operand" "r")
10463 (define_expand "x86_shift_adj_2"
10464 [(use (match_operand:SI 0 "register_operand" ""))
10465 (use (match_operand:SI 1 "register_operand" ""))
10466 (use (match_operand:QI 2 "register_operand" ""))]
10469 rtx label = gen_label_rtx ();
10472 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
10474 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
10475 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
10476 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
10477 gen_rtx_LABEL_REF (VOIDmode, label),
10479 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
10480 JUMP_LABEL (tmp) = label;
10482 emit_move_insn (operands[0], operands[1]);
10483 ix86_expand_clear (operands[1]);
10485 emit_label (label);
10486 LABEL_NUSES (label) = 1;
10491 (define_expand "ashlsi3"
10492 [(set (match_operand:SI 0 "nonimmediate_operand" "")
10493 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
10494 (match_operand:QI 2 "nonmemory_operand" "")))
10495 (clobber (reg:CC FLAGS_REG))]
10497 "ix86_expand_binary_operator (ASHIFT, SImode, operands); DONE;")
10499 (define_insn "*ashlsi3_1"
10500 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
10501 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l")
10502 (match_operand:QI 2 "nonmemory_operand" "cI,M")))
10503 (clobber (reg:CC FLAGS_REG))]
10504 "ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10506 switch (get_attr_type (insn))
10509 gcc_assert (operands[2] == const1_rtx);
10510 gcc_assert (rtx_equal_p (operands[0], operands[1]));
10511 return "add{l}\t{%0, %0|%0, %0}";
10517 if (REG_P (operands[2]))
10518 return "sal{l}\t{%b2, %0|%0, %b2}";
10519 else if (operands[2] == const1_rtx
10520 && (TARGET_SHIFT1 || optimize_size))
10521 return "sal{l}\t%0";
10523 return "sal{l}\t{%2, %0|%0, %2}";
10526 [(set (attr "type")
10527 (cond [(eq_attr "alternative" "1")
10528 (const_string "lea")
10529 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10531 (match_operand 0 "register_operand" ""))
10532 (match_operand 2 "const1_operand" ""))
10533 (const_string "alu")
10535 (const_string "ishift")))
10536 (set_attr "mode" "SI")])
10538 ;; Convert lea to the lea pattern to avoid flags dependency.
10540 [(set (match_operand 0 "register_operand" "")
10541 (ashift (match_operand 1 "index_register_operand" "")
10542 (match_operand:QI 2 "const_int_operand" "")))
10543 (clobber (reg:CC FLAGS_REG))]
10545 && true_regnum (operands[0]) != true_regnum (operands[1])
10546 && GET_MODE_SIZE (GET_MODE (operands[0])) <= 4"
10550 enum machine_mode mode = GET_MODE (operands[0]);
10552 if (GET_MODE_SIZE (mode) < 4)
10553 operands[0] = gen_lowpart (SImode, operands[0]);
10555 operands[1] = gen_lowpart (Pmode, operands[1]);
10556 operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
10558 pat = gen_rtx_MULT (Pmode, operands[1], operands[2]);
10559 if (Pmode != SImode)
10560 pat = gen_rtx_SUBREG (SImode, pat, 0);
10561 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
10565 ;; Rare case of shifting RSP is handled by generating move and shift
10567 [(set (match_operand 0 "register_operand" "")
10568 (ashift (match_operand 1 "register_operand" "")
10569 (match_operand:QI 2 "const_int_operand" "")))
10570 (clobber (reg:CC FLAGS_REG))]
10572 && true_regnum (operands[0]) != true_regnum (operands[1])"
10576 emit_move_insn (operands[1], operands[0]);
10577 pat = gen_rtx_SET (VOIDmode, operands[0],
10578 gen_rtx_ASHIFT (GET_MODE (operands[0]),
10579 operands[0], operands[2]));
10580 clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
10581 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, pat, clob)));
10585 (define_insn "*ashlsi3_1_zext"
10586 [(set (match_operand:DI 0 "register_operand" "=r,r")
10587 (zero_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "0,l")
10588 (match_operand:QI 2 "nonmemory_operand" "cI,M"))))
10589 (clobber (reg:CC FLAGS_REG))]
10590 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10592 switch (get_attr_type (insn))
10595 gcc_assert (operands[2] == const1_rtx);
10596 return "add{l}\t{%k0, %k0|%k0, %k0}";
10602 if (REG_P (operands[2]))
10603 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10604 else if (operands[2] == const1_rtx
10605 && (TARGET_SHIFT1 || optimize_size))
10606 return "sal{l}\t%k0";
10608 return "sal{l}\t{%2, %k0|%k0, %2}";
10611 [(set (attr "type")
10612 (cond [(eq_attr "alternative" "1")
10613 (const_string "lea")
10614 (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10616 (match_operand 2 "const1_operand" ""))
10617 (const_string "alu")
10619 (const_string "ishift")))
10620 (set_attr "mode" "SI")])
10622 ;; Convert lea to the lea pattern to avoid flags dependency.
10624 [(set (match_operand:DI 0 "register_operand" "")
10625 (zero_extend:DI (ashift (match_operand 1 "register_operand" "")
10626 (match_operand:QI 2 "const_int_operand" ""))))
10627 (clobber (reg:CC FLAGS_REG))]
10628 "TARGET_64BIT && reload_completed
10629 && true_regnum (operands[0]) != true_regnum (operands[1])"
10630 [(set (match_dup 0) (zero_extend:DI
10631 (subreg:SI (mult:SI (match_dup 1)
10632 (match_dup 2)) 0)))]
10634 operands[1] = gen_lowpart (Pmode, operands[1]);
10635 operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
10638 ;; This pattern can't accept a variable shift count, since shifts by
10639 ;; zero don't affect the flags. We assume that shifts by constant
10640 ;; zero are optimized away.
10641 (define_insn "*ashlsi3_cmp"
10642 [(set (reg FLAGS_REG)
10644 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
10645 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10647 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10648 (ashift:SI (match_dup 1) (match_dup 2)))]
10649 "ix86_match_ccmode (insn, CCGOCmode)
10650 && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10652 switch (get_attr_type (insn))
10655 gcc_assert (operands[2] == const1_rtx);
10656 return "add{l}\t{%0, %0|%0, %0}";
10659 if (REG_P (operands[2]))
10660 return "sal{l}\t{%b2, %0|%0, %b2}";
10661 else if (operands[2] == const1_rtx
10662 && (TARGET_SHIFT1 || optimize_size))
10663 return "sal{l}\t%0";
10665 return "sal{l}\t{%2, %0|%0, %2}";
10668 [(set (attr "type")
10669 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10671 (match_operand 0 "register_operand" ""))
10672 (match_operand 2 "const1_operand" ""))
10673 (const_string "alu")
10675 (const_string "ishift")))
10676 (set_attr "mode" "SI")])
10678 (define_insn "*ashlsi3_cmp_zext"
10679 [(set (reg FLAGS_REG)
10681 (ashift:SI (match_operand:SI 1 "register_operand" "0")
10682 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10684 (set (match_operand:DI 0 "register_operand" "=r")
10685 (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
10686 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10687 && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10689 switch (get_attr_type (insn))
10692 gcc_assert (operands[2] == const1_rtx);
10693 return "add{l}\t{%k0, %k0|%k0, %k0}";
10696 if (REG_P (operands[2]))
10697 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10698 else if (operands[2] == const1_rtx
10699 && (TARGET_SHIFT1 || optimize_size))
10700 return "sal{l}\t%k0";
10702 return "sal{l}\t{%2, %k0|%k0, %2}";
10705 [(set (attr "type")
10706 (cond [(and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10708 (match_operand 2 "const1_operand" ""))
10709 (const_string "alu")
10711 (const_string "ishift")))
10712 (set_attr "mode" "SI")])
10714 (define_expand "ashlhi3"
10715 [(set (match_operand:HI 0 "nonimmediate_operand" "")
10716 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "")
10717 (match_operand:QI 2 "nonmemory_operand" "")))
10718 (clobber (reg:CC FLAGS_REG))]
10719 "TARGET_HIMODE_MATH"
10720 "ix86_expand_binary_operator (ASHIFT, HImode, operands); DONE;")
10722 (define_insn "*ashlhi3_1_lea"
10723 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
10724 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
10725 (match_operand:QI 2 "nonmemory_operand" "cI,M")))
10726 (clobber (reg:CC FLAGS_REG))]
10727 "!TARGET_PARTIAL_REG_STALL
10728 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10730 switch (get_attr_type (insn))
10735 gcc_assert (operands[2] == const1_rtx);
10736 return "add{w}\t{%0, %0|%0, %0}";
10739 if (REG_P (operands[2]))
10740 return "sal{w}\t{%b2, %0|%0, %b2}";
10741 else if (operands[2] == const1_rtx
10742 && (TARGET_SHIFT1 || optimize_size))
10743 return "sal{w}\t%0";
10745 return "sal{w}\t{%2, %0|%0, %2}";
10748 [(set (attr "type")
10749 (cond [(eq_attr "alternative" "1")
10750 (const_string "lea")
10751 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10753 (match_operand 0 "register_operand" ""))
10754 (match_operand 2 "const1_operand" ""))
10755 (const_string "alu")
10757 (const_string "ishift")))
10758 (set_attr "mode" "HI,SI")])
10760 (define_insn "*ashlhi3_1"
10761 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10762 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
10763 (match_operand:QI 2 "nonmemory_operand" "cI")))
10764 (clobber (reg:CC FLAGS_REG))]
10765 "TARGET_PARTIAL_REG_STALL
10766 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10768 switch (get_attr_type (insn))
10771 gcc_assert (operands[2] == const1_rtx);
10772 return "add{w}\t{%0, %0|%0, %0}";
10775 if (REG_P (operands[2]))
10776 return "sal{w}\t{%b2, %0|%0, %b2}";
10777 else if (operands[2] == const1_rtx
10778 && (TARGET_SHIFT1 || optimize_size))
10779 return "sal{w}\t%0";
10781 return "sal{w}\t{%2, %0|%0, %2}";
10784 [(set (attr "type")
10785 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10787 (match_operand 0 "register_operand" ""))
10788 (match_operand 2 "const1_operand" ""))
10789 (const_string "alu")
10791 (const_string "ishift")))
10792 (set_attr "mode" "HI")])
10794 ;; This pattern can't accept a variable shift count, since shifts by
10795 ;; zero don't affect the flags. We assume that shifts by constant
10796 ;; zero are optimized away.
10797 (define_insn "*ashlhi3_cmp"
10798 [(set (reg FLAGS_REG)
10800 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
10801 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10803 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10804 (ashift:HI (match_dup 1) (match_dup 2)))]
10805 "ix86_match_ccmode (insn, CCGOCmode)
10806 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10808 switch (get_attr_type (insn))
10811 gcc_assert (operands[2] == const1_rtx);
10812 return "add{w}\t{%0, %0|%0, %0}";
10815 if (REG_P (operands[2]))
10816 return "sal{w}\t{%b2, %0|%0, %b2}";
10817 else if (operands[2] == const1_rtx
10818 && (TARGET_SHIFT1 || optimize_size))
10819 return "sal{w}\t%0";
10821 return "sal{w}\t{%2, %0|%0, %2}";
10824 [(set (attr "type")
10825 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10827 (match_operand 0 "register_operand" ""))
10828 (match_operand 2 "const1_operand" ""))
10829 (const_string "alu")
10831 (const_string "ishift")))
10832 (set_attr "mode" "HI")])
10834 (define_expand "ashlqi3"
10835 [(set (match_operand:QI 0 "nonimmediate_operand" "")
10836 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "")
10837 (match_operand:QI 2 "nonmemory_operand" "")))
10838 (clobber (reg:CC FLAGS_REG))]
10839 "TARGET_QIMODE_MATH"
10840 "ix86_expand_binary_operator (ASHIFT, QImode, operands); DONE;")
10842 ;; %%% Potential partial reg stall on alternative 2. What to do?
10844 (define_insn "*ashlqi3_1_lea"
10845 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r")
10846 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
10847 (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
10848 (clobber (reg:CC FLAGS_REG))]
10849 "!TARGET_PARTIAL_REG_STALL
10850 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10852 switch (get_attr_type (insn))
10857 gcc_assert (operands[2] == const1_rtx);
10858 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
10859 return "add{l}\t{%k0, %k0|%k0, %k0}";
10861 return "add{b}\t{%0, %0|%0, %0}";
10864 if (REG_P (operands[2]))
10866 if (get_attr_mode (insn) == MODE_SI)
10867 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10869 return "sal{b}\t{%b2, %0|%0, %b2}";
10871 else if (operands[2] == const1_rtx
10872 && (TARGET_SHIFT1 || optimize_size))
10874 if (get_attr_mode (insn) == MODE_SI)
10875 return "sal{l}\t%0";
10877 return "sal{b}\t%0";
10881 if (get_attr_mode (insn) == MODE_SI)
10882 return "sal{l}\t{%2, %k0|%k0, %2}";
10884 return "sal{b}\t{%2, %0|%0, %2}";
10888 [(set (attr "type")
10889 (cond [(eq_attr "alternative" "2")
10890 (const_string "lea")
10891 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10893 (match_operand 0 "register_operand" ""))
10894 (match_operand 2 "const1_operand" ""))
10895 (const_string "alu")
10897 (const_string "ishift")))
10898 (set_attr "mode" "QI,SI,SI")])
10900 (define_insn "*ashlqi3_1"
10901 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10902 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
10903 (match_operand:QI 2 "nonmemory_operand" "cI,cI")))
10904 (clobber (reg:CC FLAGS_REG))]
10905 "TARGET_PARTIAL_REG_STALL
10906 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10908 switch (get_attr_type (insn))
10911 gcc_assert (operands[2] == const1_rtx);
10912 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
10913 return "add{l}\t{%k0, %k0|%k0, %k0}";
10915 return "add{b}\t{%0, %0|%0, %0}";
10918 if (REG_P (operands[2]))
10920 if (get_attr_mode (insn) == MODE_SI)
10921 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10923 return "sal{b}\t{%b2, %0|%0, %b2}";
10925 else if (operands[2] == const1_rtx
10926 && (TARGET_SHIFT1 || optimize_size))
10928 if (get_attr_mode (insn) == MODE_SI)
10929 return "sal{l}\t%0";
10931 return "sal{b}\t%0";
10935 if (get_attr_mode (insn) == MODE_SI)
10936 return "sal{l}\t{%2, %k0|%k0, %2}";
10938 return "sal{b}\t{%2, %0|%0, %2}";
10942 [(set (attr "type")
10943 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10945 (match_operand 0 "register_operand" ""))
10946 (match_operand 2 "const1_operand" ""))
10947 (const_string "alu")
10949 (const_string "ishift")))
10950 (set_attr "mode" "QI,SI")])
10952 ;; This pattern can't accept a variable shift count, since shifts by
10953 ;; zero don't affect the flags. We assume that shifts by constant
10954 ;; zero are optimized away.
10955 (define_insn "*ashlqi3_cmp"
10956 [(set (reg FLAGS_REG)
10958 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
10959 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10961 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10962 (ashift:QI (match_dup 1) (match_dup 2)))]
10963 "ix86_match_ccmode (insn, CCGOCmode)
10964 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10966 switch (get_attr_type (insn))
10969 gcc_assert (operands[2] == const1_rtx);
10970 return "add{b}\t{%0, %0|%0, %0}";
10973 if (REG_P (operands[2]))
10974 return "sal{b}\t{%b2, %0|%0, %b2}";
10975 else if (operands[2] == const1_rtx
10976 && (TARGET_SHIFT1 || optimize_size))
10977 return "sal{b}\t%0";
10979 return "sal{b}\t{%2, %0|%0, %2}";
10982 [(set (attr "type")
10983 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10985 (match_operand 0 "register_operand" ""))
10986 (match_operand 2 "const1_operand" ""))
10987 (const_string "alu")
10989 (const_string "ishift")))
10990 (set_attr "mode" "QI")])
10992 ;; See comment above `ashldi3' about how this works.
10994 (define_expand "ashrti3"
10995 [(parallel [(set (match_operand:TI 0 "register_operand" "")
10996 (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
10997 (match_operand:QI 2 "nonmemory_operand" "")))
10998 (clobber (reg:CC FLAGS_REG))])]
11001 if (! immediate_operand (operands[2], QImode))
11003 emit_insn (gen_ashrti3_1 (operands[0], operands[1], operands[2]));
11006 ix86_expand_binary_operator (ASHIFTRT, TImode, operands);
11010 (define_insn "ashrti3_1"
11011 [(set (match_operand:TI 0 "register_operand" "=r")
11012 (ashiftrt:TI (match_operand:TI 1 "register_operand" "0")
11013 (match_operand:QI 2 "register_operand" "c")))
11014 (clobber (match_scratch:DI 3 "=&r"))
11015 (clobber (reg:CC FLAGS_REG))]
11018 [(set_attr "type" "multi")])
11020 (define_insn "*ashrti3_2"
11021 [(set (match_operand:TI 0 "register_operand" "=r")
11022 (ashiftrt:TI (match_operand:TI 1 "register_operand" "0")
11023 (match_operand:QI 2 "immediate_operand" "O")))
11024 (clobber (reg:CC FLAGS_REG))]
11027 [(set_attr "type" "multi")])
11030 [(set (match_operand:TI 0 "register_operand" "")
11031 (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
11032 (match_operand:QI 2 "register_operand" "")))
11033 (clobber (match_scratch:DI 3 ""))
11034 (clobber (reg:CC FLAGS_REG))]
11035 "TARGET_64BIT && reload_completed"
11037 "ix86_split_ashr (operands, operands[3], TImode); DONE;")
11040 [(set (match_operand:TI 0 "register_operand" "")
11041 (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
11042 (match_operand:QI 2 "immediate_operand" "")))
11043 (clobber (reg:CC FLAGS_REG))]
11044 "TARGET_64BIT && reload_completed"
11046 "ix86_split_ashr (operands, NULL_RTX, TImode); DONE;")
11048 (define_insn "x86_64_shrd"
11049 [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m,r*m")
11050 (ior:DI (ashiftrt:DI (match_dup 0)
11051 (match_operand:QI 2 "nonmemory_operand" "J,c"))
11052 (ashift:DI (match_operand:DI 1 "register_operand" "r,r")
11053 (minus:QI (const_int 64) (match_dup 2)))))
11054 (clobber (reg:CC FLAGS_REG))]
11057 shrd{q}\t{%2, %1, %0|%0, %1, %2}
11058 shrd{q}\t{%s2%1, %0|%0, %1, %2}"
11059 [(set_attr "type" "ishift")
11060 (set_attr "prefix_0f" "1")
11061 (set_attr "mode" "DI")
11062 (set_attr "athlon_decode" "vector")])
11064 (define_expand "ashrdi3"
11065 [(set (match_operand:DI 0 "shiftdi_operand" "")
11066 (ashiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
11067 (match_operand:QI 2 "nonmemory_operand" "")))]
11069 "ix86_expand_binary_operator (ASHIFTRT, DImode, operands); DONE;")
11071 (define_insn "*ashrdi3_63_rex64"
11072 [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
11073 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
11074 (match_operand:DI 2 "const_int_operand" "i,i")))
11075 (clobber (reg:CC FLAGS_REG))]
11076 "TARGET_64BIT && INTVAL (operands[2]) == 63
11077 && (TARGET_USE_CLTD || optimize_size)
11078 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11081 sar{q}\t{%2, %0|%0, %2}"
11082 [(set_attr "type" "imovx,ishift")
11083 (set_attr "prefix_0f" "0,*")
11084 (set_attr "length_immediate" "0,*")
11085 (set_attr "modrm" "0,1")
11086 (set_attr "mode" "DI")])
11088 (define_insn "*ashrdi3_1_one_bit_rex64"
11089 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11090 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11091 (match_operand:QI 2 "const1_operand" "")))
11092 (clobber (reg:CC FLAGS_REG))]
11093 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)
11094 && (TARGET_SHIFT1 || optimize_size)"
11096 [(set_attr "type" "ishift")
11097 (set (attr "length")
11098 (if_then_else (match_operand:DI 0 "register_operand" "")
11100 (const_string "*")))])
11102 (define_insn "*ashrdi3_1_rex64"
11103 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11104 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11105 (match_operand:QI 2 "nonmemory_operand" "J,c")))
11106 (clobber (reg:CC FLAGS_REG))]
11107 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11109 sar{q}\t{%2, %0|%0, %2}
11110 sar{q}\t{%b2, %0|%0, %b2}"
11111 [(set_attr "type" "ishift")
11112 (set_attr "mode" "DI")])
11114 ;; This pattern can't accept a variable shift count, since shifts by
11115 ;; zero don't affect the flags. We assume that shifts by constant
11116 ;; zero are optimized away.
11117 (define_insn "*ashrdi3_one_bit_cmp_rex64"
11118 [(set (reg FLAGS_REG)
11120 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11121 (match_operand:QI 2 "const1_operand" ""))
11123 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11124 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
11125 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11126 && (TARGET_SHIFT1 || optimize_size)
11127 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11129 [(set_attr "type" "ishift")
11130 (set (attr "length")
11131 (if_then_else (match_operand:DI 0 "register_operand" "")
11133 (const_string "*")))])
11135 ;; This pattern can't accept a variable shift count, since shifts by
11136 ;; zero don't affect the flags. We assume that shifts by constant
11137 ;; zero are optimized away.
11138 (define_insn "*ashrdi3_cmp_rex64"
11139 [(set (reg FLAGS_REG)
11141 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11142 (match_operand:QI 2 "const_int_operand" "n"))
11144 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11145 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
11146 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11147 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11148 "sar{q}\t{%2, %0|%0, %2}"
11149 [(set_attr "type" "ishift")
11150 (set_attr "mode" "DI")])
11152 (define_insn "*ashrdi3_1"
11153 [(set (match_operand:DI 0 "register_operand" "=r")
11154 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
11155 (match_operand:QI 2 "nonmemory_operand" "Jc")))
11156 (clobber (reg:CC FLAGS_REG))]
11159 [(set_attr "type" "multi")])
11161 ;; By default we don't ask for a scratch register, because when DImode
11162 ;; values are manipulated, registers are already at a premium. But if
11163 ;; we have one handy, we won't turn it away.
11165 [(match_scratch:SI 3 "r")
11166 (parallel [(set (match_operand:DI 0 "register_operand" "")
11167 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
11168 (match_operand:QI 2 "nonmemory_operand" "")))
11169 (clobber (reg:CC FLAGS_REG))])
11171 "!TARGET_64BIT && TARGET_CMOVE"
11173 "ix86_split_ashr (operands, operands[3], DImode); DONE;")
11176 [(set (match_operand:DI 0 "register_operand" "")
11177 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
11178 (match_operand:QI 2 "nonmemory_operand" "")))
11179 (clobber (reg:CC FLAGS_REG))]
11180 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
11181 ? flow2_completed : reload_completed)"
11183 "ix86_split_ashr (operands, NULL_RTX, DImode); DONE;")
11185 (define_insn "x86_shrd_1"
11186 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
11187 (ior:SI (ashiftrt:SI (match_dup 0)
11188 (match_operand:QI 2 "nonmemory_operand" "I,c"))
11189 (ashift:SI (match_operand:SI 1 "register_operand" "r,r")
11190 (minus:QI (const_int 32) (match_dup 2)))))
11191 (clobber (reg:CC FLAGS_REG))]
11194 shrd{l}\t{%2, %1, %0|%0, %1, %2}
11195 shrd{l}\t{%s2%1, %0|%0, %1, %2}"
11196 [(set_attr "type" "ishift")
11197 (set_attr "prefix_0f" "1")
11198 (set_attr "pent_pair" "np")
11199 (set_attr "mode" "SI")])
11201 (define_expand "x86_shift_adj_3"
11202 [(use (match_operand:SI 0 "register_operand" ""))
11203 (use (match_operand:SI 1 "register_operand" ""))
11204 (use (match_operand:QI 2 "register_operand" ""))]
11207 rtx label = gen_label_rtx ();
11210 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
11212 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
11213 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
11214 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
11215 gen_rtx_LABEL_REF (VOIDmode, label),
11217 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
11218 JUMP_LABEL (tmp) = label;
11220 emit_move_insn (operands[0], operands[1]);
11221 emit_insn (gen_ashrsi3_31 (operands[1], operands[1], GEN_INT (31)));
11223 emit_label (label);
11224 LABEL_NUSES (label) = 1;
11229 (define_insn "ashrsi3_31"
11230 [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
11231 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
11232 (match_operand:SI 2 "const_int_operand" "i,i")))
11233 (clobber (reg:CC FLAGS_REG))]
11234 "INTVAL (operands[2]) == 31 && (TARGET_USE_CLTD || optimize_size)
11235 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11238 sar{l}\t{%2, %0|%0, %2}"
11239 [(set_attr "type" "imovx,ishift")
11240 (set_attr "prefix_0f" "0,*")
11241 (set_attr "length_immediate" "0,*")
11242 (set_attr "modrm" "0,1")
11243 (set_attr "mode" "SI")])
11245 (define_insn "*ashrsi3_31_zext"
11246 [(set (match_operand:DI 0 "register_operand" "=*d,r")
11247 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
11248 (match_operand:SI 2 "const_int_operand" "i,i"))))
11249 (clobber (reg:CC FLAGS_REG))]
11250 "TARGET_64BIT && (TARGET_USE_CLTD || optimize_size)
11251 && INTVAL (operands[2]) == 31
11252 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11255 sar{l}\t{%2, %k0|%k0, %2}"
11256 [(set_attr "type" "imovx,ishift")
11257 (set_attr "prefix_0f" "0,*")
11258 (set_attr "length_immediate" "0,*")
11259 (set_attr "modrm" "0,1")
11260 (set_attr "mode" "SI")])
11262 (define_expand "ashrsi3"
11263 [(set (match_operand:SI 0 "nonimmediate_operand" "")
11264 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
11265 (match_operand:QI 2 "nonmemory_operand" "")))
11266 (clobber (reg:CC FLAGS_REG))]
11268 "ix86_expand_binary_operator (ASHIFTRT, SImode, operands); DONE;")
11270 (define_insn "*ashrsi3_1_one_bit"
11271 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11272 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11273 (match_operand:QI 2 "const1_operand" "")))
11274 (clobber (reg:CC FLAGS_REG))]
11275 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
11276 && (TARGET_SHIFT1 || optimize_size)"
11278 [(set_attr "type" "ishift")
11279 (set (attr "length")
11280 (if_then_else (match_operand:SI 0 "register_operand" "")
11282 (const_string "*")))])
11284 (define_insn "*ashrsi3_1_one_bit_zext"
11285 [(set (match_operand:DI 0 "register_operand" "=r")
11286 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11287 (match_operand:QI 2 "const1_operand" ""))))
11288 (clobber (reg:CC FLAGS_REG))]
11289 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
11290 && (TARGET_SHIFT1 || optimize_size)"
11292 [(set_attr "type" "ishift")
11293 (set_attr "length" "2")])
11295 (define_insn "*ashrsi3_1"
11296 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11297 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11298 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11299 (clobber (reg:CC FLAGS_REG))]
11300 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11302 sar{l}\t{%2, %0|%0, %2}
11303 sar{l}\t{%b2, %0|%0, %b2}"
11304 [(set_attr "type" "ishift")
11305 (set_attr "mode" "SI")])
11307 (define_insn "*ashrsi3_1_zext"
11308 [(set (match_operand:DI 0 "register_operand" "=r,r")
11309 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0")
11310 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11311 (clobber (reg:CC FLAGS_REG))]
11312 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11314 sar{l}\t{%2, %k0|%k0, %2}
11315 sar{l}\t{%b2, %k0|%k0, %b2}"
11316 [(set_attr "type" "ishift")
11317 (set_attr "mode" "SI")])
11319 ;; This pattern can't accept a variable shift count, since shifts by
11320 ;; zero don't affect the flags. We assume that shifts by constant
11321 ;; zero are optimized away.
11322 (define_insn "*ashrsi3_one_bit_cmp"
11323 [(set (reg FLAGS_REG)
11325 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11326 (match_operand:QI 2 "const1_operand" ""))
11328 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11329 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
11330 "ix86_match_ccmode (insn, CCGOCmode)
11331 && (TARGET_SHIFT1 || optimize_size)
11332 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11334 [(set_attr "type" "ishift")
11335 (set (attr "length")
11336 (if_then_else (match_operand:SI 0 "register_operand" "")
11338 (const_string "*")))])
11340 (define_insn "*ashrsi3_one_bit_cmp_zext"
11341 [(set (reg FLAGS_REG)
11343 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11344 (match_operand:QI 2 "const1_operand" ""))
11346 (set (match_operand:DI 0 "register_operand" "=r")
11347 (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
11348 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
11349 && (TARGET_SHIFT1 || optimize_size)
11350 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11352 [(set_attr "type" "ishift")
11353 (set_attr "length" "2")])
11355 ;; This pattern can't accept a variable shift count, since shifts by
11356 ;; zero don't affect the flags. We assume that shifts by constant
11357 ;; zero are optimized away.
11358 (define_insn "*ashrsi3_cmp"
11359 [(set (reg FLAGS_REG)
11361 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11362 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11364 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11365 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
11366 "ix86_match_ccmode (insn, CCGOCmode)
11367 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11368 "sar{l}\t{%2, %0|%0, %2}"
11369 [(set_attr "type" "ishift")
11370 (set_attr "mode" "SI")])
11372 (define_insn "*ashrsi3_cmp_zext"
11373 [(set (reg FLAGS_REG)
11375 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11376 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11378 (set (match_operand:DI 0 "register_operand" "=r")
11379 (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
11380 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11381 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11382 "sar{l}\t{%2, %k0|%k0, %2}"
11383 [(set_attr "type" "ishift")
11384 (set_attr "mode" "SI")])
11386 (define_expand "ashrhi3"
11387 [(set (match_operand:HI 0 "nonimmediate_operand" "")
11388 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
11389 (match_operand:QI 2 "nonmemory_operand" "")))
11390 (clobber (reg:CC FLAGS_REG))]
11391 "TARGET_HIMODE_MATH"
11392 "ix86_expand_binary_operator (ASHIFTRT, HImode, operands); DONE;")
11394 (define_insn "*ashrhi3_1_one_bit"
11395 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11396 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11397 (match_operand:QI 2 "const1_operand" "")))
11398 (clobber (reg:CC FLAGS_REG))]
11399 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)
11400 && (TARGET_SHIFT1 || optimize_size)"
11402 [(set_attr "type" "ishift")
11403 (set (attr "length")
11404 (if_then_else (match_operand 0 "register_operand" "")
11406 (const_string "*")))])
11408 (define_insn "*ashrhi3_1"
11409 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11410 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11411 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11412 (clobber (reg:CC FLAGS_REG))]
11413 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11415 sar{w}\t{%2, %0|%0, %2}
11416 sar{w}\t{%b2, %0|%0, %b2}"
11417 [(set_attr "type" "ishift")
11418 (set_attr "mode" "HI")])
11420 ;; This pattern can't accept a variable shift count, since shifts by
11421 ;; zero don't affect the flags. We assume that shifts by constant
11422 ;; zero are optimized away.
11423 (define_insn "*ashrhi3_one_bit_cmp"
11424 [(set (reg FLAGS_REG)
11426 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11427 (match_operand:QI 2 "const1_operand" ""))
11429 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11430 (ashiftrt:HI (match_dup 1) (match_dup 2)))]
11431 "ix86_match_ccmode (insn, CCGOCmode)
11432 && (TARGET_SHIFT1 || optimize_size)
11433 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11435 [(set_attr "type" "ishift")
11436 (set (attr "length")
11437 (if_then_else (match_operand 0 "register_operand" "")
11439 (const_string "*")))])
11441 ;; This pattern can't accept a variable shift count, since shifts by
11442 ;; zero don't affect the flags. We assume that shifts by constant
11443 ;; zero are optimized away.
11444 (define_insn "*ashrhi3_cmp"
11445 [(set (reg FLAGS_REG)
11447 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11448 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11450 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11451 (ashiftrt:HI (match_dup 1) (match_dup 2)))]
11452 "ix86_match_ccmode (insn, CCGOCmode)
11453 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11454 "sar{w}\t{%2, %0|%0, %2}"
11455 [(set_attr "type" "ishift")
11456 (set_attr "mode" "HI")])
11458 (define_expand "ashrqi3"
11459 [(set (match_operand:QI 0 "nonimmediate_operand" "")
11460 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
11461 (match_operand:QI 2 "nonmemory_operand" "")))
11462 (clobber (reg:CC FLAGS_REG))]
11463 "TARGET_QIMODE_MATH"
11464 "ix86_expand_binary_operator (ASHIFTRT, QImode, operands); DONE;")
11466 (define_insn "*ashrqi3_1_one_bit"
11467 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11468 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11469 (match_operand:QI 2 "const1_operand" "")))
11470 (clobber (reg:CC FLAGS_REG))]
11471 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
11472 && (TARGET_SHIFT1 || optimize_size)"
11474 [(set_attr "type" "ishift")
11475 (set (attr "length")
11476 (if_then_else (match_operand 0 "register_operand" "")
11478 (const_string "*")))])
11480 (define_insn "*ashrqi3_1_one_bit_slp"
11481 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11482 (ashiftrt:QI (match_dup 0)
11483 (match_operand:QI 1 "const1_operand" "")))
11484 (clobber (reg:CC FLAGS_REG))]
11485 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
11486 && (! TARGET_PARTIAL_REG_STALL || optimize_size)
11487 && (TARGET_SHIFT1 || optimize_size)"
11489 [(set_attr "type" "ishift1")
11490 (set (attr "length")
11491 (if_then_else (match_operand 0 "register_operand" "")
11493 (const_string "*")))])
11495 (define_insn "*ashrqi3_1"
11496 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11497 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11498 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11499 (clobber (reg:CC FLAGS_REG))]
11500 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11502 sar{b}\t{%2, %0|%0, %2}
11503 sar{b}\t{%b2, %0|%0, %b2}"
11504 [(set_attr "type" "ishift")
11505 (set_attr "mode" "QI")])
11507 (define_insn "*ashrqi3_1_slp"
11508 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11509 (ashiftrt:QI (match_dup 0)
11510 (match_operand:QI 1 "nonmemory_operand" "I,c")))
11511 (clobber (reg:CC FLAGS_REG))]
11512 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11513 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11515 sar{b}\t{%1, %0|%0, %1}
11516 sar{b}\t{%b1, %0|%0, %b1}"
11517 [(set_attr "type" "ishift1")
11518 (set_attr "mode" "QI")])
11520 ;; This pattern can't accept a variable shift count, since shifts by
11521 ;; zero don't affect the flags. We assume that shifts by constant
11522 ;; zero are optimized away.
11523 (define_insn "*ashrqi3_one_bit_cmp"
11524 [(set (reg FLAGS_REG)
11526 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11527 (match_operand:QI 2 "const1_operand" "I"))
11529 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11530 (ashiftrt:QI (match_dup 1) (match_dup 2)))]
11531 "ix86_match_ccmode (insn, CCGOCmode)
11532 && (TARGET_SHIFT1 || optimize_size)
11533 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11535 [(set_attr "type" "ishift")
11536 (set (attr "length")
11537 (if_then_else (match_operand 0 "register_operand" "")
11539 (const_string "*")))])
11541 ;; This pattern can't accept a variable shift count, since shifts by
11542 ;; zero don't affect the flags. We assume that shifts by constant
11543 ;; zero are optimized away.
11544 (define_insn "*ashrqi3_cmp"
11545 [(set (reg FLAGS_REG)
11547 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11548 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11550 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11551 (ashiftrt:QI (match_dup 1) (match_dup 2)))]
11552 "ix86_match_ccmode (insn, CCGOCmode)
11553 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11554 "sar{b}\t{%2, %0|%0, %2}"
11555 [(set_attr "type" "ishift")
11556 (set_attr "mode" "QI")])
11558 ;; Logical shift instructions
11560 ;; See comment above `ashldi3' about how this works.
11562 (define_expand "lshrti3"
11563 [(parallel [(set (match_operand:TI 0 "register_operand" "")
11564 (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
11565 (match_operand:QI 2 "nonmemory_operand" "")))
11566 (clobber (reg:CC FLAGS_REG))])]
11569 if (! immediate_operand (operands[2], QImode))
11571 emit_insn (gen_lshrti3_1 (operands[0], operands[1], operands[2]));
11574 ix86_expand_binary_operator (LSHIFTRT, TImode, operands);
11578 (define_insn "lshrti3_1"
11579 [(set (match_operand:TI 0 "register_operand" "=r")
11580 (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
11581 (match_operand:QI 2 "register_operand" "c")))
11582 (clobber (match_scratch:DI 3 "=&r"))
11583 (clobber (reg:CC FLAGS_REG))]
11586 [(set_attr "type" "multi")])
11588 (define_insn "*lshrti3_2"
11589 [(set (match_operand:TI 0 "register_operand" "=r")
11590 (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
11591 (match_operand:QI 2 "immediate_operand" "O")))
11592 (clobber (reg:CC FLAGS_REG))]
11595 [(set_attr "type" "multi")])
11598 [(set (match_operand:TI 0 "register_operand" "")
11599 (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
11600 (match_operand:QI 2 "register_operand" "")))
11601 (clobber (match_scratch:DI 3 ""))
11602 (clobber (reg:CC FLAGS_REG))]
11603 "TARGET_64BIT && reload_completed"
11605 "ix86_split_lshr (operands, operands[3], TImode); DONE;")
11608 [(set (match_operand:TI 0 "register_operand" "")
11609 (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
11610 (match_operand:QI 2 "immediate_operand" "")))
11611 (clobber (reg:CC FLAGS_REG))]
11612 "TARGET_64BIT && reload_completed"
11614 "ix86_split_lshr (operands, NULL_RTX, TImode); DONE;")
11616 (define_expand "lshrdi3"
11617 [(set (match_operand:DI 0 "shiftdi_operand" "")
11618 (lshiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
11619 (match_operand:QI 2 "nonmemory_operand" "")))]
11621 "ix86_expand_binary_operator (LSHIFTRT, DImode, operands); DONE;")
11623 (define_insn "*lshrdi3_1_one_bit_rex64"
11624 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11625 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11626 (match_operand:QI 2 "const1_operand" "")))
11627 (clobber (reg:CC FLAGS_REG))]
11628 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11629 && (TARGET_SHIFT1 || optimize_size)"
11631 [(set_attr "type" "ishift")
11632 (set (attr "length")
11633 (if_then_else (match_operand:DI 0 "register_operand" "")
11635 (const_string "*")))])
11637 (define_insn "*lshrdi3_1_rex64"
11638 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11639 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11640 (match_operand:QI 2 "nonmemory_operand" "J,c")))
11641 (clobber (reg:CC FLAGS_REG))]
11642 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11644 shr{q}\t{%2, %0|%0, %2}
11645 shr{q}\t{%b2, %0|%0, %b2}"
11646 [(set_attr "type" "ishift")
11647 (set_attr "mode" "DI")])
11649 ;; This pattern can't accept a variable shift count, since shifts by
11650 ;; zero don't affect the flags. We assume that shifts by constant
11651 ;; zero are optimized away.
11652 (define_insn "*lshrdi3_cmp_one_bit_rex64"
11653 [(set (reg FLAGS_REG)
11655 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11656 (match_operand:QI 2 "const1_operand" ""))
11658 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11659 (lshiftrt:DI (match_dup 1) (match_dup 2)))]
11660 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11661 && (TARGET_SHIFT1 || optimize_size)
11662 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11664 [(set_attr "type" "ishift")
11665 (set (attr "length")
11666 (if_then_else (match_operand:DI 0 "register_operand" "")
11668 (const_string "*")))])
11670 ;; This pattern can't accept a variable shift count, since shifts by
11671 ;; zero don't affect the flags. We assume that shifts by constant
11672 ;; zero are optimized away.
11673 (define_insn "*lshrdi3_cmp_rex64"
11674 [(set (reg FLAGS_REG)
11676 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11677 (match_operand:QI 2 "const_int_operand" "e"))
11679 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11680 (lshiftrt:DI (match_dup 1) (match_dup 2)))]
11681 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11682 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11683 "shr{q}\t{%2, %0|%0, %2}"
11684 [(set_attr "type" "ishift")
11685 (set_attr "mode" "DI")])
11687 (define_insn "*lshrdi3_1"
11688 [(set (match_operand:DI 0 "register_operand" "=r")
11689 (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
11690 (match_operand:QI 2 "nonmemory_operand" "Jc")))
11691 (clobber (reg:CC FLAGS_REG))]
11694 [(set_attr "type" "multi")])
11696 ;; By default we don't ask for a scratch register, because when DImode
11697 ;; values are manipulated, registers are already at a premium. But if
11698 ;; we have one handy, we won't turn it away.
11700 [(match_scratch:SI 3 "r")
11701 (parallel [(set (match_operand:DI 0 "register_operand" "")
11702 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
11703 (match_operand:QI 2 "nonmemory_operand" "")))
11704 (clobber (reg:CC FLAGS_REG))])
11706 "!TARGET_64BIT && TARGET_CMOVE"
11708 "ix86_split_lshr (operands, operands[3], DImode); DONE;")
11711 [(set (match_operand:DI 0 "register_operand" "")
11712 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
11713 (match_operand:QI 2 "nonmemory_operand" "")))
11714 (clobber (reg:CC FLAGS_REG))]
11715 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
11716 ? flow2_completed : reload_completed)"
11718 "ix86_split_lshr (operands, NULL_RTX, DImode); DONE;")
11720 (define_expand "lshrsi3"
11721 [(set (match_operand:SI 0 "nonimmediate_operand" "")
11722 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
11723 (match_operand:QI 2 "nonmemory_operand" "")))
11724 (clobber (reg:CC FLAGS_REG))]
11726 "ix86_expand_binary_operator (LSHIFTRT, SImode, operands); DONE;")
11728 (define_insn "*lshrsi3_1_one_bit"
11729 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11730 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11731 (match_operand:QI 2 "const1_operand" "")))
11732 (clobber (reg:CC FLAGS_REG))]
11733 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11734 && (TARGET_SHIFT1 || optimize_size)"
11736 [(set_attr "type" "ishift")
11737 (set (attr "length")
11738 (if_then_else (match_operand:SI 0 "register_operand" "")
11740 (const_string "*")))])
11742 (define_insn "*lshrsi3_1_one_bit_zext"
11743 [(set (match_operand:DI 0 "register_operand" "=r")
11744 (lshiftrt:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "0"))
11745 (match_operand:QI 2 "const1_operand" "")))
11746 (clobber (reg:CC FLAGS_REG))]
11747 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11748 && (TARGET_SHIFT1 || optimize_size)"
11750 [(set_attr "type" "ishift")
11751 (set_attr "length" "2")])
11753 (define_insn "*lshrsi3_1"
11754 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11755 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11756 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11757 (clobber (reg:CC FLAGS_REG))]
11758 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11760 shr{l}\t{%2, %0|%0, %2}
11761 shr{l}\t{%b2, %0|%0, %b2}"
11762 [(set_attr "type" "ishift")
11763 (set_attr "mode" "SI")])
11765 (define_insn "*lshrsi3_1_zext"
11766 [(set (match_operand:DI 0 "register_operand" "=r,r")
11768 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11769 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11770 (clobber (reg:CC FLAGS_REG))]
11771 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11773 shr{l}\t{%2, %k0|%k0, %2}
11774 shr{l}\t{%b2, %k0|%k0, %b2}"
11775 [(set_attr "type" "ishift")
11776 (set_attr "mode" "SI")])
11778 ;; This pattern can't accept a variable shift count, since shifts by
11779 ;; zero don't affect the flags. We assume that shifts by constant
11780 ;; zero are optimized away.
11781 (define_insn "*lshrsi3_one_bit_cmp"
11782 [(set (reg FLAGS_REG)
11784 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11785 (match_operand:QI 2 "const1_operand" ""))
11787 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11788 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
11789 "ix86_match_ccmode (insn, CCGOCmode)
11790 && (TARGET_SHIFT1 || optimize_size)
11791 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11793 [(set_attr "type" "ishift")
11794 (set (attr "length")
11795 (if_then_else (match_operand:SI 0 "register_operand" "")
11797 (const_string "*")))])
11799 (define_insn "*lshrsi3_cmp_one_bit_zext"
11800 [(set (reg FLAGS_REG)
11802 (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
11803 (match_operand:QI 2 "const1_operand" ""))
11805 (set (match_operand:DI 0 "register_operand" "=r")
11806 (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
11807 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11808 && (TARGET_SHIFT1 || optimize_size)
11809 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11811 [(set_attr "type" "ishift")
11812 (set_attr "length" "2")])
11814 ;; This pattern can't accept a variable shift count, since shifts by
11815 ;; zero don't affect the flags. We assume that shifts by constant
11816 ;; zero are optimized away.
11817 (define_insn "*lshrsi3_cmp"
11818 [(set (reg FLAGS_REG)
11820 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11821 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11823 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11824 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
11825 "ix86_match_ccmode (insn, CCGOCmode)
11826 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11827 "shr{l}\t{%2, %0|%0, %2}"
11828 [(set_attr "type" "ishift")
11829 (set_attr "mode" "SI")])
11831 (define_insn "*lshrsi3_cmp_zext"
11832 [(set (reg FLAGS_REG)
11834 (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
11835 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11837 (set (match_operand:DI 0 "register_operand" "=r")
11838 (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
11839 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11840 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11841 "shr{l}\t{%2, %k0|%k0, %2}"
11842 [(set_attr "type" "ishift")
11843 (set_attr "mode" "SI")])
11845 (define_expand "lshrhi3"
11846 [(set (match_operand:HI 0 "nonimmediate_operand" "")
11847 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
11848 (match_operand:QI 2 "nonmemory_operand" "")))
11849 (clobber (reg:CC FLAGS_REG))]
11850 "TARGET_HIMODE_MATH"
11851 "ix86_expand_binary_operator (LSHIFTRT, HImode, operands); DONE;")
11853 (define_insn "*lshrhi3_1_one_bit"
11854 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11855 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11856 (match_operand:QI 2 "const1_operand" "")))
11857 (clobber (reg:CC FLAGS_REG))]
11858 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11859 && (TARGET_SHIFT1 || optimize_size)"
11861 [(set_attr "type" "ishift")
11862 (set (attr "length")
11863 (if_then_else (match_operand 0 "register_operand" "")
11865 (const_string "*")))])
11867 (define_insn "*lshrhi3_1"
11868 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11869 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11870 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11871 (clobber (reg:CC FLAGS_REG))]
11872 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11874 shr{w}\t{%2, %0|%0, %2}
11875 shr{w}\t{%b2, %0|%0, %b2}"
11876 [(set_attr "type" "ishift")
11877 (set_attr "mode" "HI")])
11879 ;; This pattern can't accept a variable shift count, since shifts by
11880 ;; zero don't affect the flags. We assume that shifts by constant
11881 ;; zero are optimized away.
11882 (define_insn "*lshrhi3_one_bit_cmp"
11883 [(set (reg FLAGS_REG)
11885 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11886 (match_operand:QI 2 "const1_operand" ""))
11888 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11889 (lshiftrt:HI (match_dup 1) (match_dup 2)))]
11890 "ix86_match_ccmode (insn, CCGOCmode)
11891 && (TARGET_SHIFT1 || optimize_size)
11892 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11894 [(set_attr "type" "ishift")
11895 (set (attr "length")
11896 (if_then_else (match_operand:SI 0 "register_operand" "")
11898 (const_string "*")))])
11900 ;; This pattern can't accept a variable shift count, since shifts by
11901 ;; zero don't affect the flags. We assume that shifts by constant
11902 ;; zero are optimized away.
11903 (define_insn "*lshrhi3_cmp"
11904 [(set (reg FLAGS_REG)
11906 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11907 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11909 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11910 (lshiftrt:HI (match_dup 1) (match_dup 2)))]
11911 "ix86_match_ccmode (insn, CCGOCmode)
11912 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11913 "shr{w}\t{%2, %0|%0, %2}"
11914 [(set_attr "type" "ishift")
11915 (set_attr "mode" "HI")])
11917 (define_expand "lshrqi3"
11918 [(set (match_operand:QI 0 "nonimmediate_operand" "")
11919 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
11920 (match_operand:QI 2 "nonmemory_operand" "")))
11921 (clobber (reg:CC FLAGS_REG))]
11922 "TARGET_QIMODE_MATH"
11923 "ix86_expand_binary_operator (LSHIFTRT, QImode, operands); DONE;")
11925 (define_insn "*lshrqi3_1_one_bit"
11926 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11927 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11928 (match_operand:QI 2 "const1_operand" "")))
11929 (clobber (reg:CC FLAGS_REG))]
11930 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)
11931 && (TARGET_SHIFT1 || optimize_size)"
11933 [(set_attr "type" "ishift")
11934 (set (attr "length")
11935 (if_then_else (match_operand 0 "register_operand" "")
11937 (const_string "*")))])
11939 (define_insn "*lshrqi3_1_one_bit_slp"
11940 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11941 (lshiftrt:QI (match_dup 0)
11942 (match_operand:QI 1 "const1_operand" "")))
11943 (clobber (reg:CC FLAGS_REG))]
11944 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11945 && (TARGET_SHIFT1 || optimize_size)"
11947 [(set_attr "type" "ishift1")
11948 (set (attr "length")
11949 (if_then_else (match_operand 0 "register_operand" "")
11951 (const_string "*")))])
11953 (define_insn "*lshrqi3_1"
11954 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11955 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11956 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11957 (clobber (reg:CC FLAGS_REG))]
11958 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
11960 shr{b}\t{%2, %0|%0, %2}
11961 shr{b}\t{%b2, %0|%0, %b2}"
11962 [(set_attr "type" "ishift")
11963 (set_attr "mode" "QI")])
11965 (define_insn "*lshrqi3_1_slp"
11966 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11967 (lshiftrt:QI (match_dup 0)
11968 (match_operand:QI 1 "nonmemory_operand" "I,c")))
11969 (clobber (reg:CC FLAGS_REG))]
11970 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11971 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11973 shr{b}\t{%1, %0|%0, %1}
11974 shr{b}\t{%b1, %0|%0, %b1}"
11975 [(set_attr "type" "ishift1")
11976 (set_attr "mode" "QI")])
11978 ;; This pattern can't accept a variable shift count, since shifts by
11979 ;; zero don't affect the flags. We assume that shifts by constant
11980 ;; zero are optimized away.
11981 (define_insn "*lshrqi2_one_bit_cmp"
11982 [(set (reg FLAGS_REG)
11984 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11985 (match_operand:QI 2 "const1_operand" ""))
11987 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11988 (lshiftrt:QI (match_dup 1) (match_dup 2)))]
11989 "ix86_match_ccmode (insn, CCGOCmode)
11990 && (TARGET_SHIFT1 || optimize_size)
11991 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
11993 [(set_attr "type" "ishift")
11994 (set (attr "length")
11995 (if_then_else (match_operand:SI 0 "register_operand" "")
11997 (const_string "*")))])
11999 ;; This pattern can't accept a variable shift count, since shifts by
12000 ;; zero don't affect the flags. We assume that shifts by constant
12001 ;; zero are optimized away.
12002 (define_insn "*lshrqi2_cmp"
12003 [(set (reg FLAGS_REG)
12005 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12006 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12008 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12009 (lshiftrt:QI (match_dup 1) (match_dup 2)))]
12010 "ix86_match_ccmode (insn, CCGOCmode)
12011 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
12012 "shr{b}\t{%2, %0|%0, %2}"
12013 [(set_attr "type" "ishift")
12014 (set_attr "mode" "QI")])
12016 ;; Rotate instructions
12018 (define_expand "rotldi3"
12019 [(set (match_operand:DI 0 "shiftdi_operand" "")
12020 (rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
12021 (match_operand:QI 2 "nonmemory_operand" "")))
12022 (clobber (reg:CC FLAGS_REG))]
12027 ix86_expand_binary_operator (ROTATE, DImode, operands);
12030 if (!const_1_to_31_operand (operands[2], VOIDmode))
12032 emit_insn (gen_ix86_rotldi3 (operands[0], operands[1], operands[2]));
12036 ;; Implement rotation using two double-precision shift instructions
12037 ;; and a scratch register.
12038 (define_insn_and_split "ix86_rotldi3"
12039 [(set (match_operand:DI 0 "register_operand" "=r")
12040 (rotate:DI (match_operand:DI 1 "register_operand" "0")
12041 (match_operand:QI 2 "const_1_to_31_operand" "I")))
12042 (clobber (reg:CC FLAGS_REG))
12043 (clobber (match_scratch:SI 3 "=&r"))]
12046 "&& reload_completed"
12047 [(set (match_dup 3) (match_dup 4))
12049 [(set (match_dup 4)
12050 (ior:SI (ashift:SI (match_dup 4) (match_dup 2))
12051 (lshiftrt:SI (match_dup 5)
12052 (minus:QI (const_int 32) (match_dup 2)))))
12053 (clobber (reg:CC FLAGS_REG))])
12055 [(set (match_dup 5)
12056 (ior:SI (ashift:SI (match_dup 5) (match_dup 2))
12057 (lshiftrt:SI (match_dup 3)
12058 (minus:QI (const_int 32) (match_dup 2)))))
12059 (clobber (reg:CC FLAGS_REG))])]
12060 "split_di (operands, 1, operands + 4, operands + 5);")
12062 (define_insn "*rotlsi3_1_one_bit_rex64"
12063 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12064 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12065 (match_operand:QI 2 "const1_operand" "")))
12066 (clobber (reg:CC FLAGS_REG))]
12067 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)
12068 && (TARGET_SHIFT1 || optimize_size)"
12070 [(set_attr "type" "rotate")
12071 (set (attr "length")
12072 (if_then_else (match_operand:DI 0 "register_operand" "")
12074 (const_string "*")))])
12076 (define_insn "*rotldi3_1_rex64"
12077 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
12078 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
12079 (match_operand:QI 2 "nonmemory_operand" "e,c")))
12080 (clobber (reg:CC FLAGS_REG))]
12081 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)"
12083 rol{q}\t{%2, %0|%0, %2}
12084 rol{q}\t{%b2, %0|%0, %b2}"
12085 [(set_attr "type" "rotate")
12086 (set_attr "mode" "DI")])
12088 (define_expand "rotlsi3"
12089 [(set (match_operand:SI 0 "nonimmediate_operand" "")
12090 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
12091 (match_operand:QI 2 "nonmemory_operand" "")))
12092 (clobber (reg:CC FLAGS_REG))]
12094 "ix86_expand_binary_operator (ROTATE, SImode, operands); DONE;")
12096 (define_insn "*rotlsi3_1_one_bit"
12097 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12098 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12099 (match_operand:QI 2 "const1_operand" "")))
12100 (clobber (reg:CC FLAGS_REG))]
12101 "ix86_binary_operator_ok (ROTATE, SImode, operands)
12102 && (TARGET_SHIFT1 || optimize_size)"
12104 [(set_attr "type" "rotate")
12105 (set (attr "length")
12106 (if_then_else (match_operand:SI 0 "register_operand" "")
12108 (const_string "*")))])
12110 (define_insn "*rotlsi3_1_one_bit_zext"
12111 [(set (match_operand:DI 0 "register_operand" "=r")
12113 (rotate:SI (match_operand:SI 1 "register_operand" "0")
12114 (match_operand:QI 2 "const1_operand" ""))))
12115 (clobber (reg:CC FLAGS_REG))]
12116 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)
12117 && (TARGET_SHIFT1 || optimize_size)"
12119 [(set_attr "type" "rotate")
12120 (set_attr "length" "2")])
12122 (define_insn "*rotlsi3_1"
12123 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12124 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12125 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12126 (clobber (reg:CC FLAGS_REG))]
12127 "ix86_binary_operator_ok (ROTATE, SImode, operands)"
12129 rol{l}\t{%2, %0|%0, %2}
12130 rol{l}\t{%b2, %0|%0, %b2}"
12131 [(set_attr "type" "rotate")
12132 (set_attr "mode" "SI")])
12134 (define_insn "*rotlsi3_1_zext"
12135 [(set (match_operand:DI 0 "register_operand" "=r,r")
12137 (rotate:SI (match_operand:SI 1 "register_operand" "0,0")
12138 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12139 (clobber (reg:CC FLAGS_REG))]
12140 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)"
12142 rol{l}\t{%2, %k0|%k0, %2}
12143 rol{l}\t{%b2, %k0|%k0, %b2}"
12144 [(set_attr "type" "rotate")
12145 (set_attr "mode" "SI")])
12147 (define_expand "rotlhi3"
12148 [(set (match_operand:HI 0 "nonimmediate_operand" "")
12149 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "")
12150 (match_operand:QI 2 "nonmemory_operand" "")))
12151 (clobber (reg:CC FLAGS_REG))]
12152 "TARGET_HIMODE_MATH"
12153 "ix86_expand_binary_operator (ROTATE, HImode, operands); DONE;")
12155 (define_insn "*rotlhi3_1_one_bit"
12156 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12157 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12158 (match_operand:QI 2 "const1_operand" "")))
12159 (clobber (reg:CC FLAGS_REG))]
12160 "ix86_binary_operator_ok (ROTATE, HImode, operands)
12161 && (TARGET_SHIFT1 || optimize_size)"
12163 [(set_attr "type" "rotate")
12164 (set (attr "length")
12165 (if_then_else (match_operand 0 "register_operand" "")
12167 (const_string "*")))])
12169 (define_insn "*rotlhi3_1"
12170 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12171 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12172 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12173 (clobber (reg:CC FLAGS_REG))]
12174 "ix86_binary_operator_ok (ROTATE, HImode, operands)"
12176 rol{w}\t{%2, %0|%0, %2}
12177 rol{w}\t{%b2, %0|%0, %b2}"
12178 [(set_attr "type" "rotate")
12179 (set_attr "mode" "HI")])
12181 (define_expand "rotlqi3"
12182 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12183 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "")
12184 (match_operand:QI 2 "nonmemory_operand" "")))
12185 (clobber (reg:CC FLAGS_REG))]
12186 "TARGET_QIMODE_MATH"
12187 "ix86_expand_binary_operator (ROTATE, QImode, operands); DONE;")
12189 (define_insn "*rotlqi3_1_one_bit_slp"
12190 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12191 (rotate:QI (match_dup 0)
12192 (match_operand:QI 1 "const1_operand" "")))
12193 (clobber (reg:CC FLAGS_REG))]
12194 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12195 && (TARGET_SHIFT1 || optimize_size)"
12197 [(set_attr "type" "rotate1")
12198 (set (attr "length")
12199 (if_then_else (match_operand 0 "register_operand" "")
12201 (const_string "*")))])
12203 (define_insn "*rotlqi3_1_one_bit"
12204 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12205 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12206 (match_operand:QI 2 "const1_operand" "")))
12207 (clobber (reg:CC FLAGS_REG))]
12208 "ix86_binary_operator_ok (ROTATE, QImode, operands)
12209 && (TARGET_SHIFT1 || optimize_size)"
12211 [(set_attr "type" "rotate")
12212 (set (attr "length")
12213 (if_then_else (match_operand 0 "register_operand" "")
12215 (const_string "*")))])
12217 (define_insn "*rotlqi3_1_slp"
12218 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12219 (rotate:QI (match_dup 0)
12220 (match_operand:QI 1 "nonmemory_operand" "I,c")))
12221 (clobber (reg:CC FLAGS_REG))]
12222 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12223 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
12225 rol{b}\t{%1, %0|%0, %1}
12226 rol{b}\t{%b1, %0|%0, %b1}"
12227 [(set_attr "type" "rotate1")
12228 (set_attr "mode" "QI")])
12230 (define_insn "*rotlqi3_1"
12231 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12232 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12233 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12234 (clobber (reg:CC FLAGS_REG))]
12235 "ix86_binary_operator_ok (ROTATE, QImode, operands)"
12237 rol{b}\t{%2, %0|%0, %2}
12238 rol{b}\t{%b2, %0|%0, %b2}"
12239 [(set_attr "type" "rotate")
12240 (set_attr "mode" "QI")])
12242 (define_expand "rotrdi3"
12243 [(set (match_operand:DI 0 "shiftdi_operand" "")
12244 (rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
12245 (match_operand:QI 2 "nonmemory_operand" "")))
12246 (clobber (reg:CC FLAGS_REG))]
12251 ix86_expand_binary_operator (ROTATERT, DImode, operands);
12254 if (!const_1_to_31_operand (operands[2], VOIDmode))
12256 emit_insn (gen_ix86_rotrdi3 (operands[0], operands[1], operands[2]));
12260 ;; Implement rotation using two double-precision shift instructions
12261 ;; and a scratch register.
12262 (define_insn_and_split "ix86_rotrdi3"
12263 [(set (match_operand:DI 0 "register_operand" "=r")
12264 (rotatert:DI (match_operand:DI 1 "register_operand" "0")
12265 (match_operand:QI 2 "const_1_to_31_operand" "I")))
12266 (clobber (reg:CC FLAGS_REG))
12267 (clobber (match_scratch:SI 3 "=&r"))]
12270 "&& reload_completed"
12271 [(set (match_dup 3) (match_dup 4))
12273 [(set (match_dup 4)
12274 (ior:SI (ashiftrt:SI (match_dup 4) (match_dup 2))
12275 (ashift:SI (match_dup 5)
12276 (minus:QI (const_int 32) (match_dup 2)))))
12277 (clobber (reg:CC FLAGS_REG))])
12279 [(set (match_dup 5)
12280 (ior:SI (ashiftrt:SI (match_dup 5) (match_dup 2))
12281 (ashift:SI (match_dup 3)
12282 (minus:QI (const_int 32) (match_dup 2)))))
12283 (clobber (reg:CC FLAGS_REG))])]
12284 "split_di (operands, 1, operands + 4, operands + 5);")
12286 (define_insn "*rotrdi3_1_one_bit_rex64"
12287 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12288 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12289 (match_operand:QI 2 "const1_operand" "")))
12290 (clobber (reg:CC FLAGS_REG))]
12291 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)
12292 && (TARGET_SHIFT1 || optimize_size)"
12294 [(set_attr "type" "rotate")
12295 (set (attr "length")
12296 (if_then_else (match_operand:DI 0 "register_operand" "")
12298 (const_string "*")))])
12300 (define_insn "*rotrdi3_1_rex64"
12301 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
12302 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
12303 (match_operand:QI 2 "nonmemory_operand" "J,c")))
12304 (clobber (reg:CC FLAGS_REG))]
12305 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
12307 ror{q}\t{%2, %0|%0, %2}
12308 ror{q}\t{%b2, %0|%0, %b2}"
12309 [(set_attr "type" "rotate")
12310 (set_attr "mode" "DI")])
12312 (define_expand "rotrsi3"
12313 [(set (match_operand:SI 0 "nonimmediate_operand" "")
12314 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
12315 (match_operand:QI 2 "nonmemory_operand" "")))
12316 (clobber (reg:CC FLAGS_REG))]
12318 "ix86_expand_binary_operator (ROTATERT, SImode, operands); DONE;")
12320 (define_insn "*rotrsi3_1_one_bit"
12321 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12322 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12323 (match_operand:QI 2 "const1_operand" "")))
12324 (clobber (reg:CC FLAGS_REG))]
12325 "ix86_binary_operator_ok (ROTATERT, SImode, operands)
12326 && (TARGET_SHIFT1 || optimize_size)"
12328 [(set_attr "type" "rotate")
12329 (set (attr "length")
12330 (if_then_else (match_operand:SI 0 "register_operand" "")
12332 (const_string "*")))])
12334 (define_insn "*rotrsi3_1_one_bit_zext"
12335 [(set (match_operand:DI 0 "register_operand" "=r")
12337 (rotatert:SI (match_operand:SI 1 "register_operand" "0")
12338 (match_operand:QI 2 "const1_operand" ""))))
12339 (clobber (reg:CC FLAGS_REG))]
12340 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)
12341 && (TARGET_SHIFT1 || optimize_size)"
12343 [(set_attr "type" "rotate")
12344 (set (attr "length")
12345 (if_then_else (match_operand:SI 0 "register_operand" "")
12347 (const_string "*")))])
12349 (define_insn "*rotrsi3_1"
12350 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12351 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12352 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12353 (clobber (reg:CC FLAGS_REG))]
12354 "ix86_binary_operator_ok (ROTATERT, SImode, operands)"
12356 ror{l}\t{%2, %0|%0, %2}
12357 ror{l}\t{%b2, %0|%0, %b2}"
12358 [(set_attr "type" "rotate")
12359 (set_attr "mode" "SI")])
12361 (define_insn "*rotrsi3_1_zext"
12362 [(set (match_operand:DI 0 "register_operand" "=r,r")
12364 (rotatert:SI (match_operand:SI 1 "register_operand" "0,0")
12365 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12366 (clobber (reg:CC FLAGS_REG))]
12367 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
12369 ror{l}\t{%2, %k0|%k0, %2}
12370 ror{l}\t{%b2, %k0|%k0, %b2}"
12371 [(set_attr "type" "rotate")
12372 (set_attr "mode" "SI")])
12374 (define_expand "rotrhi3"
12375 [(set (match_operand:HI 0 "nonimmediate_operand" "")
12376 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "")
12377 (match_operand:QI 2 "nonmemory_operand" "")))
12378 (clobber (reg:CC FLAGS_REG))]
12379 "TARGET_HIMODE_MATH"
12380 "ix86_expand_binary_operator (ROTATERT, HImode, operands); DONE;")
12382 (define_insn "*rotrhi3_one_bit"
12383 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12384 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12385 (match_operand:QI 2 "const1_operand" "")))
12386 (clobber (reg:CC FLAGS_REG))]
12387 "ix86_binary_operator_ok (ROTATERT, HImode, operands)
12388 && (TARGET_SHIFT1 || optimize_size)"
12390 [(set_attr "type" "rotate")
12391 (set (attr "length")
12392 (if_then_else (match_operand 0 "register_operand" "")
12394 (const_string "*")))])
12396 (define_insn "*rotrhi3"
12397 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12398 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12399 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12400 (clobber (reg:CC FLAGS_REG))]
12401 "ix86_binary_operator_ok (ROTATERT, HImode, operands)"
12403 ror{w}\t{%2, %0|%0, %2}
12404 ror{w}\t{%b2, %0|%0, %b2}"
12405 [(set_attr "type" "rotate")
12406 (set_attr "mode" "HI")])
12408 (define_expand "rotrqi3"
12409 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12410 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "")
12411 (match_operand:QI 2 "nonmemory_operand" "")))
12412 (clobber (reg:CC FLAGS_REG))]
12413 "TARGET_QIMODE_MATH"
12414 "ix86_expand_binary_operator (ROTATERT, QImode, operands); DONE;")
12416 (define_insn "*rotrqi3_1_one_bit"
12417 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12418 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12419 (match_operand:QI 2 "const1_operand" "")))
12420 (clobber (reg:CC FLAGS_REG))]
12421 "ix86_binary_operator_ok (ROTATERT, QImode, operands)
12422 && (TARGET_SHIFT1 || optimize_size)"
12424 [(set_attr "type" "rotate")
12425 (set (attr "length")
12426 (if_then_else (match_operand 0 "register_operand" "")
12428 (const_string "*")))])
12430 (define_insn "*rotrqi3_1_one_bit_slp"
12431 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12432 (rotatert:QI (match_dup 0)
12433 (match_operand:QI 1 "const1_operand" "")))
12434 (clobber (reg:CC FLAGS_REG))]
12435 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12436 && (TARGET_SHIFT1 || optimize_size)"
12438 [(set_attr "type" "rotate1")
12439 (set (attr "length")
12440 (if_then_else (match_operand 0 "register_operand" "")
12442 (const_string "*")))])
12444 (define_insn "*rotrqi3_1"
12445 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12446 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12447 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12448 (clobber (reg:CC FLAGS_REG))]
12449 "ix86_binary_operator_ok (ROTATERT, QImode, operands)"
12451 ror{b}\t{%2, %0|%0, %2}
12452 ror{b}\t{%b2, %0|%0, %b2}"
12453 [(set_attr "type" "rotate")
12454 (set_attr "mode" "QI")])
12456 (define_insn "*rotrqi3_1_slp"
12457 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12458 (rotatert:QI (match_dup 0)
12459 (match_operand:QI 1 "nonmemory_operand" "I,c")))
12460 (clobber (reg:CC FLAGS_REG))]
12461 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12462 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
12464 ror{b}\t{%1, %0|%0, %1}
12465 ror{b}\t{%b1, %0|%0, %b1}"
12466 [(set_attr "type" "rotate1")
12467 (set_attr "mode" "QI")])
12469 ;; Bit set / bit test instructions
12471 (define_expand "extv"
12472 [(set (match_operand:SI 0 "register_operand" "")
12473 (sign_extract:SI (match_operand:SI 1 "register_operand" "")
12474 (match_operand:SI 2 "immediate_operand" "")
12475 (match_operand:SI 3 "immediate_operand" "")))]
12478 /* Handle extractions from %ah et al. */
12479 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
12482 /* From mips.md: extract_bit_field doesn't verify that our source
12483 matches the predicate, so check it again here. */
12484 if (! ext_register_operand (operands[1], VOIDmode))
12488 (define_expand "extzv"
12489 [(set (match_operand:SI 0 "register_operand" "")
12490 (zero_extract:SI (match_operand 1 "ext_register_operand" "")
12491 (match_operand:SI 2 "immediate_operand" "")
12492 (match_operand:SI 3 "immediate_operand" "")))]
12495 /* Handle extractions from %ah et al. */
12496 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
12499 /* From mips.md: extract_bit_field doesn't verify that our source
12500 matches the predicate, so check it again here. */
12501 if (! ext_register_operand (operands[1], VOIDmode))
12505 (define_expand "insv"
12506 [(set (zero_extract (match_operand 0 "ext_register_operand" "")
12507 (match_operand 1 "immediate_operand" "")
12508 (match_operand 2 "immediate_operand" ""))
12509 (match_operand 3 "register_operand" ""))]
12512 /* Handle extractions from %ah et al. */
12513 if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
12516 /* From mips.md: insert_bit_field doesn't verify that our source
12517 matches the predicate, so check it again here. */
12518 if (! ext_register_operand (operands[0], VOIDmode))
12522 emit_insn (gen_movdi_insv_1_rex64 (operands[0], operands[3]));
12524 emit_insn (gen_movsi_insv_1 (operands[0], operands[3]));
12529 ;; %%% bts, btr, btc, bt.
12530 ;; In general these instructions are *slow* when applied to memory,
12531 ;; since they enforce atomic operation. When applied to registers,
12532 ;; it depends on the cpu implementation. They're never faster than
12533 ;; the corresponding and/ior/xor operations, so with 32-bit there's
12534 ;; no point. But in 64-bit, we can't hold the relevant immediates
12535 ;; within the instruction itself, so operating on bits in the high
12536 ;; 32-bits of a register becomes easier.
12538 ;; These are slow on Nocona, but fast on Athlon64. We do require the use
12539 ;; of btrq and btcq for corner cases of post-reload expansion of absdf and
12540 ;; negdf respectively, so they can never be disabled entirely.
12542 (define_insn "*btsq"
12543 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12545 (match_operand:DI 1 "const_0_to_63_operand" ""))
12547 (clobber (reg:CC FLAGS_REG))]
12548 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12550 [(set_attr "type" "alu1")])
12552 (define_insn "*btrq"
12553 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12555 (match_operand:DI 1 "const_0_to_63_operand" ""))
12557 (clobber (reg:CC FLAGS_REG))]
12558 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12560 [(set_attr "type" "alu1")])
12562 (define_insn "*btcq"
12563 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12565 (match_operand:DI 1 "const_0_to_63_operand" ""))
12566 (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
12567 (clobber (reg:CC FLAGS_REG))]
12568 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12570 [(set_attr "type" "alu1")])
12572 ;; Allow Nocona to avoid these instructions if a register is available.
12575 [(match_scratch:DI 2 "r")
12576 (parallel [(set (zero_extract:DI
12577 (match_operand:DI 0 "register_operand" "")
12579 (match_operand:DI 1 "const_0_to_63_operand" ""))
12581 (clobber (reg:CC FLAGS_REG))])]
12582 "TARGET_64BIT && !TARGET_USE_BT"
12585 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12588 if (HOST_BITS_PER_WIDE_INT >= 64)
12589 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12590 else if (i < HOST_BITS_PER_WIDE_INT)
12591 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12593 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12595 op1 = immed_double_const (lo, hi, DImode);
12598 emit_move_insn (operands[2], op1);
12602 emit_insn (gen_iordi3 (operands[0], operands[0], op1));
12607 [(match_scratch:DI 2 "r")
12608 (parallel [(set (zero_extract:DI
12609 (match_operand:DI 0 "register_operand" "")
12611 (match_operand:DI 1 "const_0_to_63_operand" ""))
12613 (clobber (reg:CC FLAGS_REG))])]
12614 "TARGET_64BIT && !TARGET_USE_BT"
12617 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12620 if (HOST_BITS_PER_WIDE_INT >= 64)
12621 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12622 else if (i < HOST_BITS_PER_WIDE_INT)
12623 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12625 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12627 op1 = immed_double_const (~lo, ~hi, DImode);
12630 emit_move_insn (operands[2], op1);
12634 emit_insn (gen_anddi3 (operands[0], operands[0], op1));
12639 [(match_scratch:DI 2 "r")
12640 (parallel [(set (zero_extract:DI
12641 (match_operand:DI 0 "register_operand" "")
12643 (match_operand:DI 1 "const_0_to_63_operand" ""))
12644 (not:DI (zero_extract:DI
12645 (match_dup 0) (const_int 1) (match_dup 1))))
12646 (clobber (reg:CC FLAGS_REG))])]
12647 "TARGET_64BIT && !TARGET_USE_BT"
12650 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12653 if (HOST_BITS_PER_WIDE_INT >= 64)
12654 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12655 else if (i < HOST_BITS_PER_WIDE_INT)
12656 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12658 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12660 op1 = immed_double_const (lo, hi, DImode);
12663 emit_move_insn (operands[2], op1);
12667 emit_insn (gen_xordi3 (operands[0], operands[0], op1));
12671 ;; Store-flag instructions.
12673 ;; For all sCOND expanders, also expand the compare or test insn that
12674 ;; generates cc0. Generate an equality comparison if `seq' or `sne'.
12676 ;; %%% Do the expansion to SImode. If PII, do things the xor+setcc way
12677 ;; to avoid partial register stalls. Otherwise do things the setcc+movzx
12678 ;; way, which can later delete the movzx if only QImode is needed.
12680 (define_expand "seq"
12681 [(set (match_operand:QI 0 "register_operand" "")
12682 (eq:QI (reg:CC FLAGS_REG) (const_int 0)))]
12684 "if (ix86_expand_setcc (EQ, operands[0])) DONE; else FAIL;")
12686 (define_expand "sne"
12687 [(set (match_operand:QI 0 "register_operand" "")
12688 (ne:QI (reg:CC FLAGS_REG) (const_int 0)))]
12690 "if (ix86_expand_setcc (NE, operands[0])) DONE; else FAIL;")
12692 (define_expand "sgt"
12693 [(set (match_operand:QI 0 "register_operand" "")
12694 (gt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12696 "if (ix86_expand_setcc (GT, operands[0])) DONE; else FAIL;")
12698 (define_expand "sgtu"
12699 [(set (match_operand:QI 0 "register_operand" "")
12700 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12702 "if (ix86_expand_setcc (GTU, operands[0])) DONE; else FAIL;")
12704 (define_expand "slt"
12705 [(set (match_operand:QI 0 "register_operand" "")
12706 (lt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12708 "if (ix86_expand_setcc (LT, operands[0])) DONE; else FAIL;")
12710 (define_expand "sltu"
12711 [(set (match_operand:QI 0 "register_operand" "")
12712 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12714 "if (ix86_expand_setcc (LTU, operands[0])) DONE; else FAIL;")
12716 (define_expand "sge"
12717 [(set (match_operand:QI 0 "register_operand" "")
12718 (ge:QI (reg:CC FLAGS_REG) (const_int 0)))]
12720 "if (ix86_expand_setcc (GE, operands[0])) DONE; else FAIL;")
12722 (define_expand "sgeu"
12723 [(set (match_operand:QI 0 "register_operand" "")
12724 (geu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12726 "if (ix86_expand_setcc (GEU, operands[0])) DONE; else FAIL;")
12728 (define_expand "sle"
12729 [(set (match_operand:QI 0 "register_operand" "")
12730 (le:QI (reg:CC FLAGS_REG) (const_int 0)))]
12732 "if (ix86_expand_setcc (LE, operands[0])) DONE; else FAIL;")
12734 (define_expand "sleu"
12735 [(set (match_operand:QI 0 "register_operand" "")
12736 (leu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12738 "if (ix86_expand_setcc (LEU, operands[0])) DONE; else FAIL;")
12740 (define_expand "sunordered"
12741 [(set (match_operand:QI 0 "register_operand" "")
12742 (unordered:QI (reg:CC FLAGS_REG) (const_int 0)))]
12743 "TARGET_80387 || TARGET_SSE"
12744 "if (ix86_expand_setcc (UNORDERED, operands[0])) DONE; else FAIL;")
12746 (define_expand "sordered"
12747 [(set (match_operand:QI 0 "register_operand" "")
12748 (ordered:QI (reg:CC FLAGS_REG) (const_int 0)))]
12750 "if (ix86_expand_setcc (ORDERED, operands[0])) DONE; else FAIL;")
12752 (define_expand "suneq"
12753 [(set (match_operand:QI 0 "register_operand" "")
12754 (uneq:QI (reg:CC FLAGS_REG) (const_int 0)))]
12755 "TARGET_80387 || TARGET_SSE"
12756 "if (ix86_expand_setcc (UNEQ, operands[0])) DONE; else FAIL;")
12758 (define_expand "sunge"
12759 [(set (match_operand:QI 0 "register_operand" "")
12760 (unge:QI (reg:CC FLAGS_REG) (const_int 0)))]
12761 "TARGET_80387 || TARGET_SSE"
12762 "if (ix86_expand_setcc (UNGE, operands[0])) DONE; else FAIL;")
12764 (define_expand "sungt"
12765 [(set (match_operand:QI 0 "register_operand" "")
12766 (ungt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12767 "TARGET_80387 || TARGET_SSE"
12768 "if (ix86_expand_setcc (UNGT, operands[0])) DONE; else FAIL;")
12770 (define_expand "sunle"
12771 [(set (match_operand:QI 0 "register_operand" "")
12772 (unle:QI (reg:CC FLAGS_REG) (const_int 0)))]
12773 "TARGET_80387 || TARGET_SSE"
12774 "if (ix86_expand_setcc (UNLE, operands[0])) DONE; else FAIL;")
12776 (define_expand "sunlt"
12777 [(set (match_operand:QI 0 "register_operand" "")
12778 (unlt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12779 "TARGET_80387 || TARGET_SSE"
12780 "if (ix86_expand_setcc (UNLT, operands[0])) DONE; else FAIL;")
12782 (define_expand "sltgt"
12783 [(set (match_operand:QI 0 "register_operand" "")
12784 (ltgt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12785 "TARGET_80387 || TARGET_SSE"
12786 "if (ix86_expand_setcc (LTGT, operands[0])) DONE; else FAIL;")
12788 (define_insn "*setcc_1"
12789 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12790 (match_operator:QI 1 "ix86_comparison_operator"
12791 [(reg FLAGS_REG) (const_int 0)]))]
12794 [(set_attr "type" "setcc")
12795 (set_attr "mode" "QI")])
12797 (define_insn "*setcc_2"
12798 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12799 (match_operator:QI 1 "ix86_comparison_operator"
12800 [(reg FLAGS_REG) (const_int 0)]))]
12803 [(set_attr "type" "setcc")
12804 (set_attr "mode" "QI")])
12806 ;; In general it is not safe to assume too much about CCmode registers,
12807 ;; so simplify-rtx stops when it sees a second one. Under certain
12808 ;; conditions this is safe on x86, so help combine not create
12815 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12816 (ne:QI (match_operator 1 "ix86_comparison_operator"
12817 [(reg FLAGS_REG) (const_int 0)])
12820 [(set (match_dup 0) (match_dup 1))]
12822 PUT_MODE (operands[1], QImode);
12826 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
12827 (ne:QI (match_operator 1 "ix86_comparison_operator"
12828 [(reg FLAGS_REG) (const_int 0)])
12831 [(set (match_dup 0) (match_dup 1))]
12833 PUT_MODE (operands[1], QImode);
12837 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12838 (eq:QI (match_operator 1 "ix86_comparison_operator"
12839 [(reg FLAGS_REG) (const_int 0)])
12842 [(set (match_dup 0) (match_dup 1))]
12844 rtx new_op1 = copy_rtx (operands[1]);
12845 operands[1] = new_op1;
12846 PUT_MODE (new_op1, QImode);
12847 PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
12848 GET_MODE (XEXP (new_op1, 0))));
12850 /* Make sure that (a) the CCmode we have for the flags is strong
12851 enough for the reversed compare or (b) we have a valid FP compare. */
12852 if (! ix86_comparison_operator (new_op1, VOIDmode))
12857 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
12858 (eq:QI (match_operator 1 "ix86_comparison_operator"
12859 [(reg FLAGS_REG) (const_int 0)])
12862 [(set (match_dup 0) (match_dup 1))]
12864 rtx new_op1 = copy_rtx (operands[1]);
12865 operands[1] = new_op1;
12866 PUT_MODE (new_op1, QImode);
12867 PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
12868 GET_MODE (XEXP (new_op1, 0))));
12870 /* Make sure that (a) the CCmode we have for the flags is strong
12871 enough for the reversed compare or (b) we have a valid FP compare. */
12872 if (! ix86_comparison_operator (new_op1, VOIDmode))
12876 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
12877 ;; subsequent logical operations are used to imitate conditional moves.
12878 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
12881 (define_insn "*sse_setccsf"
12882 [(set (match_operand:SF 0 "register_operand" "=x")
12883 (match_operator:SF 1 "sse_comparison_operator"
12884 [(match_operand:SF 2 "register_operand" "0")
12885 (match_operand:SF 3 "nonimmediate_operand" "xm")]))]
12887 "cmp%D1ss\t{%3, %0|%0, %3}"
12888 [(set_attr "type" "ssecmp")
12889 (set_attr "mode" "SF")])
12891 (define_insn "*sse_setccdf"
12892 [(set (match_operand:DF 0 "register_operand" "=Y")
12893 (match_operator:DF 1 "sse_comparison_operator"
12894 [(match_operand:DF 2 "register_operand" "0")
12895 (match_operand:DF 3 "nonimmediate_operand" "Ym")]))]
12897 "cmp%D1sd\t{%3, %0|%0, %3}"
12898 [(set_attr "type" "ssecmp")
12899 (set_attr "mode" "DF")])
12901 ;; Basic conditional jump instructions.
12902 ;; We ignore the overflow flag for signed branch instructions.
12904 ;; For all bCOND expanders, also expand the compare or test insn that
12905 ;; generates reg FLAGS_REG. Generate an equality comparison if `beq' or `bne'.
12907 (define_expand "beq"
12909 (if_then_else (match_dup 1)
12910 (label_ref (match_operand 0 "" ""))
12913 "ix86_expand_branch (EQ, operands[0]); DONE;")
12915 (define_expand "bne"
12917 (if_then_else (match_dup 1)
12918 (label_ref (match_operand 0 "" ""))
12921 "ix86_expand_branch (NE, operands[0]); DONE;")
12923 (define_expand "bgt"
12925 (if_then_else (match_dup 1)
12926 (label_ref (match_operand 0 "" ""))
12929 "ix86_expand_branch (GT, operands[0]); DONE;")
12931 (define_expand "bgtu"
12933 (if_then_else (match_dup 1)
12934 (label_ref (match_operand 0 "" ""))
12937 "ix86_expand_branch (GTU, operands[0]); DONE;")
12939 (define_expand "blt"
12941 (if_then_else (match_dup 1)
12942 (label_ref (match_operand 0 "" ""))
12945 "ix86_expand_branch (LT, operands[0]); DONE;")
12947 (define_expand "bltu"
12949 (if_then_else (match_dup 1)
12950 (label_ref (match_operand 0 "" ""))
12953 "ix86_expand_branch (LTU, operands[0]); DONE;")
12955 (define_expand "bge"
12957 (if_then_else (match_dup 1)
12958 (label_ref (match_operand 0 "" ""))
12961 "ix86_expand_branch (GE, operands[0]); DONE;")
12963 (define_expand "bgeu"
12965 (if_then_else (match_dup 1)
12966 (label_ref (match_operand 0 "" ""))
12969 "ix86_expand_branch (GEU, operands[0]); DONE;")
12971 (define_expand "ble"
12973 (if_then_else (match_dup 1)
12974 (label_ref (match_operand 0 "" ""))
12977 "ix86_expand_branch (LE, operands[0]); DONE;")
12979 (define_expand "bleu"
12981 (if_then_else (match_dup 1)
12982 (label_ref (match_operand 0 "" ""))
12985 "ix86_expand_branch (LEU, operands[0]); DONE;")
12987 (define_expand "bunordered"
12989 (if_then_else (match_dup 1)
12990 (label_ref (match_operand 0 "" ""))
12992 "TARGET_80387 || TARGET_SSE_MATH"
12993 "ix86_expand_branch (UNORDERED, operands[0]); DONE;")
12995 (define_expand "bordered"
12997 (if_then_else (match_dup 1)
12998 (label_ref (match_operand 0 "" ""))
13000 "TARGET_80387 || TARGET_SSE_MATH"
13001 "ix86_expand_branch (ORDERED, operands[0]); DONE;")
13003 (define_expand "buneq"
13005 (if_then_else (match_dup 1)
13006 (label_ref (match_operand 0 "" ""))
13008 "TARGET_80387 || TARGET_SSE_MATH"
13009 "ix86_expand_branch (UNEQ, operands[0]); DONE;")
13011 (define_expand "bunge"
13013 (if_then_else (match_dup 1)
13014 (label_ref (match_operand 0 "" ""))
13016 "TARGET_80387 || TARGET_SSE_MATH"
13017 "ix86_expand_branch (UNGE, operands[0]); DONE;")
13019 (define_expand "bungt"
13021 (if_then_else (match_dup 1)
13022 (label_ref (match_operand 0 "" ""))
13024 "TARGET_80387 || TARGET_SSE_MATH"
13025 "ix86_expand_branch (UNGT, operands[0]); DONE;")
13027 (define_expand "bunle"
13029 (if_then_else (match_dup 1)
13030 (label_ref (match_operand 0 "" ""))
13032 "TARGET_80387 || TARGET_SSE_MATH"
13033 "ix86_expand_branch (UNLE, operands[0]); DONE;")
13035 (define_expand "bunlt"
13037 (if_then_else (match_dup 1)
13038 (label_ref (match_operand 0 "" ""))
13040 "TARGET_80387 || TARGET_SSE_MATH"
13041 "ix86_expand_branch (UNLT, operands[0]); DONE;")
13043 (define_expand "bltgt"
13045 (if_then_else (match_dup 1)
13046 (label_ref (match_operand 0 "" ""))
13048 "TARGET_80387 || TARGET_SSE_MATH"
13049 "ix86_expand_branch (LTGT, operands[0]); DONE;")
13051 (define_insn "*jcc_1"
13053 (if_then_else (match_operator 1 "ix86_comparison_operator"
13054 [(reg FLAGS_REG) (const_int 0)])
13055 (label_ref (match_operand 0 "" ""))
13059 [(set_attr "type" "ibr")
13060 (set_attr "modrm" "0")
13061 (set (attr "length")
13062 (if_then_else (and (ge (minus (match_dup 0) (pc))
13064 (lt (minus (match_dup 0) (pc))
13069 (define_insn "*jcc_2"
13071 (if_then_else (match_operator 1 "ix86_comparison_operator"
13072 [(reg FLAGS_REG) (const_int 0)])
13074 (label_ref (match_operand 0 "" ""))))]
13077 [(set_attr "type" "ibr")
13078 (set_attr "modrm" "0")
13079 (set (attr "length")
13080 (if_then_else (and (ge (minus (match_dup 0) (pc))
13082 (lt (minus (match_dup 0) (pc))
13087 ;; In general it is not safe to assume too much about CCmode registers,
13088 ;; so simplify-rtx stops when it sees a second one. Under certain
13089 ;; conditions this is safe on x86, so help combine not create
13097 (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
13098 [(reg FLAGS_REG) (const_int 0)])
13100 (label_ref (match_operand 1 "" ""))
13104 (if_then_else (match_dup 0)
13105 (label_ref (match_dup 1))
13108 PUT_MODE (operands[0], VOIDmode);
13113 (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
13114 [(reg FLAGS_REG) (const_int 0)])
13116 (label_ref (match_operand 1 "" ""))
13120 (if_then_else (match_dup 0)
13121 (label_ref (match_dup 1))
13124 rtx new_op0 = copy_rtx (operands[0]);
13125 operands[0] = new_op0;
13126 PUT_MODE (new_op0, VOIDmode);
13127 PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0),
13128 GET_MODE (XEXP (new_op0, 0))));
13130 /* Make sure that (a) the CCmode we have for the flags is strong
13131 enough for the reversed compare or (b) we have a valid FP compare. */
13132 if (! ix86_comparison_operator (new_op0, VOIDmode))
13136 ;; Define combination compare-and-branch fp compare instructions to use
13137 ;; during early optimization. Splitting the operation apart early makes
13138 ;; for bad code when we want to reverse the operation.
13140 (define_insn "*fp_jcc_1_mixed"
13142 (if_then_else (match_operator 0 "comparison_operator"
13143 [(match_operand 1 "register_operand" "f#x,x#f")
13144 (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
13145 (label_ref (match_operand 3 "" ""))
13147 (clobber (reg:CCFP FPSR_REG))
13148 (clobber (reg:CCFP FLAGS_REG))]
13149 "TARGET_MIX_SSE_I387
13150 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13151 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13152 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13155 (define_insn "*fp_jcc_1_sse"
13157 (if_then_else (match_operator 0 "comparison_operator"
13158 [(match_operand 1 "register_operand" "x")
13159 (match_operand 2 "nonimmediate_operand" "xm")])
13160 (label_ref (match_operand 3 "" ""))
13162 (clobber (reg:CCFP FPSR_REG))
13163 (clobber (reg:CCFP FLAGS_REG))]
13165 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13166 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13167 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13170 (define_insn "*fp_jcc_1_387"
13172 (if_then_else (match_operator 0 "comparison_operator"
13173 [(match_operand 1 "register_operand" "f")
13174 (match_operand 2 "register_operand" "f")])
13175 (label_ref (match_operand 3 "" ""))
13177 (clobber (reg:CCFP FPSR_REG))
13178 (clobber (reg:CCFP FLAGS_REG))]
13179 "TARGET_CMOVE && TARGET_80387
13180 && FLOAT_MODE_P (GET_MODE (operands[1]))
13181 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13182 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13185 (define_insn "*fp_jcc_2_mixed"
13187 (if_then_else (match_operator 0 "comparison_operator"
13188 [(match_operand 1 "register_operand" "f#x,x#f")
13189 (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
13191 (label_ref (match_operand 3 "" ""))))
13192 (clobber (reg:CCFP FPSR_REG))
13193 (clobber (reg:CCFP FLAGS_REG))]
13194 "TARGET_MIX_SSE_I387
13195 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13196 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13197 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13200 (define_insn "*fp_jcc_2_sse"
13202 (if_then_else (match_operator 0 "comparison_operator"
13203 [(match_operand 1 "register_operand" "x")
13204 (match_operand 2 "nonimmediate_operand" "xm")])
13206 (label_ref (match_operand 3 "" ""))))
13207 (clobber (reg:CCFP FPSR_REG))
13208 (clobber (reg:CCFP FLAGS_REG))]
13210 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13211 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13212 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13215 (define_insn "*fp_jcc_2_387"
13217 (if_then_else (match_operator 0 "comparison_operator"
13218 [(match_operand 1 "register_operand" "f")
13219 (match_operand 2 "register_operand" "f")])
13221 (label_ref (match_operand 3 "" ""))))
13222 (clobber (reg:CCFP FPSR_REG))
13223 (clobber (reg:CCFP FLAGS_REG))]
13224 "TARGET_CMOVE && TARGET_80387
13225 && FLOAT_MODE_P (GET_MODE (operands[1]))
13226 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13227 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13230 (define_insn "*fp_jcc_3_387"
13232 (if_then_else (match_operator 0 "comparison_operator"
13233 [(match_operand 1 "register_operand" "f")
13234 (match_operand 2 "nonimmediate_operand" "fm")])
13235 (label_ref (match_operand 3 "" ""))
13237 (clobber (reg:CCFP FPSR_REG))
13238 (clobber (reg:CCFP FLAGS_REG))
13239 (clobber (match_scratch:HI 4 "=a"))]
13241 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
13242 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13243 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
13244 && SELECT_CC_MODE (GET_CODE (operands[0]),
13245 operands[1], operands[2]) == CCFPmode
13246 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13249 (define_insn "*fp_jcc_4_387"
13251 (if_then_else (match_operator 0 "comparison_operator"
13252 [(match_operand 1 "register_operand" "f")
13253 (match_operand 2 "nonimmediate_operand" "fm")])
13255 (label_ref (match_operand 3 "" ""))))
13256 (clobber (reg:CCFP FPSR_REG))
13257 (clobber (reg:CCFP FLAGS_REG))
13258 (clobber (match_scratch:HI 4 "=a"))]
13260 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
13261 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13262 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
13263 && SELECT_CC_MODE (GET_CODE (operands[0]),
13264 operands[1], operands[2]) == CCFPmode
13265 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13268 (define_insn "*fp_jcc_5_387"
13270 (if_then_else (match_operator 0 "comparison_operator"
13271 [(match_operand 1 "register_operand" "f")
13272 (match_operand 2 "register_operand" "f")])
13273 (label_ref (match_operand 3 "" ""))
13275 (clobber (reg:CCFP FPSR_REG))
13276 (clobber (reg:CCFP FLAGS_REG))
13277 (clobber (match_scratch:HI 4 "=a"))]
13279 && FLOAT_MODE_P (GET_MODE (operands[1]))
13280 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13281 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13284 (define_insn "*fp_jcc_6_387"
13286 (if_then_else (match_operator 0 "comparison_operator"
13287 [(match_operand 1 "register_operand" "f")
13288 (match_operand 2 "register_operand" "f")])
13290 (label_ref (match_operand 3 "" ""))))
13291 (clobber (reg:CCFP FPSR_REG))
13292 (clobber (reg:CCFP FLAGS_REG))
13293 (clobber (match_scratch:HI 4 "=a"))]
13295 && FLOAT_MODE_P (GET_MODE (operands[1]))
13296 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13297 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13300 (define_insn "*fp_jcc_7_387"
13302 (if_then_else (match_operator 0 "comparison_operator"
13303 [(match_operand 1 "register_operand" "f")
13304 (match_operand 2 "const0_operand" "X")])
13305 (label_ref (match_operand 3 "" ""))
13307 (clobber (reg:CCFP FPSR_REG))
13308 (clobber (reg:CCFP FLAGS_REG))
13309 (clobber (match_scratch:HI 4 "=a"))]
13311 && FLOAT_MODE_P (GET_MODE (operands[1]))
13312 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13313 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
13314 && SELECT_CC_MODE (GET_CODE (operands[0]),
13315 operands[1], operands[2]) == CCFPmode
13316 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13319 ;; The order of operands in *fp_jcc_8_387 is forced by combine in
13320 ;; simplify_comparison () function. Float operator is treated as RTX_OBJ
13321 ;; with a precedence over other operators and is always put in the first
13322 ;; place. Swap condition and operands to match ficom instruction.
13324 (define_insn "*fp_jcc_8<mode>_387"
13326 (if_then_else (match_operator 0 "comparison_operator"
13327 [(match_operator 1 "float_operator"
13328 [(match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r")])
13329 (match_operand 3 "register_operand" "f,f")])
13330 (label_ref (match_operand 4 "" ""))
13332 (clobber (reg:CCFP FPSR_REG))
13333 (clobber (reg:CCFP FLAGS_REG))
13334 (clobber (match_scratch:HI 5 "=a,a"))]
13335 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
13336 && FLOAT_MODE_P (GET_MODE (operands[3]))
13337 && GET_MODE (operands[1]) == GET_MODE (operands[3])
13338 && !ix86_use_fcomi_compare (swap_condition (GET_CODE (operands[0])))
13339 && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode
13340 && ix86_fp_jump_nontrivial_p (swap_condition (GET_CODE (operands[0])))"
13345 (if_then_else (match_operator 0 "comparison_operator"
13346 [(match_operand 1 "register_operand" "")
13347 (match_operand 2 "nonimmediate_operand" "")])
13348 (match_operand 3 "" "")
13349 (match_operand 4 "" "")))
13350 (clobber (reg:CCFP FPSR_REG))
13351 (clobber (reg:CCFP FLAGS_REG))]
13355 ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
13356 operands[3], operands[4], NULL_RTX, NULL_RTX);
13362 (if_then_else (match_operator 0 "comparison_operator"
13363 [(match_operand 1 "register_operand" "")
13364 (match_operand 2 "general_operand" "")])
13365 (match_operand 3 "" "")
13366 (match_operand 4 "" "")))
13367 (clobber (reg:CCFP FPSR_REG))
13368 (clobber (reg:CCFP FLAGS_REG))
13369 (clobber (match_scratch:HI 5 "=a"))]
13373 ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
13374 operands[3], operands[4], operands[5], NULL_RTX);
13380 (if_then_else (match_operator 0 "comparison_operator"
13381 [(match_operator 1 "float_operator"
13382 [(match_operand:X87MODEI12 2 "memory_operand" "")])
13383 (match_operand 3 "register_operand" "")])
13384 (match_operand 4 "" "")
13385 (match_operand 5 "" "")))
13386 (clobber (reg:CCFP FPSR_REG))
13387 (clobber (reg:CCFP FLAGS_REG))
13388 (clobber (match_scratch:HI 6 "=a"))]
13392 operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]);
13393 ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
13394 operands[3], operands[7],
13395 operands[4], operands[5], operands[6], NULL_RTX);
13399 ;; %%% Kill this when reload knows how to do it.
13402 (if_then_else (match_operator 0 "comparison_operator"
13403 [(match_operator 1 "float_operator"
13404 [(match_operand:X87MODEI12 2 "register_operand" "")])
13405 (match_operand 3 "register_operand" "")])
13406 (match_operand 4 "" "")
13407 (match_operand 5 "" "")))
13408 (clobber (reg:CCFP FPSR_REG))
13409 (clobber (reg:CCFP FLAGS_REG))
13410 (clobber (match_scratch:HI 6 "=a"))]
13414 operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
13415 operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]);
13416 ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
13417 operands[3], operands[7],
13418 operands[4], operands[5], operands[6], operands[2]);
13422 ;; Unconditional and other jump instructions
13424 (define_insn "jump"
13426 (label_ref (match_operand 0 "" "")))]
13429 [(set_attr "type" "ibr")
13430 (set (attr "length")
13431 (if_then_else (and (ge (minus (match_dup 0) (pc))
13433 (lt (minus (match_dup 0) (pc))
13437 (set_attr "modrm" "0")])
13439 (define_expand "indirect_jump"
13440 [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))]
13444 (define_insn "*indirect_jump"
13445 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))]
13448 [(set_attr "type" "ibr")
13449 (set_attr "length_immediate" "0")])
13451 (define_insn "*indirect_jump_rtx64"
13452 [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))]
13455 [(set_attr "type" "ibr")
13456 (set_attr "length_immediate" "0")])
13458 (define_expand "tablejump"
13459 [(parallel [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))
13460 (use (label_ref (match_operand 1 "" "")))])]
13463 /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
13464 relative. Convert the relative address to an absolute address. */
13468 enum rtx_code code;
13474 op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
13476 else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
13480 op1 = pic_offset_table_rtx;
13485 op0 = pic_offset_table_rtx;
13489 operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
13494 (define_insn "*tablejump_1"
13495 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))
13496 (use (label_ref (match_operand 1 "" "")))]
13499 [(set_attr "type" "ibr")
13500 (set_attr "length_immediate" "0")])
13502 (define_insn "*tablejump_1_rtx64"
13503 [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))
13504 (use (label_ref (match_operand 1 "" "")))]
13507 [(set_attr "type" "ibr")
13508 (set_attr "length_immediate" "0")])
13510 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
13513 [(set (reg FLAGS_REG) (match_operand 0 "" ""))
13514 (set (match_operand:QI 1 "register_operand" "")
13515 (match_operator:QI 2 "ix86_comparison_operator"
13516 [(reg FLAGS_REG) (const_int 0)]))
13517 (set (match_operand 3 "q_regs_operand" "")
13518 (zero_extend (match_dup 1)))]
13519 "(peep2_reg_dead_p (3, operands[1])
13520 || operands_match_p (operands[1], operands[3]))
13521 && ! reg_overlap_mentioned_p (operands[3], operands[0])"
13522 [(set (match_dup 4) (match_dup 0))
13523 (set (strict_low_part (match_dup 5))
13526 operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
13527 operands[5] = gen_lowpart (QImode, operands[3]);
13528 ix86_expand_clear (operands[3]);
13531 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
13534 [(set (reg FLAGS_REG) (match_operand 0 "" ""))
13535 (set (match_operand:QI 1 "register_operand" "")
13536 (match_operator:QI 2 "ix86_comparison_operator"
13537 [(reg FLAGS_REG) (const_int 0)]))
13538 (parallel [(set (match_operand 3 "q_regs_operand" "")
13539 (zero_extend (match_dup 1)))
13540 (clobber (reg:CC FLAGS_REG))])]
13541 "(peep2_reg_dead_p (3, operands[1])
13542 || operands_match_p (operands[1], operands[3]))
13543 && ! reg_overlap_mentioned_p (operands[3], operands[0])"
13544 [(set (match_dup 4) (match_dup 0))
13545 (set (strict_low_part (match_dup 5))
13548 operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
13549 operands[5] = gen_lowpart (QImode, operands[3]);
13550 ix86_expand_clear (operands[3]);
13553 ;; Call instructions.
13555 ;; The predicates normally associated with named expanders are not properly
13556 ;; checked for calls. This is a bug in the generic code, but it isn't that
13557 ;; easy to fix. Ignore it for now and be prepared to fix things up.
13559 ;; Call subroutine returning no value.
13561 (define_expand "call_pop"
13562 [(parallel [(call (match_operand:QI 0 "" "")
13563 (match_operand:SI 1 "" ""))
13564 (set (reg:SI SP_REG)
13565 (plus:SI (reg:SI SP_REG)
13566 (match_operand:SI 3 "" "")))])]
13569 ix86_expand_call (NULL, operands[0], operands[1], operands[2], operands[3], 0);
13573 (define_insn "*call_pop_0"
13574 [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" ""))
13575 (match_operand:SI 1 "" ""))
13576 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
13577 (match_operand:SI 2 "immediate_operand" "")))]
13580 if (SIBLING_CALL_P (insn))
13583 return "call\t%P0";
13585 [(set_attr "type" "call")])
13587 (define_insn "*call_pop_1"
13588 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
13589 (match_operand:SI 1 "" ""))
13590 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
13591 (match_operand:SI 2 "immediate_operand" "i")))]
13594 if (constant_call_address_operand (operands[0], Pmode))
13596 if (SIBLING_CALL_P (insn))
13599 return "call\t%P0";
13601 if (SIBLING_CALL_P (insn))
13604 return "call\t%A0";
13606 [(set_attr "type" "call")])
13608 (define_expand "call"
13609 [(call (match_operand:QI 0 "" "")
13610 (match_operand 1 "" ""))
13611 (use (match_operand 2 "" ""))]
13614 ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 0);
13618 (define_expand "sibcall"
13619 [(call (match_operand:QI 0 "" "")
13620 (match_operand 1 "" ""))
13621 (use (match_operand 2 "" ""))]
13624 ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 1);
13628 (define_insn "*call_0"
13629 [(call (mem:QI (match_operand 0 "constant_call_address_operand" ""))
13630 (match_operand 1 "" ""))]
13633 if (SIBLING_CALL_P (insn))
13636 return "call\t%P0";
13638 [(set_attr "type" "call")])
13640 (define_insn "*call_1"
13641 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
13642 (match_operand 1 "" ""))]
13643 "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
13645 if (constant_call_address_operand (operands[0], Pmode))
13646 return "call\t%P0";
13647 return "call\t%A0";
13649 [(set_attr "type" "call")])
13651 (define_insn "*sibcall_1"
13652 [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "s,c,d,a"))
13653 (match_operand 1 "" ""))]
13654 "SIBLING_CALL_P (insn) && !TARGET_64BIT"
13656 if (constant_call_address_operand (operands[0], Pmode))
13660 [(set_attr "type" "call")])
13662 (define_insn "*call_1_rex64"
13663 [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rsm"))
13664 (match_operand 1 "" ""))]
13665 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
13667 if (constant_call_address_operand (operands[0], Pmode))
13668 return "call\t%P0";
13669 return "call\t%A0";
13671 [(set_attr "type" "call")])
13673 (define_insn "*sibcall_1_rex64"
13674 [(call (mem:QI (match_operand:DI 0 "constant_call_address_operand" ""))
13675 (match_operand 1 "" ""))]
13676 "SIBLING_CALL_P (insn) && TARGET_64BIT"
13678 [(set_attr "type" "call")])
13680 (define_insn "*sibcall_1_rex64_v"
13681 [(call (mem:QI (reg:DI 40))
13682 (match_operand 0 "" ""))]
13683 "SIBLING_CALL_P (insn) && TARGET_64BIT"
13685 [(set_attr "type" "call")])
13688 ;; Call subroutine, returning value in operand 0
13690 (define_expand "call_value_pop"
13691 [(parallel [(set (match_operand 0 "" "")
13692 (call (match_operand:QI 1 "" "")
13693 (match_operand:SI 2 "" "")))
13694 (set (reg:SI SP_REG)
13695 (plus:SI (reg:SI SP_REG)
13696 (match_operand:SI 4 "" "")))])]
13699 ix86_expand_call (operands[0], operands[1], operands[2],
13700 operands[3], operands[4], 0);
13704 (define_expand "call_value"
13705 [(set (match_operand 0 "" "")
13706 (call (match_operand:QI 1 "" "")
13707 (match_operand:SI 2 "" "")))
13708 (use (match_operand:SI 3 "" ""))]
13709 ;; Operand 2 not used on the i386.
13712 ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 0);
13716 (define_expand "sibcall_value"
13717 [(set (match_operand 0 "" "")
13718 (call (match_operand:QI 1 "" "")
13719 (match_operand:SI 2 "" "")))
13720 (use (match_operand:SI 3 "" ""))]
13721 ;; Operand 2 not used on the i386.
13724 ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 1);
13728 ;; Call subroutine returning any type.
13730 (define_expand "untyped_call"
13731 [(parallel [(call (match_operand 0 "" "")
13733 (match_operand 1 "" "")
13734 (match_operand 2 "" "")])]
13739 /* In order to give reg-stack an easier job in validating two
13740 coprocessor registers as containing a possible return value,
13741 simply pretend the untyped call returns a complex long double
13744 ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
13745 ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
13746 operands[0], const0_rtx, GEN_INT (SSE_REGPARM_MAX - 1),
13749 for (i = 0; i < XVECLEN (operands[2], 0); i++)
13751 rtx set = XVECEXP (operands[2], 0, i);
13752 emit_move_insn (SET_DEST (set), SET_SRC (set));
13755 /* The optimizer does not know that the call sets the function value
13756 registers we stored in the result block. We avoid problems by
13757 claiming that all hard registers are used and clobbered at this
13759 emit_insn (gen_blockage (const0_rtx));
13764 ;; Prologue and epilogue instructions
13766 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
13767 ;; all of memory. This blocks insns from being moved across this point.
13769 (define_insn "blockage"
13770 [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_BLOCKAGE)]
13773 [(set_attr "length" "0")])
13775 ;; Insn emitted into the body of a function to return from a function.
13776 ;; This is only done if the function's epilogue is known to be simple.
13777 ;; See comments for ix86_can_use_return_insn_p in i386.c.
13779 (define_expand "return"
13781 "ix86_can_use_return_insn_p ()"
13783 if (current_function_pops_args)
13785 rtx popc = GEN_INT (current_function_pops_args);
13786 emit_jump_insn (gen_return_pop_internal (popc));
13791 (define_insn "return_internal"
13795 [(set_attr "length" "1")
13796 (set_attr "length_immediate" "0")
13797 (set_attr "modrm" "0")])
13799 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
13800 ;; instruction Athlon and K8 have.
13802 (define_insn "return_internal_long"
13804 (unspec [(const_int 0)] UNSPEC_REP)]
13807 [(set_attr "length" "1")
13808 (set_attr "length_immediate" "0")
13809 (set_attr "prefix_rep" "1")
13810 (set_attr "modrm" "0")])
13812 (define_insn "return_pop_internal"
13814 (use (match_operand:SI 0 "const_int_operand" ""))]
13817 [(set_attr "length" "3")
13818 (set_attr "length_immediate" "2")
13819 (set_attr "modrm" "0")])
13821 (define_insn "return_indirect_internal"
13823 (use (match_operand:SI 0 "register_operand" "r"))]
13826 [(set_attr "type" "ibr")
13827 (set_attr "length_immediate" "0")])
13833 [(set_attr "length" "1")
13834 (set_attr "length_immediate" "0")
13835 (set_attr "modrm" "0")])
13837 ;; Align to 16-byte boundary, max skip in op0. Used to avoid
13838 ;; branch prediction penalty for the third jump in a 16-byte
13841 (define_insn "align"
13842 [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
13845 #ifdef ASM_OUTPUT_MAX_SKIP_ALIGN
13846 ASM_OUTPUT_MAX_SKIP_ALIGN (asm_out_file, 4, (int)INTVAL (operands[0]));
13848 /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
13849 The align insn is used to avoid 3 jump instructions in the row to improve
13850 branch prediction and the benefits hardly outweight the cost of extra 8
13851 nops on the average inserted by full alignment pseudo operation. */
13855 [(set_attr "length" "16")])
13857 (define_expand "prologue"
13860 "ix86_expand_prologue (); DONE;")
13862 (define_insn "set_got"
13863 [(set (match_operand:SI 0 "register_operand" "=r")
13864 (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
13865 (clobber (reg:CC FLAGS_REG))]
13867 { return output_set_got (operands[0]); }
13868 [(set_attr "type" "multi")
13869 (set_attr "length" "12")])
13871 (define_insn "set_got_rex64"
13872 [(set (match_operand:DI 0 "register_operand" "=r")
13873 (unspec:DI [(const_int 0)] UNSPEC_SET_GOT))]
13875 "lea{q}\t_GLOBAL_OFFSET_TABLE_(%%rip), %0"
13876 [(set_attr "type" "lea")
13877 (set_attr "length" "6")])
13879 (define_expand "epilogue"
13882 "ix86_expand_epilogue (1); DONE;")
13884 (define_expand "sibcall_epilogue"
13887 "ix86_expand_epilogue (0); DONE;")
13889 (define_expand "eh_return"
13890 [(use (match_operand 0 "register_operand" ""))]
13893 rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
13895 /* Tricky bit: we write the address of the handler to which we will
13896 be returning into someone else's stack frame, one word below the
13897 stack address we wish to restore. */
13898 tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
13899 tmp = plus_constant (tmp, -UNITS_PER_WORD);
13900 tmp = gen_rtx_MEM (Pmode, tmp);
13901 emit_move_insn (tmp, ra);
13903 if (Pmode == SImode)
13904 emit_jump_insn (gen_eh_return_si (sa));
13906 emit_jump_insn (gen_eh_return_di (sa));
13911 (define_insn_and_split "eh_return_si"
13913 (unspec [(match_operand:SI 0 "register_operand" "c")]
13914 UNSPEC_EH_RETURN))]
13919 "ix86_expand_epilogue (2); DONE;")
13921 (define_insn_and_split "eh_return_di"
13923 (unspec [(match_operand:DI 0 "register_operand" "c")]
13924 UNSPEC_EH_RETURN))]
13929 "ix86_expand_epilogue (2); DONE;")
13931 (define_insn "leave"
13932 [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4)))
13933 (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG)))
13934 (clobber (mem:BLK (scratch)))]
13937 [(set_attr "type" "leave")])
13939 (define_insn "leave_rex64"
13940 [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8)))
13941 (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG)))
13942 (clobber (mem:BLK (scratch)))]
13945 [(set_attr "type" "leave")])
13947 (define_expand "ffssi2"
13949 [(set (match_operand:SI 0 "register_operand" "")
13950 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "")))
13951 (clobber (match_scratch:SI 2 ""))
13952 (clobber (reg:CC FLAGS_REG))])]
13956 (define_insn_and_split "*ffs_cmove"
13957 [(set (match_operand:SI 0 "register_operand" "=r")
13958 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
13959 (clobber (match_scratch:SI 2 "=&r"))
13960 (clobber (reg:CC FLAGS_REG))]
13963 "&& reload_completed"
13964 [(set (match_dup 2) (const_int -1))
13965 (parallel [(set (reg:CCZ FLAGS_REG) (compare:CCZ (match_dup 1) (const_int 0)))
13966 (set (match_dup 0) (ctz:SI (match_dup 1)))])
13967 (set (match_dup 0) (if_then_else:SI
13968 (eq (reg:CCZ FLAGS_REG) (const_int 0))
13971 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
13972 (clobber (reg:CC FLAGS_REG))])]
13975 (define_insn_and_split "*ffs_no_cmove"
13976 [(set (match_operand:SI 0 "nonimmediate_operand" "=r")
13977 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
13978 (clobber (match_scratch:SI 2 "=&q"))
13979 (clobber (reg:CC FLAGS_REG))]
13983 [(parallel [(set (reg:CCZ FLAGS_REG) (compare:CCZ (match_dup 1) (const_int 0)))
13984 (set (match_dup 0) (ctz:SI (match_dup 1)))])
13985 (set (strict_low_part (match_dup 3))
13986 (eq:QI (reg:CCZ FLAGS_REG) (const_int 0)))
13987 (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
13988 (clobber (reg:CC FLAGS_REG))])
13989 (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
13990 (clobber (reg:CC FLAGS_REG))])
13991 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
13992 (clobber (reg:CC FLAGS_REG))])]
13994 operands[3] = gen_lowpart (QImode, operands[2]);
13995 ix86_expand_clear (operands[2]);
13998 (define_insn "*ffssi_1"
13999 [(set (reg:CCZ FLAGS_REG)
14000 (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "rm")
14002 (set (match_operand:SI 0 "register_operand" "=r")
14003 (ctz:SI (match_dup 1)))]
14005 "bsf{l}\t{%1, %0|%0, %1}"
14006 [(set_attr "prefix_0f" "1")])
14008 (define_expand "ffsdi2"
14010 [(set (match_operand:DI 0 "register_operand" "")
14011 (ffs:DI (match_operand:DI 1 "nonimmediate_operand" "")))
14012 (clobber (match_scratch:DI 2 ""))
14013 (clobber (reg:CC FLAGS_REG))])]
14014 "TARGET_64BIT && TARGET_CMOVE"
14017 (define_insn_and_split "*ffs_rex64"
14018 [(set (match_operand:DI 0 "register_operand" "=r")
14019 (ffs:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
14020 (clobber (match_scratch:DI 2 "=&r"))
14021 (clobber (reg:CC FLAGS_REG))]
14022 "TARGET_64BIT && TARGET_CMOVE"
14024 "&& reload_completed"
14025 [(set (match_dup 2) (const_int -1))
14026 (parallel [(set (reg:CCZ FLAGS_REG)
14027 (compare:CCZ (match_dup 1) (const_int 0)))
14028 (set (match_dup 0) (ctz:DI (match_dup 1)))])
14029 (set (match_dup 0) (if_then_else:DI
14030 (eq (reg:CCZ FLAGS_REG) (const_int 0))
14033 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (const_int 1)))
14034 (clobber (reg:CC FLAGS_REG))])]
14037 (define_insn "*ffsdi_1"
14038 [(set (reg:CCZ FLAGS_REG)
14039 (compare:CCZ (match_operand:DI 1 "nonimmediate_operand" "rm")
14041 (set (match_operand:DI 0 "register_operand" "=r")
14042 (ctz:DI (match_dup 1)))]
14044 "bsf{q}\t{%1, %0|%0, %1}"
14045 [(set_attr "prefix_0f" "1")])
14047 (define_insn "ctzsi2"
14048 [(set (match_operand:SI 0 "register_operand" "=r")
14049 (ctz:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
14050 (clobber (reg:CC FLAGS_REG))]
14052 "bsf{l}\t{%1, %0|%0, %1}"
14053 [(set_attr "prefix_0f" "1")])
14055 (define_insn "ctzdi2"
14056 [(set (match_operand:DI 0 "register_operand" "=r")
14057 (ctz:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
14058 (clobber (reg:CC FLAGS_REG))]
14060 "bsf{q}\t{%1, %0|%0, %1}"
14061 [(set_attr "prefix_0f" "1")])
14063 (define_expand "clzsi2"
14065 [(set (match_operand:SI 0 "register_operand" "")
14066 (minus:SI (const_int 31)
14067 (clz:SI (match_operand:SI 1 "nonimmediate_operand" ""))))
14068 (clobber (reg:CC FLAGS_REG))])
14070 [(set (match_dup 0) (xor:SI (match_dup 0) (const_int 31)))
14071 (clobber (reg:CC FLAGS_REG))])]
14075 (define_insn "*bsr"
14076 [(set (match_operand:SI 0 "register_operand" "=r")
14077 (minus:SI (const_int 31)
14078 (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
14079 (clobber (reg:CC FLAGS_REG))]
14081 "bsr{l}\t{%1, %0|%0, %1}"
14082 [(set_attr "prefix_0f" "1")])
14084 (define_expand "clzdi2"
14086 [(set (match_operand:DI 0 "register_operand" "")
14087 (minus:DI (const_int 63)
14088 (clz:DI (match_operand:DI 1 "nonimmediate_operand" ""))))
14089 (clobber (reg:CC FLAGS_REG))])
14091 [(set (match_dup 0) (xor:DI (match_dup 0) (const_int 63)))
14092 (clobber (reg:CC FLAGS_REG))])]
14096 (define_insn "*bsr_rex64"
14097 [(set (match_operand:DI 0 "register_operand" "=r")
14098 (minus:DI (const_int 63)
14099 (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))))
14100 (clobber (reg:CC FLAGS_REG))]
14102 "bsr{q}\t{%1, %0|%0, %1}"
14103 [(set_attr "prefix_0f" "1")])
14105 ;; Thread-local storage patterns for ELF.
14107 ;; Note that these code sequences must appear exactly as shown
14108 ;; in order to allow linker relaxation.
14110 (define_insn "*tls_global_dynamic_32_gnu"
14111 [(set (match_operand:SI 0 "register_operand" "=a")
14112 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14113 (match_operand:SI 2 "tls_symbolic_operand" "")
14114 (match_operand:SI 3 "call_insn_operand" "")]
14116 (clobber (match_scratch:SI 4 "=d"))
14117 (clobber (match_scratch:SI 5 "=c"))
14118 (clobber (reg:CC FLAGS_REG))]
14119 "!TARGET_64BIT && TARGET_GNU_TLS"
14120 "lea{l}\t{%a2@TLSGD(,%1,1), %0|%0, %a2@TLSGD[%1*1]}\;call\t%P3"
14121 [(set_attr "type" "multi")
14122 (set_attr "length" "12")])
14124 (define_insn "*tls_global_dynamic_32_sun"
14125 [(set (match_operand:SI 0 "register_operand" "=a")
14126 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14127 (match_operand:SI 2 "tls_symbolic_operand" "")
14128 (match_operand:SI 3 "call_insn_operand" "")]
14130 (clobber (match_scratch:SI 4 "=d"))
14131 (clobber (match_scratch:SI 5 "=c"))
14132 (clobber (reg:CC FLAGS_REG))]
14133 "!TARGET_64BIT && TARGET_SUN_TLS"
14134 "lea{l}\t{%a2@DTLNDX(%1), %4|%4, %a2@DTLNDX[%1]}
14135 push{l}\t%4\;call\t%a2@TLSPLT\;pop{l}\t%4\;nop"
14136 [(set_attr "type" "multi")
14137 (set_attr "length" "14")])
14139 (define_expand "tls_global_dynamic_32"
14140 [(parallel [(set (match_operand:SI 0 "register_operand" "")
14143 (match_operand:SI 1 "tls_symbolic_operand" "")
14146 (clobber (match_scratch:SI 4 ""))
14147 (clobber (match_scratch:SI 5 ""))
14148 (clobber (reg:CC FLAGS_REG))])]
14152 operands[2] = pic_offset_table_rtx;
14155 operands[2] = gen_reg_rtx (Pmode);
14156 emit_insn (gen_set_got (operands[2]));
14158 operands[3] = ix86_tls_get_addr ();
14161 (define_insn "*tls_global_dynamic_64"
14162 [(set (match_operand:DI 0 "register_operand" "=a")
14163 (call:DI (mem:QI (match_operand:DI 2 "call_insn_operand" ""))
14164 (match_operand:DI 3 "" "")))
14165 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
14168 ".byte\t0x66\;lea{q}\t{%a1@TLSGD(%%rip), %%rdi|%%rdi, %a1@TLSGD[%%rip]}\;.word\t0x6666\;rex64\;call\t%P2"
14169 [(set_attr "type" "multi")
14170 (set_attr "length" "16")])
14172 (define_expand "tls_global_dynamic_64"
14173 [(parallel [(set (match_operand:DI 0 "register_operand" "")
14174 (call:DI (mem:QI (match_dup 2)) (const_int 0)))
14175 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
14179 operands[2] = ix86_tls_get_addr ();
14182 (define_insn "*tls_local_dynamic_base_32_gnu"
14183 [(set (match_operand:SI 0 "register_operand" "=a")
14184 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14185 (match_operand:SI 2 "call_insn_operand" "")]
14186 UNSPEC_TLS_LD_BASE))
14187 (clobber (match_scratch:SI 3 "=d"))
14188 (clobber (match_scratch:SI 4 "=c"))
14189 (clobber (reg:CC FLAGS_REG))]
14190 "!TARGET_64BIT && TARGET_GNU_TLS"
14191 "lea{l}\t{%&@TLSLDM(%1), %0|%0, %&@TLSLDM[%1]}\;call\t%P2"
14192 [(set_attr "type" "multi")
14193 (set_attr "length" "11")])
14195 (define_insn "*tls_local_dynamic_base_32_sun"
14196 [(set (match_operand:SI 0 "register_operand" "=a")
14197 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14198 (match_operand:SI 2 "call_insn_operand" "")]
14199 UNSPEC_TLS_LD_BASE))
14200 (clobber (match_scratch:SI 3 "=d"))
14201 (clobber (match_scratch:SI 4 "=c"))
14202 (clobber (reg:CC FLAGS_REG))]
14203 "!TARGET_64BIT && TARGET_SUN_TLS"
14204 "lea{l}\t{%&@TMDNX(%1), %3|%3, %&@TMDNX[%1]}
14205 push{l}\t%3\;call\t%&@TLSPLT\;pop{l}\t%3"
14206 [(set_attr "type" "multi")
14207 (set_attr "length" "13")])
14209 (define_expand "tls_local_dynamic_base_32"
14210 [(parallel [(set (match_operand:SI 0 "register_operand" "")
14211 (unspec:SI [(match_dup 1) (match_dup 2)]
14212 UNSPEC_TLS_LD_BASE))
14213 (clobber (match_scratch:SI 3 ""))
14214 (clobber (match_scratch:SI 4 ""))
14215 (clobber (reg:CC FLAGS_REG))])]
14219 operands[1] = pic_offset_table_rtx;
14222 operands[1] = gen_reg_rtx (Pmode);
14223 emit_insn (gen_set_got (operands[1]));
14225 operands[2] = ix86_tls_get_addr ();
14228 (define_insn "*tls_local_dynamic_base_64"
14229 [(set (match_operand:DI 0 "register_operand" "=a")
14230 (call:DI (mem:QI (match_operand:DI 1 "call_insn_operand" ""))
14231 (match_operand:DI 2 "" "")))
14232 (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
14234 "lea{q}\t{%&@TLSLD(%%rip), %%rdi|%%rdi, %&@TLSLD[%%rip]}\;call\t%P1"
14235 [(set_attr "type" "multi")
14236 (set_attr "length" "12")])
14238 (define_expand "tls_local_dynamic_base_64"
14239 [(parallel [(set (match_operand:DI 0 "register_operand" "")
14240 (call:DI (mem:QI (match_dup 1)) (const_int 0)))
14241 (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])]
14244 operands[1] = ix86_tls_get_addr ();
14247 ;; Local dynamic of a single variable is a lose. Show combine how
14248 ;; to convert that back to global dynamic.
14250 (define_insn_and_split "*tls_local_dynamic_32_once"
14251 [(set (match_operand:SI 0 "register_operand" "=a")
14252 (plus:SI (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14253 (match_operand:SI 2 "call_insn_operand" "")]
14254 UNSPEC_TLS_LD_BASE)
14255 (const:SI (unspec:SI
14256 [(match_operand:SI 3 "tls_symbolic_operand" "")]
14258 (clobber (match_scratch:SI 4 "=d"))
14259 (clobber (match_scratch:SI 5 "=c"))
14260 (clobber (reg:CC FLAGS_REG))]
14264 [(parallel [(set (match_dup 0)
14265 (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
14267 (clobber (match_dup 4))
14268 (clobber (match_dup 5))
14269 (clobber (reg:CC FLAGS_REG))])]
14272 ;; Load and add the thread base pointer from %gs:0.
14274 (define_insn "*load_tp_si"
14275 [(set (match_operand:SI 0 "register_operand" "=r")
14276 (unspec:SI [(const_int 0)] UNSPEC_TP))]
14278 "mov{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}"
14279 [(set_attr "type" "imov")
14280 (set_attr "modrm" "0")
14281 (set_attr "length" "7")
14282 (set_attr "memory" "load")
14283 (set_attr "imm_disp" "false")])
14285 (define_insn "*add_tp_si"
14286 [(set (match_operand:SI 0 "register_operand" "=r")
14287 (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
14288 (match_operand:SI 1 "register_operand" "0")))
14289 (clobber (reg:CC FLAGS_REG))]
14291 "add{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}"
14292 [(set_attr "type" "alu")
14293 (set_attr "modrm" "0")
14294 (set_attr "length" "7")
14295 (set_attr "memory" "load")
14296 (set_attr "imm_disp" "false")])
14298 (define_insn "*load_tp_di"
14299 [(set (match_operand:DI 0 "register_operand" "=r")
14300 (unspec:DI [(const_int 0)] UNSPEC_TP))]
14302 "mov{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}"
14303 [(set_attr "type" "imov")
14304 (set_attr "modrm" "0")
14305 (set_attr "length" "7")
14306 (set_attr "memory" "load")
14307 (set_attr "imm_disp" "false")])
14309 (define_insn "*add_tp_di"
14310 [(set (match_operand:DI 0 "register_operand" "=r")
14311 (plus:DI (unspec:DI [(const_int 0)] UNSPEC_TP)
14312 (match_operand:DI 1 "register_operand" "0")))
14313 (clobber (reg:CC FLAGS_REG))]
14315 "add{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}"
14316 [(set_attr "type" "alu")
14317 (set_attr "modrm" "0")
14318 (set_attr "length" "7")
14319 (set_attr "memory" "load")
14320 (set_attr "imm_disp" "false")])
14322 ;; These patterns match the binary 387 instructions for addM3, subM3,
14323 ;; mulM3 and divM3. There are three patterns for each of DFmode and
14324 ;; SFmode. The first is the normal insn, the second the same insn but
14325 ;; with one operand a conversion, and the third the same insn but with
14326 ;; the other operand a conversion. The conversion may be SFmode or
14327 ;; SImode if the target mode DFmode, but only SImode if the target mode
14330 ;; Gcc is slightly more smart about handling normal two address instructions
14331 ;; so use special patterns for add and mull.
14333 (define_insn "*fop_sf_comm_mixed"
14334 [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
14335 (match_operator:SF 3 "binary_fp_operator"
14336 [(match_operand:SF 1 "nonimmediate_operand" "%0,0")
14337 (match_operand:SF 2 "nonimmediate_operand" "fm#x,xm#f")]))]
14338 "TARGET_MIX_SSE_I387
14339 && COMMUTATIVE_ARITH_P (operands[3])
14340 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14341 "* return output_387_binary_op (insn, operands);"
14342 [(set (attr "type")
14343 (if_then_else (eq_attr "alternative" "1")
14344 (if_then_else (match_operand:SF 3 "mult_operator" "")
14345 (const_string "ssemul")
14346 (const_string "sseadd"))
14347 (if_then_else (match_operand:SF 3 "mult_operator" "")
14348 (const_string "fmul")
14349 (const_string "fop"))))
14350 (set_attr "mode" "SF")])
14352 (define_insn "*fop_sf_comm_sse"
14353 [(set (match_operand:SF 0 "register_operand" "=x")
14354 (match_operator:SF 3 "binary_fp_operator"
14355 [(match_operand:SF 1 "nonimmediate_operand" "%0")
14356 (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
14358 && COMMUTATIVE_ARITH_P (operands[3])
14359 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14360 "* return output_387_binary_op (insn, operands);"
14361 [(set (attr "type")
14362 (if_then_else (match_operand:SF 3 "mult_operator" "")
14363 (const_string "ssemul")
14364 (const_string "sseadd")))
14365 (set_attr "mode" "SF")])
14367 (define_insn "*fop_sf_comm_i387"
14368 [(set (match_operand:SF 0 "register_operand" "=f")
14369 (match_operator:SF 3 "binary_fp_operator"
14370 [(match_operand:SF 1 "nonimmediate_operand" "%0")
14371 (match_operand:SF 2 "nonimmediate_operand" "fm")]))]
14373 && COMMUTATIVE_ARITH_P (operands[3])
14374 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14375 "* return output_387_binary_op (insn, operands);"
14376 [(set (attr "type")
14377 (if_then_else (match_operand:SF 3 "mult_operator" "")
14378 (const_string "fmul")
14379 (const_string "fop")))
14380 (set_attr "mode" "SF")])
14382 (define_insn "*fop_sf_1_mixed"
14383 [(set (match_operand:SF 0 "register_operand" "=f,f,x")
14384 (match_operator:SF 3 "binary_fp_operator"
14385 [(match_operand:SF 1 "nonimmediate_operand" "0,fm,0")
14386 (match_operand:SF 2 "nonimmediate_operand" "fm,0,xm#f")]))]
14387 "TARGET_MIX_SSE_I387
14388 && !COMMUTATIVE_ARITH_P (operands[3])
14389 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14390 "* return output_387_binary_op (insn, operands);"
14391 [(set (attr "type")
14392 (cond [(and (eq_attr "alternative" "2")
14393 (match_operand:SF 3 "mult_operator" ""))
14394 (const_string "ssemul")
14395 (and (eq_attr "alternative" "2")
14396 (match_operand:SF 3 "div_operator" ""))
14397 (const_string "ssediv")
14398 (eq_attr "alternative" "2")
14399 (const_string "sseadd")
14400 (match_operand:SF 3 "mult_operator" "")
14401 (const_string "fmul")
14402 (match_operand:SF 3 "div_operator" "")
14403 (const_string "fdiv")
14405 (const_string "fop")))
14406 (set_attr "mode" "SF")])
14408 (define_insn "*fop_sf_1_sse"
14409 [(set (match_operand:SF 0 "register_operand" "=x")
14410 (match_operator:SF 3 "binary_fp_operator"
14411 [(match_operand:SF 1 "register_operand" "0")
14412 (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
14414 && !COMMUTATIVE_ARITH_P (operands[3])"
14415 "* return output_387_binary_op (insn, operands);"
14416 [(set (attr "type")
14417 (cond [(match_operand:SF 3 "mult_operator" "")
14418 (const_string "ssemul")
14419 (match_operand:SF 3 "div_operator" "")
14420 (const_string "ssediv")
14422 (const_string "sseadd")))
14423 (set_attr "mode" "SF")])
14425 ;; This pattern is not fully shadowed by the pattern above.
14426 (define_insn "*fop_sf_1_i387"
14427 [(set (match_operand:SF 0 "register_operand" "=f,f")
14428 (match_operator:SF 3 "binary_fp_operator"
14429 [(match_operand:SF 1 "nonimmediate_operand" "0,fm")
14430 (match_operand:SF 2 "nonimmediate_operand" "fm,0")]))]
14431 "TARGET_80387 && !TARGET_SSE_MATH
14432 && !COMMUTATIVE_ARITH_P (operands[3])
14433 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14434 "* return output_387_binary_op (insn, operands);"
14435 [(set (attr "type")
14436 (cond [(match_operand:SF 3 "mult_operator" "")
14437 (const_string "fmul")
14438 (match_operand:SF 3 "div_operator" "")
14439 (const_string "fdiv")
14441 (const_string "fop")))
14442 (set_attr "mode" "SF")])
14444 ;; ??? Add SSE splitters for these!
14445 (define_insn "*fop_sf_2<mode>_i387"
14446 [(set (match_operand:SF 0 "register_operand" "=f,f")
14447 (match_operator:SF 3 "binary_fp_operator"
14448 [(float:SF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14449 (match_operand:SF 2 "register_operand" "0,0")]))]
14450 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH"
14451 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14452 [(set (attr "type")
14453 (cond [(match_operand:SF 3 "mult_operator" "")
14454 (const_string "fmul")
14455 (match_operand:SF 3 "div_operator" "")
14456 (const_string "fdiv")
14458 (const_string "fop")))
14459 (set_attr "fp_int_src" "true")
14460 (set_attr "mode" "<MODE>")])
14462 (define_insn "*fop_sf_3<mode>_i387"
14463 [(set (match_operand:SF 0 "register_operand" "=f,f")
14464 (match_operator:SF 3 "binary_fp_operator"
14465 [(match_operand:SF 1 "register_operand" "0,0")
14466 (float:SF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14467 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH"
14468 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14469 [(set (attr "type")
14470 (cond [(match_operand:SF 3 "mult_operator" "")
14471 (const_string "fmul")
14472 (match_operand:SF 3 "div_operator" "")
14473 (const_string "fdiv")
14475 (const_string "fop")))
14476 (set_attr "fp_int_src" "true")
14477 (set_attr "mode" "<MODE>")])
14479 (define_insn "*fop_df_comm_mixed"
14480 [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
14481 (match_operator:DF 3 "binary_fp_operator"
14482 [(match_operand:DF 1 "nonimmediate_operand" "%0,0")
14483 (match_operand:DF 2 "nonimmediate_operand" "fm#Y,Ym#f")]))]
14484 "TARGET_SSE2 && TARGET_MIX_SSE_I387
14485 && COMMUTATIVE_ARITH_P (operands[3])
14486 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14487 "* return output_387_binary_op (insn, operands);"
14488 [(set (attr "type")
14489 (if_then_else (eq_attr "alternative" "1")
14490 (if_then_else (match_operand:SF 3 "mult_operator" "")
14491 (const_string "ssemul")
14492 (const_string "sseadd"))
14493 (if_then_else (match_operand:SF 3 "mult_operator" "")
14494 (const_string "fmul")
14495 (const_string "fop"))))
14496 (set_attr "mode" "DF")])
14498 (define_insn "*fop_df_comm_sse"
14499 [(set (match_operand:DF 0 "register_operand" "=Y")
14500 (match_operator:DF 3 "binary_fp_operator"
14501 [(match_operand:DF 1 "nonimmediate_operand" "%0")
14502 (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
14503 "TARGET_SSE2 && TARGET_SSE_MATH
14504 && COMMUTATIVE_ARITH_P (operands[3])
14505 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14506 "* return output_387_binary_op (insn, operands);"
14507 [(set (attr "type")
14508 (if_then_else (match_operand:SF 3 "mult_operator" "")
14509 (const_string "ssemul")
14510 (const_string "sseadd")))
14511 (set_attr "mode" "DF")])
14513 (define_insn "*fop_df_comm_i387"
14514 [(set (match_operand:DF 0 "register_operand" "=f")
14515 (match_operator:DF 3 "binary_fp_operator"
14516 [(match_operand:DF 1 "nonimmediate_operand" "%0")
14517 (match_operand:DF 2 "nonimmediate_operand" "fm")]))]
14519 && COMMUTATIVE_ARITH_P (operands[3])
14520 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14521 "* return output_387_binary_op (insn, operands);"
14522 [(set (attr "type")
14523 (if_then_else (match_operand:SF 3 "mult_operator" "")
14524 (const_string "fmul")
14525 (const_string "fop")))
14526 (set_attr "mode" "DF")])
14528 (define_insn "*fop_df_1_mixed"
14529 [(set (match_operand:DF 0 "register_operand" "=f#Y,f#Y,Y#f")
14530 (match_operator:DF 3 "binary_fp_operator"
14531 [(match_operand:DF 1 "nonimmediate_operand" "0,fm,0")
14532 (match_operand:DF 2 "nonimmediate_operand" "fm,0,Ym#f")]))]
14533 "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
14534 && !COMMUTATIVE_ARITH_P (operands[3])
14535 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14536 "* return output_387_binary_op (insn, operands);"
14537 [(set (attr "type")
14538 (cond [(and (eq_attr "alternative" "2")
14539 (match_operand:SF 3 "mult_operator" ""))
14540 (const_string "ssemul")
14541 (and (eq_attr "alternative" "2")
14542 (match_operand:SF 3 "div_operator" ""))
14543 (const_string "ssediv")
14544 (eq_attr "alternative" "2")
14545 (const_string "sseadd")
14546 (match_operand:DF 3 "mult_operator" "")
14547 (const_string "fmul")
14548 (match_operand:DF 3 "div_operator" "")
14549 (const_string "fdiv")
14551 (const_string "fop")))
14552 (set_attr "mode" "DF")])
14554 (define_insn "*fop_df_1_sse"
14555 [(set (match_operand:DF 0 "register_operand" "=Y")
14556 (match_operator:DF 3 "binary_fp_operator"
14557 [(match_operand:DF 1 "register_operand" "0")
14558 (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
14559 "TARGET_SSE2 && TARGET_SSE_MATH
14560 && !COMMUTATIVE_ARITH_P (operands[3])"
14561 "* return output_387_binary_op (insn, operands);"
14562 [(set_attr "mode" "DF")
14564 (cond [(match_operand:SF 3 "mult_operator" "")
14565 (const_string "ssemul")
14566 (match_operand:SF 3 "div_operator" "")
14567 (const_string "ssediv")
14569 (const_string "sseadd")))])
14571 ;; This pattern is not fully shadowed by the pattern above.
14572 (define_insn "*fop_df_1_i387"
14573 [(set (match_operand:DF 0 "register_operand" "=f,f")
14574 (match_operator:DF 3 "binary_fp_operator"
14575 [(match_operand:DF 1 "nonimmediate_operand" "0,fm")
14576 (match_operand:DF 2 "nonimmediate_operand" "fm,0")]))]
14577 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
14578 && !COMMUTATIVE_ARITH_P (operands[3])
14579 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14580 "* return output_387_binary_op (insn, operands);"
14581 [(set (attr "type")
14582 (cond [(match_operand:DF 3 "mult_operator" "")
14583 (const_string "fmul")
14584 (match_operand:DF 3 "div_operator" "")
14585 (const_string "fdiv")
14587 (const_string "fop")))
14588 (set_attr "mode" "DF")])
14590 ;; ??? Add SSE splitters for these!
14591 (define_insn "*fop_df_2<mode>_i387"
14592 [(set (match_operand:DF 0 "register_operand" "=f,f")
14593 (match_operator:DF 3 "binary_fp_operator"
14594 [(float:DF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14595 (match_operand:DF 2 "register_operand" "0,0")]))]
14596 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
14597 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14598 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14599 [(set (attr "type")
14600 (cond [(match_operand:DF 3 "mult_operator" "")
14601 (const_string "fmul")
14602 (match_operand:DF 3 "div_operator" "")
14603 (const_string "fdiv")
14605 (const_string "fop")))
14606 (set_attr "fp_int_src" "true")
14607 (set_attr "mode" "<MODE>")])
14609 (define_insn "*fop_df_3<mode>_i387"
14610 [(set (match_operand:DF 0 "register_operand" "=f,f")
14611 (match_operator:DF 3 "binary_fp_operator"
14612 [(match_operand:DF 1 "register_operand" "0,0")
14613 (float:DF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14614 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
14615 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14616 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14617 [(set (attr "type")
14618 (cond [(match_operand:DF 3 "mult_operator" "")
14619 (const_string "fmul")
14620 (match_operand:DF 3 "div_operator" "")
14621 (const_string "fdiv")
14623 (const_string "fop")))
14624 (set_attr "fp_int_src" "true")
14625 (set_attr "mode" "<MODE>")])
14627 (define_insn "*fop_df_4_i387"
14628 [(set (match_operand:DF 0 "register_operand" "=f,f")
14629 (match_operator:DF 3 "binary_fp_operator"
14630 [(float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
14631 (match_operand:DF 2 "register_operand" "0,f")]))]
14632 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
14633 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14634 "* return output_387_binary_op (insn, operands);"
14635 [(set (attr "type")
14636 (cond [(match_operand:DF 3 "mult_operator" "")
14637 (const_string "fmul")
14638 (match_operand:DF 3 "div_operator" "")
14639 (const_string "fdiv")
14641 (const_string "fop")))
14642 (set_attr "mode" "SF")])
14644 (define_insn "*fop_df_5_i387"
14645 [(set (match_operand:DF 0 "register_operand" "=f,f")
14646 (match_operator:DF 3 "binary_fp_operator"
14647 [(match_operand:DF 1 "register_operand" "0,f")
14649 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
14650 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14651 "* return output_387_binary_op (insn, operands);"
14652 [(set (attr "type")
14653 (cond [(match_operand:DF 3 "mult_operator" "")
14654 (const_string "fmul")
14655 (match_operand:DF 3 "div_operator" "")
14656 (const_string "fdiv")
14658 (const_string "fop")))
14659 (set_attr "mode" "SF")])
14661 (define_insn "*fop_df_6_i387"
14662 [(set (match_operand:DF 0 "register_operand" "=f,f")
14663 (match_operator:DF 3 "binary_fp_operator"
14665 (match_operand:SF 1 "register_operand" "0,f"))
14667 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
14668 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14669 "* return output_387_binary_op (insn, operands);"
14670 [(set (attr "type")
14671 (cond [(match_operand:DF 3 "mult_operator" "")
14672 (const_string "fmul")
14673 (match_operand:DF 3 "div_operator" "")
14674 (const_string "fdiv")
14676 (const_string "fop")))
14677 (set_attr "mode" "SF")])
14679 (define_insn "*fop_xf_comm_i387"
14680 [(set (match_operand:XF 0 "register_operand" "=f")
14681 (match_operator:XF 3 "binary_fp_operator"
14682 [(match_operand:XF 1 "register_operand" "%0")
14683 (match_operand:XF 2 "register_operand" "f")]))]
14685 && COMMUTATIVE_ARITH_P (operands[3])"
14686 "* return output_387_binary_op (insn, operands);"
14687 [(set (attr "type")
14688 (if_then_else (match_operand:XF 3 "mult_operator" "")
14689 (const_string "fmul")
14690 (const_string "fop")))
14691 (set_attr "mode" "XF")])
14693 (define_insn "*fop_xf_1_i387"
14694 [(set (match_operand:XF 0 "register_operand" "=f,f")
14695 (match_operator:XF 3 "binary_fp_operator"
14696 [(match_operand:XF 1 "register_operand" "0,f")
14697 (match_operand:XF 2 "register_operand" "f,0")]))]
14699 && !COMMUTATIVE_ARITH_P (operands[3])"
14700 "* return output_387_binary_op (insn, operands);"
14701 [(set (attr "type")
14702 (cond [(match_operand:XF 3 "mult_operator" "")
14703 (const_string "fmul")
14704 (match_operand:XF 3 "div_operator" "")
14705 (const_string "fdiv")
14707 (const_string "fop")))
14708 (set_attr "mode" "XF")])
14710 (define_insn "*fop_xf_2<mode>_i387"
14711 [(set (match_operand:XF 0 "register_operand" "=f,f")
14712 (match_operator:XF 3 "binary_fp_operator"
14713 [(float:XF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14714 (match_operand:XF 2 "register_operand" "0,0")]))]
14715 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP"
14716 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14717 [(set (attr "type")
14718 (cond [(match_operand:XF 3 "mult_operator" "")
14719 (const_string "fmul")
14720 (match_operand:XF 3 "div_operator" "")
14721 (const_string "fdiv")
14723 (const_string "fop")))
14724 (set_attr "fp_int_src" "true")
14725 (set_attr "mode" "<MODE>")])
14727 (define_insn "*fop_xf_3<mode>_i387"
14728 [(set (match_operand:XF 0 "register_operand" "=f,f")
14729 (match_operator:XF 3 "binary_fp_operator"
14730 [(match_operand:XF 1 "register_operand" "0,0")
14731 (float:XF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14732 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP"
14733 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14734 [(set (attr "type")
14735 (cond [(match_operand:XF 3 "mult_operator" "")
14736 (const_string "fmul")
14737 (match_operand:XF 3 "div_operator" "")
14738 (const_string "fdiv")
14740 (const_string "fop")))
14741 (set_attr "fp_int_src" "true")
14742 (set_attr "mode" "<MODE>")])
14744 (define_insn "*fop_xf_4_i387"
14745 [(set (match_operand:XF 0 "register_operand" "=f,f")
14746 (match_operator:XF 3 "binary_fp_operator"
14747 [(float_extend:XF (match_operand 1 "nonimmediate_operand" "fm,0"))
14748 (match_operand:XF 2 "register_operand" "0,f")]))]
14750 "* return output_387_binary_op (insn, operands);"
14751 [(set (attr "type")
14752 (cond [(match_operand:XF 3 "mult_operator" "")
14753 (const_string "fmul")
14754 (match_operand:XF 3 "div_operator" "")
14755 (const_string "fdiv")
14757 (const_string "fop")))
14758 (set_attr "mode" "SF")])
14760 (define_insn "*fop_xf_5_i387"
14761 [(set (match_operand:XF 0 "register_operand" "=f,f")
14762 (match_operator:XF 3 "binary_fp_operator"
14763 [(match_operand:XF 1 "register_operand" "0,f")
14765 (match_operand 2 "nonimmediate_operand" "fm,0"))]))]
14767 "* return output_387_binary_op (insn, operands);"
14768 [(set (attr "type")
14769 (cond [(match_operand:XF 3 "mult_operator" "")
14770 (const_string "fmul")
14771 (match_operand:XF 3 "div_operator" "")
14772 (const_string "fdiv")
14774 (const_string "fop")))
14775 (set_attr "mode" "SF")])
14777 (define_insn "*fop_xf_6_i387"
14778 [(set (match_operand:XF 0 "register_operand" "=f,f")
14779 (match_operator:XF 3 "binary_fp_operator"
14781 (match_operand 1 "register_operand" "0,f"))
14783 (match_operand 2 "nonimmediate_operand" "fm,0"))]))]
14785 "* return output_387_binary_op (insn, operands);"
14786 [(set (attr "type")
14787 (cond [(match_operand:XF 3 "mult_operator" "")
14788 (const_string "fmul")
14789 (match_operand:XF 3 "div_operator" "")
14790 (const_string "fdiv")
14792 (const_string "fop")))
14793 (set_attr "mode" "SF")])
14796 [(set (match_operand 0 "register_operand" "")
14797 (match_operator 3 "binary_fp_operator"
14798 [(float (match_operand:X87MODEI12 1 "register_operand" ""))
14799 (match_operand 2 "register_operand" "")]))]
14800 "TARGET_80387 && reload_completed
14801 && FLOAT_MODE_P (GET_MODE (operands[0]))"
14804 operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
14805 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
14806 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
14807 gen_rtx_fmt_ee (GET_CODE (operands[3]),
14808 GET_MODE (operands[3]),
14811 ix86_free_from_memory (GET_MODE (operands[1]));
14816 [(set (match_operand 0 "register_operand" "")
14817 (match_operator 3 "binary_fp_operator"
14818 [(match_operand 1 "register_operand" "")
14819 (float (match_operand:X87MODEI12 2 "register_operand" ""))]))]
14820 "TARGET_80387 && reload_completed
14821 && FLOAT_MODE_P (GET_MODE (operands[0]))"
14824 operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
14825 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
14826 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
14827 gen_rtx_fmt_ee (GET_CODE (operands[3]),
14828 GET_MODE (operands[3]),
14831 ix86_free_from_memory (GET_MODE (operands[2]));
14835 ;; FPU special functions.
14837 (define_expand "sqrtsf2"
14838 [(set (match_operand:SF 0 "register_operand" "")
14839 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
14840 "TARGET_USE_FANCY_MATH_387 || TARGET_SSE_MATH"
14842 if (!TARGET_SSE_MATH)
14843 operands[1] = force_reg (SFmode, operands[1]);
14846 (define_insn "*sqrtsf2_mixed"
14847 [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
14848 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "0#x,xm#f")))]
14849 "TARGET_USE_FANCY_MATH_387 && TARGET_MIX_SSE_I387"
14852 sqrtss\t{%1, %0|%0, %1}"
14853 [(set_attr "type" "fpspc,sse")
14854 (set_attr "mode" "SF,SF")
14855 (set_attr "athlon_decode" "direct,*")])
14857 (define_insn "*sqrtsf2_sse"
14858 [(set (match_operand:SF 0 "register_operand" "=x")
14859 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
14861 "sqrtss\t{%1, %0|%0, %1}"
14862 [(set_attr "type" "sse")
14863 (set_attr "mode" "SF")
14864 (set_attr "athlon_decode" "*")])
14866 (define_insn "*sqrtsf2_i387"
14867 [(set (match_operand:SF 0 "register_operand" "=f")
14868 (sqrt:SF (match_operand:SF 1 "register_operand" "0")))]
14869 "TARGET_USE_FANCY_MATH_387"
14871 [(set_attr "type" "fpspc")
14872 (set_attr "mode" "SF")
14873 (set_attr "athlon_decode" "direct")])
14875 (define_expand "sqrtdf2"
14876 [(set (match_operand:DF 0 "register_operand" "")
14877 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
14878 "TARGET_USE_FANCY_MATH_387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
14880 if (!(TARGET_SSE2 && TARGET_SSE_MATH))
14881 operands[1] = force_reg (DFmode, operands[1]);
14884 (define_insn "*sqrtdf2_mixed"
14885 [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
14886 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "0#Y,Ym#f")))]
14887 "TARGET_USE_FANCY_MATH_387 && TARGET_SSE2 && TARGET_MIX_SSE_I387"
14890 sqrtsd\t{%1, %0|%0, %1}"
14891 [(set_attr "type" "fpspc,sse")
14892 (set_attr "mode" "DF,DF")
14893 (set_attr "athlon_decode" "direct,*")])
14895 (define_insn "*sqrtdf2_sse"
14896 [(set (match_operand:DF 0 "register_operand" "=Y")
14897 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
14898 "TARGET_SSE2 && TARGET_SSE_MATH"
14899 "sqrtsd\t{%1, %0|%0, %1}"
14900 [(set_attr "type" "sse")
14901 (set_attr "mode" "DF")
14902 (set_attr "athlon_decode" "*")])
14904 (define_insn "*sqrtdf2_i387"
14905 [(set (match_operand:DF 0 "register_operand" "=f")
14906 (sqrt:DF (match_operand:DF 1 "register_operand" "0")))]
14907 "TARGET_USE_FANCY_MATH_387"
14909 [(set_attr "type" "fpspc")
14910 (set_attr "mode" "DF")
14911 (set_attr "athlon_decode" "direct")])
14913 (define_insn "*sqrtextendsfdf2_i387"
14914 [(set (match_operand:DF 0 "register_operand" "=f")
14915 (sqrt:DF (float_extend:DF
14916 (match_operand:SF 1 "register_operand" "0"))))]
14917 "TARGET_USE_FANCY_MATH_387
14918 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)"
14920 [(set_attr "type" "fpspc")
14921 (set_attr "mode" "DF")
14922 (set_attr "athlon_decode" "direct")])
14924 (define_insn "sqrtxf2"
14925 [(set (match_operand:XF 0 "register_operand" "=f")
14926 (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
14927 "TARGET_USE_FANCY_MATH_387
14928 && (TARGET_IEEE_FP || flag_unsafe_math_optimizations) "
14930 [(set_attr "type" "fpspc")
14931 (set_attr "mode" "XF")
14932 (set_attr "athlon_decode" "direct")])
14934 (define_insn "*sqrtextendsfxf2_i387"
14935 [(set (match_operand:XF 0 "register_operand" "=f")
14936 (sqrt:XF (float_extend:XF
14937 (match_operand:SF 1 "register_operand" "0"))))]
14938 "TARGET_USE_FANCY_MATH_387"
14940 [(set_attr "type" "fpspc")
14941 (set_attr "mode" "XF")
14942 (set_attr "athlon_decode" "direct")])
14944 (define_insn "*sqrtextenddfxf2_i387"
14945 [(set (match_operand:XF 0 "register_operand" "=f")
14946 (sqrt:XF (float_extend:XF
14947 (match_operand:DF 1 "register_operand" "0"))))]
14948 "TARGET_USE_FANCY_MATH_387"
14950 [(set_attr "type" "fpspc")
14951 (set_attr "mode" "XF")
14952 (set_attr "athlon_decode" "direct")])
14954 (define_insn "fpremxf4"
14955 [(set (match_operand:XF 0 "register_operand" "=f")
14956 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
14957 (match_operand:XF 3 "register_operand" "1")]
14959 (set (match_operand:XF 1 "register_operand" "=u")
14960 (unspec:XF [(match_dup 2) (match_dup 3)]
14962 (set (reg:CCFP FPSR_REG)
14963 (unspec:CCFP [(const_int 0)] UNSPEC_NOP))]
14964 "TARGET_USE_FANCY_MATH_387
14965 && flag_unsafe_math_optimizations"
14967 [(set_attr "type" "fpspc")
14968 (set_attr "mode" "XF")])
14970 (define_expand "fmodsf3"
14971 [(use (match_operand:SF 0 "register_operand" ""))
14972 (use (match_operand:SF 1 "register_operand" ""))
14973 (use (match_operand:SF 2 "register_operand" ""))]
14974 "TARGET_USE_FANCY_MATH_387
14975 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14976 && flag_unsafe_math_optimizations"
14978 rtx label = gen_label_rtx ();
14980 rtx op1 = gen_reg_rtx (XFmode);
14981 rtx op2 = gen_reg_rtx (XFmode);
14983 emit_insn(gen_extendsfxf2 (op1, operands[1]));
14984 emit_insn(gen_extendsfxf2 (op2, operands[2]));
14986 emit_label (label);
14988 emit_insn (gen_fpremxf4 (op1, op2, op1, op2));
14989 ix86_emit_fp_unordered_jump (label);
14991 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op1));
14995 (define_expand "fmoddf3"
14996 [(use (match_operand:DF 0 "register_operand" ""))
14997 (use (match_operand:DF 1 "register_operand" ""))
14998 (use (match_operand:DF 2 "register_operand" ""))]
14999 "TARGET_USE_FANCY_MATH_387
15000 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15001 && flag_unsafe_math_optimizations"
15003 rtx label = gen_label_rtx ();
15005 rtx op1 = gen_reg_rtx (XFmode);
15006 rtx op2 = gen_reg_rtx (XFmode);
15008 emit_insn (gen_extenddfxf2 (op1, operands[1]));
15009 emit_insn (gen_extenddfxf2 (op2, operands[2]));
15011 emit_label (label);
15013 emit_insn (gen_fpremxf4 (op1, op2, op1, op2));
15014 ix86_emit_fp_unordered_jump (label);
15016 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op1));
15020 (define_expand "fmodxf3"
15021 [(use (match_operand:XF 0 "register_operand" ""))
15022 (use (match_operand:XF 1 "register_operand" ""))
15023 (use (match_operand:XF 2 "register_operand" ""))]
15024 "TARGET_USE_FANCY_MATH_387
15025 && flag_unsafe_math_optimizations"
15027 rtx label = gen_label_rtx ();
15029 emit_label (label);
15031 emit_insn (gen_fpremxf4 (operands[1], operands[2],
15032 operands[1], operands[2]));
15033 ix86_emit_fp_unordered_jump (label);
15035 emit_move_insn (operands[0], operands[1]);
15039 (define_insn "fprem1xf4"
15040 [(set (match_operand:XF 0 "register_operand" "=f")
15041 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15042 (match_operand:XF 3 "register_operand" "1")]
15044 (set (match_operand:XF 1 "register_operand" "=u")
15045 (unspec:XF [(match_dup 2) (match_dup 3)]
15047 (set (reg:CCFP FPSR_REG)
15048 (unspec:CCFP [(const_int 0)] UNSPEC_NOP))]
15049 "TARGET_USE_FANCY_MATH_387
15050 && flag_unsafe_math_optimizations"
15052 [(set_attr "type" "fpspc")
15053 (set_attr "mode" "XF")])
15055 (define_expand "dremsf3"
15056 [(use (match_operand:SF 0 "register_operand" ""))
15057 (use (match_operand:SF 1 "register_operand" ""))
15058 (use (match_operand:SF 2 "register_operand" ""))]
15059 "TARGET_USE_FANCY_MATH_387
15060 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15061 && flag_unsafe_math_optimizations"
15063 rtx label = gen_label_rtx ();
15065 rtx op1 = gen_reg_rtx (XFmode);
15066 rtx op2 = gen_reg_rtx (XFmode);
15068 emit_insn(gen_extendsfxf2 (op1, operands[1]));
15069 emit_insn(gen_extendsfxf2 (op2, operands[2]));
15071 emit_label (label);
15073 emit_insn (gen_fprem1xf4 (op1, op2, op1, op2));
15074 ix86_emit_fp_unordered_jump (label);
15076 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op1));
15080 (define_expand "dremdf3"
15081 [(use (match_operand:DF 0 "register_operand" ""))
15082 (use (match_operand:DF 1 "register_operand" ""))
15083 (use (match_operand:DF 2 "register_operand" ""))]
15084 "TARGET_USE_FANCY_MATH_387
15085 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15086 && flag_unsafe_math_optimizations"
15088 rtx label = gen_label_rtx ();
15090 rtx op1 = gen_reg_rtx (XFmode);
15091 rtx op2 = gen_reg_rtx (XFmode);
15093 emit_insn (gen_extenddfxf2 (op1, operands[1]));
15094 emit_insn (gen_extenddfxf2 (op2, operands[2]));
15096 emit_label (label);
15098 emit_insn (gen_fprem1xf4 (op1, op2, op1, op2));
15099 ix86_emit_fp_unordered_jump (label);
15101 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op1));
15105 (define_expand "dremxf3"
15106 [(use (match_operand:XF 0 "register_operand" ""))
15107 (use (match_operand:XF 1 "register_operand" ""))
15108 (use (match_operand:XF 2 "register_operand" ""))]
15109 "TARGET_USE_FANCY_MATH_387
15110 && flag_unsafe_math_optimizations"
15112 rtx label = gen_label_rtx ();
15114 emit_label (label);
15116 emit_insn (gen_fprem1xf4 (operands[1], operands[2],
15117 operands[1], operands[2]));
15118 ix86_emit_fp_unordered_jump (label);
15120 emit_move_insn (operands[0], operands[1]);
15124 (define_insn "*sindf2"
15125 [(set (match_operand:DF 0 "register_operand" "=f")
15126 (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_SIN))]
15127 "TARGET_USE_FANCY_MATH_387
15128 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15129 && flag_unsafe_math_optimizations"
15131 [(set_attr "type" "fpspc")
15132 (set_attr "mode" "DF")])
15134 (define_insn "*sinsf2"
15135 [(set (match_operand:SF 0 "register_operand" "=f")
15136 (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_SIN))]
15137 "TARGET_USE_FANCY_MATH_387
15138 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15139 && flag_unsafe_math_optimizations"
15141 [(set_attr "type" "fpspc")
15142 (set_attr "mode" "SF")])
15144 (define_insn "*sinextendsfdf2"
15145 [(set (match_operand:DF 0 "register_operand" "=f")
15146 (unspec:DF [(float_extend:DF
15147 (match_operand:SF 1 "register_operand" "0"))]
15149 "TARGET_USE_FANCY_MATH_387
15150 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15151 && flag_unsafe_math_optimizations"
15153 [(set_attr "type" "fpspc")
15154 (set_attr "mode" "DF")])
15156 (define_insn "*sinxf2"
15157 [(set (match_operand:XF 0 "register_operand" "=f")
15158 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
15159 "TARGET_USE_FANCY_MATH_387
15160 && flag_unsafe_math_optimizations"
15162 [(set_attr "type" "fpspc")
15163 (set_attr "mode" "XF")])
15165 (define_insn "*cosdf2"
15166 [(set (match_operand:DF 0 "register_operand" "=f")
15167 (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_COS))]
15168 "TARGET_USE_FANCY_MATH_387
15169 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15170 && flag_unsafe_math_optimizations"
15172 [(set_attr "type" "fpspc")
15173 (set_attr "mode" "DF")])
15175 (define_insn "*cossf2"
15176 [(set (match_operand:SF 0 "register_operand" "=f")
15177 (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_COS))]
15178 "TARGET_USE_FANCY_MATH_387
15179 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15180 && flag_unsafe_math_optimizations"
15182 [(set_attr "type" "fpspc")
15183 (set_attr "mode" "SF")])
15185 (define_insn "*cosextendsfdf2"
15186 [(set (match_operand:DF 0 "register_operand" "=f")
15187 (unspec:DF [(float_extend:DF
15188 (match_operand:SF 1 "register_operand" "0"))]
15190 "TARGET_USE_FANCY_MATH_387
15191 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15192 && flag_unsafe_math_optimizations"
15194 [(set_attr "type" "fpspc")
15195 (set_attr "mode" "DF")])
15197 (define_insn "*cosxf2"
15198 [(set (match_operand:XF 0 "register_operand" "=f")
15199 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
15200 "TARGET_USE_FANCY_MATH_387
15201 && flag_unsafe_math_optimizations"
15203 [(set_attr "type" "fpspc")
15204 (set_attr "mode" "XF")])
15206 ;; With sincos pattern defined, sin and cos builtin function will be
15207 ;; expanded to sincos pattern with one of its outputs left unused.
15208 ;; Cse pass will detected, if two sincos patterns can be combined,
15209 ;; otherwise sincos pattern will be split back to sin or cos pattern,
15210 ;; depending on the unused output.
15212 (define_insn "sincosdf3"
15213 [(set (match_operand:DF 0 "register_operand" "=f")
15214 (unspec:DF [(match_operand:DF 2 "register_operand" "0")]
15215 UNSPEC_SINCOS_COS))
15216 (set (match_operand:DF 1 "register_operand" "=u")
15217 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15218 "TARGET_USE_FANCY_MATH_387
15219 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15220 && flag_unsafe_math_optimizations"
15222 [(set_attr "type" "fpspc")
15223 (set_attr "mode" "DF")])
15226 [(set (match_operand:DF 0 "register_operand" "")
15227 (unspec:DF [(match_operand:DF 2 "register_operand" "")]
15228 UNSPEC_SINCOS_COS))
15229 (set (match_operand:DF 1 "register_operand" "")
15230 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15231 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
15232 && !reload_completed && !reload_in_progress"
15233 [(set (match_dup 1) (unspec:DF [(match_dup 2)] UNSPEC_SIN))]
15237 [(set (match_operand:DF 0 "register_operand" "")
15238 (unspec:DF [(match_operand:DF 2 "register_operand" "")]
15239 UNSPEC_SINCOS_COS))
15240 (set (match_operand:DF 1 "register_operand" "")
15241 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15242 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
15243 && !reload_completed && !reload_in_progress"
15244 [(set (match_dup 0) (unspec:DF [(match_dup 2)] UNSPEC_COS))]
15247 (define_insn "sincossf3"
15248 [(set (match_operand:SF 0 "register_operand" "=f")
15249 (unspec:SF [(match_operand:SF 2 "register_operand" "0")]
15250 UNSPEC_SINCOS_COS))
15251 (set (match_operand:SF 1 "register_operand" "=u")
15252 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15253 "TARGET_USE_FANCY_MATH_387
15254 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15255 && flag_unsafe_math_optimizations"
15257 [(set_attr "type" "fpspc")
15258 (set_attr "mode" "SF")])
15261 [(set (match_operand:SF 0 "register_operand" "")
15262 (unspec:SF [(match_operand:SF 2 "register_operand" "")]
15263 UNSPEC_SINCOS_COS))
15264 (set (match_operand:SF 1 "register_operand" "")
15265 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15266 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
15267 && !reload_completed && !reload_in_progress"
15268 [(set (match_dup 1) (unspec:SF [(match_dup 2)] UNSPEC_SIN))]
15272 [(set (match_operand:SF 0 "register_operand" "")
15273 (unspec:SF [(match_operand:SF 2 "register_operand" "")]
15274 UNSPEC_SINCOS_COS))
15275 (set (match_operand:SF 1 "register_operand" "")
15276 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15277 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
15278 && !reload_completed && !reload_in_progress"
15279 [(set (match_dup 0) (unspec:SF [(match_dup 2)] UNSPEC_COS))]
15282 (define_insn "*sincosextendsfdf3"
15283 [(set (match_operand:DF 0 "register_operand" "=f")
15284 (unspec:DF [(float_extend:DF
15285 (match_operand:SF 2 "register_operand" "0"))]
15286 UNSPEC_SINCOS_COS))
15287 (set (match_operand:DF 1 "register_operand" "=u")
15288 (unspec:DF [(float_extend:DF
15289 (match_dup 2))] UNSPEC_SINCOS_SIN))]
15290 "TARGET_USE_FANCY_MATH_387
15291 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15292 && flag_unsafe_math_optimizations"
15294 [(set_attr "type" "fpspc")
15295 (set_attr "mode" "DF")])
15298 [(set (match_operand:DF 0 "register_operand" "")
15299 (unspec:DF [(float_extend:DF
15300 (match_operand:SF 2 "register_operand" ""))]
15301 UNSPEC_SINCOS_COS))
15302 (set (match_operand:DF 1 "register_operand" "")
15303 (unspec:DF [(float_extend:DF
15304 (match_dup 2))] UNSPEC_SINCOS_SIN))]
15305 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
15306 && !reload_completed && !reload_in_progress"
15307 [(set (match_dup 1) (unspec:DF [(float_extend:DF
15308 (match_dup 2))] UNSPEC_SIN))]
15312 [(set (match_operand:DF 0 "register_operand" "")
15313 (unspec:DF [(float_extend:DF
15314 (match_operand:SF 2 "register_operand" ""))]
15315 UNSPEC_SINCOS_COS))
15316 (set (match_operand:DF 1 "register_operand" "")
15317 (unspec:DF [(float_extend:DF
15318 (match_dup 2))] UNSPEC_SINCOS_SIN))]
15319 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
15320 && !reload_completed && !reload_in_progress"
15321 [(set (match_dup 0) (unspec:DF [(float_extend:DF
15322 (match_dup 2))] UNSPEC_COS))]
15325 (define_insn "sincosxf3"
15326 [(set (match_operand:XF 0 "register_operand" "=f")
15327 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15328 UNSPEC_SINCOS_COS))
15329 (set (match_operand:XF 1 "register_operand" "=u")
15330 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15331 "TARGET_USE_FANCY_MATH_387
15332 && flag_unsafe_math_optimizations"
15334 [(set_attr "type" "fpspc")
15335 (set_attr "mode" "XF")])
15338 [(set (match_operand:XF 0 "register_operand" "")
15339 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
15340 UNSPEC_SINCOS_COS))
15341 (set (match_operand:XF 1 "register_operand" "")
15342 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15343 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
15344 && !reload_completed && !reload_in_progress"
15345 [(set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_SIN))]
15349 [(set (match_operand:XF 0 "register_operand" "")
15350 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
15351 UNSPEC_SINCOS_COS))
15352 (set (match_operand:XF 1 "register_operand" "")
15353 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15354 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
15355 && !reload_completed && !reload_in_progress"
15356 [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))]
15359 (define_insn "*tandf3_1"
15360 [(set (match_operand:DF 0 "register_operand" "=f")
15361 (unspec:DF [(match_operand:DF 2 "register_operand" "0")]
15363 (set (match_operand:DF 1 "register_operand" "=u")
15364 (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))]
15365 "TARGET_USE_FANCY_MATH_387
15366 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15367 && flag_unsafe_math_optimizations"
15369 [(set_attr "type" "fpspc")
15370 (set_attr "mode" "DF")])
15372 ;; optimize sequence: fptan
15375 ;; into fptan insn.
15378 [(parallel[(set (match_operand:DF 0 "register_operand" "")
15379 (unspec:DF [(match_operand:DF 2 "register_operand" "")]
15381 (set (match_operand:DF 1 "register_operand" "")
15382 (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))])
15384 (match_operand:DF 3 "immediate_operand" ""))]
15385 "standard_80387_constant_p (operands[3]) == 2"
15386 [(parallel[(set (match_dup 0) (unspec:DF [(match_dup 2)] UNSPEC_TAN_ONE))
15387 (set (match_dup 1) (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15390 (define_expand "tandf2"
15391 [(parallel [(set (match_dup 2)
15392 (unspec:DF [(match_operand:DF 1 "register_operand" "")]
15394 (set (match_operand:DF 0 "register_operand" "")
15395 (unspec:DF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15396 "TARGET_USE_FANCY_MATH_387
15397 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15398 && flag_unsafe_math_optimizations"
15400 operands[2] = gen_reg_rtx (DFmode);
15403 (define_insn "*tansf3_1"
15404 [(set (match_operand:SF 0 "register_operand" "=f")
15405 (unspec:SF [(match_operand:SF 2 "register_operand" "0")]
15407 (set (match_operand:SF 1 "register_operand" "=u")
15408 (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))]
15409 "TARGET_USE_FANCY_MATH_387
15410 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15411 && flag_unsafe_math_optimizations"
15413 [(set_attr "type" "fpspc")
15414 (set_attr "mode" "SF")])
15416 ;; optimize sequence: fptan
15419 ;; into fptan insn.
15422 [(parallel[(set (match_operand:SF 0 "register_operand" "")
15423 (unspec:SF [(match_operand:SF 2 "register_operand" "")]
15425 (set (match_operand:SF 1 "register_operand" "")
15426 (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))])
15428 (match_operand:SF 3 "immediate_operand" ""))]
15429 "standard_80387_constant_p (operands[3]) == 2"
15430 [(parallel[(set (match_dup 0) (unspec:SF [(match_dup 2)] UNSPEC_TAN_ONE))
15431 (set (match_dup 1) (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15434 (define_expand "tansf2"
15435 [(parallel [(set (match_dup 2)
15436 (unspec:SF [(match_operand:SF 1 "register_operand" "")]
15438 (set (match_operand:SF 0 "register_operand" "")
15439 (unspec:SF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15440 "TARGET_USE_FANCY_MATH_387
15441 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15442 && flag_unsafe_math_optimizations"
15444 operands[2] = gen_reg_rtx (SFmode);
15447 (define_insn "*tanxf3_1"
15448 [(set (match_operand:XF 0 "register_operand" "=f")
15449 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15451 (set (match_operand:XF 1 "register_operand" "=u")
15452 (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))]
15453 "TARGET_USE_FANCY_MATH_387
15454 && flag_unsafe_math_optimizations"
15456 [(set_attr "type" "fpspc")
15457 (set_attr "mode" "XF")])
15459 ;; optimize sequence: fptan
15462 ;; into fptan insn.
15465 [(parallel[(set (match_operand:XF 0 "register_operand" "")
15466 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
15468 (set (match_operand:XF 1 "register_operand" "")
15469 (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))])
15471 (match_operand:XF 3 "immediate_operand" ""))]
15472 "standard_80387_constant_p (operands[3]) == 2"
15473 [(parallel[(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_TAN_ONE))
15474 (set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15477 (define_expand "tanxf2"
15478 [(parallel [(set (match_dup 2)
15479 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15481 (set (match_operand:XF 0 "register_operand" "")
15482 (unspec:XF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15483 "TARGET_USE_FANCY_MATH_387
15484 && flag_unsafe_math_optimizations"
15486 operands[2] = gen_reg_rtx (XFmode);
15489 (define_insn "atan2df3_1"
15490 [(set (match_operand:DF 0 "register_operand" "=f")
15491 (unspec:DF [(match_operand:DF 2 "register_operand" "0")
15492 (match_operand:DF 1 "register_operand" "u")]
15494 (clobber (match_scratch:DF 3 "=1"))]
15495 "TARGET_USE_FANCY_MATH_387
15496 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15497 && flag_unsafe_math_optimizations"
15499 [(set_attr "type" "fpspc")
15500 (set_attr "mode" "DF")])
15502 (define_expand "atan2df3"
15503 [(use (match_operand:DF 0 "register_operand" ""))
15504 (use (match_operand:DF 2 "register_operand" ""))
15505 (use (match_operand:DF 1 "register_operand" ""))]
15506 "TARGET_USE_FANCY_MATH_387
15507 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15508 && flag_unsafe_math_optimizations"
15510 rtx copy = gen_reg_rtx (DFmode);
15511 emit_move_insn (copy, operands[1]);
15512 emit_insn (gen_atan2df3_1 (operands[0], copy, operands[2]));
15516 (define_expand "atandf2"
15517 [(parallel [(set (match_operand:DF 0 "register_operand" "")
15518 (unspec:DF [(match_dup 2)
15519 (match_operand:DF 1 "register_operand" "")]
15521 (clobber (match_scratch:DF 3 ""))])]
15522 "TARGET_USE_FANCY_MATH_387
15523 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15524 && flag_unsafe_math_optimizations"
15526 operands[2] = gen_reg_rtx (DFmode);
15527 emit_move_insn (operands[2], CONST1_RTX (DFmode)); /* fld1 */
15530 (define_insn "atan2sf3_1"
15531 [(set (match_operand:SF 0 "register_operand" "=f")
15532 (unspec:SF [(match_operand:SF 2 "register_operand" "0")
15533 (match_operand:SF 1 "register_operand" "u")]
15535 (clobber (match_scratch:SF 3 "=1"))]
15536 "TARGET_USE_FANCY_MATH_387
15537 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15538 && flag_unsafe_math_optimizations"
15540 [(set_attr "type" "fpspc")
15541 (set_attr "mode" "SF")])
15543 (define_expand "atan2sf3"
15544 [(use (match_operand:SF 0 "register_operand" ""))
15545 (use (match_operand:SF 2 "register_operand" ""))
15546 (use (match_operand:SF 1 "register_operand" ""))]
15547 "TARGET_USE_FANCY_MATH_387
15548 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15549 && flag_unsafe_math_optimizations"
15551 rtx copy = gen_reg_rtx (SFmode);
15552 emit_move_insn (copy, operands[1]);
15553 emit_insn (gen_atan2sf3_1 (operands[0], copy, operands[2]));
15557 (define_expand "atansf2"
15558 [(parallel [(set (match_operand:SF 0 "register_operand" "")
15559 (unspec:SF [(match_dup 2)
15560 (match_operand:SF 1 "register_operand" "")]
15562 (clobber (match_scratch:SF 3 ""))])]
15563 "TARGET_USE_FANCY_MATH_387
15564 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15565 && flag_unsafe_math_optimizations"
15567 operands[2] = gen_reg_rtx (SFmode);
15568 emit_move_insn (operands[2], CONST1_RTX (SFmode)); /* fld1 */
15571 (define_insn "atan2xf3_1"
15572 [(set (match_operand:XF 0 "register_operand" "=f")
15573 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15574 (match_operand:XF 1 "register_operand" "u")]
15576 (clobber (match_scratch:XF 3 "=1"))]
15577 "TARGET_USE_FANCY_MATH_387
15578 && flag_unsafe_math_optimizations"
15580 [(set_attr "type" "fpspc")
15581 (set_attr "mode" "XF")])
15583 (define_expand "atan2xf3"
15584 [(use (match_operand:XF 0 "register_operand" ""))
15585 (use (match_operand:XF 2 "register_operand" ""))
15586 (use (match_operand:XF 1 "register_operand" ""))]
15587 "TARGET_USE_FANCY_MATH_387
15588 && flag_unsafe_math_optimizations"
15590 rtx copy = gen_reg_rtx (XFmode);
15591 emit_move_insn (copy, operands[1]);
15592 emit_insn (gen_atan2xf3_1 (operands[0], copy, operands[2]));
15596 (define_expand "atanxf2"
15597 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15598 (unspec:XF [(match_dup 2)
15599 (match_operand:XF 1 "register_operand" "")]
15601 (clobber (match_scratch:XF 3 ""))])]
15602 "TARGET_USE_FANCY_MATH_387
15603 && flag_unsafe_math_optimizations"
15605 operands[2] = gen_reg_rtx (XFmode);
15606 emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
15609 (define_expand "asindf2"
15610 [(set (match_dup 2)
15611 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15612 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15613 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15614 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15615 (parallel [(set (match_dup 7)
15616 (unspec:XF [(match_dup 6) (match_dup 2)]
15618 (clobber (match_scratch:XF 8 ""))])
15619 (set (match_operand:DF 0 "register_operand" "")
15620 (float_truncate:DF (match_dup 7)))]
15621 "TARGET_USE_FANCY_MATH_387
15622 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15623 && flag_unsafe_math_optimizations"
15627 for (i=2; i<8; i++)
15628 operands[i] = gen_reg_rtx (XFmode);
15630 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15633 (define_expand "asinsf2"
15634 [(set (match_dup 2)
15635 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15636 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15637 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15638 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15639 (parallel [(set (match_dup 7)
15640 (unspec:XF [(match_dup 6) (match_dup 2)]
15642 (clobber (match_scratch:XF 8 ""))])
15643 (set (match_operand:SF 0 "register_operand" "")
15644 (float_truncate:SF (match_dup 7)))]
15645 "TARGET_USE_FANCY_MATH_387
15646 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15647 && flag_unsafe_math_optimizations"
15651 for (i=2; i<8; i++)
15652 operands[i] = gen_reg_rtx (XFmode);
15654 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15657 (define_expand "asinxf2"
15658 [(set (match_dup 2)
15659 (mult:XF (match_operand:XF 1 "register_operand" "")
15661 (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
15662 (set (match_dup 5) (sqrt:XF (match_dup 4)))
15663 (parallel [(set (match_operand:XF 0 "register_operand" "")
15664 (unspec:XF [(match_dup 5) (match_dup 1)]
15666 (clobber (match_scratch:XF 6 ""))])]
15667 "TARGET_USE_FANCY_MATH_387
15668 && flag_unsafe_math_optimizations"
15672 for (i=2; i<6; i++)
15673 operands[i] = gen_reg_rtx (XFmode);
15675 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15678 (define_expand "acosdf2"
15679 [(set (match_dup 2)
15680 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15681 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15682 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15683 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15684 (parallel [(set (match_dup 7)
15685 (unspec:XF [(match_dup 2) (match_dup 6)]
15687 (clobber (match_scratch:XF 8 ""))])
15688 (set (match_operand:DF 0 "register_operand" "")
15689 (float_truncate:DF (match_dup 7)))]
15690 "TARGET_USE_FANCY_MATH_387
15691 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15692 && flag_unsafe_math_optimizations"
15696 for (i=2; i<8; i++)
15697 operands[i] = gen_reg_rtx (XFmode);
15699 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15702 (define_expand "acossf2"
15703 [(set (match_dup 2)
15704 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15705 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15706 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15707 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15708 (parallel [(set (match_dup 7)
15709 (unspec:XF [(match_dup 2) (match_dup 6)]
15711 (clobber (match_scratch:XF 8 ""))])
15712 (set (match_operand:SF 0 "register_operand" "")
15713 (float_truncate:SF (match_dup 7)))]
15714 "TARGET_USE_FANCY_MATH_387
15715 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15716 && flag_unsafe_math_optimizations"
15720 for (i=2; i<8; i++)
15721 operands[i] = gen_reg_rtx (XFmode);
15723 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15726 (define_expand "acosxf2"
15727 [(set (match_dup 2)
15728 (mult:XF (match_operand:XF 1 "register_operand" "")
15730 (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
15731 (set (match_dup 5) (sqrt:XF (match_dup 4)))
15732 (parallel [(set (match_operand:XF 0 "register_operand" "")
15733 (unspec:XF [(match_dup 1) (match_dup 5)]
15735 (clobber (match_scratch:XF 6 ""))])]
15736 "TARGET_USE_FANCY_MATH_387
15737 && flag_unsafe_math_optimizations"
15741 for (i=2; i<6; i++)
15742 operands[i] = gen_reg_rtx (XFmode);
15744 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15747 (define_insn "fyl2x_xf3"
15748 [(set (match_operand:XF 0 "register_operand" "=f")
15749 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15750 (match_operand:XF 1 "register_operand" "u")]
15752 (clobber (match_scratch:XF 3 "=1"))]
15753 "TARGET_USE_FANCY_MATH_387
15754 && flag_unsafe_math_optimizations"
15756 [(set_attr "type" "fpspc")
15757 (set_attr "mode" "XF")])
15759 (define_expand "logsf2"
15760 [(set (match_dup 2)
15761 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15762 (parallel [(set (match_dup 4)
15763 (unspec:XF [(match_dup 2)
15764 (match_dup 3)] UNSPEC_FYL2X))
15765 (clobber (match_scratch:XF 5 ""))])
15766 (set (match_operand:SF 0 "register_operand" "")
15767 (float_truncate:SF (match_dup 4)))]
15768 "TARGET_USE_FANCY_MATH_387
15769 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15770 && flag_unsafe_math_optimizations"
15774 operands[2] = gen_reg_rtx (XFmode);
15775 operands[3] = gen_reg_rtx (XFmode);
15776 operands[4] = gen_reg_rtx (XFmode);
15778 temp = standard_80387_constant_rtx (4); /* fldln2 */
15779 emit_move_insn (operands[3], temp);
15782 (define_expand "logdf2"
15783 [(set (match_dup 2)
15784 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15785 (parallel [(set (match_dup 4)
15786 (unspec:XF [(match_dup 2)
15787 (match_dup 3)] UNSPEC_FYL2X))
15788 (clobber (match_scratch:XF 5 ""))])
15789 (set (match_operand:DF 0 "register_operand" "")
15790 (float_truncate:DF (match_dup 4)))]
15791 "TARGET_USE_FANCY_MATH_387
15792 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15793 && flag_unsafe_math_optimizations"
15797 operands[2] = gen_reg_rtx (XFmode);
15798 operands[3] = gen_reg_rtx (XFmode);
15799 operands[4] = gen_reg_rtx (XFmode);
15801 temp = standard_80387_constant_rtx (4); /* fldln2 */
15802 emit_move_insn (operands[3], temp);
15805 (define_expand "logxf2"
15806 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15807 (unspec:XF [(match_operand:XF 1 "register_operand" "")
15808 (match_dup 2)] UNSPEC_FYL2X))
15809 (clobber (match_scratch:XF 3 ""))])]
15810 "TARGET_USE_FANCY_MATH_387
15811 && flag_unsafe_math_optimizations"
15815 operands[2] = gen_reg_rtx (XFmode);
15816 temp = standard_80387_constant_rtx (4); /* fldln2 */
15817 emit_move_insn (operands[2], temp);
15820 (define_expand "log10sf2"
15821 [(set (match_dup 2)
15822 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15823 (parallel [(set (match_dup 4)
15824 (unspec:XF [(match_dup 2)
15825 (match_dup 3)] UNSPEC_FYL2X))
15826 (clobber (match_scratch:XF 5 ""))])
15827 (set (match_operand:SF 0 "register_operand" "")
15828 (float_truncate:SF (match_dup 4)))]
15829 "TARGET_USE_FANCY_MATH_387
15830 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15831 && flag_unsafe_math_optimizations"
15835 operands[2] = gen_reg_rtx (XFmode);
15836 operands[3] = gen_reg_rtx (XFmode);
15837 operands[4] = gen_reg_rtx (XFmode);
15839 temp = standard_80387_constant_rtx (3); /* fldlg2 */
15840 emit_move_insn (operands[3], temp);
15843 (define_expand "log10df2"
15844 [(set (match_dup 2)
15845 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15846 (parallel [(set (match_dup 4)
15847 (unspec:XF [(match_dup 2)
15848 (match_dup 3)] UNSPEC_FYL2X))
15849 (clobber (match_scratch:XF 5 ""))])
15850 (set (match_operand:DF 0 "register_operand" "")
15851 (float_truncate:DF (match_dup 4)))]
15852 "TARGET_USE_FANCY_MATH_387
15853 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15854 && flag_unsafe_math_optimizations"
15858 operands[2] = gen_reg_rtx (XFmode);
15859 operands[3] = gen_reg_rtx (XFmode);
15860 operands[4] = gen_reg_rtx (XFmode);
15862 temp = standard_80387_constant_rtx (3); /* fldlg2 */
15863 emit_move_insn (operands[3], temp);
15866 (define_expand "log10xf2"
15867 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15868 (unspec:XF [(match_operand:XF 1 "register_operand" "")
15869 (match_dup 2)] UNSPEC_FYL2X))
15870 (clobber (match_scratch:XF 3 ""))])]
15871 "TARGET_USE_FANCY_MATH_387
15872 && flag_unsafe_math_optimizations"
15876 operands[2] = gen_reg_rtx (XFmode);
15877 temp = standard_80387_constant_rtx (3); /* fldlg2 */
15878 emit_move_insn (operands[2], temp);
15881 (define_expand "log2sf2"
15882 [(set (match_dup 2)
15883 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15884 (parallel [(set (match_dup 4)
15885 (unspec:XF [(match_dup 2)
15886 (match_dup 3)] UNSPEC_FYL2X))
15887 (clobber (match_scratch:XF 5 ""))])
15888 (set (match_operand:SF 0 "register_operand" "")
15889 (float_truncate:SF (match_dup 4)))]
15890 "TARGET_USE_FANCY_MATH_387
15891 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15892 && flag_unsafe_math_optimizations"
15894 operands[2] = gen_reg_rtx (XFmode);
15895 operands[3] = gen_reg_rtx (XFmode);
15896 operands[4] = gen_reg_rtx (XFmode);
15898 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15901 (define_expand "log2df2"
15902 [(set (match_dup 2)
15903 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15904 (parallel [(set (match_dup 4)
15905 (unspec:XF [(match_dup 2)
15906 (match_dup 3)] UNSPEC_FYL2X))
15907 (clobber (match_scratch:XF 5 ""))])
15908 (set (match_operand:DF 0 "register_operand" "")
15909 (float_truncate:DF (match_dup 4)))]
15910 "TARGET_USE_FANCY_MATH_387
15911 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15912 && flag_unsafe_math_optimizations"
15914 operands[2] = gen_reg_rtx (XFmode);
15915 operands[3] = gen_reg_rtx (XFmode);
15916 operands[4] = gen_reg_rtx (XFmode);
15918 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15921 (define_expand "log2xf2"
15922 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15923 (unspec:XF [(match_operand:XF 1 "register_operand" "")
15924 (match_dup 2)] UNSPEC_FYL2X))
15925 (clobber (match_scratch:XF 3 ""))])]
15926 "TARGET_USE_FANCY_MATH_387
15927 && flag_unsafe_math_optimizations"
15929 operands[2] = gen_reg_rtx (XFmode);
15930 emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
15933 (define_insn "fyl2xp1_xf3"
15934 [(set (match_operand:XF 0 "register_operand" "=f")
15935 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15936 (match_operand:XF 1 "register_operand" "u")]
15938 (clobber (match_scratch:XF 3 "=1"))]
15939 "TARGET_USE_FANCY_MATH_387
15940 && flag_unsafe_math_optimizations"
15942 [(set_attr "type" "fpspc")
15943 (set_attr "mode" "XF")])
15945 (define_expand "log1psf2"
15946 [(use (match_operand:SF 0 "register_operand" ""))
15947 (use (match_operand:SF 1 "register_operand" ""))]
15948 "TARGET_USE_FANCY_MATH_387
15949 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15950 && flag_unsafe_math_optimizations"
15952 rtx op0 = gen_reg_rtx (XFmode);
15953 rtx op1 = gen_reg_rtx (XFmode);
15955 emit_insn (gen_extendsfxf2 (op1, operands[1]));
15956 ix86_emit_i387_log1p (op0, op1);
15957 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
15961 (define_expand "log1pdf2"
15962 [(use (match_operand:DF 0 "register_operand" ""))
15963 (use (match_operand:DF 1 "register_operand" ""))]
15964 "TARGET_USE_FANCY_MATH_387
15965 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15966 && flag_unsafe_math_optimizations"
15968 rtx op0 = gen_reg_rtx (XFmode);
15969 rtx op1 = gen_reg_rtx (XFmode);
15971 emit_insn (gen_extenddfxf2 (op1, operands[1]));
15972 ix86_emit_i387_log1p (op0, op1);
15973 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
15977 (define_expand "log1pxf2"
15978 [(use (match_operand:XF 0 "register_operand" ""))
15979 (use (match_operand:XF 1 "register_operand" ""))]
15980 "TARGET_USE_FANCY_MATH_387
15981 && flag_unsafe_math_optimizations"
15983 ix86_emit_i387_log1p (operands[0], operands[1]);
15987 (define_insn "*fxtractxf3"
15988 [(set (match_operand:XF 0 "register_operand" "=f")
15989 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15990 UNSPEC_XTRACT_FRACT))
15991 (set (match_operand:XF 1 "register_operand" "=u")
15992 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]
15993 "TARGET_USE_FANCY_MATH_387
15994 && flag_unsafe_math_optimizations"
15996 [(set_attr "type" "fpspc")
15997 (set_attr "mode" "XF")])
15999 (define_expand "logbsf2"
16000 [(set (match_dup 2)
16001 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16002 (parallel [(set (match_dup 3)
16003 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_FRACT))
16005 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))])
16006 (set (match_operand:SF 0 "register_operand" "")
16007 (float_truncate:SF (match_dup 4)))]
16008 "TARGET_USE_FANCY_MATH_387
16009 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16010 && flag_unsafe_math_optimizations"
16012 operands[2] = gen_reg_rtx (XFmode);
16013 operands[3] = gen_reg_rtx (XFmode);
16014 operands[4] = gen_reg_rtx (XFmode);
16017 (define_expand "logbdf2"
16018 [(set (match_dup 2)
16019 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16020 (parallel [(set (match_dup 3)
16021 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_FRACT))
16023 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))])
16024 (set (match_operand:DF 0 "register_operand" "")
16025 (float_truncate:DF (match_dup 4)))]
16026 "TARGET_USE_FANCY_MATH_387
16027 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16028 && flag_unsafe_math_optimizations"
16030 operands[2] = gen_reg_rtx (XFmode);
16031 operands[3] = gen_reg_rtx (XFmode);
16032 operands[4] = gen_reg_rtx (XFmode);
16035 (define_expand "logbxf2"
16036 [(parallel [(set (match_dup 2)
16037 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
16038 UNSPEC_XTRACT_FRACT))
16039 (set (match_operand:XF 0 "register_operand" "")
16040 (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
16041 "TARGET_USE_FANCY_MATH_387
16042 && flag_unsafe_math_optimizations"
16044 operands[2] = gen_reg_rtx (XFmode);
16047 (define_expand "ilogbsi2"
16048 [(parallel [(set (match_dup 2)
16049 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
16050 UNSPEC_XTRACT_FRACT))
16051 (set (match_operand:XF 3 "register_operand" "")
16052 (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])
16053 (parallel [(set (match_operand:SI 0 "register_operand" "")
16054 (fix:SI (match_dup 3)))
16055 (clobber (reg:CC FLAGS_REG))])]
16056 "TARGET_USE_FANCY_MATH_387
16057 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16058 && flag_unsafe_math_optimizations"
16060 operands[2] = gen_reg_rtx (XFmode);
16061 operands[3] = gen_reg_rtx (XFmode);
16064 (define_insn "*f2xm1xf2"
16065 [(set (match_operand:XF 0 "register_operand" "=f")
16066 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16068 "TARGET_USE_FANCY_MATH_387
16069 && flag_unsafe_math_optimizations"
16071 [(set_attr "type" "fpspc")
16072 (set_attr "mode" "XF")])
16074 (define_insn "*fscalexf4"
16075 [(set (match_operand:XF 0 "register_operand" "=f")
16076 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
16077 (match_operand:XF 3 "register_operand" "1")]
16078 UNSPEC_FSCALE_FRACT))
16079 (set (match_operand:XF 1 "register_operand" "=u")
16080 (unspec:XF [(match_dup 2) (match_dup 3)]
16081 UNSPEC_FSCALE_EXP))]
16082 "TARGET_USE_FANCY_MATH_387
16083 && flag_unsafe_math_optimizations"
16085 [(set_attr "type" "fpspc")
16086 (set_attr "mode" "XF")])
16088 (define_expand "expsf2"
16089 [(set (match_dup 2)
16090 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16091 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16092 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16093 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16094 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16095 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
16096 (parallel [(set (match_dup 10)
16097 (unspec:XF [(match_dup 9) (match_dup 5)]
16098 UNSPEC_FSCALE_FRACT))
16099 (set (match_dup 11)
16100 (unspec:XF [(match_dup 9) (match_dup 5)]
16101 UNSPEC_FSCALE_EXP))])
16102 (set (match_operand:SF 0 "register_operand" "")
16103 (float_truncate:SF (match_dup 10)))]
16104 "TARGET_USE_FANCY_MATH_387
16105 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16106 && flag_unsafe_math_optimizations"
16111 for (i=2; i<12; i++)
16112 operands[i] = gen_reg_rtx (XFmode);
16113 temp = standard_80387_constant_rtx (5); /* fldl2e */
16114 emit_move_insn (operands[3], temp);
16115 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
16118 (define_expand "expdf2"
16119 [(set (match_dup 2)
16120 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16121 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16122 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16123 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16124 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16125 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
16126 (parallel [(set (match_dup 10)
16127 (unspec:XF [(match_dup 9) (match_dup 5)]
16128 UNSPEC_FSCALE_FRACT))
16129 (set (match_dup 11)
16130 (unspec:XF [(match_dup 9) (match_dup 5)]
16131 UNSPEC_FSCALE_EXP))])
16132 (set (match_operand:DF 0 "register_operand" "")
16133 (float_truncate:DF (match_dup 10)))]
16134 "TARGET_USE_FANCY_MATH_387
16135 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16136 && flag_unsafe_math_optimizations"
16141 for (i=2; i<12; i++)
16142 operands[i] = gen_reg_rtx (XFmode);
16143 temp = standard_80387_constant_rtx (5); /* fldl2e */
16144 emit_move_insn (operands[3], temp);
16145 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
16148 (define_expand "expxf2"
16149 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
16151 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
16152 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
16153 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
16154 (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
16155 (parallel [(set (match_operand:XF 0 "register_operand" "")
16156 (unspec:XF [(match_dup 8) (match_dup 4)]
16157 UNSPEC_FSCALE_FRACT))
16159 (unspec:XF [(match_dup 8) (match_dup 4)]
16160 UNSPEC_FSCALE_EXP))])]
16161 "TARGET_USE_FANCY_MATH_387
16162 && flag_unsafe_math_optimizations"
16167 for (i=2; i<10; i++)
16168 operands[i] = gen_reg_rtx (XFmode);
16169 temp = standard_80387_constant_rtx (5); /* fldl2e */
16170 emit_move_insn (operands[2], temp);
16171 emit_move_insn (operands[7], CONST1_RTX (XFmode)); /* fld1 */
16174 (define_expand "exp10sf2"
16175 [(set (match_dup 2)
16176 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16177 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16178 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16179 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16180 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16181 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
16182 (parallel [(set (match_dup 10)
16183 (unspec:XF [(match_dup 9) (match_dup 5)]
16184 UNSPEC_FSCALE_FRACT))
16185 (set (match_dup 11)
16186 (unspec:XF [(match_dup 9) (match_dup 5)]
16187 UNSPEC_FSCALE_EXP))])
16188 (set (match_operand:SF 0 "register_operand" "")
16189 (float_truncate:SF (match_dup 10)))]
16190 "TARGET_USE_FANCY_MATH_387
16191 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16192 && flag_unsafe_math_optimizations"
16197 for (i=2; i<12; i++)
16198 operands[i] = gen_reg_rtx (XFmode);
16199 temp = standard_80387_constant_rtx (6); /* fldl2t */
16200 emit_move_insn (operands[3], temp);
16201 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
16204 (define_expand "exp10df2"
16205 [(set (match_dup 2)
16206 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16207 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16208 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16209 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16210 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16211 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
16212 (parallel [(set (match_dup 10)
16213 (unspec:XF [(match_dup 9) (match_dup 5)]
16214 UNSPEC_FSCALE_FRACT))
16215 (set (match_dup 11)
16216 (unspec:XF [(match_dup 9) (match_dup 5)]
16217 UNSPEC_FSCALE_EXP))])
16218 (set (match_operand:DF 0 "register_operand" "")
16219 (float_truncate:DF (match_dup 10)))]
16220 "TARGET_USE_FANCY_MATH_387
16221 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16222 && flag_unsafe_math_optimizations"
16227 for (i=2; i<12; i++)
16228 operands[i] = gen_reg_rtx (XFmode);
16229 temp = standard_80387_constant_rtx (6); /* fldl2t */
16230 emit_move_insn (operands[3], temp);
16231 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
16234 (define_expand "exp10xf2"
16235 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
16237 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
16238 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
16239 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
16240 (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
16241 (parallel [(set (match_operand:XF 0 "register_operand" "")
16242 (unspec:XF [(match_dup 8) (match_dup 4)]
16243 UNSPEC_FSCALE_FRACT))
16245 (unspec:XF [(match_dup 8) (match_dup 4)]
16246 UNSPEC_FSCALE_EXP))])]
16247 "TARGET_USE_FANCY_MATH_387
16248 && flag_unsafe_math_optimizations"
16253 for (i=2; i<10; i++)
16254 operands[i] = gen_reg_rtx (XFmode);
16255 temp = standard_80387_constant_rtx (6); /* fldl2t */
16256 emit_move_insn (operands[2], temp);
16257 emit_move_insn (operands[7], CONST1_RTX (XFmode)); /* fld1 */
16260 (define_expand "exp2sf2"
16261 [(set (match_dup 2)
16262 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16263 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
16264 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
16265 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
16266 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
16267 (parallel [(set (match_dup 8)
16268 (unspec:XF [(match_dup 7) (match_dup 3)]
16269 UNSPEC_FSCALE_FRACT))
16271 (unspec:XF [(match_dup 7) (match_dup 3)]
16272 UNSPEC_FSCALE_EXP))])
16273 (set (match_operand:SF 0 "register_operand" "")
16274 (float_truncate:SF (match_dup 8)))]
16275 "TARGET_USE_FANCY_MATH_387
16276 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16277 && flag_unsafe_math_optimizations"
16281 for (i=2; i<10; i++)
16282 operands[i] = gen_reg_rtx (XFmode);
16283 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */
16286 (define_expand "exp2df2"
16287 [(set (match_dup 2)
16288 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16289 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
16290 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
16291 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
16292 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
16293 (parallel [(set (match_dup 8)
16294 (unspec:XF [(match_dup 7) (match_dup 3)]
16295 UNSPEC_FSCALE_FRACT))
16297 (unspec:XF [(match_dup 7) (match_dup 3)]
16298 UNSPEC_FSCALE_EXP))])
16299 (set (match_operand:DF 0 "register_operand" "")
16300 (float_truncate:DF (match_dup 8)))]
16301 "TARGET_USE_FANCY_MATH_387
16302 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16303 && flag_unsafe_math_optimizations"
16307 for (i=2; i<10; i++)
16308 operands[i] = gen_reg_rtx (XFmode);
16309 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */
16312 (define_expand "exp2xf2"
16313 [(set (match_dup 2) (match_operand:XF 1 "register_operand" ""))
16314 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
16315 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
16316 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
16317 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
16318 (parallel [(set (match_operand:XF 0 "register_operand" "")
16319 (unspec:XF [(match_dup 7) (match_dup 3)]
16320 UNSPEC_FSCALE_FRACT))
16322 (unspec:XF [(match_dup 7) (match_dup 3)]
16323 UNSPEC_FSCALE_EXP))])]
16324 "TARGET_USE_FANCY_MATH_387
16325 && flag_unsafe_math_optimizations"
16329 for (i=2; i<9; i++)
16330 operands[i] = gen_reg_rtx (XFmode);
16331 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */
16334 (define_expand "expm1df2"
16335 [(set (match_dup 2)
16336 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16337 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16338 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16339 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16340 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16341 (parallel [(set (match_dup 8)
16342 (unspec:XF [(match_dup 7) (match_dup 5)]
16343 UNSPEC_FSCALE_FRACT))
16345 (unspec:XF [(match_dup 7) (match_dup 5)]
16346 UNSPEC_FSCALE_EXP))])
16347 (parallel [(set (match_dup 11)
16348 (unspec:XF [(match_dup 10) (match_dup 9)]
16349 UNSPEC_FSCALE_FRACT))
16350 (set (match_dup 12)
16351 (unspec:XF [(match_dup 10) (match_dup 9)]
16352 UNSPEC_FSCALE_EXP))])
16353 (set (match_dup 13) (minus:XF (match_dup 11) (match_dup 10)))
16354 (set (match_dup 14) (plus:XF (match_dup 13) (match_dup 8)))
16355 (set (match_operand:DF 0 "register_operand" "")
16356 (float_truncate:DF (match_dup 14)))]
16357 "TARGET_USE_FANCY_MATH_387
16358 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16359 && flag_unsafe_math_optimizations"
16364 for (i=2; i<15; i++)
16365 operands[i] = gen_reg_rtx (XFmode);
16366 temp = standard_80387_constant_rtx (5); /* fldl2e */
16367 emit_move_insn (operands[3], temp);
16368 emit_move_insn (operands[10], CONST1_RTX (XFmode)); /* fld1 */
16371 (define_expand "expm1sf2"
16372 [(set (match_dup 2)
16373 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16374 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16375 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16376 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16377 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16378 (parallel [(set (match_dup 8)
16379 (unspec:XF [(match_dup 7) (match_dup 5)]
16380 UNSPEC_FSCALE_FRACT))
16382 (unspec:XF [(match_dup 7) (match_dup 5)]
16383 UNSPEC_FSCALE_EXP))])
16384 (parallel [(set (match_dup 11)
16385 (unspec:XF [(match_dup 10) (match_dup 9)]
16386 UNSPEC_FSCALE_FRACT))
16387 (set (match_dup 12)
16388 (unspec:XF [(match_dup 10) (match_dup 9)]
16389 UNSPEC_FSCALE_EXP))])
16390 (set (match_dup 13) (minus:XF (match_dup 11) (match_dup 10)))
16391 (set (match_dup 14) (plus:XF (match_dup 13) (match_dup 8)))
16392 (set (match_operand:SF 0 "register_operand" "")
16393 (float_truncate:SF (match_dup 14)))]
16394 "TARGET_USE_FANCY_MATH_387
16395 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16396 && flag_unsafe_math_optimizations"
16401 for (i=2; i<15; i++)
16402 operands[i] = gen_reg_rtx (XFmode);
16403 temp = standard_80387_constant_rtx (5); /* fldl2e */
16404 emit_move_insn (operands[3], temp);
16405 emit_move_insn (operands[10], CONST1_RTX (XFmode)); /* fld1 */
16408 (define_expand "expm1xf2"
16409 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
16411 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
16412 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
16413 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
16414 (parallel [(set (match_dup 7)
16415 (unspec:XF [(match_dup 6) (match_dup 4)]
16416 UNSPEC_FSCALE_FRACT))
16418 (unspec:XF [(match_dup 6) (match_dup 4)]
16419 UNSPEC_FSCALE_EXP))])
16420 (parallel [(set (match_dup 10)
16421 (unspec:XF [(match_dup 9) (match_dup 8)]
16422 UNSPEC_FSCALE_FRACT))
16423 (set (match_dup 11)
16424 (unspec:XF [(match_dup 9) (match_dup 8)]
16425 UNSPEC_FSCALE_EXP))])
16426 (set (match_dup 12) (minus:XF (match_dup 10) (match_dup 9)))
16427 (set (match_operand:XF 0 "register_operand" "")
16428 (plus:XF (match_dup 12) (match_dup 7)))]
16429 "TARGET_USE_FANCY_MATH_387
16430 && flag_unsafe_math_optimizations"
16435 for (i=2; i<13; i++)
16436 operands[i] = gen_reg_rtx (XFmode);
16437 temp = standard_80387_constant_rtx (5); /* fldl2e */
16438 emit_move_insn (operands[2], temp);
16439 emit_move_insn (operands[9], CONST1_RTX (XFmode)); /* fld1 */
16442 (define_expand "ldexpdf3"
16443 [(set (match_dup 3)
16444 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16446 (float:XF (match_operand:SI 2 "register_operand" "")))
16447 (parallel [(set (match_dup 5)
16448 (unspec:XF [(match_dup 3) (match_dup 4)]
16449 UNSPEC_FSCALE_FRACT))
16451 (unspec:XF [(match_dup 3) (match_dup 4)]
16452 UNSPEC_FSCALE_EXP))])
16453 (set (match_operand:DF 0 "register_operand" "")
16454 (float_truncate:DF (match_dup 5)))]
16455 "TARGET_USE_FANCY_MATH_387
16456 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16457 && flag_unsafe_math_optimizations"
16461 for (i=3; i<7; i++)
16462 operands[i] = gen_reg_rtx (XFmode);
16465 (define_expand "ldexpsf3"
16466 [(set (match_dup 3)
16467 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16469 (float:XF (match_operand:SI 2 "register_operand" "")))
16470 (parallel [(set (match_dup 5)
16471 (unspec:XF [(match_dup 3) (match_dup 4)]
16472 UNSPEC_FSCALE_FRACT))
16474 (unspec:XF [(match_dup 3) (match_dup 4)]
16475 UNSPEC_FSCALE_EXP))])
16476 (set (match_operand:SF 0 "register_operand" "")
16477 (float_truncate:SF (match_dup 5)))]
16478 "TARGET_USE_FANCY_MATH_387
16479 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16480 && flag_unsafe_math_optimizations"
16484 for (i=3; i<7; i++)
16485 operands[i] = gen_reg_rtx (XFmode);
16488 (define_expand "ldexpxf3"
16489 [(set (match_dup 3)
16490 (float:XF (match_operand:SI 2 "register_operand" "")))
16491 (parallel [(set (match_operand:XF 0 " register_operand" "")
16492 (unspec:XF [(match_operand:XF 1 "register_operand" "")
16494 UNSPEC_FSCALE_FRACT))
16496 (unspec:XF [(match_dup 1) (match_dup 3)]
16497 UNSPEC_FSCALE_EXP))])]
16498 "TARGET_USE_FANCY_MATH_387
16499 && flag_unsafe_math_optimizations"
16503 for (i=3; i<5; i++)
16504 operands[i] = gen_reg_rtx (XFmode);
16508 (define_insn "frndintxf2"
16509 [(set (match_operand:XF 0 "register_operand" "=f")
16510 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16512 "TARGET_USE_FANCY_MATH_387
16513 && flag_unsafe_math_optimizations"
16515 [(set_attr "type" "fpspc")
16516 (set_attr "mode" "XF")])
16518 (define_expand "rintdf2"
16519 [(use (match_operand:DF 0 "register_operand" ""))
16520 (use (match_operand:DF 1 "register_operand" ""))]
16521 "TARGET_USE_FANCY_MATH_387
16522 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16523 && flag_unsafe_math_optimizations"
16525 rtx op0 = gen_reg_rtx (XFmode);
16526 rtx op1 = gen_reg_rtx (XFmode);
16528 emit_insn (gen_extenddfxf2 (op1, operands[1]));
16529 emit_insn (gen_frndintxf2 (op0, op1));
16531 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16535 (define_expand "rintsf2"
16536 [(use (match_operand:SF 0 "register_operand" ""))
16537 (use (match_operand:SF 1 "register_operand" ""))]
16538 "TARGET_USE_FANCY_MATH_387
16539 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16540 && flag_unsafe_math_optimizations"
16542 rtx op0 = gen_reg_rtx (XFmode);
16543 rtx op1 = gen_reg_rtx (XFmode);
16545 emit_insn (gen_extendsfxf2 (op1, operands[1]));
16546 emit_insn (gen_frndintxf2 (op0, op1));
16548 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16552 (define_expand "rintxf2"
16553 [(use (match_operand:XF 0 "register_operand" ""))
16554 (use (match_operand:XF 1 "register_operand" ""))]
16555 "TARGET_USE_FANCY_MATH_387
16556 && flag_unsafe_math_optimizations"
16558 emit_insn (gen_frndintxf2 (operands[0], operands[1]));
16562 (define_insn_and_split "*fistdi2_1"
16563 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
16564 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
16566 "TARGET_USE_FANCY_MATH_387
16567 && flag_unsafe_math_optimizations
16568 && !(reload_completed || reload_in_progress)"
16573 if (memory_operand (operands[0], VOIDmode))
16574 emit_insn (gen_fistdi2 (operands[0], operands[1]));
16577 operands[2] = assign_386_stack_local (DImode, SLOT_TEMP);
16578 emit_insn (gen_fistdi2_with_temp (operands[0], operands[1],
16583 [(set_attr "type" "fpspc")
16584 (set_attr "mode" "DI")])
16586 (define_insn "fistdi2"
16587 [(set (match_operand:DI 0 "memory_operand" "=m")
16588 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
16590 (clobber (match_scratch:XF 2 "=&1f"))]
16591 "TARGET_USE_FANCY_MATH_387
16592 && flag_unsafe_math_optimizations"
16593 "* return output_fix_trunc (insn, operands, 0);"
16594 [(set_attr "type" "fpspc")
16595 (set_attr "mode" "DI")])
16597 (define_insn "fistdi2_with_temp"
16598 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
16599 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
16601 (clobber (match_operand:DI 2 "memory_operand" "=m,m"))
16602 (clobber (match_scratch:XF 3 "=&1f,&1f"))]
16603 "TARGET_USE_FANCY_MATH_387
16604 && flag_unsafe_math_optimizations"
16606 [(set_attr "type" "fpspc")
16607 (set_attr "mode" "DI")])
16610 [(set (match_operand:DI 0 "register_operand" "")
16611 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16613 (clobber (match_operand:DI 2 "memory_operand" ""))
16614 (clobber (match_scratch 3 ""))]
16616 [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
16617 (clobber (match_dup 3))])
16618 (set (match_dup 0) (match_dup 2))]
16622 [(set (match_operand:DI 0 "memory_operand" "")
16623 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16625 (clobber (match_operand:DI 2 "memory_operand" ""))
16626 (clobber (match_scratch 3 ""))]
16628 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
16629 (clobber (match_dup 3))])]
16632 (define_insn_and_split "*fist<mode>2_1"
16633 [(set (match_operand:X87MODEI12 0 "register_operand" "=r")
16634 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16636 "TARGET_USE_FANCY_MATH_387
16637 && flag_unsafe_math_optimizations
16638 && !(reload_completed || reload_in_progress)"
16643 operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
16644 emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1],
16648 [(set_attr "type" "fpspc")
16649 (set_attr "mode" "<MODE>")])
16651 (define_insn "fist<mode>2"
16652 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
16653 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16655 "TARGET_USE_FANCY_MATH_387
16656 && flag_unsafe_math_optimizations"
16657 "* return output_fix_trunc (insn, operands, 0);"
16658 [(set_attr "type" "fpspc")
16659 (set_attr "mode" "<MODE>")])
16661 (define_insn "fist<mode>2_with_temp"
16662 [(set (match_operand:X87MODEI12 0 "register_operand" "=r")
16663 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16665 (clobber (match_operand:X87MODEI12 2 "memory_operand" "=m"))]
16666 "TARGET_USE_FANCY_MATH_387
16667 && flag_unsafe_math_optimizations"
16669 [(set_attr "type" "fpspc")
16670 (set_attr "mode" "<MODE>")])
16673 [(set (match_operand:X87MODEI12 0 "register_operand" "")
16674 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16676 (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
16678 [(set (match_dup 2) (unspec:X87MODEI12 [(match_dup 1)]
16680 (set (match_dup 0) (match_dup 2))]
16684 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
16685 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16687 (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
16689 [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
16693 (define_expand "lrint<mode>2"
16694 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
16695 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
16697 "TARGET_USE_FANCY_MATH_387
16698 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16699 && flag_unsafe_math_optimizations"
16702 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16703 (define_insn_and_split "frndintxf2_floor"
16704 [(set (match_operand:XF 0 "register_operand" "=f")
16705 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16706 UNSPEC_FRNDINT_FLOOR))
16707 (clobber (reg:CC FLAGS_REG))]
16708 "TARGET_USE_FANCY_MATH_387
16709 && flag_unsafe_math_optimizations
16710 && !(reload_completed || reload_in_progress)"
16715 ix86_optimize_mode_switching[I387_FLOOR] = 1;
16717 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16718 operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
16720 emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1],
16721 operands[2], operands[3]));
16724 [(set_attr "type" "frndint")
16725 (set_attr "i387_cw" "floor")
16726 (set_attr "mode" "XF")])
16728 (define_insn "frndintxf2_floor_i387"
16729 [(set (match_operand:XF 0 "register_operand" "=f")
16730 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16731 UNSPEC_FRNDINT_FLOOR))
16732 (use (match_operand:HI 2 "memory_operand" "m"))
16733 (use (match_operand:HI 3 "memory_operand" "m"))]
16734 "TARGET_USE_FANCY_MATH_387
16735 && flag_unsafe_math_optimizations"
16736 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
16737 [(set_attr "type" "frndint")
16738 (set_attr "i387_cw" "floor")
16739 (set_attr "mode" "XF")])
16741 (define_expand "floorxf2"
16742 [(use (match_operand:XF 0 "register_operand" ""))
16743 (use (match_operand:XF 1 "register_operand" ""))]
16744 "TARGET_USE_FANCY_MATH_387
16745 && flag_unsafe_math_optimizations"
16747 emit_insn (gen_frndintxf2_floor (operands[0], operands[1]));
16751 (define_expand "floordf2"
16752 [(use (match_operand:DF 0 "register_operand" ""))
16753 (use (match_operand:DF 1 "register_operand" ""))]
16754 "TARGET_USE_FANCY_MATH_387
16755 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16756 && flag_unsafe_math_optimizations"
16758 rtx op0 = gen_reg_rtx (XFmode);
16759 rtx op1 = gen_reg_rtx (XFmode);
16761 emit_insn (gen_extenddfxf2 (op1, operands[1]));
16762 emit_insn (gen_frndintxf2_floor (op0, op1));
16764 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16768 (define_expand "floorsf2"
16769 [(use (match_operand:SF 0 "register_operand" ""))
16770 (use (match_operand:SF 1 "register_operand" ""))]
16771 "TARGET_USE_FANCY_MATH_387
16772 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16773 && flag_unsafe_math_optimizations"
16775 rtx op0 = gen_reg_rtx (XFmode);
16776 rtx op1 = gen_reg_rtx (XFmode);
16778 emit_insn (gen_extendsfxf2 (op1, operands[1]));
16779 emit_insn (gen_frndintxf2_floor (op0, op1));
16781 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16785 (define_insn_and_split "*fist<mode>2_floor_1"
16786 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
16787 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "f,f")]
16788 UNSPEC_FIST_FLOOR))
16789 (clobber (reg:CC FLAGS_REG))]
16790 "TARGET_USE_FANCY_MATH_387
16791 && flag_unsafe_math_optimizations
16792 && !(reload_completed || reload_in_progress)"
16797 ix86_optimize_mode_switching[I387_FLOOR] = 1;
16799 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16800 operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
16801 if (memory_operand (operands[0], VOIDmode))
16802 emit_insn (gen_fist<mode>2_floor (operands[0], operands[1],
16803 operands[2], operands[3]));
16806 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
16807 emit_insn (gen_fist<mode>2_floor_with_temp (operands[0], operands[1],
16808 operands[2], operands[3],
16813 [(set_attr "type" "fistp")
16814 (set_attr "i387_cw" "floor")
16815 (set_attr "mode" "<MODE>")])
16817 (define_insn "fistdi2_floor"
16818 [(set (match_operand:DI 0 "memory_operand" "=m")
16819 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
16820 UNSPEC_FIST_FLOOR))
16821 (use (match_operand:HI 2 "memory_operand" "m"))
16822 (use (match_operand:HI 3 "memory_operand" "m"))
16823 (clobber (match_scratch:XF 4 "=&1f"))]
16824 "TARGET_USE_FANCY_MATH_387
16825 && flag_unsafe_math_optimizations"
16826 "* return output_fix_trunc (insn, operands, 0);"
16827 [(set_attr "type" "fistp")
16828 (set_attr "i387_cw" "floor")
16829 (set_attr "mode" "DI")])
16831 (define_insn "fistdi2_floor_with_temp"
16832 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
16833 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
16834 UNSPEC_FIST_FLOOR))
16835 (use (match_operand:HI 2 "memory_operand" "m,m"))
16836 (use (match_operand:HI 3 "memory_operand" "m,m"))
16837 (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
16838 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
16839 "TARGET_USE_FANCY_MATH_387
16840 && flag_unsafe_math_optimizations"
16842 [(set_attr "type" "fistp")
16843 (set_attr "i387_cw" "floor")
16844 (set_attr "mode" "DI")])
16847 [(set (match_operand:DI 0 "register_operand" "")
16848 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16849 UNSPEC_FIST_FLOOR))
16850 (use (match_operand:HI 2 "memory_operand" ""))
16851 (use (match_operand:HI 3 "memory_operand" ""))
16852 (clobber (match_operand:DI 4 "memory_operand" ""))
16853 (clobber (match_scratch 5 ""))]
16855 [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
16856 (use (match_dup 2))
16857 (use (match_dup 3))
16858 (clobber (match_dup 5))])
16859 (set (match_dup 0) (match_dup 4))]
16863 [(set (match_operand:DI 0 "memory_operand" "")
16864 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16865 UNSPEC_FIST_FLOOR))
16866 (use (match_operand:HI 2 "memory_operand" ""))
16867 (use (match_operand:HI 3 "memory_operand" ""))
16868 (clobber (match_operand:DI 4 "memory_operand" ""))
16869 (clobber (match_scratch 5 ""))]
16871 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
16872 (use (match_dup 2))
16873 (use (match_dup 3))
16874 (clobber (match_dup 5))])]
16877 (define_insn "fist<mode>2_floor"
16878 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
16879 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16880 UNSPEC_FIST_FLOOR))
16881 (use (match_operand:HI 2 "memory_operand" "m"))
16882 (use (match_operand:HI 3 "memory_operand" "m"))]
16883 "TARGET_USE_FANCY_MATH_387
16884 && flag_unsafe_math_optimizations"
16885 "* return output_fix_trunc (insn, operands, 0);"
16886 [(set_attr "type" "fistp")
16887 (set_attr "i387_cw" "floor")
16888 (set_attr "mode" "<MODE>")])
16890 (define_insn "fist<mode>2_floor_with_temp"
16891 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
16892 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
16893 UNSPEC_FIST_FLOOR))
16894 (use (match_operand:HI 2 "memory_operand" "m,m"))
16895 (use (match_operand:HI 3 "memory_operand" "m,m"))
16896 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
16897 "TARGET_USE_FANCY_MATH_387
16898 && flag_unsafe_math_optimizations"
16900 [(set_attr "type" "fistp")
16901 (set_attr "i387_cw" "floor")
16902 (set_attr "mode" "<MODE>")])
16905 [(set (match_operand:X87MODEI12 0 "register_operand" "")
16906 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16907 UNSPEC_FIST_FLOOR))
16908 (use (match_operand:HI 2 "memory_operand" ""))
16909 (use (match_operand:HI 3 "memory_operand" ""))
16910 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
16912 [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
16913 UNSPEC_FIST_FLOOR))
16914 (use (match_dup 2))
16915 (use (match_dup 3))])
16916 (set (match_dup 0) (match_dup 4))]
16920 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
16921 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16922 UNSPEC_FIST_FLOOR))
16923 (use (match_operand:HI 2 "memory_operand" ""))
16924 (use (match_operand:HI 3 "memory_operand" ""))
16925 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
16927 [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
16928 UNSPEC_FIST_FLOOR))
16929 (use (match_dup 2))
16930 (use (match_dup 3))])]
16933 (define_expand "lfloor<mode>2"
16934 [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
16935 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
16936 UNSPEC_FIST_FLOOR))
16937 (clobber (reg:CC FLAGS_REG))])]
16938 "TARGET_USE_FANCY_MATH_387
16939 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16940 && flag_unsafe_math_optimizations"
16943 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16944 (define_insn_and_split "frndintxf2_ceil"
16945 [(set (match_operand:XF 0 "register_operand" "=f")
16946 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16947 UNSPEC_FRNDINT_CEIL))
16948 (clobber (reg:CC FLAGS_REG))]
16949 "TARGET_USE_FANCY_MATH_387
16950 && flag_unsafe_math_optimizations
16951 && !(reload_completed || reload_in_progress)"
16956 ix86_optimize_mode_switching[I387_CEIL] = 1;
16958 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16959 operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
16961 emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1],
16962 operands[2], operands[3]));
16965 [(set_attr "type" "frndint")
16966 (set_attr "i387_cw" "ceil")
16967 (set_attr "mode" "XF")])
16969 (define_insn "frndintxf2_ceil_i387"
16970 [(set (match_operand:XF 0 "register_operand" "=f")
16971 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16972 UNSPEC_FRNDINT_CEIL))
16973 (use (match_operand:HI 2 "memory_operand" "m"))
16974 (use (match_operand:HI 3 "memory_operand" "m"))]
16975 "TARGET_USE_FANCY_MATH_387
16976 && flag_unsafe_math_optimizations"
16977 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
16978 [(set_attr "type" "frndint")
16979 (set_attr "i387_cw" "ceil")
16980 (set_attr "mode" "XF")])
16982 (define_expand "ceilxf2"
16983 [(use (match_operand:XF 0 "register_operand" ""))
16984 (use (match_operand:XF 1 "register_operand" ""))]
16985 "TARGET_USE_FANCY_MATH_387
16986 && flag_unsafe_math_optimizations"
16988 emit_insn (gen_frndintxf2_ceil (operands[0], operands[1]));
16992 (define_expand "ceildf2"
16993 [(use (match_operand:DF 0 "register_operand" ""))
16994 (use (match_operand:DF 1 "register_operand" ""))]
16995 "TARGET_USE_FANCY_MATH_387
16996 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16997 && flag_unsafe_math_optimizations"
16999 rtx op0 = gen_reg_rtx (XFmode);
17000 rtx op1 = gen_reg_rtx (XFmode);
17002 emit_insn (gen_extenddfxf2 (op1, operands[1]));
17003 emit_insn (gen_frndintxf2_ceil (op0, op1));
17005 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
17009 (define_expand "ceilsf2"
17010 [(use (match_operand:SF 0 "register_operand" ""))
17011 (use (match_operand:SF 1 "register_operand" ""))]
17012 "TARGET_USE_FANCY_MATH_387
17013 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
17014 && flag_unsafe_math_optimizations"
17016 rtx op0 = gen_reg_rtx (XFmode);
17017 rtx op1 = gen_reg_rtx (XFmode);
17019 emit_insn (gen_extendsfxf2 (op1, operands[1]));
17020 emit_insn (gen_frndintxf2_ceil (op0, op1));
17022 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
17026 (define_insn_and_split "*fist<mode>2_ceil_1"
17027 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
17028 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "f,f")]
17030 (clobber (reg:CC FLAGS_REG))]
17031 "TARGET_USE_FANCY_MATH_387
17032 && flag_unsafe_math_optimizations
17033 && !(reload_completed || reload_in_progress)"
17038 ix86_optimize_mode_switching[I387_CEIL] = 1;
17040 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17041 operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
17042 if (memory_operand (operands[0], VOIDmode))
17043 emit_insn (gen_fist<mode>2_ceil (operands[0], operands[1],
17044 operands[2], operands[3]));
17047 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
17048 emit_insn (gen_fist<mode>2_ceil_with_temp (operands[0], operands[1],
17049 operands[2], operands[3],
17054 [(set_attr "type" "fistp")
17055 (set_attr "i387_cw" "ceil")
17056 (set_attr "mode" "<MODE>")])
17058 (define_insn "fistdi2_ceil"
17059 [(set (match_operand:DI 0 "memory_operand" "=m")
17060 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
17062 (use (match_operand:HI 2 "memory_operand" "m"))
17063 (use (match_operand:HI 3 "memory_operand" "m"))
17064 (clobber (match_scratch:XF 4 "=&1f"))]
17065 "TARGET_USE_FANCY_MATH_387
17066 && flag_unsafe_math_optimizations"
17067 "* return output_fix_trunc (insn, operands, 0);"
17068 [(set_attr "type" "fistp")
17069 (set_attr "i387_cw" "ceil")
17070 (set_attr "mode" "DI")])
17072 (define_insn "fistdi2_ceil_with_temp"
17073 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
17074 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
17076 (use (match_operand:HI 2 "memory_operand" "m,m"))
17077 (use (match_operand:HI 3 "memory_operand" "m,m"))
17078 (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
17079 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
17080 "TARGET_USE_FANCY_MATH_387
17081 && flag_unsafe_math_optimizations"
17083 [(set_attr "type" "fistp")
17084 (set_attr "i387_cw" "ceil")
17085 (set_attr "mode" "DI")])
17088 [(set (match_operand:DI 0 "register_operand" "")
17089 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17091 (use (match_operand:HI 2 "memory_operand" ""))
17092 (use (match_operand:HI 3 "memory_operand" ""))
17093 (clobber (match_operand:DI 4 "memory_operand" ""))
17094 (clobber (match_scratch 5 ""))]
17096 [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
17097 (use (match_dup 2))
17098 (use (match_dup 3))
17099 (clobber (match_dup 5))])
17100 (set (match_dup 0) (match_dup 4))]
17104 [(set (match_operand:DI 0 "memory_operand" "")
17105 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17107 (use (match_operand:HI 2 "memory_operand" ""))
17108 (use (match_operand:HI 3 "memory_operand" ""))
17109 (clobber (match_operand:DI 4 "memory_operand" ""))
17110 (clobber (match_scratch 5 ""))]
17112 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
17113 (use (match_dup 2))
17114 (use (match_dup 3))
17115 (clobber (match_dup 5))])]
17118 (define_insn "fist<mode>2_ceil"
17119 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
17120 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
17122 (use (match_operand:HI 2 "memory_operand" "m"))
17123 (use (match_operand:HI 3 "memory_operand" "m"))]
17124 "TARGET_USE_FANCY_MATH_387
17125 && flag_unsafe_math_optimizations"
17126 "* return output_fix_trunc (insn, operands, 0);"
17127 [(set_attr "type" "fistp")
17128 (set_attr "i387_cw" "ceil")
17129 (set_attr "mode" "<MODE>")])
17131 (define_insn "fist<mode>2_ceil_with_temp"
17132 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
17133 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
17135 (use (match_operand:HI 2 "memory_operand" "m,m"))
17136 (use (match_operand:HI 3 "memory_operand" "m,m"))
17137 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
17138 "TARGET_USE_FANCY_MATH_387
17139 && flag_unsafe_math_optimizations"
17141 [(set_attr "type" "fistp")
17142 (set_attr "i387_cw" "ceil")
17143 (set_attr "mode" "<MODE>")])
17146 [(set (match_operand:X87MODEI12 0 "register_operand" "")
17147 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17149 (use (match_operand:HI 2 "memory_operand" ""))
17150 (use (match_operand:HI 3 "memory_operand" ""))
17151 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
17153 [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
17155 (use (match_dup 2))
17156 (use (match_dup 3))])
17157 (set (match_dup 0) (match_dup 4))]
17161 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
17162 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17164 (use (match_operand:HI 2 "memory_operand" ""))
17165 (use (match_operand:HI 3 "memory_operand" ""))
17166 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
17168 [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
17170 (use (match_dup 2))
17171 (use (match_dup 3))])]
17174 (define_expand "lceil<mode>2"
17175 [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
17176 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
17178 (clobber (reg:CC FLAGS_REG))])]
17179 "TARGET_USE_FANCY_MATH_387
17180 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
17181 && flag_unsafe_math_optimizations"
17184 ;; Rounding mode control word calculation could clobber FLAGS_REG.
17185 (define_insn_and_split "frndintxf2_trunc"
17186 [(set (match_operand:XF 0 "register_operand" "=f")
17187 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17188 UNSPEC_FRNDINT_TRUNC))
17189 (clobber (reg:CC FLAGS_REG))]
17190 "TARGET_USE_FANCY_MATH_387
17191 && flag_unsafe_math_optimizations
17192 && !(reload_completed || reload_in_progress)"
17197 ix86_optimize_mode_switching[I387_TRUNC] = 1;
17199 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17200 operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
17202 emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1],
17203 operands[2], operands[3]));
17206 [(set_attr "type" "frndint")
17207 (set_attr "i387_cw" "trunc")
17208 (set_attr "mode" "XF")])
17210 (define_insn "frndintxf2_trunc_i387"
17211 [(set (match_operand:XF 0 "register_operand" "=f")
17212 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17213 UNSPEC_FRNDINT_TRUNC))
17214 (use (match_operand:HI 2 "memory_operand" "m"))
17215 (use (match_operand:HI 3 "memory_operand" "m"))]
17216 "TARGET_USE_FANCY_MATH_387
17217 && flag_unsafe_math_optimizations"
17218 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
17219 [(set_attr "type" "frndint")
17220 (set_attr "i387_cw" "trunc")
17221 (set_attr "mode" "XF")])
17223 (define_expand "btruncxf2"
17224 [(use (match_operand:XF 0 "register_operand" ""))
17225 (use (match_operand:XF 1 "register_operand" ""))]
17226 "TARGET_USE_FANCY_MATH_387
17227 && flag_unsafe_math_optimizations"
17229 emit_insn (gen_frndintxf2_trunc (operands[0], operands[1]));
17233 (define_expand "btruncdf2"
17234 [(use (match_operand:DF 0 "register_operand" ""))
17235 (use (match_operand:DF 1 "register_operand" ""))]
17236 "TARGET_USE_FANCY_MATH_387
17237 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
17238 && flag_unsafe_math_optimizations"
17240 rtx op0 = gen_reg_rtx (XFmode);
17241 rtx op1 = gen_reg_rtx (XFmode);
17243 emit_insn (gen_extenddfxf2 (op1, operands[1]));
17244 emit_insn (gen_frndintxf2_trunc (op0, op1));
17246 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
17250 (define_expand "btruncsf2"
17251 [(use (match_operand:SF 0 "register_operand" ""))
17252 (use (match_operand:SF 1 "register_operand" ""))]
17253 "TARGET_USE_FANCY_MATH_387
17254 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
17255 && flag_unsafe_math_optimizations"
17257 rtx op0 = gen_reg_rtx (XFmode);
17258 rtx op1 = gen_reg_rtx (XFmode);
17260 emit_insn (gen_extendsfxf2 (op1, operands[1]));
17261 emit_insn (gen_frndintxf2_trunc (op0, op1));
17263 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
17267 ;; Rounding mode control word calculation could clobber FLAGS_REG.
17268 (define_insn_and_split "frndintxf2_mask_pm"
17269 [(set (match_operand:XF 0 "register_operand" "=f")
17270 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17271 UNSPEC_FRNDINT_MASK_PM))
17272 (clobber (reg:CC FLAGS_REG))]
17273 "TARGET_USE_FANCY_MATH_387
17274 && flag_unsafe_math_optimizations
17275 && !(reload_completed || reload_in_progress)"
17280 ix86_optimize_mode_switching[I387_MASK_PM] = 1;
17282 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17283 operands[3] = assign_386_stack_local (HImode, SLOT_CW_MASK_PM);
17285 emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1],
17286 operands[2], operands[3]));
17289 [(set_attr "type" "frndint")
17290 (set_attr "i387_cw" "mask_pm")
17291 (set_attr "mode" "XF")])
17293 (define_insn "frndintxf2_mask_pm_i387"
17294 [(set (match_operand:XF 0 "register_operand" "=f")
17295 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17296 UNSPEC_FRNDINT_MASK_PM))
17297 (use (match_operand:HI 2 "memory_operand" "m"))
17298 (use (match_operand:HI 3 "memory_operand" "m"))]
17299 "TARGET_USE_FANCY_MATH_387
17300 && flag_unsafe_math_optimizations"
17301 "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2"
17302 [(set_attr "type" "frndint")
17303 (set_attr "i387_cw" "mask_pm")
17304 (set_attr "mode" "XF")])
17306 (define_expand "nearbyintxf2"
17307 [(use (match_operand:XF 0 "register_operand" ""))
17308 (use (match_operand:XF 1 "register_operand" ""))]
17309 "TARGET_USE_FANCY_MATH_387
17310 && flag_unsafe_math_optimizations"
17312 emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1]));
17317 (define_expand "nearbyintdf2"
17318 [(use (match_operand:DF 0 "register_operand" ""))
17319 (use (match_operand:DF 1 "register_operand" ""))]
17320 "TARGET_USE_FANCY_MATH_387
17321 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
17322 && flag_unsafe_math_optimizations"
17324 rtx op0 = gen_reg_rtx (XFmode);
17325 rtx op1 = gen_reg_rtx (XFmode);
17327 emit_insn (gen_extenddfxf2 (op1, operands[1]));
17328 emit_insn (gen_frndintxf2_mask_pm (op0, op1));
17330 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
17334 (define_expand "nearbyintsf2"
17335 [(use (match_operand:SF 0 "register_operand" ""))
17336 (use (match_operand:SF 1 "register_operand" ""))]
17337 "TARGET_USE_FANCY_MATH_387
17338 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
17339 && flag_unsafe_math_optimizations"
17341 rtx op0 = gen_reg_rtx (XFmode);
17342 rtx op1 = gen_reg_rtx (XFmode);
17344 emit_insn (gen_extendsfxf2 (op1, operands[1]));
17345 emit_insn (gen_frndintxf2_mask_pm (op0, op1));
17347 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
17352 ;; Block operation instructions
17355 [(set (reg:SI DIRFLAG_REG) (const_int 0))]
17358 [(set_attr "type" "cld")])
17360 (define_expand "movmemsi"
17361 [(use (match_operand:BLK 0 "memory_operand" ""))
17362 (use (match_operand:BLK 1 "memory_operand" ""))
17363 (use (match_operand:SI 2 "nonmemory_operand" ""))
17364 (use (match_operand:SI 3 "const_int_operand" ""))]
17365 "! optimize_size || TARGET_INLINE_ALL_STRINGOPS"
17367 if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3]))
17373 (define_expand "movmemdi"
17374 [(use (match_operand:BLK 0 "memory_operand" ""))
17375 (use (match_operand:BLK 1 "memory_operand" ""))
17376 (use (match_operand:DI 2 "nonmemory_operand" ""))
17377 (use (match_operand:DI 3 "const_int_operand" ""))]
17380 if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3]))
17386 ;; Most CPUs don't like single string operations
17387 ;; Handle this case here to simplify previous expander.
17389 (define_expand "strmov"
17390 [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
17391 (set (match_operand 1 "memory_operand" "") (match_dup 4))
17392 (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
17393 (clobber (reg:CC FLAGS_REG))])
17394 (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
17395 (clobber (reg:CC FLAGS_REG))])]
17398 rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
17400 /* If .md ever supports :P for Pmode, these can be directly
17401 in the pattern above. */
17402 operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
17403 operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
17405 if (TARGET_SINGLE_STRINGOP || optimize_size)
17407 emit_insn (gen_strmov_singleop (operands[0], operands[1],
17408 operands[2], operands[3],
17409 operands[5], operands[6]));
17413 operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
17416 (define_expand "strmov_singleop"
17417 [(parallel [(set (match_operand 1 "memory_operand" "")
17418 (match_operand 3 "memory_operand" ""))
17419 (set (match_operand 0 "register_operand" "")
17420 (match_operand 4 "" ""))
17421 (set (match_operand 2 "register_operand" "")
17422 (match_operand 5 "" ""))
17423 (use (reg:SI DIRFLAG_REG))])]
17424 "TARGET_SINGLE_STRINGOP || optimize_size"
17427 (define_insn "*strmovdi_rex_1"
17428 [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
17429 (mem:DI (match_operand:DI 3 "register_operand" "1")))
17430 (set (match_operand:DI 0 "register_operand" "=D")
17431 (plus:DI (match_dup 2)
17433 (set (match_operand:DI 1 "register_operand" "=S")
17434 (plus:DI (match_dup 3)
17436 (use (reg:SI DIRFLAG_REG))]
17437 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17439 [(set_attr "type" "str")
17440 (set_attr "mode" "DI")
17441 (set_attr "memory" "both")])
17443 (define_insn "*strmovsi_1"
17444 [(set (mem:SI (match_operand:SI 2 "register_operand" "0"))
17445 (mem:SI (match_operand:SI 3 "register_operand" "1")))
17446 (set (match_operand:SI 0 "register_operand" "=D")
17447 (plus:SI (match_dup 2)
17449 (set (match_operand:SI 1 "register_operand" "=S")
17450 (plus:SI (match_dup 3)
17452 (use (reg:SI DIRFLAG_REG))]
17453 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17455 [(set_attr "type" "str")
17456 (set_attr "mode" "SI")
17457 (set_attr "memory" "both")])
17459 (define_insn "*strmovsi_rex_1"
17460 [(set (mem:SI (match_operand:DI 2 "register_operand" "0"))
17461 (mem:SI (match_operand:DI 3 "register_operand" "1")))
17462 (set (match_operand:DI 0 "register_operand" "=D")
17463 (plus:DI (match_dup 2)
17465 (set (match_operand:DI 1 "register_operand" "=S")
17466 (plus:DI (match_dup 3)
17468 (use (reg:SI DIRFLAG_REG))]
17469 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17471 [(set_attr "type" "str")
17472 (set_attr "mode" "SI")
17473 (set_attr "memory" "both")])
17475 (define_insn "*strmovhi_1"
17476 [(set (mem:HI (match_operand:SI 2 "register_operand" "0"))
17477 (mem:HI (match_operand:SI 3 "register_operand" "1")))
17478 (set (match_operand:SI 0 "register_operand" "=D")
17479 (plus:SI (match_dup 2)
17481 (set (match_operand:SI 1 "register_operand" "=S")
17482 (plus:SI (match_dup 3)
17484 (use (reg:SI DIRFLAG_REG))]
17485 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17487 [(set_attr "type" "str")
17488 (set_attr "memory" "both")
17489 (set_attr "mode" "HI")])
17491 (define_insn "*strmovhi_rex_1"
17492 [(set (mem:HI (match_operand:DI 2 "register_operand" "0"))
17493 (mem:HI (match_operand:DI 3 "register_operand" "1")))
17494 (set (match_operand:DI 0 "register_operand" "=D")
17495 (plus:DI (match_dup 2)
17497 (set (match_operand:DI 1 "register_operand" "=S")
17498 (plus:DI (match_dup 3)
17500 (use (reg:SI DIRFLAG_REG))]
17501 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17503 [(set_attr "type" "str")
17504 (set_attr "memory" "both")
17505 (set_attr "mode" "HI")])
17507 (define_insn "*strmovqi_1"
17508 [(set (mem:QI (match_operand:SI 2 "register_operand" "0"))
17509 (mem:QI (match_operand:SI 3 "register_operand" "1")))
17510 (set (match_operand:SI 0 "register_operand" "=D")
17511 (plus:SI (match_dup 2)
17513 (set (match_operand:SI 1 "register_operand" "=S")
17514 (plus:SI (match_dup 3)
17516 (use (reg:SI DIRFLAG_REG))]
17517 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17519 [(set_attr "type" "str")
17520 (set_attr "memory" "both")
17521 (set_attr "mode" "QI")])
17523 (define_insn "*strmovqi_rex_1"
17524 [(set (mem:QI (match_operand:DI 2 "register_operand" "0"))
17525 (mem:QI (match_operand:DI 3 "register_operand" "1")))
17526 (set (match_operand:DI 0 "register_operand" "=D")
17527 (plus:DI (match_dup 2)
17529 (set (match_operand:DI 1 "register_operand" "=S")
17530 (plus:DI (match_dup 3)
17532 (use (reg:SI DIRFLAG_REG))]
17533 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17535 [(set_attr "type" "str")
17536 (set_attr "memory" "both")
17537 (set_attr "mode" "QI")])
17539 (define_expand "rep_mov"
17540 [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
17541 (set (match_operand 0 "register_operand" "")
17542 (match_operand 5 "" ""))
17543 (set (match_operand 2 "register_operand" "")
17544 (match_operand 6 "" ""))
17545 (set (match_operand 1 "memory_operand" "")
17546 (match_operand 3 "memory_operand" ""))
17547 (use (match_dup 4))
17548 (use (reg:SI DIRFLAG_REG))])]
17552 (define_insn "*rep_movdi_rex64"
17553 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
17554 (set (match_operand:DI 0 "register_operand" "=D")
17555 (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
17557 (match_operand:DI 3 "register_operand" "0")))
17558 (set (match_operand:DI 1 "register_operand" "=S")
17559 (plus:DI (ashift:DI (match_dup 5) (const_int 3))
17560 (match_operand:DI 4 "register_operand" "1")))
17561 (set (mem:BLK (match_dup 3))
17562 (mem:BLK (match_dup 4)))
17563 (use (match_dup 5))
17564 (use (reg:SI DIRFLAG_REG))]
17566 "{rep\;movsq|rep movsq}"
17567 [(set_attr "type" "str")
17568 (set_attr "prefix_rep" "1")
17569 (set_attr "memory" "both")
17570 (set_attr "mode" "DI")])
17572 (define_insn "*rep_movsi"
17573 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
17574 (set (match_operand:SI 0 "register_operand" "=D")
17575 (plus:SI (ashift:SI (match_operand:SI 5 "register_operand" "2")
17577 (match_operand:SI 3 "register_operand" "0")))
17578 (set (match_operand:SI 1 "register_operand" "=S")
17579 (plus:SI (ashift:SI (match_dup 5) (const_int 2))
17580 (match_operand:SI 4 "register_operand" "1")))
17581 (set (mem:BLK (match_dup 3))
17582 (mem:BLK (match_dup 4)))
17583 (use (match_dup 5))
17584 (use (reg:SI DIRFLAG_REG))]
17586 "{rep\;movsl|rep movsd}"
17587 [(set_attr "type" "str")
17588 (set_attr "prefix_rep" "1")
17589 (set_attr "memory" "both")
17590 (set_attr "mode" "SI")])
17592 (define_insn "*rep_movsi_rex64"
17593 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
17594 (set (match_operand:DI 0 "register_operand" "=D")
17595 (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
17597 (match_operand:DI 3 "register_operand" "0")))
17598 (set (match_operand:DI 1 "register_operand" "=S")
17599 (plus:DI (ashift:DI (match_dup 5) (const_int 2))
17600 (match_operand:DI 4 "register_operand" "1")))
17601 (set (mem:BLK (match_dup 3))
17602 (mem:BLK (match_dup 4)))
17603 (use (match_dup 5))
17604 (use (reg:SI DIRFLAG_REG))]
17606 "{rep\;movsl|rep movsd}"
17607 [(set_attr "type" "str")
17608 (set_attr "prefix_rep" "1")
17609 (set_attr "memory" "both")
17610 (set_attr "mode" "SI")])
17612 (define_insn "*rep_movqi"
17613 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
17614 (set (match_operand:SI 0 "register_operand" "=D")
17615 (plus:SI (match_operand:SI 3 "register_operand" "0")
17616 (match_operand:SI 5 "register_operand" "2")))
17617 (set (match_operand:SI 1 "register_operand" "=S")
17618 (plus:SI (match_operand:SI 4 "register_operand" "1") (match_dup 5)))
17619 (set (mem:BLK (match_dup 3))
17620 (mem:BLK (match_dup 4)))
17621 (use (match_dup 5))
17622 (use (reg:SI DIRFLAG_REG))]
17624 "{rep\;movsb|rep movsb}"
17625 [(set_attr "type" "str")
17626 (set_attr "prefix_rep" "1")
17627 (set_attr "memory" "both")
17628 (set_attr "mode" "SI")])
17630 (define_insn "*rep_movqi_rex64"
17631 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
17632 (set (match_operand:DI 0 "register_operand" "=D")
17633 (plus:DI (match_operand:DI 3 "register_operand" "0")
17634 (match_operand:DI 5 "register_operand" "2")))
17635 (set (match_operand:DI 1 "register_operand" "=S")
17636 (plus:DI (match_operand:DI 4 "register_operand" "1") (match_dup 5)))
17637 (set (mem:BLK (match_dup 3))
17638 (mem:BLK (match_dup 4)))
17639 (use (match_dup 5))
17640 (use (reg:SI DIRFLAG_REG))]
17642 "{rep\;movsb|rep movsb}"
17643 [(set_attr "type" "str")
17644 (set_attr "prefix_rep" "1")
17645 (set_attr "memory" "both")
17646 (set_attr "mode" "SI")])
17648 (define_expand "setmemsi"
17649 [(use (match_operand:BLK 0 "memory_operand" ""))
17650 (use (match_operand:SI 1 "nonmemory_operand" ""))
17651 (use (match_operand 2 "const_int_operand" ""))
17652 (use (match_operand 3 "const_int_operand" ""))]
17655 /* If value to set is not zero, use the library routine. */
17656 if (operands[2] != const0_rtx)
17659 if (ix86_expand_clrmem (operands[0], operands[1], operands[3]))
17665 (define_expand "setmemdi"
17666 [(use (match_operand:BLK 0 "memory_operand" ""))
17667 (use (match_operand:DI 1 "nonmemory_operand" ""))
17668 (use (match_operand 2 "const_int_operand" ""))
17669 (use (match_operand 3 "const_int_operand" ""))]
17672 /* If value to set is not zero, use the library routine. */
17673 if (operands[2] != const0_rtx)
17676 if (ix86_expand_clrmem (operands[0], operands[1], operands[3]))
17682 ;; Most CPUs don't like single string operations
17683 ;; Handle this case here to simplify previous expander.
17685 (define_expand "strset"
17686 [(set (match_operand 1 "memory_operand" "")
17687 (match_operand 2 "register_operand" ""))
17688 (parallel [(set (match_operand 0 "register_operand" "")
17690 (clobber (reg:CC FLAGS_REG))])]
17693 if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
17694 operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
17696 /* If .md ever supports :P for Pmode, this can be directly
17697 in the pattern above. */
17698 operands[3] = gen_rtx_PLUS (Pmode, operands[0],
17699 GEN_INT (GET_MODE_SIZE (GET_MODE
17701 if (TARGET_SINGLE_STRINGOP || optimize_size)
17703 emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
17709 (define_expand "strset_singleop"
17710 [(parallel [(set (match_operand 1 "memory_operand" "")
17711 (match_operand 2 "register_operand" ""))
17712 (set (match_operand 0 "register_operand" "")
17713 (match_operand 3 "" ""))
17714 (use (reg:SI DIRFLAG_REG))])]
17715 "TARGET_SINGLE_STRINGOP || optimize_size"
17718 (define_insn "*strsetdi_rex_1"
17719 [(set (mem:DI (match_operand:DI 1 "register_operand" "0"))
17720 (match_operand:DI 2 "register_operand" "a"))
17721 (set (match_operand:DI 0 "register_operand" "=D")
17722 (plus:DI (match_dup 1)
17724 (use (reg:SI DIRFLAG_REG))]
17725 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17727 [(set_attr "type" "str")
17728 (set_attr "memory" "store")
17729 (set_attr "mode" "DI")])
17731 (define_insn "*strsetsi_1"
17732 [(set (mem:SI (match_operand:SI 1 "register_operand" "0"))
17733 (match_operand:SI 2 "register_operand" "a"))
17734 (set (match_operand:SI 0 "register_operand" "=D")
17735 (plus:SI (match_dup 1)
17737 (use (reg:SI DIRFLAG_REG))]
17738 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17740 [(set_attr "type" "str")
17741 (set_attr "memory" "store")
17742 (set_attr "mode" "SI")])
17744 (define_insn "*strsetsi_rex_1"
17745 [(set (mem:SI (match_operand:DI 1 "register_operand" "0"))
17746 (match_operand:SI 2 "register_operand" "a"))
17747 (set (match_operand:DI 0 "register_operand" "=D")
17748 (plus:DI (match_dup 1)
17750 (use (reg:SI DIRFLAG_REG))]
17751 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17753 [(set_attr "type" "str")
17754 (set_attr "memory" "store")
17755 (set_attr "mode" "SI")])
17757 (define_insn "*strsethi_1"
17758 [(set (mem:HI (match_operand:SI 1 "register_operand" "0"))
17759 (match_operand:HI 2 "register_operand" "a"))
17760 (set (match_operand:SI 0 "register_operand" "=D")
17761 (plus:SI (match_dup 1)
17763 (use (reg:SI DIRFLAG_REG))]
17764 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17766 [(set_attr "type" "str")
17767 (set_attr "memory" "store")
17768 (set_attr "mode" "HI")])
17770 (define_insn "*strsethi_rex_1"
17771 [(set (mem:HI (match_operand:DI 1 "register_operand" "0"))
17772 (match_operand:HI 2 "register_operand" "a"))
17773 (set (match_operand:DI 0 "register_operand" "=D")
17774 (plus:DI (match_dup 1)
17776 (use (reg:SI DIRFLAG_REG))]
17777 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17779 [(set_attr "type" "str")
17780 (set_attr "memory" "store")
17781 (set_attr "mode" "HI")])
17783 (define_insn "*strsetqi_1"
17784 [(set (mem:QI (match_operand:SI 1 "register_operand" "0"))
17785 (match_operand:QI 2 "register_operand" "a"))
17786 (set (match_operand:SI 0 "register_operand" "=D")
17787 (plus:SI (match_dup 1)
17789 (use (reg:SI DIRFLAG_REG))]
17790 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17792 [(set_attr "type" "str")
17793 (set_attr "memory" "store")
17794 (set_attr "mode" "QI")])
17796 (define_insn "*strsetqi_rex_1"
17797 [(set (mem:QI (match_operand:DI 1 "register_operand" "0"))
17798 (match_operand:QI 2 "register_operand" "a"))
17799 (set (match_operand:DI 0 "register_operand" "=D")
17800 (plus:DI (match_dup 1)
17802 (use (reg:SI DIRFLAG_REG))]
17803 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17805 [(set_attr "type" "str")
17806 (set_attr "memory" "store")
17807 (set_attr "mode" "QI")])
17809 (define_expand "rep_stos"
17810 [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
17811 (set (match_operand 0 "register_operand" "")
17812 (match_operand 4 "" ""))
17813 (set (match_operand 2 "memory_operand" "") (const_int 0))
17814 (use (match_operand 3 "register_operand" ""))
17815 (use (match_dup 1))
17816 (use (reg:SI DIRFLAG_REG))])]
17820 (define_insn "*rep_stosdi_rex64"
17821 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17822 (set (match_operand:DI 0 "register_operand" "=D")
17823 (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
17825 (match_operand:DI 3 "register_operand" "0")))
17826 (set (mem:BLK (match_dup 3))
17828 (use (match_operand:DI 2 "register_operand" "a"))
17829 (use (match_dup 4))
17830 (use (reg:SI DIRFLAG_REG))]
17832 "{rep\;stosq|rep stosq}"
17833 [(set_attr "type" "str")
17834 (set_attr "prefix_rep" "1")
17835 (set_attr "memory" "store")
17836 (set_attr "mode" "DI")])
17838 (define_insn "*rep_stossi"
17839 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
17840 (set (match_operand:SI 0 "register_operand" "=D")
17841 (plus:SI (ashift:SI (match_operand:SI 4 "register_operand" "1")
17843 (match_operand:SI 3 "register_operand" "0")))
17844 (set (mem:BLK (match_dup 3))
17846 (use (match_operand:SI 2 "register_operand" "a"))
17847 (use (match_dup 4))
17848 (use (reg:SI DIRFLAG_REG))]
17850 "{rep\;stosl|rep stosd}"
17851 [(set_attr "type" "str")
17852 (set_attr "prefix_rep" "1")
17853 (set_attr "memory" "store")
17854 (set_attr "mode" "SI")])
17856 (define_insn "*rep_stossi_rex64"
17857 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17858 (set (match_operand:DI 0 "register_operand" "=D")
17859 (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
17861 (match_operand:DI 3 "register_operand" "0")))
17862 (set (mem:BLK (match_dup 3))
17864 (use (match_operand:SI 2 "register_operand" "a"))
17865 (use (match_dup 4))
17866 (use (reg:SI DIRFLAG_REG))]
17868 "{rep\;stosl|rep stosd}"
17869 [(set_attr "type" "str")
17870 (set_attr "prefix_rep" "1")
17871 (set_attr "memory" "store")
17872 (set_attr "mode" "SI")])
17874 (define_insn "*rep_stosqi"
17875 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
17876 (set (match_operand:SI 0 "register_operand" "=D")
17877 (plus:SI (match_operand:SI 3 "register_operand" "0")
17878 (match_operand:SI 4 "register_operand" "1")))
17879 (set (mem:BLK (match_dup 3))
17881 (use (match_operand:QI 2 "register_operand" "a"))
17882 (use (match_dup 4))
17883 (use (reg:SI DIRFLAG_REG))]
17885 "{rep\;stosb|rep stosb}"
17886 [(set_attr "type" "str")
17887 (set_attr "prefix_rep" "1")
17888 (set_attr "memory" "store")
17889 (set_attr "mode" "QI")])
17891 (define_insn "*rep_stosqi_rex64"
17892 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17893 (set (match_operand:DI 0 "register_operand" "=D")
17894 (plus:DI (match_operand:DI 3 "register_operand" "0")
17895 (match_operand:DI 4 "register_operand" "1")))
17896 (set (mem:BLK (match_dup 3))
17898 (use (match_operand:QI 2 "register_operand" "a"))
17899 (use (match_dup 4))
17900 (use (reg:SI DIRFLAG_REG))]
17902 "{rep\;stosb|rep stosb}"
17903 [(set_attr "type" "str")
17904 (set_attr "prefix_rep" "1")
17905 (set_attr "memory" "store")
17906 (set_attr "mode" "QI")])
17908 (define_expand "cmpstrnsi"
17909 [(set (match_operand:SI 0 "register_operand" "")
17910 (compare:SI (match_operand:BLK 1 "general_operand" "")
17911 (match_operand:BLK 2 "general_operand" "")))
17912 (use (match_operand 3 "general_operand" ""))
17913 (use (match_operand 4 "immediate_operand" ""))]
17914 "! optimize_size || TARGET_INLINE_ALL_STRINGOPS"
17916 rtx addr1, addr2, out, outlow, count, countreg, align;
17918 /* Can't use this if the user has appropriated esi or edi. */
17919 if (global_regs[4] || global_regs[5])
17923 if (GET_CODE (out) != REG)
17924 out = gen_reg_rtx (SImode);
17926 addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
17927 addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
17928 if (addr1 != XEXP (operands[1], 0))
17929 operands[1] = replace_equiv_address_nv (operands[1], addr1);
17930 if (addr2 != XEXP (operands[2], 0))
17931 operands[2] = replace_equiv_address_nv (operands[2], addr2);
17933 count = operands[3];
17934 countreg = ix86_zero_extend_to_Pmode (count);
17936 /* %%% Iff we are testing strict equality, we can use known alignment
17937 to good advantage. This may be possible with combine, particularly
17938 once cc0 is dead. */
17939 align = operands[4];
17941 emit_insn (gen_cld ());
17942 if (GET_CODE (count) == CONST_INT)
17944 if (INTVAL (count) == 0)
17946 emit_move_insn (operands[0], const0_rtx);
17949 emit_insn (gen_cmpstrnqi_nz_1 (addr1, addr2, countreg, align,
17950 operands[1], operands[2]));
17955 emit_insn (gen_cmpdi_1_rex64 (countreg, countreg));
17957 emit_insn (gen_cmpsi_1 (countreg, countreg));
17958 emit_insn (gen_cmpstrnqi_1 (addr1, addr2, countreg, align,
17959 operands[1], operands[2]));
17962 outlow = gen_lowpart (QImode, out);
17963 emit_insn (gen_cmpintqi (outlow));
17964 emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
17966 if (operands[0] != out)
17967 emit_move_insn (operands[0], out);
17972 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
17974 (define_expand "cmpintqi"
17975 [(set (match_dup 1)
17976 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
17978 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
17979 (parallel [(set (match_operand:QI 0 "register_operand" "")
17980 (minus:QI (match_dup 1)
17982 (clobber (reg:CC FLAGS_REG))])]
17984 "operands[1] = gen_reg_rtx (QImode);
17985 operands[2] = gen_reg_rtx (QImode);")
17987 ;; memcmp recognizers. The `cmpsb' opcode does nothing if the count is
17988 ;; zero. Emit extra code to make sure that a zero-length compare is EQ.
17990 (define_expand "cmpstrnqi_nz_1"
17991 [(parallel [(set (reg:CC FLAGS_REG)
17992 (compare:CC (match_operand 4 "memory_operand" "")
17993 (match_operand 5 "memory_operand" "")))
17994 (use (match_operand 2 "register_operand" ""))
17995 (use (match_operand:SI 3 "immediate_operand" ""))
17996 (use (reg:SI DIRFLAG_REG))
17997 (clobber (match_operand 0 "register_operand" ""))
17998 (clobber (match_operand 1 "register_operand" ""))
17999 (clobber (match_dup 2))])]
18003 (define_insn "*cmpstrnqi_nz_1"
18004 [(set (reg:CC FLAGS_REG)
18005 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
18006 (mem:BLK (match_operand:SI 5 "register_operand" "1"))))
18007 (use (match_operand:SI 6 "register_operand" "2"))
18008 (use (match_operand:SI 3 "immediate_operand" "i"))
18009 (use (reg:SI DIRFLAG_REG))
18010 (clobber (match_operand:SI 0 "register_operand" "=S"))
18011 (clobber (match_operand:SI 1 "register_operand" "=D"))
18012 (clobber (match_operand:SI 2 "register_operand" "=c"))]
18015 [(set_attr "type" "str")
18016 (set_attr "mode" "QI")
18017 (set_attr "prefix_rep" "1")])
18019 (define_insn "*cmpstrnqi_nz_rex_1"
18020 [(set (reg:CC FLAGS_REG)
18021 (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
18022 (mem:BLK (match_operand:DI 5 "register_operand" "1"))))
18023 (use (match_operand:DI 6 "register_operand" "2"))
18024 (use (match_operand:SI 3 "immediate_operand" "i"))
18025 (use (reg:SI DIRFLAG_REG))
18026 (clobber (match_operand:DI 0 "register_operand" "=S"))
18027 (clobber (match_operand:DI 1 "register_operand" "=D"))
18028 (clobber (match_operand:DI 2 "register_operand" "=c"))]
18031 [(set_attr "type" "str")
18032 (set_attr "mode" "QI")
18033 (set_attr "prefix_rep" "1")])
18035 ;; The same, but the count is not known to not be zero.
18037 (define_expand "cmpstrnqi_1"
18038 [(parallel [(set (reg:CC FLAGS_REG)
18039 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
18041 (compare:CC (match_operand 4 "memory_operand" "")
18042 (match_operand 5 "memory_operand" ""))
18044 (use (match_operand:SI 3 "immediate_operand" ""))
18045 (use (reg:CC FLAGS_REG))
18046 (use (reg:SI DIRFLAG_REG))
18047 (clobber (match_operand 0 "register_operand" ""))
18048 (clobber (match_operand 1 "register_operand" ""))
18049 (clobber (match_dup 2))])]
18053 (define_insn "*cmpstrnqi_1"
18054 [(set (reg:CC FLAGS_REG)
18055 (if_then_else:CC (ne (match_operand:SI 6 "register_operand" "2")
18057 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
18058 (mem:BLK (match_operand:SI 5 "register_operand" "1")))
18060 (use (match_operand:SI 3 "immediate_operand" "i"))
18061 (use (reg:CC FLAGS_REG))
18062 (use (reg:SI DIRFLAG_REG))
18063 (clobber (match_operand:SI 0 "register_operand" "=S"))
18064 (clobber (match_operand:SI 1 "register_operand" "=D"))
18065 (clobber (match_operand:SI 2 "register_operand" "=c"))]
18068 [(set_attr "type" "str")
18069 (set_attr "mode" "QI")
18070 (set_attr "prefix_rep" "1")])
18072 (define_insn "*cmpstrnqi_rex_1"
18073 [(set (reg:CC FLAGS_REG)
18074 (if_then_else:CC (ne (match_operand:DI 6 "register_operand" "2")
18076 (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
18077 (mem:BLK (match_operand:DI 5 "register_operand" "1")))
18079 (use (match_operand:SI 3 "immediate_operand" "i"))
18080 (use (reg:CC FLAGS_REG))
18081 (use (reg:SI DIRFLAG_REG))
18082 (clobber (match_operand:DI 0 "register_operand" "=S"))
18083 (clobber (match_operand:DI 1 "register_operand" "=D"))
18084 (clobber (match_operand:DI 2 "register_operand" "=c"))]
18087 [(set_attr "type" "str")
18088 (set_attr "mode" "QI")
18089 (set_attr "prefix_rep" "1")])
18091 (define_expand "strlensi"
18092 [(set (match_operand:SI 0 "register_operand" "")
18093 (unspec:SI [(match_operand:BLK 1 "general_operand" "")
18094 (match_operand:QI 2 "immediate_operand" "")
18095 (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
18098 if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
18104 (define_expand "strlendi"
18105 [(set (match_operand:DI 0 "register_operand" "")
18106 (unspec:DI [(match_operand:BLK 1 "general_operand" "")
18107 (match_operand:QI 2 "immediate_operand" "")
18108 (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
18111 if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
18117 (define_expand "strlenqi_1"
18118 [(parallel [(set (match_operand 0 "register_operand" "") (match_operand 2 "" ""))
18119 (use (reg:SI DIRFLAG_REG))
18120 (clobber (match_operand 1 "register_operand" ""))
18121 (clobber (reg:CC FLAGS_REG))])]
18125 (define_insn "*strlenqi_1"
18126 [(set (match_operand:SI 0 "register_operand" "=&c")
18127 (unspec:SI [(mem:BLK (match_operand:SI 5 "register_operand" "1"))
18128 (match_operand:QI 2 "register_operand" "a")
18129 (match_operand:SI 3 "immediate_operand" "i")
18130 (match_operand:SI 4 "register_operand" "0")] UNSPEC_SCAS))
18131 (use (reg:SI DIRFLAG_REG))
18132 (clobber (match_operand:SI 1 "register_operand" "=D"))
18133 (clobber (reg:CC FLAGS_REG))]
18136 [(set_attr "type" "str")
18137 (set_attr "mode" "QI")
18138 (set_attr "prefix_rep" "1")])
18140 (define_insn "*strlenqi_rex_1"
18141 [(set (match_operand:DI 0 "register_operand" "=&c")
18142 (unspec:DI [(mem:BLK (match_operand:DI 5 "register_operand" "1"))
18143 (match_operand:QI 2 "register_operand" "a")
18144 (match_operand:DI 3 "immediate_operand" "i")
18145 (match_operand:DI 4 "register_operand" "0")] UNSPEC_SCAS))
18146 (use (reg:SI DIRFLAG_REG))
18147 (clobber (match_operand:DI 1 "register_operand" "=D"))
18148 (clobber (reg:CC FLAGS_REG))]
18151 [(set_attr "type" "str")
18152 (set_attr "mode" "QI")
18153 (set_attr "prefix_rep" "1")])
18155 ;; Peephole optimizations to clean up after cmpstrn*. This should be
18156 ;; handled in combine, but it is not currently up to the task.
18157 ;; When used for their truth value, the cmpstrn* expanders generate
18166 ;; The intermediate three instructions are unnecessary.
18168 ;; This one handles cmpstrn*_nz_1...
18171 (set (reg:CC FLAGS_REG)
18172 (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
18173 (mem:BLK (match_operand 5 "register_operand" ""))))
18174 (use (match_operand 6 "register_operand" ""))
18175 (use (match_operand:SI 3 "immediate_operand" ""))
18176 (use (reg:SI DIRFLAG_REG))
18177 (clobber (match_operand 0 "register_operand" ""))
18178 (clobber (match_operand 1 "register_operand" ""))
18179 (clobber (match_operand 2 "register_operand" ""))])
18180 (set (match_operand:QI 7 "register_operand" "")
18181 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
18182 (set (match_operand:QI 8 "register_operand" "")
18183 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
18184 (set (reg FLAGS_REG)
18185 (compare (match_dup 7) (match_dup 8)))
18187 "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
18189 (set (reg:CC FLAGS_REG)
18190 (compare:CC (mem:BLK (match_dup 4))
18191 (mem:BLK (match_dup 5))))
18192 (use (match_dup 6))
18193 (use (match_dup 3))
18194 (use (reg:SI DIRFLAG_REG))
18195 (clobber (match_dup 0))
18196 (clobber (match_dup 1))
18197 (clobber (match_dup 2))])]
18200 ;; ...and this one handles cmpstrn*_1.
18203 (set (reg:CC FLAGS_REG)
18204 (if_then_else:CC (ne (match_operand 6 "register_operand" "")
18206 (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
18207 (mem:BLK (match_operand 5 "register_operand" "")))
18209 (use (match_operand:SI 3 "immediate_operand" ""))
18210 (use (reg:CC FLAGS_REG))
18211 (use (reg:SI DIRFLAG_REG))
18212 (clobber (match_operand 0 "register_operand" ""))
18213 (clobber (match_operand 1 "register_operand" ""))
18214 (clobber (match_operand 2 "register_operand" ""))])
18215 (set (match_operand:QI 7 "register_operand" "")
18216 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
18217 (set (match_operand:QI 8 "register_operand" "")
18218 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
18219 (set (reg FLAGS_REG)
18220 (compare (match_dup 7) (match_dup 8)))
18222 "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
18224 (set (reg:CC FLAGS_REG)
18225 (if_then_else:CC (ne (match_dup 6)
18227 (compare:CC (mem:BLK (match_dup 4))
18228 (mem:BLK (match_dup 5)))
18230 (use (match_dup 3))
18231 (use (reg:CC FLAGS_REG))
18232 (use (reg:SI DIRFLAG_REG))
18233 (clobber (match_dup 0))
18234 (clobber (match_dup 1))
18235 (clobber (match_dup 2))])]
18240 ;; Conditional move instructions.
18242 (define_expand "movdicc"
18243 [(set (match_operand:DI 0 "register_operand" "")
18244 (if_then_else:DI (match_operand 1 "comparison_operator" "")
18245 (match_operand:DI 2 "general_operand" "")
18246 (match_operand:DI 3 "general_operand" "")))]
18248 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
18250 (define_insn "x86_movdicc_0_m1_rex64"
18251 [(set (match_operand:DI 0 "register_operand" "=r")
18252 (if_then_else:DI (match_operand 1 "ix86_carry_flag_operator" "")
18255 (clobber (reg:CC FLAGS_REG))]
18258 ; Since we don't have the proper number of operands for an alu insn,
18259 ; fill in all the blanks.
18260 [(set_attr "type" "alu")
18261 (set_attr "pent_pair" "pu")
18262 (set_attr "memory" "none")
18263 (set_attr "imm_disp" "false")
18264 (set_attr "mode" "DI")
18265 (set_attr "length_immediate" "0")])
18267 (define_insn "*movdicc_c_rex64"
18268 [(set (match_operand:DI 0 "register_operand" "=r,r")
18269 (if_then_else:DI (match_operator 1 "ix86_comparison_operator"
18270 [(reg FLAGS_REG) (const_int 0)])
18271 (match_operand:DI 2 "nonimmediate_operand" "rm,0")
18272 (match_operand:DI 3 "nonimmediate_operand" "0,rm")))]
18273 "TARGET_64BIT && TARGET_CMOVE
18274 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18276 cmov%O2%C1\t{%2, %0|%0, %2}
18277 cmov%O2%c1\t{%3, %0|%0, %3}"
18278 [(set_attr "type" "icmov")
18279 (set_attr "mode" "DI")])
18281 (define_expand "movsicc"
18282 [(set (match_operand:SI 0 "register_operand" "")
18283 (if_then_else:SI (match_operand 1 "comparison_operator" "")
18284 (match_operand:SI 2 "general_operand" "")
18285 (match_operand:SI 3 "general_operand" "")))]
18287 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
18289 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
18290 ;; the register first winds up with `sbbl $0,reg', which is also weird.
18291 ;; So just document what we're doing explicitly.
18293 (define_insn "x86_movsicc_0_m1"
18294 [(set (match_operand:SI 0 "register_operand" "=r")
18295 (if_then_else:SI (match_operand 1 "ix86_carry_flag_operator" "")
18298 (clobber (reg:CC FLAGS_REG))]
18301 ; Since we don't have the proper number of operands for an alu insn,
18302 ; fill in all the blanks.
18303 [(set_attr "type" "alu")
18304 (set_attr "pent_pair" "pu")
18305 (set_attr "memory" "none")
18306 (set_attr "imm_disp" "false")
18307 (set_attr "mode" "SI")
18308 (set_attr "length_immediate" "0")])
18310 (define_insn "*movsicc_noc"
18311 [(set (match_operand:SI 0 "register_operand" "=r,r")
18312 (if_then_else:SI (match_operator 1 "ix86_comparison_operator"
18313 [(reg FLAGS_REG) (const_int 0)])
18314 (match_operand:SI 2 "nonimmediate_operand" "rm,0")
18315 (match_operand:SI 3 "nonimmediate_operand" "0,rm")))]
18317 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18319 cmov%O2%C1\t{%2, %0|%0, %2}
18320 cmov%O2%c1\t{%3, %0|%0, %3}"
18321 [(set_attr "type" "icmov")
18322 (set_attr "mode" "SI")])
18324 (define_expand "movhicc"
18325 [(set (match_operand:HI 0 "register_operand" "")
18326 (if_then_else:HI (match_operand 1 "comparison_operator" "")
18327 (match_operand:HI 2 "general_operand" "")
18328 (match_operand:HI 3 "general_operand" "")))]
18329 "TARGET_HIMODE_MATH"
18330 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
18332 (define_insn "*movhicc_noc"
18333 [(set (match_operand:HI 0 "register_operand" "=r,r")
18334 (if_then_else:HI (match_operator 1 "ix86_comparison_operator"
18335 [(reg FLAGS_REG) (const_int 0)])
18336 (match_operand:HI 2 "nonimmediate_operand" "rm,0")
18337 (match_operand:HI 3 "nonimmediate_operand" "0,rm")))]
18339 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18341 cmov%O2%C1\t{%2, %0|%0, %2}
18342 cmov%O2%c1\t{%3, %0|%0, %3}"
18343 [(set_attr "type" "icmov")
18344 (set_attr "mode" "HI")])
18346 (define_expand "movqicc"
18347 [(set (match_operand:QI 0 "register_operand" "")
18348 (if_then_else:QI (match_operand 1 "comparison_operator" "")
18349 (match_operand:QI 2 "general_operand" "")
18350 (match_operand:QI 3 "general_operand" "")))]
18351 "TARGET_QIMODE_MATH"
18352 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
18354 (define_insn_and_split "*movqicc_noc"
18355 [(set (match_operand:QI 0 "register_operand" "=r,r")
18356 (if_then_else:QI (match_operator 1 "ix86_comparison_operator"
18357 [(match_operand 4 "flags_reg_operand" "")
18359 (match_operand:QI 2 "register_operand" "r,0")
18360 (match_operand:QI 3 "register_operand" "0,r")))]
18361 "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
18363 "&& reload_completed"
18364 [(set (match_dup 0)
18365 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
18368 "operands[0] = gen_lowpart (SImode, operands[0]);
18369 operands[2] = gen_lowpart (SImode, operands[2]);
18370 operands[3] = gen_lowpart (SImode, operands[3]);"
18371 [(set_attr "type" "icmov")
18372 (set_attr "mode" "SI")])
18374 (define_expand "movsfcc"
18375 [(set (match_operand:SF 0 "register_operand" "")
18376 (if_then_else:SF (match_operand 1 "comparison_operator" "")
18377 (match_operand:SF 2 "register_operand" "")
18378 (match_operand:SF 3 "register_operand" "")))]
18379 "(TARGET_80387 && TARGET_CMOVE) || TARGET_SSE_MATH"
18380 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
18382 (define_insn "*movsfcc_1_387"
18383 [(set (match_operand:SF 0 "register_operand" "=f#r,f#r,r#f,r#f")
18384 (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
18385 [(reg FLAGS_REG) (const_int 0)])
18386 (match_operand:SF 2 "nonimmediate_operand" "f#r,0,rm#f,0")
18387 (match_operand:SF 3 "nonimmediate_operand" "0,f#r,0,rm#f")))]
18388 "TARGET_80387 && TARGET_CMOVE
18389 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18391 fcmov%F1\t{%2, %0|%0, %2}
18392 fcmov%f1\t{%3, %0|%0, %3}
18393 cmov%O2%C1\t{%2, %0|%0, %2}
18394 cmov%O2%c1\t{%3, %0|%0, %3}"
18395 [(set_attr "type" "fcmov,fcmov,icmov,icmov")
18396 (set_attr "mode" "SF,SF,SI,SI")])
18398 (define_expand "movdfcc"
18399 [(set (match_operand:DF 0 "register_operand" "")
18400 (if_then_else:DF (match_operand 1 "comparison_operator" "")
18401 (match_operand:DF 2 "register_operand" "")
18402 (match_operand:DF 3 "register_operand" "")))]
18403 "(TARGET_80387 && TARGET_CMOVE) || (TARGET_SSE2 && TARGET_SSE_MATH)"
18404 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
18406 (define_insn "*movdfcc_1"
18407 [(set (match_operand:DF 0 "register_operand" "=f#r,f#r,&r#f,&r#f")
18408 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
18409 [(reg FLAGS_REG) (const_int 0)])
18410 (match_operand:DF 2 "nonimmediate_operand" "f#r,0,rm#f,0")
18411 (match_operand:DF 3 "nonimmediate_operand" "0,f#r,0,rm#f")))]
18412 "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
18413 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18415 fcmov%F1\t{%2, %0|%0, %2}
18416 fcmov%f1\t{%3, %0|%0, %3}
18419 [(set_attr "type" "fcmov,fcmov,multi,multi")
18420 (set_attr "mode" "DF")])
18422 (define_insn "*movdfcc_1_rex64"
18423 [(set (match_operand:DF 0 "register_operand" "=f#r,f#r,r#f,r#f")
18424 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
18425 [(reg FLAGS_REG) (const_int 0)])
18426 (match_operand:DF 2 "nonimmediate_operand" "f#r,0#r,rm#f,0#f")
18427 (match_operand:DF 3 "nonimmediate_operand" "0#r,f#r,0#f,rm#f")))]
18428 "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
18429 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18431 fcmov%F1\t{%2, %0|%0, %2}
18432 fcmov%f1\t{%3, %0|%0, %3}
18433 cmov%O2%C1\t{%2, %0|%0, %2}
18434 cmov%O2%c1\t{%3, %0|%0, %3}"
18435 [(set_attr "type" "fcmov,fcmov,icmov,icmov")
18436 (set_attr "mode" "DF")])
18439 [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand" "")
18440 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
18441 [(match_operand 4 "flags_reg_operand" "")
18443 (match_operand:DF 2 "nonimmediate_operand" "")
18444 (match_operand:DF 3 "nonimmediate_operand" "")))]
18445 "!TARGET_64BIT && reload_completed"
18446 [(set (match_dup 2)
18447 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
18451 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
18454 "split_di (operands+2, 1, operands+5, operands+6);
18455 split_di (operands+3, 1, operands+7, operands+8);
18456 split_di (operands, 1, operands+2, operands+3);")
18458 (define_expand "movxfcc"
18459 [(set (match_operand:XF 0 "register_operand" "")
18460 (if_then_else:XF (match_operand 1 "comparison_operator" "")
18461 (match_operand:XF 2 "register_operand" "")
18462 (match_operand:XF 3 "register_operand" "")))]
18463 "TARGET_80387 && TARGET_CMOVE"
18464 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
18466 (define_insn "*movxfcc_1"
18467 [(set (match_operand:XF 0 "register_operand" "=f,f")
18468 (if_then_else:XF (match_operator 1 "fcmov_comparison_operator"
18469 [(reg FLAGS_REG) (const_int 0)])
18470 (match_operand:XF 2 "register_operand" "f,0")
18471 (match_operand:XF 3 "register_operand" "0,f")))]
18472 "TARGET_80387 && TARGET_CMOVE"
18474 fcmov%F1\t{%2, %0|%0, %2}
18475 fcmov%f1\t{%3, %0|%0, %3}"
18476 [(set_attr "type" "fcmov")
18477 (set_attr "mode" "XF")])
18479 ;; These versions of the min/max patterns are intentionally ignorant of
18480 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
18481 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
18482 ;; are undefined in this condition, we're certain this is correct.
18484 (define_insn "sminsf3"
18485 [(set (match_operand:SF 0 "register_operand" "=x")
18486 (smin:SF (match_operand:SF 1 "nonimmediate_operand" "%0")
18487 (match_operand:SF 2 "nonimmediate_operand" "xm")))]
18489 "minss\t{%2, %0|%0, %2}"
18490 [(set_attr "type" "sseadd")
18491 (set_attr "mode" "SF")])
18493 (define_insn "smaxsf3"
18494 [(set (match_operand:SF 0 "register_operand" "=x")
18495 (smax:SF (match_operand:SF 1 "nonimmediate_operand" "%0")
18496 (match_operand:SF 2 "nonimmediate_operand" "xm")))]
18498 "maxss\t{%2, %0|%0, %2}"
18499 [(set_attr "type" "sseadd")
18500 (set_attr "mode" "SF")])
18502 (define_insn "smindf3"
18503 [(set (match_operand:DF 0 "register_operand" "=x")
18504 (smin:DF (match_operand:DF 1 "nonimmediate_operand" "%0")
18505 (match_operand:DF 2 "nonimmediate_operand" "xm")))]
18506 "TARGET_SSE2 && TARGET_SSE_MATH"
18507 "minsd\t{%2, %0|%0, %2}"
18508 [(set_attr "type" "sseadd")
18509 (set_attr "mode" "DF")])
18511 (define_insn "smaxdf3"
18512 [(set (match_operand:DF 0 "register_operand" "=x")
18513 (smax:DF (match_operand:DF 1 "nonimmediate_operand" "%0")
18514 (match_operand:DF 2 "nonimmediate_operand" "xm")))]
18515 "TARGET_SSE2 && TARGET_SSE_MATH"
18516 "maxsd\t{%2, %0|%0, %2}"
18517 [(set_attr "type" "sseadd")
18518 (set_attr "mode" "DF")])
18520 ;; These versions of the min/max patterns implement exactly the operations
18521 ;; min = (op1 < op2 ? op1 : op2)
18522 ;; max = (!(op1 < op2) ? op1 : op2)
18523 ;; Their operands are not commutative, and thus they may be used in the
18524 ;; presence of -0.0 and NaN.
18526 (define_insn "*ieee_sminsf3"
18527 [(set (match_operand:SF 0 "register_operand" "=x")
18528 (unspec:SF [(match_operand:SF 1 "register_operand" "0")
18529 (match_operand:SF 2 "nonimmediate_operand" "xm")]
18532 "minss\t{%2, %0|%0, %2}"
18533 [(set_attr "type" "sseadd")
18534 (set_attr "mode" "SF")])
18536 (define_insn "*ieee_smaxsf3"
18537 [(set (match_operand:SF 0 "register_operand" "=x")
18538 (unspec:SF [(match_operand:SF 1 "register_operand" "0")
18539 (match_operand:SF 2 "nonimmediate_operand" "xm")]
18542 "maxss\t{%2, %0|%0, %2}"
18543 [(set_attr "type" "sseadd")
18544 (set_attr "mode" "SF")])
18546 (define_insn "*ieee_smindf3"
18547 [(set (match_operand:DF 0 "register_operand" "=x")
18548 (unspec:DF [(match_operand:DF 1 "register_operand" "0")
18549 (match_operand:DF 2 "nonimmediate_operand" "xm")]
18551 "TARGET_SSE2 && TARGET_SSE_MATH"
18552 "minsd\t{%2, %0|%0, %2}"
18553 [(set_attr "type" "sseadd")
18554 (set_attr "mode" "DF")])
18556 (define_insn "*ieee_smaxdf3"
18557 [(set (match_operand:DF 0 "register_operand" "=x")
18558 (unspec:DF [(match_operand:DF 1 "register_operand" "0")
18559 (match_operand:DF 2 "nonimmediate_operand" "xm")]
18561 "TARGET_SSE2 && TARGET_SSE_MATH"
18562 "maxsd\t{%2, %0|%0, %2}"
18563 [(set_attr "type" "sseadd")
18564 (set_attr "mode" "DF")])
18566 ;; Conditional addition patterns
18567 (define_expand "addqicc"
18568 [(match_operand:QI 0 "register_operand" "")
18569 (match_operand 1 "comparison_operator" "")
18570 (match_operand:QI 2 "register_operand" "")
18571 (match_operand:QI 3 "const_int_operand" "")]
18573 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18575 (define_expand "addhicc"
18576 [(match_operand:HI 0 "register_operand" "")
18577 (match_operand 1 "comparison_operator" "")
18578 (match_operand:HI 2 "register_operand" "")
18579 (match_operand:HI 3 "const_int_operand" "")]
18581 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18583 (define_expand "addsicc"
18584 [(match_operand:SI 0 "register_operand" "")
18585 (match_operand 1 "comparison_operator" "")
18586 (match_operand:SI 2 "register_operand" "")
18587 (match_operand:SI 3 "const_int_operand" "")]
18589 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18591 (define_expand "adddicc"
18592 [(match_operand:DI 0 "register_operand" "")
18593 (match_operand 1 "comparison_operator" "")
18594 (match_operand:DI 2 "register_operand" "")
18595 (match_operand:DI 3 "const_int_operand" "")]
18597 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18600 ;; Misc patterns (?)
18602 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
18603 ;; Otherwise there will be nothing to keep
18605 ;; [(set (reg ebp) (reg esp))]
18606 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
18607 ;; (clobber (eflags)]
18608 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
18610 ;; in proper program order.
18611 (define_insn "pro_epilogue_adjust_stack_1"
18612 [(set (match_operand:SI 0 "register_operand" "=r,r")
18613 (plus:SI (match_operand:SI 1 "register_operand" "0,r")
18614 (match_operand:SI 2 "immediate_operand" "i,i")))
18615 (clobber (reg:CC FLAGS_REG))
18616 (clobber (mem:BLK (scratch)))]
18619 switch (get_attr_type (insn))
18622 return "mov{l}\t{%1, %0|%0, %1}";
18625 if (GET_CODE (operands[2]) == CONST_INT
18626 && (INTVAL (operands[2]) == 128
18627 || (INTVAL (operands[2]) < 0
18628 && INTVAL (operands[2]) != -128)))
18630 operands[2] = GEN_INT (-INTVAL (operands[2]));
18631 return "sub{l}\t{%2, %0|%0, %2}";
18633 return "add{l}\t{%2, %0|%0, %2}";
18636 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
18637 return "lea{l}\t{%a2, %0|%0, %a2}";
18640 gcc_unreachable ();
18643 [(set (attr "type")
18644 (cond [(eq_attr "alternative" "0")
18645 (const_string "alu")
18646 (match_operand:SI 2 "const0_operand" "")
18647 (const_string "imov")
18649 (const_string "lea")))
18650 (set_attr "mode" "SI")])
18652 (define_insn "pro_epilogue_adjust_stack_rex64"
18653 [(set (match_operand:DI 0 "register_operand" "=r,r")
18654 (plus:DI (match_operand:DI 1 "register_operand" "0,r")
18655 (match_operand:DI 2 "x86_64_immediate_operand" "e,e")))
18656 (clobber (reg:CC FLAGS_REG))
18657 (clobber (mem:BLK (scratch)))]
18660 switch (get_attr_type (insn))
18663 return "mov{q}\t{%1, %0|%0, %1}";
18666 if (GET_CODE (operands[2]) == CONST_INT
18667 /* Avoid overflows. */
18668 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
18669 && (INTVAL (operands[2]) == 128
18670 || (INTVAL (operands[2]) < 0
18671 && INTVAL (operands[2]) != -128)))
18673 operands[2] = GEN_INT (-INTVAL (operands[2]));
18674 return "sub{q}\t{%2, %0|%0, %2}";
18676 return "add{q}\t{%2, %0|%0, %2}";
18679 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
18680 return "lea{q}\t{%a2, %0|%0, %a2}";
18683 gcc_unreachable ();
18686 [(set (attr "type")
18687 (cond [(eq_attr "alternative" "0")
18688 (const_string "alu")
18689 (match_operand:DI 2 "const0_operand" "")
18690 (const_string "imov")
18692 (const_string "lea")))
18693 (set_attr "mode" "DI")])
18695 (define_insn "pro_epilogue_adjust_stack_rex64_2"
18696 [(set (match_operand:DI 0 "register_operand" "=r,r")
18697 (plus:DI (match_operand:DI 1 "register_operand" "0,r")
18698 (match_operand:DI 3 "immediate_operand" "i,i")))
18699 (use (match_operand:DI 2 "register_operand" "r,r"))
18700 (clobber (reg:CC FLAGS_REG))
18701 (clobber (mem:BLK (scratch)))]
18704 switch (get_attr_type (insn))
18707 return "add{q}\t{%2, %0|%0, %2}";
18710 operands[2] = gen_rtx_PLUS (DImode, operands[1], operands[2]);
18711 return "lea{q}\t{%a2, %0|%0, %a2}";
18714 gcc_unreachable ();
18717 [(set_attr "type" "alu,lea")
18718 (set_attr "mode" "DI")])
18720 (define_expand "allocate_stack_worker"
18721 [(match_operand:SI 0 "register_operand" "")]
18722 "TARGET_STACK_PROBE"
18724 if (reload_completed)
18727 emit_insn (gen_allocate_stack_worker_rex64_postreload (operands[0]));
18729 emit_insn (gen_allocate_stack_worker_postreload (operands[0]));
18734 emit_insn (gen_allocate_stack_worker_rex64 (operands[0]));
18736 emit_insn (gen_allocate_stack_worker_1 (operands[0]));
18741 (define_insn "allocate_stack_worker_1"
18742 [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")]
18743 UNSPECV_STACK_PROBE)
18744 (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0)))
18745 (clobber (match_scratch:SI 1 "=0"))
18746 (clobber (reg:CC FLAGS_REG))]
18747 "!TARGET_64BIT && TARGET_STACK_PROBE"
18749 [(set_attr "type" "multi")
18750 (set_attr "length" "5")])
18752 (define_expand "allocate_stack_worker_postreload"
18753 [(parallel [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")]
18754 UNSPECV_STACK_PROBE)
18755 (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0)))
18756 (clobber (match_dup 0))
18757 (clobber (reg:CC FLAGS_REG))])]
18761 (define_insn "allocate_stack_worker_rex64"
18762 [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")]
18763 UNSPECV_STACK_PROBE)
18764 (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0)))
18765 (clobber (match_scratch:DI 1 "=0"))
18766 (clobber (reg:CC FLAGS_REG))]
18767 "TARGET_64BIT && TARGET_STACK_PROBE"
18769 [(set_attr "type" "multi")
18770 (set_attr "length" "5")])
18772 (define_expand "allocate_stack_worker_rex64_postreload"
18773 [(parallel [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")]
18774 UNSPECV_STACK_PROBE)
18775 (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0)))
18776 (clobber (match_dup 0))
18777 (clobber (reg:CC FLAGS_REG))])]
18781 (define_expand "allocate_stack"
18782 [(parallel [(set (match_operand:SI 0 "register_operand" "=r")
18783 (minus:SI (reg:SI SP_REG)
18784 (match_operand:SI 1 "general_operand" "")))
18785 (clobber (reg:CC FLAGS_REG))])
18786 (parallel [(set (reg:SI SP_REG)
18787 (minus:SI (reg:SI SP_REG) (match_dup 1)))
18788 (clobber (reg:CC FLAGS_REG))])]
18789 "TARGET_STACK_PROBE"
18791 #ifdef CHECK_STACK_LIMIT
18792 if (GET_CODE (operands[1]) == CONST_INT
18793 && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
18794 emit_insn (gen_subsi3 (stack_pointer_rtx, stack_pointer_rtx,
18798 emit_insn (gen_allocate_stack_worker (copy_to_mode_reg (SImode,
18801 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
18805 (define_expand "builtin_setjmp_receiver"
18806 [(label_ref (match_operand 0 "" ""))]
18807 "!TARGET_64BIT && flag_pic"
18809 emit_insn (gen_set_got (pic_offset_table_rtx));
18813 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
18816 [(set (match_operand 0 "register_operand" "")
18817 (match_operator 3 "promotable_binary_operator"
18818 [(match_operand 1 "register_operand" "")
18819 (match_operand 2 "aligned_operand" "")]))
18820 (clobber (reg:CC FLAGS_REG))]
18821 "! TARGET_PARTIAL_REG_STALL && reload_completed
18822 && ((GET_MODE (operands[0]) == HImode
18823 && ((!optimize_size && !TARGET_FAST_PREFIX)
18824 || GET_CODE (operands[2]) != CONST_INT
18825 || CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')))
18826 || (GET_MODE (operands[0]) == QImode
18827 && (TARGET_PROMOTE_QImode || optimize_size)))"
18828 [(parallel [(set (match_dup 0)
18829 (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
18830 (clobber (reg:CC FLAGS_REG))])]
18831 "operands[0] = gen_lowpart (SImode, operands[0]);
18832 operands[1] = gen_lowpart (SImode, operands[1]);
18833 if (GET_CODE (operands[3]) != ASHIFT)
18834 operands[2] = gen_lowpart (SImode, operands[2]);
18835 PUT_MODE (operands[3], SImode);")
18837 ; Promote the QImode tests, as i386 has encoding of the AND
18838 ; instruction with 32-bit sign-extended immediate and thus the
18839 ; instruction size is unchanged, except in the %eax case for
18840 ; which it is increased by one byte, hence the ! optimize_size.
18842 [(set (match_operand 0 "flags_reg_operand" "")
18843 (match_operator 2 "compare_operator"
18844 [(and (match_operand 3 "aligned_operand" "")
18845 (match_operand 4 "const_int_operand" ""))
18847 (set (match_operand 1 "register_operand" "")
18848 (and (match_dup 3) (match_dup 4)))]
18849 "! TARGET_PARTIAL_REG_STALL && reload_completed
18850 /* Ensure that the operand will remain sign-extended immediate. */
18851 && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)
18853 && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
18854 || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))"
18855 [(parallel [(set (match_dup 0)
18856 (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
18859 (and:SI (match_dup 3) (match_dup 4)))])]
18862 = gen_int_mode (INTVAL (operands[4])
18863 & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
18864 operands[1] = gen_lowpart (SImode, operands[1]);
18865 operands[3] = gen_lowpart (SImode, operands[3]);
18868 ; Don't promote the QImode tests, as i386 doesn't have encoding of
18869 ; the TEST instruction with 32-bit sign-extended immediate and thus
18870 ; the instruction size would at least double, which is not what we
18871 ; want even with ! optimize_size.
18873 [(set (match_operand 0 "flags_reg_operand" "")
18874 (match_operator 1 "compare_operator"
18875 [(and (match_operand:HI 2 "aligned_operand" "")
18876 (match_operand:HI 3 "const_int_operand" ""))
18878 "! TARGET_PARTIAL_REG_STALL && reload_completed
18879 /* Ensure that the operand will remain sign-extended immediate. */
18880 && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)
18881 && ! TARGET_FAST_PREFIX
18882 && ! optimize_size"
18883 [(set (match_dup 0)
18884 (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
18888 = gen_int_mode (INTVAL (operands[3])
18889 & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
18890 operands[2] = gen_lowpart (SImode, operands[2]);
18894 [(set (match_operand 0 "register_operand" "")
18895 (neg (match_operand 1 "register_operand" "")))
18896 (clobber (reg:CC FLAGS_REG))]
18897 "! TARGET_PARTIAL_REG_STALL && reload_completed
18898 && (GET_MODE (operands[0]) == HImode
18899 || (GET_MODE (operands[0]) == QImode
18900 && (TARGET_PROMOTE_QImode || optimize_size)))"
18901 [(parallel [(set (match_dup 0)
18902 (neg:SI (match_dup 1)))
18903 (clobber (reg:CC FLAGS_REG))])]
18904 "operands[0] = gen_lowpart (SImode, operands[0]);
18905 operands[1] = gen_lowpart (SImode, operands[1]);")
18908 [(set (match_operand 0 "register_operand" "")
18909 (not (match_operand 1 "register_operand" "")))]
18910 "! TARGET_PARTIAL_REG_STALL && reload_completed
18911 && (GET_MODE (operands[0]) == HImode
18912 || (GET_MODE (operands[0]) == QImode
18913 && (TARGET_PROMOTE_QImode || optimize_size)))"
18914 [(set (match_dup 0)
18915 (not:SI (match_dup 1)))]
18916 "operands[0] = gen_lowpart (SImode, operands[0]);
18917 operands[1] = gen_lowpart (SImode, operands[1]);")
18920 [(set (match_operand 0 "register_operand" "")
18921 (if_then_else (match_operator 1 "comparison_operator"
18922 [(reg FLAGS_REG) (const_int 0)])
18923 (match_operand 2 "register_operand" "")
18924 (match_operand 3 "register_operand" "")))]
18925 "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE
18926 && (GET_MODE (operands[0]) == HImode
18927 || (GET_MODE (operands[0]) == QImode
18928 && (TARGET_PROMOTE_QImode || optimize_size)))"
18929 [(set (match_dup 0)
18930 (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
18931 "operands[0] = gen_lowpart (SImode, operands[0]);
18932 operands[2] = gen_lowpart (SImode, operands[2]);
18933 operands[3] = gen_lowpart (SImode, operands[3]);")
18936 ;; RTL Peephole optimizations, run before sched2. These primarily look to
18937 ;; transform a complex memory operation into two memory to register operations.
18939 ;; Don't push memory operands
18941 [(set (match_operand:SI 0 "push_operand" "")
18942 (match_operand:SI 1 "memory_operand" ""))
18943 (match_scratch:SI 2 "r")]
18944 "!optimize_size && !TARGET_PUSH_MEMORY
18945 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
18946 [(set (match_dup 2) (match_dup 1))
18947 (set (match_dup 0) (match_dup 2))]
18951 [(set (match_operand:DI 0 "push_operand" "")
18952 (match_operand:DI 1 "memory_operand" ""))
18953 (match_scratch:DI 2 "r")]
18954 "!optimize_size && !TARGET_PUSH_MEMORY
18955 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
18956 [(set (match_dup 2) (match_dup 1))
18957 (set (match_dup 0) (match_dup 2))]
18960 ;; We need to handle SFmode only, because DFmode and XFmode is split to
18963 [(set (match_operand:SF 0 "push_operand" "")
18964 (match_operand:SF 1 "memory_operand" ""))
18965 (match_scratch:SF 2 "r")]
18966 "!optimize_size && !TARGET_PUSH_MEMORY
18967 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
18968 [(set (match_dup 2) (match_dup 1))
18969 (set (match_dup 0) (match_dup 2))]
18973 [(set (match_operand:HI 0 "push_operand" "")
18974 (match_operand:HI 1 "memory_operand" ""))
18975 (match_scratch:HI 2 "r")]
18976 "!optimize_size && !TARGET_PUSH_MEMORY
18977 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
18978 [(set (match_dup 2) (match_dup 1))
18979 (set (match_dup 0) (match_dup 2))]
18983 [(set (match_operand:QI 0 "push_operand" "")
18984 (match_operand:QI 1 "memory_operand" ""))
18985 (match_scratch:QI 2 "q")]
18986 "!optimize_size && !TARGET_PUSH_MEMORY
18987 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
18988 [(set (match_dup 2) (match_dup 1))
18989 (set (match_dup 0) (match_dup 2))]
18992 ;; Don't move an immediate directly to memory when the instruction
18995 [(match_scratch:SI 1 "r")
18996 (set (match_operand:SI 0 "memory_operand" "")
18999 && ! TARGET_USE_MOV0
19000 && TARGET_SPLIT_LONG_MOVES
19001 && get_attr_length (insn) >= ix86_cost->large_insn
19002 && peep2_regno_dead_p (0, FLAGS_REG)"
19003 [(parallel [(set (match_dup 1) (const_int 0))
19004 (clobber (reg:CC FLAGS_REG))])
19005 (set (match_dup 0) (match_dup 1))]
19009 [(match_scratch:HI 1 "r")
19010 (set (match_operand:HI 0 "memory_operand" "")
19013 && ! TARGET_USE_MOV0
19014 && TARGET_SPLIT_LONG_MOVES
19015 && get_attr_length (insn) >= ix86_cost->large_insn
19016 && peep2_regno_dead_p (0, FLAGS_REG)"
19017 [(parallel [(set (match_dup 2) (const_int 0))
19018 (clobber (reg:CC FLAGS_REG))])
19019 (set (match_dup 0) (match_dup 1))]
19020 "operands[2] = gen_lowpart (SImode, operands[1]);")
19023 [(match_scratch:QI 1 "q")
19024 (set (match_operand:QI 0 "memory_operand" "")
19027 && ! TARGET_USE_MOV0
19028 && TARGET_SPLIT_LONG_MOVES
19029 && get_attr_length (insn) >= ix86_cost->large_insn
19030 && peep2_regno_dead_p (0, FLAGS_REG)"
19031 [(parallel [(set (match_dup 2) (const_int 0))
19032 (clobber (reg:CC FLAGS_REG))])
19033 (set (match_dup 0) (match_dup 1))]
19034 "operands[2] = gen_lowpart (SImode, operands[1]);")
19037 [(match_scratch:SI 2 "r")
19038 (set (match_operand:SI 0 "memory_operand" "")
19039 (match_operand:SI 1 "immediate_operand" ""))]
19041 && get_attr_length (insn) >= ix86_cost->large_insn
19042 && TARGET_SPLIT_LONG_MOVES"
19043 [(set (match_dup 2) (match_dup 1))
19044 (set (match_dup 0) (match_dup 2))]
19048 [(match_scratch:HI 2 "r")
19049 (set (match_operand:HI 0 "memory_operand" "")
19050 (match_operand:HI 1 "immediate_operand" ""))]
19051 "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
19052 && TARGET_SPLIT_LONG_MOVES"
19053 [(set (match_dup 2) (match_dup 1))
19054 (set (match_dup 0) (match_dup 2))]
19058 [(match_scratch:QI 2 "q")
19059 (set (match_operand:QI 0 "memory_operand" "")
19060 (match_operand:QI 1 "immediate_operand" ""))]
19061 "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
19062 && TARGET_SPLIT_LONG_MOVES"
19063 [(set (match_dup 2) (match_dup 1))
19064 (set (match_dup 0) (match_dup 2))]
19067 ;; Don't compare memory with zero, load and use a test instead.
19069 [(set (match_operand 0 "flags_reg_operand" "")
19070 (match_operator 1 "compare_operator"
19071 [(match_operand:SI 2 "memory_operand" "")
19073 (match_scratch:SI 3 "r")]
19074 "ix86_match_ccmode (insn, CCNOmode) && ! optimize_size"
19075 [(set (match_dup 3) (match_dup 2))
19076 (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))]
19079 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer.
19080 ;; Don't split NOTs with a displacement operand, because resulting XOR
19081 ;; will not be pairable anyway.
19083 ;; On AMD K6, NOT is vector decoded with memory operand that cannot be
19084 ;; represented using a modRM byte. The XOR replacement is long decoded,
19085 ;; so this split helps here as well.
19087 ;; Note: Can't do this as a regular split because we can't get proper
19088 ;; lifetime information then.
19091 [(set (match_operand:SI 0 "nonimmediate_operand" "")
19092 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
19094 && peep2_regno_dead_p (0, FLAGS_REG)
19095 && ((TARGET_PENTIUM
19096 && (GET_CODE (operands[0]) != MEM
19097 || !memory_displacement_operand (operands[0], SImode)))
19098 || (TARGET_K6 && long_memory_operand (operands[0], SImode)))"
19099 [(parallel [(set (match_dup 0)
19100 (xor:SI (match_dup 1) (const_int -1)))
19101 (clobber (reg:CC FLAGS_REG))])]
19105 [(set (match_operand:HI 0 "nonimmediate_operand" "")
19106 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
19108 && peep2_regno_dead_p (0, FLAGS_REG)
19109 && ((TARGET_PENTIUM
19110 && (GET_CODE (operands[0]) != MEM
19111 || !memory_displacement_operand (operands[0], HImode)))
19112 || (TARGET_K6 && long_memory_operand (operands[0], HImode)))"
19113 [(parallel [(set (match_dup 0)
19114 (xor:HI (match_dup 1) (const_int -1)))
19115 (clobber (reg:CC FLAGS_REG))])]
19119 [(set (match_operand:QI 0 "nonimmediate_operand" "")
19120 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
19122 && peep2_regno_dead_p (0, FLAGS_REG)
19123 && ((TARGET_PENTIUM
19124 && (GET_CODE (operands[0]) != MEM
19125 || !memory_displacement_operand (operands[0], QImode)))
19126 || (TARGET_K6 && long_memory_operand (operands[0], QImode)))"
19127 [(parallel [(set (match_dup 0)
19128 (xor:QI (match_dup 1) (const_int -1)))
19129 (clobber (reg:CC FLAGS_REG))])]
19132 ;; Non pairable "test imm, reg" instructions can be translated to
19133 ;; "and imm, reg" if reg dies. The "and" form is also shorter (one
19134 ;; byte opcode instead of two, have a short form for byte operands),
19135 ;; so do it for other CPUs as well. Given that the value was dead,
19136 ;; this should not create any new dependencies. Pass on the sub-word
19137 ;; versions if we're concerned about partial register stalls.
19140 [(set (match_operand 0 "flags_reg_operand" "")
19141 (match_operator 1 "compare_operator"
19142 [(and:SI (match_operand:SI 2 "register_operand" "")
19143 (match_operand:SI 3 "immediate_operand" ""))
19145 "ix86_match_ccmode (insn, CCNOmode)
19146 && (true_regnum (operands[2]) != 0
19147 || (GET_CODE (operands[3]) == CONST_INT
19148 && CONST_OK_FOR_LETTER_P (INTVAL (operands[3]), 'K')))
19149 && peep2_reg_dead_p (1, operands[2])"
19151 [(set (match_dup 0)
19152 (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
19155 (and:SI (match_dup 2) (match_dup 3)))])]
19158 ;; We don't need to handle HImode case, because it will be promoted to SImode
19159 ;; on ! TARGET_PARTIAL_REG_STALL
19162 [(set (match_operand 0 "flags_reg_operand" "")
19163 (match_operator 1 "compare_operator"
19164 [(and:QI (match_operand:QI 2 "register_operand" "")
19165 (match_operand:QI 3 "immediate_operand" ""))
19167 "! TARGET_PARTIAL_REG_STALL
19168 && ix86_match_ccmode (insn, CCNOmode)
19169 && true_regnum (operands[2]) != 0
19170 && peep2_reg_dead_p (1, operands[2])"
19172 [(set (match_dup 0)
19173 (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
19176 (and:QI (match_dup 2) (match_dup 3)))])]
19180 [(set (match_operand 0 "flags_reg_operand" "")
19181 (match_operator 1 "compare_operator"
19184 (match_operand 2 "ext_register_operand" "")
19187 (match_operand 3 "const_int_operand" ""))
19189 "! TARGET_PARTIAL_REG_STALL
19190 && ix86_match_ccmode (insn, CCNOmode)
19191 && true_regnum (operands[2]) != 0
19192 && peep2_reg_dead_p (1, operands[2])"
19193 [(parallel [(set (match_dup 0)
19202 (set (zero_extract:SI (match_dup 2)
19213 ;; Don't do logical operations with memory inputs.
19215 [(match_scratch:SI 2 "r")
19216 (parallel [(set (match_operand:SI 0 "register_operand" "")
19217 (match_operator:SI 3 "arith_or_logical_operator"
19219 (match_operand:SI 1 "memory_operand" "")]))
19220 (clobber (reg:CC FLAGS_REG))])]
19221 "! optimize_size && ! TARGET_READ_MODIFY"
19222 [(set (match_dup 2) (match_dup 1))
19223 (parallel [(set (match_dup 0)
19224 (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
19225 (clobber (reg:CC FLAGS_REG))])]
19229 [(match_scratch:SI 2 "r")
19230 (parallel [(set (match_operand:SI 0 "register_operand" "")
19231 (match_operator:SI 3 "arith_or_logical_operator"
19232 [(match_operand:SI 1 "memory_operand" "")
19234 (clobber (reg:CC FLAGS_REG))])]
19235 "! optimize_size && ! TARGET_READ_MODIFY"
19236 [(set (match_dup 2) (match_dup 1))
19237 (parallel [(set (match_dup 0)
19238 (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
19239 (clobber (reg:CC FLAGS_REG))])]
19242 ; Don't do logical operations with memory outputs
19244 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
19245 ; instruction into two 1-uop insns plus a 2-uop insn. That last has
19246 ; the same decoder scheduling characteristics as the original.
19249 [(match_scratch:SI 2 "r")
19250 (parallel [(set (match_operand:SI 0 "memory_operand" "")
19251 (match_operator:SI 3 "arith_or_logical_operator"
19253 (match_operand:SI 1 "nonmemory_operand" "")]))
19254 (clobber (reg:CC FLAGS_REG))])]
19255 "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
19256 [(set (match_dup 2) (match_dup 0))
19257 (parallel [(set (match_dup 2)
19258 (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
19259 (clobber (reg:CC FLAGS_REG))])
19260 (set (match_dup 0) (match_dup 2))]
19264 [(match_scratch:SI 2 "r")
19265 (parallel [(set (match_operand:SI 0 "memory_operand" "")
19266 (match_operator:SI 3 "arith_or_logical_operator"
19267 [(match_operand:SI 1 "nonmemory_operand" "")
19269 (clobber (reg:CC FLAGS_REG))])]
19270 "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
19271 [(set (match_dup 2) (match_dup 0))
19272 (parallel [(set (match_dup 2)
19273 (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
19274 (clobber (reg:CC FLAGS_REG))])
19275 (set (match_dup 0) (match_dup 2))]
19278 ;; Attempt to always use XOR for zeroing registers.
19280 [(set (match_operand 0 "register_operand" "")
19281 (match_operand 1 "const0_operand" ""))]
19282 "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD
19283 && (! TARGET_USE_MOV0 || optimize_size)
19284 && GENERAL_REG_P (operands[0])
19285 && peep2_regno_dead_p (0, FLAGS_REG)"
19286 [(parallel [(set (match_dup 0) (const_int 0))
19287 (clobber (reg:CC FLAGS_REG))])]
19289 operands[0] = gen_lowpart (word_mode, operands[0]);
19293 [(set (strict_low_part (match_operand 0 "register_operand" ""))
19295 "(GET_MODE (operands[0]) == QImode
19296 || GET_MODE (operands[0]) == HImode)
19297 && (! TARGET_USE_MOV0 || optimize_size)
19298 && peep2_regno_dead_p (0, FLAGS_REG)"
19299 [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
19300 (clobber (reg:CC FLAGS_REG))])])
19302 ;; For HI and SI modes, or $-1,reg is smaller than mov $-1,reg.
19304 [(set (match_operand 0 "register_operand" "")
19306 "(GET_MODE (operands[0]) == HImode
19307 || GET_MODE (operands[0]) == SImode
19308 || (GET_MODE (operands[0]) == DImode && TARGET_64BIT))
19309 && (optimize_size || TARGET_PENTIUM)
19310 && peep2_regno_dead_p (0, FLAGS_REG)"
19311 [(parallel [(set (match_dup 0) (const_int -1))
19312 (clobber (reg:CC FLAGS_REG))])]
19313 "operands[0] = gen_lowpart (GET_MODE (operands[0]) == DImode ? DImode : SImode,
19316 ;; Attempt to convert simple leas to adds. These can be created by
19319 [(set (match_operand:SI 0 "register_operand" "")
19320 (plus:SI (match_dup 0)
19321 (match_operand:SI 1 "nonmemory_operand" "")))]
19322 "peep2_regno_dead_p (0, FLAGS_REG)"
19323 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
19324 (clobber (reg:CC FLAGS_REG))])]
19328 [(set (match_operand:SI 0 "register_operand" "")
19329 (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
19330 (match_operand:DI 2 "nonmemory_operand" "")) 0))]
19331 "peep2_regno_dead_p (0, FLAGS_REG) && REGNO (operands[0]) == REGNO (operands[1])"
19332 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
19333 (clobber (reg:CC FLAGS_REG))])]
19334 "operands[2] = gen_lowpart (SImode, operands[2]);")
19337 [(set (match_operand:DI 0 "register_operand" "")
19338 (plus:DI (match_dup 0)
19339 (match_operand:DI 1 "x86_64_general_operand" "")))]
19340 "peep2_regno_dead_p (0, FLAGS_REG)"
19341 [(parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
19342 (clobber (reg:CC FLAGS_REG))])]
19346 [(set (match_operand:SI 0 "register_operand" "")
19347 (mult:SI (match_dup 0)
19348 (match_operand:SI 1 "const_int_operand" "")))]
19349 "exact_log2 (INTVAL (operands[1])) >= 0
19350 && peep2_regno_dead_p (0, FLAGS_REG)"
19351 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
19352 (clobber (reg:CC FLAGS_REG))])]
19353 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
19356 [(set (match_operand:DI 0 "register_operand" "")
19357 (mult:DI (match_dup 0)
19358 (match_operand:DI 1 "const_int_operand" "")))]
19359 "exact_log2 (INTVAL (operands[1])) >= 0
19360 && peep2_regno_dead_p (0, FLAGS_REG)"
19361 [(parallel [(set (match_dup 0) (ashift:DI (match_dup 0) (match_dup 2)))
19362 (clobber (reg:CC FLAGS_REG))])]
19363 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
19366 [(set (match_operand:SI 0 "register_operand" "")
19367 (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
19368 (match_operand:DI 2 "const_int_operand" "")) 0))]
19369 "exact_log2 (INTVAL (operands[2])) >= 0
19370 && REGNO (operands[0]) == REGNO (operands[1])
19371 && peep2_regno_dead_p (0, FLAGS_REG)"
19372 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
19373 (clobber (reg:CC FLAGS_REG))])]
19374 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
19376 ;; The ESP adjustments can be done by the push and pop instructions. Resulting
19377 ;; code is shorter, since push is only 1 byte, while add imm, %esp 3 bytes. On
19378 ;; many CPUs it is also faster, since special hardware to avoid esp
19379 ;; dependencies is present.
19381 ;; While some of these conversions may be done using splitters, we use peepholes
19382 ;; in order to allow combine_stack_adjustments pass to see nonobfuscated RTL.
19384 ;; Convert prologue esp subtractions to push.
19385 ;; We need register to push. In order to keep verify_flow_info happy we have
19387 ;; - use scratch and clobber it in order to avoid dependencies
19388 ;; - use already live register
19389 ;; We can't use the second way right now, since there is no reliable way how to
19390 ;; verify that given register is live. First choice will also most likely in
19391 ;; fewer dependencies. On the place of esp adjustments it is very likely that
19392 ;; call clobbered registers are dead. We may want to use base pointer as an
19393 ;; alternative when no register is available later.
19396 [(match_scratch:SI 0 "r")
19397 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
19398 (clobber (reg:CC FLAGS_REG))
19399 (clobber (mem:BLK (scratch)))])]
19400 "optimize_size || !TARGET_SUB_ESP_4"
19401 [(clobber (match_dup 0))
19402 (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
19403 (clobber (mem:BLK (scratch)))])])
19406 [(match_scratch:SI 0 "r")
19407 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
19408 (clobber (reg:CC FLAGS_REG))
19409 (clobber (mem:BLK (scratch)))])]
19410 "optimize_size || !TARGET_SUB_ESP_8"
19411 [(clobber (match_dup 0))
19412 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
19413 (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
19414 (clobber (mem:BLK (scratch)))])])
19416 ;; Convert esp subtractions to push.
19418 [(match_scratch:SI 0 "r")
19419 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
19420 (clobber (reg:CC FLAGS_REG))])]
19421 "optimize_size || !TARGET_SUB_ESP_4"
19422 [(clobber (match_dup 0))
19423 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
19426 [(match_scratch:SI 0 "r")
19427 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
19428 (clobber (reg:CC FLAGS_REG))])]
19429 "optimize_size || !TARGET_SUB_ESP_8"
19430 [(clobber (match_dup 0))
19431 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
19432 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
19434 ;; Convert epilogue deallocator to pop.
19436 [(match_scratch:SI 0 "r")
19437 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19438 (clobber (reg:CC FLAGS_REG))
19439 (clobber (mem:BLK (scratch)))])]
19440 "optimize_size || !TARGET_ADD_ESP_4"
19441 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19442 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19443 (clobber (mem:BLK (scratch)))])]
19446 ;; Two pops case is tricky, since pop causes dependency on destination register.
19447 ;; We use two registers if available.
19449 [(match_scratch:SI 0 "r")
19450 (match_scratch:SI 1 "r")
19451 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19452 (clobber (reg:CC FLAGS_REG))
19453 (clobber (mem:BLK (scratch)))])]
19454 "optimize_size || !TARGET_ADD_ESP_8"
19455 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19456 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19457 (clobber (mem:BLK (scratch)))])
19458 (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
19459 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19463 [(match_scratch:SI 0 "r")
19464 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19465 (clobber (reg:CC FLAGS_REG))
19466 (clobber (mem:BLK (scratch)))])]
19468 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19469 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19470 (clobber (mem:BLK (scratch)))])
19471 (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19472 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19475 ;; Convert esp additions to pop.
19477 [(match_scratch:SI 0 "r")
19478 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19479 (clobber (reg:CC FLAGS_REG))])]
19481 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19482 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19485 ;; Two pops case is tricky, since pop causes dependency on destination register.
19486 ;; We use two registers if available.
19488 [(match_scratch:SI 0 "r")
19489 (match_scratch:SI 1 "r")
19490 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19491 (clobber (reg:CC FLAGS_REG))])]
19493 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19494 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
19495 (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
19496 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19500 [(match_scratch:SI 0 "r")
19501 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19502 (clobber (reg:CC FLAGS_REG))])]
19504 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19505 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
19506 (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19507 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19510 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
19511 ;; required and register dies. Similarly for 128 to plus -128.
19513 [(set (match_operand 0 "flags_reg_operand" "")
19514 (match_operator 1 "compare_operator"
19515 [(match_operand 2 "register_operand" "")
19516 (match_operand 3 "const_int_operand" "")]))]
19517 "(INTVAL (operands[3]) == -1
19518 || INTVAL (operands[3]) == 1
19519 || INTVAL (operands[3]) == 128)
19520 && ix86_match_ccmode (insn, CCGCmode)
19521 && peep2_reg_dead_p (1, operands[2])"
19522 [(parallel [(set (match_dup 0)
19523 (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
19524 (clobber (match_dup 2))])]
19528 [(match_scratch:DI 0 "r")
19529 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
19530 (clobber (reg:CC FLAGS_REG))
19531 (clobber (mem:BLK (scratch)))])]
19532 "optimize_size || !TARGET_SUB_ESP_4"
19533 [(clobber (match_dup 0))
19534 (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19535 (clobber (mem:BLK (scratch)))])])
19538 [(match_scratch:DI 0 "r")
19539 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
19540 (clobber (reg:CC FLAGS_REG))
19541 (clobber (mem:BLK (scratch)))])]
19542 "optimize_size || !TARGET_SUB_ESP_8"
19543 [(clobber (match_dup 0))
19544 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19545 (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19546 (clobber (mem:BLK (scratch)))])])
19548 ;; Convert esp subtractions to push.
19550 [(match_scratch:DI 0 "r")
19551 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
19552 (clobber (reg:CC FLAGS_REG))])]
19553 "optimize_size || !TARGET_SUB_ESP_4"
19554 [(clobber (match_dup 0))
19555 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
19558 [(match_scratch:DI 0 "r")
19559 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
19560 (clobber (reg:CC FLAGS_REG))])]
19561 "optimize_size || !TARGET_SUB_ESP_8"
19562 [(clobber (match_dup 0))
19563 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19564 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
19566 ;; Convert epilogue deallocator to pop.
19568 [(match_scratch:DI 0 "r")
19569 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19570 (clobber (reg:CC FLAGS_REG))
19571 (clobber (mem:BLK (scratch)))])]
19572 "optimize_size || !TARGET_ADD_ESP_4"
19573 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19574 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19575 (clobber (mem:BLK (scratch)))])]
19578 ;; Two pops case is tricky, since pop causes dependency on destination register.
19579 ;; We use two registers if available.
19581 [(match_scratch:DI 0 "r")
19582 (match_scratch:DI 1 "r")
19583 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19584 (clobber (reg:CC FLAGS_REG))
19585 (clobber (mem:BLK (scratch)))])]
19586 "optimize_size || !TARGET_ADD_ESP_8"
19587 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19588 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19589 (clobber (mem:BLK (scratch)))])
19590 (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
19591 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19595 [(match_scratch:DI 0 "r")
19596 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19597 (clobber (reg:CC FLAGS_REG))
19598 (clobber (mem:BLK (scratch)))])]
19600 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19601 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19602 (clobber (mem:BLK (scratch)))])
19603 (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19604 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19607 ;; Convert esp additions to pop.
19609 [(match_scratch:DI 0 "r")
19610 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19611 (clobber (reg:CC FLAGS_REG))])]
19613 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19614 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19617 ;; Two pops case is tricky, since pop causes dependency on destination register.
19618 ;; We use two registers if available.
19620 [(match_scratch:DI 0 "r")
19621 (match_scratch:DI 1 "r")
19622 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19623 (clobber (reg:CC FLAGS_REG))])]
19625 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19626 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
19627 (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
19628 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19632 [(match_scratch:DI 0 "r")
19633 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19634 (clobber (reg:CC FLAGS_REG))])]
19636 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19637 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
19638 (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19639 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19642 ;; Convert imul by three, five and nine into lea
19645 [(set (match_operand:SI 0 "register_operand" "")
19646 (mult:SI (match_operand:SI 1 "register_operand" "")
19647 (match_operand:SI 2 "const_int_operand" "")))
19648 (clobber (reg:CC FLAGS_REG))])]
19649 "INTVAL (operands[2]) == 3
19650 || INTVAL (operands[2]) == 5
19651 || INTVAL (operands[2]) == 9"
19652 [(set (match_dup 0)
19653 (plus:SI (mult:SI (match_dup 1) (match_dup 2))
19655 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19659 [(set (match_operand:SI 0 "register_operand" "")
19660 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
19661 (match_operand:SI 2 "const_int_operand" "")))
19662 (clobber (reg:CC FLAGS_REG))])]
19664 && (INTVAL (operands[2]) == 3
19665 || INTVAL (operands[2]) == 5
19666 || INTVAL (operands[2]) == 9)"
19667 [(set (match_dup 0) (match_dup 1))
19669 (plus:SI (mult:SI (match_dup 0) (match_dup 2))
19671 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19675 [(set (match_operand:DI 0 "register_operand" "")
19676 (mult:DI (match_operand:DI 1 "register_operand" "")
19677 (match_operand:DI 2 "const_int_operand" "")))
19678 (clobber (reg:CC FLAGS_REG))])]
19680 && (INTVAL (operands[2]) == 3
19681 || INTVAL (operands[2]) == 5
19682 || INTVAL (operands[2]) == 9)"
19683 [(set (match_dup 0)
19684 (plus:DI (mult:DI (match_dup 1) (match_dup 2))
19686 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19690 [(set (match_operand:DI 0 "register_operand" "")
19691 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
19692 (match_operand:DI 2 "const_int_operand" "")))
19693 (clobber (reg:CC FLAGS_REG))])]
19696 && (INTVAL (operands[2]) == 3
19697 || INTVAL (operands[2]) == 5
19698 || INTVAL (operands[2]) == 9)"
19699 [(set (match_dup 0) (match_dup 1))
19701 (plus:DI (mult:DI (match_dup 0) (match_dup 2))
19703 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19705 ;; Imul $32bit_imm, mem, reg is vector decoded, while
19706 ;; imul $32bit_imm, reg, reg is direct decoded.
19708 [(match_scratch:DI 3 "r")
19709 (parallel [(set (match_operand:DI 0 "register_operand" "")
19710 (mult:DI (match_operand:DI 1 "memory_operand" "")
19711 (match_operand:DI 2 "immediate_operand" "")))
19712 (clobber (reg:CC FLAGS_REG))])]
19713 "TARGET_K8 && !optimize_size
19714 && (GET_CODE (operands[2]) != CONST_INT
19715 || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19716 [(set (match_dup 3) (match_dup 1))
19717 (parallel [(set (match_dup 0) (mult:DI (match_dup 3) (match_dup 2)))
19718 (clobber (reg:CC FLAGS_REG))])]
19722 [(match_scratch:SI 3 "r")
19723 (parallel [(set (match_operand:SI 0 "register_operand" "")
19724 (mult:SI (match_operand:SI 1 "memory_operand" "")
19725 (match_operand:SI 2 "immediate_operand" "")))
19726 (clobber (reg:CC FLAGS_REG))])]
19727 "TARGET_K8 && !optimize_size
19728 && (GET_CODE (operands[2]) != CONST_INT
19729 || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19730 [(set (match_dup 3) (match_dup 1))
19731 (parallel [(set (match_dup 0) (mult:SI (match_dup 3) (match_dup 2)))
19732 (clobber (reg:CC FLAGS_REG))])]
19736 [(match_scratch:SI 3 "r")
19737 (parallel [(set (match_operand:DI 0 "register_operand" "")
19739 (mult:SI (match_operand:SI 1 "memory_operand" "")
19740 (match_operand:SI 2 "immediate_operand" ""))))
19741 (clobber (reg:CC FLAGS_REG))])]
19742 "TARGET_K8 && !optimize_size
19743 && (GET_CODE (operands[2]) != CONST_INT
19744 || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19745 [(set (match_dup 3) (match_dup 1))
19746 (parallel [(set (match_dup 0) (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
19747 (clobber (reg:CC FLAGS_REG))])]
19750 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
19751 ;; Convert it into imul reg, reg
19752 ;; It would be better to force assembler to encode instruction using long
19753 ;; immediate, but there is apparently no way to do so.
19755 [(parallel [(set (match_operand:DI 0 "register_operand" "")
19756 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
19757 (match_operand:DI 2 "const_int_operand" "")))
19758 (clobber (reg:CC FLAGS_REG))])
19759 (match_scratch:DI 3 "r")]
19760 "TARGET_K8 && !optimize_size
19761 && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')"
19762 [(set (match_dup 3) (match_dup 2))
19763 (parallel [(set (match_dup 0) (mult:DI (match_dup 0) (match_dup 3)))
19764 (clobber (reg:CC FLAGS_REG))])]
19766 if (!rtx_equal_p (operands[0], operands[1]))
19767 emit_move_insn (operands[0], operands[1]);
19771 [(parallel [(set (match_operand:SI 0 "register_operand" "")
19772 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
19773 (match_operand:SI 2 "const_int_operand" "")))
19774 (clobber (reg:CC FLAGS_REG))])
19775 (match_scratch:SI 3 "r")]
19776 "TARGET_K8 && !optimize_size
19777 && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')"
19778 [(set (match_dup 3) (match_dup 2))
19779 (parallel [(set (match_dup 0) (mult:SI (match_dup 0) (match_dup 3)))
19780 (clobber (reg:CC FLAGS_REG))])]
19782 if (!rtx_equal_p (operands[0], operands[1]))
19783 emit_move_insn (operands[0], operands[1]);
19787 [(parallel [(set (match_operand:HI 0 "register_operand" "")
19788 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "")
19789 (match_operand:HI 2 "immediate_operand" "")))
19790 (clobber (reg:CC FLAGS_REG))])
19791 (match_scratch:HI 3 "r")]
19792 "TARGET_K8 && !optimize_size"
19793 [(set (match_dup 3) (match_dup 2))
19794 (parallel [(set (match_dup 0) (mult:HI (match_dup 0) (match_dup 3)))
19795 (clobber (reg:CC FLAGS_REG))])]
19797 if (!rtx_equal_p (operands[0], operands[1]))
19798 emit_move_insn (operands[0], operands[1]);
19801 ;; After splitting up read-modify operations, array accesses with memory
19802 ;; operands might end up in form:
19804 ;; movl 4(%esp), %edx
19806 ;; instead of pre-splitting:
19808 ;; addl 4(%esp), %eax
19810 ;; movl 4(%esp), %edx
19811 ;; leal (%edx,%eax,4), %eax
19814 [(parallel [(set (match_operand 0 "register_operand" "")
19815 (ashift (match_operand 1 "register_operand" "")
19816 (match_operand 2 "const_int_operand" "")))
19817 (clobber (reg:CC FLAGS_REG))])
19818 (set (match_operand 3 "register_operand")
19819 (match_operand 4 "x86_64_general_operand" ""))
19820 (parallel [(set (match_operand 5 "register_operand" "")
19821 (plus (match_operand 6 "register_operand" "")
19822 (match_operand 7 "register_operand" "")))
19823 (clobber (reg:CC FLAGS_REG))])]
19824 "INTVAL (operands[2]) >= 0 && INTVAL (operands[2]) <= 3
19825 /* Validate MODE for lea. */
19826 && ((!TARGET_PARTIAL_REG_STALL
19827 && (GET_MODE (operands[0]) == QImode
19828 || GET_MODE (operands[0]) == HImode))
19829 || GET_MODE (operands[0]) == SImode
19830 || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
19831 /* We reorder load and the shift. */
19832 && !rtx_equal_p (operands[1], operands[3])
19833 && !reg_overlap_mentioned_p (operands[0], operands[4])
19834 /* Last PLUS must consist of operand 0 and 3. */
19835 && !rtx_equal_p (operands[0], operands[3])
19836 && (rtx_equal_p (operands[3], operands[6])
19837 || rtx_equal_p (operands[3], operands[7]))
19838 && (rtx_equal_p (operands[0], operands[6])
19839 || rtx_equal_p (operands[0], operands[7]))
19840 /* The intermediate operand 0 must die or be same as output. */
19841 && (rtx_equal_p (operands[0], operands[5])
19842 || peep2_reg_dead_p (3, operands[0]))"
19843 [(set (match_dup 3) (match_dup 4))
19844 (set (match_dup 0) (match_dup 1))]
19846 enum machine_mode mode = GET_MODE (operands[5]) == DImode ? DImode : SImode;
19847 int scale = 1 << INTVAL (operands[2]);
19848 rtx index = gen_lowpart (Pmode, operands[1]);
19849 rtx base = gen_lowpart (Pmode, operands[3]);
19850 rtx dest = gen_lowpart (mode, operands[5]);
19852 operands[1] = gen_rtx_PLUS (Pmode, base,
19853 gen_rtx_MULT (Pmode, index, GEN_INT (scale)));
19855 operands[1] = gen_rtx_SUBREG (mode, operands[1], 0);
19856 operands[0] = dest;
19859 ;; Call-value patterns last so that the wildcard operand does not
19860 ;; disrupt insn-recog's switch tables.
19862 (define_insn "*call_value_pop_0"
19863 [(set (match_operand 0 "" "")
19864 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
19865 (match_operand:SI 2 "" "")))
19866 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
19867 (match_operand:SI 3 "immediate_operand" "")))]
19870 if (SIBLING_CALL_P (insn))
19873 return "call\t%P1";
19875 [(set_attr "type" "callv")])
19877 (define_insn "*call_value_pop_1"
19878 [(set (match_operand 0 "" "")
19879 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
19880 (match_operand:SI 2 "" "")))
19881 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
19882 (match_operand:SI 3 "immediate_operand" "i")))]
19885 if (constant_call_address_operand (operands[1], Pmode))
19887 if (SIBLING_CALL_P (insn))
19890 return "call\t%P1";
19892 if (SIBLING_CALL_P (insn))
19895 return "call\t%A1";
19897 [(set_attr "type" "callv")])
19899 (define_insn "*call_value_0"
19900 [(set (match_operand 0 "" "")
19901 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
19902 (match_operand:SI 2 "" "")))]
19905 if (SIBLING_CALL_P (insn))
19908 return "call\t%P1";
19910 [(set_attr "type" "callv")])
19912 (define_insn "*call_value_0_rex64"
19913 [(set (match_operand 0 "" "")
19914 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
19915 (match_operand:DI 2 "const_int_operand" "")))]
19918 if (SIBLING_CALL_P (insn))
19921 return "call\t%P1";
19923 [(set_attr "type" "callv")])
19925 (define_insn "*call_value_1"
19926 [(set (match_operand 0 "" "")
19927 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
19928 (match_operand:SI 2 "" "")))]
19929 "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
19931 if (constant_call_address_operand (operands[1], Pmode))
19932 return "call\t%P1";
19933 return "call\t%A1";
19935 [(set_attr "type" "callv")])
19937 (define_insn "*sibcall_value_1"
19938 [(set (match_operand 0 "" "")
19939 (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "s,c,d,a"))
19940 (match_operand:SI 2 "" "")))]
19941 "SIBLING_CALL_P (insn) && !TARGET_64BIT"
19943 if (constant_call_address_operand (operands[1], Pmode))
19947 [(set_attr "type" "callv")])
19949 (define_insn "*call_value_1_rex64"
19950 [(set (match_operand 0 "" "")
19951 (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rsm"))
19952 (match_operand:DI 2 "" "")))]
19953 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
19955 if (constant_call_address_operand (operands[1], Pmode))
19956 return "call\t%P1";
19957 return "call\t%A1";
19959 [(set_attr "type" "callv")])
19961 (define_insn "*sibcall_value_1_rex64"
19962 [(set (match_operand 0 "" "")
19963 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
19964 (match_operand:DI 2 "" "")))]
19965 "SIBLING_CALL_P (insn) && TARGET_64BIT"
19967 [(set_attr "type" "callv")])
19969 (define_insn "*sibcall_value_1_rex64_v"
19970 [(set (match_operand 0 "" "")
19971 (call (mem:QI (reg:DI 40))
19972 (match_operand:DI 1 "" "")))]
19973 "SIBLING_CALL_P (insn) && TARGET_64BIT"
19975 [(set_attr "type" "callv")])
19977 ;; We used to use "int $5", in honor of #BR which maps to interrupt vector 5.
19978 ;; That, however, is usually mapped by the OS to SIGSEGV, which is often
19979 ;; caught for use by garbage collectors and the like. Using an insn that
19980 ;; maps to SIGILL makes it more likely the program will rightfully die.
19981 ;; Keeping with tradition, "6" is in honor of #UD.
19982 (define_insn "trap"
19983 [(trap_if (const_int 1) (const_int 6))]
19986 [(set_attr "length" "2")])
19988 (define_expand "sse_prologue_save"
19989 [(parallel [(set (match_operand:BLK 0 "" "")
19990 (unspec:BLK [(reg:DI 21)
19997 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
19998 (use (match_operand:DI 1 "register_operand" ""))
19999 (use (match_operand:DI 2 "immediate_operand" ""))
20000 (use (label_ref:DI (match_operand 3 "" "")))])]
20004 (define_insn "*sse_prologue_save_insn"
20005 [(set (mem:BLK (plus:DI (match_operand:DI 0 "register_operand" "R")
20006 (match_operand:DI 4 "const_int_operand" "n")))
20007 (unspec:BLK [(reg:DI 21)
20014 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
20015 (use (match_operand:DI 1 "register_operand" "r"))
20016 (use (match_operand:DI 2 "const_int_operand" "i"))
20017 (use (label_ref:DI (match_operand 3 "" "X")))]
20019 && INTVAL (operands[4]) + SSE_REGPARM_MAX * 16 - 16 < 128
20020 && INTVAL (operands[4]) + INTVAL (operands[2]) * 16 >= -128"
20024 operands[0] = gen_rtx_MEM (Pmode,
20025 gen_rtx_PLUS (Pmode, operands[0], operands[4]));
20026 output_asm_insn (\"jmp\\t%A1\", operands);
20027 for (i = SSE_REGPARM_MAX - 1; i >= INTVAL (operands[2]); i--)
20029 operands[4] = adjust_address (operands[0], DImode, i*16);
20030 operands[5] = gen_rtx_REG (TImode, SSE_REGNO (i));
20031 PUT_MODE (operands[4], TImode);
20032 if (GET_CODE (XEXP (operands[0], 0)) != PLUS)
20033 output_asm_insn (\"rex\", operands);
20034 output_asm_insn (\"movaps\\t{%5, %4|%4, %5}\", operands);
20036 (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
20037 CODE_LABEL_NUMBER (operands[3]));
20041 [(set_attr "type" "other")
20042 (set_attr "length_immediate" "0")
20043 (set_attr "length_address" "0")
20044 (set_attr "length" "135")
20045 (set_attr "memory" "store")
20046 (set_attr "modrm" "0")
20047 (set_attr "mode" "DI")])
20049 (define_expand "prefetch"
20050 [(prefetch (match_operand 0 "address_operand" "")
20051 (match_operand:SI 1 "const_int_operand" "")
20052 (match_operand:SI 2 "const_int_operand" ""))]
20053 "TARGET_PREFETCH_SSE || TARGET_3DNOW"
20055 int rw = INTVAL (operands[1]);
20056 int locality = INTVAL (operands[2]);
20058 gcc_assert (rw == 0 || rw == 1);
20059 gcc_assert (locality >= 0 && locality <= 3);
20060 gcc_assert (GET_MODE (operands[0]) == Pmode
20061 || GET_MODE (operands[0]) == VOIDmode);
20063 /* Use 3dNOW prefetch in case we are asking for write prefetch not
20064 supported by SSE counterpart or the SSE prefetch is not available
20065 (K6 machines). Otherwise use SSE prefetch as it allows specifying
20067 if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
20068 operands[2] = GEN_INT (3);
20070 operands[1] = const0_rtx;
20073 (define_insn "*prefetch_sse"
20074 [(prefetch (match_operand:SI 0 "address_operand" "p")
20076 (match_operand:SI 1 "const_int_operand" ""))]
20077 "TARGET_PREFETCH_SSE && !TARGET_64BIT"
20079 static const char * const patterns[4] = {
20080 "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
20083 int locality = INTVAL (operands[1]);
20084 gcc_assert (locality >= 0 && locality <= 3);
20086 return patterns[locality];
20088 [(set_attr "type" "sse")
20089 (set_attr "memory" "none")])
20091 (define_insn "*prefetch_sse_rex"
20092 [(prefetch (match_operand:DI 0 "address_operand" "p")
20094 (match_operand:SI 1 "const_int_operand" ""))]
20095 "TARGET_PREFETCH_SSE && TARGET_64BIT"
20097 static const char * const patterns[4] = {
20098 "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
20101 int locality = INTVAL (operands[1]);
20102 gcc_assert (locality >= 0 && locality <= 3);
20104 return patterns[locality];
20106 [(set_attr "type" "sse")
20107 (set_attr "memory" "none")])
20109 (define_insn "*prefetch_3dnow"
20110 [(prefetch (match_operand:SI 0 "address_operand" "p")
20111 (match_operand:SI 1 "const_int_operand" "n")
20113 "TARGET_3DNOW && !TARGET_64BIT"
20115 if (INTVAL (operands[1]) == 0)
20116 return "prefetch\t%a0";
20118 return "prefetchw\t%a0";
20120 [(set_attr "type" "mmx")
20121 (set_attr "memory" "none")])
20123 (define_insn "*prefetch_3dnow_rex"
20124 [(prefetch (match_operand:DI 0 "address_operand" "p")
20125 (match_operand:SI 1 "const_int_operand" "n")
20127 "TARGET_3DNOW && TARGET_64BIT"
20129 if (INTVAL (operands[1]) == 0)
20130 return "prefetch\t%a0";
20132 return "prefetchw\t%a0";
20134 [(set_attr "type" "mmx")
20135 (set_attr "memory" "none")])
20137 (define_expand "stack_protect_set"
20138 [(match_operand 0 "memory_operand" "")
20139 (match_operand 1 "memory_operand" "")]
20142 #ifdef TARGET_THREAD_SSP_OFFSET
20144 emit_insn (gen_stack_tls_protect_set_di (operands[0],
20145 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
20147 emit_insn (gen_stack_tls_protect_set_si (operands[0],
20148 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
20151 emit_insn (gen_stack_protect_set_di (operands[0], operands[1]));
20153 emit_insn (gen_stack_protect_set_si (operands[0], operands[1]));
20158 (define_insn "stack_protect_set_si"
20159 [(set (match_operand:SI 0 "memory_operand" "=m")
20160 (unspec:SI [(match_operand:SI 1 "memory_operand" "m")] UNSPEC_SP_SET))
20161 (set (match_scratch:SI 2 "=&r") (const_int 0))
20162 (clobber (reg:CC FLAGS_REG))]
20164 "mov{l}\t{%1, %2|%2, %1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
20165 [(set_attr "type" "multi")])
20167 (define_insn "stack_protect_set_di"
20168 [(set (match_operand:DI 0 "memory_operand" "=m")
20169 (unspec:DI [(match_operand:DI 1 "memory_operand" "m")] UNSPEC_SP_SET))
20170 (set (match_scratch:DI 2 "=&r") (const_int 0))
20171 (clobber (reg:CC FLAGS_REG))]
20173 "mov{q}\t{%1, %2|%2, %1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
20174 [(set_attr "type" "multi")])
20176 (define_insn "stack_tls_protect_set_si"
20177 [(set (match_operand:SI 0 "memory_operand" "=m")
20178 (unspec:SI [(match_operand:SI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
20179 (set (match_scratch:SI 2 "=&r") (const_int 0))
20180 (clobber (reg:CC FLAGS_REG))]
20182 "mov{l}\t{%%gs:%P1, %2|%2, DWORD PTR %%gs:%P1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
20183 [(set_attr "type" "multi")])
20185 (define_insn "stack_tls_protect_set_di"
20186 [(set (match_operand:DI 0 "memory_operand" "=m")
20187 (unspec:DI [(match_operand:DI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
20188 (set (match_scratch:DI 2 "=&r") (const_int 0))
20189 (clobber (reg:CC FLAGS_REG))]
20191 "mov{q}\t{%%fs:%P1, %2|%2, QWORD PTR %%fs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
20192 [(set_attr "type" "multi")])
20194 (define_expand "stack_protect_test"
20195 [(match_operand 0 "memory_operand" "")
20196 (match_operand 1 "memory_operand" "")
20197 (match_operand 2 "" "")]
20200 rtx flags = gen_rtx_REG (CCZmode, FLAGS_REG);
20201 ix86_compare_op0 = operands[0];
20202 ix86_compare_op1 = operands[1];
20203 ix86_compare_emitted = flags;
20205 #ifdef TARGET_THREAD_SSP_OFFSET
20207 emit_insn (gen_stack_tls_protect_test_di (flags, operands[0],
20208 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
20210 emit_insn (gen_stack_tls_protect_test_si (flags, operands[0],
20211 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
20214 emit_insn (gen_stack_protect_test_di (flags, operands[0], operands[1]));
20216 emit_insn (gen_stack_protect_test_si (flags, operands[0], operands[1]));
20218 emit_jump_insn (gen_beq (operands[2]));
20222 (define_insn "stack_protect_test_si"
20223 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
20224 (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
20225 (match_operand:SI 2 "memory_operand" "m")]
20227 (clobber (match_scratch:SI 3 "=&r"))]
20229 "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%2, %3|%3, %2}"
20230 [(set_attr "type" "multi")])
20232 (define_insn "stack_protect_test_di"
20233 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
20234 (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
20235 (match_operand:DI 2 "memory_operand" "m")]
20237 (clobber (match_scratch:DI 3 "=&r"))]
20239 "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%2, %3|%3, %2}"
20240 [(set_attr "type" "multi")])
20242 (define_insn "stack_tls_protect_test_si"
20243 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
20244 (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
20245 (match_operand:SI 2 "const_int_operand" "i")]
20246 UNSPEC_SP_TLS_TEST))
20247 (clobber (match_scratch:SI 3 "=r"))]
20249 "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%%gs:%P2, %3|%3, DWORD PTR %%gs:%P2}"
20250 [(set_attr "type" "multi")])
20252 (define_insn "stack_tls_protect_test_di"
20253 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
20254 (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
20255 (match_operand:DI 2 "const_int_operand" "i")]
20256 UNSPEC_SP_TLS_TEST))
20257 (clobber (match_scratch:DI 3 "=r"))]
20259 "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%fs:%P2, %3|%3, QWORD PTR %%fs:%P2}"
20260 [(set_attr "type" "multi")])
20264 (include "sync.md")