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)
73 (UNSPEC_TLS_LD_BASE 17)
75 ; Other random patterns
85 ; For SSE/MMX support:
86 (UNSPEC_FIX_NOTRUNC 30)
94 (UNSPEC_NOP 38) ; prevents combiner cleverness
105 ; Generic math support
107 (UNSPEC_IEEE_MIN 51) ; not commutative
108 (UNSPEC_IEEE_MAX 52) ; not commutative
121 (UNSPEC_FRNDINT_FLOOR 70)
122 (UNSPEC_FRNDINT_CEIL 71)
123 (UNSPEC_FRNDINT_TRUNC 72)
124 (UNSPEC_FRNDINT_MASK_PM 73)
125 (UNSPEC_FIST_FLOOR 74)
126 (UNSPEC_FIST_CEIL 75)
128 ; x87 Double output FP
129 (UNSPEC_SINCOS_COS 80)
130 (UNSPEC_SINCOS_SIN 81)
133 (UNSPEC_XTRACT_FRACT 84)
134 (UNSPEC_XTRACT_EXP 85)
135 (UNSPEC_FSCALE_FRACT 86)
136 (UNSPEC_FSCALE_EXP 87)
145 (UNSPEC_SP_TLS_SET 102)
146 (UNSPEC_SP_TLS_TEST 103)
150 [(UNSPECV_BLOCKAGE 0)
151 (UNSPECV_STACK_PROBE 1)
160 (UNSPECV_CMPXCHG_1 10)
161 (UNSPECV_CMPXCHG_2 11)
166 ;; Registers by name.
175 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
178 ;; In C guard expressions, put expressions which may be compile-time
179 ;; constants first. This allows for better optimization. For
180 ;; example, write "TARGET_64BIT && reload_completed", not
181 ;; "reload_completed && TARGET_64BIT".
184 ;; Processor type. This attribute must exactly match the processor_type
185 ;; enumeration in i386.h.
186 (define_attr "cpu" "i386,i486,pentium,pentiumpro,k6,athlon,pentium4,k8,nocona"
187 (const (symbol_ref "ix86_tune")))
189 ;; A basic instruction type. Refinements due to arguments to be
190 ;; provided in other attributes.
193 alu,alu1,negnot,imov,imovx,lea,
194 incdec,ishift,ishift1,rotate,rotate1,imul,idiv,
195 icmp,test,ibr,setcc,icmov,
196 push,pop,call,callv,leave,
198 fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint,
199 sselog,sselog1,sseiadd,sseishft,sseimul,
200 sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv,
201 mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft"
202 (const_string "other"))
204 ;; Main data type used by the insn
206 "unknown,none,QI,HI,SI,DI,SF,DF,XF,TI,V4SF,V2DF,V2SF,V1DF"
207 (const_string "unknown"))
209 ;; The CPU unit operations uses.
210 (define_attr "unit" "integer,i387,sse,mmx,unknown"
211 (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint")
212 (const_string "i387")
213 (eq_attr "type" "sselog,sselog1,sseiadd,sseishft,sseimul,
214 sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv")
216 (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft")
218 (eq_attr "type" "other")
219 (const_string "unknown")]
220 (const_string "integer")))
222 ;; The (bounding maximum) length of an instruction immediate.
223 (define_attr "length_immediate" ""
224 (cond [(eq_attr "type" "incdec,setcc,icmov,str,cld,lea,other,multi,idiv,leave")
226 (eq_attr "unit" "i387,sse,mmx")
228 (eq_attr "type" "alu,alu1,negnot,imovx,ishift,rotate,ishift1,rotate1,
230 (symbol_ref "ix86_attr_length_immediate_default(insn,1)")
231 (eq_attr "type" "imov,test")
232 (symbol_ref "ix86_attr_length_immediate_default(insn,0)")
233 (eq_attr "type" "call")
234 (if_then_else (match_operand 0 "constant_call_address_operand" "")
237 (eq_attr "type" "callv")
238 (if_then_else (match_operand 1 "constant_call_address_operand" "")
241 ;; We don't know the size before shorten_branches. Expect
242 ;; the instruction to fit for better scheduling.
243 (eq_attr "type" "ibr")
246 (symbol_ref "/* Update immediate_length and other attributes! */
247 gcc_unreachable (),1")))
249 ;; The (bounding maximum) length of an instruction address.
250 (define_attr "length_address" ""
251 (cond [(eq_attr "type" "str,cld,other,multi,fxch")
253 (and (eq_attr "type" "call")
254 (match_operand 0 "constant_call_address_operand" ""))
256 (and (eq_attr "type" "callv")
257 (match_operand 1 "constant_call_address_operand" ""))
260 (symbol_ref "ix86_attr_length_address_default (insn)")))
262 ;; Set when length prefix is used.
263 (define_attr "prefix_data16" ""
264 (if_then_else (ior (eq_attr "mode" "HI")
265 (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF")))
269 ;; Set when string REP prefix is used.
270 (define_attr "prefix_rep" ""
271 (if_then_else (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF"))
275 ;; Set when 0f opcode prefix is used.
276 (define_attr "prefix_0f" ""
278 (ior (eq_attr "type" "imovx,setcc,icmov")
279 (eq_attr "unit" "sse,mmx"))
283 ;; Set when REX opcode prefix is used.
284 (define_attr "prefix_rex" ""
285 (cond [(and (eq_attr "mode" "DI")
286 (eq_attr "type" "!push,pop,call,callv,leave,ibr"))
288 (and (eq_attr "mode" "QI")
289 (ne (symbol_ref "x86_extended_QIreg_mentioned_p (insn)")
292 (ne (symbol_ref "x86_extended_reg_mentioned_p (insn)")
298 ;; Set when modrm byte is used.
299 (define_attr "modrm" ""
300 (cond [(eq_attr "type" "str,cld,leave")
302 (eq_attr "unit" "i387")
304 (and (eq_attr "type" "incdec")
305 (ior (match_operand:SI 1 "register_operand" "")
306 (match_operand:HI 1 "register_operand" "")))
308 (and (eq_attr "type" "push")
309 (not (match_operand 1 "memory_operand" "")))
311 (and (eq_attr "type" "pop")
312 (not (match_operand 0 "memory_operand" "")))
314 (and (eq_attr "type" "imov")
315 (and (match_operand 0 "register_operand" "")
316 (match_operand 1 "immediate_operand" "")))
318 (and (eq_attr "type" "call")
319 (match_operand 0 "constant_call_address_operand" ""))
321 (and (eq_attr "type" "callv")
322 (match_operand 1 "constant_call_address_operand" ""))
327 ;; The (bounding maximum) length of an instruction in bytes.
328 ;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences.
329 ;; Later we may want to split them and compute proper length as for
331 (define_attr "length" ""
332 (cond [(eq_attr "type" "other,multi,fistp,frndint")
334 (eq_attr "type" "fcmp")
336 (eq_attr "unit" "i387")
338 (plus (attr "prefix_data16")
339 (attr "length_address")))]
340 (plus (plus (attr "modrm")
341 (plus (attr "prefix_0f")
342 (plus (attr "prefix_rex")
344 (plus (attr "prefix_rep")
345 (plus (attr "prefix_data16")
346 (plus (attr "length_immediate")
347 (attr "length_address")))))))
349 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
350 ;; `store' if there is a simple memory reference therein, or `unknown'
351 ;; if the instruction is complex.
353 (define_attr "memory" "none,load,store,both,unknown"
354 (cond [(eq_attr "type" "other,multi,str")
355 (const_string "unknown")
356 (eq_attr "type" "lea,fcmov,fpspc,cld")
357 (const_string "none")
358 (eq_attr "type" "fistp,leave")
359 (const_string "both")
360 (eq_attr "type" "frndint")
361 (const_string "load")
362 (eq_attr "type" "push")
363 (if_then_else (match_operand 1 "memory_operand" "")
364 (const_string "both")
365 (const_string "store"))
366 (eq_attr "type" "pop")
367 (if_then_else (match_operand 0 "memory_operand" "")
368 (const_string "both")
369 (const_string "load"))
370 (eq_attr "type" "setcc")
371 (if_then_else (match_operand 0 "memory_operand" "")
372 (const_string "store")
373 (const_string "none"))
374 (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp")
375 (if_then_else (ior (match_operand 0 "memory_operand" "")
376 (match_operand 1 "memory_operand" ""))
377 (const_string "load")
378 (const_string "none"))
379 (eq_attr "type" "ibr")
380 (if_then_else (match_operand 0 "memory_operand" "")
381 (const_string "load")
382 (const_string "none"))
383 (eq_attr "type" "call")
384 (if_then_else (match_operand 0 "constant_call_address_operand" "")
385 (const_string "none")
386 (const_string "load"))
387 (eq_attr "type" "callv")
388 (if_then_else (match_operand 1 "constant_call_address_operand" "")
389 (const_string "none")
390 (const_string "load"))
391 (and (eq_attr "type" "alu1,negnot,ishift1,sselog1")
392 (match_operand 1 "memory_operand" ""))
393 (const_string "both")
394 (and (match_operand 0 "memory_operand" "")
395 (match_operand 1 "memory_operand" ""))
396 (const_string "both")
397 (match_operand 0 "memory_operand" "")
398 (const_string "store")
399 (match_operand 1 "memory_operand" "")
400 (const_string "load")
402 "!alu1,negnot,ishift1,
403 imov,imovx,icmp,test,
405 sse,ssemov,ssecmp,ssecomi,ssecvt,sseicvt,sselog1,
406 mmx,mmxmov,mmxcmp,mmxcvt")
407 (match_operand 2 "memory_operand" ""))
408 (const_string "load")
409 (and (eq_attr "type" "icmov")
410 (match_operand 3 "memory_operand" ""))
411 (const_string "load")
413 (const_string "none")))
415 ;; Indicates if an instruction has both an immediate and a displacement.
417 (define_attr "imm_disp" "false,true,unknown"
418 (cond [(eq_attr "type" "other,multi")
419 (const_string "unknown")
420 (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1")
421 (and (match_operand 0 "memory_displacement_operand" "")
422 (match_operand 1 "immediate_operand" "")))
423 (const_string "true")
424 (and (eq_attr "type" "alu,ishift,rotate,imul,idiv")
425 (and (match_operand 0 "memory_displacement_operand" "")
426 (match_operand 2 "immediate_operand" "")))
427 (const_string "true")
429 (const_string "false")))
431 ;; Indicates if an FP operation has an integer source.
433 (define_attr "fp_int_src" "false,true"
434 (const_string "false"))
436 ;; Defines rounding mode of an FP operation.
438 (define_attr "i387_cw" "trunc,floor,ceil,mask_pm,uninitialized,any"
439 (const_string "any"))
441 ;; Describe a user's asm statement.
442 (define_asm_attributes
443 [(set_attr "length" "128")
444 (set_attr "type" "multi")])
446 ;; All x87 floating point modes
447 (define_mode_macro X87MODEF [SF DF XF])
449 ;; All integer modes handled by x87 fisttp operator.
450 (define_mode_macro X87MODEI [HI SI DI])
452 ;; All integer modes handled by integer x87 operators.
453 (define_mode_macro X87MODEI12 [HI SI])
455 ;; All SSE floating point modes
456 (define_mode_macro SSEMODEF [SF DF])
458 ;; All integer modes handled by SSE cvtts?2si* operators.
459 (define_mode_macro SSEMODEI24 [SI DI])
462 ;; Scheduling descriptions
464 (include "pentium.md")
467 (include "athlon.md")
470 ;; Operand and operator predicates
472 (include "predicates.md")
475 ;; Compare instructions.
477 ;; All compare insns have expanders that save the operands away without
478 ;; actually generating RTL. The bCOND or sCOND (emitted immediately
479 ;; after the cmp) will actually emit the cmpM.
481 (define_expand "cmpdi"
482 [(set (reg:CC FLAGS_REG)
483 (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
484 (match_operand:DI 1 "x86_64_general_operand" "")))]
487 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
488 operands[0] = force_reg (DImode, operands[0]);
489 ix86_compare_op0 = operands[0];
490 ix86_compare_op1 = operands[1];
494 (define_expand "cmpsi"
495 [(set (reg:CC FLAGS_REG)
496 (compare:CC (match_operand:SI 0 "cmpsi_operand" "")
497 (match_operand:SI 1 "general_operand" "")))]
500 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
501 operands[0] = force_reg (SImode, operands[0]);
502 ix86_compare_op0 = operands[0];
503 ix86_compare_op1 = operands[1];
507 (define_expand "cmphi"
508 [(set (reg:CC FLAGS_REG)
509 (compare:CC (match_operand:HI 0 "nonimmediate_operand" "")
510 (match_operand:HI 1 "general_operand" "")))]
513 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
514 operands[0] = force_reg (HImode, operands[0]);
515 ix86_compare_op0 = operands[0];
516 ix86_compare_op1 = operands[1];
520 (define_expand "cmpqi"
521 [(set (reg:CC FLAGS_REG)
522 (compare:CC (match_operand:QI 0 "nonimmediate_operand" "")
523 (match_operand:QI 1 "general_operand" "")))]
526 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
527 operands[0] = force_reg (QImode, operands[0]);
528 ix86_compare_op0 = operands[0];
529 ix86_compare_op1 = operands[1];
533 (define_insn "cmpdi_ccno_1_rex64"
534 [(set (reg FLAGS_REG)
535 (compare (match_operand:DI 0 "nonimmediate_operand" "r,?mr")
536 (match_operand:DI 1 "const0_operand" "n,n")))]
537 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
539 test{q}\t{%0, %0|%0, %0}
540 cmp{q}\t{%1, %0|%0, %1}"
541 [(set_attr "type" "test,icmp")
542 (set_attr "length_immediate" "0,1")
543 (set_attr "mode" "DI")])
545 (define_insn "*cmpdi_minus_1_rex64"
546 [(set (reg FLAGS_REG)
547 (compare (minus:DI (match_operand:DI 0 "nonimmediate_operand" "rm,r")
548 (match_operand:DI 1 "x86_64_general_operand" "re,mr"))
550 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)"
551 "cmp{q}\t{%1, %0|%0, %1}"
552 [(set_attr "type" "icmp")
553 (set_attr "mode" "DI")])
555 (define_expand "cmpdi_1_rex64"
556 [(set (reg:CC FLAGS_REG)
557 (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
558 (match_operand:DI 1 "general_operand" "")))]
562 (define_insn "cmpdi_1_insn_rex64"
563 [(set (reg FLAGS_REG)
564 (compare (match_operand:DI 0 "nonimmediate_operand" "mr,r")
565 (match_operand:DI 1 "x86_64_general_operand" "re,mr")))]
566 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
567 "cmp{q}\t{%1, %0|%0, %1}"
568 [(set_attr "type" "icmp")
569 (set_attr "mode" "DI")])
572 (define_insn "*cmpsi_ccno_1"
573 [(set (reg FLAGS_REG)
574 (compare (match_operand:SI 0 "nonimmediate_operand" "r,?mr")
575 (match_operand:SI 1 "const0_operand" "n,n")))]
576 "ix86_match_ccmode (insn, CCNOmode)"
578 test{l}\t{%0, %0|%0, %0}
579 cmp{l}\t{%1, %0|%0, %1}"
580 [(set_attr "type" "test,icmp")
581 (set_attr "length_immediate" "0,1")
582 (set_attr "mode" "SI")])
584 (define_insn "*cmpsi_minus_1"
585 [(set (reg FLAGS_REG)
586 (compare (minus:SI (match_operand:SI 0 "nonimmediate_operand" "rm,r")
587 (match_operand:SI 1 "general_operand" "ri,mr"))
589 "ix86_match_ccmode (insn, CCGOCmode)"
590 "cmp{l}\t{%1, %0|%0, %1}"
591 [(set_attr "type" "icmp")
592 (set_attr "mode" "SI")])
594 (define_expand "cmpsi_1"
595 [(set (reg:CC FLAGS_REG)
596 (compare:CC (match_operand:SI 0 "nonimmediate_operand" "rm,r")
597 (match_operand:SI 1 "general_operand" "ri,mr")))]
601 (define_insn "*cmpsi_1_insn"
602 [(set (reg FLAGS_REG)
603 (compare (match_operand:SI 0 "nonimmediate_operand" "rm,r")
604 (match_operand:SI 1 "general_operand" "ri,mr")))]
605 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
606 && ix86_match_ccmode (insn, CCmode)"
607 "cmp{l}\t{%1, %0|%0, %1}"
608 [(set_attr "type" "icmp")
609 (set_attr "mode" "SI")])
611 (define_insn "*cmphi_ccno_1"
612 [(set (reg FLAGS_REG)
613 (compare (match_operand:HI 0 "nonimmediate_operand" "r,?mr")
614 (match_operand:HI 1 "const0_operand" "n,n")))]
615 "ix86_match_ccmode (insn, CCNOmode)"
617 test{w}\t{%0, %0|%0, %0}
618 cmp{w}\t{%1, %0|%0, %1}"
619 [(set_attr "type" "test,icmp")
620 (set_attr "length_immediate" "0,1")
621 (set_attr "mode" "HI")])
623 (define_insn "*cmphi_minus_1"
624 [(set (reg FLAGS_REG)
625 (compare (minus:HI (match_operand:HI 0 "nonimmediate_operand" "rm,r")
626 (match_operand:HI 1 "general_operand" "ri,mr"))
628 "ix86_match_ccmode (insn, CCGOCmode)"
629 "cmp{w}\t{%1, %0|%0, %1}"
630 [(set_attr "type" "icmp")
631 (set_attr "mode" "HI")])
633 (define_insn "*cmphi_1"
634 [(set (reg FLAGS_REG)
635 (compare (match_operand:HI 0 "nonimmediate_operand" "rm,r")
636 (match_operand:HI 1 "general_operand" "ri,mr")))]
637 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
638 && ix86_match_ccmode (insn, CCmode)"
639 "cmp{w}\t{%1, %0|%0, %1}"
640 [(set_attr "type" "icmp")
641 (set_attr "mode" "HI")])
643 (define_insn "*cmpqi_ccno_1"
644 [(set (reg FLAGS_REG)
645 (compare (match_operand:QI 0 "nonimmediate_operand" "q,?mq")
646 (match_operand:QI 1 "const0_operand" "n,n")))]
647 "ix86_match_ccmode (insn, CCNOmode)"
649 test{b}\t{%0, %0|%0, %0}
650 cmp{b}\t{$0, %0|%0, 0}"
651 [(set_attr "type" "test,icmp")
652 (set_attr "length_immediate" "0,1")
653 (set_attr "mode" "QI")])
655 (define_insn "*cmpqi_1"
656 [(set (reg FLAGS_REG)
657 (compare (match_operand:QI 0 "nonimmediate_operand" "qm,q")
658 (match_operand:QI 1 "general_operand" "qi,mq")))]
659 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
660 && ix86_match_ccmode (insn, CCmode)"
661 "cmp{b}\t{%1, %0|%0, %1}"
662 [(set_attr "type" "icmp")
663 (set_attr "mode" "QI")])
665 (define_insn "*cmpqi_minus_1"
666 [(set (reg FLAGS_REG)
667 (compare (minus:QI (match_operand:QI 0 "nonimmediate_operand" "qm,q")
668 (match_operand:QI 1 "general_operand" "qi,mq"))
670 "ix86_match_ccmode (insn, CCGOCmode)"
671 "cmp{b}\t{%1, %0|%0, %1}"
672 [(set_attr "type" "icmp")
673 (set_attr "mode" "QI")])
675 (define_insn "*cmpqi_ext_1"
676 [(set (reg FLAGS_REG)
678 (match_operand:QI 0 "general_operand" "Qm")
681 (match_operand 1 "ext_register_operand" "Q")
684 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
685 "cmp{b}\t{%h1, %0|%0, %h1}"
686 [(set_attr "type" "icmp")
687 (set_attr "mode" "QI")])
689 (define_insn "*cmpqi_ext_1_rex64"
690 [(set (reg FLAGS_REG)
692 (match_operand:QI 0 "register_operand" "Q")
695 (match_operand 1 "ext_register_operand" "Q")
698 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
699 "cmp{b}\t{%h1, %0|%0, %h1}"
700 [(set_attr "type" "icmp")
701 (set_attr "mode" "QI")])
703 (define_insn "*cmpqi_ext_2"
704 [(set (reg FLAGS_REG)
708 (match_operand 0 "ext_register_operand" "Q")
711 (match_operand:QI 1 "const0_operand" "n")))]
712 "ix86_match_ccmode (insn, CCNOmode)"
714 [(set_attr "type" "test")
715 (set_attr "length_immediate" "0")
716 (set_attr "mode" "QI")])
718 (define_expand "cmpqi_ext_3"
719 [(set (reg:CC FLAGS_REG)
723 (match_operand 0 "ext_register_operand" "")
726 (match_operand:QI 1 "general_operand" "")))]
730 (define_insn "cmpqi_ext_3_insn"
731 [(set (reg FLAGS_REG)
735 (match_operand 0 "ext_register_operand" "Q")
738 (match_operand:QI 1 "general_operand" "Qmn")))]
739 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
740 "cmp{b}\t{%1, %h0|%h0, %1}"
741 [(set_attr "type" "icmp")
742 (set_attr "mode" "QI")])
744 (define_insn "cmpqi_ext_3_insn_rex64"
745 [(set (reg FLAGS_REG)
749 (match_operand 0 "ext_register_operand" "Q")
752 (match_operand:QI 1 "nonmemory_operand" "Qn")))]
753 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
754 "cmp{b}\t{%1, %h0|%h0, %1}"
755 [(set_attr "type" "icmp")
756 (set_attr "mode" "QI")])
758 (define_insn "*cmpqi_ext_4"
759 [(set (reg FLAGS_REG)
763 (match_operand 0 "ext_register_operand" "Q")
768 (match_operand 1 "ext_register_operand" "Q")
771 "ix86_match_ccmode (insn, CCmode)"
772 "cmp{b}\t{%h1, %h0|%h0, %h1}"
773 [(set_attr "type" "icmp")
774 (set_attr "mode" "QI")])
776 ;; These implement float point compares.
777 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
778 ;; which would allow mix and match FP modes on the compares. Which is what
779 ;; the old patterns did, but with many more of them.
781 (define_expand "cmpxf"
782 [(set (reg:CC FLAGS_REG)
783 (compare:CC (match_operand:XF 0 "cmp_fp_expander_operand" "")
784 (match_operand:XF 1 "cmp_fp_expander_operand" "")))]
787 ix86_compare_op0 = operands[0];
788 ix86_compare_op1 = operands[1];
792 (define_expand "cmpdf"
793 [(set (reg:CC FLAGS_REG)
794 (compare:CC (match_operand:DF 0 "cmp_fp_expander_operand" "")
795 (match_operand:DF 1 "cmp_fp_expander_operand" "")))]
796 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
798 ix86_compare_op0 = operands[0];
799 ix86_compare_op1 = operands[1];
803 (define_expand "cmpsf"
804 [(set (reg:CC FLAGS_REG)
805 (compare:CC (match_operand:SF 0 "cmp_fp_expander_operand" "")
806 (match_operand:SF 1 "cmp_fp_expander_operand" "")))]
807 "TARGET_80387 || TARGET_SSE_MATH"
809 ix86_compare_op0 = operands[0];
810 ix86_compare_op1 = operands[1];
814 ;; FP compares, step 1:
815 ;; Set the FP condition codes.
817 ;; CCFPmode compare with exceptions
818 ;; CCFPUmode compare with no exceptions
820 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
821 ;; used to manage the reg stack popping would not be preserved.
823 (define_insn "*cmpfp_0"
824 [(set (match_operand:HI 0 "register_operand" "=a")
827 (match_operand 1 "register_operand" "f")
828 (match_operand 2 "const0_operand" "X"))]
831 && FLOAT_MODE_P (GET_MODE (operands[1]))
832 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
833 "* return output_fp_compare (insn, operands, 0, 0);"
834 [(set_attr "type" "multi")
835 (set_attr "unit" "i387")
837 (cond [(match_operand:SF 1 "" "")
839 (match_operand:DF 1 "" "")
842 (const_string "XF")))])
844 (define_insn "*cmpfp_sf"
845 [(set (match_operand:HI 0 "register_operand" "=a")
848 (match_operand:SF 1 "register_operand" "f")
849 (match_operand:SF 2 "nonimmediate_operand" "fm"))]
852 "* return output_fp_compare (insn, operands, 0, 0);"
853 [(set_attr "type" "multi")
854 (set_attr "unit" "i387")
855 (set_attr "mode" "SF")])
857 (define_insn "*cmpfp_df"
858 [(set (match_operand:HI 0 "register_operand" "=a")
861 (match_operand:DF 1 "register_operand" "f")
862 (match_operand:DF 2 "nonimmediate_operand" "fm"))]
865 "* return output_fp_compare (insn, operands, 0, 0);"
866 [(set_attr "type" "multi")
867 (set_attr "unit" "i387")
868 (set_attr "mode" "DF")])
870 (define_insn "*cmpfp_xf"
871 [(set (match_operand:HI 0 "register_operand" "=a")
874 (match_operand:XF 1 "register_operand" "f")
875 (match_operand:XF 2 "register_operand" "f"))]
878 "* return output_fp_compare (insn, operands, 0, 0);"
879 [(set_attr "type" "multi")
880 (set_attr "unit" "i387")
881 (set_attr "mode" "XF")])
883 (define_insn "*cmpfp_u"
884 [(set (match_operand:HI 0 "register_operand" "=a")
887 (match_operand 1 "register_operand" "f")
888 (match_operand 2 "register_operand" "f"))]
891 && FLOAT_MODE_P (GET_MODE (operands[1]))
892 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
893 "* return output_fp_compare (insn, operands, 0, 1);"
894 [(set_attr "type" "multi")
895 (set_attr "unit" "i387")
897 (cond [(match_operand:SF 1 "" "")
899 (match_operand:DF 1 "" "")
902 (const_string "XF")))])
904 (define_insn "*cmpfp_<mode>"
905 [(set (match_operand:HI 0 "register_operand" "=a")
908 (match_operand 1 "register_operand" "f")
909 (match_operator 3 "float_operator"
910 [(match_operand:X87MODEI12 2 "memory_operand" "m")]))]
912 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
913 && FLOAT_MODE_P (GET_MODE (operands[1]))
914 && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
915 "* return output_fp_compare (insn, operands, 0, 0);"
916 [(set_attr "type" "multi")
917 (set_attr "unit" "i387")
918 (set_attr "fp_int_src" "true")
919 (set_attr "mode" "<MODE>")])
921 ;; FP compares, step 2
922 ;; Move the fpsw to ax.
924 (define_insn "x86_fnstsw_1"
925 [(set (match_operand:HI 0 "register_operand" "=a")
926 (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))]
929 [(set_attr "length" "2")
930 (set_attr "mode" "SI")
931 (set_attr "unit" "i387")])
933 ;; FP compares, step 3
934 ;; Get ax into flags, general case.
936 (define_insn "x86_sahf_1"
937 [(set (reg:CC FLAGS_REG)
938 (unspec:CC [(match_operand:HI 0 "register_operand" "a")] UNSPEC_SAHF))]
941 [(set_attr "length" "1")
942 (set_attr "athlon_decode" "vector")
943 (set_attr "mode" "SI")])
945 ;; Pentium Pro can do steps 1 through 3 in one go.
947 (define_insn "*cmpfp_i_mixed"
948 [(set (reg:CCFP FLAGS_REG)
949 (compare:CCFP (match_operand 0 "register_operand" "f#x,x#f")
950 (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
952 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
953 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
954 "* return output_fp_compare (insn, operands, 1, 0);"
955 [(set_attr "type" "fcmp,ssecomi")
957 (if_then_else (match_operand:SF 1 "" "")
959 (const_string "DF")))
960 (set_attr "athlon_decode" "vector")])
962 (define_insn "*cmpfp_i_sse"
963 [(set (reg:CCFP FLAGS_REG)
964 (compare:CCFP (match_operand 0 "register_operand" "x")
965 (match_operand 1 "nonimmediate_operand" "xm")))]
967 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
968 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
969 "* return output_fp_compare (insn, operands, 1, 0);"
970 [(set_attr "type" "ssecomi")
972 (if_then_else (match_operand:SF 1 "" "")
974 (const_string "DF")))
975 (set_attr "athlon_decode" "vector")])
977 (define_insn "*cmpfp_i_i387"
978 [(set (reg:CCFP FLAGS_REG)
979 (compare:CCFP (match_operand 0 "register_operand" "f")
980 (match_operand 1 "register_operand" "f")))]
981 "TARGET_80387 && TARGET_CMOVE
982 && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0])))
983 && FLOAT_MODE_P (GET_MODE (operands[0]))
984 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
985 "* return output_fp_compare (insn, operands, 1, 0);"
986 [(set_attr "type" "fcmp")
988 (cond [(match_operand:SF 1 "" "")
990 (match_operand:DF 1 "" "")
993 (const_string "XF")))
994 (set_attr "athlon_decode" "vector")])
996 (define_insn "*cmpfp_iu_mixed"
997 [(set (reg:CCFPU FLAGS_REG)
998 (compare:CCFPU (match_operand 0 "register_operand" "f#x,x#f")
999 (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
1000 "TARGET_MIX_SSE_I387
1001 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1002 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1003 "* return output_fp_compare (insn, operands, 1, 1);"
1004 [(set_attr "type" "fcmp,ssecomi")
1006 (if_then_else (match_operand:SF 1 "" "")
1008 (const_string "DF")))
1009 (set_attr "athlon_decode" "vector")])
1011 (define_insn "*cmpfp_iu_sse"
1012 [(set (reg:CCFPU FLAGS_REG)
1013 (compare:CCFPU (match_operand 0 "register_operand" "x")
1014 (match_operand 1 "nonimmediate_operand" "xm")))]
1016 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1017 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1018 "* return output_fp_compare (insn, operands, 1, 1);"
1019 [(set_attr "type" "ssecomi")
1021 (if_then_else (match_operand:SF 1 "" "")
1023 (const_string "DF")))
1024 (set_attr "athlon_decode" "vector")])
1026 (define_insn "*cmpfp_iu_387"
1027 [(set (reg:CCFPU FLAGS_REG)
1028 (compare:CCFPU (match_operand 0 "register_operand" "f")
1029 (match_operand 1 "register_operand" "f")))]
1030 "TARGET_80387 && TARGET_CMOVE
1031 && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0])))
1032 && FLOAT_MODE_P (GET_MODE (operands[0]))
1033 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1034 "* return output_fp_compare (insn, operands, 1, 1);"
1035 [(set_attr "type" "fcmp")
1037 (cond [(match_operand:SF 1 "" "")
1039 (match_operand:DF 1 "" "")
1042 (const_string "XF")))
1043 (set_attr "athlon_decode" "vector")])
1045 ;; Move instructions.
1047 ;; General case of fullword move.
1049 (define_expand "movsi"
1050 [(set (match_operand:SI 0 "nonimmediate_operand" "")
1051 (match_operand:SI 1 "general_operand" ""))]
1053 "ix86_expand_move (SImode, operands); DONE;")
1055 ;; Push/pop instructions. They are separate since autoinc/dec is not a
1058 ;; %%% We don't use a post-inc memory reference because x86 is not a
1059 ;; general AUTO_INC_DEC host, which impacts how it is treated in flow.
1060 ;; Changing this impacts compiler performance on other non-AUTO_INC_DEC
1061 ;; targets without our curiosities, and it is just as easy to represent
1062 ;; this differently.
1064 (define_insn "*pushsi2"
1065 [(set (match_operand:SI 0 "push_operand" "=<")
1066 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1069 [(set_attr "type" "push")
1070 (set_attr "mode" "SI")])
1072 ;; For 64BIT abi we always round up to 8 bytes.
1073 (define_insn "*pushsi2_rex64"
1074 [(set (match_operand:SI 0 "push_operand" "=X")
1075 (match_operand:SI 1 "nonmemory_no_elim_operand" "ri"))]
1078 [(set_attr "type" "push")
1079 (set_attr "mode" "SI")])
1081 (define_insn "*pushsi2_prologue"
1082 [(set (match_operand:SI 0 "push_operand" "=<")
1083 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))
1084 (clobber (mem:BLK (scratch)))]
1087 [(set_attr "type" "push")
1088 (set_attr "mode" "SI")])
1090 (define_insn "*popsi1_epilogue"
1091 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1092 (mem:SI (reg:SI SP_REG)))
1093 (set (reg:SI SP_REG)
1094 (plus:SI (reg:SI SP_REG) (const_int 4)))
1095 (clobber (mem:BLK (scratch)))]
1098 [(set_attr "type" "pop")
1099 (set_attr "mode" "SI")])
1101 (define_insn "popsi1"
1102 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1103 (mem:SI (reg:SI SP_REG)))
1104 (set (reg:SI SP_REG)
1105 (plus:SI (reg:SI SP_REG) (const_int 4)))]
1108 [(set_attr "type" "pop")
1109 (set_attr "mode" "SI")])
1111 (define_insn "*movsi_xor"
1112 [(set (match_operand:SI 0 "register_operand" "=r")
1113 (match_operand:SI 1 "const0_operand" "i"))
1114 (clobber (reg:CC FLAGS_REG))]
1115 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1116 "xor{l}\t{%0, %0|%0, %0}"
1117 [(set_attr "type" "alu1")
1118 (set_attr "mode" "SI")
1119 (set_attr "length_immediate" "0")])
1121 (define_insn "*movsi_or"
1122 [(set (match_operand:SI 0 "register_operand" "=r")
1123 (match_operand:SI 1 "immediate_operand" "i"))
1124 (clobber (reg:CC FLAGS_REG))]
1126 && operands[1] == constm1_rtx
1127 && (TARGET_PENTIUM || optimize_size)"
1129 operands[1] = constm1_rtx;
1130 return "or{l}\t{%1, %0|%0, %1}";
1132 [(set_attr "type" "alu1")
1133 (set_attr "mode" "SI")
1134 (set_attr "length_immediate" "1")])
1136 (define_insn "*movsi_1"
1137 [(set (match_operand:SI 0 "nonimmediate_operand"
1138 "=r ,m ,*y,*y,?rm,?*y,*x,*x,?r,m ,?*Y,*x")
1139 (match_operand:SI 1 "general_operand"
1140 "rinm,rin,C ,*y,*y ,rm ,C ,*x,*Y,*x,r ,m "))]
1141 "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1143 switch (get_attr_type (insn))
1146 if (get_attr_mode (insn) == MODE_TI)
1147 return "pxor\t%0, %0";
1148 return "xorps\t%0, %0";
1151 switch (get_attr_mode (insn))
1154 return "movdqa\t{%1, %0|%0, %1}";
1156 return "movaps\t{%1, %0|%0, %1}";
1158 return "movd\t{%1, %0|%0, %1}";
1160 return "movss\t{%1, %0|%0, %1}";
1166 return "pxor\t%0, %0";
1169 if (get_attr_mode (insn) == MODE_DI)
1170 return "movq\t{%1, %0|%0, %1}";
1171 return "movd\t{%1, %0|%0, %1}";
1174 return "lea{l}\t{%1, %0|%0, %1}";
1177 gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
1178 return "mov{l}\t{%1, %0|%0, %1}";
1182 (cond [(eq_attr "alternative" "2")
1183 (const_string "mmx")
1184 (eq_attr "alternative" "3,4,5")
1185 (const_string "mmxmov")
1186 (eq_attr "alternative" "6")
1187 (const_string "sselog1")
1188 (eq_attr "alternative" "7,8,9,10,11")
1189 (const_string "ssemov")
1190 (and (ne (symbol_ref "flag_pic") (const_int 0))
1191 (match_operand:SI 1 "symbolic_operand" ""))
1192 (const_string "lea")
1194 (const_string "imov")))
1196 (cond [(eq_attr "alternative" "2,3")
1198 (eq_attr "alternative" "6,7")
1200 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
1201 (const_string "V4SF")
1202 (const_string "TI"))
1203 (and (eq_attr "alternative" "8,9,10,11")
1204 (eq (symbol_ref "TARGET_SSE2") (const_int 0)))
1207 (const_string "SI")))])
1209 ;; Stores and loads of ax to arbitrary constant address.
1210 ;; We fake an second form of instruction to force reload to load address
1211 ;; into register when rax is not available
1212 (define_insn "*movabssi_1_rex64"
1213 [(set (mem:SI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1214 (match_operand:SI 1 "nonmemory_operand" "a,er"))]
1215 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1217 movabs{l}\t{%1, %P0|%P0, %1}
1218 mov{l}\t{%1, %a0|%a0, %1}"
1219 [(set_attr "type" "imov")
1220 (set_attr "modrm" "0,*")
1221 (set_attr "length_address" "8,0")
1222 (set_attr "length_immediate" "0,*")
1223 (set_attr "memory" "store")
1224 (set_attr "mode" "SI")])
1226 (define_insn "*movabssi_2_rex64"
1227 [(set (match_operand:SI 0 "register_operand" "=a,r")
1228 (mem:SI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1229 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1231 movabs{l}\t{%P1, %0|%0, %P1}
1232 mov{l}\t{%a1, %0|%0, %a1}"
1233 [(set_attr "type" "imov")
1234 (set_attr "modrm" "0,*")
1235 (set_attr "length_address" "8,0")
1236 (set_attr "length_immediate" "0")
1237 (set_attr "memory" "load")
1238 (set_attr "mode" "SI")])
1240 (define_insn "*swapsi"
1241 [(set (match_operand:SI 0 "register_operand" "+r")
1242 (match_operand:SI 1 "register_operand" "+r"))
1247 [(set_attr "type" "imov")
1248 (set_attr "mode" "SI")
1249 (set_attr "pent_pair" "np")
1250 (set_attr "athlon_decode" "vector")])
1252 (define_expand "movhi"
1253 [(set (match_operand:HI 0 "nonimmediate_operand" "")
1254 (match_operand:HI 1 "general_operand" ""))]
1256 "ix86_expand_move (HImode, operands); DONE;")
1258 (define_insn "*pushhi2"
1259 [(set (match_operand:HI 0 "push_operand" "=<,<")
1260 (match_operand:HI 1 "general_no_elim_operand" "n,r*m"))]
1263 push{w}\t{|WORD PTR }%1
1265 [(set_attr "type" "push")
1266 (set_attr "mode" "HI")])
1268 ;; For 64BIT abi we always round up to 8 bytes.
1269 (define_insn "*pushhi2_rex64"
1270 [(set (match_operand:HI 0 "push_operand" "=X")
1271 (match_operand:HI 1 "nonmemory_no_elim_operand" "ri"))]
1274 [(set_attr "type" "push")
1275 (set_attr "mode" "QI")])
1277 (define_insn "*movhi_1"
1278 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
1279 (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
1280 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1282 switch (get_attr_type (insn))
1285 /* movzwl is faster than movw on p2 due to partial word stalls,
1286 though not as fast as an aligned movl. */
1287 return "movz{wl|x}\t{%1, %k0|%k0, %1}";
1289 if (get_attr_mode (insn) == MODE_SI)
1290 return "mov{l}\t{%k1, %k0|%k0, %k1}";
1292 return "mov{w}\t{%1, %0|%0, %1}";
1296 (cond [(ne (symbol_ref "optimize_size") (const_int 0))
1297 (const_string "imov")
1298 (and (eq_attr "alternative" "0")
1299 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1301 (eq (symbol_ref "TARGET_HIMODE_MATH")
1303 (const_string "imov")
1304 (and (eq_attr "alternative" "1,2")
1305 (match_operand:HI 1 "aligned_operand" ""))
1306 (const_string "imov")
1307 (and (ne (symbol_ref "TARGET_MOVX")
1309 (eq_attr "alternative" "0,2"))
1310 (const_string "imovx")
1312 (const_string "imov")))
1314 (cond [(eq_attr "type" "imovx")
1316 (and (eq_attr "alternative" "1,2")
1317 (match_operand:HI 1 "aligned_operand" ""))
1319 (and (eq_attr "alternative" "0")
1320 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1322 (eq (symbol_ref "TARGET_HIMODE_MATH")
1326 (const_string "HI")))])
1328 ;; Stores and loads of ax to arbitrary constant address.
1329 ;; We fake an second form of instruction to force reload to load address
1330 ;; into register when rax is not available
1331 (define_insn "*movabshi_1_rex64"
1332 [(set (mem:HI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1333 (match_operand:HI 1 "nonmemory_operand" "a,er"))]
1334 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1336 movabs{w}\t{%1, %P0|%P0, %1}
1337 mov{w}\t{%1, %a0|%a0, %1}"
1338 [(set_attr "type" "imov")
1339 (set_attr "modrm" "0,*")
1340 (set_attr "length_address" "8,0")
1341 (set_attr "length_immediate" "0,*")
1342 (set_attr "memory" "store")
1343 (set_attr "mode" "HI")])
1345 (define_insn "*movabshi_2_rex64"
1346 [(set (match_operand:HI 0 "register_operand" "=a,r")
1347 (mem:HI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1348 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1350 movabs{w}\t{%P1, %0|%0, %P1}
1351 mov{w}\t{%a1, %0|%0, %a1}"
1352 [(set_attr "type" "imov")
1353 (set_attr "modrm" "0,*")
1354 (set_attr "length_address" "8,0")
1355 (set_attr "length_immediate" "0")
1356 (set_attr "memory" "load")
1357 (set_attr "mode" "HI")])
1359 (define_insn "*swaphi_1"
1360 [(set (match_operand:HI 0 "register_operand" "+r")
1361 (match_operand:HI 1 "register_operand" "+r"))
1364 "!TARGET_PARTIAL_REG_STALL || optimize_size"
1366 [(set_attr "type" "imov")
1367 (set_attr "mode" "SI")
1368 (set_attr "pent_pair" "np")
1369 (set_attr "athlon_decode" "vector")])
1371 (define_insn "*swaphi_2"
1372 [(set (match_operand:HI 0 "register_operand" "+r")
1373 (match_operand:HI 1 "register_operand" "+r"))
1376 "TARGET_PARTIAL_REG_STALL"
1378 [(set_attr "type" "imov")
1379 (set_attr "mode" "HI")
1380 (set_attr "pent_pair" "np")
1381 (set_attr "athlon_decode" "vector")])
1383 (define_expand "movstricthi"
1384 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" ""))
1385 (match_operand:HI 1 "general_operand" ""))]
1386 "! TARGET_PARTIAL_REG_STALL || optimize_size"
1388 /* Don't generate memory->memory moves, go through a register */
1389 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1390 operands[1] = force_reg (HImode, operands[1]);
1393 (define_insn "*movstricthi_1"
1394 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+rm,r"))
1395 (match_operand:HI 1 "general_operand" "rn,m"))]
1396 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1397 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1398 "mov{w}\t{%1, %0|%0, %1}"
1399 [(set_attr "type" "imov")
1400 (set_attr "mode" "HI")])
1402 (define_insn "*movstricthi_xor"
1403 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
1404 (match_operand:HI 1 "const0_operand" "i"))
1405 (clobber (reg:CC FLAGS_REG))]
1407 && ((!TARGET_USE_MOV0 && !TARGET_PARTIAL_REG_STALL) || optimize_size)"
1408 "xor{w}\t{%0, %0|%0, %0}"
1409 [(set_attr "type" "alu1")
1410 (set_attr "mode" "HI")
1411 (set_attr "length_immediate" "0")])
1413 (define_expand "movqi"
1414 [(set (match_operand:QI 0 "nonimmediate_operand" "")
1415 (match_operand:QI 1 "general_operand" ""))]
1417 "ix86_expand_move (QImode, operands); DONE;")
1419 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1420 ;; "push a byte". But actually we use pushw, which has the effect
1421 ;; of rounding the amount pushed up to a halfword.
1423 (define_insn "*pushqi2"
1424 [(set (match_operand:QI 0 "push_operand" "=X,X")
1425 (match_operand:QI 1 "nonmemory_no_elim_operand" "n,r"))]
1428 push{w}\t{|word ptr }%1
1430 [(set_attr "type" "push")
1431 (set_attr "mode" "HI")])
1433 ;; For 64BIT abi we always round up to 8 bytes.
1434 (define_insn "*pushqi2_rex64"
1435 [(set (match_operand:QI 0 "push_operand" "=X")
1436 (match_operand:QI 1 "nonmemory_no_elim_operand" "qi"))]
1439 [(set_attr "type" "push")
1440 (set_attr "mode" "QI")])
1442 ;; Situation is quite tricky about when to choose full sized (SImode) move
1443 ;; over QImode moves. For Q_REG -> Q_REG move we use full size only for
1444 ;; partial register dependency machines (such as AMD Athlon), where QImode
1445 ;; moves issue extra dependency and for partial register stalls machines
1446 ;; that don't use QImode patterns (and QImode move cause stall on the next
1449 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
1450 ;; register stall machines with, where we use QImode instructions, since
1451 ;; partial register stall can be caused there. Then we use movzx.
1452 (define_insn "*movqi_1"
1453 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
1454 (match_operand:QI 1 "general_operand" " q,qn,qm,q,rn,m ,qn"))]
1455 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1457 switch (get_attr_type (insn))
1460 gcc_assert (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM);
1461 return "movz{bl|x}\t{%1, %k0|%k0, %1}";
1463 if (get_attr_mode (insn) == MODE_SI)
1464 return "mov{l}\t{%k1, %k0|%k0, %k1}";
1466 return "mov{b}\t{%1, %0|%0, %1}";
1470 (cond [(eq_attr "alternative" "5")
1471 (const_string "imovx")
1472 (ne (symbol_ref "optimize_size") (const_int 0))
1473 (const_string "imov")
1474 (and (eq_attr "alternative" "3")
1475 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1477 (eq (symbol_ref "TARGET_QIMODE_MATH")
1479 (const_string "imov")
1480 (eq_attr "alternative" "3")
1481 (const_string "imovx")
1482 (and (ne (symbol_ref "TARGET_MOVX")
1484 (eq_attr "alternative" "2"))
1485 (const_string "imovx")
1487 (const_string "imov")))
1489 (cond [(eq_attr "alternative" "3,4,5")
1491 (eq_attr "alternative" "6")
1493 (eq_attr "type" "imovx")
1495 (and (eq_attr "type" "imov")
1496 (and (eq_attr "alternative" "0,1")
1497 (ne (symbol_ref "TARGET_PARTIAL_REG_DEPENDENCY")
1500 ;; Avoid partial register stalls when not using QImode arithmetic
1501 (and (eq_attr "type" "imov")
1502 (and (eq_attr "alternative" "0,1")
1503 (and (ne (symbol_ref "TARGET_PARTIAL_REG_STALL")
1505 (eq (symbol_ref "TARGET_QIMODE_MATH")
1509 (const_string "QI")))])
1511 (define_expand "reload_outqi"
1512 [(parallel [(match_operand:QI 0 "" "=m")
1513 (match_operand:QI 1 "register_operand" "r")
1514 (match_operand:QI 2 "register_operand" "=&q")])]
1518 op0 = operands[0]; op1 = operands[1]; op2 = operands[2];
1520 gcc_assert (!reg_overlap_mentioned_p (op2, op0));
1521 if (! q_regs_operand (op1, QImode))
1523 emit_insn (gen_movqi (op2, op1));
1526 emit_insn (gen_movqi (op0, op1));
1530 (define_insn "*swapqi_1"
1531 [(set (match_operand:QI 0 "register_operand" "+r")
1532 (match_operand:QI 1 "register_operand" "+r"))
1535 "!TARGET_PARTIAL_REG_STALL || optimize_size"
1537 [(set_attr "type" "imov")
1538 (set_attr "mode" "SI")
1539 (set_attr "pent_pair" "np")
1540 (set_attr "athlon_decode" "vector")])
1542 (define_insn "*swapqi_2"
1543 [(set (match_operand:QI 0 "register_operand" "+q")
1544 (match_operand:QI 1 "register_operand" "+q"))
1547 "TARGET_PARTIAL_REG_STALL"
1549 [(set_attr "type" "imov")
1550 (set_attr "mode" "QI")
1551 (set_attr "pent_pair" "np")
1552 (set_attr "athlon_decode" "vector")])
1554 (define_expand "movstrictqi"
1555 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
1556 (match_operand:QI 1 "general_operand" ""))]
1557 "! TARGET_PARTIAL_REG_STALL || optimize_size"
1559 /* Don't generate memory->memory moves, go through a register. */
1560 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1561 operands[1] = force_reg (QImode, operands[1]);
1564 (define_insn "*movstrictqi_1"
1565 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
1566 (match_operand:QI 1 "general_operand" "*qn,m"))]
1567 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1568 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1569 "mov{b}\t{%1, %0|%0, %1}"
1570 [(set_attr "type" "imov")
1571 (set_attr "mode" "QI")])
1573 (define_insn "*movstrictqi_xor"
1574 [(set (strict_low_part (match_operand:QI 0 "q_regs_operand" "+q"))
1575 (match_operand:QI 1 "const0_operand" "i"))
1576 (clobber (reg:CC FLAGS_REG))]
1577 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1578 "xor{b}\t{%0, %0|%0, %0}"
1579 [(set_attr "type" "alu1")
1580 (set_attr "mode" "QI")
1581 (set_attr "length_immediate" "0")])
1583 (define_insn "*movsi_extv_1"
1584 [(set (match_operand:SI 0 "register_operand" "=R")
1585 (sign_extract:SI (match_operand 1 "ext_register_operand" "Q")
1589 "movs{bl|x}\t{%h1, %0|%0, %h1}"
1590 [(set_attr "type" "imovx")
1591 (set_attr "mode" "SI")])
1593 (define_insn "*movhi_extv_1"
1594 [(set (match_operand:HI 0 "register_operand" "=R")
1595 (sign_extract:HI (match_operand 1 "ext_register_operand" "Q")
1599 "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
1600 [(set_attr "type" "imovx")
1601 (set_attr "mode" "SI")])
1603 (define_insn "*movqi_extv_1"
1604 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
1605 (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1610 switch (get_attr_type (insn))
1613 return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1615 return "mov{b}\t{%h1, %0|%0, %h1}";
1619 (if_then_else (and (match_operand:QI 0 "register_operand" "")
1620 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1621 (ne (symbol_ref "TARGET_MOVX")
1623 (const_string "imovx")
1624 (const_string "imov")))
1626 (if_then_else (eq_attr "type" "imovx")
1628 (const_string "QI")))])
1630 (define_insn "*movqi_extv_1_rex64"
1631 [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1632 (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1637 switch (get_attr_type (insn))
1640 return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1642 return "mov{b}\t{%h1, %0|%0, %h1}";
1646 (if_then_else (and (match_operand:QI 0 "register_operand" "")
1647 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1648 (ne (symbol_ref "TARGET_MOVX")
1650 (const_string "imovx")
1651 (const_string "imov")))
1653 (if_then_else (eq_attr "type" "imovx")
1655 (const_string "QI")))])
1657 ;; Stores and loads of ax to arbitrary constant address.
1658 ;; We fake an second form of instruction to force reload to load address
1659 ;; into register when rax is not available
1660 (define_insn "*movabsqi_1_rex64"
1661 [(set (mem:QI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1662 (match_operand:QI 1 "nonmemory_operand" "a,er"))]
1663 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1665 movabs{b}\t{%1, %P0|%P0, %1}
1666 mov{b}\t{%1, %a0|%a0, %1}"
1667 [(set_attr "type" "imov")
1668 (set_attr "modrm" "0,*")
1669 (set_attr "length_address" "8,0")
1670 (set_attr "length_immediate" "0,*")
1671 (set_attr "memory" "store")
1672 (set_attr "mode" "QI")])
1674 (define_insn "*movabsqi_2_rex64"
1675 [(set (match_operand:QI 0 "register_operand" "=a,r")
1676 (mem:QI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1677 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1679 movabs{b}\t{%P1, %0|%0, %P1}
1680 mov{b}\t{%a1, %0|%0, %a1}"
1681 [(set_attr "type" "imov")
1682 (set_attr "modrm" "0,*")
1683 (set_attr "length_address" "8,0")
1684 (set_attr "length_immediate" "0")
1685 (set_attr "memory" "load")
1686 (set_attr "mode" "QI")])
1688 (define_insn "*movsi_extzv_1"
1689 [(set (match_operand:SI 0 "register_operand" "=R")
1690 (zero_extract:SI (match_operand 1 "ext_register_operand" "Q")
1694 "movz{bl|x}\t{%h1, %0|%0, %h1}"
1695 [(set_attr "type" "imovx")
1696 (set_attr "mode" "SI")])
1698 (define_insn "*movqi_extzv_2"
1699 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
1700 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1705 switch (get_attr_type (insn))
1708 return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1710 return "mov{b}\t{%h1, %0|%0, %h1}";
1714 (if_then_else (and (match_operand:QI 0 "register_operand" "")
1715 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1716 (ne (symbol_ref "TARGET_MOVX")
1718 (const_string "imovx")
1719 (const_string "imov")))
1721 (if_then_else (eq_attr "type" "imovx")
1723 (const_string "QI")))])
1725 (define_insn "*movqi_extzv_2_rex64"
1726 [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1727 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1732 switch (get_attr_type (insn))
1735 return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1737 return "mov{b}\t{%h1, %0|%0, %h1}";
1741 (if_then_else (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1742 (ne (symbol_ref "TARGET_MOVX")
1744 (const_string "imovx")
1745 (const_string "imov")))
1747 (if_then_else (eq_attr "type" "imovx")
1749 (const_string "QI")))])
1751 (define_insn "movsi_insv_1"
1752 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
1755 (match_operand:SI 1 "general_operand" "Qmn"))]
1757 "mov{b}\t{%b1, %h0|%h0, %b1}"
1758 [(set_attr "type" "imov")
1759 (set_attr "mode" "QI")])
1761 (define_insn "movdi_insv_1_rex64"
1762 [(set (zero_extract:DI (match_operand 0 "ext_register_operand" "+Q")
1765 (match_operand:DI 1 "nonmemory_operand" "Qn"))]
1767 "mov{b}\t{%b1, %h0|%h0, %b1}"
1768 [(set_attr "type" "imov")
1769 (set_attr "mode" "QI")])
1771 (define_insn "*movqi_insv_2"
1772 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
1775 (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
1778 "mov{b}\t{%h1, %h0|%h0, %h1}"
1779 [(set_attr "type" "imov")
1780 (set_attr "mode" "QI")])
1782 (define_expand "movdi"
1783 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1784 (match_operand:DI 1 "general_operand" ""))]
1786 "ix86_expand_move (DImode, operands); DONE;")
1788 (define_insn "*pushdi"
1789 [(set (match_operand:DI 0 "push_operand" "=<")
1790 (match_operand:DI 1 "general_no_elim_operand" "riF*m"))]
1794 (define_insn "*pushdi2_rex64"
1795 [(set (match_operand:DI 0 "push_operand" "=<,!<")
1796 (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
1801 [(set_attr "type" "push,multi")
1802 (set_attr "mode" "DI")])
1804 ;; Convert impossible pushes of immediate to existing instructions.
1805 ;; First try to get scratch register and go through it. In case this
1806 ;; fails, push sign extended lower part first and then overwrite
1807 ;; upper part by 32bit move.
1809 [(match_scratch:DI 2 "r")
1810 (set (match_operand:DI 0 "push_operand" "")
1811 (match_operand:DI 1 "immediate_operand" ""))]
1812 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1813 && !x86_64_immediate_operand (operands[1], DImode)"
1814 [(set (match_dup 2) (match_dup 1))
1815 (set (match_dup 0) (match_dup 2))]
1818 ;; We need to define this as both peepholer and splitter for case
1819 ;; peephole2 pass is not run.
1820 ;; "&& 1" is needed to keep it from matching the previous pattern.
1822 [(set (match_operand:DI 0 "push_operand" "")
1823 (match_operand:DI 1 "immediate_operand" ""))]
1824 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1825 && !x86_64_immediate_operand (operands[1], DImode) && 1"
1826 [(set (match_dup 0) (match_dup 1))
1827 (set (match_dup 2) (match_dup 3))]
1828 "split_di (operands + 1, 1, operands + 2, operands + 3);
1829 operands[1] = gen_lowpart (DImode, operands[2]);
1830 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1835 [(set (match_operand:DI 0 "push_operand" "")
1836 (match_operand:DI 1 "immediate_operand" ""))]
1837 "TARGET_64BIT && (flag_peephole2 ? flow2_completed : reload_completed)
1838 && !symbolic_operand (operands[1], DImode)
1839 && !x86_64_immediate_operand (operands[1], DImode)"
1840 [(set (match_dup 0) (match_dup 1))
1841 (set (match_dup 2) (match_dup 3))]
1842 "split_di (operands + 1, 1, operands + 2, operands + 3);
1843 operands[1] = gen_lowpart (DImode, operands[2]);
1844 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1848 (define_insn "*pushdi2_prologue_rex64"
1849 [(set (match_operand:DI 0 "push_operand" "=<")
1850 (match_operand:DI 1 "general_no_elim_operand" "re*m"))
1851 (clobber (mem:BLK (scratch)))]
1854 [(set_attr "type" "push")
1855 (set_attr "mode" "DI")])
1857 (define_insn "*popdi1_epilogue_rex64"
1858 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
1859 (mem:DI (reg:DI SP_REG)))
1860 (set (reg:DI SP_REG)
1861 (plus:DI (reg:DI SP_REG) (const_int 8)))
1862 (clobber (mem:BLK (scratch)))]
1865 [(set_attr "type" "pop")
1866 (set_attr "mode" "DI")])
1868 (define_insn "popdi1"
1869 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
1870 (mem:DI (reg:DI SP_REG)))
1871 (set (reg:DI SP_REG)
1872 (plus:DI (reg:DI SP_REG) (const_int 8)))]
1875 [(set_attr "type" "pop")
1876 (set_attr "mode" "DI")])
1878 (define_insn "*movdi_xor_rex64"
1879 [(set (match_operand:DI 0 "register_operand" "=r")
1880 (match_operand:DI 1 "const0_operand" "i"))
1881 (clobber (reg:CC FLAGS_REG))]
1882 "TARGET_64BIT && (!TARGET_USE_MOV0 || optimize_size)
1883 && reload_completed"
1884 "xor{l}\t{%k0, %k0|%k0, %k0}"
1885 [(set_attr "type" "alu1")
1886 (set_attr "mode" "SI")
1887 (set_attr "length_immediate" "0")])
1889 (define_insn "*movdi_or_rex64"
1890 [(set (match_operand:DI 0 "register_operand" "=r")
1891 (match_operand:DI 1 "const_int_operand" "i"))
1892 (clobber (reg:CC FLAGS_REG))]
1893 "TARGET_64BIT && (TARGET_PENTIUM || optimize_size)
1895 && operands[1] == constm1_rtx"
1897 operands[1] = constm1_rtx;
1898 return "or{q}\t{%1, %0|%0, %1}";
1900 [(set_attr "type" "alu1")
1901 (set_attr "mode" "DI")
1902 (set_attr "length_immediate" "1")])
1904 (define_insn "*movdi_2"
1905 [(set (match_operand:DI 0 "nonimmediate_operand"
1906 "=r ,o ,*y,m*y,*y,*Y,m ,*Y,*Y,*x,m ,*x,*x")
1907 (match_operand:DI 1 "general_operand"
1908 "riFo,riF,C ,*y ,m ,C ,*Y,*Y,m ,C ,*x,*x,m "))]
1909 "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1914 movq\t{%1, %0|%0, %1}
1915 movq\t{%1, %0|%0, %1}
1917 movq\t{%1, %0|%0, %1}
1918 movdqa\t{%1, %0|%0, %1}
1919 movq\t{%1, %0|%0, %1}
1921 movlps\t{%1, %0|%0, %1}
1922 movaps\t{%1, %0|%0, %1}
1923 movlps\t{%1, %0|%0, %1}"
1924 [(set_attr "type" "*,*,mmx,mmxmov,mmxmov,sselog1,ssemov,ssemov,ssemov,sselog1,ssemov,ssemov,ssemov")
1925 (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF")])
1928 [(set (match_operand:DI 0 "push_operand" "")
1929 (match_operand:DI 1 "general_operand" ""))]
1930 "!TARGET_64BIT && reload_completed
1931 && (! MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
1933 "ix86_split_long_move (operands); DONE;")
1935 ;; %%% This multiword shite has got to go.
1937 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1938 (match_operand:DI 1 "general_operand" ""))]
1939 "!TARGET_64BIT && reload_completed
1940 && (!MMX_REG_P (operands[0]) && !SSE_REG_P (operands[0]))
1941 && (!MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
1943 "ix86_split_long_move (operands); DONE;")
1945 (define_insn "*movdi_1_rex64"
1946 [(set (match_operand:DI 0 "nonimmediate_operand"
1947 "=r,r ,r,m ,!m,*y,*y,?rm,?*y,*x,*x,?rm,?*x,?*x,?*y")
1948 (match_operand:DI 1 "general_operand"
1949 "Z ,rem,i,re,n ,C ,*y,*y ,rm ,C ,*x,*x ,rm ,*y ,*x"))]
1950 "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1952 switch (get_attr_type (insn))
1955 if (which_alternative == 13)
1956 return "movq2dq\t{%1, %0|%0, %1}";
1958 return "movdq2q\t{%1, %0|%0, %1}";
1960 if (get_attr_mode (insn) == MODE_TI)
1961 return "movdqa\t{%1, %0|%0, %1}";
1964 /* Moves from and into integer register is done using movd opcode with
1966 if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
1967 return "movd\t{%1, %0|%0, %1}";
1968 return "movq\t{%1, %0|%0, %1}";
1971 return "pxor\t%0, %0";
1975 return "lea{q}\t{%a1, %0|%0, %a1}";
1977 gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
1978 if (get_attr_mode (insn) == MODE_SI)
1979 return "mov{l}\t{%k1, %k0|%k0, %k1}";
1980 else if (which_alternative == 2)
1981 return "movabs{q}\t{%1, %0|%0, %1}";
1983 return "mov{q}\t{%1, %0|%0, %1}";
1987 (cond [(eq_attr "alternative" "5")
1988 (const_string "mmx")
1989 (eq_attr "alternative" "6,7,8")
1990 (const_string "mmxmov")
1991 (eq_attr "alternative" "9")
1992 (const_string "sselog1")
1993 (eq_attr "alternative" "10,11,12")
1994 (const_string "ssemov")
1995 (eq_attr "alternative" "13,14")
1996 (const_string "ssecvt")
1997 (eq_attr "alternative" "4")
1998 (const_string "multi")
1999 (and (ne (symbol_ref "flag_pic") (const_int 0))
2000 (match_operand:DI 1 "symbolic_operand" ""))
2001 (const_string "lea")
2003 (const_string "imov")))
2004 (set_attr "modrm" "*,0,0,*,*,*,*,*,*,*,*,*,*,*,*")
2005 (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*,*,*,*,*,*,*")
2006 (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,TI,TI,DI,DI,DI,DI")])
2008 ;; Stores and loads of ax to arbitrary constant address.
2009 ;; We fake an second form of instruction to force reload to load address
2010 ;; into register when rax is not available
2011 (define_insn "*movabsdi_1_rex64"
2012 [(set (mem:DI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2013 (match_operand:DI 1 "nonmemory_operand" "a,er"))]
2014 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
2016 movabs{q}\t{%1, %P0|%P0, %1}
2017 mov{q}\t{%1, %a0|%a0, %1}"
2018 [(set_attr "type" "imov")
2019 (set_attr "modrm" "0,*")
2020 (set_attr "length_address" "8,0")
2021 (set_attr "length_immediate" "0,*")
2022 (set_attr "memory" "store")
2023 (set_attr "mode" "DI")])
2025 (define_insn "*movabsdi_2_rex64"
2026 [(set (match_operand:DI 0 "register_operand" "=a,r")
2027 (mem:DI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2028 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
2030 movabs{q}\t{%P1, %0|%0, %P1}
2031 mov{q}\t{%a1, %0|%0, %a1}"
2032 [(set_attr "type" "imov")
2033 (set_attr "modrm" "0,*")
2034 (set_attr "length_address" "8,0")
2035 (set_attr "length_immediate" "0")
2036 (set_attr "memory" "load")
2037 (set_attr "mode" "DI")])
2039 ;; Convert impossible stores of immediate to existing instructions.
2040 ;; First try to get scratch register and go through it. In case this
2041 ;; fails, move by 32bit parts.
2043 [(match_scratch:DI 2 "r")
2044 (set (match_operand:DI 0 "memory_operand" "")
2045 (match_operand:DI 1 "immediate_operand" ""))]
2046 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2047 && !x86_64_immediate_operand (operands[1], DImode)"
2048 [(set (match_dup 2) (match_dup 1))
2049 (set (match_dup 0) (match_dup 2))]
2052 ;; We need to define this as both peepholer and splitter for case
2053 ;; peephole2 pass is not run.
2054 ;; "&& 1" is needed to keep it from matching the previous pattern.
2056 [(set (match_operand:DI 0 "memory_operand" "")
2057 (match_operand:DI 1 "immediate_operand" ""))]
2058 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2059 && !x86_64_immediate_operand (operands[1], DImode) && 1"
2060 [(set (match_dup 2) (match_dup 3))
2061 (set (match_dup 4) (match_dup 5))]
2062 "split_di (operands, 2, operands + 2, operands + 4);")
2065 [(set (match_operand:DI 0 "memory_operand" "")
2066 (match_operand:DI 1 "immediate_operand" ""))]
2067 "TARGET_64BIT && (flag_peephole2 ? flow2_completed : reload_completed)
2068 && !symbolic_operand (operands[1], DImode)
2069 && !x86_64_immediate_operand (operands[1], DImode)"
2070 [(set (match_dup 2) (match_dup 3))
2071 (set (match_dup 4) (match_dup 5))]
2072 "split_di (operands, 2, operands + 2, operands + 4);")
2074 (define_insn "*swapdi_rex64"
2075 [(set (match_operand:DI 0 "register_operand" "+r")
2076 (match_operand:DI 1 "register_operand" "+r"))
2081 [(set_attr "type" "imov")
2082 (set_attr "mode" "DI")
2083 (set_attr "pent_pair" "np")
2084 (set_attr "athlon_decode" "vector")])
2086 (define_expand "movti"
2087 [(set (match_operand:TI 0 "nonimmediate_operand" "")
2088 (match_operand:TI 1 "nonimmediate_operand" ""))]
2089 "TARGET_SSE || TARGET_64BIT"
2092 ix86_expand_move (TImode, operands);
2094 ix86_expand_vector_move (TImode, operands);
2098 (define_insn "*movti_internal"
2099 [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
2100 (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
2101 "TARGET_SSE && !TARGET_64BIT
2102 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2104 switch (which_alternative)
2107 if (get_attr_mode (insn) == MODE_V4SF)
2108 return "xorps\t%0, %0";
2110 return "pxor\t%0, %0";
2113 if (get_attr_mode (insn) == MODE_V4SF)
2114 return "movaps\t{%1, %0|%0, %1}";
2116 return "movdqa\t{%1, %0|%0, %1}";
2121 [(set_attr "type" "ssemov,ssemov,ssemov")
2123 (cond [(eq (symbol_ref "TARGET_SSE2") (const_int 0))
2124 (const_string "V4SF")
2126 (eq_attr "alternative" "0,1")
2128 (ne (symbol_ref "optimize_size")
2130 (const_string "V4SF")
2131 (const_string "TI"))
2132 (eq_attr "alternative" "2")
2134 (ne (symbol_ref "optimize_size")
2136 (const_string "V4SF")
2137 (const_string "TI"))]
2138 (const_string "TI")))])
2140 (define_insn "*movti_rex64"
2141 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o,x,x,xm")
2142 (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
2144 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2146 switch (which_alternative)
2152 if (get_attr_mode (insn) == MODE_V4SF)
2153 return "xorps\t%0, %0";
2155 return "pxor\t%0, %0";
2158 if (get_attr_mode (insn) == MODE_V4SF)
2159 return "movaps\t{%1, %0|%0, %1}";
2161 return "movdqa\t{%1, %0|%0, %1}";
2166 [(set_attr "type" "*,*,ssemov,ssemov,ssemov")
2168 (cond [(eq_attr "alternative" "2,3")
2170 (ne (symbol_ref "optimize_size")
2172 (const_string "V4SF")
2173 (const_string "TI"))
2174 (eq_attr "alternative" "4")
2176 (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2178 (ne (symbol_ref "optimize_size")
2180 (const_string "V4SF")
2181 (const_string "TI"))]
2182 (const_string "DI")))])
2185 [(set (match_operand:TI 0 "nonimmediate_operand" "")
2186 (match_operand:TI 1 "general_operand" ""))]
2187 "reload_completed && !SSE_REG_P (operands[0])
2188 && !SSE_REG_P (operands[1])"
2190 "ix86_split_long_move (operands); DONE;")
2192 (define_expand "movsf"
2193 [(set (match_operand:SF 0 "nonimmediate_operand" "")
2194 (match_operand:SF 1 "general_operand" ""))]
2196 "ix86_expand_move (SFmode, operands); DONE;")
2198 (define_insn "*pushsf"
2199 [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2200 (match_operand:SF 1 "general_no_elim_operand" "f#rx,rFm#fx,x#rf"))]
2203 /* Anything else should be already split before reg-stack. */
2204 gcc_assert (which_alternative == 1);
2205 return "push{l}\t%1";
2207 [(set_attr "type" "multi,push,multi")
2208 (set_attr "unit" "i387,*,*")
2209 (set_attr "mode" "SF,SI,SF")])
2211 (define_insn "*pushsf_rex64"
2212 [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2213 (match_operand:SF 1 "nonmemory_no_elim_operand" "f#rx,rF#fx,x#rf"))]
2216 /* Anything else should be already split before reg-stack. */
2217 gcc_assert (which_alternative == 1);
2218 return "push{q}\t%q1";
2220 [(set_attr "type" "multi,push,multi")
2221 (set_attr "unit" "i387,*,*")
2222 (set_attr "mode" "SF,DI,SF")])
2225 [(set (match_operand:SF 0 "push_operand" "")
2226 (match_operand:SF 1 "memory_operand" ""))]
2228 && GET_CODE (operands[1]) == MEM
2229 && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
2230 && CONSTANT_POOL_ADDRESS_P (XEXP (operands[1], 0))"
2233 "operands[1] = get_pool_constant (XEXP (operands[1], 0));")
2236 ;; %%% Kill this when call knows how to work this out.
2238 [(set (match_operand:SF 0 "push_operand" "")
2239 (match_operand:SF 1 "any_fp_register_operand" ""))]
2241 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
2242 (set (mem:SF (reg:SI SP_REG)) (match_dup 1))])
2245 [(set (match_operand:SF 0 "push_operand" "")
2246 (match_operand:SF 1 "any_fp_register_operand" ""))]
2248 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2249 (set (mem:SF (reg:DI SP_REG)) (match_dup 1))])
2251 (define_insn "*movsf_1"
2252 [(set (match_operand:SF 0 "nonimmediate_operand"
2253 "=f#xr,m ,f#xr,r#xf ,m ,x#rf,x#rf,x#rf ,m ,!*y,!rm,!*y")
2254 (match_operand:SF 1 "general_operand"
2255 "fm#rx,f#rx,G ,rmF#fx,Fr#fx,C ,x ,xm#rf,x#rf,rm ,*y ,*y"))]
2256 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2257 && (reload_in_progress || reload_completed
2258 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2259 || GET_CODE (operands[1]) != CONST_DOUBLE
2260 || memory_operand (operands[0], SFmode))"
2262 switch (which_alternative)
2265 return output_387_reg_move (insn, operands);
2268 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2269 return "fstp%z0\t%y0";
2271 return "fst%z0\t%y0";
2274 return standard_80387_constant_opcode (operands[1]);
2278 return "mov{l}\t{%1, %0|%0, %1}";
2280 if (get_attr_mode (insn) == MODE_TI)
2281 return "pxor\t%0, %0";
2283 return "xorps\t%0, %0";
2285 if (get_attr_mode (insn) == MODE_V4SF)
2286 return "movaps\t{%1, %0|%0, %1}";
2288 return "movss\t{%1, %0|%0, %1}";
2291 return "movss\t{%1, %0|%0, %1}";
2295 return "movd\t{%1, %0|%0, %1}";
2298 return "movq\t{%1, %0|%0, %1}";
2304 [(set_attr "type" "fmov,fmov,fmov,imov,imov,ssemov,ssemov,ssemov,ssemov,mmxmov,mmxmov,mmxmov")
2306 (cond [(eq_attr "alternative" "3,4,9,10")
2308 (eq_attr "alternative" "5")
2310 (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2312 (ne (symbol_ref "TARGET_SSE2")
2314 (eq (symbol_ref "optimize_size")
2317 (const_string "V4SF"))
2318 /* For architectures resolving dependencies on
2319 whole SSE registers use APS move to break dependency
2320 chains, otherwise use short move to avoid extra work.
2322 Do the same for architectures resolving dependencies on
2323 the parts. While in DF mode it is better to always handle
2324 just register parts, the SF mode is different due to lack
2325 of instructions to load just part of the register. It is
2326 better to maintain the whole registers in single format
2327 to avoid problems on using packed logical operations. */
2328 (eq_attr "alternative" "6")
2330 (ior (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2332 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2334 (const_string "V4SF")
2335 (const_string "SF"))
2336 (eq_attr "alternative" "11")
2337 (const_string "DI")]
2338 (const_string "SF")))])
2340 (define_insn "*swapsf"
2341 [(set (match_operand:SF 0 "fp_register_operand" "+f")
2342 (match_operand:SF 1 "fp_register_operand" "+f"))
2345 "reload_completed || TARGET_80387"
2347 if (STACK_TOP_P (operands[0]))
2352 [(set_attr "type" "fxch")
2353 (set_attr "mode" "SF")])
2355 (define_expand "movdf"
2356 [(set (match_operand:DF 0 "nonimmediate_operand" "")
2357 (match_operand:DF 1 "general_operand" ""))]
2359 "ix86_expand_move (DFmode, operands); DONE;")
2361 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2362 ;; Size of pushdf using integer instructions is 2+2*memory operand size
2363 ;; On the average, pushdf using integers can be still shorter. Allow this
2364 ;; pattern for optimize_size too.
2366 (define_insn "*pushdf_nointeger"
2367 [(set (match_operand:DF 0 "push_operand" "=<,<,<,<")
2368 (match_operand:DF 1 "general_no_elim_operand" "f#Y,Fo#fY,*r#fY,Y#f"))]
2369 "!TARGET_64BIT && !TARGET_INTEGER_DFMODE_MOVES"
2371 /* This insn should be already split before reg-stack. */
2374 [(set_attr "type" "multi")
2375 (set_attr "unit" "i387,*,*,*")
2376 (set_attr "mode" "DF,SI,SI,DF")])
2378 (define_insn "*pushdf_integer"
2379 [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2380 (match_operand:DF 1 "general_no_elim_operand" "f#rY,rFo#fY,Y#rf"))]
2381 "TARGET_64BIT || TARGET_INTEGER_DFMODE_MOVES"
2383 /* This insn should be already split before reg-stack. */
2386 [(set_attr "type" "multi")
2387 (set_attr "unit" "i387,*,*")
2388 (set_attr "mode" "DF,SI,DF")])
2390 ;; %%% Kill this when call knows how to work this out.
2392 [(set (match_operand:DF 0 "push_operand" "")
2393 (match_operand:DF 1 "any_fp_register_operand" ""))]
2394 "!TARGET_64BIT && reload_completed"
2395 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
2396 (set (mem:DF (reg:SI SP_REG)) (match_dup 1))]
2400 [(set (match_operand:DF 0 "push_operand" "")
2401 (match_operand:DF 1 "any_fp_register_operand" ""))]
2402 "TARGET_64BIT && reload_completed"
2403 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2404 (set (mem:DF (reg:DI SP_REG)) (match_dup 1))]
2408 [(set (match_operand:DF 0 "push_operand" "")
2409 (match_operand:DF 1 "general_operand" ""))]
2412 "ix86_split_long_move (operands); DONE;")
2414 ;; Moving is usually shorter when only FP registers are used. This separate
2415 ;; movdf pattern avoids the use of integer registers for FP operations
2416 ;; when optimizing for size.
2418 (define_insn "*movdf_nointeger"
2419 [(set (match_operand:DF 0 "nonimmediate_operand"
2420 "=f#Y,m ,f#Y,*r ,o ,Y*x#f,Y*x#f,Y*x#f ,m ")
2421 (match_operand:DF 1 "general_operand"
2422 "fm#Y,f#Y,G ,*roF,F*r,C ,Y*x#f,HmY*x#f,Y*x#f"))]
2423 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2424 && ((optimize_size || !TARGET_INTEGER_DFMODE_MOVES) && !TARGET_64BIT)
2425 && (reload_in_progress || reload_completed
2426 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2427 || GET_CODE (operands[1]) != CONST_DOUBLE
2428 || memory_operand (operands[0], DFmode))"
2430 switch (which_alternative)
2433 return output_387_reg_move (insn, operands);
2436 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2437 return "fstp%z0\t%y0";
2439 return "fst%z0\t%y0";
2442 return standard_80387_constant_opcode (operands[1]);
2448 switch (get_attr_mode (insn))
2451 return "xorps\t%0, %0";
2453 return "xorpd\t%0, %0";
2455 return "pxor\t%0, %0";
2462 switch (get_attr_mode (insn))
2465 return "movaps\t{%1, %0|%0, %1}";
2467 return "movapd\t{%1, %0|%0, %1}";
2469 return "movdqa\t{%1, %0|%0, %1}";
2471 return "movq\t{%1, %0|%0, %1}";
2473 return "movsd\t{%1, %0|%0, %1}";
2475 return "movlpd\t{%1, %0|%0, %1}";
2477 return "movlps\t{%1, %0|%0, %1}";
2486 [(set_attr "type" "fmov,fmov,fmov,multi,multi,ssemov,ssemov,ssemov,ssemov")
2488 (cond [(eq_attr "alternative" "0,1,2")
2490 (eq_attr "alternative" "3,4")
2493 /* For SSE1, we have many fewer alternatives. */
2494 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2495 (cond [(eq_attr "alternative" "5,6")
2496 (const_string "V4SF")
2498 (const_string "V2SF"))
2500 /* xorps is one byte shorter. */
2501 (eq_attr "alternative" "5")
2502 (cond [(ne (symbol_ref "optimize_size")
2504 (const_string "V4SF")
2505 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2509 (const_string "V2DF"))
2511 /* For architectures resolving dependencies on
2512 whole SSE registers use APD move to break dependency
2513 chains, otherwise use short move to avoid extra work.
2515 movaps encodes one byte shorter. */
2516 (eq_attr "alternative" "6")
2518 [(ne (symbol_ref "optimize_size")
2520 (const_string "V4SF")
2521 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2523 (const_string "V2DF")
2525 (const_string "DF"))
2526 /* For architectures resolving dependencies on register
2527 parts we may avoid extra work to zero out upper part
2529 (eq_attr "alternative" "7")
2531 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2533 (const_string "V1DF")
2534 (const_string "DF"))
2536 (const_string "DF")))])
2538 (define_insn "*movdf_integer"
2539 [(set (match_operand:DF 0 "nonimmediate_operand"
2540 "=f#Yr,m ,f#Yr,r#Yf ,o ,Y*x#rf,Y*x#rf,Y*x#rf,m")
2541 (match_operand:DF 1 "general_operand"
2542 "fm#Yr,f#Yr,G ,roF#Yf,Fr#Yf,C ,Y*x#rf,m ,Y*x#rf"))]
2543 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2544 && ((!optimize_size && TARGET_INTEGER_DFMODE_MOVES) || TARGET_64BIT)
2545 && (reload_in_progress || reload_completed
2546 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2547 || GET_CODE (operands[1]) != CONST_DOUBLE
2548 || memory_operand (operands[0], DFmode))"
2550 switch (which_alternative)
2553 return output_387_reg_move (insn, operands);
2556 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2557 return "fstp%z0\t%y0";
2559 return "fst%z0\t%y0";
2562 return standard_80387_constant_opcode (operands[1]);
2569 switch (get_attr_mode (insn))
2572 return "xorps\t%0, %0";
2574 return "xorpd\t%0, %0";
2576 return "pxor\t%0, %0";
2583 switch (get_attr_mode (insn))
2586 return "movaps\t{%1, %0|%0, %1}";
2588 return "movapd\t{%1, %0|%0, %1}";
2590 return "movdqa\t{%1, %0|%0, %1}";
2592 return "movq\t{%1, %0|%0, %1}";
2594 return "movsd\t{%1, %0|%0, %1}";
2596 return "movlpd\t{%1, %0|%0, %1}";
2598 return "movlps\t{%1, %0|%0, %1}";
2607 [(set_attr "type" "fmov,fmov,fmov,multi,multi,ssemov,ssemov,ssemov,ssemov")
2609 (cond [(eq_attr "alternative" "0,1,2")
2611 (eq_attr "alternative" "3,4")
2614 /* For SSE1, we have many fewer alternatives. */
2615 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2616 (cond [(eq_attr "alternative" "5,6")
2617 (const_string "V4SF")
2619 (const_string "V2SF"))
2621 /* xorps is one byte shorter. */
2622 (eq_attr "alternative" "5")
2623 (cond [(ne (symbol_ref "optimize_size")
2625 (const_string "V4SF")
2626 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2630 (const_string "V2DF"))
2632 /* For architectures resolving dependencies on
2633 whole SSE registers use APD move to break dependency
2634 chains, otherwise use short move to avoid extra work.
2636 movaps encodes one byte shorter. */
2637 (eq_attr "alternative" "6")
2639 [(ne (symbol_ref "optimize_size")
2641 (const_string "V4SF")
2642 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2644 (const_string "V2DF")
2646 (const_string "DF"))
2647 /* For architectures resolving dependencies on register
2648 parts we may avoid extra work to zero out upper part
2650 (eq_attr "alternative" "7")
2652 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2654 (const_string "V1DF")
2655 (const_string "DF"))
2657 (const_string "DF")))])
2660 [(set (match_operand:DF 0 "nonimmediate_operand" "")
2661 (match_operand:DF 1 "general_operand" ""))]
2663 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2664 && ! (ANY_FP_REG_P (operands[0]) ||
2665 (GET_CODE (operands[0]) == SUBREG
2666 && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2667 && ! (ANY_FP_REG_P (operands[1]) ||
2668 (GET_CODE (operands[1]) == SUBREG
2669 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2671 "ix86_split_long_move (operands); DONE;")
2673 (define_insn "*swapdf"
2674 [(set (match_operand:DF 0 "fp_register_operand" "+f")
2675 (match_operand:DF 1 "fp_register_operand" "+f"))
2678 "reload_completed || TARGET_80387"
2680 if (STACK_TOP_P (operands[0]))
2685 [(set_attr "type" "fxch")
2686 (set_attr "mode" "DF")])
2688 (define_expand "movxf"
2689 [(set (match_operand:XF 0 "nonimmediate_operand" "")
2690 (match_operand:XF 1 "general_operand" ""))]
2692 "ix86_expand_move (XFmode, operands); DONE;")
2694 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2695 ;; Size of pushdf using integer instructions is 3+3*memory operand size
2696 ;; Pushing using integer instructions is longer except for constants
2697 ;; and direct memory references.
2698 ;; (assuming that any given constant is pushed only once, but this ought to be
2699 ;; handled elsewhere).
2701 (define_insn "*pushxf_nointeger"
2702 [(set (match_operand:XF 0 "push_operand" "=X,X,X")
2703 (match_operand:XF 1 "general_no_elim_operand" "f,Fo,*r"))]
2706 /* This insn should be already split before reg-stack. */
2709 [(set_attr "type" "multi")
2710 (set_attr "unit" "i387,*,*")
2711 (set_attr "mode" "XF,SI,SI")])
2713 (define_insn "*pushxf_integer"
2714 [(set (match_operand:XF 0 "push_operand" "=<,<")
2715 (match_operand:XF 1 "general_no_elim_operand" "f#r,ro#f"))]
2718 /* This insn should be already split before reg-stack. */
2721 [(set_attr "type" "multi")
2722 (set_attr "unit" "i387,*")
2723 (set_attr "mode" "XF,SI")])
2726 [(set (match_operand 0 "push_operand" "")
2727 (match_operand 1 "general_operand" ""))]
2729 && (GET_MODE (operands[0]) == XFmode
2730 || GET_MODE (operands[0]) == DFmode)
2731 && !ANY_FP_REG_P (operands[1])"
2733 "ix86_split_long_move (operands); DONE;")
2736 [(set (match_operand:XF 0 "push_operand" "")
2737 (match_operand:XF 1 "any_fp_register_operand" ""))]
2739 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
2740 (set (mem:XF (reg:SI SP_REG)) (match_dup 1))]
2741 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
2744 [(set (match_operand:XF 0 "push_operand" "")
2745 (match_operand:XF 1 "any_fp_register_operand" ""))]
2747 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
2748 (set (mem:XF (reg:DI SP_REG)) (match_dup 1))]
2749 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
2751 ;; Do not use integer registers when optimizing for size
2752 (define_insn "*movxf_nointeger"
2753 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,*r,o")
2754 (match_operand:XF 1 "general_operand" "fm,f,G,*roF,F*r"))]
2756 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2757 && (reload_in_progress || reload_completed
2758 || GET_CODE (operands[1]) != CONST_DOUBLE
2759 || memory_operand (operands[0], XFmode))"
2761 switch (which_alternative)
2764 return output_387_reg_move (insn, operands);
2767 /* There is no non-popping store to memory for XFmode. So if
2768 we need one, follow the store with a load. */
2769 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2770 return "fstp%z0\t%y0\;fld%z0\t%y0";
2772 return "fstp%z0\t%y0";
2775 return standard_80387_constant_opcode (operands[1]);
2783 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2784 (set_attr "mode" "XF,XF,XF,SI,SI")])
2786 (define_insn "*movxf_integer"
2787 [(set (match_operand:XF 0 "nonimmediate_operand" "=f#r,m,f#r,r#f,o")
2788 (match_operand:XF 1 "general_operand" "fm#r,f#r,G,roF#f,Fr#f"))]
2790 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2791 && (reload_in_progress || reload_completed
2792 || GET_CODE (operands[1]) != CONST_DOUBLE
2793 || memory_operand (operands[0], XFmode))"
2795 switch (which_alternative)
2798 return output_387_reg_move (insn, operands);
2801 /* There is no non-popping store to memory for XFmode. So if
2802 we need one, follow the store with a load. */
2803 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2804 return "fstp%z0\t%y0\;fld%z0\t%y0";
2806 return "fstp%z0\t%y0";
2809 return standard_80387_constant_opcode (operands[1]);
2818 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2819 (set_attr "mode" "XF,XF,XF,SI,SI")])
2822 [(set (match_operand 0 "nonimmediate_operand" "")
2823 (match_operand 1 "general_operand" ""))]
2825 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2826 && GET_MODE (operands[0]) == XFmode
2827 && ! (ANY_FP_REG_P (operands[0]) ||
2828 (GET_CODE (operands[0]) == SUBREG
2829 && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2830 && ! (ANY_FP_REG_P (operands[1]) ||
2831 (GET_CODE (operands[1]) == SUBREG
2832 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2834 "ix86_split_long_move (operands); DONE;")
2837 [(set (match_operand 0 "register_operand" "")
2838 (match_operand 1 "memory_operand" ""))]
2840 && GET_CODE (operands[1]) == MEM
2841 && (GET_MODE (operands[0]) == XFmode
2842 || GET_MODE (operands[0]) == SFmode || GET_MODE (operands[0]) == DFmode)
2843 && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
2844 && CONSTANT_POOL_ADDRESS_P (XEXP (operands[1], 0))"
2845 [(set (match_dup 0) (match_dup 1))]
2847 rtx c = get_pool_constant (XEXP (operands[1], 0));
2848 rtx r = operands[0];
2850 if (GET_CODE (r) == SUBREG)
2855 if (!standard_sse_constant_p (c))
2858 else if (FP_REG_P (r))
2860 if (!standard_80387_constant_p (c))
2863 else if (MMX_REG_P (r))
2869 (define_insn "swapxf"
2870 [(set (match_operand:XF 0 "register_operand" "+f")
2871 (match_operand:XF 1 "register_operand" "+f"))
2876 if (STACK_TOP_P (operands[0]))
2881 [(set_attr "type" "fxch")
2882 (set_attr "mode" "XF")])
2884 (define_expand "movtf"
2885 [(set (match_operand:TF 0 "nonimmediate_operand" "")
2886 (match_operand:TF 1 "nonimmediate_operand" ""))]
2889 ix86_expand_move (TFmode, operands);
2893 (define_insn "*movtf_internal"
2894 [(set (match_operand:TF 0 "nonimmediate_operand" "=r,o,x,x,xm")
2895 (match_operand:TF 1 "general_operand" "riFo,riF,C,xm,x"))]
2897 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2899 switch (which_alternative)
2905 if (get_attr_mode (insn) == MODE_V4SF)
2906 return "xorps\t%0, %0";
2908 return "pxor\t%0, %0";
2911 if (get_attr_mode (insn) == MODE_V4SF)
2912 return "movaps\t{%1, %0|%0, %1}";
2914 return "movdqa\t{%1, %0|%0, %1}";
2919 [(set_attr "type" "*,*,ssemov,ssemov,ssemov")
2921 (cond [(eq_attr "alternative" "2,3")
2923 (ne (symbol_ref "optimize_size")
2925 (const_string "V4SF")
2926 (const_string "TI"))
2927 (eq_attr "alternative" "4")
2929 (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2931 (ne (symbol_ref "optimize_size")
2933 (const_string "V4SF")
2934 (const_string "TI"))]
2935 (const_string "DI")))])
2938 [(set (match_operand:TF 0 "nonimmediate_operand" "")
2939 (match_operand:TF 1 "general_operand" ""))]
2940 "reload_completed && !SSE_REG_P (operands[0])
2941 && !SSE_REG_P (operands[1])"
2943 "ix86_split_long_move (operands); DONE;")
2945 ;; Zero extension instructions
2947 (define_expand "zero_extendhisi2"
2948 [(set (match_operand:SI 0 "register_operand" "")
2949 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
2952 if (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
2954 operands[1] = force_reg (HImode, operands[1]);
2955 emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
2960 (define_insn "zero_extendhisi2_and"
2961 [(set (match_operand:SI 0 "register_operand" "=r")
2962 (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
2963 (clobber (reg:CC FLAGS_REG))]
2964 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
2966 [(set_attr "type" "alu1")
2967 (set_attr "mode" "SI")])
2970 [(set (match_operand:SI 0 "register_operand" "")
2971 (zero_extend:SI (match_operand:HI 1 "register_operand" "")))
2972 (clobber (reg:CC FLAGS_REG))]
2973 "reload_completed && TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
2974 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
2975 (clobber (reg:CC FLAGS_REG))])]
2978 (define_insn "*zero_extendhisi2_movzwl"
2979 [(set (match_operand:SI 0 "register_operand" "=r")
2980 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
2981 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
2982 "movz{wl|x}\t{%1, %0|%0, %1}"
2983 [(set_attr "type" "imovx")
2984 (set_attr "mode" "SI")])
2986 (define_expand "zero_extendqihi2"
2988 [(set (match_operand:HI 0 "register_operand" "")
2989 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
2990 (clobber (reg:CC FLAGS_REG))])]
2994 (define_insn "*zero_extendqihi2_and"
2995 [(set (match_operand:HI 0 "register_operand" "=r,?&q")
2996 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
2997 (clobber (reg:CC FLAGS_REG))]
2998 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3000 [(set_attr "type" "alu1")
3001 (set_attr "mode" "HI")])
3003 (define_insn "*zero_extendqihi2_movzbw_and"
3004 [(set (match_operand:HI 0 "register_operand" "=r,r")
3005 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3006 (clobber (reg:CC FLAGS_REG))]
3007 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3009 [(set_attr "type" "imovx,alu1")
3010 (set_attr "mode" "HI")])
3012 (define_insn "*zero_extendqihi2_movzbw"
3013 [(set (match_operand:HI 0 "register_operand" "=r")
3014 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3015 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3016 "movz{bw|x}\t{%1, %0|%0, %1}"
3017 [(set_attr "type" "imovx")
3018 (set_attr "mode" "HI")])
3020 ;; For the movzbw case strip only the clobber
3022 [(set (match_operand:HI 0 "register_operand" "")
3023 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3024 (clobber (reg:CC FLAGS_REG))]
3026 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3027 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3028 [(set (match_operand:HI 0 "register_operand" "")
3029 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))])
3031 ;; When source and destination does not overlap, clear destination
3032 ;; first and then do the movb
3034 [(set (match_operand:HI 0 "register_operand" "")
3035 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3036 (clobber (reg:CC FLAGS_REG))]
3038 && ANY_QI_REG_P (operands[0])
3039 && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3040 && !reg_overlap_mentioned_p (operands[0], operands[1])"
3041 [(set (match_dup 0) (const_int 0))
3042 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3043 "operands[2] = gen_lowpart (QImode, operands[0]);")
3045 ;; Rest is handled by single and.
3047 [(set (match_operand:HI 0 "register_operand" "")
3048 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))
3049 (clobber (reg:CC FLAGS_REG))]
3051 && true_regnum (operands[0]) == true_regnum (operands[1])"
3052 [(parallel [(set (match_dup 0) (and:HI (match_dup 0) (const_int 255)))
3053 (clobber (reg:CC FLAGS_REG))])]
3056 (define_expand "zero_extendqisi2"
3058 [(set (match_operand:SI 0 "register_operand" "")
3059 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3060 (clobber (reg:CC FLAGS_REG))])]
3064 (define_insn "*zero_extendqisi2_and"
3065 [(set (match_operand:SI 0 "register_operand" "=r,?&q")
3066 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3067 (clobber (reg:CC FLAGS_REG))]
3068 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3070 [(set_attr "type" "alu1")
3071 (set_attr "mode" "SI")])
3073 (define_insn "*zero_extendqisi2_movzbw_and"
3074 [(set (match_operand:SI 0 "register_operand" "=r,r")
3075 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3076 (clobber (reg:CC FLAGS_REG))]
3077 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3079 [(set_attr "type" "imovx,alu1")
3080 (set_attr "mode" "SI")])
3082 (define_insn "*zero_extendqisi2_movzbw"
3083 [(set (match_operand:SI 0 "register_operand" "=r")
3084 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3085 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3086 "movz{bl|x}\t{%1, %0|%0, %1}"
3087 [(set_attr "type" "imovx")
3088 (set_attr "mode" "SI")])
3090 ;; For the movzbl case strip only the clobber
3092 [(set (match_operand:SI 0 "register_operand" "")
3093 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3094 (clobber (reg:CC FLAGS_REG))]
3096 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3097 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3099 (zero_extend:SI (match_dup 1)))])
3101 ;; When source and destination does not overlap, clear destination
3102 ;; first and then do the movb
3104 [(set (match_operand:SI 0 "register_operand" "")
3105 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3106 (clobber (reg:CC FLAGS_REG))]
3108 && ANY_QI_REG_P (operands[0])
3109 && (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM)
3110 && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3111 && !reg_overlap_mentioned_p (operands[0], operands[1])"
3112 [(set (match_dup 0) (const_int 0))
3113 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3114 "operands[2] = gen_lowpart (QImode, operands[0]);")
3116 ;; Rest is handled by single and.
3118 [(set (match_operand:SI 0 "register_operand" "")
3119 (zero_extend:SI (match_operand:QI 1 "register_operand" "")))
3120 (clobber (reg:CC FLAGS_REG))]
3122 && true_regnum (operands[0]) == true_regnum (operands[1])"
3123 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 255)))
3124 (clobber (reg:CC FLAGS_REG))])]
3127 ;; %%% Kill me once multi-word ops are sane.
3128 (define_expand "zero_extendsidi2"
3129 [(set (match_operand:DI 0 "register_operand" "=r")
3130 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm")))]
3134 emit_insn (gen_zero_extendsidi2_32 (operands[0], operands[1]));
3139 (define_insn "zero_extendsidi2_32"
3140 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?*o,?*y,?*Y")
3141 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "0,rm,r,rm,rm")))
3142 (clobber (reg:CC FLAGS_REG))]
3148 movd\t{%1, %0|%0, %1}
3149 movd\t{%1, %0|%0, %1}"
3150 [(set_attr "mode" "SI,SI,SI,DI,TI")
3151 (set_attr "type" "multi,multi,multi,mmxmov,ssemov")])
3153 (define_insn "zero_extendsidi2_rex64"
3154 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,?*y,?*Y")
3155 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm,0,rm,rm")))]
3158 mov\t{%k1, %k0|%k0, %k1}
3160 movd\t{%1, %0|%0, %1}
3161 movd\t{%1, %0|%0, %1}"
3162 [(set_attr "type" "imovx,imov,mmxmov,ssemov")
3163 (set_attr "mode" "SI,DI,SI,SI")])
3166 [(set (match_operand:DI 0 "memory_operand" "")
3167 (zero_extend:DI (match_dup 0)))]
3169 [(set (match_dup 4) (const_int 0))]
3170 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3173 [(set (match_operand:DI 0 "register_operand" "")
3174 (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3175 (clobber (reg:CC FLAGS_REG))]
3176 "!TARGET_64BIT && reload_completed
3177 && true_regnum (operands[0]) == true_regnum (operands[1])"
3178 [(set (match_dup 4) (const_int 0))]
3179 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3182 [(set (match_operand:DI 0 "nonimmediate_operand" "")
3183 (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3184 (clobber (reg:CC FLAGS_REG))]
3185 "!TARGET_64BIT && reload_completed
3186 && !SSE_REG_P (operands[0]) && !MMX_REG_P (operands[0])"
3187 [(set (match_dup 3) (match_dup 1))
3188 (set (match_dup 4) (const_int 0))]
3189 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3191 (define_insn "zero_extendhidi2"
3192 [(set (match_operand:DI 0 "register_operand" "=r,r")
3193 (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "r,m")))]
3196 movz{wl|x}\t{%1, %k0|%k0, %1}
3197 movz{wq|x}\t{%1, %0|%0, %1}"
3198 [(set_attr "type" "imovx")
3199 (set_attr "mode" "SI,DI")])
3201 (define_insn "zero_extendqidi2"
3202 [(set (match_operand:DI 0 "register_operand" "=r,r")
3203 (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "Q,m")))]
3206 movz{bl|x}\t{%1, %k0|%k0, %1}
3207 movz{bq|x}\t{%1, %0|%0, %1}"
3208 [(set_attr "type" "imovx")
3209 (set_attr "mode" "SI,DI")])
3211 ;; Sign extension instructions
3213 (define_expand "extendsidi2"
3214 [(parallel [(set (match_operand:DI 0 "register_operand" "")
3215 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3216 (clobber (reg:CC FLAGS_REG))
3217 (clobber (match_scratch:SI 2 ""))])]
3222 emit_insn (gen_extendsidi2_rex64 (operands[0], operands[1]));
3227 (define_insn "*extendsidi2_1"
3228 [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3229 (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3230 (clobber (reg:CC FLAGS_REG))
3231 (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3235 (define_insn "extendsidi2_rex64"
3236 [(set (match_operand:DI 0 "register_operand" "=*a,r")
3237 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3241 movs{lq|x}\t{%1,%0|%0, %1}"
3242 [(set_attr "type" "imovx")
3243 (set_attr "mode" "DI")
3244 (set_attr "prefix_0f" "0")
3245 (set_attr "modrm" "0,1")])
3247 (define_insn "extendhidi2"
3248 [(set (match_operand:DI 0 "register_operand" "=r")
3249 (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3251 "movs{wq|x}\t{%1,%0|%0, %1}"
3252 [(set_attr "type" "imovx")
3253 (set_attr "mode" "DI")])
3255 (define_insn "extendqidi2"
3256 [(set (match_operand:DI 0 "register_operand" "=r")
3257 (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3259 "movs{bq|x}\t{%1,%0|%0, %1}"
3260 [(set_attr "type" "imovx")
3261 (set_attr "mode" "DI")])
3263 ;; Extend to memory case when source register does die.
3265 [(set (match_operand:DI 0 "memory_operand" "")
3266 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3267 (clobber (reg:CC FLAGS_REG))
3268 (clobber (match_operand:SI 2 "register_operand" ""))]
3270 && dead_or_set_p (insn, operands[1])
3271 && !reg_mentioned_p (operands[1], operands[0]))"
3272 [(set (match_dup 3) (match_dup 1))
3273 (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3274 (clobber (reg:CC FLAGS_REG))])
3275 (set (match_dup 4) (match_dup 1))]
3276 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3278 ;; Extend to memory case when source register does not die.
3280 [(set (match_operand:DI 0 "memory_operand" "")
3281 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3282 (clobber (reg:CC FLAGS_REG))
3283 (clobber (match_operand:SI 2 "register_operand" ""))]
3287 split_di (&operands[0], 1, &operands[3], &operands[4]);
3289 emit_move_insn (operands[3], operands[1]);
3291 /* Generate a cltd if possible and doing so it profitable. */
3292 if (true_regnum (operands[1]) == 0
3293 && true_regnum (operands[2]) == 1
3294 && (optimize_size || TARGET_USE_CLTD))
3296 emit_insn (gen_ashrsi3_31 (operands[2], operands[1], GEN_INT (31)));
3300 emit_move_insn (operands[2], operands[1]);
3301 emit_insn (gen_ashrsi3_31 (operands[2], operands[2], GEN_INT (31)));
3303 emit_move_insn (operands[4], operands[2]);
3307 ;; Extend to register case. Optimize case where source and destination
3308 ;; registers match and cases where we can use cltd.
3310 [(set (match_operand:DI 0 "register_operand" "")
3311 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3312 (clobber (reg:CC FLAGS_REG))
3313 (clobber (match_scratch:SI 2 ""))]
3317 split_di (&operands[0], 1, &operands[3], &operands[4]);
3319 if (true_regnum (operands[3]) != true_regnum (operands[1]))
3320 emit_move_insn (operands[3], operands[1]);
3322 /* Generate a cltd if possible and doing so it profitable. */
3323 if (true_regnum (operands[3]) == 0
3324 && (optimize_size || TARGET_USE_CLTD))
3326 emit_insn (gen_ashrsi3_31 (operands[4], operands[3], GEN_INT (31)));
3330 if (true_regnum (operands[4]) != true_regnum (operands[1]))
3331 emit_move_insn (operands[4], operands[1]);
3333 emit_insn (gen_ashrsi3_31 (operands[4], operands[4], GEN_INT (31)));
3337 (define_insn "extendhisi2"
3338 [(set (match_operand:SI 0 "register_operand" "=*a,r")
3339 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3342 switch (get_attr_prefix_0f (insn))
3345 return "{cwtl|cwde}";
3347 return "movs{wl|x}\t{%1,%0|%0, %1}";
3350 [(set_attr "type" "imovx")
3351 (set_attr "mode" "SI")
3352 (set (attr "prefix_0f")
3353 ;; movsx is short decodable while cwtl is vector decoded.
3354 (if_then_else (and (eq_attr "cpu" "!k6")
3355 (eq_attr "alternative" "0"))
3357 (const_string "1")))
3359 (if_then_else (eq_attr "prefix_0f" "0")
3361 (const_string "1")))])
3363 (define_insn "*extendhisi2_zext"
3364 [(set (match_operand:DI 0 "register_operand" "=*a,r")
3366 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3369 switch (get_attr_prefix_0f (insn))
3372 return "{cwtl|cwde}";
3374 return "movs{wl|x}\t{%1,%k0|%k0, %1}";
3377 [(set_attr "type" "imovx")
3378 (set_attr "mode" "SI")
3379 (set (attr "prefix_0f")
3380 ;; movsx is short decodable while cwtl is vector decoded.
3381 (if_then_else (and (eq_attr "cpu" "!k6")
3382 (eq_attr "alternative" "0"))
3384 (const_string "1")))
3386 (if_then_else (eq_attr "prefix_0f" "0")
3388 (const_string "1")))])
3390 (define_insn "extendqihi2"
3391 [(set (match_operand:HI 0 "register_operand" "=*a,r")
3392 (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3395 switch (get_attr_prefix_0f (insn))
3398 return "{cbtw|cbw}";
3400 return "movs{bw|x}\t{%1,%0|%0, %1}";
3403 [(set_attr "type" "imovx")
3404 (set_attr "mode" "HI")
3405 (set (attr "prefix_0f")
3406 ;; movsx is short decodable while cwtl is vector decoded.
3407 (if_then_else (and (eq_attr "cpu" "!k6")
3408 (eq_attr "alternative" "0"))
3410 (const_string "1")))
3412 (if_then_else (eq_attr "prefix_0f" "0")
3414 (const_string "1")))])
3416 (define_insn "extendqisi2"
3417 [(set (match_operand:SI 0 "register_operand" "=r")
3418 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3420 "movs{bl|x}\t{%1,%0|%0, %1}"
3421 [(set_attr "type" "imovx")
3422 (set_attr "mode" "SI")])
3424 (define_insn "*extendqisi2_zext"
3425 [(set (match_operand:DI 0 "register_operand" "=r")
3427 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3429 "movs{bl|x}\t{%1,%k0|%k0, %1}"
3430 [(set_attr "type" "imovx")
3431 (set_attr "mode" "SI")])
3433 ;; Conversions between float and double.
3435 ;; These are all no-ops in the model used for the 80387. So just
3438 ;; %%% Kill these when call knows how to work out a DFmode push earlier.
3439 (define_insn "*dummy_extendsfdf2"
3440 [(set (match_operand:DF 0 "push_operand" "=<")
3441 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fY")))]
3446 [(set (match_operand:DF 0 "push_operand" "")
3447 (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3449 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
3450 (set (mem:DF (reg:SI SP_REG)) (float_extend:DF (match_dup 1)))])
3453 [(set (match_operand:DF 0 "push_operand" "")
3454 (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3456 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
3457 (set (mem:DF (reg:DI SP_REG)) (float_extend:DF (match_dup 1)))])
3459 (define_insn "*dummy_extendsfxf2"
3460 [(set (match_operand:XF 0 "push_operand" "=<")
3461 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "f")))]
3466 [(set (match_operand:XF 0 "push_operand" "")
3467 (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3469 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3470 (set (mem:XF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))]
3471 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3474 [(set (match_operand:XF 0 "push_operand" "")
3475 (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3477 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3478 (set (mem:DF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))]
3479 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3482 [(set (match_operand:XF 0 "push_operand" "")
3483 (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3485 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3486 (set (mem:DF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))]
3487 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3490 [(set (match_operand:XF 0 "push_operand" "")
3491 (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3493 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3494 (set (mem:XF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))]
3495 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3497 (define_expand "extendsfdf2"
3498 [(set (match_operand:DF 0 "nonimmediate_operand" "")
3499 (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
3500 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3502 /* ??? Needed for compress_float_constant since all fp constants
3503 are LEGITIMATE_CONSTANT_P. */
3504 if (GET_CODE (operands[1]) == CONST_DOUBLE)
3505 operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3506 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3507 operands[1] = force_reg (SFmode, operands[1]);
3510 (define_insn "*extendsfdf2_mixed"
3511 [(set (match_operand:DF 0 "nonimmediate_operand" "=f#Y,m#fY,Y#f")
3512 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm#Y,f#Y,mY#f")))]
3513 "TARGET_SSE2 && TARGET_MIX_SSE_I387
3514 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3516 switch (which_alternative)
3519 return output_387_reg_move (insn, operands);
3522 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3523 return "fstp%z0\t%y0";
3525 return "fst%z0\t%y0";
3528 return "cvtss2sd\t{%1, %0|%0, %1}";
3534 [(set_attr "type" "fmov,fmov,ssecvt")
3535 (set_attr "mode" "SF,XF,DF")])
3537 (define_insn "*extendsfdf2_sse"
3538 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y")
3539 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "mY")))]
3540 "TARGET_SSE2 && TARGET_SSE_MATH
3541 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3542 "cvtss2sd\t{%1, %0|%0, %1}"
3543 [(set_attr "type" "ssecvt")
3544 (set_attr "mode" "DF")])
3546 (define_insn "*extendsfdf2_i387"
3547 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
3548 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3550 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3552 switch (which_alternative)
3555 return output_387_reg_move (insn, operands);
3558 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3559 return "fstp%z0\t%y0";
3561 return "fst%z0\t%y0";
3567 [(set_attr "type" "fmov")
3568 (set_attr "mode" "SF,XF")])
3570 (define_expand "extendsfxf2"
3571 [(set (match_operand:XF 0 "nonimmediate_operand" "")
3572 (float_extend:XF (match_operand:SF 1 "general_operand" "")))]
3575 /* ??? Needed for compress_float_constant since all fp constants
3576 are LEGITIMATE_CONSTANT_P. */
3577 if (GET_CODE (operands[1]) == CONST_DOUBLE)
3578 operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3579 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3580 operands[1] = force_reg (SFmode, operands[1]);
3583 (define_insn "*extendsfxf2_i387"
3584 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3585 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3587 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3589 switch (which_alternative)
3592 return output_387_reg_move (insn, operands);
3595 /* There is no non-popping store to memory for XFmode. So if
3596 we need one, follow the store with a load. */
3597 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3598 return "fstp%z0\t%y0";
3600 return "fstp%z0\t%y0\n\tfld%z0\t%y0";
3606 [(set_attr "type" "fmov")
3607 (set_attr "mode" "SF,XF")])
3609 (define_expand "extenddfxf2"
3610 [(set (match_operand:XF 0 "nonimmediate_operand" "")
3611 (float_extend:XF (match_operand:DF 1 "general_operand" "")))]
3614 /* ??? Needed for compress_float_constant since all fp constants
3615 are LEGITIMATE_CONSTANT_P. */
3616 if (GET_CODE (operands[1]) == CONST_DOUBLE)
3617 operands[1] = validize_mem (force_const_mem (DFmode, operands[1]));
3618 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3619 operands[1] = force_reg (DFmode, operands[1]);
3622 (define_insn "*extenddfxf2_i387"
3623 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3624 (float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "fm,f")))]
3626 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3628 switch (which_alternative)
3631 return output_387_reg_move (insn, operands);
3634 /* There is no non-popping store to memory for XFmode. So if
3635 we need one, follow the store with a load. */
3636 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3637 return "fstp%z0\t%y0\n\tfld%z0\t%y0";
3639 return "fstp%z0\t%y0";
3645 [(set_attr "type" "fmov")
3646 (set_attr "mode" "DF,XF")])
3648 ;; %%% This seems bad bad news.
3649 ;; This cannot output into an f-reg because there is no way to be sure
3650 ;; of truncating in that case. Otherwise this is just like a simple move
3651 ;; insn. So we pretend we can output to a reg in order to get better
3652 ;; register preferencing, but we really use a stack slot.
3654 ;; Conversion from DFmode to SFmode.
3656 (define_expand "truncdfsf2"
3657 [(set (match_operand:SF 0 "nonimmediate_operand" "")
3659 (match_operand:DF 1 "nonimmediate_operand" "")))]
3660 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3662 if (MEM_P (operands[0]) && MEM_P (operands[1]))
3663 operands[1] = force_reg (DFmode, operands[1]);
3665 if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387)
3667 else if (flag_unsafe_math_optimizations)
3671 rtx temp = assign_386_stack_local (SFmode, SLOT_TEMP);
3672 emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp));
3677 (define_expand "truncdfsf2_with_temp"
3678 [(parallel [(set (match_operand:SF 0 "" "")
3679 (float_truncate:SF (match_operand:DF 1 "" "")))
3680 (clobber (match_operand:SF 2 "" ""))])]
3683 (define_insn "*truncdfsf_fast_mixed"
3684 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,f,Y")
3686 (match_operand:DF 1 "nonimmediate_operand" "f ,f,Ym")))]
3687 "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations"
3689 switch (which_alternative)
3692 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3693 return "fstp%z0\t%y0";
3695 return "fst%z0\t%y0";
3697 return output_387_reg_move (insn, operands);
3699 return "cvtsd2ss\t{%1, %0|%0, %1}";
3704 [(set_attr "type" "fmov,fmov,ssecvt")
3705 (set_attr "mode" "SF")])
3707 ;; Yes, this one doesn't depend on flag_unsafe_math_optimizations,
3708 ;; because nothing we do here is unsafe.
3709 (define_insn "*truncdfsf_fast_sse"
3710 [(set (match_operand:SF 0 "nonimmediate_operand" "=Y")
3712 (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
3713 "TARGET_SSE2 && TARGET_SSE_MATH"
3714 "cvtsd2ss\t{%1, %0|%0, %1}"
3715 [(set_attr "type" "ssecvt")
3716 (set_attr "mode" "SF")])
3718 (define_insn "*truncdfsf_fast_i387"
3719 [(set (match_operand:SF 0 "nonimmediate_operand" "=fm")
3721 (match_operand:DF 1 "nonimmediate_operand" "f")))]
3722 "TARGET_80387 && flag_unsafe_math_optimizations"
3723 "* return output_387_reg_move (insn, operands);"
3724 [(set_attr "type" "fmov")
3725 (set_attr "mode" "SF")])
3727 (define_insn "*truncdfsf_mixed"
3728 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r,Y")
3730 (match_operand:DF 1 "nonimmediate_operand" "f ,f ,Ym")))
3731 (clobber (match_operand:SF 2 "memory_operand" "=X,m ,X"))]
3732 "TARGET_MIX_SSE_I387"
3734 switch (which_alternative)
3737 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3738 return "fstp%z0\t%y0";
3740 return "fst%z0\t%y0";
3744 return "cvtsd2ss\t{%1, %0|%0, %1}";
3749 [(set_attr "type" "fmov,multi,ssecvt")
3750 (set_attr "unit" "*,i387,*")
3751 (set_attr "mode" "SF")])
3753 (define_insn "*truncdfsf_i387"
3754 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r")
3756 (match_operand:DF 1 "nonimmediate_operand" "f,f")))
3757 (clobber (match_operand:SF 2 "memory_operand" "=X,m"))]
3760 switch (which_alternative)
3763 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3764 return "fstp%z0\t%y0";
3766 return "fst%z0\t%y0";
3773 [(set_attr "type" "fmov,multi")
3774 (set_attr "unit" "*,i387")
3775 (set_attr "mode" "SF")])
3777 (define_insn "*truncdfsf2_i387_1"
3778 [(set (match_operand:SF 0 "memory_operand" "=m")
3780 (match_operand:DF 1 "register_operand" "f")))]
3782 && !(TARGET_SSE2 && TARGET_SSE_MATH)
3783 && !TARGET_MIX_SSE_I387"
3785 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3786 return "fstp%z0\t%y0";
3788 return "fst%z0\t%y0";
3790 [(set_attr "type" "fmov")
3791 (set_attr "mode" "SF")])
3794 [(set (match_operand:SF 0 "register_operand" "")
3796 (match_operand:DF 1 "fp_register_operand" "")))
3797 (clobber (match_operand 2 "" ""))]
3799 [(set (match_dup 2) (match_dup 1))
3800 (set (match_dup 0) (match_dup 2))]
3802 operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1]));
3805 ;; Conversion from XFmode to SFmode.
3807 (define_expand "truncxfsf2"
3808 [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
3810 (match_operand:XF 1 "register_operand" "")))
3811 (clobber (match_dup 2))])]
3814 if (flag_unsafe_math_optimizations)
3816 rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SFmode);
3817 emit_insn (gen_truncxfsf2_i387_noop (reg, operands[1]));
3818 if (reg != operands[0])
3819 emit_move_insn (operands[0], reg);
3823 operands[2] = assign_386_stack_local (SFmode, SLOT_TEMP);
3826 (define_insn "*truncxfsf2_mixed"
3827 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f#rx,?r#fx,?x#rf")
3829 (match_operand:XF 1 "register_operand" "f,f,f,f")))
3830 (clobber (match_operand:SF 2 "memory_operand" "=X,m,m,m"))]
3831 "TARGET_MIX_SSE_I387"
3833 gcc_assert (!which_alternative);
3834 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3835 return "fstp%z0\t%y0";
3837 return "fst%z0\t%y0";
3839 [(set_attr "type" "fmov,multi,multi,multi")
3840 (set_attr "unit" "*,i387,i387,i387")
3841 (set_attr "mode" "SF")])
3843 (define_insn "truncxfsf2_i387_noop"
3844 [(set (match_operand:SF 0 "register_operand" "=f")
3845 (float_truncate:SF (match_operand:XF 1 "register_operand" "f")))]
3846 "TARGET_80387 && flag_unsafe_math_optimizations"
3848 return output_387_reg_move (insn, operands);
3850 [(set_attr "type" "fmov")
3851 (set_attr "mode" "SF")])
3853 (define_insn "*truncxfsf2_i387"
3854 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f#r,?r#f")
3856 (match_operand:XF 1 "register_operand" "f,f,f")))
3857 (clobber (match_operand:SF 2 "memory_operand" "=X,m,m"))]
3860 gcc_assert (!which_alternative);
3861 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3862 return "fstp%z0\t%y0";
3864 return "fst%z0\t%y0";
3866 [(set_attr "type" "fmov,multi,multi")
3867 (set_attr "unit" "*,i387,i387")
3868 (set_attr "mode" "SF")])
3870 (define_insn "*truncxfsf2_i387_1"
3871 [(set (match_operand:SF 0 "memory_operand" "=m")
3873 (match_operand:XF 1 "register_operand" "f")))]
3876 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3877 return "fstp%z0\t%y0";
3879 return "fst%z0\t%y0";
3881 [(set_attr "type" "fmov")
3882 (set_attr "mode" "SF")])
3885 [(set (match_operand:SF 0 "register_operand" "")
3887 (match_operand:XF 1 "register_operand" "")))
3888 (clobber (match_operand:SF 2 "memory_operand" ""))]
3889 "TARGET_80387 && reload_completed"
3890 [(set (match_dup 2) (float_truncate:SF (match_dup 1)))
3891 (set (match_dup 0) (match_dup 2))]
3895 [(set (match_operand:SF 0 "memory_operand" "")
3897 (match_operand:XF 1 "register_operand" "")))
3898 (clobber (match_operand:SF 2 "memory_operand" ""))]
3900 [(set (match_dup 0) (float_truncate:SF (match_dup 1)))]
3903 ;; Conversion from XFmode to DFmode.
3905 (define_expand "truncxfdf2"
3906 [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
3908 (match_operand:XF 1 "register_operand" "")))
3909 (clobber (match_dup 2))])]
3912 if (flag_unsafe_math_optimizations)
3914 rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DFmode);
3915 emit_insn (gen_truncxfdf2_i387_noop (reg, operands[1]));
3916 if (reg != operands[0])
3917 emit_move_insn (operands[0], reg);
3921 operands[2] = assign_386_stack_local (DFmode, SLOT_TEMP);
3924 (define_insn "*truncxfdf2_mixed"
3925 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f#rY,?r#fY,?Y#rf")
3927 (match_operand:XF 1 "register_operand" "f,f,f,f")))
3928 (clobber (match_operand:DF 2 "memory_operand" "=X,m,m,m"))]
3929 "TARGET_SSE2 && TARGET_MIX_SSE_I387"
3931 gcc_assert (!which_alternative);
3932 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3933 return "fstp%z0\t%y0";
3935 return "fst%z0\t%y0";
3937 [(set_attr "type" "fmov,multi,multi,multi")
3938 (set_attr "unit" "*,i387,i387,i387")
3939 (set_attr "mode" "DF")])
3941 (define_insn "truncxfdf2_i387_noop"
3942 [(set (match_operand:DF 0 "register_operand" "=f")
3943 (float_truncate:DF (match_operand:XF 1 "register_operand" "f")))]
3944 "TARGET_80387 && flag_unsafe_math_optimizations"
3946 return output_387_reg_move (insn, operands);
3948 [(set_attr "type" "fmov")
3949 (set_attr "mode" "DF")])
3951 (define_insn "*truncxfdf2_i387"
3952 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f#r,?r#f")
3954 (match_operand:XF 1 "register_operand" "f,f,f")))
3955 (clobber (match_operand:DF 2 "memory_operand" "=X,m,m"))]
3958 gcc_assert (!which_alternative);
3959 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3960 return "fstp%z0\t%y0";
3962 return "fst%z0\t%y0";
3964 [(set_attr "type" "fmov,multi,multi")
3965 (set_attr "unit" "*,i387,i387")
3966 (set_attr "mode" "DF")])
3968 (define_insn "*truncxfdf2_i387_1"
3969 [(set (match_operand:DF 0 "memory_operand" "=m")
3971 (match_operand:XF 1 "register_operand" "f")))]
3974 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3975 return "fstp%z0\t%y0";
3977 return "fst%z0\t%y0";
3979 [(set_attr "type" "fmov")
3980 (set_attr "mode" "DF")])
3983 [(set (match_operand:DF 0 "register_operand" "")
3985 (match_operand:XF 1 "register_operand" "")))
3986 (clobber (match_operand:DF 2 "memory_operand" ""))]
3987 "TARGET_80387 && reload_completed"
3988 [(set (match_dup 2) (float_truncate:DF (match_dup 1)))
3989 (set (match_dup 0) (match_dup 2))]
3993 [(set (match_operand:DF 0 "memory_operand" "")
3995 (match_operand:XF 1 "register_operand" "")))
3996 (clobber (match_operand:DF 2 "memory_operand" ""))]
3998 [(set (match_dup 0) (float_truncate:DF (match_dup 1)))]
4001 ;; Signed conversion to DImode.
4003 (define_expand "fix_truncxfdi2"
4004 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4005 (fix:DI (match_operand:XF 1 "register_operand" "")))
4006 (clobber (reg:CC FLAGS_REG))])]
4011 emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4016 (define_expand "fix_trunc<mode>di2"
4017 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4018 (fix:DI (match_operand:SSEMODEF 1 "register_operand" "")))
4019 (clobber (reg:CC FLAGS_REG))])]
4020 "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))"
4023 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4025 emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4028 if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))
4030 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4031 emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1]));
4032 if (out != operands[0])
4033 emit_move_insn (operands[0], out);
4038 ;; Signed conversion to SImode.
4040 (define_expand "fix_truncxfsi2"
4041 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4042 (fix:SI (match_operand:XF 1 "register_operand" "")))
4043 (clobber (reg:CC FLAGS_REG))])]
4048 emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4053 (define_expand "fix_trunc<mode>si2"
4054 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4055 (fix:SI (match_operand:SSEMODEF 1 "register_operand" "")))
4056 (clobber (reg:CC FLAGS_REG))])]
4057 "TARGET_80387 || (SSE_FLOAT_MODE_P (<MODE>mode))"
4060 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4062 emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4065 if (SSE_FLOAT_MODE_P (<MODE>mode))
4067 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4068 emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1]));
4069 if (out != operands[0])
4070 emit_move_insn (operands[0], out);
4075 ;; Signed conversion to HImode.
4077 (define_expand "fix_trunc<mode>hi2"
4078 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4079 (fix:HI (match_operand:X87MODEF 1 "register_operand" "")))
4080 (clobber (reg:CC FLAGS_REG))])]
4082 && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))"
4086 emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1]));
4091 ;; When SSE is available, it is always faster to use it!
4092 (define_insn "fix_truncsfdi_sse"
4093 [(set (match_operand:DI 0 "register_operand" "=r,r")
4094 (fix:DI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))]
4095 "TARGET_64BIT && TARGET_SSE && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4096 "cvttss2si{q}\t{%1, %0|%0, %1}"
4097 [(set_attr "type" "sseicvt")
4098 (set_attr "mode" "SF")
4099 (set_attr "athlon_decode" "double,vector")])
4101 (define_insn "fix_truncdfdi_sse"
4102 [(set (match_operand:DI 0 "register_operand" "=r,r")
4103 (fix:DI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))]
4104 "TARGET_64BIT && TARGET_SSE2 && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4105 "cvttsd2si{q}\t{%1, %0|%0, %1}"
4106 [(set_attr "type" "sseicvt")
4107 (set_attr "mode" "DF")
4108 (set_attr "athlon_decode" "double,vector")])
4110 (define_insn "fix_truncsfsi_sse"
4111 [(set (match_operand:SI 0 "register_operand" "=r,r")
4112 (fix:SI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))]
4113 "TARGET_SSE && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4114 "cvttss2si\t{%1, %0|%0, %1}"
4115 [(set_attr "type" "sseicvt")
4116 (set_attr "mode" "DF")
4117 (set_attr "athlon_decode" "double,vector")])
4119 (define_insn "fix_truncdfsi_sse"
4120 [(set (match_operand:SI 0 "register_operand" "=r,r")
4121 (fix:SI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))]
4122 "TARGET_SSE2 && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4123 "cvttsd2si\t{%1, %0|%0, %1}"
4124 [(set_attr "type" "sseicvt")
4125 (set_attr "mode" "DF")
4126 (set_attr "athlon_decode" "double,vector")])
4128 ;; Avoid vector decoded forms of the instruction.
4130 [(match_scratch:DF 2 "Y")
4131 (set (match_operand:SSEMODEI24 0 "register_operand" "")
4132 (fix:SSEMODEI24 (match_operand:DF 1 "memory_operand" "")))]
4133 "TARGET_K8 && !optimize_size"
4134 [(set (match_dup 2) (match_dup 1))
4135 (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4139 [(match_scratch:SF 2 "x")
4140 (set (match_operand:SSEMODEI24 0 "register_operand" "")
4141 (fix:SSEMODEI24 (match_operand:SF 1 "memory_operand" "")))]
4142 "TARGET_K8 && !optimize_size"
4143 [(set (match_dup 2) (match_dup 1))
4144 (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4147 (define_insn_and_split "fix_trunc<mode>_fisttp_i387_1"
4148 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4149 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))]
4150 "TARGET_80387 && TARGET_FISTTP
4151 && FLOAT_MODE_P (GET_MODE (operands[1]))
4152 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4153 && (TARGET_64BIT || <MODE>mode != DImode))
4155 && !(reload_completed || reload_in_progress)"
4160 if (memory_operand (operands[0], VOIDmode))
4161 emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1]));
4164 operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4165 emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0],
4171 [(set_attr "type" "fisttp")
4172 (set_attr "mode" "<MODE>")])
4174 (define_insn "fix_trunc<mode>_i387_fisttp"
4175 [(set (match_operand:X87MODEI 0 "memory_operand" "=m")
4176 (fix:X87MODEI (match_operand 1 "register_operand" "f")))
4177 (clobber (match_scratch:XF 2 "=&1f"))]
4178 "TARGET_80387 && TARGET_FISTTP
4179 && FLOAT_MODE_P (GET_MODE (operands[1]))
4180 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4181 && (TARGET_64BIT || <MODE>mode != DImode))
4182 && TARGET_SSE_MATH)"
4183 "* return output_fix_trunc (insn, operands, 1);"
4184 [(set_attr "type" "fisttp")
4185 (set_attr "mode" "<MODE>")])
4187 (define_insn "fix_trunc<mode>_i387_fisttp_with_temp"
4188 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4189 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
4190 (clobber (match_operand:X87MODEI 2 "memory_operand" "=m,m"))
4191 (clobber (match_scratch:XF 3 "=&1f,&1f"))]
4192 "TARGET_80387 && TARGET_FISTTP
4193 && FLOAT_MODE_P (GET_MODE (operands[1]))
4194 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4195 && (TARGET_64BIT || <MODE>mode != DImode))
4196 && TARGET_SSE_MATH)"
4198 [(set_attr "type" "fisttp")
4199 (set_attr "mode" "<MODE>")])
4202 [(set (match_operand:X87MODEI 0 "register_operand" "")
4203 (fix:X87MODEI (match_operand 1 "register_operand" "")))
4204 (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4205 (clobber (match_scratch 3 ""))]
4207 [(parallel [(set (match_dup 2) (fix:X87MODEI (match_dup 1)))
4208 (clobber (match_dup 3))])
4209 (set (match_dup 0) (match_dup 2))]
4213 [(set (match_operand:X87MODEI 0 "memory_operand" "")
4214 (fix:X87MODEI (match_operand 1 "register_operand" "")))
4215 (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4216 (clobber (match_scratch 3 ""))]
4218 [(parallel [(set (match_dup 0) (fix:X87MODEI (match_dup 1)))
4219 (clobber (match_dup 3))])]
4222 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4223 ;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control
4224 ;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG
4225 ;; clobbering insns can be used. Look at emit_i387_cw_initialization ()
4226 ;; function in i386.c.
4227 (define_insn_and_split "*fix_trunc<mode>_i387_1"
4228 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4229 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
4230 (clobber (reg:CC FLAGS_REG))]
4231 "TARGET_80387 && !TARGET_FISTTP
4232 && FLOAT_MODE_P (GET_MODE (operands[1]))
4233 && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4234 && (TARGET_64BIT || <MODE>mode != DImode))
4235 && !(reload_completed || reload_in_progress)"
4240 ix86_optimize_mode_switching[I387_TRUNC] = 1;
4242 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
4243 operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
4244 if (memory_operand (operands[0], VOIDmode))
4245 emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1],
4246 operands[2], operands[3]));
4249 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4250 emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1],
4251 operands[2], operands[3],
4256 [(set_attr "type" "fistp")
4257 (set_attr "i387_cw" "trunc")
4258 (set_attr "mode" "<MODE>")])
4260 (define_insn "fix_truncdi_i387"
4261 [(set (match_operand:DI 0 "memory_operand" "=m")
4262 (fix:DI (match_operand 1 "register_operand" "f")))
4263 (use (match_operand:HI 2 "memory_operand" "m"))
4264 (use (match_operand:HI 3 "memory_operand" "m"))
4265 (clobber (match_scratch:XF 4 "=&1f"))]
4266 "TARGET_80387 && !TARGET_FISTTP
4267 && FLOAT_MODE_P (GET_MODE (operands[1]))
4268 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4269 "* return output_fix_trunc (insn, operands, 0);"
4270 [(set_attr "type" "fistp")
4271 (set_attr "i387_cw" "trunc")
4272 (set_attr "mode" "DI")])
4274 (define_insn "fix_truncdi_i387_with_temp"
4275 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4276 (fix:DI (match_operand 1 "register_operand" "f,f")))
4277 (use (match_operand:HI 2 "memory_operand" "m,m"))
4278 (use (match_operand:HI 3 "memory_operand" "m,m"))
4279 (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
4280 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
4281 "TARGET_80387 && !TARGET_FISTTP
4282 && FLOAT_MODE_P (GET_MODE (operands[1]))
4283 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4285 [(set_attr "type" "fistp")
4286 (set_attr "i387_cw" "trunc")
4287 (set_attr "mode" "DI")])
4290 [(set (match_operand:DI 0 "register_operand" "")
4291 (fix:DI (match_operand 1 "register_operand" "")))
4292 (use (match_operand:HI 2 "memory_operand" ""))
4293 (use (match_operand:HI 3 "memory_operand" ""))
4294 (clobber (match_operand:DI 4 "memory_operand" ""))
4295 (clobber (match_scratch 5 ""))]
4297 [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
4300 (clobber (match_dup 5))])
4301 (set (match_dup 0) (match_dup 4))]
4305 [(set (match_operand:DI 0 "memory_operand" "")
4306 (fix:DI (match_operand 1 "register_operand" "")))
4307 (use (match_operand:HI 2 "memory_operand" ""))
4308 (use (match_operand:HI 3 "memory_operand" ""))
4309 (clobber (match_operand:DI 4 "memory_operand" ""))
4310 (clobber (match_scratch 5 ""))]
4312 [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
4315 (clobber (match_dup 5))])]
4318 (define_insn "fix_trunc<mode>_i387"
4319 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
4320 (fix:X87MODEI12 (match_operand 1 "register_operand" "f")))
4321 (use (match_operand:HI 2 "memory_operand" "m"))
4322 (use (match_operand:HI 3 "memory_operand" "m"))]
4323 "TARGET_80387 && !TARGET_FISTTP
4324 && FLOAT_MODE_P (GET_MODE (operands[1]))
4325 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4326 "* return output_fix_trunc (insn, operands, 0);"
4327 [(set_attr "type" "fistp")
4328 (set_attr "i387_cw" "trunc")
4329 (set_attr "mode" "<MODE>")])
4331 (define_insn "fix_trunc<mode>_i387_with_temp"
4332 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
4333 (fix:X87MODEI12 (match_operand 1 "register_operand" "f,f")))
4334 (use (match_operand:HI 2 "memory_operand" "m,m"))
4335 (use (match_operand:HI 3 "memory_operand" "m,m"))
4336 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
4337 "TARGET_80387 && !TARGET_FISTTP
4338 && FLOAT_MODE_P (GET_MODE (operands[1]))
4339 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4341 [(set_attr "type" "fistp")
4342 (set_attr "i387_cw" "trunc")
4343 (set_attr "mode" "<MODE>")])
4346 [(set (match_operand:X87MODEI12 0 "register_operand" "")
4347 (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4348 (use (match_operand:HI 2 "memory_operand" ""))
4349 (use (match_operand:HI 3 "memory_operand" ""))
4350 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4352 [(parallel [(set (match_dup 4) (fix:X87MODEI12 (match_dup 1)))
4354 (use (match_dup 3))])
4355 (set (match_dup 0) (match_dup 4))]
4359 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
4360 (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4361 (use (match_operand:HI 2 "memory_operand" ""))
4362 (use (match_operand:HI 3 "memory_operand" ""))
4363 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4365 [(parallel [(set (match_dup 0) (fix:X87MODEI12 (match_dup 1)))
4367 (use (match_dup 3))])]
4370 (define_insn "x86_fnstcw_1"
4371 [(set (match_operand:HI 0 "memory_operand" "=m")
4372 (unspec:HI [(reg:HI FPSR_REG)] UNSPEC_FSTCW))]
4375 [(set_attr "length" "2")
4376 (set_attr "mode" "HI")
4377 (set_attr "unit" "i387")])
4379 (define_insn "x86_fldcw_1"
4380 [(set (reg:HI FPSR_REG)
4381 (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
4384 [(set_attr "length" "2")
4385 (set_attr "mode" "HI")
4386 (set_attr "unit" "i387")
4387 (set_attr "athlon_decode" "vector")])
4389 ;; Conversion between fixed point and floating point.
4391 ;; Even though we only accept memory inputs, the backend _really_
4392 ;; wants to be able to do this between registers.
4394 (define_expand "floathisf2"
4395 [(set (match_operand:SF 0 "register_operand" "")
4396 (float:SF (match_operand:HI 1 "nonimmediate_operand" "")))]
4397 "TARGET_80387 || TARGET_SSE_MATH"
4399 if (TARGET_SSE_MATH)
4401 emit_insn (gen_floatsisf2 (operands[0],
4402 convert_to_mode (SImode, operands[1], 0)));
4407 (define_insn "*floathisf2_i387"
4408 [(set (match_operand:SF 0 "register_operand" "=f,f")
4409 (float:SF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4410 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
4414 [(set_attr "type" "fmov,multi")
4415 (set_attr "mode" "SF")
4416 (set_attr "unit" "*,i387")
4417 (set_attr "fp_int_src" "true")])
4419 (define_expand "floatsisf2"
4420 [(set (match_operand:SF 0 "register_operand" "")
4421 (float:SF (match_operand:SI 1 "nonimmediate_operand" "")))]
4422 "TARGET_80387 || TARGET_SSE_MATH"
4425 (define_insn "*floatsisf2_mixed"
4426 [(set (match_operand:SF 0 "register_operand" "=f#x,?f#x,x#f,x#f")
4427 (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))]
4428 "TARGET_MIX_SSE_I387"
4432 cvtsi2ss\t{%1, %0|%0, %1}
4433 cvtsi2ss\t{%1, %0|%0, %1}"
4434 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4435 (set_attr "mode" "SF")
4436 (set_attr "unit" "*,i387,*,*")
4437 (set_attr "athlon_decode" "*,*,vector,double")
4438 (set_attr "fp_int_src" "true")])
4440 (define_insn "*floatsisf2_sse"
4441 [(set (match_operand:SF 0 "register_operand" "=x,x")
4442 (float:SF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))]
4444 "cvtsi2ss\t{%1, %0|%0, %1}"
4445 [(set_attr "type" "sseicvt")
4446 (set_attr "mode" "SF")
4447 (set_attr "athlon_decode" "vector,double")
4448 (set_attr "fp_int_src" "true")])
4450 (define_insn "*floatsisf2_i387"
4451 [(set (match_operand:SF 0 "register_operand" "=f,f")
4452 (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4457 [(set_attr "type" "fmov,multi")
4458 (set_attr "mode" "SF")
4459 (set_attr "unit" "*,i387")
4460 (set_attr "fp_int_src" "true")])
4462 (define_expand "floatdisf2"
4463 [(set (match_operand:SF 0 "register_operand" "")
4464 (float:SF (match_operand:DI 1 "nonimmediate_operand" "")))]
4465 "TARGET_80387 || (TARGET_64BIT && TARGET_SSE_MATH)"
4468 (define_insn "*floatdisf2_mixed"
4469 [(set (match_operand:SF 0 "register_operand" "=f#x,?f#x,x#f,x#f")
4470 (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))]
4471 "TARGET_64BIT && TARGET_MIX_SSE_I387"
4475 cvtsi2ss{q}\t{%1, %0|%0, %1}
4476 cvtsi2ss{q}\t{%1, %0|%0, %1}"
4477 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4478 (set_attr "mode" "SF")
4479 (set_attr "unit" "*,i387,*,*")
4480 (set_attr "athlon_decode" "*,*,vector,double")
4481 (set_attr "fp_int_src" "true")])
4483 (define_insn "*floatdisf2_sse"
4484 [(set (match_operand:SF 0 "register_operand" "=x,x")
4485 (float:SF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))]
4486 "TARGET_64BIT && TARGET_SSE_MATH"
4487 "cvtsi2ss{q}\t{%1, %0|%0, %1}"
4488 [(set_attr "type" "sseicvt")
4489 (set_attr "mode" "SF")
4490 (set_attr "athlon_decode" "vector,double")
4491 (set_attr "fp_int_src" "true")])
4493 (define_insn "*floatdisf2_i387"
4494 [(set (match_operand:SF 0 "register_operand" "=f,f")
4495 (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4500 [(set_attr "type" "fmov,multi")
4501 (set_attr "mode" "SF")
4502 (set_attr "unit" "*,i387")
4503 (set_attr "fp_int_src" "true")])
4505 (define_expand "floathidf2"
4506 [(set (match_operand:DF 0 "register_operand" "")
4507 (float:DF (match_operand:HI 1 "nonimmediate_operand" "")))]
4508 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4510 if (TARGET_SSE2 && TARGET_SSE_MATH)
4512 emit_insn (gen_floatsidf2 (operands[0],
4513 convert_to_mode (SImode, operands[1], 0)));
4518 (define_insn "*floathidf2_i387"
4519 [(set (match_operand:DF 0 "register_operand" "=f,f")
4520 (float:DF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4521 "TARGET_80387 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)"
4525 [(set_attr "type" "fmov,multi")
4526 (set_attr "mode" "DF")
4527 (set_attr "unit" "*,i387")
4528 (set_attr "fp_int_src" "true")])
4530 (define_expand "floatsidf2"
4531 [(set (match_operand:DF 0 "register_operand" "")
4532 (float:DF (match_operand:SI 1 "nonimmediate_operand" "")))]
4533 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4536 (define_insn "*floatsidf2_mixed"
4537 [(set (match_operand:DF 0 "register_operand" "=f#Y,?f#Y,Y#f,Y#f")
4538 (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))]
4539 "TARGET_SSE2 && TARGET_MIX_SSE_I387"
4543 cvtsi2sd\t{%1, %0|%0, %1}
4544 cvtsi2sd\t{%1, %0|%0, %1}"
4545 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4546 (set_attr "mode" "DF")
4547 (set_attr "unit" "*,i387,*,*")
4548 (set_attr "athlon_decode" "*,*,double,direct")
4549 (set_attr "fp_int_src" "true")])
4551 (define_insn "*floatsidf2_sse"
4552 [(set (match_operand:DF 0 "register_operand" "=Y,Y")
4553 (float:DF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))]
4554 "TARGET_SSE2 && TARGET_SSE_MATH"
4555 "cvtsi2sd\t{%1, %0|%0, %1}"
4556 [(set_attr "type" "sseicvt")
4557 (set_attr "mode" "DF")
4558 (set_attr "athlon_decode" "double,direct")
4559 (set_attr "fp_int_src" "true")])
4561 (define_insn "*floatsidf2_i387"
4562 [(set (match_operand:DF 0 "register_operand" "=f,f")
4563 (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4568 [(set_attr "type" "fmov,multi")
4569 (set_attr "mode" "DF")
4570 (set_attr "unit" "*,i387")
4571 (set_attr "fp_int_src" "true")])
4573 (define_expand "floatdidf2"
4574 [(set (match_operand:DF 0 "register_operand" "")
4575 (float:DF (match_operand:DI 1 "nonimmediate_operand" "")))]
4576 "TARGET_80387 || (TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH)"
4579 (define_insn "*floatdidf2_mixed"
4580 [(set (match_operand:DF 0 "register_operand" "=f#Y,?f#Y,Y#f,Y#f")
4581 (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))]
4582 "TARGET_64BIT && TARGET_SSE2 && TARGET_MIX_SSE_I387"
4586 cvtsi2sd{q}\t{%1, %0|%0, %1}
4587 cvtsi2sd{q}\t{%1, %0|%0, %1}"
4588 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4589 (set_attr "mode" "DF")
4590 (set_attr "unit" "*,i387,*,*")
4591 (set_attr "athlon_decode" "*,*,double,direct")
4592 (set_attr "fp_int_src" "true")])
4594 (define_insn "*floatdidf2_sse"
4595 [(set (match_operand:DF 0 "register_operand" "=Y,Y")
4596 (float:DF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))]
4597 "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4598 "cvtsi2sd{q}\t{%1, %0|%0, %1}"
4599 [(set_attr "type" "sseicvt")
4600 (set_attr "mode" "DF")
4601 (set_attr "athlon_decode" "double,direct")
4602 (set_attr "fp_int_src" "true")])
4604 (define_insn "*floatdidf2_i387"
4605 [(set (match_operand:DF 0 "register_operand" "=f,f")
4606 (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4611 [(set_attr "type" "fmov,multi")
4612 (set_attr "mode" "DF")
4613 (set_attr "unit" "*,i387")
4614 (set_attr "fp_int_src" "true")])
4616 (define_insn "floathixf2"
4617 [(set (match_operand:XF 0 "register_operand" "=f,f")
4618 (float:XF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4623 [(set_attr "type" "fmov,multi")
4624 (set_attr "mode" "XF")
4625 (set_attr "unit" "*,i387")
4626 (set_attr "fp_int_src" "true")])
4628 (define_insn "floatsixf2"
4629 [(set (match_operand:XF 0 "register_operand" "=f,f")
4630 (float:XF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4635 [(set_attr "type" "fmov,multi")
4636 (set_attr "mode" "XF")
4637 (set_attr "unit" "*,i387")
4638 (set_attr "fp_int_src" "true")])
4640 (define_insn "floatdixf2"
4641 [(set (match_operand:XF 0 "register_operand" "=f,f")
4642 (float:XF (match_operand:DI 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 ;; %%% Kill these when reload knows how to do it.
4654 [(set (match_operand 0 "fp_register_operand" "")
4655 (float (match_operand 1 "register_operand" "")))]
4658 && FLOAT_MODE_P (GET_MODE (operands[0]))"
4661 operands[2] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
4662 operands[2] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[2]);
4663 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[2]));
4664 ix86_free_from_memory (GET_MODE (operands[1]));
4668 (define_expand "floatunssisf2"
4669 [(use (match_operand:SF 0 "register_operand" ""))
4670 (use (match_operand:SI 1 "register_operand" ""))]
4671 "!TARGET_64BIT && TARGET_SSE_MATH"
4672 "x86_emit_floatuns (operands); DONE;")
4674 (define_expand "floatunsdisf2"
4675 [(use (match_operand:SF 0 "register_operand" ""))
4676 (use (match_operand:DI 1 "register_operand" ""))]
4677 "TARGET_64BIT && TARGET_SSE_MATH"
4678 "x86_emit_floatuns (operands); DONE;")
4680 (define_expand "floatunsdidf2"
4681 [(use (match_operand:DF 0 "register_operand" ""))
4682 (use (match_operand:DI 1 "register_operand" ""))]
4683 "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4684 "x86_emit_floatuns (operands); DONE;")
4686 ;; SSE extract/set expanders
4691 ;; %%% splits for addsidi3
4692 ; [(set (match_operand:DI 0 "nonimmediate_operand" "")
4693 ; (plus:DI (match_operand:DI 1 "general_operand" "")
4694 ; (zero_extend:DI (match_operand:SI 2 "general_operand" ""))))]
4696 (define_expand "adddi3"
4697 [(set (match_operand:DI 0 "nonimmediate_operand" "")
4698 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4699 (match_operand:DI 2 "x86_64_general_operand" "")))
4700 (clobber (reg:CC FLAGS_REG))]
4702 "ix86_expand_binary_operator (PLUS, DImode, operands); DONE;")
4704 (define_insn "*adddi3_1"
4705 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
4706 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
4707 (match_operand:DI 2 "general_operand" "roiF,riF")))
4708 (clobber (reg:CC FLAGS_REG))]
4709 "!TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4713 [(set (match_operand:DI 0 "nonimmediate_operand" "")
4714 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4715 (match_operand:DI 2 "general_operand" "")))
4716 (clobber (reg:CC FLAGS_REG))]
4717 "!TARGET_64BIT && reload_completed"
4718 [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
4720 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))])
4721 (parallel [(set (match_dup 3)
4722 (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
4725 (clobber (reg:CC FLAGS_REG))])]
4726 "split_di (operands+0, 1, operands+0, operands+3);
4727 split_di (operands+1, 1, operands+1, operands+4);
4728 split_di (operands+2, 1, operands+2, operands+5);")
4730 (define_insn "adddi3_carry_rex64"
4731 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
4732 (plus:DI (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
4733 (match_operand:DI 1 "nonimmediate_operand" "%0,0"))
4734 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
4735 (clobber (reg:CC FLAGS_REG))]
4736 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4737 "adc{q}\t{%2, %0|%0, %2}"
4738 [(set_attr "type" "alu")
4739 (set_attr "pent_pair" "pu")
4740 (set_attr "mode" "DI")])
4742 (define_insn "*adddi3_cc_rex64"
4743 [(set (reg:CC FLAGS_REG)
4744 (unspec:CC [(match_operand:DI 1 "nonimmediate_operand" "%0,0")
4745 (match_operand:DI 2 "x86_64_general_operand" "re,rm")]
4747 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
4748 (plus:DI (match_dup 1) (match_dup 2)))]
4749 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4750 "add{q}\t{%2, %0|%0, %2}"
4751 [(set_attr "type" "alu")
4752 (set_attr "mode" "DI")])
4754 (define_insn "addqi3_carry"
4755 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
4756 (plus:QI (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
4757 (match_operand:QI 1 "nonimmediate_operand" "%0,0"))
4758 (match_operand:QI 2 "general_operand" "qi,qm")))
4759 (clobber (reg:CC FLAGS_REG))]
4760 "ix86_binary_operator_ok (PLUS, QImode, operands)"
4761 "adc{b}\t{%2, %0|%0, %2}"
4762 [(set_attr "type" "alu")
4763 (set_attr "pent_pair" "pu")
4764 (set_attr "mode" "QI")])
4766 (define_insn "addhi3_carry"
4767 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
4768 (plus:HI (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
4769 (match_operand:HI 1 "nonimmediate_operand" "%0,0"))
4770 (match_operand:HI 2 "general_operand" "ri,rm")))
4771 (clobber (reg:CC FLAGS_REG))]
4772 "ix86_binary_operator_ok (PLUS, HImode, operands)"
4773 "adc{w}\t{%2, %0|%0, %2}"
4774 [(set_attr "type" "alu")
4775 (set_attr "pent_pair" "pu")
4776 (set_attr "mode" "HI")])
4778 (define_insn "addsi3_carry"
4779 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
4780 (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
4781 (match_operand:SI 1 "nonimmediate_operand" "%0,0"))
4782 (match_operand:SI 2 "general_operand" "ri,rm")))
4783 (clobber (reg:CC FLAGS_REG))]
4784 "ix86_binary_operator_ok (PLUS, SImode, operands)"
4785 "adc{l}\t{%2, %0|%0, %2}"
4786 [(set_attr "type" "alu")
4787 (set_attr "pent_pair" "pu")
4788 (set_attr "mode" "SI")])
4790 (define_insn "*addsi3_carry_zext"
4791 [(set (match_operand:DI 0 "register_operand" "=r")
4793 (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
4794 (match_operand:SI 1 "nonimmediate_operand" "%0"))
4795 (match_operand:SI 2 "general_operand" "rim"))))
4796 (clobber (reg:CC FLAGS_REG))]
4797 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
4798 "adc{l}\t{%2, %k0|%k0, %2}"
4799 [(set_attr "type" "alu")
4800 (set_attr "pent_pair" "pu")
4801 (set_attr "mode" "SI")])
4803 (define_insn "*addsi3_cc"
4804 [(set (reg:CC FLAGS_REG)
4805 (unspec:CC [(match_operand:SI 1 "nonimmediate_operand" "%0,0")
4806 (match_operand:SI 2 "general_operand" "ri,rm")]
4808 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
4809 (plus:SI (match_dup 1) (match_dup 2)))]
4810 "ix86_binary_operator_ok (PLUS, SImode, operands)"
4811 "add{l}\t{%2, %0|%0, %2}"
4812 [(set_attr "type" "alu")
4813 (set_attr "mode" "SI")])
4815 (define_insn "addqi3_cc"
4816 [(set (reg:CC FLAGS_REG)
4817 (unspec:CC [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
4818 (match_operand:QI 2 "general_operand" "qi,qm")]
4820 (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
4821 (plus:QI (match_dup 1) (match_dup 2)))]
4822 "ix86_binary_operator_ok (PLUS, QImode, operands)"
4823 "add{b}\t{%2, %0|%0, %2}"
4824 [(set_attr "type" "alu")
4825 (set_attr "mode" "QI")])
4827 (define_expand "addsi3"
4828 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4829 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
4830 (match_operand:SI 2 "general_operand" "")))
4831 (clobber (reg:CC FLAGS_REG))])]
4833 "ix86_expand_binary_operator (PLUS, SImode, operands); DONE;")
4835 (define_insn "*lea_1"
4836 [(set (match_operand:SI 0 "register_operand" "=r")
4837 (match_operand:SI 1 "no_seg_address_operand" "p"))]
4839 "lea{l}\t{%a1, %0|%0, %a1}"
4840 [(set_attr "type" "lea")
4841 (set_attr "mode" "SI")])
4843 (define_insn "*lea_1_rex64"
4844 [(set (match_operand:SI 0 "register_operand" "=r")
4845 (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0))]
4847 "lea{l}\t{%a1, %0|%0, %a1}"
4848 [(set_attr "type" "lea")
4849 (set_attr "mode" "SI")])
4851 (define_insn "*lea_1_zext"
4852 [(set (match_operand:DI 0 "register_operand" "=r")
4854 (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0)))]
4856 "lea{l}\t{%a1, %k0|%k0, %a1}"
4857 [(set_attr "type" "lea")
4858 (set_attr "mode" "SI")])
4860 (define_insn "*lea_2_rex64"
4861 [(set (match_operand:DI 0 "register_operand" "=r")
4862 (match_operand:DI 1 "no_seg_address_operand" "p"))]
4864 "lea{q}\t{%a1, %0|%0, %a1}"
4865 [(set_attr "type" "lea")
4866 (set_attr "mode" "DI")])
4868 ;; The lea patterns for non-Pmodes needs to be matched by several
4869 ;; insns converted to real lea by splitters.
4871 (define_insn_and_split "*lea_general_1"
4872 [(set (match_operand 0 "register_operand" "=r")
4873 (plus (plus (match_operand 1 "index_register_operand" "l")
4874 (match_operand 2 "register_operand" "r"))
4875 (match_operand 3 "immediate_operand" "i")))]
4876 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
4877 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
4878 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
4879 && GET_MODE (operands[0]) == GET_MODE (operands[1])
4880 && GET_MODE (operands[0]) == GET_MODE (operands[2])
4881 && (GET_MODE (operands[0]) == GET_MODE (operands[3])
4882 || GET_MODE (operands[3]) == VOIDmode)"
4884 "&& reload_completed"
4888 operands[0] = gen_lowpart (SImode, operands[0]);
4889 operands[1] = gen_lowpart (Pmode, operands[1]);
4890 operands[2] = gen_lowpart (Pmode, operands[2]);
4891 operands[3] = gen_lowpart (Pmode, operands[3]);
4892 pat = gen_rtx_PLUS (Pmode, gen_rtx_PLUS (Pmode, operands[1], operands[2]),
4894 if (Pmode != SImode)
4895 pat = gen_rtx_SUBREG (SImode, pat, 0);
4896 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
4899 [(set_attr "type" "lea")
4900 (set_attr "mode" "SI")])
4902 (define_insn_and_split "*lea_general_1_zext"
4903 [(set (match_operand:DI 0 "register_operand" "=r")
4905 (plus:SI (plus:SI (match_operand:SI 1 "index_register_operand" "l")
4906 (match_operand:SI 2 "register_operand" "r"))
4907 (match_operand:SI 3 "immediate_operand" "i"))))]
4910 "&& reload_completed"
4912 (zero_extend:DI (subreg:SI (plus:DI (plus:DI (match_dup 1)
4914 (match_dup 3)) 0)))]
4916 operands[1] = gen_lowpart (Pmode, operands[1]);
4917 operands[2] = gen_lowpart (Pmode, operands[2]);
4918 operands[3] = gen_lowpart (Pmode, operands[3]);
4920 [(set_attr "type" "lea")
4921 (set_attr "mode" "SI")])
4923 (define_insn_and_split "*lea_general_2"
4924 [(set (match_operand 0 "register_operand" "=r")
4925 (plus (mult (match_operand 1 "index_register_operand" "l")
4926 (match_operand 2 "const248_operand" "i"))
4927 (match_operand 3 "nonmemory_operand" "ri")))]
4928 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
4929 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
4930 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
4931 && GET_MODE (operands[0]) == GET_MODE (operands[1])
4932 && (GET_MODE (operands[0]) == GET_MODE (operands[3])
4933 || GET_MODE (operands[3]) == VOIDmode)"
4935 "&& reload_completed"
4939 operands[0] = gen_lowpart (SImode, operands[0]);
4940 operands[1] = gen_lowpart (Pmode, operands[1]);
4941 operands[3] = gen_lowpart (Pmode, operands[3]);
4942 pat = gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], operands[2]),
4944 if (Pmode != SImode)
4945 pat = gen_rtx_SUBREG (SImode, pat, 0);
4946 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
4949 [(set_attr "type" "lea")
4950 (set_attr "mode" "SI")])
4952 (define_insn_and_split "*lea_general_2_zext"
4953 [(set (match_operand:DI 0 "register_operand" "=r")
4955 (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "l")
4956 (match_operand:SI 2 "const248_operand" "n"))
4957 (match_operand:SI 3 "nonmemory_operand" "ri"))))]
4960 "&& reload_completed"
4962 (zero_extend:DI (subreg:SI (plus:DI (mult:DI (match_dup 1)
4964 (match_dup 3)) 0)))]
4966 operands[1] = gen_lowpart (Pmode, operands[1]);
4967 operands[3] = gen_lowpart (Pmode, operands[3]);
4969 [(set_attr "type" "lea")
4970 (set_attr "mode" "SI")])
4972 (define_insn_and_split "*lea_general_3"
4973 [(set (match_operand 0 "register_operand" "=r")
4974 (plus (plus (mult (match_operand 1 "index_register_operand" "l")
4975 (match_operand 2 "const248_operand" "i"))
4976 (match_operand 3 "register_operand" "r"))
4977 (match_operand 4 "immediate_operand" "i")))]
4978 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
4979 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
4980 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
4981 && GET_MODE (operands[0]) == GET_MODE (operands[1])
4982 && GET_MODE (operands[0]) == GET_MODE (operands[3])"
4984 "&& reload_completed"
4988 operands[0] = gen_lowpart (SImode, operands[0]);
4989 operands[1] = gen_lowpart (Pmode, operands[1]);
4990 operands[3] = gen_lowpart (Pmode, operands[3]);
4991 operands[4] = gen_lowpart (Pmode, operands[4]);
4992 pat = gen_rtx_PLUS (Pmode,
4993 gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1],
4997 if (Pmode != SImode)
4998 pat = gen_rtx_SUBREG (SImode, pat, 0);
4999 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5002 [(set_attr "type" "lea")
5003 (set_attr "mode" "SI")])
5005 (define_insn_and_split "*lea_general_3_zext"
5006 [(set (match_operand:DI 0 "register_operand" "=r")
5008 (plus:SI (plus:SI (mult:SI
5009 (match_operand:SI 1 "index_register_operand" "l")
5010 (match_operand:SI 2 "const248_operand" "n"))
5011 (match_operand:SI 3 "register_operand" "r"))
5012 (match_operand:SI 4 "immediate_operand" "i"))))]
5015 "&& reload_completed"
5017 (zero_extend:DI (subreg:SI (plus:DI (plus:DI (mult:DI (match_dup 1)
5020 (match_dup 4)) 0)))]
5022 operands[1] = gen_lowpart (Pmode, operands[1]);
5023 operands[3] = gen_lowpart (Pmode, operands[3]);
5024 operands[4] = gen_lowpart (Pmode, operands[4]);
5026 [(set_attr "type" "lea")
5027 (set_attr "mode" "SI")])
5029 (define_insn "*adddi_1_rex64"
5030 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r")
5031 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,r")
5032 (match_operand:DI 2 "x86_64_general_operand" "rme,re,le")))
5033 (clobber (reg:CC FLAGS_REG))]
5034 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5036 switch (get_attr_type (insn))
5039 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5040 return "lea{q}\t{%a2, %0|%0, %a2}";
5043 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5044 if (operands[2] == const1_rtx)
5045 return "inc{q}\t%0";
5048 gcc_assert (operands[2] == constm1_rtx);
5049 return "dec{q}\t%0";
5053 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5055 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5056 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5057 if (GET_CODE (operands[2]) == CONST_INT
5058 /* Avoid overflows. */
5059 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5060 && (INTVAL (operands[2]) == 128
5061 || (INTVAL (operands[2]) < 0
5062 && INTVAL (operands[2]) != -128)))
5064 operands[2] = GEN_INT (-INTVAL (operands[2]));
5065 return "sub{q}\t{%2, %0|%0, %2}";
5067 return "add{q}\t{%2, %0|%0, %2}";
5071 (cond [(eq_attr "alternative" "2")
5072 (const_string "lea")
5073 ; Current assemblers are broken and do not allow @GOTOFF in
5074 ; ought but a memory context.
5075 (match_operand:DI 2 "pic_symbolic_operand" "")
5076 (const_string "lea")
5077 (match_operand:DI 2 "incdec_operand" "")
5078 (const_string "incdec")
5080 (const_string "alu")))
5081 (set_attr "mode" "DI")])
5083 ;; Convert lea to the lea pattern to avoid flags dependency.
5085 [(set (match_operand:DI 0 "register_operand" "")
5086 (plus:DI (match_operand:DI 1 "register_operand" "")
5087 (match_operand:DI 2 "x86_64_nonmemory_operand" "")))
5088 (clobber (reg:CC FLAGS_REG))]
5089 "TARGET_64BIT && reload_completed
5090 && true_regnum (operands[0]) != true_regnum (operands[1])"
5092 (plus:DI (match_dup 1)
5096 (define_insn "*adddi_2_rex64"
5097 [(set (reg FLAGS_REG)
5099 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5100 (match_operand:DI 2 "x86_64_general_operand" "rme,re"))
5102 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
5103 (plus:DI (match_dup 1) (match_dup 2)))]
5104 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5105 && ix86_binary_operator_ok (PLUS, DImode, operands)
5106 /* Current assemblers are broken and do not allow @GOTOFF in
5107 ought but a memory context. */
5108 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5110 switch (get_attr_type (insn))
5113 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5114 if (operands[2] == const1_rtx)
5115 return "inc{q}\t%0";
5118 gcc_assert (operands[2] == constm1_rtx);
5119 return "dec{q}\t%0";
5123 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5124 /* ???? We ought to handle there the 32bit case too
5125 - do we need new constraint? */
5126 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5127 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5128 if (GET_CODE (operands[2]) == CONST_INT
5129 /* Avoid overflows. */
5130 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5131 && (INTVAL (operands[2]) == 128
5132 || (INTVAL (operands[2]) < 0
5133 && INTVAL (operands[2]) != -128)))
5135 operands[2] = GEN_INT (-INTVAL (operands[2]));
5136 return "sub{q}\t{%2, %0|%0, %2}";
5138 return "add{q}\t{%2, %0|%0, %2}";
5142 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5143 (const_string "incdec")
5144 (const_string "alu")))
5145 (set_attr "mode" "DI")])
5147 (define_insn "*adddi_3_rex64"
5148 [(set (reg FLAGS_REG)
5149 (compare (neg:DI (match_operand:DI 2 "x86_64_general_operand" "rme"))
5150 (match_operand:DI 1 "x86_64_general_operand" "%0")))
5151 (clobber (match_scratch:DI 0 "=r"))]
5153 && ix86_match_ccmode (insn, CCZmode)
5154 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5155 /* Current assemblers are broken and do not allow @GOTOFF in
5156 ought but a memory context. */
5157 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5159 switch (get_attr_type (insn))
5162 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5163 if (operands[2] == const1_rtx)
5164 return "inc{q}\t%0";
5167 gcc_assert (operands[2] == constm1_rtx);
5168 return "dec{q}\t%0";
5172 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5173 /* ???? We ought to handle there the 32bit case too
5174 - do we need new constraint? */
5175 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5176 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5177 if (GET_CODE (operands[2]) == CONST_INT
5178 /* Avoid overflows. */
5179 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5180 && (INTVAL (operands[2]) == 128
5181 || (INTVAL (operands[2]) < 0
5182 && INTVAL (operands[2]) != -128)))
5184 operands[2] = GEN_INT (-INTVAL (operands[2]));
5185 return "sub{q}\t{%2, %0|%0, %2}";
5187 return "add{q}\t{%2, %0|%0, %2}";
5191 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5192 (const_string "incdec")
5193 (const_string "alu")))
5194 (set_attr "mode" "DI")])
5196 ; For comparisons against 1, -1 and 128, we may generate better code
5197 ; by converting cmp to add, inc or dec as done by peephole2. This pattern
5198 ; is matched then. We can't accept general immediate, because for
5199 ; case of overflows, the result is messed up.
5200 ; This pattern also don't hold of 0x8000000000000000, since the value overflows
5202 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5203 ; only for comparisons not depending on it.
5204 (define_insn "*adddi_4_rex64"
5205 [(set (reg FLAGS_REG)
5206 (compare (match_operand:DI 1 "nonimmediate_operand" "0")
5207 (match_operand:DI 2 "x86_64_immediate_operand" "e")))
5208 (clobber (match_scratch:DI 0 "=rm"))]
5210 && ix86_match_ccmode (insn, CCGCmode)"
5212 switch (get_attr_type (insn))
5215 if (operands[2] == constm1_rtx)
5216 return "inc{q}\t%0";
5219 gcc_assert (operands[2] == const1_rtx);
5220 return "dec{q}\t%0";
5224 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5225 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5226 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5227 if ((INTVAL (operands[2]) == -128
5228 || (INTVAL (operands[2]) > 0
5229 && INTVAL (operands[2]) != 128))
5230 /* Avoid overflows. */
5231 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))))
5232 return "sub{q}\t{%2, %0|%0, %2}";
5233 operands[2] = GEN_INT (-INTVAL (operands[2]));
5234 return "add{q}\t{%2, %0|%0, %2}";
5238 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5239 (const_string "incdec")
5240 (const_string "alu")))
5241 (set_attr "mode" "DI")])
5243 (define_insn "*adddi_5_rex64"
5244 [(set (reg FLAGS_REG)
5246 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5247 (match_operand:DI 2 "x86_64_general_operand" "rme"))
5249 (clobber (match_scratch:DI 0 "=r"))]
5251 && ix86_match_ccmode (insn, CCGOCmode)
5252 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5253 /* Current assemblers are broken and do not allow @GOTOFF in
5254 ought but a memory context. */
5255 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5257 switch (get_attr_type (insn))
5260 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5261 if (operands[2] == const1_rtx)
5262 return "inc{q}\t%0";
5265 gcc_assert (operands[2] == constm1_rtx);
5266 return "dec{q}\t%0";
5270 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5271 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5272 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5273 if (GET_CODE (operands[2]) == CONST_INT
5274 /* Avoid overflows. */
5275 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5276 && (INTVAL (operands[2]) == 128
5277 || (INTVAL (operands[2]) < 0
5278 && INTVAL (operands[2]) != -128)))
5280 operands[2] = GEN_INT (-INTVAL (operands[2]));
5281 return "sub{q}\t{%2, %0|%0, %2}";
5283 return "add{q}\t{%2, %0|%0, %2}";
5287 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5288 (const_string "incdec")
5289 (const_string "alu")))
5290 (set_attr "mode" "DI")])
5293 (define_insn "*addsi_1"
5294 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,rm,r")
5295 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,r")
5296 (match_operand:SI 2 "general_operand" "rmni,rni,lni")))
5297 (clobber (reg:CC FLAGS_REG))]
5298 "ix86_binary_operator_ok (PLUS, SImode, operands)"
5300 switch (get_attr_type (insn))
5303 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5304 return "lea{l}\t{%a2, %0|%0, %a2}";
5307 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5308 if (operands[2] == const1_rtx)
5309 return "inc{l}\t%0";
5312 gcc_assert (operands[2] == constm1_rtx);
5313 return "dec{l}\t%0";
5317 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5319 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5320 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5321 if (GET_CODE (operands[2]) == CONST_INT
5322 && (INTVAL (operands[2]) == 128
5323 || (INTVAL (operands[2]) < 0
5324 && INTVAL (operands[2]) != -128)))
5326 operands[2] = GEN_INT (-INTVAL (operands[2]));
5327 return "sub{l}\t{%2, %0|%0, %2}";
5329 return "add{l}\t{%2, %0|%0, %2}";
5333 (cond [(eq_attr "alternative" "2")
5334 (const_string "lea")
5335 ; Current assemblers are broken and do not allow @GOTOFF in
5336 ; ought but a memory context.
5337 (match_operand:SI 2 "pic_symbolic_operand" "")
5338 (const_string "lea")
5339 (match_operand:SI 2 "incdec_operand" "")
5340 (const_string "incdec")
5342 (const_string "alu")))
5343 (set_attr "mode" "SI")])
5345 ;; Convert lea to the lea pattern to avoid flags dependency.
5347 [(set (match_operand 0 "register_operand" "")
5348 (plus (match_operand 1 "register_operand" "")
5349 (match_operand 2 "nonmemory_operand" "")))
5350 (clobber (reg:CC FLAGS_REG))]
5352 && true_regnum (operands[0]) != true_regnum (operands[1])"
5356 /* In -fPIC mode the constructs like (const (unspec [symbol_ref]))
5357 may confuse gen_lowpart. */
5358 if (GET_MODE (operands[0]) != Pmode)
5360 operands[1] = gen_lowpart (Pmode, operands[1]);
5361 operands[2] = gen_lowpart (Pmode, operands[2]);
5363 operands[0] = gen_lowpart (SImode, operands[0]);
5364 pat = gen_rtx_PLUS (Pmode, operands[1], operands[2]);
5365 if (Pmode != SImode)
5366 pat = gen_rtx_SUBREG (SImode, pat, 0);
5367 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5371 ;; It may seem that nonimmediate operand is proper one for operand 1.
5372 ;; The addsi_1 pattern allows nonimmediate operand at that place and
5373 ;; we take care in ix86_binary_operator_ok to not allow two memory
5374 ;; operands so proper swapping will be done in reload. This allow
5375 ;; patterns constructed from addsi_1 to match.
5376 (define_insn "addsi_1_zext"
5377 [(set (match_operand:DI 0 "register_operand" "=r,r")
5379 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r")
5380 (match_operand:SI 2 "general_operand" "rmni,lni"))))
5381 (clobber (reg:CC FLAGS_REG))]
5382 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5384 switch (get_attr_type (insn))
5387 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5388 return "lea{l}\t{%a2, %k0|%k0, %a2}";
5391 if (operands[2] == const1_rtx)
5392 return "inc{l}\t%k0";
5395 gcc_assert (operands[2] == constm1_rtx);
5396 return "dec{l}\t%k0";
5400 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5401 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5402 if (GET_CODE (operands[2]) == CONST_INT
5403 && (INTVAL (operands[2]) == 128
5404 || (INTVAL (operands[2]) < 0
5405 && INTVAL (operands[2]) != -128)))
5407 operands[2] = GEN_INT (-INTVAL (operands[2]));
5408 return "sub{l}\t{%2, %k0|%k0, %2}";
5410 return "add{l}\t{%2, %k0|%k0, %2}";
5414 (cond [(eq_attr "alternative" "1")
5415 (const_string "lea")
5416 ; Current assemblers are broken and do not allow @GOTOFF in
5417 ; ought but a memory context.
5418 (match_operand:SI 2 "pic_symbolic_operand" "")
5419 (const_string "lea")
5420 (match_operand:SI 2 "incdec_operand" "")
5421 (const_string "incdec")
5423 (const_string "alu")))
5424 (set_attr "mode" "SI")])
5426 ;; Convert lea to the lea pattern to avoid flags dependency.
5428 [(set (match_operand:DI 0 "register_operand" "")
5430 (plus:SI (match_operand:SI 1 "register_operand" "")
5431 (match_operand:SI 2 "nonmemory_operand" ""))))
5432 (clobber (reg:CC FLAGS_REG))]
5433 "TARGET_64BIT && reload_completed
5434 && true_regnum (operands[0]) != true_regnum (operands[1])"
5436 (zero_extend:DI (subreg:SI (plus:DI (match_dup 1) (match_dup 2)) 0)))]
5438 operands[1] = gen_lowpart (Pmode, operands[1]);
5439 operands[2] = gen_lowpart (Pmode, operands[2]);
5442 (define_insn "*addsi_2"
5443 [(set (reg FLAGS_REG)
5445 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
5446 (match_operand:SI 2 "general_operand" "rmni,rni"))
5448 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
5449 (plus:SI (match_dup 1) (match_dup 2)))]
5450 "ix86_match_ccmode (insn, CCGOCmode)
5451 && ix86_binary_operator_ok (PLUS, SImode, operands)
5452 /* Current assemblers are broken and do not allow @GOTOFF in
5453 ought but a memory context. */
5454 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5456 switch (get_attr_type (insn))
5459 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5460 if (operands[2] == const1_rtx)
5461 return "inc{l}\t%0";
5464 gcc_assert (operands[2] == constm1_rtx);
5465 return "dec{l}\t%0";
5469 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5470 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5471 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5472 if (GET_CODE (operands[2]) == CONST_INT
5473 && (INTVAL (operands[2]) == 128
5474 || (INTVAL (operands[2]) < 0
5475 && INTVAL (operands[2]) != -128)))
5477 operands[2] = GEN_INT (-INTVAL (operands[2]));
5478 return "sub{l}\t{%2, %0|%0, %2}";
5480 return "add{l}\t{%2, %0|%0, %2}";
5484 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5485 (const_string "incdec")
5486 (const_string "alu")))
5487 (set_attr "mode" "SI")])
5489 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5490 (define_insn "*addsi_2_zext"
5491 [(set (reg FLAGS_REG)
5493 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5494 (match_operand:SI 2 "general_operand" "rmni"))
5496 (set (match_operand:DI 0 "register_operand" "=r")
5497 (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5498 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5499 && ix86_binary_operator_ok (PLUS, SImode, operands)
5500 /* Current assemblers are broken and do not allow @GOTOFF in
5501 ought but a memory context. */
5502 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5504 switch (get_attr_type (insn))
5507 if (operands[2] == const1_rtx)
5508 return "inc{l}\t%k0";
5511 gcc_assert (operands[2] == constm1_rtx);
5512 return "dec{l}\t%k0";
5516 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5517 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5518 if (GET_CODE (operands[2]) == CONST_INT
5519 && (INTVAL (operands[2]) == 128
5520 || (INTVAL (operands[2]) < 0
5521 && INTVAL (operands[2]) != -128)))
5523 operands[2] = GEN_INT (-INTVAL (operands[2]));
5524 return "sub{l}\t{%2, %k0|%k0, %2}";
5526 return "add{l}\t{%2, %k0|%k0, %2}";
5530 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5531 (const_string "incdec")
5532 (const_string "alu")))
5533 (set_attr "mode" "SI")])
5535 (define_insn "*addsi_3"
5536 [(set (reg FLAGS_REG)
5537 (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5538 (match_operand:SI 1 "nonimmediate_operand" "%0")))
5539 (clobber (match_scratch:SI 0 "=r"))]
5540 "ix86_match_ccmode (insn, CCZmode)
5541 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5542 /* Current assemblers are broken and do not allow @GOTOFF in
5543 ought but a memory context. */
5544 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5546 switch (get_attr_type (insn))
5549 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5550 if (operands[2] == const1_rtx)
5551 return "inc{l}\t%0";
5554 gcc_assert (operands[2] == constm1_rtx);
5555 return "dec{l}\t%0";
5559 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5560 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5561 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5562 if (GET_CODE (operands[2]) == CONST_INT
5563 && (INTVAL (operands[2]) == 128
5564 || (INTVAL (operands[2]) < 0
5565 && INTVAL (operands[2]) != -128)))
5567 operands[2] = GEN_INT (-INTVAL (operands[2]));
5568 return "sub{l}\t{%2, %0|%0, %2}";
5570 return "add{l}\t{%2, %0|%0, %2}";
5574 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5575 (const_string "incdec")
5576 (const_string "alu")))
5577 (set_attr "mode" "SI")])
5579 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5580 (define_insn "*addsi_3_zext"
5581 [(set (reg FLAGS_REG)
5582 (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5583 (match_operand:SI 1 "nonimmediate_operand" "%0")))
5584 (set (match_operand:DI 0 "register_operand" "=r")
5585 (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5586 "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
5587 && ix86_binary_operator_ok (PLUS, SImode, operands)
5588 /* Current assemblers are broken and do not allow @GOTOFF in
5589 ought but a memory context. */
5590 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5592 switch (get_attr_type (insn))
5595 if (operands[2] == const1_rtx)
5596 return "inc{l}\t%k0";
5599 gcc_assert (operands[2] == constm1_rtx);
5600 return "dec{l}\t%k0";
5604 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5605 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5606 if (GET_CODE (operands[2]) == CONST_INT
5607 && (INTVAL (operands[2]) == 128
5608 || (INTVAL (operands[2]) < 0
5609 && INTVAL (operands[2]) != -128)))
5611 operands[2] = GEN_INT (-INTVAL (operands[2]));
5612 return "sub{l}\t{%2, %k0|%k0, %2}";
5614 return "add{l}\t{%2, %k0|%k0, %2}";
5618 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5619 (const_string "incdec")
5620 (const_string "alu")))
5621 (set_attr "mode" "SI")])
5623 ; For comparisons against 1, -1 and 128, we may generate better code
5624 ; by converting cmp to add, inc or dec as done by peephole2. This pattern
5625 ; is matched then. We can't accept general immediate, because for
5626 ; case of overflows, the result is messed up.
5627 ; This pattern also don't hold of 0x80000000, since the value overflows
5629 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5630 ; only for comparisons not depending on it.
5631 (define_insn "*addsi_4"
5632 [(set (reg FLAGS_REG)
5633 (compare (match_operand:SI 1 "nonimmediate_operand" "0")
5634 (match_operand:SI 2 "const_int_operand" "n")))
5635 (clobber (match_scratch:SI 0 "=rm"))]
5636 "ix86_match_ccmode (insn, CCGCmode)
5637 && (INTVAL (operands[2]) & 0xffffffff) != 0x80000000"
5639 switch (get_attr_type (insn))
5642 if (operands[2] == constm1_rtx)
5643 return "inc{l}\t%0";
5646 gcc_assert (operands[2] == const1_rtx);
5647 return "dec{l}\t%0";
5651 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5652 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5653 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5654 if ((INTVAL (operands[2]) == -128
5655 || (INTVAL (operands[2]) > 0
5656 && INTVAL (operands[2]) != 128)))
5657 return "sub{l}\t{%2, %0|%0, %2}";
5658 operands[2] = GEN_INT (-INTVAL (operands[2]));
5659 return "add{l}\t{%2, %0|%0, %2}";
5663 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5664 (const_string "incdec")
5665 (const_string "alu")))
5666 (set_attr "mode" "SI")])
5668 (define_insn "*addsi_5"
5669 [(set (reg FLAGS_REG)
5671 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5672 (match_operand:SI 2 "general_operand" "rmni"))
5674 (clobber (match_scratch:SI 0 "=r"))]
5675 "ix86_match_ccmode (insn, CCGOCmode)
5676 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5677 /* Current assemblers are broken and do not allow @GOTOFF in
5678 ought but a memory context. */
5679 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5681 switch (get_attr_type (insn))
5684 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5685 if (operands[2] == const1_rtx)
5686 return "inc{l}\t%0";
5689 gcc_assert (operands[2] == constm1_rtx);
5690 return "dec{l}\t%0";
5694 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5695 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5696 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5697 if (GET_CODE (operands[2]) == CONST_INT
5698 && (INTVAL (operands[2]) == 128
5699 || (INTVAL (operands[2]) < 0
5700 && INTVAL (operands[2]) != -128)))
5702 operands[2] = GEN_INT (-INTVAL (operands[2]));
5703 return "sub{l}\t{%2, %0|%0, %2}";
5705 return "add{l}\t{%2, %0|%0, %2}";
5709 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5710 (const_string "incdec")
5711 (const_string "alu")))
5712 (set_attr "mode" "SI")])
5714 (define_expand "addhi3"
5715 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
5716 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "")
5717 (match_operand:HI 2 "general_operand" "")))
5718 (clobber (reg:CC FLAGS_REG))])]
5719 "TARGET_HIMODE_MATH"
5720 "ix86_expand_binary_operator (PLUS, HImode, operands); DONE;")
5722 ;; %%% After Dave's SUBREG_BYTE stuff goes in, re-enable incb %ah
5723 ;; type optimizations enabled by define-splits. This is not important
5724 ;; for PII, and in fact harmful because of partial register stalls.
5726 (define_insn "*addhi_1_lea"
5727 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
5728 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r")
5729 (match_operand:HI 2 "general_operand" "ri,rm,lni")))
5730 (clobber (reg:CC FLAGS_REG))]
5731 "!TARGET_PARTIAL_REG_STALL
5732 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5734 switch (get_attr_type (insn))
5739 if (operands[2] == const1_rtx)
5740 return "inc{w}\t%0";
5743 gcc_assert (operands[2] == constm1_rtx);
5744 return "dec{w}\t%0";
5748 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5749 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5750 if (GET_CODE (operands[2]) == CONST_INT
5751 && (INTVAL (operands[2]) == 128
5752 || (INTVAL (operands[2]) < 0
5753 && INTVAL (operands[2]) != -128)))
5755 operands[2] = GEN_INT (-INTVAL (operands[2]));
5756 return "sub{w}\t{%2, %0|%0, %2}";
5758 return "add{w}\t{%2, %0|%0, %2}";
5762 (if_then_else (eq_attr "alternative" "2")
5763 (const_string "lea")
5764 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5765 (const_string "incdec")
5766 (const_string "alu"))))
5767 (set_attr "mode" "HI,HI,SI")])
5769 (define_insn "*addhi_1"
5770 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
5771 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
5772 (match_operand:HI 2 "general_operand" "ri,rm")))
5773 (clobber (reg:CC FLAGS_REG))]
5774 "TARGET_PARTIAL_REG_STALL
5775 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5777 switch (get_attr_type (insn))
5780 if (operands[2] == const1_rtx)
5781 return "inc{w}\t%0";
5784 gcc_assert (operands[2] == constm1_rtx);
5785 return "dec{w}\t%0";
5789 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5790 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5791 if (GET_CODE (operands[2]) == CONST_INT
5792 && (INTVAL (operands[2]) == 128
5793 || (INTVAL (operands[2]) < 0
5794 && INTVAL (operands[2]) != -128)))
5796 operands[2] = GEN_INT (-INTVAL (operands[2]));
5797 return "sub{w}\t{%2, %0|%0, %2}";
5799 return "add{w}\t{%2, %0|%0, %2}";
5803 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5804 (const_string "incdec")
5805 (const_string "alu")))
5806 (set_attr "mode" "HI")])
5808 (define_insn "*addhi_2"
5809 [(set (reg FLAGS_REG)
5811 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
5812 (match_operand:HI 2 "general_operand" "rmni,rni"))
5814 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
5815 (plus:HI (match_dup 1) (match_dup 2)))]
5816 "ix86_match_ccmode (insn, CCGOCmode)
5817 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5819 switch (get_attr_type (insn))
5822 if (operands[2] == const1_rtx)
5823 return "inc{w}\t%0";
5826 gcc_assert (operands[2] == constm1_rtx);
5827 return "dec{w}\t%0";
5831 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5832 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5833 if (GET_CODE (operands[2]) == CONST_INT
5834 && (INTVAL (operands[2]) == 128
5835 || (INTVAL (operands[2]) < 0
5836 && INTVAL (operands[2]) != -128)))
5838 operands[2] = GEN_INT (-INTVAL (operands[2]));
5839 return "sub{w}\t{%2, %0|%0, %2}";
5841 return "add{w}\t{%2, %0|%0, %2}";
5845 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5846 (const_string "incdec")
5847 (const_string "alu")))
5848 (set_attr "mode" "HI")])
5850 (define_insn "*addhi_3"
5851 [(set (reg FLAGS_REG)
5852 (compare (neg:HI (match_operand:HI 2 "general_operand" "rmni"))
5853 (match_operand:HI 1 "nonimmediate_operand" "%0")))
5854 (clobber (match_scratch:HI 0 "=r"))]
5855 "ix86_match_ccmode (insn, CCZmode)
5856 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5858 switch (get_attr_type (insn))
5861 if (operands[2] == const1_rtx)
5862 return "inc{w}\t%0";
5865 gcc_assert (operands[2] == constm1_rtx);
5866 return "dec{w}\t%0";
5870 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5871 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5872 if (GET_CODE (operands[2]) == CONST_INT
5873 && (INTVAL (operands[2]) == 128
5874 || (INTVAL (operands[2]) < 0
5875 && INTVAL (operands[2]) != -128)))
5877 operands[2] = GEN_INT (-INTVAL (operands[2]));
5878 return "sub{w}\t{%2, %0|%0, %2}";
5880 return "add{w}\t{%2, %0|%0, %2}";
5884 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5885 (const_string "incdec")
5886 (const_string "alu")))
5887 (set_attr "mode" "HI")])
5889 ; See comments above addsi_4 for details.
5890 (define_insn "*addhi_4"
5891 [(set (reg FLAGS_REG)
5892 (compare (match_operand:HI 1 "nonimmediate_operand" "0")
5893 (match_operand:HI 2 "const_int_operand" "n")))
5894 (clobber (match_scratch:HI 0 "=rm"))]
5895 "ix86_match_ccmode (insn, CCGCmode)
5896 && (INTVAL (operands[2]) & 0xffff) != 0x8000"
5898 switch (get_attr_type (insn))
5901 if (operands[2] == constm1_rtx)
5902 return "inc{w}\t%0";
5905 gcc_assert (operands[2] == const1_rtx);
5906 return "dec{w}\t%0";
5910 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5911 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5912 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5913 if ((INTVAL (operands[2]) == -128
5914 || (INTVAL (operands[2]) > 0
5915 && INTVAL (operands[2]) != 128)))
5916 return "sub{w}\t{%2, %0|%0, %2}";
5917 operands[2] = GEN_INT (-INTVAL (operands[2]));
5918 return "add{w}\t{%2, %0|%0, %2}";
5922 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5923 (const_string "incdec")
5924 (const_string "alu")))
5925 (set_attr "mode" "SI")])
5928 (define_insn "*addhi_5"
5929 [(set (reg FLAGS_REG)
5931 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
5932 (match_operand:HI 2 "general_operand" "rmni"))
5934 (clobber (match_scratch:HI 0 "=r"))]
5935 "ix86_match_ccmode (insn, CCGOCmode)
5936 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5938 switch (get_attr_type (insn))
5941 if (operands[2] == const1_rtx)
5942 return "inc{w}\t%0";
5945 gcc_assert (operands[2] == constm1_rtx);
5946 return "dec{w}\t%0";
5950 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5951 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5952 if (GET_CODE (operands[2]) == CONST_INT
5953 && (INTVAL (operands[2]) == 128
5954 || (INTVAL (operands[2]) < 0
5955 && INTVAL (operands[2]) != -128)))
5957 operands[2] = GEN_INT (-INTVAL (operands[2]));
5958 return "sub{w}\t{%2, %0|%0, %2}";
5960 return "add{w}\t{%2, %0|%0, %2}";
5964 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5965 (const_string "incdec")
5966 (const_string "alu")))
5967 (set_attr "mode" "HI")])
5969 (define_expand "addqi3"
5970 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
5971 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "")
5972 (match_operand:QI 2 "general_operand" "")))
5973 (clobber (reg:CC FLAGS_REG))])]
5974 "TARGET_QIMODE_MATH"
5975 "ix86_expand_binary_operator (PLUS, QImode, operands); DONE;")
5977 ;; %%% Potential partial reg stall on alternative 2. What to do?
5978 (define_insn "*addqi_1_lea"
5979 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r,r")
5980 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,r")
5981 (match_operand:QI 2 "general_operand" "qn,qmn,rn,ln")))
5982 (clobber (reg:CC FLAGS_REG))]
5983 "!TARGET_PARTIAL_REG_STALL
5984 && ix86_binary_operator_ok (PLUS, QImode, operands)"
5986 int widen = (which_alternative == 2);
5987 switch (get_attr_type (insn))
5992 if (operands[2] == const1_rtx)
5993 return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
5996 gcc_assert (operands[2] == constm1_rtx);
5997 return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6001 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6002 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6003 if (GET_CODE (operands[2]) == CONST_INT
6004 && (INTVAL (operands[2]) == 128
6005 || (INTVAL (operands[2]) < 0
6006 && INTVAL (operands[2]) != -128)))
6008 operands[2] = GEN_INT (-INTVAL (operands[2]));
6010 return "sub{l}\t{%2, %k0|%k0, %2}";
6012 return "sub{b}\t{%2, %0|%0, %2}";
6015 return "add{l}\t{%k2, %k0|%k0, %k2}";
6017 return "add{b}\t{%2, %0|%0, %2}";
6021 (if_then_else (eq_attr "alternative" "3")
6022 (const_string "lea")
6023 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6024 (const_string "incdec")
6025 (const_string "alu"))))
6026 (set_attr "mode" "QI,QI,SI,SI")])
6028 (define_insn "*addqi_1"
6029 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
6030 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
6031 (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
6032 (clobber (reg:CC FLAGS_REG))]
6033 "TARGET_PARTIAL_REG_STALL
6034 && ix86_binary_operator_ok (PLUS, QImode, operands)"
6036 int widen = (which_alternative == 2);
6037 switch (get_attr_type (insn))
6040 if (operands[2] == const1_rtx)
6041 return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6044 gcc_assert (operands[2] == constm1_rtx);
6045 return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6049 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6050 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6051 if (GET_CODE (operands[2]) == CONST_INT
6052 && (INTVAL (operands[2]) == 128
6053 || (INTVAL (operands[2]) < 0
6054 && INTVAL (operands[2]) != -128)))
6056 operands[2] = GEN_INT (-INTVAL (operands[2]));
6058 return "sub{l}\t{%2, %k0|%k0, %2}";
6060 return "sub{b}\t{%2, %0|%0, %2}";
6063 return "add{l}\t{%k2, %k0|%k0, %k2}";
6065 return "add{b}\t{%2, %0|%0, %2}";
6069 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6070 (const_string "incdec")
6071 (const_string "alu")))
6072 (set_attr "mode" "QI,QI,SI")])
6074 (define_insn "*addqi_1_slp"
6075 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6076 (plus:QI (match_dup 0)
6077 (match_operand:QI 1 "general_operand" "qn,qnm")))
6078 (clobber (reg:CC FLAGS_REG))]
6079 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6080 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
6082 switch (get_attr_type (insn))
6085 if (operands[1] == const1_rtx)
6086 return "inc{b}\t%0";
6089 gcc_assert (operands[1] == constm1_rtx);
6090 return "dec{b}\t%0";
6094 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. */
6095 if (GET_CODE (operands[1]) == CONST_INT
6096 && INTVAL (operands[1]) < 0)
6098 operands[1] = GEN_INT (-INTVAL (operands[1]));
6099 return "sub{b}\t{%1, %0|%0, %1}";
6101 return "add{b}\t{%1, %0|%0, %1}";
6105 (if_then_else (match_operand:QI 1 "incdec_operand" "")
6106 (const_string "incdec")
6107 (const_string "alu1")))
6108 (set (attr "memory")
6109 (if_then_else (match_operand 1 "memory_operand" "")
6110 (const_string "load")
6111 (const_string "none")))
6112 (set_attr "mode" "QI")])
6114 (define_insn "*addqi_2"
6115 [(set (reg FLAGS_REG)
6117 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
6118 (match_operand:QI 2 "general_operand" "qmni,qni"))
6120 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
6121 (plus:QI (match_dup 1) (match_dup 2)))]
6122 "ix86_match_ccmode (insn, CCGOCmode)
6123 && ix86_binary_operator_ok (PLUS, QImode, operands)"
6125 switch (get_attr_type (insn))
6128 if (operands[2] == const1_rtx)
6129 return "inc{b}\t%0";
6132 gcc_assert (operands[2] == constm1_rtx
6133 || (GET_CODE (operands[2]) == CONST_INT
6134 && INTVAL (operands[2]) == 255));
6135 return "dec{b}\t%0";
6139 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
6140 if (GET_CODE (operands[2]) == CONST_INT
6141 && INTVAL (operands[2]) < 0)
6143 operands[2] = GEN_INT (-INTVAL (operands[2]));
6144 return "sub{b}\t{%2, %0|%0, %2}";
6146 return "add{b}\t{%2, %0|%0, %2}";
6150 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6151 (const_string "incdec")
6152 (const_string "alu")))
6153 (set_attr "mode" "QI")])
6155 (define_insn "*addqi_3"
6156 [(set (reg FLAGS_REG)
6157 (compare (neg:QI (match_operand:QI 2 "general_operand" "qmni"))
6158 (match_operand:QI 1 "nonimmediate_operand" "%0")))
6159 (clobber (match_scratch:QI 0 "=q"))]
6160 "ix86_match_ccmode (insn, CCZmode)
6161 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6163 switch (get_attr_type (insn))
6166 if (operands[2] == const1_rtx)
6167 return "inc{b}\t%0";
6170 gcc_assert (operands[2] == constm1_rtx
6171 || (GET_CODE (operands[2]) == CONST_INT
6172 && INTVAL (operands[2]) == 255));
6173 return "dec{b}\t%0";
6177 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
6178 if (GET_CODE (operands[2]) == CONST_INT
6179 && INTVAL (operands[2]) < 0)
6181 operands[2] = GEN_INT (-INTVAL (operands[2]));
6182 return "sub{b}\t{%2, %0|%0, %2}";
6184 return "add{b}\t{%2, %0|%0, %2}";
6188 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6189 (const_string "incdec")
6190 (const_string "alu")))
6191 (set_attr "mode" "QI")])
6193 ; See comments above addsi_4 for details.
6194 (define_insn "*addqi_4"
6195 [(set (reg FLAGS_REG)
6196 (compare (match_operand:QI 1 "nonimmediate_operand" "0")
6197 (match_operand:QI 2 "const_int_operand" "n")))
6198 (clobber (match_scratch:QI 0 "=qm"))]
6199 "ix86_match_ccmode (insn, CCGCmode)
6200 && (INTVAL (operands[2]) & 0xff) != 0x80"
6202 switch (get_attr_type (insn))
6205 if (operands[2] == constm1_rtx
6206 || (GET_CODE (operands[2]) == CONST_INT
6207 && INTVAL (operands[2]) == 255))
6208 return "inc{b}\t%0";
6211 gcc_assert (operands[2] == const1_rtx);
6212 return "dec{b}\t%0";
6216 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6217 if (INTVAL (operands[2]) < 0)
6219 operands[2] = GEN_INT (-INTVAL (operands[2]));
6220 return "add{b}\t{%2, %0|%0, %2}";
6222 return "sub{b}\t{%2, %0|%0, %2}";
6226 (if_then_else (match_operand:HI 2 "incdec_operand" "")
6227 (const_string "incdec")
6228 (const_string "alu")))
6229 (set_attr "mode" "QI")])
6232 (define_insn "*addqi_5"
6233 [(set (reg FLAGS_REG)
6235 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6236 (match_operand:QI 2 "general_operand" "qmni"))
6238 (clobber (match_scratch:QI 0 "=q"))]
6239 "ix86_match_ccmode (insn, CCGOCmode)
6240 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6242 switch (get_attr_type (insn))
6245 if (operands[2] == const1_rtx)
6246 return "inc{b}\t%0";
6249 gcc_assert (operands[2] == constm1_rtx
6250 || (GET_CODE (operands[2]) == CONST_INT
6251 && INTVAL (operands[2]) == 255));
6252 return "dec{b}\t%0";
6256 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
6257 if (GET_CODE (operands[2]) == CONST_INT
6258 && INTVAL (operands[2]) < 0)
6260 operands[2] = GEN_INT (-INTVAL (operands[2]));
6261 return "sub{b}\t{%2, %0|%0, %2}";
6263 return "add{b}\t{%2, %0|%0, %2}";
6267 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6268 (const_string "incdec")
6269 (const_string "alu")))
6270 (set_attr "mode" "QI")])
6273 (define_insn "addqi_ext_1"
6274 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6279 (match_operand 1 "ext_register_operand" "0")
6282 (match_operand:QI 2 "general_operand" "Qmn")))
6283 (clobber (reg:CC FLAGS_REG))]
6286 switch (get_attr_type (insn))
6289 if (operands[2] == const1_rtx)
6290 return "inc{b}\t%h0";
6293 gcc_assert (operands[2] == constm1_rtx
6294 || (GET_CODE (operands[2]) == CONST_INT
6295 && INTVAL (operands[2]) == 255));
6296 return "dec{b}\t%h0";
6300 return "add{b}\t{%2, %h0|%h0, %2}";
6304 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6305 (const_string "incdec")
6306 (const_string "alu")))
6307 (set_attr "mode" "QI")])
6309 (define_insn "*addqi_ext_1_rex64"
6310 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6315 (match_operand 1 "ext_register_operand" "0")
6318 (match_operand:QI 2 "nonmemory_operand" "Qn")))
6319 (clobber (reg:CC FLAGS_REG))]
6322 switch (get_attr_type (insn))
6325 if (operands[2] == const1_rtx)
6326 return "inc{b}\t%h0";
6329 gcc_assert (operands[2] == constm1_rtx
6330 || (GET_CODE (operands[2]) == CONST_INT
6331 && INTVAL (operands[2]) == 255));
6332 return "dec{b}\t%h0";
6336 return "add{b}\t{%2, %h0|%h0, %2}";
6340 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6341 (const_string "incdec")
6342 (const_string "alu")))
6343 (set_attr "mode" "QI")])
6345 (define_insn "*addqi_ext_2"
6346 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6351 (match_operand 1 "ext_register_operand" "%0")
6355 (match_operand 2 "ext_register_operand" "Q")
6358 (clobber (reg:CC FLAGS_REG))]
6360 "add{b}\t{%h2, %h0|%h0, %h2}"
6361 [(set_attr "type" "alu")
6362 (set_attr "mode" "QI")])
6364 ;; The patterns that match these are at the end of this file.
6366 (define_expand "addxf3"
6367 [(set (match_operand:XF 0 "register_operand" "")
6368 (plus:XF (match_operand:XF 1 "register_operand" "")
6369 (match_operand:XF 2 "register_operand" "")))]
6373 (define_expand "adddf3"
6374 [(set (match_operand:DF 0 "register_operand" "")
6375 (plus:DF (match_operand:DF 1 "register_operand" "")
6376 (match_operand:DF 2 "nonimmediate_operand" "")))]
6377 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
6380 (define_expand "addsf3"
6381 [(set (match_operand:SF 0 "register_operand" "")
6382 (plus:SF (match_operand:SF 1 "register_operand" "")
6383 (match_operand:SF 2 "nonimmediate_operand" "")))]
6384 "TARGET_80387 || TARGET_SSE_MATH"
6387 ;; Subtract instructions
6389 ;; %%% splits for subsidi3
6391 (define_expand "subdi3"
6392 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
6393 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6394 (match_operand:DI 2 "x86_64_general_operand" "")))
6395 (clobber (reg:CC FLAGS_REG))])]
6397 "ix86_expand_binary_operator (MINUS, DImode, operands); DONE;")
6399 (define_insn "*subdi3_1"
6400 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
6401 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6402 (match_operand:DI 2 "general_operand" "roiF,riF")))
6403 (clobber (reg:CC FLAGS_REG))]
6404 "!TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6408 [(set (match_operand:DI 0 "nonimmediate_operand" "")
6409 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6410 (match_operand:DI 2 "general_operand" "")))
6411 (clobber (reg:CC FLAGS_REG))]
6412 "!TARGET_64BIT && reload_completed"
6413 [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
6414 (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 2)))])
6415 (parallel [(set (match_dup 3)
6416 (minus:SI (match_dup 4)
6417 (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
6419 (clobber (reg:CC FLAGS_REG))])]
6420 "split_di (operands+0, 1, operands+0, operands+3);
6421 split_di (operands+1, 1, operands+1, operands+4);
6422 split_di (operands+2, 1, operands+2, operands+5);")
6424 (define_insn "subdi3_carry_rex64"
6425 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6426 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6427 (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
6428 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))))
6429 (clobber (reg:CC FLAGS_REG))]
6430 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6431 "sbb{q}\t{%2, %0|%0, %2}"
6432 [(set_attr "type" "alu")
6433 (set_attr "pent_pair" "pu")
6434 (set_attr "mode" "DI")])
6436 (define_insn "*subdi_1_rex64"
6437 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6438 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6439 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6440 (clobber (reg:CC FLAGS_REG))]
6441 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6442 "sub{q}\t{%2, %0|%0, %2}"
6443 [(set_attr "type" "alu")
6444 (set_attr "mode" "DI")])
6446 (define_insn "*subdi_2_rex64"
6447 [(set (reg FLAGS_REG)
6449 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6450 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))
6452 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6453 (minus:DI (match_dup 1) (match_dup 2)))]
6454 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6455 && ix86_binary_operator_ok (MINUS, DImode, operands)"
6456 "sub{q}\t{%2, %0|%0, %2}"
6457 [(set_attr "type" "alu")
6458 (set_attr "mode" "DI")])
6460 (define_insn "*subdi_3_rex63"
6461 [(set (reg FLAGS_REG)
6462 (compare (match_operand:DI 1 "nonimmediate_operand" "0,0")
6463 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6464 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6465 (minus:DI (match_dup 1) (match_dup 2)))]
6466 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6467 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6468 "sub{q}\t{%2, %0|%0, %2}"
6469 [(set_attr "type" "alu")
6470 (set_attr "mode" "DI")])
6472 (define_insn "subqi3_carry"
6473 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6474 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6475 (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
6476 (match_operand:QI 2 "general_operand" "qi,qm"))))
6477 (clobber (reg:CC FLAGS_REG))]
6478 "ix86_binary_operator_ok (MINUS, QImode, operands)"
6479 "sbb{b}\t{%2, %0|%0, %2}"
6480 [(set_attr "type" "alu")
6481 (set_attr "pent_pair" "pu")
6482 (set_attr "mode" "QI")])
6484 (define_insn "subhi3_carry"
6485 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6486 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6487 (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
6488 (match_operand:HI 2 "general_operand" "ri,rm"))))
6489 (clobber (reg:CC FLAGS_REG))]
6490 "ix86_binary_operator_ok (MINUS, HImode, operands)"
6491 "sbb{w}\t{%2, %0|%0, %2}"
6492 [(set_attr "type" "alu")
6493 (set_attr "pent_pair" "pu")
6494 (set_attr "mode" "HI")])
6496 (define_insn "subsi3_carry"
6497 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6498 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6499 (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6500 (match_operand:SI 2 "general_operand" "ri,rm"))))
6501 (clobber (reg:CC FLAGS_REG))]
6502 "ix86_binary_operator_ok (MINUS, SImode, operands)"
6503 "sbb{l}\t{%2, %0|%0, %2}"
6504 [(set_attr "type" "alu")
6505 (set_attr "pent_pair" "pu")
6506 (set_attr "mode" "SI")])
6508 (define_insn "subsi3_carry_zext"
6509 [(set (match_operand:DI 0 "register_operand" "=rm,r")
6511 (minus:SI (match_operand:SI 1 "register_operand" "0,0")
6512 (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6513 (match_operand:SI 2 "general_operand" "ri,rm")))))
6514 (clobber (reg:CC FLAGS_REG))]
6515 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6516 "sbb{l}\t{%2, %k0|%k0, %2}"
6517 [(set_attr "type" "alu")
6518 (set_attr "pent_pair" "pu")
6519 (set_attr "mode" "SI")])
6521 (define_expand "subsi3"
6522 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
6523 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "")
6524 (match_operand:SI 2 "general_operand" "")))
6525 (clobber (reg:CC FLAGS_REG))])]
6527 "ix86_expand_binary_operator (MINUS, SImode, operands); DONE;")
6529 (define_insn "*subsi_1"
6530 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6531 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6532 (match_operand:SI 2 "general_operand" "ri,rm")))
6533 (clobber (reg:CC FLAGS_REG))]
6534 "ix86_binary_operator_ok (MINUS, SImode, operands)"
6535 "sub{l}\t{%2, %0|%0, %2}"
6536 [(set_attr "type" "alu")
6537 (set_attr "mode" "SI")])
6539 (define_insn "*subsi_1_zext"
6540 [(set (match_operand:DI 0 "register_operand" "=r")
6542 (minus:SI (match_operand:SI 1 "register_operand" "0")
6543 (match_operand:SI 2 "general_operand" "rim"))))
6544 (clobber (reg:CC FLAGS_REG))]
6545 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6546 "sub{l}\t{%2, %k0|%k0, %2}"
6547 [(set_attr "type" "alu")
6548 (set_attr "mode" "SI")])
6550 (define_insn "*subsi_2"
6551 [(set (reg FLAGS_REG)
6553 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6554 (match_operand:SI 2 "general_operand" "ri,rm"))
6556 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6557 (minus:SI (match_dup 1) (match_dup 2)))]
6558 "ix86_match_ccmode (insn, CCGOCmode)
6559 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6560 "sub{l}\t{%2, %0|%0, %2}"
6561 [(set_attr "type" "alu")
6562 (set_attr "mode" "SI")])
6564 (define_insn "*subsi_2_zext"
6565 [(set (reg FLAGS_REG)
6567 (minus:SI (match_operand:SI 1 "register_operand" "0")
6568 (match_operand:SI 2 "general_operand" "rim"))
6570 (set (match_operand:DI 0 "register_operand" "=r")
6572 (minus:SI (match_dup 1)
6574 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6575 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6576 "sub{l}\t{%2, %k0|%k0, %2}"
6577 [(set_attr "type" "alu")
6578 (set_attr "mode" "SI")])
6580 (define_insn "*subsi_3"
6581 [(set (reg FLAGS_REG)
6582 (compare (match_operand:SI 1 "nonimmediate_operand" "0,0")
6583 (match_operand:SI 2 "general_operand" "ri,rm")))
6584 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6585 (minus:SI (match_dup 1) (match_dup 2)))]
6586 "ix86_match_ccmode (insn, CCmode)
6587 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6588 "sub{l}\t{%2, %0|%0, %2}"
6589 [(set_attr "type" "alu")
6590 (set_attr "mode" "SI")])
6592 (define_insn "*subsi_3_zext"
6593 [(set (reg FLAGS_REG)
6594 (compare (match_operand:SI 1 "register_operand" "0")
6595 (match_operand:SI 2 "general_operand" "rim")))
6596 (set (match_operand:DI 0 "register_operand" "=r")
6598 (minus:SI (match_dup 1)
6600 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6601 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6602 "sub{q}\t{%2, %0|%0, %2}"
6603 [(set_attr "type" "alu")
6604 (set_attr "mode" "DI")])
6606 (define_expand "subhi3"
6607 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
6608 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "")
6609 (match_operand:HI 2 "general_operand" "")))
6610 (clobber (reg:CC FLAGS_REG))])]
6611 "TARGET_HIMODE_MATH"
6612 "ix86_expand_binary_operator (MINUS, HImode, operands); DONE;")
6614 (define_insn "*subhi_1"
6615 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6616 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6617 (match_operand:HI 2 "general_operand" "ri,rm")))
6618 (clobber (reg:CC FLAGS_REG))]
6619 "ix86_binary_operator_ok (MINUS, HImode, operands)"
6620 "sub{w}\t{%2, %0|%0, %2}"
6621 [(set_attr "type" "alu")
6622 (set_attr "mode" "HI")])
6624 (define_insn "*subhi_2"
6625 [(set (reg FLAGS_REG)
6627 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6628 (match_operand:HI 2 "general_operand" "ri,rm"))
6630 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6631 (minus:HI (match_dup 1) (match_dup 2)))]
6632 "ix86_match_ccmode (insn, CCGOCmode)
6633 && ix86_binary_operator_ok (MINUS, HImode, operands)"
6634 "sub{w}\t{%2, %0|%0, %2}"
6635 [(set_attr "type" "alu")
6636 (set_attr "mode" "HI")])
6638 (define_insn "*subhi_3"
6639 [(set (reg FLAGS_REG)
6640 (compare (match_operand:HI 1 "nonimmediate_operand" "0,0")
6641 (match_operand:HI 2 "general_operand" "ri,rm")))
6642 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6643 (minus:HI (match_dup 1) (match_dup 2)))]
6644 "ix86_match_ccmode (insn, CCmode)
6645 && ix86_binary_operator_ok (MINUS, HImode, operands)"
6646 "sub{w}\t{%2, %0|%0, %2}"
6647 [(set_attr "type" "alu")
6648 (set_attr "mode" "HI")])
6650 (define_expand "subqi3"
6651 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6652 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6653 (match_operand:QI 2 "general_operand" "")))
6654 (clobber (reg:CC FLAGS_REG))])]
6655 "TARGET_QIMODE_MATH"
6656 "ix86_expand_binary_operator (MINUS, QImode, operands); DONE;")
6658 (define_insn "*subqi_1"
6659 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6660 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6661 (match_operand:QI 2 "general_operand" "qn,qmn")))
6662 (clobber (reg:CC FLAGS_REG))]
6663 "ix86_binary_operator_ok (MINUS, QImode, operands)"
6664 "sub{b}\t{%2, %0|%0, %2}"
6665 [(set_attr "type" "alu")
6666 (set_attr "mode" "QI")])
6668 (define_insn "*subqi_1_slp"
6669 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6670 (minus:QI (match_dup 0)
6671 (match_operand:QI 1 "general_operand" "qn,qmn")))
6672 (clobber (reg:CC FLAGS_REG))]
6673 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6674 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
6675 "sub{b}\t{%1, %0|%0, %1}"
6676 [(set_attr "type" "alu1")
6677 (set_attr "mode" "QI")])
6679 (define_insn "*subqi_2"
6680 [(set (reg FLAGS_REG)
6682 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6683 (match_operand:QI 2 "general_operand" "qi,qm"))
6685 (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6686 (minus:HI (match_dup 1) (match_dup 2)))]
6687 "ix86_match_ccmode (insn, CCGOCmode)
6688 && ix86_binary_operator_ok (MINUS, QImode, operands)"
6689 "sub{b}\t{%2, %0|%0, %2}"
6690 [(set_attr "type" "alu")
6691 (set_attr "mode" "QI")])
6693 (define_insn "*subqi_3"
6694 [(set (reg FLAGS_REG)
6695 (compare (match_operand:QI 1 "nonimmediate_operand" "0,0")
6696 (match_operand:QI 2 "general_operand" "qi,qm")))
6697 (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6698 (minus:HI (match_dup 1) (match_dup 2)))]
6699 "ix86_match_ccmode (insn, CCmode)
6700 && ix86_binary_operator_ok (MINUS, QImode, operands)"
6701 "sub{b}\t{%2, %0|%0, %2}"
6702 [(set_attr "type" "alu")
6703 (set_attr "mode" "QI")])
6705 ;; The patterns that match these are at the end of this file.
6707 (define_expand "subxf3"
6708 [(set (match_operand:XF 0 "register_operand" "")
6709 (minus:XF (match_operand:XF 1 "register_operand" "")
6710 (match_operand:XF 2 "register_operand" "")))]
6714 (define_expand "subdf3"
6715 [(set (match_operand:DF 0 "register_operand" "")
6716 (minus:DF (match_operand:DF 1 "register_operand" "")
6717 (match_operand:DF 2 "nonimmediate_operand" "")))]
6718 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
6721 (define_expand "subsf3"
6722 [(set (match_operand:SF 0 "register_operand" "")
6723 (minus:SF (match_operand:SF 1 "register_operand" "")
6724 (match_operand:SF 2 "nonimmediate_operand" "")))]
6725 "TARGET_80387 || TARGET_SSE_MATH"
6728 ;; Multiply instructions
6730 (define_expand "muldi3"
6731 [(parallel [(set (match_operand:DI 0 "register_operand" "")
6732 (mult:DI (match_operand:DI 1 "register_operand" "")
6733 (match_operand:DI 2 "x86_64_general_operand" "")))
6734 (clobber (reg:CC FLAGS_REG))])]
6738 (define_insn "*muldi3_1_rex64"
6739 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6740 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%rm,rm,0")
6741 (match_operand:DI 2 "x86_64_general_operand" "K,e,mr")))
6742 (clobber (reg:CC FLAGS_REG))]
6744 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6746 imul{q}\t{%2, %1, %0|%0, %1, %2}
6747 imul{q}\t{%2, %1, %0|%0, %1, %2}
6748 imul{q}\t{%2, %0|%0, %2}"
6749 [(set_attr "type" "imul")
6750 (set_attr "prefix_0f" "0,0,1")
6751 (set (attr "athlon_decode")
6752 (cond [(eq_attr "cpu" "athlon")
6753 (const_string "vector")
6754 (eq_attr "alternative" "1")
6755 (const_string "vector")
6756 (and (eq_attr "alternative" "2")
6757 (match_operand 1 "memory_operand" ""))
6758 (const_string "vector")]
6759 (const_string "direct")))
6760 (set_attr "mode" "DI")])
6762 (define_expand "mulsi3"
6763 [(parallel [(set (match_operand:SI 0 "register_operand" "")
6764 (mult:SI (match_operand:SI 1 "register_operand" "")
6765 (match_operand:SI 2 "general_operand" "")))
6766 (clobber (reg:CC FLAGS_REG))])]
6770 (define_insn "*mulsi3_1"
6771 [(set (match_operand:SI 0 "register_operand" "=r,r,r")
6772 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6773 (match_operand:SI 2 "general_operand" "K,i,mr")))
6774 (clobber (reg:CC FLAGS_REG))]
6775 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6777 imul{l}\t{%2, %1, %0|%0, %1, %2}
6778 imul{l}\t{%2, %1, %0|%0, %1, %2}
6779 imul{l}\t{%2, %0|%0, %2}"
6780 [(set_attr "type" "imul")
6781 (set_attr "prefix_0f" "0,0,1")
6782 (set (attr "athlon_decode")
6783 (cond [(eq_attr "cpu" "athlon")
6784 (const_string "vector")
6785 (eq_attr "alternative" "1")
6786 (const_string "vector")
6787 (and (eq_attr "alternative" "2")
6788 (match_operand 1 "memory_operand" ""))
6789 (const_string "vector")]
6790 (const_string "direct")))
6791 (set_attr "mode" "SI")])
6793 (define_insn "*mulsi3_1_zext"
6794 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6796 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6797 (match_operand:SI 2 "general_operand" "K,i,mr"))))
6798 (clobber (reg:CC FLAGS_REG))]
6800 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6802 imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6803 imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6804 imul{l}\t{%2, %k0|%k0, %2}"
6805 [(set_attr "type" "imul")
6806 (set_attr "prefix_0f" "0,0,1")
6807 (set (attr "athlon_decode")
6808 (cond [(eq_attr "cpu" "athlon")
6809 (const_string "vector")
6810 (eq_attr "alternative" "1")
6811 (const_string "vector")
6812 (and (eq_attr "alternative" "2")
6813 (match_operand 1 "memory_operand" ""))
6814 (const_string "vector")]
6815 (const_string "direct")))
6816 (set_attr "mode" "SI")])
6818 (define_expand "mulhi3"
6819 [(parallel [(set (match_operand:HI 0 "register_operand" "")
6820 (mult:HI (match_operand:HI 1 "register_operand" "")
6821 (match_operand:HI 2 "general_operand" "")))
6822 (clobber (reg:CC FLAGS_REG))])]
6823 "TARGET_HIMODE_MATH"
6826 (define_insn "*mulhi3_1"
6827 [(set (match_operand:HI 0 "register_operand" "=r,r,r")
6828 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
6829 (match_operand:HI 2 "general_operand" "K,i,mr")))
6830 (clobber (reg:CC FLAGS_REG))]
6831 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6833 imul{w}\t{%2, %1, %0|%0, %1, %2}
6834 imul{w}\t{%2, %1, %0|%0, %1, %2}
6835 imul{w}\t{%2, %0|%0, %2}"
6836 [(set_attr "type" "imul")
6837 (set_attr "prefix_0f" "0,0,1")
6838 (set (attr "athlon_decode")
6839 (cond [(eq_attr "cpu" "athlon")
6840 (const_string "vector")
6841 (eq_attr "alternative" "1,2")
6842 (const_string "vector")]
6843 (const_string "direct")))
6844 (set_attr "mode" "HI")])
6846 (define_expand "mulqi3"
6847 [(parallel [(set (match_operand:QI 0 "register_operand" "")
6848 (mult:QI (match_operand:QI 1 "nonimmediate_operand" "")
6849 (match_operand:QI 2 "register_operand" "")))
6850 (clobber (reg:CC FLAGS_REG))])]
6851 "TARGET_QIMODE_MATH"
6854 (define_insn "*mulqi3_1"
6855 [(set (match_operand:QI 0 "register_operand" "=a")
6856 (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6857 (match_operand:QI 2 "nonimmediate_operand" "qm")))
6858 (clobber (reg:CC FLAGS_REG))]
6860 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6862 [(set_attr "type" "imul")
6863 (set_attr "length_immediate" "0")
6864 (set (attr "athlon_decode")
6865 (if_then_else (eq_attr "cpu" "athlon")
6866 (const_string "vector")
6867 (const_string "direct")))
6868 (set_attr "mode" "QI")])
6870 (define_expand "umulqihi3"
6871 [(parallel [(set (match_operand:HI 0 "register_operand" "")
6872 (mult:HI (zero_extend:HI
6873 (match_operand:QI 1 "nonimmediate_operand" ""))
6875 (match_operand:QI 2 "register_operand" ""))))
6876 (clobber (reg:CC FLAGS_REG))])]
6877 "TARGET_QIMODE_MATH"
6880 (define_insn "*umulqihi3_1"
6881 [(set (match_operand:HI 0 "register_operand" "=a")
6882 (mult:HI (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
6883 (zero_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6884 (clobber (reg:CC FLAGS_REG))]
6886 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6888 [(set_attr "type" "imul")
6889 (set_attr "length_immediate" "0")
6890 (set (attr "athlon_decode")
6891 (if_then_else (eq_attr "cpu" "athlon")
6892 (const_string "vector")
6893 (const_string "direct")))
6894 (set_attr "mode" "QI")])
6896 (define_expand "mulqihi3"
6897 [(parallel [(set (match_operand:HI 0 "register_operand" "")
6898 (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))
6899 (sign_extend:HI (match_operand:QI 2 "register_operand" ""))))
6900 (clobber (reg:CC FLAGS_REG))])]
6901 "TARGET_QIMODE_MATH"
6904 (define_insn "*mulqihi3_insn"
6905 [(set (match_operand:HI 0 "register_operand" "=a")
6906 (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
6907 (sign_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6908 (clobber (reg:CC FLAGS_REG))]
6910 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6912 [(set_attr "type" "imul")
6913 (set_attr "length_immediate" "0")
6914 (set (attr "athlon_decode")
6915 (if_then_else (eq_attr "cpu" "athlon")
6916 (const_string "vector")
6917 (const_string "direct")))
6918 (set_attr "mode" "QI")])
6920 (define_expand "umulditi3"
6921 [(parallel [(set (match_operand:TI 0 "register_operand" "")
6922 (mult:TI (zero_extend:TI
6923 (match_operand:DI 1 "nonimmediate_operand" ""))
6925 (match_operand:DI 2 "register_operand" ""))))
6926 (clobber (reg:CC FLAGS_REG))])]
6930 (define_insn "*umulditi3_insn"
6931 [(set (match_operand:TI 0 "register_operand" "=A")
6932 (mult:TI (zero_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
6933 (zero_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
6934 (clobber (reg:CC FLAGS_REG))]
6936 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6938 [(set_attr "type" "imul")
6939 (set_attr "length_immediate" "0")
6940 (set (attr "athlon_decode")
6941 (if_then_else (eq_attr "cpu" "athlon")
6942 (const_string "vector")
6943 (const_string "double")))
6944 (set_attr "mode" "DI")])
6946 ;; We can't use this pattern in 64bit mode, since it results in two separate 32bit registers
6947 (define_expand "umulsidi3"
6948 [(parallel [(set (match_operand:DI 0 "register_operand" "")
6949 (mult:DI (zero_extend:DI
6950 (match_operand:SI 1 "nonimmediate_operand" ""))
6952 (match_operand:SI 2 "register_operand" ""))))
6953 (clobber (reg:CC FLAGS_REG))])]
6957 (define_insn "*umulsidi3_insn"
6958 [(set (match_operand:DI 0 "register_operand" "=A")
6959 (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
6960 (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
6961 (clobber (reg:CC FLAGS_REG))]
6963 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6965 [(set_attr "type" "imul")
6966 (set_attr "length_immediate" "0")
6967 (set (attr "athlon_decode")
6968 (if_then_else (eq_attr "cpu" "athlon")
6969 (const_string "vector")
6970 (const_string "double")))
6971 (set_attr "mode" "SI")])
6973 (define_expand "mulditi3"
6974 [(parallel [(set (match_operand:TI 0 "register_operand" "")
6975 (mult:TI (sign_extend:TI
6976 (match_operand:DI 1 "nonimmediate_operand" ""))
6978 (match_operand:DI 2 "register_operand" ""))))
6979 (clobber (reg:CC FLAGS_REG))])]
6983 (define_insn "*mulditi3_insn"
6984 [(set (match_operand:TI 0 "register_operand" "=A")
6985 (mult:TI (sign_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
6986 (sign_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
6987 (clobber (reg:CC FLAGS_REG))]
6989 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6991 [(set_attr "type" "imul")
6992 (set_attr "length_immediate" "0")
6993 (set (attr "athlon_decode")
6994 (if_then_else (eq_attr "cpu" "athlon")
6995 (const_string "vector")
6996 (const_string "double")))
6997 (set_attr "mode" "DI")])
6999 (define_expand "mulsidi3"
7000 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7001 (mult:DI (sign_extend:DI
7002 (match_operand:SI 1 "nonimmediate_operand" ""))
7004 (match_operand:SI 2 "register_operand" ""))))
7005 (clobber (reg:CC FLAGS_REG))])]
7009 (define_insn "*mulsidi3_insn"
7010 [(set (match_operand:DI 0 "register_operand" "=A")
7011 (mult:DI (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7012 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7013 (clobber (reg:CC FLAGS_REG))]
7015 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7017 [(set_attr "type" "imul")
7018 (set_attr "length_immediate" "0")
7019 (set (attr "athlon_decode")
7020 (if_then_else (eq_attr "cpu" "athlon")
7021 (const_string "vector")
7022 (const_string "double")))
7023 (set_attr "mode" "SI")])
7025 (define_expand "umuldi3_highpart"
7026 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7029 (mult:TI (zero_extend:TI
7030 (match_operand:DI 1 "nonimmediate_operand" ""))
7032 (match_operand:DI 2 "register_operand" "")))
7034 (clobber (match_scratch:DI 3 ""))
7035 (clobber (reg:CC FLAGS_REG))])]
7039 (define_insn "*umuldi3_highpart_rex64"
7040 [(set (match_operand:DI 0 "register_operand" "=d")
7043 (mult:TI (zero_extend:TI
7044 (match_operand:DI 1 "nonimmediate_operand" "%a"))
7046 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7048 (clobber (match_scratch:DI 3 "=1"))
7049 (clobber (reg:CC FLAGS_REG))]
7051 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7053 [(set_attr "type" "imul")
7054 (set_attr "length_immediate" "0")
7055 (set (attr "athlon_decode")
7056 (if_then_else (eq_attr "cpu" "athlon")
7057 (const_string "vector")
7058 (const_string "double")))
7059 (set_attr "mode" "DI")])
7061 (define_expand "umulsi3_highpart"
7062 [(parallel [(set (match_operand:SI 0 "register_operand" "")
7065 (mult:DI (zero_extend:DI
7066 (match_operand:SI 1 "nonimmediate_operand" ""))
7068 (match_operand:SI 2 "register_operand" "")))
7070 (clobber (match_scratch:SI 3 ""))
7071 (clobber (reg:CC FLAGS_REG))])]
7075 (define_insn "*umulsi3_highpart_insn"
7076 [(set (match_operand:SI 0 "register_operand" "=d")
7079 (mult:DI (zero_extend:DI
7080 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7082 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7084 (clobber (match_scratch:SI 3 "=1"))
7085 (clobber (reg:CC FLAGS_REG))]
7086 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7088 [(set_attr "type" "imul")
7089 (set_attr "length_immediate" "0")
7090 (set (attr "athlon_decode")
7091 (if_then_else (eq_attr "cpu" "athlon")
7092 (const_string "vector")
7093 (const_string "double")))
7094 (set_attr "mode" "SI")])
7096 (define_insn "*umulsi3_highpart_zext"
7097 [(set (match_operand:DI 0 "register_operand" "=d")
7098 (zero_extend:DI (truncate:SI
7100 (mult:DI (zero_extend:DI
7101 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7103 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7105 (clobber (match_scratch:SI 3 "=1"))
7106 (clobber (reg:CC FLAGS_REG))]
7108 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7110 [(set_attr "type" "imul")
7111 (set_attr "length_immediate" "0")
7112 (set (attr "athlon_decode")
7113 (if_then_else (eq_attr "cpu" "athlon")
7114 (const_string "vector")
7115 (const_string "double")))
7116 (set_attr "mode" "SI")])
7118 (define_expand "smuldi3_highpart"
7119 [(parallel [(set (match_operand:DI 0 "register_operand" "=d")
7122 (mult:TI (sign_extend:TI
7123 (match_operand:DI 1 "nonimmediate_operand" ""))
7125 (match_operand:DI 2 "register_operand" "")))
7127 (clobber (match_scratch:DI 3 ""))
7128 (clobber (reg:CC FLAGS_REG))])]
7132 (define_insn "*smuldi3_highpart_rex64"
7133 [(set (match_operand:DI 0 "register_operand" "=d")
7136 (mult:TI (sign_extend:TI
7137 (match_operand:DI 1 "nonimmediate_operand" "%a"))
7139 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7141 (clobber (match_scratch:DI 3 "=1"))
7142 (clobber (reg:CC FLAGS_REG))]
7144 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7146 [(set_attr "type" "imul")
7147 (set (attr "athlon_decode")
7148 (if_then_else (eq_attr "cpu" "athlon")
7149 (const_string "vector")
7150 (const_string "double")))
7151 (set_attr "mode" "DI")])
7153 (define_expand "smulsi3_highpart"
7154 [(parallel [(set (match_operand:SI 0 "register_operand" "")
7157 (mult:DI (sign_extend:DI
7158 (match_operand:SI 1 "nonimmediate_operand" ""))
7160 (match_operand:SI 2 "register_operand" "")))
7162 (clobber (match_scratch:SI 3 ""))
7163 (clobber (reg:CC FLAGS_REG))])]
7167 (define_insn "*smulsi3_highpart_insn"
7168 [(set (match_operand:SI 0 "register_operand" "=d")
7171 (mult:DI (sign_extend:DI
7172 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7174 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7176 (clobber (match_scratch:SI 3 "=1"))
7177 (clobber (reg:CC FLAGS_REG))]
7178 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7180 [(set_attr "type" "imul")
7181 (set (attr "athlon_decode")
7182 (if_then_else (eq_attr "cpu" "athlon")
7183 (const_string "vector")
7184 (const_string "double")))
7185 (set_attr "mode" "SI")])
7187 (define_insn "*smulsi3_highpart_zext"
7188 [(set (match_operand:DI 0 "register_operand" "=d")
7189 (zero_extend:DI (truncate:SI
7191 (mult:DI (sign_extend:DI
7192 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7194 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7196 (clobber (match_scratch:SI 3 "=1"))
7197 (clobber (reg:CC FLAGS_REG))]
7199 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7201 [(set_attr "type" "imul")
7202 (set (attr "athlon_decode")
7203 (if_then_else (eq_attr "cpu" "athlon")
7204 (const_string "vector")
7205 (const_string "double")))
7206 (set_attr "mode" "SI")])
7208 ;; The patterns that match these are at the end of this file.
7210 (define_expand "mulxf3"
7211 [(set (match_operand:XF 0 "register_operand" "")
7212 (mult:XF (match_operand:XF 1 "register_operand" "")
7213 (match_operand:XF 2 "register_operand" "")))]
7217 (define_expand "muldf3"
7218 [(set (match_operand:DF 0 "register_operand" "")
7219 (mult:DF (match_operand:DF 1 "register_operand" "")
7220 (match_operand:DF 2 "nonimmediate_operand" "")))]
7221 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
7224 (define_expand "mulsf3"
7225 [(set (match_operand:SF 0 "register_operand" "")
7226 (mult:SF (match_operand:SF 1 "register_operand" "")
7227 (match_operand:SF 2 "nonimmediate_operand" "")))]
7228 "TARGET_80387 || TARGET_SSE_MATH"
7231 ;; Divide instructions
7233 (define_insn "divqi3"
7234 [(set (match_operand:QI 0 "register_operand" "=a")
7235 (div:QI (match_operand:HI 1 "register_operand" "0")
7236 (match_operand:QI 2 "nonimmediate_operand" "qm")))
7237 (clobber (reg:CC FLAGS_REG))]
7238 "TARGET_QIMODE_MATH"
7240 [(set_attr "type" "idiv")
7241 (set_attr "mode" "QI")])
7243 (define_insn "udivqi3"
7244 [(set (match_operand:QI 0 "register_operand" "=a")
7245 (udiv:QI (match_operand:HI 1 "register_operand" "0")
7246 (match_operand:QI 2 "nonimmediate_operand" "qm")))
7247 (clobber (reg:CC FLAGS_REG))]
7248 "TARGET_QIMODE_MATH"
7250 [(set_attr "type" "idiv")
7251 (set_attr "mode" "QI")])
7253 ;; The patterns that match these are at the end of this file.
7255 (define_expand "divxf3"
7256 [(set (match_operand:XF 0 "register_operand" "")
7257 (div:XF (match_operand:XF 1 "register_operand" "")
7258 (match_operand:XF 2 "register_operand" "")))]
7262 (define_expand "divdf3"
7263 [(set (match_operand:DF 0 "register_operand" "")
7264 (div:DF (match_operand:DF 1 "register_operand" "")
7265 (match_operand:DF 2 "nonimmediate_operand" "")))]
7266 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
7269 (define_expand "divsf3"
7270 [(set (match_operand:SF 0 "register_operand" "")
7271 (div:SF (match_operand:SF 1 "register_operand" "")
7272 (match_operand:SF 2 "nonimmediate_operand" "")))]
7273 "TARGET_80387 || TARGET_SSE_MATH"
7276 ;; Remainder instructions.
7278 (define_expand "divmoddi4"
7279 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7280 (div:DI (match_operand:DI 1 "register_operand" "")
7281 (match_operand:DI 2 "nonimmediate_operand" "")))
7282 (set (match_operand:DI 3 "register_operand" "")
7283 (mod:DI (match_dup 1) (match_dup 2)))
7284 (clobber (reg:CC FLAGS_REG))])]
7288 ;; Allow to come the parameter in eax or edx to avoid extra moves.
7289 ;; Penalize eax case slightly because it results in worse scheduling
7291 (define_insn "*divmoddi4_nocltd_rex64"
7292 [(set (match_operand:DI 0 "register_operand" "=&a,?a")
7293 (div:DI (match_operand:DI 2 "register_operand" "1,0")
7294 (match_operand:DI 3 "nonimmediate_operand" "rm,rm")))
7295 (set (match_operand:DI 1 "register_operand" "=&d,&d")
7296 (mod:DI (match_dup 2) (match_dup 3)))
7297 (clobber (reg:CC FLAGS_REG))]
7298 "TARGET_64BIT && !optimize_size && !TARGET_USE_CLTD"
7300 [(set_attr "type" "multi")])
7302 (define_insn "*divmoddi4_cltd_rex64"
7303 [(set (match_operand:DI 0 "register_operand" "=a")
7304 (div:DI (match_operand:DI 2 "register_operand" "a")
7305 (match_operand:DI 3 "nonimmediate_operand" "rm")))
7306 (set (match_operand:DI 1 "register_operand" "=&d")
7307 (mod:DI (match_dup 2) (match_dup 3)))
7308 (clobber (reg:CC FLAGS_REG))]
7309 "TARGET_64BIT && (optimize_size || TARGET_USE_CLTD)"
7311 [(set_attr "type" "multi")])
7313 (define_insn "*divmoddi_noext_rex64"
7314 [(set (match_operand:DI 0 "register_operand" "=a")
7315 (div:DI (match_operand:DI 1 "register_operand" "0")
7316 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7317 (set (match_operand:DI 3 "register_operand" "=d")
7318 (mod:DI (match_dup 1) (match_dup 2)))
7319 (use (match_operand:DI 4 "register_operand" "3"))
7320 (clobber (reg:CC FLAGS_REG))]
7323 [(set_attr "type" "idiv")
7324 (set_attr "mode" "DI")])
7327 [(set (match_operand:DI 0 "register_operand" "")
7328 (div:DI (match_operand:DI 1 "register_operand" "")
7329 (match_operand:DI 2 "nonimmediate_operand" "")))
7330 (set (match_operand:DI 3 "register_operand" "")
7331 (mod:DI (match_dup 1) (match_dup 2)))
7332 (clobber (reg:CC FLAGS_REG))]
7333 "TARGET_64BIT && reload_completed"
7334 [(parallel [(set (match_dup 3)
7335 (ashiftrt:DI (match_dup 4) (const_int 63)))
7336 (clobber (reg:CC FLAGS_REG))])
7337 (parallel [(set (match_dup 0)
7338 (div:DI (reg:DI 0) (match_dup 2)))
7340 (mod:DI (reg:DI 0) (match_dup 2)))
7342 (clobber (reg:CC FLAGS_REG))])]
7344 /* Avoid use of cltd in favor of a mov+shift. */
7345 if (!TARGET_USE_CLTD && !optimize_size)
7347 if (true_regnum (operands[1]))
7348 emit_move_insn (operands[0], operands[1]);
7350 emit_move_insn (operands[3], operands[1]);
7351 operands[4] = operands[3];
7355 gcc_assert (!true_regnum (operands[1]));
7356 operands[4] = operands[1];
7361 (define_expand "divmodsi4"
7362 [(parallel [(set (match_operand:SI 0 "register_operand" "")
7363 (div:SI (match_operand:SI 1 "register_operand" "")
7364 (match_operand:SI 2 "nonimmediate_operand" "")))
7365 (set (match_operand:SI 3 "register_operand" "")
7366 (mod:SI (match_dup 1) (match_dup 2)))
7367 (clobber (reg:CC FLAGS_REG))])]
7371 ;; Allow to come the parameter in eax or edx to avoid extra moves.
7372 ;; Penalize eax case slightly because it results in worse scheduling
7374 (define_insn "*divmodsi4_nocltd"
7375 [(set (match_operand:SI 0 "register_operand" "=&a,?a")
7376 (div:SI (match_operand:SI 2 "register_operand" "1,0")
7377 (match_operand:SI 3 "nonimmediate_operand" "rm,rm")))
7378 (set (match_operand:SI 1 "register_operand" "=&d,&d")
7379 (mod:SI (match_dup 2) (match_dup 3)))
7380 (clobber (reg:CC FLAGS_REG))]
7381 "!optimize_size && !TARGET_USE_CLTD"
7383 [(set_attr "type" "multi")])
7385 (define_insn "*divmodsi4_cltd"
7386 [(set (match_operand:SI 0 "register_operand" "=a")
7387 (div:SI (match_operand:SI 2 "register_operand" "a")
7388 (match_operand:SI 3 "nonimmediate_operand" "rm")))
7389 (set (match_operand:SI 1 "register_operand" "=&d")
7390 (mod:SI (match_dup 2) (match_dup 3)))
7391 (clobber (reg:CC FLAGS_REG))]
7392 "optimize_size || TARGET_USE_CLTD"
7394 [(set_attr "type" "multi")])
7396 (define_insn "*divmodsi_noext"
7397 [(set (match_operand:SI 0 "register_operand" "=a")
7398 (div:SI (match_operand:SI 1 "register_operand" "0")
7399 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7400 (set (match_operand:SI 3 "register_operand" "=d")
7401 (mod:SI (match_dup 1) (match_dup 2)))
7402 (use (match_operand:SI 4 "register_operand" "3"))
7403 (clobber (reg:CC FLAGS_REG))]
7406 [(set_attr "type" "idiv")
7407 (set_attr "mode" "SI")])
7410 [(set (match_operand:SI 0 "register_operand" "")
7411 (div:SI (match_operand:SI 1 "register_operand" "")
7412 (match_operand:SI 2 "nonimmediate_operand" "")))
7413 (set (match_operand:SI 3 "register_operand" "")
7414 (mod:SI (match_dup 1) (match_dup 2)))
7415 (clobber (reg:CC FLAGS_REG))]
7417 [(parallel [(set (match_dup 3)
7418 (ashiftrt:SI (match_dup 4) (const_int 31)))
7419 (clobber (reg:CC FLAGS_REG))])
7420 (parallel [(set (match_dup 0)
7421 (div:SI (reg:SI 0) (match_dup 2)))
7423 (mod:SI (reg:SI 0) (match_dup 2)))
7425 (clobber (reg:CC FLAGS_REG))])]
7427 /* Avoid use of cltd in favor of a mov+shift. */
7428 if (!TARGET_USE_CLTD && !optimize_size)
7430 if (true_regnum (operands[1]))
7431 emit_move_insn (operands[0], operands[1]);
7433 emit_move_insn (operands[3], operands[1]);
7434 operands[4] = operands[3];
7438 gcc_assert (!true_regnum (operands[1]));
7439 operands[4] = operands[1];
7443 (define_insn "divmodhi4"
7444 [(set (match_operand:HI 0 "register_operand" "=a")
7445 (div:HI (match_operand:HI 1 "register_operand" "0")
7446 (match_operand:HI 2 "nonimmediate_operand" "rm")))
7447 (set (match_operand:HI 3 "register_operand" "=&d")
7448 (mod:HI (match_dup 1) (match_dup 2)))
7449 (clobber (reg:CC FLAGS_REG))]
7450 "TARGET_HIMODE_MATH"
7452 [(set_attr "type" "multi")
7453 (set_attr "length_immediate" "0")
7454 (set_attr "mode" "SI")])
7456 (define_insn "udivmoddi4"
7457 [(set (match_operand:DI 0 "register_operand" "=a")
7458 (udiv:DI (match_operand:DI 1 "register_operand" "0")
7459 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7460 (set (match_operand:DI 3 "register_operand" "=&d")
7461 (umod:DI (match_dup 1) (match_dup 2)))
7462 (clobber (reg:CC FLAGS_REG))]
7464 "xor{q}\t%3, %3\;div{q}\t%2"
7465 [(set_attr "type" "multi")
7466 (set_attr "length_immediate" "0")
7467 (set_attr "mode" "DI")])
7469 (define_insn "*udivmoddi4_noext"
7470 [(set (match_operand:DI 0 "register_operand" "=a")
7471 (udiv:DI (match_operand:DI 1 "register_operand" "0")
7472 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7473 (set (match_operand:DI 3 "register_operand" "=d")
7474 (umod:DI (match_dup 1) (match_dup 2)))
7476 (clobber (reg:CC FLAGS_REG))]
7479 [(set_attr "type" "idiv")
7480 (set_attr "mode" "DI")])
7483 [(set (match_operand:DI 0 "register_operand" "")
7484 (udiv:DI (match_operand:DI 1 "register_operand" "")
7485 (match_operand:DI 2 "nonimmediate_operand" "")))
7486 (set (match_operand:DI 3 "register_operand" "")
7487 (umod:DI (match_dup 1) (match_dup 2)))
7488 (clobber (reg:CC FLAGS_REG))]
7489 "TARGET_64BIT && reload_completed"
7490 [(set (match_dup 3) (const_int 0))
7491 (parallel [(set (match_dup 0)
7492 (udiv:DI (match_dup 1) (match_dup 2)))
7494 (umod:DI (match_dup 1) (match_dup 2)))
7496 (clobber (reg:CC FLAGS_REG))])]
7499 (define_insn "udivmodsi4"
7500 [(set (match_operand:SI 0 "register_operand" "=a")
7501 (udiv:SI (match_operand:SI 1 "register_operand" "0")
7502 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7503 (set (match_operand:SI 3 "register_operand" "=&d")
7504 (umod:SI (match_dup 1) (match_dup 2)))
7505 (clobber (reg:CC FLAGS_REG))]
7507 "xor{l}\t%3, %3\;div{l}\t%2"
7508 [(set_attr "type" "multi")
7509 (set_attr "length_immediate" "0")
7510 (set_attr "mode" "SI")])
7512 (define_insn "*udivmodsi4_noext"
7513 [(set (match_operand:SI 0 "register_operand" "=a")
7514 (udiv:SI (match_operand:SI 1 "register_operand" "0")
7515 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7516 (set (match_operand:SI 3 "register_operand" "=d")
7517 (umod:SI (match_dup 1) (match_dup 2)))
7519 (clobber (reg:CC FLAGS_REG))]
7522 [(set_attr "type" "idiv")
7523 (set_attr "mode" "SI")])
7526 [(set (match_operand:SI 0 "register_operand" "")
7527 (udiv:SI (match_operand:SI 1 "register_operand" "")
7528 (match_operand:SI 2 "nonimmediate_operand" "")))
7529 (set (match_operand:SI 3 "register_operand" "")
7530 (umod:SI (match_dup 1) (match_dup 2)))
7531 (clobber (reg:CC FLAGS_REG))]
7533 [(set (match_dup 3) (const_int 0))
7534 (parallel [(set (match_dup 0)
7535 (udiv:SI (match_dup 1) (match_dup 2)))
7537 (umod:SI (match_dup 1) (match_dup 2)))
7539 (clobber (reg:CC FLAGS_REG))])]
7542 (define_expand "udivmodhi4"
7543 [(set (match_dup 4) (const_int 0))
7544 (parallel [(set (match_operand:HI 0 "register_operand" "")
7545 (udiv:HI (match_operand:HI 1 "register_operand" "")
7546 (match_operand:HI 2 "nonimmediate_operand" "")))
7547 (set (match_operand:HI 3 "register_operand" "")
7548 (umod:HI (match_dup 1) (match_dup 2)))
7550 (clobber (reg:CC FLAGS_REG))])]
7551 "TARGET_HIMODE_MATH"
7552 "operands[4] = gen_reg_rtx (HImode);")
7554 (define_insn "*udivmodhi_noext"
7555 [(set (match_operand:HI 0 "register_operand" "=a")
7556 (udiv:HI (match_operand:HI 1 "register_operand" "0")
7557 (match_operand:HI 2 "nonimmediate_operand" "rm")))
7558 (set (match_operand:HI 3 "register_operand" "=d")
7559 (umod:HI (match_dup 1) (match_dup 2)))
7560 (use (match_operand:HI 4 "register_operand" "3"))
7561 (clobber (reg:CC FLAGS_REG))]
7564 [(set_attr "type" "idiv")
7565 (set_attr "mode" "HI")])
7567 ;; We cannot use div/idiv for double division, because it causes
7568 ;; "division by zero" on the overflow and that's not what we expect
7569 ;; from truncate. Because true (non truncating) double division is
7570 ;; never generated, we can't create this insn anyway.
7573 ; [(set (match_operand:SI 0 "register_operand" "=a")
7575 ; (udiv:DI (match_operand:DI 1 "register_operand" "A")
7577 ; (match_operand:SI 2 "nonimmediate_operand" "rm")))))
7578 ; (set (match_operand:SI 3 "register_operand" "=d")
7580 ; (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
7581 ; (clobber (reg:CC FLAGS_REG))]
7583 ; "div{l}\t{%2, %0|%0, %2}"
7584 ; [(set_attr "type" "idiv")])
7586 ;;- Logical AND instructions
7588 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
7589 ;; Note that this excludes ah.
7591 (define_insn "*testdi_1_rex64"
7592 [(set (reg FLAGS_REG)
7594 (and:DI (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
7595 (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
7597 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7598 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7600 test{l}\t{%k1, %k0|%k0, %k1}
7601 test{l}\t{%k1, %k0|%k0, %k1}
7602 test{q}\t{%1, %0|%0, %1}
7603 test{q}\t{%1, %0|%0, %1}
7604 test{q}\t{%1, %0|%0, %1}"
7605 [(set_attr "type" "test")
7606 (set_attr "modrm" "0,1,0,1,1")
7607 (set_attr "mode" "SI,SI,DI,DI,DI")
7608 (set_attr "pent_pair" "uv,np,uv,np,uv")])
7610 (define_insn "testsi_1"
7611 [(set (reg FLAGS_REG)
7613 (and:SI (match_operand:SI 0 "nonimmediate_operand" "%!*a,r,rm")
7614 (match_operand:SI 1 "general_operand" "in,in,rin"))
7616 "ix86_match_ccmode (insn, CCNOmode)
7617 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7618 "test{l}\t{%1, %0|%0, %1}"
7619 [(set_attr "type" "test")
7620 (set_attr "modrm" "0,1,1")
7621 (set_attr "mode" "SI")
7622 (set_attr "pent_pair" "uv,np,uv")])
7624 (define_expand "testsi_ccno_1"
7625 [(set (reg:CCNO FLAGS_REG)
7627 (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
7628 (match_operand:SI 1 "nonmemory_operand" ""))
7633 (define_insn "*testhi_1"
7634 [(set (reg FLAGS_REG)
7635 (compare (and:HI (match_operand:HI 0 "nonimmediate_operand" "%!*a,r,rm")
7636 (match_operand:HI 1 "general_operand" "n,n,rn"))
7638 "ix86_match_ccmode (insn, CCNOmode)
7639 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7640 "test{w}\t{%1, %0|%0, %1}"
7641 [(set_attr "type" "test")
7642 (set_attr "modrm" "0,1,1")
7643 (set_attr "mode" "HI")
7644 (set_attr "pent_pair" "uv,np,uv")])
7646 (define_expand "testqi_ccz_1"
7647 [(set (reg:CCZ FLAGS_REG)
7648 (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
7649 (match_operand:QI 1 "nonmemory_operand" ""))
7654 (define_insn "*testqi_1_maybe_si"
7655 [(set (reg FLAGS_REG)
7658 (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
7659 (match_operand:QI 1 "general_operand" "n,n,qn,n"))
7661 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
7662 && ix86_match_ccmode (insn,
7663 GET_CODE (operands[1]) == CONST_INT
7664 && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
7666 if (which_alternative == 3)
7668 if (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) < 0)
7669 operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
7670 return "test{l}\t{%1, %k0|%k0, %1}";
7672 return "test{b}\t{%1, %0|%0, %1}";
7674 [(set_attr "type" "test")
7675 (set_attr "modrm" "0,1,1,1")
7676 (set_attr "mode" "QI,QI,QI,SI")
7677 (set_attr "pent_pair" "uv,np,uv,np")])
7679 (define_insn "*testqi_1"
7680 [(set (reg FLAGS_REG)
7683 (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm")
7684 (match_operand:QI 1 "general_operand" "n,n,qn"))
7686 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
7687 && ix86_match_ccmode (insn, CCNOmode)"
7688 "test{b}\t{%1, %0|%0, %1}"
7689 [(set_attr "type" "test")
7690 (set_attr "modrm" "0,1,1")
7691 (set_attr "mode" "QI")
7692 (set_attr "pent_pair" "uv,np,uv")])
7694 (define_expand "testqi_ext_ccno_0"
7695 [(set (reg:CCNO FLAGS_REG)
7699 (match_operand 0 "ext_register_operand" "")
7702 (match_operand 1 "const_int_operand" ""))
7707 (define_insn "*testqi_ext_0"
7708 [(set (reg FLAGS_REG)
7712 (match_operand 0 "ext_register_operand" "Q")
7715 (match_operand 1 "const_int_operand" "n"))
7717 "ix86_match_ccmode (insn, CCNOmode)"
7718 "test{b}\t{%1, %h0|%h0, %1}"
7719 [(set_attr "type" "test")
7720 (set_attr "mode" "QI")
7721 (set_attr "length_immediate" "1")
7722 (set_attr "pent_pair" "np")])
7724 (define_insn "*testqi_ext_1"
7725 [(set (reg FLAGS_REG)
7729 (match_operand 0 "ext_register_operand" "Q")
7733 (match_operand:QI 1 "general_operand" "Qm")))
7735 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7736 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7737 "test{b}\t{%1, %h0|%h0, %1}"
7738 [(set_attr "type" "test")
7739 (set_attr "mode" "QI")])
7741 (define_insn "*testqi_ext_1_rex64"
7742 [(set (reg FLAGS_REG)
7746 (match_operand 0 "ext_register_operand" "Q")
7750 (match_operand:QI 1 "register_operand" "Q")))
7752 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7753 "test{b}\t{%1, %h0|%h0, %1}"
7754 [(set_attr "type" "test")
7755 (set_attr "mode" "QI")])
7757 (define_insn "*testqi_ext_2"
7758 [(set (reg FLAGS_REG)
7762 (match_operand 0 "ext_register_operand" "Q")
7766 (match_operand 1 "ext_register_operand" "Q")
7770 "ix86_match_ccmode (insn, CCNOmode)"
7771 "test{b}\t{%h1, %h0|%h0, %h1}"
7772 [(set_attr "type" "test")
7773 (set_attr "mode" "QI")])
7775 ;; Combine likes to form bit extractions for some tests. Humor it.
7776 (define_insn "*testqi_ext_3"
7777 [(set (reg FLAGS_REG)
7778 (compare (zero_extract:SI
7779 (match_operand 0 "nonimmediate_operand" "rm")
7780 (match_operand:SI 1 "const_int_operand" "")
7781 (match_operand:SI 2 "const_int_operand" ""))
7783 "ix86_match_ccmode (insn, CCNOmode)
7784 && (GET_MODE (operands[0]) == SImode
7785 || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
7786 || GET_MODE (operands[0]) == HImode
7787 || GET_MODE (operands[0]) == QImode)"
7790 (define_insn "*testqi_ext_3_rex64"
7791 [(set (reg FLAGS_REG)
7792 (compare (zero_extract:DI
7793 (match_operand 0 "nonimmediate_operand" "rm")
7794 (match_operand:DI 1 "const_int_operand" "")
7795 (match_operand:DI 2 "const_int_operand" ""))
7798 && ix86_match_ccmode (insn, CCNOmode)
7799 /* The code below cannot deal with constants outside HOST_WIDE_INT. */
7800 && INTVAL (operands[1]) + INTVAL (operands[2]) < HOST_BITS_PER_WIDE_INT
7801 /* Ensure that resulting mask is zero or sign extended operand. */
7802 && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7803 || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
7804 && INTVAL (operands[1]) > 32))
7805 && (GET_MODE (operands[0]) == SImode
7806 || GET_MODE (operands[0]) == DImode
7807 || GET_MODE (operands[0]) == HImode
7808 || GET_MODE (operands[0]) == QImode)"
7812 [(set (match_operand 0 "flags_reg_operand" "")
7813 (match_operator 1 "compare_operator"
7815 (match_operand 2 "nonimmediate_operand" "")
7816 (match_operand 3 "const_int_operand" "")
7817 (match_operand 4 "const_int_operand" ""))
7819 "ix86_match_ccmode (insn, CCNOmode)"
7820 [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
7822 rtx val = operands[2];
7823 HOST_WIDE_INT len = INTVAL (operands[3]);
7824 HOST_WIDE_INT pos = INTVAL (operands[4]);
7826 enum machine_mode mode, submode;
7828 mode = GET_MODE (val);
7829 if (GET_CODE (val) == MEM)
7831 /* ??? Combine likes to put non-volatile mem extractions in QImode
7832 no matter the size of the test. So find a mode that works. */
7833 if (! MEM_VOLATILE_P (val))
7835 mode = smallest_mode_for_size (pos + len, MODE_INT);
7836 val = adjust_address (val, mode, 0);
7839 else if (GET_CODE (val) == SUBREG
7840 && (submode = GET_MODE (SUBREG_REG (val)),
7841 GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
7842 && pos + len <= GET_MODE_BITSIZE (submode))
7844 /* Narrow a paradoxical subreg to prevent partial register stalls. */
7846 val = SUBREG_REG (val);
7848 else if (mode == HImode && pos + len <= 8)
7850 /* Small HImode tests can be converted to QImode. */
7852 val = gen_lowpart (QImode, val);
7855 mask = ((HOST_WIDE_INT)1 << (pos + len)) - 1;
7856 mask &= ~(((HOST_WIDE_INT)1 << pos) - 1);
7858 operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
7861 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
7862 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
7863 ;; this is relatively important trick.
7864 ;; Do the conversion only post-reload to avoid limiting of the register class
7867 [(set (match_operand 0 "flags_reg_operand" "")
7868 (match_operator 1 "compare_operator"
7869 [(and (match_operand 2 "register_operand" "")
7870 (match_operand 3 "const_int_operand" ""))
7873 && QI_REG_P (operands[2])
7874 && GET_MODE (operands[2]) != QImode
7875 && ((ix86_match_ccmode (insn, CCZmode)
7876 && !(INTVAL (operands[3]) & ~(255 << 8)))
7877 || (ix86_match_ccmode (insn, CCNOmode)
7878 && !(INTVAL (operands[3]) & ~(127 << 8))))"
7881 [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
7884 "operands[2] = gen_lowpart (SImode, operands[2]);
7885 operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);")
7888 [(set (match_operand 0 "flags_reg_operand" "")
7889 (match_operator 1 "compare_operator"
7890 [(and (match_operand 2 "nonimmediate_operand" "")
7891 (match_operand 3 "const_int_operand" ""))
7894 && GET_MODE (operands[2]) != QImode
7895 && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
7896 && ((ix86_match_ccmode (insn, CCZmode)
7897 && !(INTVAL (operands[3]) & ~255))
7898 || (ix86_match_ccmode (insn, CCNOmode)
7899 && !(INTVAL (operands[3]) & ~127)))"
7901 (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
7903 "operands[2] = gen_lowpart (QImode, operands[2]);
7904 operands[3] = gen_lowpart (QImode, operands[3]);")
7907 ;; %%% This used to optimize known byte-wide and operations to memory,
7908 ;; and sometimes to QImode registers. If this is considered useful,
7909 ;; it should be done with splitters.
7911 (define_expand "anddi3"
7912 [(set (match_operand:DI 0 "nonimmediate_operand" "")
7913 (and:DI (match_operand:DI 1 "nonimmediate_operand" "")
7914 (match_operand:DI 2 "x86_64_szext_general_operand" "")))
7915 (clobber (reg:CC FLAGS_REG))]
7917 "ix86_expand_binary_operator (AND, DImode, operands); DONE;")
7919 (define_insn "*anddi_1_rex64"
7920 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
7921 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
7922 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
7923 (clobber (reg:CC FLAGS_REG))]
7924 "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
7926 switch (get_attr_type (insn))
7930 enum machine_mode mode;
7932 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
7933 if (INTVAL (operands[2]) == 0xff)
7937 gcc_assert (INTVAL (operands[2]) == 0xffff);
7941 operands[1] = gen_lowpart (mode, operands[1]);
7943 return "movz{bq|x}\t{%1,%0|%0, %1}";
7945 return "movz{wq|x}\t{%1,%0|%0, %1}";
7949 gcc_assert (rtx_equal_p (operands[0], operands[1]));
7950 if (get_attr_mode (insn) == MODE_SI)
7951 return "and{l}\t{%k2, %k0|%k0, %k2}";
7953 return "and{q}\t{%2, %0|%0, %2}";
7956 [(set_attr "type" "alu,alu,alu,imovx")
7957 (set_attr "length_immediate" "*,*,*,0")
7958 (set_attr "mode" "SI,DI,DI,DI")])
7960 (define_insn "*anddi_2"
7961 [(set (reg FLAGS_REG)
7962 (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
7963 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
7965 (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
7966 (and:DI (match_dup 1) (match_dup 2)))]
7967 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7968 && ix86_binary_operator_ok (AND, DImode, operands)"
7970 and{l}\t{%k2, %k0|%k0, %k2}
7971 and{q}\t{%2, %0|%0, %2}
7972 and{q}\t{%2, %0|%0, %2}"
7973 [(set_attr "type" "alu")
7974 (set_attr "mode" "SI,DI,DI")])
7976 (define_expand "andsi3"
7977 [(set (match_operand:SI 0 "nonimmediate_operand" "")
7978 (and:SI (match_operand:SI 1 "nonimmediate_operand" "")
7979 (match_operand:SI 2 "general_operand" "")))
7980 (clobber (reg:CC FLAGS_REG))]
7982 "ix86_expand_binary_operator (AND, SImode, operands); DONE;")
7984 (define_insn "*andsi_1"
7985 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
7986 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
7987 (match_operand:SI 2 "general_operand" "ri,rm,L")))
7988 (clobber (reg:CC FLAGS_REG))]
7989 "ix86_binary_operator_ok (AND, SImode, operands)"
7991 switch (get_attr_type (insn))
7995 enum machine_mode mode;
7997 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
7998 if (INTVAL (operands[2]) == 0xff)
8002 gcc_assert (INTVAL (operands[2]) == 0xffff);
8006 operands[1] = gen_lowpart (mode, operands[1]);
8008 return "movz{bl|x}\t{%1,%0|%0, %1}";
8010 return "movz{wl|x}\t{%1,%0|%0, %1}";
8014 gcc_assert (rtx_equal_p (operands[0], operands[1]));
8015 return "and{l}\t{%2, %0|%0, %2}";
8018 [(set_attr "type" "alu,alu,imovx")
8019 (set_attr "length_immediate" "*,*,0")
8020 (set_attr "mode" "SI")])
8023 [(set (match_operand 0 "register_operand" "")
8025 (const_int -65536)))
8026 (clobber (reg:CC FLAGS_REG))]
8027 "optimize_size || (TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)"
8028 [(set (strict_low_part (match_dup 1)) (const_int 0))]
8029 "operands[1] = gen_lowpart (HImode, operands[0]);")
8032 [(set (match_operand 0 "ext_register_operand" "")
8035 (clobber (reg:CC FLAGS_REG))]
8036 "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8037 [(set (strict_low_part (match_dup 1)) (const_int 0))]
8038 "operands[1] = gen_lowpart (QImode, operands[0]);")
8041 [(set (match_operand 0 "ext_register_operand" "")
8043 (const_int -65281)))
8044 (clobber (reg:CC FLAGS_REG))]
8045 "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8046 [(parallel [(set (zero_extract:SI (match_dup 0)
8050 (zero_extract:SI (match_dup 0)
8053 (zero_extract:SI (match_dup 0)
8056 (clobber (reg:CC FLAGS_REG))])]
8057 "operands[0] = gen_lowpart (SImode, operands[0]);")
8059 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8060 (define_insn "*andsi_1_zext"
8061 [(set (match_operand:DI 0 "register_operand" "=r")
8063 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8064 (match_operand:SI 2 "general_operand" "rim"))))
8065 (clobber (reg:CC FLAGS_REG))]
8066 "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
8067 "and{l}\t{%2, %k0|%k0, %2}"
8068 [(set_attr "type" "alu")
8069 (set_attr "mode" "SI")])
8071 (define_insn "*andsi_2"
8072 [(set (reg FLAGS_REG)
8073 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8074 (match_operand:SI 2 "general_operand" "rim,ri"))
8076 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8077 (and:SI (match_dup 1) (match_dup 2)))]
8078 "ix86_match_ccmode (insn, CCNOmode)
8079 && ix86_binary_operator_ok (AND, SImode, operands)"
8080 "and{l}\t{%2, %0|%0, %2}"
8081 [(set_attr "type" "alu")
8082 (set_attr "mode" "SI")])
8084 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8085 (define_insn "*andsi_2_zext"
8086 [(set (reg FLAGS_REG)
8087 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8088 (match_operand:SI 2 "general_operand" "rim"))
8090 (set (match_operand:DI 0 "register_operand" "=r")
8091 (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
8092 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8093 && ix86_binary_operator_ok (AND, SImode, operands)"
8094 "and{l}\t{%2, %k0|%k0, %2}"
8095 [(set_attr "type" "alu")
8096 (set_attr "mode" "SI")])
8098 (define_expand "andhi3"
8099 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8100 (and:HI (match_operand:HI 1 "nonimmediate_operand" "")
8101 (match_operand:HI 2 "general_operand" "")))
8102 (clobber (reg:CC FLAGS_REG))]
8103 "TARGET_HIMODE_MATH"
8104 "ix86_expand_binary_operator (AND, HImode, operands); DONE;")
8106 (define_insn "*andhi_1"
8107 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
8108 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
8109 (match_operand:HI 2 "general_operand" "ri,rm,L")))
8110 (clobber (reg:CC FLAGS_REG))]
8111 "ix86_binary_operator_ok (AND, HImode, operands)"
8113 switch (get_attr_type (insn))
8116 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
8117 gcc_assert (INTVAL (operands[2]) == 0xff);
8118 return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
8121 gcc_assert (rtx_equal_p (operands[0], operands[1]));
8123 return "and{w}\t{%2, %0|%0, %2}";
8126 [(set_attr "type" "alu,alu,imovx")
8127 (set_attr "length_immediate" "*,*,0")
8128 (set_attr "mode" "HI,HI,SI")])
8130 (define_insn "*andhi_2"
8131 [(set (reg FLAGS_REG)
8132 (compare (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8133 (match_operand:HI 2 "general_operand" "rim,ri"))
8135 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8136 (and:HI (match_dup 1) (match_dup 2)))]
8137 "ix86_match_ccmode (insn, CCNOmode)
8138 && ix86_binary_operator_ok (AND, HImode, operands)"
8139 "and{w}\t{%2, %0|%0, %2}"
8140 [(set_attr "type" "alu")
8141 (set_attr "mode" "HI")])
8143 (define_expand "andqi3"
8144 [(set (match_operand:QI 0 "nonimmediate_operand" "")
8145 (and:QI (match_operand:QI 1 "nonimmediate_operand" "")
8146 (match_operand:QI 2 "general_operand" "")))
8147 (clobber (reg:CC FLAGS_REG))]
8148 "TARGET_QIMODE_MATH"
8149 "ix86_expand_binary_operator (AND, QImode, operands); DONE;")
8151 ;; %%% Potential partial reg stall on alternative 2. What to do?
8152 (define_insn "*andqi_1"
8153 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
8154 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8155 (match_operand:QI 2 "general_operand" "qi,qmi,ri")))
8156 (clobber (reg:CC FLAGS_REG))]
8157 "ix86_binary_operator_ok (AND, QImode, operands)"
8159 and{b}\t{%2, %0|%0, %2}
8160 and{b}\t{%2, %0|%0, %2}
8161 and{l}\t{%k2, %k0|%k0, %k2}"
8162 [(set_attr "type" "alu")
8163 (set_attr "mode" "QI,QI,SI")])
8165 (define_insn "*andqi_1_slp"
8166 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
8167 (and:QI (match_dup 0)
8168 (match_operand:QI 1 "general_operand" "qi,qmi")))
8169 (clobber (reg:CC FLAGS_REG))]
8170 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8171 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8172 "and{b}\t{%1, %0|%0, %1}"
8173 [(set_attr "type" "alu1")
8174 (set_attr "mode" "QI")])
8176 (define_insn "*andqi_2_maybe_si"
8177 [(set (reg FLAGS_REG)
8179 (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8180 (match_operand:QI 2 "general_operand" "qim,qi,i"))
8182 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
8183 (and:QI (match_dup 1) (match_dup 2)))]
8184 "ix86_binary_operator_ok (AND, QImode, operands)
8185 && ix86_match_ccmode (insn,
8186 GET_CODE (operands[2]) == CONST_INT
8187 && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
8189 if (which_alternative == 2)
8191 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
8192 operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
8193 return "and{l}\t{%2, %k0|%k0, %2}";
8195 return "and{b}\t{%2, %0|%0, %2}";
8197 [(set_attr "type" "alu")
8198 (set_attr "mode" "QI,QI,SI")])
8200 (define_insn "*andqi_2"
8201 [(set (reg FLAGS_REG)
8203 (match_operand:QI 1 "nonimmediate_operand" "%0,0")
8204 (match_operand:QI 2 "general_operand" "qim,qi"))
8206 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
8207 (and:QI (match_dup 1) (match_dup 2)))]
8208 "ix86_match_ccmode (insn, CCNOmode)
8209 && ix86_binary_operator_ok (AND, QImode, operands)"
8210 "and{b}\t{%2, %0|%0, %2}"
8211 [(set_attr "type" "alu")
8212 (set_attr "mode" "QI")])
8214 (define_insn "*andqi_2_slp"
8215 [(set (reg FLAGS_REG)
8217 (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8218 (match_operand:QI 1 "nonimmediate_operand" "qmi,qi"))
8220 (set (strict_low_part (match_dup 0))
8221 (and:QI (match_dup 0) (match_dup 1)))]
8222 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8223 && ix86_match_ccmode (insn, CCNOmode)
8224 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8225 "and{b}\t{%1, %0|%0, %1}"
8226 [(set_attr "type" "alu1")
8227 (set_attr "mode" "QI")])
8229 ;; ??? A bug in recog prevents it from recognizing a const_int as an
8230 ;; operand to zero_extend in andqi_ext_1. It was checking explicitly
8231 ;; for a QImode operand, which of course failed.
8233 (define_insn "andqi_ext_0"
8234 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8239 (match_operand 1 "ext_register_operand" "0")
8242 (match_operand 2 "const_int_operand" "n")))
8243 (clobber (reg:CC FLAGS_REG))]
8245 "and{b}\t{%2, %h0|%h0, %2}"
8246 [(set_attr "type" "alu")
8247 (set_attr "length_immediate" "1")
8248 (set_attr "mode" "QI")])
8250 ;; Generated by peephole translating test to and. This shows up
8251 ;; often in fp comparisons.
8253 (define_insn "*andqi_ext_0_cc"
8254 [(set (reg FLAGS_REG)
8258 (match_operand 1 "ext_register_operand" "0")
8261 (match_operand 2 "const_int_operand" "n"))
8263 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8272 "ix86_match_ccmode (insn, CCNOmode)"
8273 "and{b}\t{%2, %h0|%h0, %2}"
8274 [(set_attr "type" "alu")
8275 (set_attr "length_immediate" "1")
8276 (set_attr "mode" "QI")])
8278 (define_insn "*andqi_ext_1"
8279 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8284 (match_operand 1 "ext_register_operand" "0")
8288 (match_operand:QI 2 "general_operand" "Qm"))))
8289 (clobber (reg:CC FLAGS_REG))]
8291 "and{b}\t{%2, %h0|%h0, %2}"
8292 [(set_attr "type" "alu")
8293 (set_attr "length_immediate" "0")
8294 (set_attr "mode" "QI")])
8296 (define_insn "*andqi_ext_1_rex64"
8297 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8302 (match_operand 1 "ext_register_operand" "0")
8306 (match_operand 2 "ext_register_operand" "Q"))))
8307 (clobber (reg:CC FLAGS_REG))]
8309 "and{b}\t{%2, %h0|%h0, %2}"
8310 [(set_attr "type" "alu")
8311 (set_attr "length_immediate" "0")
8312 (set_attr "mode" "QI")])
8314 (define_insn "*andqi_ext_2"
8315 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8320 (match_operand 1 "ext_register_operand" "%0")
8324 (match_operand 2 "ext_register_operand" "Q")
8327 (clobber (reg:CC FLAGS_REG))]
8329 "and{b}\t{%h2, %h0|%h0, %h2}"
8330 [(set_attr "type" "alu")
8331 (set_attr "length_immediate" "0")
8332 (set_attr "mode" "QI")])
8334 ;; Convert wide AND instructions with immediate operand to shorter QImode
8335 ;; equivalents when possible.
8336 ;; Don't do the splitting with memory operands, since it introduces risk
8337 ;; of memory mismatch stalls. We may want to do the splitting for optimizing
8338 ;; for size, but that can (should?) be handled by generic code instead.
8340 [(set (match_operand 0 "register_operand" "")
8341 (and (match_operand 1 "register_operand" "")
8342 (match_operand 2 "const_int_operand" "")))
8343 (clobber (reg:CC FLAGS_REG))]
8345 && QI_REG_P (operands[0])
8346 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8347 && !(~INTVAL (operands[2]) & ~(255 << 8))
8348 && GET_MODE (operands[0]) != QImode"
8349 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8350 (and:SI (zero_extract:SI (match_dup 1)
8351 (const_int 8) (const_int 8))
8353 (clobber (reg:CC FLAGS_REG))])]
8354 "operands[0] = gen_lowpart (SImode, operands[0]);
8355 operands[1] = gen_lowpart (SImode, operands[1]);
8356 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8358 ;; Since AND can be encoded with sign extended immediate, this is only
8359 ;; profitable when 7th bit is not set.
8361 [(set (match_operand 0 "register_operand" "")
8362 (and (match_operand 1 "general_operand" "")
8363 (match_operand 2 "const_int_operand" "")))
8364 (clobber (reg:CC FLAGS_REG))]
8366 && ANY_QI_REG_P (operands[0])
8367 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8368 && !(~INTVAL (operands[2]) & ~255)
8369 && !(INTVAL (operands[2]) & 128)
8370 && GET_MODE (operands[0]) != QImode"
8371 [(parallel [(set (strict_low_part (match_dup 0))
8372 (and:QI (match_dup 1)
8374 (clobber (reg:CC FLAGS_REG))])]
8375 "operands[0] = gen_lowpart (QImode, operands[0]);
8376 operands[1] = gen_lowpart (QImode, operands[1]);
8377 operands[2] = gen_lowpart (QImode, operands[2]);")
8379 ;; Logical inclusive OR instructions
8381 ;; %%% This used to optimize known byte-wide and operations to memory.
8382 ;; If this is considered useful, it should be done with splitters.
8384 (define_expand "iordi3"
8385 [(set (match_operand:DI 0 "nonimmediate_operand" "")
8386 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "")
8387 (match_operand:DI 2 "x86_64_general_operand" "")))
8388 (clobber (reg:CC FLAGS_REG))]
8390 "ix86_expand_binary_operator (IOR, DImode, operands); DONE;")
8392 (define_insn "*iordi_1_rex64"
8393 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
8394 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8395 (match_operand:DI 2 "x86_64_general_operand" "re,rme")))
8396 (clobber (reg:CC FLAGS_REG))]
8398 && ix86_binary_operator_ok (IOR, DImode, operands)"
8399 "or{q}\t{%2, %0|%0, %2}"
8400 [(set_attr "type" "alu")
8401 (set_attr "mode" "DI")])
8403 (define_insn "*iordi_2_rex64"
8404 [(set (reg FLAGS_REG)
8405 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8406 (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
8408 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
8409 (ior:DI (match_dup 1) (match_dup 2)))]
8411 && ix86_match_ccmode (insn, CCNOmode)
8412 && ix86_binary_operator_ok (IOR, DImode, operands)"
8413 "or{q}\t{%2, %0|%0, %2}"
8414 [(set_attr "type" "alu")
8415 (set_attr "mode" "DI")])
8417 (define_insn "*iordi_3_rex64"
8418 [(set (reg FLAGS_REG)
8419 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
8420 (match_operand:DI 2 "x86_64_general_operand" "rem"))
8422 (clobber (match_scratch:DI 0 "=r"))]
8424 && ix86_match_ccmode (insn, CCNOmode)
8425 && ix86_binary_operator_ok (IOR, DImode, operands)"
8426 "or{q}\t{%2, %0|%0, %2}"
8427 [(set_attr "type" "alu")
8428 (set_attr "mode" "DI")])
8431 (define_expand "iorsi3"
8432 [(set (match_operand:SI 0 "nonimmediate_operand" "")
8433 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "")
8434 (match_operand:SI 2 "general_operand" "")))
8435 (clobber (reg:CC FLAGS_REG))]
8437 "ix86_expand_binary_operator (IOR, SImode, operands); DONE;")
8439 (define_insn "*iorsi_1"
8440 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
8441 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8442 (match_operand:SI 2 "general_operand" "ri,rmi")))
8443 (clobber (reg:CC FLAGS_REG))]
8444 "ix86_binary_operator_ok (IOR, SImode, operands)"
8445 "or{l}\t{%2, %0|%0, %2}"
8446 [(set_attr "type" "alu")
8447 (set_attr "mode" "SI")])
8449 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8450 (define_insn "*iorsi_1_zext"
8451 [(set (match_operand:DI 0 "register_operand" "=rm")
8453 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8454 (match_operand:SI 2 "general_operand" "rim"))))
8455 (clobber (reg:CC FLAGS_REG))]
8456 "TARGET_64BIT && ix86_binary_operator_ok (IOR, SImode, operands)"
8457 "or{l}\t{%2, %k0|%k0, %2}"
8458 [(set_attr "type" "alu")
8459 (set_attr "mode" "SI")])
8461 (define_insn "*iorsi_1_zext_imm"
8462 [(set (match_operand:DI 0 "register_operand" "=rm")
8463 (ior:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8464 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8465 (clobber (reg:CC FLAGS_REG))]
8467 "or{l}\t{%2, %k0|%k0, %2}"
8468 [(set_attr "type" "alu")
8469 (set_attr "mode" "SI")])
8471 (define_insn "*iorsi_2"
8472 [(set (reg FLAGS_REG)
8473 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8474 (match_operand:SI 2 "general_operand" "rim,ri"))
8476 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8477 (ior:SI (match_dup 1) (match_dup 2)))]
8478 "ix86_match_ccmode (insn, CCNOmode)
8479 && ix86_binary_operator_ok (IOR, SImode, operands)"
8480 "or{l}\t{%2, %0|%0, %2}"
8481 [(set_attr "type" "alu")
8482 (set_attr "mode" "SI")])
8484 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8485 ;; ??? Special case for immediate operand is missing - it is tricky.
8486 (define_insn "*iorsi_2_zext"
8487 [(set (reg FLAGS_REG)
8488 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8489 (match_operand:SI 2 "general_operand" "rim"))
8491 (set (match_operand:DI 0 "register_operand" "=r")
8492 (zero_extend:DI (ior:SI (match_dup 1) (match_dup 2))))]
8493 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8494 && ix86_binary_operator_ok (IOR, SImode, operands)"
8495 "or{l}\t{%2, %k0|%k0, %2}"
8496 [(set_attr "type" "alu")
8497 (set_attr "mode" "SI")])
8499 (define_insn "*iorsi_2_zext_imm"
8500 [(set (reg FLAGS_REG)
8501 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8502 (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
8504 (set (match_operand:DI 0 "register_operand" "=r")
8505 (ior:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8506 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8507 && ix86_binary_operator_ok (IOR, SImode, operands)"
8508 "or{l}\t{%2, %k0|%k0, %2}"
8509 [(set_attr "type" "alu")
8510 (set_attr "mode" "SI")])
8512 (define_insn "*iorsi_3"
8513 [(set (reg FLAGS_REG)
8514 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8515 (match_operand:SI 2 "general_operand" "rim"))
8517 (clobber (match_scratch:SI 0 "=r"))]
8518 "ix86_match_ccmode (insn, CCNOmode)
8519 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8520 "or{l}\t{%2, %0|%0, %2}"
8521 [(set_attr "type" "alu")
8522 (set_attr "mode" "SI")])
8524 (define_expand "iorhi3"
8525 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8526 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "")
8527 (match_operand:HI 2 "general_operand" "")))
8528 (clobber (reg:CC FLAGS_REG))]
8529 "TARGET_HIMODE_MATH"
8530 "ix86_expand_binary_operator (IOR, HImode, operands); DONE;")
8532 (define_insn "*iorhi_1"
8533 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
8534 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8535 (match_operand:HI 2 "general_operand" "rmi,ri")))
8536 (clobber (reg:CC FLAGS_REG))]
8537 "ix86_binary_operator_ok (IOR, HImode, operands)"
8538 "or{w}\t{%2, %0|%0, %2}"
8539 [(set_attr "type" "alu")
8540 (set_attr "mode" "HI")])
8542 (define_insn "*iorhi_2"
8543 [(set (reg FLAGS_REG)
8544 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8545 (match_operand:HI 2 "general_operand" "rim,ri"))
8547 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8548 (ior:HI (match_dup 1) (match_dup 2)))]
8549 "ix86_match_ccmode (insn, CCNOmode)
8550 && ix86_binary_operator_ok (IOR, HImode, operands)"
8551 "or{w}\t{%2, %0|%0, %2}"
8552 [(set_attr "type" "alu")
8553 (set_attr "mode" "HI")])
8555 (define_insn "*iorhi_3"
8556 [(set (reg FLAGS_REG)
8557 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
8558 (match_operand:HI 2 "general_operand" "rim"))
8560 (clobber (match_scratch:HI 0 "=r"))]
8561 "ix86_match_ccmode (insn, CCNOmode)
8562 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8563 "or{w}\t{%2, %0|%0, %2}"
8564 [(set_attr "type" "alu")
8565 (set_attr "mode" "HI")])
8567 (define_expand "iorqi3"
8568 [(set (match_operand:QI 0 "nonimmediate_operand" "")
8569 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "")
8570 (match_operand:QI 2 "general_operand" "")))
8571 (clobber (reg:CC FLAGS_REG))]
8572 "TARGET_QIMODE_MATH"
8573 "ix86_expand_binary_operator (IOR, QImode, operands); DONE;")
8575 ;; %%% Potential partial reg stall on alternative 2. What to do?
8576 (define_insn "*iorqi_1"
8577 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
8578 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8579 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
8580 (clobber (reg:CC FLAGS_REG))]
8581 "ix86_binary_operator_ok (IOR, QImode, operands)"
8583 or{b}\t{%2, %0|%0, %2}
8584 or{b}\t{%2, %0|%0, %2}
8585 or{l}\t{%k2, %k0|%k0, %k2}"
8586 [(set_attr "type" "alu")
8587 (set_attr "mode" "QI,QI,SI")])
8589 (define_insn "*iorqi_1_slp"
8590 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
8591 (ior:QI (match_dup 0)
8592 (match_operand:QI 1 "general_operand" "qmi,qi")))
8593 (clobber (reg:CC FLAGS_REG))]
8594 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8595 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8596 "or{b}\t{%1, %0|%0, %1}"
8597 [(set_attr "type" "alu1")
8598 (set_attr "mode" "QI")])
8600 (define_insn "*iorqi_2"
8601 [(set (reg FLAGS_REG)
8602 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
8603 (match_operand:QI 2 "general_operand" "qim,qi"))
8605 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
8606 (ior:QI (match_dup 1) (match_dup 2)))]
8607 "ix86_match_ccmode (insn, CCNOmode)
8608 && ix86_binary_operator_ok (IOR, QImode, operands)"
8609 "or{b}\t{%2, %0|%0, %2}"
8610 [(set_attr "type" "alu")
8611 (set_attr "mode" "QI")])
8613 (define_insn "*iorqi_2_slp"
8614 [(set (reg FLAGS_REG)
8615 (compare (ior:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8616 (match_operand:QI 1 "general_operand" "qim,qi"))
8618 (set (strict_low_part (match_dup 0))
8619 (ior:QI (match_dup 0) (match_dup 1)))]
8620 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8621 && ix86_match_ccmode (insn, CCNOmode)
8622 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8623 "or{b}\t{%1, %0|%0, %1}"
8624 [(set_attr "type" "alu1")
8625 (set_attr "mode" "QI")])
8627 (define_insn "*iorqi_3"
8628 [(set (reg FLAGS_REG)
8629 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
8630 (match_operand:QI 2 "general_operand" "qim"))
8632 (clobber (match_scratch:QI 0 "=q"))]
8633 "ix86_match_ccmode (insn, CCNOmode)
8634 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8635 "or{b}\t{%2, %0|%0, %2}"
8636 [(set_attr "type" "alu")
8637 (set_attr "mode" "QI")])
8639 (define_insn "iorqi_ext_0"
8640 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8645 (match_operand 1 "ext_register_operand" "0")
8648 (match_operand 2 "const_int_operand" "n")))
8649 (clobber (reg:CC FLAGS_REG))]
8650 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8651 "or{b}\t{%2, %h0|%h0, %2}"
8652 [(set_attr "type" "alu")
8653 (set_attr "length_immediate" "1")
8654 (set_attr "mode" "QI")])
8656 (define_insn "*iorqi_ext_1"
8657 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8662 (match_operand 1 "ext_register_operand" "0")
8666 (match_operand:QI 2 "general_operand" "Qm"))))
8667 (clobber (reg:CC FLAGS_REG))]
8669 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
8670 "or{b}\t{%2, %h0|%h0, %2}"
8671 [(set_attr "type" "alu")
8672 (set_attr "length_immediate" "0")
8673 (set_attr "mode" "QI")])
8675 (define_insn "*iorqi_ext_1_rex64"
8676 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8681 (match_operand 1 "ext_register_operand" "0")
8685 (match_operand 2 "ext_register_operand" "Q"))))
8686 (clobber (reg:CC FLAGS_REG))]
8688 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
8689 "or{b}\t{%2, %h0|%h0, %2}"
8690 [(set_attr "type" "alu")
8691 (set_attr "length_immediate" "0")
8692 (set_attr "mode" "QI")])
8694 (define_insn "*iorqi_ext_2"
8695 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8699 (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
8702 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
8705 (clobber (reg:CC FLAGS_REG))]
8706 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8707 "ior{b}\t{%h2, %h0|%h0, %h2}"
8708 [(set_attr "type" "alu")
8709 (set_attr "length_immediate" "0")
8710 (set_attr "mode" "QI")])
8713 [(set (match_operand 0 "register_operand" "")
8714 (ior (match_operand 1 "register_operand" "")
8715 (match_operand 2 "const_int_operand" "")))
8716 (clobber (reg:CC FLAGS_REG))]
8718 && QI_REG_P (operands[0])
8719 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8720 && !(INTVAL (operands[2]) & ~(255 << 8))
8721 && GET_MODE (operands[0]) != QImode"
8722 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8723 (ior:SI (zero_extract:SI (match_dup 1)
8724 (const_int 8) (const_int 8))
8726 (clobber (reg:CC FLAGS_REG))])]
8727 "operands[0] = gen_lowpart (SImode, operands[0]);
8728 operands[1] = gen_lowpart (SImode, operands[1]);
8729 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8731 ;; Since OR can be encoded with sign extended immediate, this is only
8732 ;; profitable when 7th bit is set.
8734 [(set (match_operand 0 "register_operand" "")
8735 (ior (match_operand 1 "general_operand" "")
8736 (match_operand 2 "const_int_operand" "")))
8737 (clobber (reg:CC FLAGS_REG))]
8739 && ANY_QI_REG_P (operands[0])
8740 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8741 && !(INTVAL (operands[2]) & ~255)
8742 && (INTVAL (operands[2]) & 128)
8743 && GET_MODE (operands[0]) != QImode"
8744 [(parallel [(set (strict_low_part (match_dup 0))
8745 (ior:QI (match_dup 1)
8747 (clobber (reg:CC FLAGS_REG))])]
8748 "operands[0] = gen_lowpart (QImode, operands[0]);
8749 operands[1] = gen_lowpart (QImode, operands[1]);
8750 operands[2] = gen_lowpart (QImode, operands[2]);")
8752 ;; Logical XOR instructions
8754 ;; %%% This used to optimize known byte-wide and operations to memory.
8755 ;; If this is considered useful, it should be done with splitters.
8757 (define_expand "xordi3"
8758 [(set (match_operand:DI 0 "nonimmediate_operand" "")
8759 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "")
8760 (match_operand:DI 2 "x86_64_general_operand" "")))
8761 (clobber (reg:CC FLAGS_REG))]
8763 "ix86_expand_binary_operator (XOR, DImode, operands); DONE;")
8765 (define_insn "*xordi_1_rex64"
8766 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
8767 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8768 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
8769 (clobber (reg:CC FLAGS_REG))]
8771 && ix86_binary_operator_ok (XOR, DImode, operands)"
8773 xor{q}\t{%2, %0|%0, %2}
8774 xor{q}\t{%2, %0|%0, %2}"
8775 [(set_attr "type" "alu")
8776 (set_attr "mode" "DI,DI")])
8778 (define_insn "*xordi_2_rex64"
8779 [(set (reg FLAGS_REG)
8780 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8781 (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
8783 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
8784 (xor:DI (match_dup 1) (match_dup 2)))]
8786 && ix86_match_ccmode (insn, CCNOmode)
8787 && ix86_binary_operator_ok (XOR, DImode, operands)"
8789 xor{q}\t{%2, %0|%0, %2}
8790 xor{q}\t{%2, %0|%0, %2}"
8791 [(set_attr "type" "alu")
8792 (set_attr "mode" "DI,DI")])
8794 (define_insn "*xordi_3_rex64"
8795 [(set (reg FLAGS_REG)
8796 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
8797 (match_operand:DI 2 "x86_64_general_operand" "rem"))
8799 (clobber (match_scratch:DI 0 "=r"))]
8801 && ix86_match_ccmode (insn, CCNOmode)
8802 && ix86_binary_operator_ok (XOR, DImode, operands)"
8803 "xor{q}\t{%2, %0|%0, %2}"
8804 [(set_attr "type" "alu")
8805 (set_attr "mode" "DI")])
8807 (define_expand "xorsi3"
8808 [(set (match_operand:SI 0 "nonimmediate_operand" "")
8809 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "")
8810 (match_operand:SI 2 "general_operand" "")))
8811 (clobber (reg:CC FLAGS_REG))]
8813 "ix86_expand_binary_operator (XOR, SImode, operands); DONE;")
8815 (define_insn "*xorsi_1"
8816 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
8817 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8818 (match_operand:SI 2 "general_operand" "ri,rm")))
8819 (clobber (reg:CC FLAGS_REG))]
8820 "ix86_binary_operator_ok (XOR, SImode, operands)"
8821 "xor{l}\t{%2, %0|%0, %2}"
8822 [(set_attr "type" "alu")
8823 (set_attr "mode" "SI")])
8825 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8826 ;; Add speccase for immediates
8827 (define_insn "*xorsi_1_zext"
8828 [(set (match_operand:DI 0 "register_operand" "=r")
8830 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8831 (match_operand:SI 2 "general_operand" "rim"))))
8832 (clobber (reg:CC FLAGS_REG))]
8833 "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
8834 "xor{l}\t{%2, %k0|%k0, %2}"
8835 [(set_attr "type" "alu")
8836 (set_attr "mode" "SI")])
8838 (define_insn "*xorsi_1_zext_imm"
8839 [(set (match_operand:DI 0 "register_operand" "=r")
8840 (xor:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8841 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8842 (clobber (reg:CC FLAGS_REG))]
8843 "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
8844 "xor{l}\t{%2, %k0|%k0, %2}"
8845 [(set_attr "type" "alu")
8846 (set_attr "mode" "SI")])
8848 (define_insn "*xorsi_2"
8849 [(set (reg FLAGS_REG)
8850 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8851 (match_operand:SI 2 "general_operand" "rim,ri"))
8853 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8854 (xor:SI (match_dup 1) (match_dup 2)))]
8855 "ix86_match_ccmode (insn, CCNOmode)
8856 && ix86_binary_operator_ok (XOR, SImode, operands)"
8857 "xor{l}\t{%2, %0|%0, %2}"
8858 [(set_attr "type" "alu")
8859 (set_attr "mode" "SI")])
8861 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8862 ;; ??? Special case for immediate operand is missing - it is tricky.
8863 (define_insn "*xorsi_2_zext"
8864 [(set (reg FLAGS_REG)
8865 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8866 (match_operand:SI 2 "general_operand" "rim"))
8868 (set (match_operand:DI 0 "register_operand" "=r")
8869 (zero_extend:DI (xor:SI (match_dup 1) (match_dup 2))))]
8870 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8871 && ix86_binary_operator_ok (XOR, SImode, operands)"
8872 "xor{l}\t{%2, %k0|%k0, %2}"
8873 [(set_attr "type" "alu")
8874 (set_attr "mode" "SI")])
8876 (define_insn "*xorsi_2_zext_imm"
8877 [(set (reg FLAGS_REG)
8878 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8879 (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
8881 (set (match_operand:DI 0 "register_operand" "=r")
8882 (xor:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8883 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8884 && ix86_binary_operator_ok (XOR, SImode, operands)"
8885 "xor{l}\t{%2, %k0|%k0, %2}"
8886 [(set_attr "type" "alu")
8887 (set_attr "mode" "SI")])
8889 (define_insn "*xorsi_3"
8890 [(set (reg FLAGS_REG)
8891 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8892 (match_operand:SI 2 "general_operand" "rim"))
8894 (clobber (match_scratch:SI 0 "=r"))]
8895 "ix86_match_ccmode (insn, CCNOmode)
8896 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8897 "xor{l}\t{%2, %0|%0, %2}"
8898 [(set_attr "type" "alu")
8899 (set_attr "mode" "SI")])
8901 (define_expand "xorhi3"
8902 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8903 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "")
8904 (match_operand:HI 2 "general_operand" "")))
8905 (clobber (reg:CC FLAGS_REG))]
8906 "TARGET_HIMODE_MATH"
8907 "ix86_expand_binary_operator (XOR, HImode, operands); DONE;")
8909 (define_insn "*xorhi_1"
8910 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
8911 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8912 (match_operand:HI 2 "general_operand" "rmi,ri")))
8913 (clobber (reg:CC FLAGS_REG))]
8914 "ix86_binary_operator_ok (XOR, HImode, operands)"
8915 "xor{w}\t{%2, %0|%0, %2}"
8916 [(set_attr "type" "alu")
8917 (set_attr "mode" "HI")])
8919 (define_insn "*xorhi_2"
8920 [(set (reg FLAGS_REG)
8921 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8922 (match_operand:HI 2 "general_operand" "rim,ri"))
8924 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8925 (xor:HI (match_dup 1) (match_dup 2)))]
8926 "ix86_match_ccmode (insn, CCNOmode)
8927 && ix86_binary_operator_ok (XOR, HImode, operands)"
8928 "xor{w}\t{%2, %0|%0, %2}"
8929 [(set_attr "type" "alu")
8930 (set_attr "mode" "HI")])
8932 (define_insn "*xorhi_3"
8933 [(set (reg FLAGS_REG)
8934 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
8935 (match_operand:HI 2 "general_operand" "rim"))
8937 (clobber (match_scratch:HI 0 "=r"))]
8938 "ix86_match_ccmode (insn, CCNOmode)
8939 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8940 "xor{w}\t{%2, %0|%0, %2}"
8941 [(set_attr "type" "alu")
8942 (set_attr "mode" "HI")])
8944 (define_expand "xorqi3"
8945 [(set (match_operand:QI 0 "nonimmediate_operand" "")
8946 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "")
8947 (match_operand:QI 2 "general_operand" "")))
8948 (clobber (reg:CC FLAGS_REG))]
8949 "TARGET_QIMODE_MATH"
8950 "ix86_expand_binary_operator (XOR, QImode, operands); DONE;")
8952 ;; %%% Potential partial reg stall on alternative 2. What to do?
8953 (define_insn "*xorqi_1"
8954 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
8955 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8956 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
8957 (clobber (reg:CC FLAGS_REG))]
8958 "ix86_binary_operator_ok (XOR, QImode, operands)"
8960 xor{b}\t{%2, %0|%0, %2}
8961 xor{b}\t{%2, %0|%0, %2}
8962 xor{l}\t{%k2, %k0|%k0, %k2}"
8963 [(set_attr "type" "alu")
8964 (set_attr "mode" "QI,QI,SI")])
8966 (define_insn "*xorqi_1_slp"
8967 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
8968 (xor:QI (match_dup 0)
8969 (match_operand:QI 1 "general_operand" "qi,qmi")))
8970 (clobber (reg:CC FLAGS_REG))]
8971 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8972 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8973 "xor{b}\t{%1, %0|%0, %1}"
8974 [(set_attr "type" "alu1")
8975 (set_attr "mode" "QI")])
8977 (define_insn "xorqi_ext_0"
8978 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8983 (match_operand 1 "ext_register_operand" "0")
8986 (match_operand 2 "const_int_operand" "n")))
8987 (clobber (reg:CC FLAGS_REG))]
8988 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8989 "xor{b}\t{%2, %h0|%h0, %2}"
8990 [(set_attr "type" "alu")
8991 (set_attr "length_immediate" "1")
8992 (set_attr "mode" "QI")])
8994 (define_insn "*xorqi_ext_1"
8995 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9000 (match_operand 1 "ext_register_operand" "0")
9004 (match_operand:QI 2 "general_operand" "Qm"))))
9005 (clobber (reg:CC FLAGS_REG))]
9007 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9008 "xor{b}\t{%2, %h0|%h0, %2}"
9009 [(set_attr "type" "alu")
9010 (set_attr "length_immediate" "0")
9011 (set_attr "mode" "QI")])
9013 (define_insn "*xorqi_ext_1_rex64"
9014 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9019 (match_operand 1 "ext_register_operand" "0")
9023 (match_operand 2 "ext_register_operand" "Q"))))
9024 (clobber (reg:CC FLAGS_REG))]
9026 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9027 "xor{b}\t{%2, %h0|%h0, %2}"
9028 [(set_attr "type" "alu")
9029 (set_attr "length_immediate" "0")
9030 (set_attr "mode" "QI")])
9032 (define_insn "*xorqi_ext_2"
9033 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9037 (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
9040 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
9043 (clobber (reg:CC FLAGS_REG))]
9044 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9045 "xor{b}\t{%h2, %h0|%h0, %h2}"
9046 [(set_attr "type" "alu")
9047 (set_attr "length_immediate" "0")
9048 (set_attr "mode" "QI")])
9050 (define_insn "*xorqi_cc_1"
9051 [(set (reg FLAGS_REG)
9053 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9054 (match_operand:QI 2 "general_operand" "qim,qi"))
9056 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9057 (xor:QI (match_dup 1) (match_dup 2)))]
9058 "ix86_match_ccmode (insn, CCNOmode)
9059 && ix86_binary_operator_ok (XOR, QImode, operands)"
9060 "xor{b}\t{%2, %0|%0, %2}"
9061 [(set_attr "type" "alu")
9062 (set_attr "mode" "QI")])
9064 (define_insn "*xorqi_2_slp"
9065 [(set (reg FLAGS_REG)
9066 (compare (xor:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9067 (match_operand:QI 1 "general_operand" "qim,qi"))
9069 (set (strict_low_part (match_dup 0))
9070 (xor:QI (match_dup 0) (match_dup 1)))]
9071 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9072 && ix86_match_ccmode (insn, CCNOmode)
9073 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
9074 "xor{b}\t{%1, %0|%0, %1}"
9075 [(set_attr "type" "alu1")
9076 (set_attr "mode" "QI")])
9078 (define_insn "*xorqi_cc_2"
9079 [(set (reg FLAGS_REG)
9081 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
9082 (match_operand:QI 2 "general_operand" "qim"))
9084 (clobber (match_scratch:QI 0 "=q"))]
9085 "ix86_match_ccmode (insn, CCNOmode)
9086 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
9087 "xor{b}\t{%2, %0|%0, %2}"
9088 [(set_attr "type" "alu")
9089 (set_attr "mode" "QI")])
9091 (define_insn "*xorqi_cc_ext_1"
9092 [(set (reg FLAGS_REG)
9096 (match_operand 1 "ext_register_operand" "0")
9099 (match_operand:QI 2 "general_operand" "qmn"))
9101 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
9105 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9107 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9108 "xor{b}\t{%2, %h0|%h0, %2}"
9109 [(set_attr "type" "alu")
9110 (set_attr "mode" "QI")])
9112 (define_insn "*xorqi_cc_ext_1_rex64"
9113 [(set (reg FLAGS_REG)
9117 (match_operand 1 "ext_register_operand" "0")
9120 (match_operand:QI 2 "nonmemory_operand" "Qn"))
9122 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9126 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9128 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9129 "xor{b}\t{%2, %h0|%h0, %2}"
9130 [(set_attr "type" "alu")
9131 (set_attr "mode" "QI")])
9133 (define_expand "xorqi_cc_ext_1"
9135 (set (reg:CCNO FLAGS_REG)
9139 (match_operand 1 "ext_register_operand" "")
9142 (match_operand:QI 2 "general_operand" ""))
9144 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
9148 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9154 [(set (match_operand 0 "register_operand" "")
9155 (xor (match_operand 1 "register_operand" "")
9156 (match_operand 2 "const_int_operand" "")))
9157 (clobber (reg:CC FLAGS_REG))]
9159 && QI_REG_P (operands[0])
9160 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9161 && !(INTVAL (operands[2]) & ~(255 << 8))
9162 && GET_MODE (operands[0]) != QImode"
9163 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9164 (xor:SI (zero_extract:SI (match_dup 1)
9165 (const_int 8) (const_int 8))
9167 (clobber (reg:CC FLAGS_REG))])]
9168 "operands[0] = gen_lowpart (SImode, operands[0]);
9169 operands[1] = gen_lowpart (SImode, operands[1]);
9170 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9172 ;; Since XOR can be encoded with sign extended immediate, this is only
9173 ;; profitable when 7th bit is set.
9175 [(set (match_operand 0 "register_operand" "")
9176 (xor (match_operand 1 "general_operand" "")
9177 (match_operand 2 "const_int_operand" "")))
9178 (clobber (reg:CC FLAGS_REG))]
9180 && ANY_QI_REG_P (operands[0])
9181 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9182 && !(INTVAL (operands[2]) & ~255)
9183 && (INTVAL (operands[2]) & 128)
9184 && GET_MODE (operands[0]) != QImode"
9185 [(parallel [(set (strict_low_part (match_dup 0))
9186 (xor:QI (match_dup 1)
9188 (clobber (reg:CC FLAGS_REG))])]
9189 "operands[0] = gen_lowpart (QImode, operands[0]);
9190 operands[1] = gen_lowpart (QImode, operands[1]);
9191 operands[2] = gen_lowpart (QImode, operands[2]);")
9193 ;; Negation instructions
9195 (define_expand "negdi2"
9196 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
9197 (neg:DI (match_operand:DI 1 "nonimmediate_operand" "")))
9198 (clobber (reg:CC FLAGS_REG))])]
9200 "ix86_expand_unary_operator (NEG, DImode, operands); DONE;")
9202 (define_insn "*negdi2_1"
9203 [(set (match_operand:DI 0 "nonimmediate_operand" "=ro")
9204 (neg:DI (match_operand:DI 1 "general_operand" "0")))
9205 (clobber (reg:CC FLAGS_REG))]
9207 && ix86_unary_operator_ok (NEG, DImode, operands)"
9211 [(set (match_operand:DI 0 "nonimmediate_operand" "")
9212 (neg:DI (match_operand:DI 1 "general_operand" "")))
9213 (clobber (reg:CC FLAGS_REG))]
9214 "!TARGET_64BIT && reload_completed"
9216 [(set (reg:CCZ FLAGS_REG)
9217 (compare:CCZ (neg:SI (match_dup 2)) (const_int 0)))
9218 (set (match_dup 0) (neg:SI (match_dup 2)))])
9221 (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
9224 (clobber (reg:CC FLAGS_REG))])
9227 (neg:SI (match_dup 1)))
9228 (clobber (reg:CC FLAGS_REG))])]
9229 "split_di (operands+1, 1, operands+2, operands+3);
9230 split_di (operands+0, 1, operands+0, operands+1);")
9232 (define_insn "*negdi2_1_rex64"
9233 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9234 (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0")))
9235 (clobber (reg:CC FLAGS_REG))]
9236 "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
9238 [(set_attr "type" "negnot")
9239 (set_attr "mode" "DI")])
9241 ;; The problem with neg is that it does not perform (compare x 0),
9242 ;; it really performs (compare 0 x), which leaves us with the zero
9243 ;; flag being the only useful item.
9245 (define_insn "*negdi2_cmpz_rex64"
9246 [(set (reg:CCZ FLAGS_REG)
9247 (compare:CCZ (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
9249 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9250 (neg:DI (match_dup 1)))]
9251 "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
9253 [(set_attr "type" "negnot")
9254 (set_attr "mode" "DI")])
9257 (define_expand "negsi2"
9258 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
9259 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "")))
9260 (clobber (reg:CC FLAGS_REG))])]
9262 "ix86_expand_unary_operator (NEG, SImode, operands); DONE;")
9264 (define_insn "*negsi2_1"
9265 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9266 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0")))
9267 (clobber (reg:CC FLAGS_REG))]
9268 "ix86_unary_operator_ok (NEG, SImode, operands)"
9270 [(set_attr "type" "negnot")
9271 (set_attr "mode" "SI")])
9273 ;; Combine is quite creative about this pattern.
9274 (define_insn "*negsi2_1_zext"
9275 [(set (match_operand:DI 0 "register_operand" "=r")
9276 (lshiftrt:DI (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
9279 (clobber (reg:CC FLAGS_REG))]
9280 "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
9282 [(set_attr "type" "negnot")
9283 (set_attr "mode" "SI")])
9285 ;; The problem with neg is that it does not perform (compare x 0),
9286 ;; it really performs (compare 0 x), which leaves us with the zero
9287 ;; flag being the only useful item.
9289 (define_insn "*negsi2_cmpz"
9290 [(set (reg:CCZ FLAGS_REG)
9291 (compare:CCZ (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
9293 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9294 (neg:SI (match_dup 1)))]
9295 "ix86_unary_operator_ok (NEG, SImode, operands)"
9297 [(set_attr "type" "negnot")
9298 (set_attr "mode" "SI")])
9300 (define_insn "*negsi2_cmpz_zext"
9301 [(set (reg:CCZ FLAGS_REG)
9302 (compare:CCZ (lshiftrt:DI
9304 (match_operand:DI 1 "register_operand" "0")
9308 (set (match_operand:DI 0 "register_operand" "=r")
9309 (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
9312 "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
9314 [(set_attr "type" "negnot")
9315 (set_attr "mode" "SI")])
9317 (define_expand "neghi2"
9318 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
9319 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "")))
9320 (clobber (reg:CC FLAGS_REG))])]
9321 "TARGET_HIMODE_MATH"
9322 "ix86_expand_unary_operator (NEG, HImode, operands); DONE;")
9324 (define_insn "*neghi2_1"
9325 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9326 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0")))
9327 (clobber (reg:CC FLAGS_REG))]
9328 "ix86_unary_operator_ok (NEG, HImode, operands)"
9330 [(set_attr "type" "negnot")
9331 (set_attr "mode" "HI")])
9333 (define_insn "*neghi2_cmpz"
9334 [(set (reg:CCZ FLAGS_REG)
9335 (compare:CCZ (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
9337 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9338 (neg:HI (match_dup 1)))]
9339 "ix86_unary_operator_ok (NEG, HImode, operands)"
9341 [(set_attr "type" "negnot")
9342 (set_attr "mode" "HI")])
9344 (define_expand "negqi2"
9345 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
9346 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "")))
9347 (clobber (reg:CC FLAGS_REG))])]
9348 "TARGET_QIMODE_MATH"
9349 "ix86_expand_unary_operator (NEG, QImode, operands); DONE;")
9351 (define_insn "*negqi2_1"
9352 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9353 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0")))
9354 (clobber (reg:CC FLAGS_REG))]
9355 "ix86_unary_operator_ok (NEG, QImode, operands)"
9357 [(set_attr "type" "negnot")
9358 (set_attr "mode" "QI")])
9360 (define_insn "*negqi2_cmpz"
9361 [(set (reg:CCZ FLAGS_REG)
9362 (compare:CCZ (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
9364 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9365 (neg:QI (match_dup 1)))]
9366 "ix86_unary_operator_ok (NEG, QImode, operands)"
9368 [(set_attr "type" "negnot")
9369 (set_attr "mode" "QI")])
9371 ;; Changing of sign for FP values is doable using integer unit too.
9373 (define_expand "negsf2"
9374 [(set (match_operand:SF 0 "nonimmediate_operand" "")
9375 (neg:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
9376 "TARGET_80387 || TARGET_SSE_MATH"
9377 "ix86_expand_fp_absneg_operator (NEG, SFmode, operands); DONE;")
9379 (define_expand "abssf2"
9380 [(set (match_operand:SF 0 "nonimmediate_operand" "")
9381 (abs:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
9382 "TARGET_80387 || TARGET_SSE_MATH"
9383 "ix86_expand_fp_absneg_operator (ABS, SFmode, operands); DONE;")
9385 (define_insn "*absnegsf2_mixed"
9386 [(set (match_operand:SF 0 "nonimmediate_operand" "=x#f,x#f,f#x,rm")
9387 (match_operator:SF 3 "absneg_operator"
9388 [(match_operand:SF 1 "nonimmediate_operand" "0 ,x#f,0 ,0")]))
9389 (use (match_operand:V4SF 2 "nonimmediate_operand" "xm ,0 ,X ,X"))
9390 (clobber (reg:CC FLAGS_REG))]
9391 "TARGET_SSE_MATH && TARGET_MIX_SSE_I387
9392 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9395 (define_insn "*absnegsf2_sse"
9396 [(set (match_operand:SF 0 "nonimmediate_operand" "=x,x,rm")
9397 (match_operator:SF 3 "absneg_operator"
9398 [(match_operand:SF 1 "nonimmediate_operand" "0 ,x,0")]))
9399 (use (match_operand:V4SF 2 "nonimmediate_operand" "xm,0,X"))
9400 (clobber (reg:CC FLAGS_REG))]
9402 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9405 (define_insn "*absnegsf2_i387"
9406 [(set (match_operand:SF 0 "nonimmediate_operand" "=f,rm")
9407 (match_operator:SF 3 "absneg_operator"
9408 [(match_operand:SF 1 "nonimmediate_operand" "0,0")]))
9409 (use (match_operand 2 "" ""))
9410 (clobber (reg:CC FLAGS_REG))]
9411 "TARGET_80387 && !TARGET_SSE_MATH
9412 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9415 (define_expand "copysignsf3"
9416 [(match_operand:SF 0 "register_operand" "")
9417 (match_operand:SF 1 "nonmemory_operand" "")
9418 (match_operand:SF 2 "register_operand" "")]
9421 ix86_expand_copysign (operands);
9425 (define_insn_and_split "copysignsf3_const"
9426 [(set (match_operand:SF 0 "register_operand" "=x")
9428 [(match_operand:V4SF 1 "vector_move_operand" "xmC")
9429 (match_operand:SF 2 "register_operand" "0")
9430 (match_operand:V4SF 3 "nonimmediate_operand" "xm")]
9434 "&& reload_completed"
9437 ix86_split_copysign_const (operands);
9441 (define_insn "copysignsf3_var"
9442 [(set (match_operand:SF 0 "register_operand" "=x, x, x, x,x")
9444 [(match_operand:SF 2 "register_operand" " x, 0, 0, x,x")
9445 (match_operand:SF 3 "register_operand" " 1, 1, x, 1,x")
9446 (match_operand:V4SF 4 "nonimmediate_operand" " X,xm,xm, 0,0")
9447 (match_operand:V4SF 5 "nonimmediate_operand" " 0,xm, 1,xm,1")]
9449 (clobber (match_scratch:V4SF 1 "=x, x, x, x,x"))]
9454 [(set (match_operand:SF 0 "register_operand" "")
9456 [(match_operand:SF 2 "register_operand" "")
9457 (match_operand:SF 3 "register_operand" "")
9458 (match_operand:V4SF 4 "" "")
9459 (match_operand:V4SF 5 "" "")]
9461 (clobber (match_scratch:V4SF 1 ""))]
9462 "TARGET_SSE_MATH && reload_completed"
9465 ix86_split_copysign_var (operands);
9469 (define_expand "negdf2"
9470 [(set (match_operand:DF 0 "nonimmediate_operand" "")
9471 (neg:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
9472 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
9473 "ix86_expand_fp_absneg_operator (NEG, DFmode, operands); DONE;")
9475 (define_expand "absdf2"
9476 [(set (match_operand:DF 0 "nonimmediate_operand" "")
9477 (abs:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
9478 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
9479 "ix86_expand_fp_absneg_operator (ABS, DFmode, operands); DONE;")
9481 (define_insn "*absnegdf2_mixed"
9482 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y#f,Y#f,f#Y,rm")
9483 (match_operator:DF 3 "absneg_operator"
9484 [(match_operand:DF 1 "nonimmediate_operand" "0 ,Y#f,0 ,0")]))
9485 (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym ,0 ,X ,X"))
9486 (clobber (reg:CC FLAGS_REG))]
9487 "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
9488 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9491 (define_insn "*absnegdf2_sse"
9492 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y,Y,rm")
9493 (match_operator:DF 3 "absneg_operator"
9494 [(match_operand:DF 1 "nonimmediate_operand" "0 ,Y,0")]))
9495 (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym,0,X"))
9496 (clobber (reg:CC FLAGS_REG))]
9497 "TARGET_SSE2 && TARGET_SSE_MATH
9498 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9501 (define_insn "*absnegdf2_i387"
9502 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,rm")
9503 (match_operator:DF 3 "absneg_operator"
9504 [(match_operand:DF 1 "nonimmediate_operand" "0,0")]))
9505 (use (match_operand 2 "" ""))
9506 (clobber (reg:CC FLAGS_REG))]
9507 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
9508 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9511 (define_expand "copysigndf3"
9512 [(match_operand:DF 0 "register_operand" "")
9513 (match_operand:DF 1 "nonmemory_operand" "")
9514 (match_operand:DF 2 "register_operand" "")]
9515 "TARGET_SSE2 && TARGET_SSE_MATH"
9517 ix86_expand_copysign (operands);
9521 (define_insn_and_split "copysigndf3_const"
9522 [(set (match_operand:DF 0 "register_operand" "=x")
9524 [(match_operand:V2DF 1 "vector_move_operand" "xmC")
9525 (match_operand:DF 2 "register_operand" "0")
9526 (match_operand:V2DF 3 "nonimmediate_operand" "xm")]
9528 "TARGET_SSE2 && TARGET_SSE_MATH"
9530 "&& reload_completed"
9533 ix86_split_copysign_const (operands);
9537 (define_insn "copysigndf3_var"
9538 [(set (match_operand:DF 0 "register_operand" "=x, x, x, x,x")
9540 [(match_operand:DF 2 "register_operand" " x, 0, 0, x,x")
9541 (match_operand:DF 3 "register_operand" " 1, 1, x, 1,x")
9542 (match_operand:V2DF 4 "nonimmediate_operand" " X,xm,xm, 0,0")
9543 (match_operand:V2DF 5 "nonimmediate_operand" " 0,xm, 1,xm,1")]
9545 (clobber (match_scratch:V2DF 1 "=x, x, x, x,x"))]
9546 "TARGET_SSE2 && TARGET_SSE_MATH"
9550 [(set (match_operand:DF 0 "register_operand" "")
9552 [(match_operand:DF 2 "register_operand" "")
9553 (match_operand:DF 3 "register_operand" "")
9554 (match_operand:V2DF 4 "" "")
9555 (match_operand:V2DF 5 "" "")]
9557 (clobber (match_scratch:V2DF 1 ""))]
9558 "TARGET_SSE2 && TARGET_SSE_MATH && reload_completed"
9561 ix86_split_copysign_var (operands);
9565 (define_expand "negxf2"
9566 [(set (match_operand:XF 0 "nonimmediate_operand" "")
9567 (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))]
9569 "ix86_expand_fp_absneg_operator (NEG, XFmode, operands); DONE;")
9571 (define_expand "absxf2"
9572 [(set (match_operand:XF 0 "nonimmediate_operand" "")
9573 (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))]
9575 "ix86_expand_fp_absneg_operator (ABS, XFmode, operands); DONE;")
9577 (define_insn "*absnegxf2_i387"
9578 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,?rm")
9579 (match_operator:XF 3 "absneg_operator"
9580 [(match_operand:XF 1 "nonimmediate_operand" "0,0")]))
9581 (use (match_operand 2 "" ""))
9582 (clobber (reg:CC FLAGS_REG))]
9584 && ix86_unary_operator_ok (GET_CODE (operands[3]), XFmode, operands)"
9587 ;; Splitters for fp abs and neg.
9590 [(set (match_operand 0 "fp_register_operand" "")
9591 (match_operator 1 "absneg_operator" [(match_dup 0)]))
9592 (use (match_operand 2 "" ""))
9593 (clobber (reg:CC FLAGS_REG))]
9595 [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))])
9598 [(set (match_operand 0 "register_operand" "")
9599 (match_operator 3 "absneg_operator"
9600 [(match_operand 1 "register_operand" "")]))
9601 (use (match_operand 2 "nonimmediate_operand" ""))
9602 (clobber (reg:CC FLAGS_REG))]
9603 "reload_completed && SSE_REG_P (operands[0])"
9604 [(set (match_dup 0) (match_dup 3))]
9606 enum machine_mode mode = GET_MODE (operands[0]);
9607 enum machine_mode vmode = GET_MODE (operands[2]);
9610 operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0);
9611 operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0);
9612 if (operands_match_p (operands[0], operands[2]))
9615 operands[1] = operands[2];
9618 if (GET_CODE (operands[3]) == ABS)
9619 tmp = gen_rtx_AND (vmode, operands[1], operands[2]);
9621 tmp = gen_rtx_XOR (vmode, operands[1], operands[2]);
9626 [(set (match_operand:SF 0 "register_operand" "")
9627 (match_operator:SF 1 "absneg_operator" [(match_dup 0)]))
9628 (use (match_operand:V4SF 2 "" ""))
9629 (clobber (reg:CC FLAGS_REG))]
9631 [(parallel [(set (match_dup 0) (match_dup 1))
9632 (clobber (reg:CC FLAGS_REG))])]
9635 operands[0] = gen_lowpart (SImode, operands[0]);
9636 if (GET_CODE (operands[1]) == ABS)
9638 tmp = gen_int_mode (0x7fffffff, SImode);
9639 tmp = gen_rtx_AND (SImode, operands[0], tmp);
9643 tmp = gen_int_mode (0x80000000, SImode);
9644 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9650 [(set (match_operand:DF 0 "register_operand" "")
9651 (match_operator:DF 1 "absneg_operator" [(match_dup 0)]))
9652 (use (match_operand 2 "" ""))
9653 (clobber (reg:CC FLAGS_REG))]
9655 [(parallel [(set (match_dup 0) (match_dup 1))
9656 (clobber (reg:CC FLAGS_REG))])]
9661 tmp = gen_lowpart (DImode, operands[0]);
9662 tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63));
9665 if (GET_CODE (operands[1]) == ABS)
9668 tmp = gen_rtx_NOT (DImode, tmp);
9672 operands[0] = gen_highpart (SImode, operands[0]);
9673 if (GET_CODE (operands[1]) == ABS)
9675 tmp = gen_int_mode (0x7fffffff, SImode);
9676 tmp = gen_rtx_AND (SImode, operands[0], tmp);
9680 tmp = gen_int_mode (0x80000000, SImode);
9681 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9688 [(set (match_operand:XF 0 "register_operand" "")
9689 (match_operator:XF 1 "absneg_operator" [(match_dup 0)]))
9690 (use (match_operand 2 "" ""))
9691 (clobber (reg:CC FLAGS_REG))]
9693 [(parallel [(set (match_dup 0) (match_dup 1))
9694 (clobber (reg:CC FLAGS_REG))])]
9697 operands[0] = gen_rtx_REG (SImode,
9698 true_regnum (operands[0])
9699 + (TARGET_64BIT ? 1 : 2));
9700 if (GET_CODE (operands[1]) == ABS)
9702 tmp = GEN_INT (0x7fff);
9703 tmp = gen_rtx_AND (SImode, operands[0], tmp);
9707 tmp = GEN_INT (0x8000);
9708 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9714 [(set (match_operand 0 "memory_operand" "")
9715 (match_operator 1 "absneg_operator" [(match_dup 0)]))
9716 (use (match_operand 2 "" ""))
9717 (clobber (reg:CC FLAGS_REG))]
9719 [(parallel [(set (match_dup 0) (match_dup 1))
9720 (clobber (reg:CC FLAGS_REG))])]
9722 enum machine_mode mode = GET_MODE (operands[0]);
9723 int size = mode == XFmode ? 10 : GET_MODE_SIZE (mode);
9726 operands[0] = adjust_address (operands[0], QImode, size - 1);
9727 if (GET_CODE (operands[1]) == ABS)
9729 tmp = gen_int_mode (0x7f, QImode);
9730 tmp = gen_rtx_AND (QImode, operands[0], tmp);
9734 tmp = gen_int_mode (0x80, QImode);
9735 tmp = gen_rtx_XOR (QImode, operands[0], tmp);
9740 ;; Conditionalize these after reload. If they match before reload, we
9741 ;; lose the clobber and ability to use integer instructions.
9743 (define_insn "*negsf2_1"
9744 [(set (match_operand:SF 0 "register_operand" "=f")
9745 (neg:SF (match_operand:SF 1 "register_operand" "0")))]
9746 "TARGET_80387 && reload_completed"
9748 [(set_attr "type" "fsgn")
9749 (set_attr "mode" "SF")])
9751 (define_insn "*negdf2_1"
9752 [(set (match_operand:DF 0 "register_operand" "=f")
9753 (neg:DF (match_operand:DF 1 "register_operand" "0")))]
9754 "TARGET_80387 && reload_completed"
9756 [(set_attr "type" "fsgn")
9757 (set_attr "mode" "DF")])
9759 (define_insn "*negxf2_1"
9760 [(set (match_operand:XF 0 "register_operand" "=f")
9761 (neg:XF (match_operand:XF 1 "register_operand" "0")))]
9762 "TARGET_80387 && reload_completed"
9764 [(set_attr "type" "fsgn")
9765 (set_attr "mode" "XF")])
9767 (define_insn "*abssf2_1"
9768 [(set (match_operand:SF 0 "register_operand" "=f")
9769 (abs:SF (match_operand:SF 1 "register_operand" "0")))]
9770 "TARGET_80387 && reload_completed"
9772 [(set_attr "type" "fsgn")
9773 (set_attr "mode" "SF")])
9775 (define_insn "*absdf2_1"
9776 [(set (match_operand:DF 0 "register_operand" "=f")
9777 (abs:DF (match_operand:DF 1 "register_operand" "0")))]
9778 "TARGET_80387 && reload_completed"
9780 [(set_attr "type" "fsgn")
9781 (set_attr "mode" "DF")])
9783 (define_insn "*absxf2_1"
9784 [(set (match_operand:XF 0 "register_operand" "=f")
9785 (abs:XF (match_operand:XF 1 "register_operand" "0")))]
9786 "TARGET_80387 && reload_completed"
9788 [(set_attr "type" "fsgn")
9789 (set_attr "mode" "DF")])
9791 (define_insn "*negextendsfdf2"
9792 [(set (match_operand:DF 0 "register_operand" "=f")
9793 (neg:DF (float_extend:DF
9794 (match_operand:SF 1 "register_operand" "0"))))]
9795 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
9797 [(set_attr "type" "fsgn")
9798 (set_attr "mode" "DF")])
9800 (define_insn "*negextenddfxf2"
9801 [(set (match_operand:XF 0 "register_operand" "=f")
9802 (neg:XF (float_extend:XF
9803 (match_operand:DF 1 "register_operand" "0"))))]
9806 [(set_attr "type" "fsgn")
9807 (set_attr "mode" "XF")])
9809 (define_insn "*negextendsfxf2"
9810 [(set (match_operand:XF 0 "register_operand" "=f")
9811 (neg:XF (float_extend:XF
9812 (match_operand:SF 1 "register_operand" "0"))))]
9815 [(set_attr "type" "fsgn")
9816 (set_attr "mode" "XF")])
9818 (define_insn "*absextendsfdf2"
9819 [(set (match_operand:DF 0 "register_operand" "=f")
9820 (abs:DF (float_extend:DF
9821 (match_operand:SF 1 "register_operand" "0"))))]
9822 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
9824 [(set_attr "type" "fsgn")
9825 (set_attr "mode" "DF")])
9827 (define_insn "*absextenddfxf2"
9828 [(set (match_operand:XF 0 "register_operand" "=f")
9829 (abs:XF (float_extend:XF
9830 (match_operand:DF 1 "register_operand" "0"))))]
9833 [(set_attr "type" "fsgn")
9834 (set_attr "mode" "XF")])
9836 (define_insn "*absextendsfxf2"
9837 [(set (match_operand:XF 0 "register_operand" "=f")
9838 (abs:XF (float_extend:XF
9839 (match_operand:SF 1 "register_operand" "0"))))]
9842 [(set_attr "type" "fsgn")
9843 (set_attr "mode" "XF")])
9845 ;; One complement instructions
9847 (define_expand "one_cmpldi2"
9848 [(set (match_operand:DI 0 "nonimmediate_operand" "")
9849 (not:DI (match_operand:DI 1 "nonimmediate_operand" "")))]
9851 "ix86_expand_unary_operator (NOT, DImode, operands); DONE;")
9853 (define_insn "*one_cmpldi2_1_rex64"
9854 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9855 (not:DI (match_operand:DI 1 "nonimmediate_operand" "0")))]
9856 "TARGET_64BIT && ix86_unary_operator_ok (NOT, DImode, operands)"
9858 [(set_attr "type" "negnot")
9859 (set_attr "mode" "DI")])
9861 (define_insn "*one_cmpldi2_2_rex64"
9862 [(set (reg FLAGS_REG)
9863 (compare (not:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
9865 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9866 (not:DI (match_dup 1)))]
9867 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9868 && ix86_unary_operator_ok (NOT, DImode, operands)"
9870 [(set_attr "type" "alu1")
9871 (set_attr "mode" "DI")])
9874 [(set (match_operand 0 "flags_reg_operand" "")
9875 (match_operator 2 "compare_operator"
9876 [(not:DI (match_operand:DI 3 "nonimmediate_operand" ""))
9878 (set (match_operand:DI 1 "nonimmediate_operand" "")
9879 (not:DI (match_dup 3)))]
9880 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9881 [(parallel [(set (match_dup 0)
9883 [(xor:DI (match_dup 3) (const_int -1))
9886 (xor:DI (match_dup 3) (const_int -1)))])]
9889 (define_expand "one_cmplsi2"
9890 [(set (match_operand:SI 0 "nonimmediate_operand" "")
9891 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
9893 "ix86_expand_unary_operator (NOT, SImode, operands); DONE;")
9895 (define_insn "*one_cmplsi2_1"
9896 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9897 (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))]
9898 "ix86_unary_operator_ok (NOT, SImode, operands)"
9900 [(set_attr "type" "negnot")
9901 (set_attr "mode" "SI")])
9903 ;; ??? Currently never generated - xor is used instead.
9904 (define_insn "*one_cmplsi2_1_zext"
9905 [(set (match_operand:DI 0 "register_operand" "=r")
9906 (zero_extend:DI (not:SI (match_operand:SI 1 "register_operand" "0"))))]
9907 "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
9909 [(set_attr "type" "negnot")
9910 (set_attr "mode" "SI")])
9912 (define_insn "*one_cmplsi2_2"
9913 [(set (reg FLAGS_REG)
9914 (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
9916 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9917 (not:SI (match_dup 1)))]
9918 "ix86_match_ccmode (insn, CCNOmode)
9919 && ix86_unary_operator_ok (NOT, SImode, operands)"
9921 [(set_attr "type" "alu1")
9922 (set_attr "mode" "SI")])
9925 [(set (match_operand 0 "flags_reg_operand" "")
9926 (match_operator 2 "compare_operator"
9927 [(not:SI (match_operand:SI 3 "nonimmediate_operand" ""))
9929 (set (match_operand:SI 1 "nonimmediate_operand" "")
9930 (not:SI (match_dup 3)))]
9931 "ix86_match_ccmode (insn, CCNOmode)"
9932 [(parallel [(set (match_dup 0)
9933 (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
9936 (xor:SI (match_dup 3) (const_int -1)))])]
9939 ;; ??? Currently never generated - xor is used instead.
9940 (define_insn "*one_cmplsi2_2_zext"
9941 [(set (reg FLAGS_REG)
9942 (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
9944 (set (match_operand:DI 0 "register_operand" "=r")
9945 (zero_extend:DI (not:SI (match_dup 1))))]
9946 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9947 && ix86_unary_operator_ok (NOT, SImode, operands)"
9949 [(set_attr "type" "alu1")
9950 (set_attr "mode" "SI")])
9953 [(set (match_operand 0 "flags_reg_operand" "")
9954 (match_operator 2 "compare_operator"
9955 [(not:SI (match_operand:SI 3 "register_operand" ""))
9957 (set (match_operand:DI 1 "register_operand" "")
9958 (zero_extend:DI (not:SI (match_dup 3))))]
9959 "ix86_match_ccmode (insn, CCNOmode)"
9960 [(parallel [(set (match_dup 0)
9961 (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
9964 (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])]
9967 (define_expand "one_cmplhi2"
9968 [(set (match_operand:HI 0 "nonimmediate_operand" "")
9969 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
9970 "TARGET_HIMODE_MATH"
9971 "ix86_expand_unary_operator (NOT, HImode, operands); DONE;")
9973 (define_insn "*one_cmplhi2_1"
9974 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9975 (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))]
9976 "ix86_unary_operator_ok (NOT, HImode, operands)"
9978 [(set_attr "type" "negnot")
9979 (set_attr "mode" "HI")])
9981 (define_insn "*one_cmplhi2_2"
9982 [(set (reg FLAGS_REG)
9983 (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
9985 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9986 (not:HI (match_dup 1)))]
9987 "ix86_match_ccmode (insn, CCNOmode)
9988 && ix86_unary_operator_ok (NEG, HImode, operands)"
9990 [(set_attr "type" "alu1")
9991 (set_attr "mode" "HI")])
9994 [(set (match_operand 0 "flags_reg_operand" "")
9995 (match_operator 2 "compare_operator"
9996 [(not:HI (match_operand:HI 3 "nonimmediate_operand" ""))
9998 (set (match_operand:HI 1 "nonimmediate_operand" "")
9999 (not:HI (match_dup 3)))]
10000 "ix86_match_ccmode (insn, CCNOmode)"
10001 [(parallel [(set (match_dup 0)
10002 (match_op_dup 2 [(xor:HI (match_dup 3) (const_int -1))
10005 (xor:HI (match_dup 3) (const_int -1)))])]
10008 ;; %%% Potential partial reg stall on alternative 1. What to do?
10009 (define_expand "one_cmplqi2"
10010 [(set (match_operand:QI 0 "nonimmediate_operand" "")
10011 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
10012 "TARGET_QIMODE_MATH"
10013 "ix86_expand_unary_operator (NOT, QImode, operands); DONE;")
10015 (define_insn "*one_cmplqi2_1"
10016 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10017 (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
10018 "ix86_unary_operator_ok (NOT, QImode, operands)"
10022 [(set_attr "type" "negnot")
10023 (set_attr "mode" "QI,SI")])
10025 (define_insn "*one_cmplqi2_2"
10026 [(set (reg FLAGS_REG)
10027 (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
10029 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10030 (not:QI (match_dup 1)))]
10031 "ix86_match_ccmode (insn, CCNOmode)
10032 && ix86_unary_operator_ok (NOT, QImode, operands)"
10034 [(set_attr "type" "alu1")
10035 (set_attr "mode" "QI")])
10038 [(set (match_operand 0 "flags_reg_operand" "")
10039 (match_operator 2 "compare_operator"
10040 [(not:QI (match_operand:QI 3 "nonimmediate_operand" ""))
10042 (set (match_operand:QI 1 "nonimmediate_operand" "")
10043 (not:QI (match_dup 3)))]
10044 "ix86_match_ccmode (insn, CCNOmode)"
10045 [(parallel [(set (match_dup 0)
10046 (match_op_dup 2 [(xor:QI (match_dup 3) (const_int -1))
10049 (xor:QI (match_dup 3) (const_int -1)))])]
10052 ;; Arithmetic shift instructions
10054 ;; DImode shifts are implemented using the i386 "shift double" opcode,
10055 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem". If the shift count
10056 ;; is variable, then the count is in %cl and the "imm" operand is dropped
10057 ;; from the assembler input.
10059 ;; This instruction shifts the target reg/mem as usual, but instead of
10060 ;; shifting in zeros, bits are shifted in from reg operand. If the insn
10061 ;; is a left shift double, bits are taken from the high order bits of
10062 ;; reg, else if the insn is a shift right double, bits are taken from the
10063 ;; low order bits of reg. So if %eax is "1234" and %edx is "5678",
10064 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
10066 ;; Since sh[lr]d does not change the `reg' operand, that is done
10067 ;; separately, making all shifts emit pairs of shift double and normal
10068 ;; shift. Since sh[lr]d does not shift more than 31 bits, and we wish to
10069 ;; support a 63 bit shift, each shift where the count is in a reg expands
10070 ;; to a pair of shifts, a branch, a shift by 32 and a label.
10072 ;; If the shift count is a constant, we need never emit more than one
10073 ;; shift pair, instead using moves and sign extension for counts greater
10076 (define_expand "ashldi3"
10077 [(set (match_operand:DI 0 "shiftdi_operand" "")
10078 (ashift:DI (match_operand:DI 1 "ashldi_input_operand" "")
10079 (match_operand:QI 2 "nonmemory_operand" "")))]
10081 "ix86_expand_binary_operator (ASHIFT, DImode, operands); DONE;")
10083 (define_insn "*ashldi3_1_rex64"
10084 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
10085 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0,l")
10086 (match_operand:QI 2 "nonmemory_operand" "cJ,M")))
10087 (clobber (reg:CC FLAGS_REG))]
10088 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10090 switch (get_attr_type (insn))
10093 gcc_assert (operands[2] == const1_rtx);
10094 gcc_assert (rtx_equal_p (operands[0], operands[1]));
10095 return "add{q}\t{%0, %0|%0, %0}";
10098 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
10099 gcc_assert ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) <= 3);
10100 operands[1] = gen_rtx_MULT (DImode, operands[1],
10101 GEN_INT (1 << INTVAL (operands[2])));
10102 return "lea{q}\t{%a1, %0|%0, %a1}";
10105 if (REG_P (operands[2]))
10106 return "sal{q}\t{%b2, %0|%0, %b2}";
10107 else if (operands[2] == const1_rtx
10108 && (TARGET_SHIFT1 || optimize_size))
10109 return "sal{q}\t%0";
10111 return "sal{q}\t{%2, %0|%0, %2}";
10114 [(set (attr "type")
10115 (cond [(eq_attr "alternative" "1")
10116 (const_string "lea")
10117 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10119 (match_operand 0 "register_operand" ""))
10120 (match_operand 2 "const1_operand" ""))
10121 (const_string "alu")
10123 (const_string "ishift")))
10124 (set_attr "mode" "DI")])
10126 ;; Convert lea to the lea pattern to avoid flags dependency.
10128 [(set (match_operand:DI 0 "register_operand" "")
10129 (ashift:DI (match_operand:DI 1 "index_register_operand" "")
10130 (match_operand:QI 2 "immediate_operand" "")))
10131 (clobber (reg:CC FLAGS_REG))]
10132 "TARGET_64BIT && reload_completed
10133 && true_regnum (operands[0]) != true_regnum (operands[1])"
10134 [(set (match_dup 0)
10135 (mult:DI (match_dup 1)
10137 "operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);")
10139 ;; This pattern can't accept a variable shift count, since shifts by
10140 ;; zero don't affect the flags. We assume that shifts by constant
10141 ;; zero are optimized away.
10142 (define_insn "*ashldi3_cmp_rex64"
10143 [(set (reg FLAGS_REG)
10145 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10146 (match_operand:QI 2 "immediate_operand" "e"))
10148 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10149 (ashift:DI (match_dup 1) (match_dup 2)))]
10150 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10151 && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10153 switch (get_attr_type (insn))
10156 gcc_assert (operands[2] == const1_rtx);
10157 return "add{q}\t{%0, %0|%0, %0}";
10160 if (REG_P (operands[2]))
10161 return "sal{q}\t{%b2, %0|%0, %b2}";
10162 else if (operands[2] == const1_rtx
10163 && (TARGET_SHIFT1 || optimize_size))
10164 return "sal{q}\t%0";
10166 return "sal{q}\t{%2, %0|%0, %2}";
10169 [(set (attr "type")
10170 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10172 (match_operand 0 "register_operand" ""))
10173 (match_operand 2 "const1_operand" ""))
10174 (const_string "alu")
10176 (const_string "ishift")))
10177 (set_attr "mode" "DI")])
10179 (define_insn "*ashldi3_1"
10180 [(set (match_operand:DI 0 "register_operand" "=&r,r")
10181 (ashift:DI (match_operand:DI 1 "reg_or_pm1_operand" "n,0")
10182 (match_operand:QI 2 "nonmemory_operand" "Jc,Jc")))
10183 (clobber (reg:CC FLAGS_REG))]
10186 [(set_attr "type" "multi")])
10188 ;; By default we don't ask for a scratch register, because when DImode
10189 ;; values are manipulated, registers are already at a premium. But if
10190 ;; we have one handy, we won't turn it away.
10192 [(match_scratch:SI 3 "r")
10193 (parallel [(set (match_operand:DI 0 "register_operand" "")
10194 (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
10195 (match_operand:QI 2 "nonmemory_operand" "")))
10196 (clobber (reg:CC FLAGS_REG))])
10198 "!TARGET_64BIT && TARGET_CMOVE"
10200 "ix86_split_ashldi (operands, operands[3]); DONE;")
10203 [(set (match_operand:DI 0 "register_operand" "")
10204 (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
10205 (match_operand:QI 2 "nonmemory_operand" "")))
10206 (clobber (reg:CC FLAGS_REG))]
10207 "!TARGET_64BIT && (flag_peephole2 ? flow2_completed : reload_completed)"
10209 "ix86_split_ashldi (operands, NULL_RTX); DONE;")
10211 (define_insn "x86_shld_1"
10212 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
10213 (ior:SI (ashift:SI (match_dup 0)
10214 (match_operand:QI 2 "nonmemory_operand" "I,c"))
10215 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
10216 (minus:QI (const_int 32) (match_dup 2)))))
10217 (clobber (reg:CC FLAGS_REG))]
10220 shld{l}\t{%2, %1, %0|%0, %1, %2}
10221 shld{l}\t{%s2%1, %0|%0, %1, %2}"
10222 [(set_attr "type" "ishift")
10223 (set_attr "prefix_0f" "1")
10224 (set_attr "mode" "SI")
10225 (set_attr "pent_pair" "np")
10226 (set_attr "athlon_decode" "vector")])
10228 (define_expand "x86_shift_adj_1"
10229 [(set (reg:CCZ FLAGS_REG)
10230 (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
10233 (set (match_operand:SI 0 "register_operand" "")
10234 (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10235 (match_operand:SI 1 "register_operand" "")
10238 (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10239 (match_operand:SI 3 "register_operand" "r")
10244 (define_expand "x86_shift_adj_2"
10245 [(use (match_operand:SI 0 "register_operand" ""))
10246 (use (match_operand:SI 1 "register_operand" ""))
10247 (use (match_operand:QI 2 "register_operand" ""))]
10250 rtx label = gen_label_rtx ();
10253 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
10255 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
10256 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
10257 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
10258 gen_rtx_LABEL_REF (VOIDmode, label),
10260 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
10261 JUMP_LABEL (tmp) = label;
10263 emit_move_insn (operands[0], operands[1]);
10264 ix86_expand_clear (operands[1]);
10266 emit_label (label);
10267 LABEL_NUSES (label) = 1;
10272 (define_expand "ashlsi3"
10273 [(set (match_operand:SI 0 "nonimmediate_operand" "")
10274 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
10275 (match_operand:QI 2 "nonmemory_operand" "")))
10276 (clobber (reg:CC FLAGS_REG))]
10278 "ix86_expand_binary_operator (ASHIFT, SImode, operands); DONE;")
10280 (define_insn "*ashlsi3_1"
10281 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
10282 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l")
10283 (match_operand:QI 2 "nonmemory_operand" "cI,M")))
10284 (clobber (reg:CC FLAGS_REG))]
10285 "ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10287 switch (get_attr_type (insn))
10290 gcc_assert (operands[2] == const1_rtx);
10291 gcc_assert (rtx_equal_p (operands[0], operands[1]));
10292 return "add{l}\t{%0, %0|%0, %0}";
10298 if (REG_P (operands[2]))
10299 return "sal{l}\t{%b2, %0|%0, %b2}";
10300 else if (operands[2] == const1_rtx
10301 && (TARGET_SHIFT1 || optimize_size))
10302 return "sal{l}\t%0";
10304 return "sal{l}\t{%2, %0|%0, %2}";
10307 [(set (attr "type")
10308 (cond [(eq_attr "alternative" "1")
10309 (const_string "lea")
10310 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10312 (match_operand 0 "register_operand" ""))
10313 (match_operand 2 "const1_operand" ""))
10314 (const_string "alu")
10316 (const_string "ishift")))
10317 (set_attr "mode" "SI")])
10319 ;; Convert lea to the lea pattern to avoid flags dependency.
10321 [(set (match_operand 0 "register_operand" "")
10322 (ashift (match_operand 1 "index_register_operand" "")
10323 (match_operand:QI 2 "const_int_operand" "")))
10324 (clobber (reg:CC FLAGS_REG))]
10326 && true_regnum (operands[0]) != true_regnum (operands[1])
10327 && GET_MODE_SIZE (GET_MODE (operands[0])) <= 4"
10331 enum machine_mode mode = GET_MODE (operands[0]);
10333 if (GET_MODE_SIZE (mode) < 4)
10334 operands[0] = gen_lowpart (SImode, operands[0]);
10336 operands[1] = gen_lowpart (Pmode, operands[1]);
10337 operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
10339 pat = gen_rtx_MULT (Pmode, operands[1], operands[2]);
10340 if (Pmode != SImode)
10341 pat = gen_rtx_SUBREG (SImode, pat, 0);
10342 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
10346 ;; Rare case of shifting RSP is handled by generating move and shift
10348 [(set (match_operand 0 "register_operand" "")
10349 (ashift (match_operand 1 "register_operand" "")
10350 (match_operand:QI 2 "const_int_operand" "")))
10351 (clobber (reg:CC FLAGS_REG))]
10353 && true_regnum (operands[0]) != true_regnum (operands[1])"
10357 emit_move_insn (operands[1], operands[0]);
10358 pat = gen_rtx_SET (VOIDmode, operands[0],
10359 gen_rtx_ASHIFT (GET_MODE (operands[0]),
10360 operands[0], operands[2]));
10361 clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
10362 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, pat, clob)));
10366 (define_insn "*ashlsi3_1_zext"
10367 [(set (match_operand:DI 0 "register_operand" "=r,r")
10368 (zero_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "0,l")
10369 (match_operand:QI 2 "nonmemory_operand" "cI,M"))))
10370 (clobber (reg:CC FLAGS_REG))]
10371 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10373 switch (get_attr_type (insn))
10376 gcc_assert (operands[2] == const1_rtx);
10377 return "add{l}\t{%k0, %k0|%k0, %k0}";
10383 if (REG_P (operands[2]))
10384 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10385 else if (operands[2] == const1_rtx
10386 && (TARGET_SHIFT1 || optimize_size))
10387 return "sal{l}\t%k0";
10389 return "sal{l}\t{%2, %k0|%k0, %2}";
10392 [(set (attr "type")
10393 (cond [(eq_attr "alternative" "1")
10394 (const_string "lea")
10395 (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10397 (match_operand 2 "const1_operand" ""))
10398 (const_string "alu")
10400 (const_string "ishift")))
10401 (set_attr "mode" "SI")])
10403 ;; Convert lea to the lea pattern to avoid flags dependency.
10405 [(set (match_operand:DI 0 "register_operand" "")
10406 (zero_extend:DI (ashift (match_operand 1 "register_operand" "")
10407 (match_operand:QI 2 "const_int_operand" ""))))
10408 (clobber (reg:CC FLAGS_REG))]
10409 "TARGET_64BIT && reload_completed
10410 && true_regnum (operands[0]) != true_regnum (operands[1])"
10411 [(set (match_dup 0) (zero_extend:DI
10412 (subreg:SI (mult:SI (match_dup 1)
10413 (match_dup 2)) 0)))]
10415 operands[1] = gen_lowpart (Pmode, operands[1]);
10416 operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
10419 ;; This pattern can't accept a variable shift count, since shifts by
10420 ;; zero don't affect the flags. We assume that shifts by constant
10421 ;; zero are optimized away.
10422 (define_insn "*ashlsi3_cmp"
10423 [(set (reg FLAGS_REG)
10425 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
10426 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10428 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10429 (ashift:SI (match_dup 1) (match_dup 2)))]
10430 "ix86_match_ccmode (insn, CCGOCmode)
10431 && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10433 switch (get_attr_type (insn))
10436 gcc_assert (operands[2] == const1_rtx);
10437 return "add{l}\t{%0, %0|%0, %0}";
10440 if (REG_P (operands[2]))
10441 return "sal{l}\t{%b2, %0|%0, %b2}";
10442 else if (operands[2] == const1_rtx
10443 && (TARGET_SHIFT1 || optimize_size))
10444 return "sal{l}\t%0";
10446 return "sal{l}\t{%2, %0|%0, %2}";
10449 [(set (attr "type")
10450 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10452 (match_operand 0 "register_operand" ""))
10453 (match_operand 2 "const1_operand" ""))
10454 (const_string "alu")
10456 (const_string "ishift")))
10457 (set_attr "mode" "SI")])
10459 (define_insn "*ashlsi3_cmp_zext"
10460 [(set (reg FLAGS_REG)
10462 (ashift:SI (match_operand:SI 1 "register_operand" "0")
10463 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10465 (set (match_operand:DI 0 "register_operand" "=r")
10466 (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
10467 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10468 && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10470 switch (get_attr_type (insn))
10473 gcc_assert (operands[2] == const1_rtx);
10474 return "add{l}\t{%k0, %k0|%k0, %k0}";
10477 if (REG_P (operands[2]))
10478 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10479 else if (operands[2] == const1_rtx
10480 && (TARGET_SHIFT1 || optimize_size))
10481 return "sal{l}\t%k0";
10483 return "sal{l}\t{%2, %k0|%k0, %2}";
10486 [(set (attr "type")
10487 (cond [(and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10489 (match_operand 2 "const1_operand" ""))
10490 (const_string "alu")
10492 (const_string "ishift")))
10493 (set_attr "mode" "SI")])
10495 (define_expand "ashlhi3"
10496 [(set (match_operand:HI 0 "nonimmediate_operand" "")
10497 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "")
10498 (match_operand:QI 2 "nonmemory_operand" "")))
10499 (clobber (reg:CC FLAGS_REG))]
10500 "TARGET_HIMODE_MATH"
10501 "ix86_expand_binary_operator (ASHIFT, HImode, operands); DONE;")
10503 (define_insn "*ashlhi3_1_lea"
10504 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
10505 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
10506 (match_operand:QI 2 "nonmemory_operand" "cI,M")))
10507 (clobber (reg:CC FLAGS_REG))]
10508 "!TARGET_PARTIAL_REG_STALL
10509 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10511 switch (get_attr_type (insn))
10516 gcc_assert (operands[2] == const1_rtx);
10517 return "add{w}\t{%0, %0|%0, %0}";
10520 if (REG_P (operands[2]))
10521 return "sal{w}\t{%b2, %0|%0, %b2}";
10522 else if (operands[2] == const1_rtx
10523 && (TARGET_SHIFT1 || optimize_size))
10524 return "sal{w}\t%0";
10526 return "sal{w}\t{%2, %0|%0, %2}";
10529 [(set (attr "type")
10530 (cond [(eq_attr "alternative" "1")
10531 (const_string "lea")
10532 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10534 (match_operand 0 "register_operand" ""))
10535 (match_operand 2 "const1_operand" ""))
10536 (const_string "alu")
10538 (const_string "ishift")))
10539 (set_attr "mode" "HI,SI")])
10541 (define_insn "*ashlhi3_1"
10542 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10543 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
10544 (match_operand:QI 2 "nonmemory_operand" "cI")))
10545 (clobber (reg:CC FLAGS_REG))]
10546 "TARGET_PARTIAL_REG_STALL
10547 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10549 switch (get_attr_type (insn))
10552 gcc_assert (operands[2] == const1_rtx);
10553 return "add{w}\t{%0, %0|%0, %0}";
10556 if (REG_P (operands[2]))
10557 return "sal{w}\t{%b2, %0|%0, %b2}";
10558 else if (operands[2] == const1_rtx
10559 && (TARGET_SHIFT1 || optimize_size))
10560 return "sal{w}\t%0";
10562 return "sal{w}\t{%2, %0|%0, %2}";
10565 [(set (attr "type")
10566 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10568 (match_operand 0 "register_operand" ""))
10569 (match_operand 2 "const1_operand" ""))
10570 (const_string "alu")
10572 (const_string "ishift")))
10573 (set_attr "mode" "HI")])
10575 ;; This pattern can't accept a variable shift count, since shifts by
10576 ;; zero don't affect the flags. We assume that shifts by constant
10577 ;; zero are optimized away.
10578 (define_insn "*ashlhi3_cmp"
10579 [(set (reg FLAGS_REG)
10581 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
10582 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10584 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10585 (ashift:HI (match_dup 1) (match_dup 2)))]
10586 "ix86_match_ccmode (insn, CCGOCmode)
10587 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10589 switch (get_attr_type (insn))
10592 gcc_assert (operands[2] == const1_rtx);
10593 return "add{w}\t{%0, %0|%0, %0}";
10596 if (REG_P (operands[2]))
10597 return "sal{w}\t{%b2, %0|%0, %b2}";
10598 else if (operands[2] == const1_rtx
10599 && (TARGET_SHIFT1 || optimize_size))
10600 return "sal{w}\t%0";
10602 return "sal{w}\t{%2, %0|%0, %2}";
10605 [(set (attr "type")
10606 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10608 (match_operand 0 "register_operand" ""))
10609 (match_operand 2 "const1_operand" ""))
10610 (const_string "alu")
10612 (const_string "ishift")))
10613 (set_attr "mode" "HI")])
10615 (define_expand "ashlqi3"
10616 [(set (match_operand:QI 0 "nonimmediate_operand" "")
10617 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "")
10618 (match_operand:QI 2 "nonmemory_operand" "")))
10619 (clobber (reg:CC FLAGS_REG))]
10620 "TARGET_QIMODE_MATH"
10621 "ix86_expand_binary_operator (ASHIFT, QImode, operands); DONE;")
10623 ;; %%% Potential partial reg stall on alternative 2. What to do?
10625 (define_insn "*ashlqi3_1_lea"
10626 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r")
10627 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
10628 (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
10629 (clobber (reg:CC FLAGS_REG))]
10630 "!TARGET_PARTIAL_REG_STALL
10631 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10633 switch (get_attr_type (insn))
10638 gcc_assert (operands[2] == const1_rtx);
10639 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
10640 return "add{l}\t{%k0, %k0|%k0, %k0}";
10642 return "add{b}\t{%0, %0|%0, %0}";
10645 if (REG_P (operands[2]))
10647 if (get_attr_mode (insn) == MODE_SI)
10648 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10650 return "sal{b}\t{%b2, %0|%0, %b2}";
10652 else if (operands[2] == const1_rtx
10653 && (TARGET_SHIFT1 || optimize_size))
10655 if (get_attr_mode (insn) == MODE_SI)
10656 return "sal{l}\t%0";
10658 return "sal{b}\t%0";
10662 if (get_attr_mode (insn) == MODE_SI)
10663 return "sal{l}\t{%2, %k0|%k0, %2}";
10665 return "sal{b}\t{%2, %0|%0, %2}";
10669 [(set (attr "type")
10670 (cond [(eq_attr "alternative" "2")
10671 (const_string "lea")
10672 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10674 (match_operand 0 "register_operand" ""))
10675 (match_operand 2 "const1_operand" ""))
10676 (const_string "alu")
10678 (const_string "ishift")))
10679 (set_attr "mode" "QI,SI,SI")])
10681 (define_insn "*ashlqi3_1"
10682 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10683 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
10684 (match_operand:QI 2 "nonmemory_operand" "cI,cI")))
10685 (clobber (reg:CC FLAGS_REG))]
10686 "TARGET_PARTIAL_REG_STALL
10687 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10689 switch (get_attr_type (insn))
10692 gcc_assert (operands[2] == const1_rtx);
10693 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
10694 return "add{l}\t{%k0, %k0|%k0, %k0}";
10696 return "add{b}\t{%0, %0|%0, %0}";
10699 if (REG_P (operands[2]))
10701 if (get_attr_mode (insn) == MODE_SI)
10702 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10704 return "sal{b}\t{%b2, %0|%0, %b2}";
10706 else if (operands[2] == const1_rtx
10707 && (TARGET_SHIFT1 || optimize_size))
10709 if (get_attr_mode (insn) == MODE_SI)
10710 return "sal{l}\t%0";
10712 return "sal{b}\t%0";
10716 if (get_attr_mode (insn) == MODE_SI)
10717 return "sal{l}\t{%2, %k0|%k0, %2}";
10719 return "sal{b}\t{%2, %0|%0, %2}";
10723 [(set (attr "type")
10724 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10726 (match_operand 0 "register_operand" ""))
10727 (match_operand 2 "const1_operand" ""))
10728 (const_string "alu")
10730 (const_string "ishift")))
10731 (set_attr "mode" "QI,SI")])
10733 ;; This pattern can't accept a variable shift count, since shifts by
10734 ;; zero don't affect the flags. We assume that shifts by constant
10735 ;; zero are optimized away.
10736 (define_insn "*ashlqi3_cmp"
10737 [(set (reg FLAGS_REG)
10739 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
10740 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10742 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10743 (ashift:QI (match_dup 1) (match_dup 2)))]
10744 "ix86_match_ccmode (insn, CCGOCmode)
10745 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10747 switch (get_attr_type (insn))
10750 gcc_assert (operands[2] == const1_rtx);
10751 return "add{b}\t{%0, %0|%0, %0}";
10754 if (REG_P (operands[2]))
10755 return "sal{b}\t{%b2, %0|%0, %b2}";
10756 else if (operands[2] == const1_rtx
10757 && (TARGET_SHIFT1 || optimize_size))
10758 return "sal{b}\t%0";
10760 return "sal{b}\t{%2, %0|%0, %2}";
10763 [(set (attr "type")
10764 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10766 (match_operand 0 "register_operand" ""))
10767 (match_operand 2 "const1_operand" ""))
10768 (const_string "alu")
10770 (const_string "ishift")))
10771 (set_attr "mode" "QI")])
10773 ;; See comment above `ashldi3' about how this works.
10775 (define_expand "ashrdi3"
10776 [(set (match_operand:DI 0 "shiftdi_operand" "")
10777 (ashiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
10778 (match_operand:QI 2 "nonmemory_operand" "")))]
10780 "ix86_expand_binary_operator (ASHIFTRT, DImode, operands); DONE;")
10782 (define_insn "*ashrdi3_63_rex64"
10783 [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
10784 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
10785 (match_operand:DI 2 "const_int_operand" "i,i")))
10786 (clobber (reg:CC FLAGS_REG))]
10787 "TARGET_64BIT && INTVAL (operands[2]) == 63
10788 && (TARGET_USE_CLTD || optimize_size)
10789 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
10792 sar{q}\t{%2, %0|%0, %2}"
10793 [(set_attr "type" "imovx,ishift")
10794 (set_attr "prefix_0f" "0,*")
10795 (set_attr "length_immediate" "0,*")
10796 (set_attr "modrm" "0,1")
10797 (set_attr "mode" "DI")])
10799 (define_insn "*ashrdi3_1_one_bit_rex64"
10800 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10801 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10802 (match_operand:QI 2 "const1_operand" "")))
10803 (clobber (reg:CC FLAGS_REG))]
10804 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)
10805 && (TARGET_SHIFT1 || optimize_size)"
10807 [(set_attr "type" "ishift")
10808 (set (attr "length")
10809 (if_then_else (match_operand:DI 0 "register_operand" "")
10811 (const_string "*")))])
10813 (define_insn "*ashrdi3_1_rex64"
10814 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
10815 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
10816 (match_operand:QI 2 "nonmemory_operand" "J,c")))
10817 (clobber (reg:CC FLAGS_REG))]
10818 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
10820 sar{q}\t{%2, %0|%0, %2}
10821 sar{q}\t{%b2, %0|%0, %b2}"
10822 [(set_attr "type" "ishift")
10823 (set_attr "mode" "DI")])
10825 ;; This pattern can't accept a variable shift count, since shifts by
10826 ;; zero don't affect the flags. We assume that shifts by constant
10827 ;; zero are optimized away.
10828 (define_insn "*ashrdi3_one_bit_cmp_rex64"
10829 [(set (reg FLAGS_REG)
10831 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10832 (match_operand:QI 2 "const1_operand" ""))
10834 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10835 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
10836 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10837 && (TARGET_SHIFT1 || optimize_size)
10838 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
10840 [(set_attr "type" "ishift")
10841 (set (attr "length")
10842 (if_then_else (match_operand:DI 0 "register_operand" "")
10844 (const_string "*")))])
10846 ;; This pattern can't accept a variable shift count, since shifts by
10847 ;; zero don't affect the flags. We assume that shifts by constant
10848 ;; zero are optimized away.
10849 (define_insn "*ashrdi3_cmp_rex64"
10850 [(set (reg FLAGS_REG)
10852 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10853 (match_operand:QI 2 "const_int_operand" "n"))
10855 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10856 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
10857 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10858 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
10859 "sar{q}\t{%2, %0|%0, %2}"
10860 [(set_attr "type" "ishift")
10861 (set_attr "mode" "DI")])
10863 (define_insn "*ashrdi3_1"
10864 [(set (match_operand:DI 0 "register_operand" "=r")
10865 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
10866 (match_operand:QI 2 "nonmemory_operand" "Jc")))
10867 (clobber (reg:CC FLAGS_REG))]
10870 [(set_attr "type" "multi")])
10872 ;; By default we don't ask for a scratch register, because when DImode
10873 ;; values are manipulated, registers are already at a premium. But if
10874 ;; we have one handy, we won't turn it away.
10876 [(match_scratch:SI 3 "r")
10877 (parallel [(set (match_operand:DI 0 "register_operand" "")
10878 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
10879 (match_operand:QI 2 "nonmemory_operand" "")))
10880 (clobber (reg:CC FLAGS_REG))])
10882 "!TARGET_64BIT && TARGET_CMOVE"
10884 "ix86_split_ashrdi (operands, operands[3]); DONE;")
10887 [(set (match_operand:DI 0 "register_operand" "")
10888 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
10889 (match_operand:QI 2 "nonmemory_operand" "")))
10890 (clobber (reg:CC FLAGS_REG))]
10891 "!TARGET_64BIT && (flag_peephole2 ? flow2_completed : reload_completed)"
10893 "ix86_split_ashrdi (operands, NULL_RTX); DONE;")
10895 (define_insn "x86_shrd_1"
10896 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
10897 (ior:SI (ashiftrt:SI (match_dup 0)
10898 (match_operand:QI 2 "nonmemory_operand" "I,c"))
10899 (ashift:SI (match_operand:SI 1 "register_operand" "r,r")
10900 (minus:QI (const_int 32) (match_dup 2)))))
10901 (clobber (reg:CC FLAGS_REG))]
10904 shrd{l}\t{%2, %1, %0|%0, %1, %2}
10905 shrd{l}\t{%s2%1, %0|%0, %1, %2}"
10906 [(set_attr "type" "ishift")
10907 (set_attr "prefix_0f" "1")
10908 (set_attr "pent_pair" "np")
10909 (set_attr "mode" "SI")])
10911 (define_expand "x86_shift_adj_3"
10912 [(use (match_operand:SI 0 "register_operand" ""))
10913 (use (match_operand:SI 1 "register_operand" ""))
10914 (use (match_operand:QI 2 "register_operand" ""))]
10917 rtx label = gen_label_rtx ();
10920 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
10922 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
10923 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
10924 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
10925 gen_rtx_LABEL_REF (VOIDmode, label),
10927 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
10928 JUMP_LABEL (tmp) = label;
10930 emit_move_insn (operands[0], operands[1]);
10931 emit_insn (gen_ashrsi3_31 (operands[1], operands[1], GEN_INT (31)));
10933 emit_label (label);
10934 LABEL_NUSES (label) = 1;
10939 (define_insn "ashrsi3_31"
10940 [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
10941 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
10942 (match_operand:SI 2 "const_int_operand" "i,i")))
10943 (clobber (reg:CC FLAGS_REG))]
10944 "INTVAL (operands[2]) == 31 && (TARGET_USE_CLTD || optimize_size)
10945 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
10948 sar{l}\t{%2, %0|%0, %2}"
10949 [(set_attr "type" "imovx,ishift")
10950 (set_attr "prefix_0f" "0,*")
10951 (set_attr "length_immediate" "0,*")
10952 (set_attr "modrm" "0,1")
10953 (set_attr "mode" "SI")])
10955 (define_insn "*ashrsi3_31_zext"
10956 [(set (match_operand:DI 0 "register_operand" "=*d,r")
10957 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
10958 (match_operand:SI 2 "const_int_operand" "i,i"))))
10959 (clobber (reg:CC FLAGS_REG))]
10960 "TARGET_64BIT && (TARGET_USE_CLTD || optimize_size)
10961 && INTVAL (operands[2]) == 31
10962 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
10965 sar{l}\t{%2, %k0|%k0, %2}"
10966 [(set_attr "type" "imovx,ishift")
10967 (set_attr "prefix_0f" "0,*")
10968 (set_attr "length_immediate" "0,*")
10969 (set_attr "modrm" "0,1")
10970 (set_attr "mode" "SI")])
10972 (define_expand "ashrsi3"
10973 [(set (match_operand:SI 0 "nonimmediate_operand" "")
10974 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
10975 (match_operand:QI 2 "nonmemory_operand" "")))
10976 (clobber (reg:CC FLAGS_REG))]
10978 "ix86_expand_binary_operator (ASHIFTRT, SImode, operands); DONE;")
10980 (define_insn "*ashrsi3_1_one_bit"
10981 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10982 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
10983 (match_operand:QI 2 "const1_operand" "")))
10984 (clobber (reg:CC FLAGS_REG))]
10985 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
10986 && (TARGET_SHIFT1 || optimize_size)"
10988 [(set_attr "type" "ishift")
10989 (set (attr "length")
10990 (if_then_else (match_operand:SI 0 "register_operand" "")
10992 (const_string "*")))])
10994 (define_insn "*ashrsi3_1_one_bit_zext"
10995 [(set (match_operand:DI 0 "register_operand" "=r")
10996 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
10997 (match_operand:QI 2 "const1_operand" ""))))
10998 (clobber (reg:CC FLAGS_REG))]
10999 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
11000 && (TARGET_SHIFT1 || optimize_size)"
11002 [(set_attr "type" "ishift")
11003 (set_attr "length" "2")])
11005 (define_insn "*ashrsi3_1"
11006 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11007 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11008 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11009 (clobber (reg:CC FLAGS_REG))]
11010 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11012 sar{l}\t{%2, %0|%0, %2}
11013 sar{l}\t{%b2, %0|%0, %b2}"
11014 [(set_attr "type" "ishift")
11015 (set_attr "mode" "SI")])
11017 (define_insn "*ashrsi3_1_zext"
11018 [(set (match_operand:DI 0 "register_operand" "=r,r")
11019 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0")
11020 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11021 (clobber (reg:CC FLAGS_REG))]
11022 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11024 sar{l}\t{%2, %k0|%k0, %2}
11025 sar{l}\t{%b2, %k0|%k0, %b2}"
11026 [(set_attr "type" "ishift")
11027 (set_attr "mode" "SI")])
11029 ;; This pattern can't accept a variable shift count, since shifts by
11030 ;; zero don't affect the flags. We assume that shifts by constant
11031 ;; zero are optimized away.
11032 (define_insn "*ashrsi3_one_bit_cmp"
11033 [(set (reg FLAGS_REG)
11035 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11036 (match_operand:QI 2 "const1_operand" ""))
11038 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11039 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
11040 "ix86_match_ccmode (insn, CCGOCmode)
11041 && (TARGET_SHIFT1 || optimize_size)
11042 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11044 [(set_attr "type" "ishift")
11045 (set (attr "length")
11046 (if_then_else (match_operand:SI 0 "register_operand" "")
11048 (const_string "*")))])
11050 (define_insn "*ashrsi3_one_bit_cmp_zext"
11051 [(set (reg FLAGS_REG)
11053 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11054 (match_operand:QI 2 "const1_operand" ""))
11056 (set (match_operand:DI 0 "register_operand" "=r")
11057 (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
11058 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
11059 && (TARGET_SHIFT1 || optimize_size)
11060 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11062 [(set_attr "type" "ishift")
11063 (set_attr "length" "2")])
11065 ;; This pattern can't accept a variable shift count, since shifts by
11066 ;; zero don't affect the flags. We assume that shifts by constant
11067 ;; zero are optimized away.
11068 (define_insn "*ashrsi3_cmp"
11069 [(set (reg FLAGS_REG)
11071 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11072 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11074 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11075 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
11076 "ix86_match_ccmode (insn, CCGOCmode)
11077 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11078 "sar{l}\t{%2, %0|%0, %2}"
11079 [(set_attr "type" "ishift")
11080 (set_attr "mode" "SI")])
11082 (define_insn "*ashrsi3_cmp_zext"
11083 [(set (reg FLAGS_REG)
11085 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11086 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11088 (set (match_operand:DI 0 "register_operand" "=r")
11089 (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
11090 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11091 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11092 "sar{l}\t{%2, %k0|%k0, %2}"
11093 [(set_attr "type" "ishift")
11094 (set_attr "mode" "SI")])
11096 (define_expand "ashrhi3"
11097 [(set (match_operand:HI 0 "nonimmediate_operand" "")
11098 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
11099 (match_operand:QI 2 "nonmemory_operand" "")))
11100 (clobber (reg:CC FLAGS_REG))]
11101 "TARGET_HIMODE_MATH"
11102 "ix86_expand_binary_operator (ASHIFTRT, HImode, operands); DONE;")
11104 (define_insn "*ashrhi3_1_one_bit"
11105 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11106 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11107 (match_operand:QI 2 "const1_operand" "")))
11108 (clobber (reg:CC FLAGS_REG))]
11109 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)
11110 && (TARGET_SHIFT1 || optimize_size)"
11112 [(set_attr "type" "ishift")
11113 (set (attr "length")
11114 (if_then_else (match_operand 0 "register_operand" "")
11116 (const_string "*")))])
11118 (define_insn "*ashrhi3_1"
11119 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11120 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11121 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11122 (clobber (reg:CC FLAGS_REG))]
11123 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11125 sar{w}\t{%2, %0|%0, %2}
11126 sar{w}\t{%b2, %0|%0, %b2}"
11127 [(set_attr "type" "ishift")
11128 (set_attr "mode" "HI")])
11130 ;; This pattern can't accept a variable shift count, since shifts by
11131 ;; zero don't affect the flags. We assume that shifts by constant
11132 ;; zero are optimized away.
11133 (define_insn "*ashrhi3_one_bit_cmp"
11134 [(set (reg FLAGS_REG)
11136 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11137 (match_operand:QI 2 "const1_operand" ""))
11139 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11140 (ashiftrt:HI (match_dup 1) (match_dup 2)))]
11141 "ix86_match_ccmode (insn, CCGOCmode)
11142 && (TARGET_SHIFT1 || optimize_size)
11143 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11145 [(set_attr "type" "ishift")
11146 (set (attr "length")
11147 (if_then_else (match_operand 0 "register_operand" "")
11149 (const_string "*")))])
11151 ;; This pattern can't accept a variable shift count, since shifts by
11152 ;; zero don't affect the flags. We assume that shifts by constant
11153 ;; zero are optimized away.
11154 (define_insn "*ashrhi3_cmp"
11155 [(set (reg FLAGS_REG)
11157 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11158 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11160 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11161 (ashiftrt:HI (match_dup 1) (match_dup 2)))]
11162 "ix86_match_ccmode (insn, CCGOCmode)
11163 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11164 "sar{w}\t{%2, %0|%0, %2}"
11165 [(set_attr "type" "ishift")
11166 (set_attr "mode" "HI")])
11168 (define_expand "ashrqi3"
11169 [(set (match_operand:QI 0 "nonimmediate_operand" "")
11170 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
11171 (match_operand:QI 2 "nonmemory_operand" "")))
11172 (clobber (reg:CC FLAGS_REG))]
11173 "TARGET_QIMODE_MATH"
11174 "ix86_expand_binary_operator (ASHIFTRT, QImode, operands); DONE;")
11176 (define_insn "*ashrqi3_1_one_bit"
11177 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11178 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11179 (match_operand:QI 2 "const1_operand" "")))
11180 (clobber (reg:CC FLAGS_REG))]
11181 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
11182 && (TARGET_SHIFT1 || optimize_size)"
11184 [(set_attr "type" "ishift")
11185 (set (attr "length")
11186 (if_then_else (match_operand 0 "register_operand" "")
11188 (const_string "*")))])
11190 (define_insn "*ashrqi3_1_one_bit_slp"
11191 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11192 (ashiftrt:QI (match_dup 0)
11193 (match_operand:QI 1 "const1_operand" "")))
11194 (clobber (reg:CC FLAGS_REG))]
11195 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
11196 && (! TARGET_PARTIAL_REG_STALL || optimize_size)
11197 && (TARGET_SHIFT1 || optimize_size)"
11199 [(set_attr "type" "ishift1")
11200 (set (attr "length")
11201 (if_then_else (match_operand 0 "register_operand" "")
11203 (const_string "*")))])
11205 (define_insn "*ashrqi3_1"
11206 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11207 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11208 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11209 (clobber (reg:CC FLAGS_REG))]
11210 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11212 sar{b}\t{%2, %0|%0, %2}
11213 sar{b}\t{%b2, %0|%0, %b2}"
11214 [(set_attr "type" "ishift")
11215 (set_attr "mode" "QI")])
11217 (define_insn "*ashrqi3_1_slp"
11218 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11219 (ashiftrt:QI (match_dup 0)
11220 (match_operand:QI 1 "nonmemory_operand" "I,c")))
11221 (clobber (reg:CC FLAGS_REG))]
11222 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11223 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11225 sar{b}\t{%1, %0|%0, %1}
11226 sar{b}\t{%b1, %0|%0, %b1}"
11227 [(set_attr "type" "ishift1")
11228 (set_attr "mode" "QI")])
11230 ;; This pattern can't accept a variable shift count, since shifts by
11231 ;; zero don't affect the flags. We assume that shifts by constant
11232 ;; zero are optimized away.
11233 (define_insn "*ashrqi3_one_bit_cmp"
11234 [(set (reg FLAGS_REG)
11236 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11237 (match_operand:QI 2 "const1_operand" "I"))
11239 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11240 (ashiftrt:QI (match_dup 1) (match_dup 2)))]
11241 "ix86_match_ccmode (insn, CCGOCmode)
11242 && (TARGET_SHIFT1 || optimize_size)
11243 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11245 [(set_attr "type" "ishift")
11246 (set (attr "length")
11247 (if_then_else (match_operand 0 "register_operand" "")
11249 (const_string "*")))])
11251 ;; This pattern can't accept a variable shift count, since shifts by
11252 ;; zero don't affect the flags. We assume that shifts by constant
11253 ;; zero are optimized away.
11254 (define_insn "*ashrqi3_cmp"
11255 [(set (reg FLAGS_REG)
11257 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11258 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11260 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11261 (ashiftrt:QI (match_dup 1) (match_dup 2)))]
11262 "ix86_match_ccmode (insn, CCGOCmode)
11263 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11264 "sar{b}\t{%2, %0|%0, %2}"
11265 [(set_attr "type" "ishift")
11266 (set_attr "mode" "QI")])
11268 ;; Logical shift instructions
11270 ;; See comment above `ashldi3' about how this works.
11272 (define_expand "lshrdi3"
11273 [(set (match_operand:DI 0 "shiftdi_operand" "")
11274 (lshiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
11275 (match_operand:QI 2 "nonmemory_operand" "")))]
11277 "ix86_expand_binary_operator (LSHIFTRT, DImode, operands); DONE;")
11279 (define_insn "*lshrdi3_1_one_bit_rex64"
11280 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11281 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11282 (match_operand:QI 2 "const1_operand" "")))
11283 (clobber (reg:CC FLAGS_REG))]
11284 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11285 && (TARGET_SHIFT1 || optimize_size)"
11287 [(set_attr "type" "ishift")
11288 (set (attr "length")
11289 (if_then_else (match_operand:DI 0 "register_operand" "")
11291 (const_string "*")))])
11293 (define_insn "*lshrdi3_1_rex64"
11294 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11295 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11296 (match_operand:QI 2 "nonmemory_operand" "J,c")))
11297 (clobber (reg:CC FLAGS_REG))]
11298 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11300 shr{q}\t{%2, %0|%0, %2}
11301 shr{q}\t{%b2, %0|%0, %b2}"
11302 [(set_attr "type" "ishift")
11303 (set_attr "mode" "DI")])
11305 ;; This pattern can't accept a variable shift count, since shifts by
11306 ;; zero don't affect the flags. We assume that shifts by constant
11307 ;; zero are optimized away.
11308 (define_insn "*lshrdi3_cmp_one_bit_rex64"
11309 [(set (reg FLAGS_REG)
11311 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11312 (match_operand:QI 2 "const1_operand" ""))
11314 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11315 (lshiftrt:DI (match_dup 1) (match_dup 2)))]
11316 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11317 && (TARGET_SHIFT1 || optimize_size)
11318 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11320 [(set_attr "type" "ishift")
11321 (set (attr "length")
11322 (if_then_else (match_operand:DI 0 "register_operand" "")
11324 (const_string "*")))])
11326 ;; This pattern can't accept a variable shift count, since shifts by
11327 ;; zero don't affect the flags. We assume that shifts by constant
11328 ;; zero are optimized away.
11329 (define_insn "*lshrdi3_cmp_rex64"
11330 [(set (reg FLAGS_REG)
11332 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11333 (match_operand:QI 2 "const_int_operand" "e"))
11335 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11336 (lshiftrt:DI (match_dup 1) (match_dup 2)))]
11337 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11338 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11339 "shr{q}\t{%2, %0|%0, %2}"
11340 [(set_attr "type" "ishift")
11341 (set_attr "mode" "DI")])
11343 (define_insn "*lshrdi3_1"
11344 [(set (match_operand:DI 0 "register_operand" "=r")
11345 (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
11346 (match_operand:QI 2 "nonmemory_operand" "Jc")))
11347 (clobber (reg:CC FLAGS_REG))]
11350 [(set_attr "type" "multi")])
11352 ;; By default we don't ask for a scratch register, because when DImode
11353 ;; values are manipulated, registers are already at a premium. But if
11354 ;; we have one handy, we won't turn it away.
11356 [(match_scratch:SI 3 "r")
11357 (parallel [(set (match_operand:DI 0 "register_operand" "")
11358 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
11359 (match_operand:QI 2 "nonmemory_operand" "")))
11360 (clobber (reg:CC FLAGS_REG))])
11362 "!TARGET_64BIT && TARGET_CMOVE"
11364 "ix86_split_lshrdi (operands, operands[3]); DONE;")
11367 [(set (match_operand:DI 0 "register_operand" "")
11368 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
11369 (match_operand:QI 2 "nonmemory_operand" "")))
11370 (clobber (reg:CC FLAGS_REG))]
11371 "!TARGET_64BIT && (flag_peephole2 ? flow2_completed : reload_completed)"
11373 "ix86_split_lshrdi (operands, NULL_RTX); DONE;")
11375 (define_expand "lshrsi3"
11376 [(set (match_operand:SI 0 "nonimmediate_operand" "")
11377 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
11378 (match_operand:QI 2 "nonmemory_operand" "")))
11379 (clobber (reg:CC FLAGS_REG))]
11381 "ix86_expand_binary_operator (LSHIFTRT, SImode, operands); DONE;")
11383 (define_insn "*lshrsi3_1_one_bit"
11384 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11385 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11386 (match_operand:QI 2 "const1_operand" "")))
11387 (clobber (reg:CC FLAGS_REG))]
11388 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11389 && (TARGET_SHIFT1 || optimize_size)"
11391 [(set_attr "type" "ishift")
11392 (set (attr "length")
11393 (if_then_else (match_operand:SI 0 "register_operand" "")
11395 (const_string "*")))])
11397 (define_insn "*lshrsi3_1_one_bit_zext"
11398 [(set (match_operand:DI 0 "register_operand" "=r")
11399 (lshiftrt:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "0"))
11400 (match_operand:QI 2 "const1_operand" "")))
11401 (clobber (reg:CC FLAGS_REG))]
11402 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11403 && (TARGET_SHIFT1 || optimize_size)"
11405 [(set_attr "type" "ishift")
11406 (set_attr "length" "2")])
11408 (define_insn "*lshrsi3_1"
11409 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11410 (lshiftrt:SI (match_operand:SI 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 (LSHIFTRT, HImode, operands)"
11415 shr{l}\t{%2, %0|%0, %2}
11416 shr{l}\t{%b2, %0|%0, %b2}"
11417 [(set_attr "type" "ishift")
11418 (set_attr "mode" "SI")])
11420 (define_insn "*lshrsi3_1_zext"
11421 [(set (match_operand:DI 0 "register_operand" "=r,r")
11423 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11424 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11425 (clobber (reg:CC FLAGS_REG))]
11426 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11428 shr{l}\t{%2, %k0|%k0, %2}
11429 shr{l}\t{%b2, %k0|%k0, %b2}"
11430 [(set_attr "type" "ishift")
11431 (set_attr "mode" "SI")])
11433 ;; This pattern can't accept a variable shift count, since shifts by
11434 ;; zero don't affect the flags. We assume that shifts by constant
11435 ;; zero are optimized away.
11436 (define_insn "*lshrsi3_one_bit_cmp"
11437 [(set (reg FLAGS_REG)
11439 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11440 (match_operand:QI 2 "const1_operand" ""))
11442 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11443 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
11444 "ix86_match_ccmode (insn, CCGOCmode)
11445 && (TARGET_SHIFT1 || optimize_size)
11446 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11448 [(set_attr "type" "ishift")
11449 (set (attr "length")
11450 (if_then_else (match_operand:SI 0 "register_operand" "")
11452 (const_string "*")))])
11454 (define_insn "*lshrsi3_cmp_one_bit_zext"
11455 [(set (reg FLAGS_REG)
11457 (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
11458 (match_operand:QI 2 "const1_operand" ""))
11460 (set (match_operand:DI 0 "register_operand" "=r")
11461 (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
11462 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11463 && (TARGET_SHIFT1 || optimize_size)
11464 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11466 [(set_attr "type" "ishift")
11467 (set_attr "length" "2")])
11469 ;; This pattern can't accept a variable shift count, since shifts by
11470 ;; zero don't affect the flags. We assume that shifts by constant
11471 ;; zero are optimized away.
11472 (define_insn "*lshrsi3_cmp"
11473 [(set (reg FLAGS_REG)
11475 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11476 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11478 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11479 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
11480 "ix86_match_ccmode (insn, CCGOCmode)
11481 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11482 "shr{l}\t{%2, %0|%0, %2}"
11483 [(set_attr "type" "ishift")
11484 (set_attr "mode" "SI")])
11486 (define_insn "*lshrsi3_cmp_zext"
11487 [(set (reg FLAGS_REG)
11489 (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
11490 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11492 (set (match_operand:DI 0 "register_operand" "=r")
11493 (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
11494 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11495 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11496 "shr{l}\t{%2, %k0|%k0, %2}"
11497 [(set_attr "type" "ishift")
11498 (set_attr "mode" "SI")])
11500 (define_expand "lshrhi3"
11501 [(set (match_operand:HI 0 "nonimmediate_operand" "")
11502 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
11503 (match_operand:QI 2 "nonmemory_operand" "")))
11504 (clobber (reg:CC FLAGS_REG))]
11505 "TARGET_HIMODE_MATH"
11506 "ix86_expand_binary_operator (LSHIFTRT, HImode, operands); DONE;")
11508 (define_insn "*lshrhi3_1_one_bit"
11509 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11510 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11511 (match_operand:QI 2 "const1_operand" "")))
11512 (clobber (reg:CC FLAGS_REG))]
11513 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11514 && (TARGET_SHIFT1 || optimize_size)"
11516 [(set_attr "type" "ishift")
11517 (set (attr "length")
11518 (if_then_else (match_operand 0 "register_operand" "")
11520 (const_string "*")))])
11522 (define_insn "*lshrhi3_1"
11523 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11524 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11525 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11526 (clobber (reg:CC FLAGS_REG))]
11527 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11529 shr{w}\t{%2, %0|%0, %2}
11530 shr{w}\t{%b2, %0|%0, %b2}"
11531 [(set_attr "type" "ishift")
11532 (set_attr "mode" "HI")])
11534 ;; This pattern can't accept a variable shift count, since shifts by
11535 ;; zero don't affect the flags. We assume that shifts by constant
11536 ;; zero are optimized away.
11537 (define_insn "*lshrhi3_one_bit_cmp"
11538 [(set (reg FLAGS_REG)
11540 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11541 (match_operand:QI 2 "const1_operand" ""))
11543 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11544 (lshiftrt:HI (match_dup 1) (match_dup 2)))]
11545 "ix86_match_ccmode (insn, CCGOCmode)
11546 && (TARGET_SHIFT1 || optimize_size)
11547 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11549 [(set_attr "type" "ishift")
11550 (set (attr "length")
11551 (if_then_else (match_operand:SI 0 "register_operand" "")
11553 (const_string "*")))])
11555 ;; This pattern can't accept a variable shift count, since shifts by
11556 ;; zero don't affect the flags. We assume that shifts by constant
11557 ;; zero are optimized away.
11558 (define_insn "*lshrhi3_cmp"
11559 [(set (reg FLAGS_REG)
11561 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11562 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11564 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11565 (lshiftrt:HI (match_dup 1) (match_dup 2)))]
11566 "ix86_match_ccmode (insn, CCGOCmode)
11567 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11568 "shr{w}\t{%2, %0|%0, %2}"
11569 [(set_attr "type" "ishift")
11570 (set_attr "mode" "HI")])
11572 (define_expand "lshrqi3"
11573 [(set (match_operand:QI 0 "nonimmediate_operand" "")
11574 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
11575 (match_operand:QI 2 "nonmemory_operand" "")))
11576 (clobber (reg:CC FLAGS_REG))]
11577 "TARGET_QIMODE_MATH"
11578 "ix86_expand_binary_operator (LSHIFTRT, QImode, operands); DONE;")
11580 (define_insn "*lshrqi3_1_one_bit"
11581 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11582 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11583 (match_operand:QI 2 "const1_operand" "")))
11584 (clobber (reg:CC FLAGS_REG))]
11585 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)
11586 && (TARGET_SHIFT1 || optimize_size)"
11588 [(set_attr "type" "ishift")
11589 (set (attr "length")
11590 (if_then_else (match_operand 0 "register_operand" "")
11592 (const_string "*")))])
11594 (define_insn "*lshrqi3_1_one_bit_slp"
11595 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11596 (lshiftrt:QI (match_dup 0)
11597 (match_operand:QI 1 "const1_operand" "")))
11598 (clobber (reg:CC FLAGS_REG))]
11599 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11600 && (TARGET_SHIFT1 || optimize_size)"
11602 [(set_attr "type" "ishift1")
11603 (set (attr "length")
11604 (if_then_else (match_operand 0 "register_operand" "")
11606 (const_string "*")))])
11608 (define_insn "*lshrqi3_1"
11609 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11610 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11611 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11612 (clobber (reg:CC FLAGS_REG))]
11613 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
11615 shr{b}\t{%2, %0|%0, %2}
11616 shr{b}\t{%b2, %0|%0, %b2}"
11617 [(set_attr "type" "ishift")
11618 (set_attr "mode" "QI")])
11620 (define_insn "*lshrqi3_1_slp"
11621 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11622 (lshiftrt:QI (match_dup 0)
11623 (match_operand:QI 1 "nonmemory_operand" "I,c")))
11624 (clobber (reg:CC FLAGS_REG))]
11625 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11626 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11628 shr{b}\t{%1, %0|%0, %1}
11629 shr{b}\t{%b1, %0|%0, %b1}"
11630 [(set_attr "type" "ishift1")
11631 (set_attr "mode" "QI")])
11633 ;; This pattern can't accept a variable shift count, since shifts by
11634 ;; zero don't affect the flags. We assume that shifts by constant
11635 ;; zero are optimized away.
11636 (define_insn "*lshrqi2_one_bit_cmp"
11637 [(set (reg FLAGS_REG)
11639 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11640 (match_operand:QI 2 "const1_operand" ""))
11642 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11643 (lshiftrt:QI (match_dup 1) (match_dup 2)))]
11644 "ix86_match_ccmode (insn, CCGOCmode)
11645 && (TARGET_SHIFT1 || optimize_size)
11646 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
11648 [(set_attr "type" "ishift")
11649 (set (attr "length")
11650 (if_then_else (match_operand:SI 0 "register_operand" "")
11652 (const_string "*")))])
11654 ;; This pattern can't accept a variable shift count, since shifts by
11655 ;; zero don't affect the flags. We assume that shifts by constant
11656 ;; zero are optimized away.
11657 (define_insn "*lshrqi2_cmp"
11658 [(set (reg FLAGS_REG)
11660 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11661 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11663 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11664 (lshiftrt:QI (match_dup 1) (match_dup 2)))]
11665 "ix86_match_ccmode (insn, CCGOCmode)
11666 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
11667 "shr{b}\t{%2, %0|%0, %2}"
11668 [(set_attr "type" "ishift")
11669 (set_attr "mode" "QI")])
11671 ;; Rotate instructions
11673 (define_expand "rotldi3"
11674 [(set (match_operand:DI 0 "nonimmediate_operand" "")
11675 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "")
11676 (match_operand:QI 2 "nonmemory_operand" "")))
11677 (clobber (reg:CC FLAGS_REG))]
11679 "ix86_expand_binary_operator (ROTATE, DImode, operands); DONE;")
11681 (define_insn "*rotlsi3_1_one_bit_rex64"
11682 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11683 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11684 (match_operand:QI 2 "const1_operand" "")))
11685 (clobber (reg:CC FLAGS_REG))]
11686 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)
11687 && (TARGET_SHIFT1 || optimize_size)"
11689 [(set_attr "type" "rotate")
11690 (set (attr "length")
11691 (if_then_else (match_operand:DI 0 "register_operand" "")
11693 (const_string "*")))])
11695 (define_insn "*rotldi3_1_rex64"
11696 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11697 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11698 (match_operand:QI 2 "nonmemory_operand" "e,c")))
11699 (clobber (reg:CC FLAGS_REG))]
11700 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)"
11702 rol{q}\t{%2, %0|%0, %2}
11703 rol{q}\t{%b2, %0|%0, %b2}"
11704 [(set_attr "type" "rotate")
11705 (set_attr "mode" "DI")])
11707 (define_expand "rotlsi3"
11708 [(set (match_operand:SI 0 "nonimmediate_operand" "")
11709 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
11710 (match_operand:QI 2 "nonmemory_operand" "")))
11711 (clobber (reg:CC FLAGS_REG))]
11713 "ix86_expand_binary_operator (ROTATE, SImode, operands); DONE;")
11715 (define_insn "*rotlsi3_1_one_bit"
11716 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11717 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11718 (match_operand:QI 2 "const1_operand" "")))
11719 (clobber (reg:CC FLAGS_REG))]
11720 "ix86_binary_operator_ok (ROTATE, SImode, operands)
11721 && (TARGET_SHIFT1 || optimize_size)"
11723 [(set_attr "type" "rotate")
11724 (set (attr "length")
11725 (if_then_else (match_operand:SI 0 "register_operand" "")
11727 (const_string "*")))])
11729 (define_insn "*rotlsi3_1_one_bit_zext"
11730 [(set (match_operand:DI 0 "register_operand" "=r")
11732 (rotate:SI (match_operand:SI 1 "register_operand" "0")
11733 (match_operand:QI 2 "const1_operand" ""))))
11734 (clobber (reg:CC FLAGS_REG))]
11735 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)
11736 && (TARGET_SHIFT1 || optimize_size)"
11738 [(set_attr "type" "rotate")
11739 (set_attr "length" "2")])
11741 (define_insn "*rotlsi3_1"
11742 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11743 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11744 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11745 (clobber (reg:CC FLAGS_REG))]
11746 "ix86_binary_operator_ok (ROTATE, SImode, operands)"
11748 rol{l}\t{%2, %0|%0, %2}
11749 rol{l}\t{%b2, %0|%0, %b2}"
11750 [(set_attr "type" "rotate")
11751 (set_attr "mode" "SI")])
11753 (define_insn "*rotlsi3_1_zext"
11754 [(set (match_operand:DI 0 "register_operand" "=r,r")
11756 (rotate:SI (match_operand:SI 1 "register_operand" "0,0")
11757 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11758 (clobber (reg:CC FLAGS_REG))]
11759 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)"
11761 rol{l}\t{%2, %k0|%k0, %2}
11762 rol{l}\t{%b2, %k0|%k0, %b2}"
11763 [(set_attr "type" "rotate")
11764 (set_attr "mode" "SI")])
11766 (define_expand "rotlhi3"
11767 [(set (match_operand:HI 0 "nonimmediate_operand" "")
11768 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "")
11769 (match_operand:QI 2 "nonmemory_operand" "")))
11770 (clobber (reg:CC FLAGS_REG))]
11771 "TARGET_HIMODE_MATH"
11772 "ix86_expand_binary_operator (ROTATE, HImode, operands); DONE;")
11774 (define_insn "*rotlhi3_1_one_bit"
11775 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11776 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11777 (match_operand:QI 2 "const1_operand" "")))
11778 (clobber (reg:CC FLAGS_REG))]
11779 "ix86_binary_operator_ok (ROTATE, HImode, operands)
11780 && (TARGET_SHIFT1 || optimize_size)"
11782 [(set_attr "type" "rotate")
11783 (set (attr "length")
11784 (if_then_else (match_operand 0 "register_operand" "")
11786 (const_string "*")))])
11788 (define_insn "*rotlhi3_1"
11789 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11790 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11791 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11792 (clobber (reg:CC FLAGS_REG))]
11793 "ix86_binary_operator_ok (ROTATE, HImode, operands)"
11795 rol{w}\t{%2, %0|%0, %2}
11796 rol{w}\t{%b2, %0|%0, %b2}"
11797 [(set_attr "type" "rotate")
11798 (set_attr "mode" "HI")])
11800 (define_expand "rotlqi3"
11801 [(set (match_operand:QI 0 "nonimmediate_operand" "")
11802 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "")
11803 (match_operand:QI 2 "nonmemory_operand" "")))
11804 (clobber (reg:CC FLAGS_REG))]
11805 "TARGET_QIMODE_MATH"
11806 "ix86_expand_binary_operator (ROTATE, QImode, operands); DONE;")
11808 (define_insn "*rotlqi3_1_one_bit_slp"
11809 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11810 (rotate:QI (match_dup 0)
11811 (match_operand:QI 1 "const1_operand" "")))
11812 (clobber (reg:CC FLAGS_REG))]
11813 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11814 && (TARGET_SHIFT1 || optimize_size)"
11816 [(set_attr "type" "rotate1")
11817 (set (attr "length")
11818 (if_then_else (match_operand 0 "register_operand" "")
11820 (const_string "*")))])
11822 (define_insn "*rotlqi3_1_one_bit"
11823 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11824 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11825 (match_operand:QI 2 "const1_operand" "")))
11826 (clobber (reg:CC FLAGS_REG))]
11827 "ix86_binary_operator_ok (ROTATE, QImode, operands)
11828 && (TARGET_SHIFT1 || optimize_size)"
11830 [(set_attr "type" "rotate")
11831 (set (attr "length")
11832 (if_then_else (match_operand 0 "register_operand" "")
11834 (const_string "*")))])
11836 (define_insn "*rotlqi3_1_slp"
11837 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11838 (rotate:QI (match_dup 0)
11839 (match_operand:QI 1 "nonmemory_operand" "I,c")))
11840 (clobber (reg:CC FLAGS_REG))]
11841 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11842 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11844 rol{b}\t{%1, %0|%0, %1}
11845 rol{b}\t{%b1, %0|%0, %b1}"
11846 [(set_attr "type" "rotate1")
11847 (set_attr "mode" "QI")])
11849 (define_insn "*rotlqi3_1"
11850 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11851 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11852 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11853 (clobber (reg:CC FLAGS_REG))]
11854 "ix86_binary_operator_ok (ROTATE, QImode, operands)"
11856 rol{b}\t{%2, %0|%0, %2}
11857 rol{b}\t{%b2, %0|%0, %b2}"
11858 [(set_attr "type" "rotate")
11859 (set_attr "mode" "QI")])
11861 (define_expand "rotrdi3"
11862 [(set (match_operand:DI 0 "nonimmediate_operand" "")
11863 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "")
11864 (match_operand:QI 2 "nonmemory_operand" "")))
11865 (clobber (reg:CC FLAGS_REG))]
11867 "ix86_expand_binary_operator (ROTATERT, DImode, operands); DONE;")
11869 (define_insn "*rotrdi3_1_one_bit_rex64"
11870 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11871 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11872 (match_operand:QI 2 "const1_operand" "")))
11873 (clobber (reg:CC FLAGS_REG))]
11874 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)
11875 && (TARGET_SHIFT1 || optimize_size)"
11877 [(set_attr "type" "rotate")
11878 (set (attr "length")
11879 (if_then_else (match_operand:DI 0 "register_operand" "")
11881 (const_string "*")))])
11883 (define_insn "*rotrdi3_1_rex64"
11884 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11885 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11886 (match_operand:QI 2 "nonmemory_operand" "J,c")))
11887 (clobber (reg:CC FLAGS_REG))]
11888 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
11890 ror{q}\t{%2, %0|%0, %2}
11891 ror{q}\t{%b2, %0|%0, %b2}"
11892 [(set_attr "type" "rotate")
11893 (set_attr "mode" "DI")])
11895 (define_expand "rotrsi3"
11896 [(set (match_operand:SI 0 "nonimmediate_operand" "")
11897 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
11898 (match_operand:QI 2 "nonmemory_operand" "")))
11899 (clobber (reg:CC FLAGS_REG))]
11901 "ix86_expand_binary_operator (ROTATERT, SImode, operands); DONE;")
11903 (define_insn "*rotrsi3_1_one_bit"
11904 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11905 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11906 (match_operand:QI 2 "const1_operand" "")))
11907 (clobber (reg:CC FLAGS_REG))]
11908 "ix86_binary_operator_ok (ROTATERT, SImode, operands)
11909 && (TARGET_SHIFT1 || optimize_size)"
11911 [(set_attr "type" "rotate")
11912 (set (attr "length")
11913 (if_then_else (match_operand:SI 0 "register_operand" "")
11915 (const_string "*")))])
11917 (define_insn "*rotrsi3_1_one_bit_zext"
11918 [(set (match_operand:DI 0 "register_operand" "=r")
11920 (rotatert:SI (match_operand:SI 1 "register_operand" "0")
11921 (match_operand:QI 2 "const1_operand" ""))))
11922 (clobber (reg:CC FLAGS_REG))]
11923 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)
11924 && (TARGET_SHIFT1 || optimize_size)"
11926 [(set_attr "type" "rotate")
11927 (set (attr "length")
11928 (if_then_else (match_operand:SI 0 "register_operand" "")
11930 (const_string "*")))])
11932 (define_insn "*rotrsi3_1"
11933 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11934 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11935 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11936 (clobber (reg:CC FLAGS_REG))]
11937 "ix86_binary_operator_ok (ROTATERT, SImode, operands)"
11939 ror{l}\t{%2, %0|%0, %2}
11940 ror{l}\t{%b2, %0|%0, %b2}"
11941 [(set_attr "type" "rotate")
11942 (set_attr "mode" "SI")])
11944 (define_insn "*rotrsi3_1_zext"
11945 [(set (match_operand:DI 0 "register_operand" "=r,r")
11947 (rotatert:SI (match_operand:SI 1 "register_operand" "0,0")
11948 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11949 (clobber (reg:CC FLAGS_REG))]
11950 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
11952 ror{l}\t{%2, %k0|%k0, %2}
11953 ror{l}\t{%b2, %k0|%k0, %b2}"
11954 [(set_attr "type" "rotate")
11955 (set_attr "mode" "SI")])
11957 (define_expand "rotrhi3"
11958 [(set (match_operand:HI 0 "nonimmediate_operand" "")
11959 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "")
11960 (match_operand:QI 2 "nonmemory_operand" "")))
11961 (clobber (reg:CC FLAGS_REG))]
11962 "TARGET_HIMODE_MATH"
11963 "ix86_expand_binary_operator (ROTATERT, HImode, operands); DONE;")
11965 (define_insn "*rotrhi3_one_bit"
11966 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11967 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11968 (match_operand:QI 2 "const1_operand" "")))
11969 (clobber (reg:CC FLAGS_REG))]
11970 "ix86_binary_operator_ok (ROTATERT, HImode, operands)
11971 && (TARGET_SHIFT1 || optimize_size)"
11973 [(set_attr "type" "rotate")
11974 (set (attr "length")
11975 (if_then_else (match_operand 0 "register_operand" "")
11977 (const_string "*")))])
11979 (define_insn "*rotrhi3"
11980 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11981 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11982 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11983 (clobber (reg:CC FLAGS_REG))]
11984 "ix86_binary_operator_ok (ROTATERT, HImode, operands)"
11986 ror{w}\t{%2, %0|%0, %2}
11987 ror{w}\t{%b2, %0|%0, %b2}"
11988 [(set_attr "type" "rotate")
11989 (set_attr "mode" "HI")])
11991 (define_expand "rotrqi3"
11992 [(set (match_operand:QI 0 "nonimmediate_operand" "")
11993 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "")
11994 (match_operand:QI 2 "nonmemory_operand" "")))
11995 (clobber (reg:CC FLAGS_REG))]
11996 "TARGET_QIMODE_MATH"
11997 "ix86_expand_binary_operator (ROTATERT, QImode, operands); DONE;")
11999 (define_insn "*rotrqi3_1_one_bit"
12000 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12001 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12002 (match_operand:QI 2 "const1_operand" "")))
12003 (clobber (reg:CC FLAGS_REG))]
12004 "ix86_binary_operator_ok (ROTATERT, QImode, operands)
12005 && (TARGET_SHIFT1 || optimize_size)"
12007 [(set_attr "type" "rotate")
12008 (set (attr "length")
12009 (if_then_else (match_operand 0 "register_operand" "")
12011 (const_string "*")))])
12013 (define_insn "*rotrqi3_1_one_bit_slp"
12014 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12015 (rotatert:QI (match_dup 0)
12016 (match_operand:QI 1 "const1_operand" "")))
12017 (clobber (reg:CC FLAGS_REG))]
12018 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12019 && (TARGET_SHIFT1 || optimize_size)"
12021 [(set_attr "type" "rotate1")
12022 (set (attr "length")
12023 (if_then_else (match_operand 0 "register_operand" "")
12025 (const_string "*")))])
12027 (define_insn "*rotrqi3_1"
12028 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12029 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12030 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12031 (clobber (reg:CC FLAGS_REG))]
12032 "ix86_binary_operator_ok (ROTATERT, QImode, operands)"
12034 ror{b}\t{%2, %0|%0, %2}
12035 ror{b}\t{%b2, %0|%0, %b2}"
12036 [(set_attr "type" "rotate")
12037 (set_attr "mode" "QI")])
12039 (define_insn "*rotrqi3_1_slp"
12040 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12041 (rotatert:QI (match_dup 0)
12042 (match_operand:QI 1 "nonmemory_operand" "I,c")))
12043 (clobber (reg:CC FLAGS_REG))]
12044 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12045 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
12047 ror{b}\t{%1, %0|%0, %1}
12048 ror{b}\t{%b1, %0|%0, %b1}"
12049 [(set_attr "type" "rotate1")
12050 (set_attr "mode" "QI")])
12052 ;; Bit set / bit test instructions
12054 (define_expand "extv"
12055 [(set (match_operand:SI 0 "register_operand" "")
12056 (sign_extract:SI (match_operand:SI 1 "register_operand" "")
12057 (match_operand:SI 2 "immediate_operand" "")
12058 (match_operand:SI 3 "immediate_operand" "")))]
12061 /* Handle extractions from %ah et al. */
12062 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
12065 /* From mips.md: extract_bit_field doesn't verify that our source
12066 matches the predicate, so check it again here. */
12067 if (! ext_register_operand (operands[1], VOIDmode))
12071 (define_expand "extzv"
12072 [(set (match_operand:SI 0 "register_operand" "")
12073 (zero_extract:SI (match_operand 1 "ext_register_operand" "")
12074 (match_operand:SI 2 "immediate_operand" "")
12075 (match_operand:SI 3 "immediate_operand" "")))]
12078 /* Handle extractions from %ah et al. */
12079 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
12082 /* From mips.md: extract_bit_field doesn't verify that our source
12083 matches the predicate, so check it again here. */
12084 if (! ext_register_operand (operands[1], VOIDmode))
12088 (define_expand "insv"
12089 [(set (zero_extract (match_operand 0 "ext_register_operand" "")
12090 (match_operand 1 "immediate_operand" "")
12091 (match_operand 2 "immediate_operand" ""))
12092 (match_operand 3 "register_operand" ""))]
12095 /* Handle extractions from %ah et al. */
12096 if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
12099 /* From mips.md: insert_bit_field doesn't verify that our source
12100 matches the predicate, so check it again here. */
12101 if (! ext_register_operand (operands[0], VOIDmode))
12105 emit_insn (gen_movdi_insv_1_rex64 (operands[0], operands[3]));
12107 emit_insn (gen_movsi_insv_1 (operands[0], operands[3]));
12112 ;; %%% bts, btr, btc, bt.
12113 ;; In general these instructions are *slow* when applied to memory,
12114 ;; since they enforce atomic operation. When applied to registers,
12115 ;; it depends on the cpu implementation. They're never faster than
12116 ;; the corresponding and/ior/xor operations, so with 32-bit there's
12117 ;; no point. But in 64-bit, we can't hold the relevant immediates
12118 ;; within the instruction itself, so operating on bits in the high
12119 ;; 32-bits of a register becomes easier.
12121 ;; These are slow on Nocona, but fast on Athlon64. We do require the use
12122 ;; of btrq and btcq for corner cases of post-reload expansion of absdf and
12123 ;; negdf respectively, so they can never be disabled entirely.
12125 (define_insn "*btsq"
12126 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12128 (match_operand:DI 1 "const_0_to_63_operand" ""))
12130 (clobber (reg:CC FLAGS_REG))]
12131 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12133 [(set_attr "type" "alu1")])
12135 (define_insn "*btrq"
12136 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12138 (match_operand:DI 1 "const_0_to_63_operand" ""))
12140 (clobber (reg:CC FLAGS_REG))]
12141 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12143 [(set_attr "type" "alu1")])
12145 (define_insn "*btcq"
12146 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12148 (match_operand:DI 1 "const_0_to_63_operand" ""))
12149 (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
12150 (clobber (reg:CC FLAGS_REG))]
12151 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12153 [(set_attr "type" "alu1")])
12155 ;; Allow Nocona to avoid these instructions if a register is available.
12158 [(match_scratch:DI 2 "r")
12159 (parallel [(set (zero_extract:DI
12160 (match_operand:DI 0 "register_operand" "")
12162 (match_operand:DI 1 "const_0_to_63_operand" ""))
12164 (clobber (reg:CC FLAGS_REG))])]
12165 "TARGET_64BIT && !TARGET_USE_BT"
12168 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12171 if (HOST_BITS_PER_WIDE_INT >= 64)
12172 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12173 else if (i < HOST_BITS_PER_WIDE_INT)
12174 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12176 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12178 op1 = immed_double_const (lo, hi, DImode);
12181 emit_move_insn (operands[2], op1);
12185 emit_insn (gen_iordi3 (operands[0], operands[0], op1));
12190 [(match_scratch:DI 2 "r")
12191 (parallel [(set (zero_extract:DI
12192 (match_operand:DI 0 "register_operand" "")
12194 (match_operand:DI 1 "const_0_to_63_operand" ""))
12196 (clobber (reg:CC FLAGS_REG))])]
12197 "TARGET_64BIT && !TARGET_USE_BT"
12200 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12203 if (HOST_BITS_PER_WIDE_INT >= 64)
12204 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12205 else if (i < HOST_BITS_PER_WIDE_INT)
12206 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12208 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12210 op1 = immed_double_const (~lo, ~hi, DImode);
12213 emit_move_insn (operands[2], op1);
12217 emit_insn (gen_anddi3 (operands[0], operands[0], op1));
12222 [(match_scratch:DI 2 "r")
12223 (parallel [(set (zero_extract:DI
12224 (match_operand:DI 0 "register_operand" "")
12226 (match_operand:DI 1 "const_0_to_63_operand" ""))
12227 (not:DI (zero_extract:DI
12228 (match_dup 0) (const_int 1) (match_dup 1))))
12229 (clobber (reg:CC FLAGS_REG))])]
12230 "TARGET_64BIT && !TARGET_USE_BT"
12233 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12236 if (HOST_BITS_PER_WIDE_INT >= 64)
12237 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12238 else if (i < HOST_BITS_PER_WIDE_INT)
12239 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12241 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12243 op1 = immed_double_const (lo, hi, DImode);
12246 emit_move_insn (operands[2], op1);
12250 emit_insn (gen_xordi3 (operands[0], operands[0], op1));
12254 ;; Store-flag instructions.
12256 ;; For all sCOND expanders, also expand the compare or test insn that
12257 ;; generates cc0. Generate an equality comparison if `seq' or `sne'.
12259 ;; %%% Do the expansion to SImode. If PII, do things the xor+setcc way
12260 ;; to avoid partial register stalls. Otherwise do things the setcc+movzx
12261 ;; way, which can later delete the movzx if only QImode is needed.
12263 (define_expand "seq"
12264 [(set (match_operand:QI 0 "register_operand" "")
12265 (eq:QI (reg:CC FLAGS_REG) (const_int 0)))]
12267 "if (ix86_expand_setcc (EQ, operands[0])) DONE; else FAIL;")
12269 (define_expand "sne"
12270 [(set (match_operand:QI 0 "register_operand" "")
12271 (ne:QI (reg:CC FLAGS_REG) (const_int 0)))]
12273 "if (ix86_expand_setcc (NE, operands[0])) DONE; else FAIL;")
12275 (define_expand "sgt"
12276 [(set (match_operand:QI 0 "register_operand" "")
12277 (gt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12279 "if (ix86_expand_setcc (GT, operands[0])) DONE; else FAIL;")
12281 (define_expand "sgtu"
12282 [(set (match_operand:QI 0 "register_operand" "")
12283 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12285 "if (ix86_expand_setcc (GTU, operands[0])) DONE; else FAIL;")
12287 (define_expand "slt"
12288 [(set (match_operand:QI 0 "register_operand" "")
12289 (lt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12291 "if (ix86_expand_setcc (LT, operands[0])) DONE; else FAIL;")
12293 (define_expand "sltu"
12294 [(set (match_operand:QI 0 "register_operand" "")
12295 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12297 "if (ix86_expand_setcc (LTU, operands[0])) DONE; else FAIL;")
12299 (define_expand "sge"
12300 [(set (match_operand:QI 0 "register_operand" "")
12301 (ge:QI (reg:CC FLAGS_REG) (const_int 0)))]
12303 "if (ix86_expand_setcc (GE, operands[0])) DONE; else FAIL;")
12305 (define_expand "sgeu"
12306 [(set (match_operand:QI 0 "register_operand" "")
12307 (geu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12309 "if (ix86_expand_setcc (GEU, operands[0])) DONE; else FAIL;")
12311 (define_expand "sle"
12312 [(set (match_operand:QI 0 "register_operand" "")
12313 (le:QI (reg:CC FLAGS_REG) (const_int 0)))]
12315 "if (ix86_expand_setcc (LE, operands[0])) DONE; else FAIL;")
12317 (define_expand "sleu"
12318 [(set (match_operand:QI 0 "register_operand" "")
12319 (leu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12321 "if (ix86_expand_setcc (LEU, operands[0])) DONE; else FAIL;")
12323 (define_expand "sunordered"
12324 [(set (match_operand:QI 0 "register_operand" "")
12325 (unordered:QI (reg:CC FLAGS_REG) (const_int 0)))]
12326 "TARGET_80387 || TARGET_SSE"
12327 "if (ix86_expand_setcc (UNORDERED, operands[0])) DONE; else FAIL;")
12329 (define_expand "sordered"
12330 [(set (match_operand:QI 0 "register_operand" "")
12331 (ordered:QI (reg:CC FLAGS_REG) (const_int 0)))]
12333 "if (ix86_expand_setcc (ORDERED, operands[0])) DONE; else FAIL;")
12335 (define_expand "suneq"
12336 [(set (match_operand:QI 0 "register_operand" "")
12337 (uneq:QI (reg:CC FLAGS_REG) (const_int 0)))]
12338 "TARGET_80387 || TARGET_SSE"
12339 "if (ix86_expand_setcc (UNEQ, operands[0])) DONE; else FAIL;")
12341 (define_expand "sunge"
12342 [(set (match_operand:QI 0 "register_operand" "")
12343 (unge:QI (reg:CC FLAGS_REG) (const_int 0)))]
12344 "TARGET_80387 || TARGET_SSE"
12345 "if (ix86_expand_setcc (UNGE, operands[0])) DONE; else FAIL;")
12347 (define_expand "sungt"
12348 [(set (match_operand:QI 0 "register_operand" "")
12349 (ungt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12350 "TARGET_80387 || TARGET_SSE"
12351 "if (ix86_expand_setcc (UNGT, operands[0])) DONE; else FAIL;")
12353 (define_expand "sunle"
12354 [(set (match_operand:QI 0 "register_operand" "")
12355 (unle:QI (reg:CC FLAGS_REG) (const_int 0)))]
12356 "TARGET_80387 || TARGET_SSE"
12357 "if (ix86_expand_setcc (UNLE, operands[0])) DONE; else FAIL;")
12359 (define_expand "sunlt"
12360 [(set (match_operand:QI 0 "register_operand" "")
12361 (unlt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12362 "TARGET_80387 || TARGET_SSE"
12363 "if (ix86_expand_setcc (UNLT, operands[0])) DONE; else FAIL;")
12365 (define_expand "sltgt"
12366 [(set (match_operand:QI 0 "register_operand" "")
12367 (ltgt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12368 "TARGET_80387 || TARGET_SSE"
12369 "if (ix86_expand_setcc (LTGT, operands[0])) DONE; else FAIL;")
12371 (define_insn "*setcc_1"
12372 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12373 (match_operator:QI 1 "ix86_comparison_operator"
12374 [(reg FLAGS_REG) (const_int 0)]))]
12377 [(set_attr "type" "setcc")
12378 (set_attr "mode" "QI")])
12380 (define_insn "*setcc_2"
12381 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12382 (match_operator:QI 1 "ix86_comparison_operator"
12383 [(reg FLAGS_REG) (const_int 0)]))]
12386 [(set_attr "type" "setcc")
12387 (set_attr "mode" "QI")])
12389 ;; In general it is not safe to assume too much about CCmode registers,
12390 ;; so simplify-rtx stops when it sees a second one. Under certain
12391 ;; conditions this is safe on x86, so help combine not create
12398 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12399 (ne:QI (match_operator 1 "ix86_comparison_operator"
12400 [(reg FLAGS_REG) (const_int 0)])
12403 [(set (match_dup 0) (match_dup 1))]
12405 PUT_MODE (operands[1], QImode);
12409 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
12410 (ne:QI (match_operator 1 "ix86_comparison_operator"
12411 [(reg FLAGS_REG) (const_int 0)])
12414 [(set (match_dup 0) (match_dup 1))]
12416 PUT_MODE (operands[1], QImode);
12420 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12421 (eq:QI (match_operator 1 "ix86_comparison_operator"
12422 [(reg FLAGS_REG) (const_int 0)])
12425 [(set (match_dup 0) (match_dup 1))]
12427 rtx new_op1 = copy_rtx (operands[1]);
12428 operands[1] = new_op1;
12429 PUT_MODE (new_op1, QImode);
12430 PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
12431 GET_MODE (XEXP (new_op1, 0))));
12433 /* Make sure that (a) the CCmode we have for the flags is strong
12434 enough for the reversed compare or (b) we have a valid FP compare. */
12435 if (! ix86_comparison_operator (new_op1, VOIDmode))
12440 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
12441 (eq:QI (match_operator 1 "ix86_comparison_operator"
12442 [(reg FLAGS_REG) (const_int 0)])
12445 [(set (match_dup 0) (match_dup 1))]
12447 rtx new_op1 = copy_rtx (operands[1]);
12448 operands[1] = new_op1;
12449 PUT_MODE (new_op1, QImode);
12450 PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
12451 GET_MODE (XEXP (new_op1, 0))));
12453 /* Make sure that (a) the CCmode we have for the flags is strong
12454 enough for the reversed compare or (b) we have a valid FP compare. */
12455 if (! ix86_comparison_operator (new_op1, VOIDmode))
12459 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
12460 ;; subsequent logical operations are used to imitate conditional moves.
12461 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
12464 (define_insn "*sse_setccsf"
12465 [(set (match_operand:SF 0 "register_operand" "=x")
12466 (match_operator:SF 1 "sse_comparison_operator"
12467 [(match_operand:SF 2 "register_operand" "0")
12468 (match_operand:SF 3 "nonimmediate_operand" "xm")]))]
12470 "cmp%D1ss\t{%3, %0|%0, %3}"
12471 [(set_attr "type" "ssecmp")
12472 (set_attr "mode" "SF")])
12474 (define_insn "*sse_setccdf"
12475 [(set (match_operand:DF 0 "register_operand" "=Y")
12476 (match_operator:DF 1 "sse_comparison_operator"
12477 [(match_operand:DF 2 "register_operand" "0")
12478 (match_operand:DF 3 "nonimmediate_operand" "Ym")]))]
12480 "cmp%D1sd\t{%3, %0|%0, %3}"
12481 [(set_attr "type" "ssecmp")
12482 (set_attr "mode" "DF")])
12484 ;; Basic conditional jump instructions.
12485 ;; We ignore the overflow flag for signed branch instructions.
12487 ;; For all bCOND expanders, also expand the compare or test insn that
12488 ;; generates reg FLAGS_REG. Generate an equality comparison if `beq' or `bne'.
12490 (define_expand "beq"
12492 (if_then_else (match_dup 1)
12493 (label_ref (match_operand 0 "" ""))
12496 "ix86_expand_branch (EQ, operands[0]); DONE;")
12498 (define_expand "bne"
12500 (if_then_else (match_dup 1)
12501 (label_ref (match_operand 0 "" ""))
12504 "ix86_expand_branch (NE, operands[0]); DONE;")
12506 (define_expand "bgt"
12508 (if_then_else (match_dup 1)
12509 (label_ref (match_operand 0 "" ""))
12512 "ix86_expand_branch (GT, operands[0]); DONE;")
12514 (define_expand "bgtu"
12516 (if_then_else (match_dup 1)
12517 (label_ref (match_operand 0 "" ""))
12520 "ix86_expand_branch (GTU, operands[0]); DONE;")
12522 (define_expand "blt"
12524 (if_then_else (match_dup 1)
12525 (label_ref (match_operand 0 "" ""))
12528 "ix86_expand_branch (LT, operands[0]); DONE;")
12530 (define_expand "bltu"
12532 (if_then_else (match_dup 1)
12533 (label_ref (match_operand 0 "" ""))
12536 "ix86_expand_branch (LTU, operands[0]); DONE;")
12538 (define_expand "bge"
12540 (if_then_else (match_dup 1)
12541 (label_ref (match_operand 0 "" ""))
12544 "ix86_expand_branch (GE, operands[0]); DONE;")
12546 (define_expand "bgeu"
12548 (if_then_else (match_dup 1)
12549 (label_ref (match_operand 0 "" ""))
12552 "ix86_expand_branch (GEU, operands[0]); DONE;")
12554 (define_expand "ble"
12556 (if_then_else (match_dup 1)
12557 (label_ref (match_operand 0 "" ""))
12560 "ix86_expand_branch (LE, operands[0]); DONE;")
12562 (define_expand "bleu"
12564 (if_then_else (match_dup 1)
12565 (label_ref (match_operand 0 "" ""))
12568 "ix86_expand_branch (LEU, operands[0]); DONE;")
12570 (define_expand "bunordered"
12572 (if_then_else (match_dup 1)
12573 (label_ref (match_operand 0 "" ""))
12575 "TARGET_80387 || TARGET_SSE_MATH"
12576 "ix86_expand_branch (UNORDERED, operands[0]); DONE;")
12578 (define_expand "bordered"
12580 (if_then_else (match_dup 1)
12581 (label_ref (match_operand 0 "" ""))
12583 "TARGET_80387 || TARGET_SSE_MATH"
12584 "ix86_expand_branch (ORDERED, operands[0]); DONE;")
12586 (define_expand "buneq"
12588 (if_then_else (match_dup 1)
12589 (label_ref (match_operand 0 "" ""))
12591 "TARGET_80387 || TARGET_SSE_MATH"
12592 "ix86_expand_branch (UNEQ, operands[0]); DONE;")
12594 (define_expand "bunge"
12596 (if_then_else (match_dup 1)
12597 (label_ref (match_operand 0 "" ""))
12599 "TARGET_80387 || TARGET_SSE_MATH"
12600 "ix86_expand_branch (UNGE, operands[0]); DONE;")
12602 (define_expand "bungt"
12604 (if_then_else (match_dup 1)
12605 (label_ref (match_operand 0 "" ""))
12607 "TARGET_80387 || TARGET_SSE_MATH"
12608 "ix86_expand_branch (UNGT, operands[0]); DONE;")
12610 (define_expand "bunle"
12612 (if_then_else (match_dup 1)
12613 (label_ref (match_operand 0 "" ""))
12615 "TARGET_80387 || TARGET_SSE_MATH"
12616 "ix86_expand_branch (UNLE, operands[0]); DONE;")
12618 (define_expand "bunlt"
12620 (if_then_else (match_dup 1)
12621 (label_ref (match_operand 0 "" ""))
12623 "TARGET_80387 || TARGET_SSE_MATH"
12624 "ix86_expand_branch (UNLT, operands[0]); DONE;")
12626 (define_expand "bltgt"
12628 (if_then_else (match_dup 1)
12629 (label_ref (match_operand 0 "" ""))
12631 "TARGET_80387 || TARGET_SSE_MATH"
12632 "ix86_expand_branch (LTGT, operands[0]); DONE;")
12634 (define_insn "*jcc_1"
12636 (if_then_else (match_operator 1 "ix86_comparison_operator"
12637 [(reg FLAGS_REG) (const_int 0)])
12638 (label_ref (match_operand 0 "" ""))
12642 [(set_attr "type" "ibr")
12643 (set_attr "modrm" "0")
12644 (set (attr "length")
12645 (if_then_else (and (ge (minus (match_dup 0) (pc))
12647 (lt (minus (match_dup 0) (pc))
12652 (define_insn "*jcc_2"
12654 (if_then_else (match_operator 1 "ix86_comparison_operator"
12655 [(reg FLAGS_REG) (const_int 0)])
12657 (label_ref (match_operand 0 "" ""))))]
12660 [(set_attr "type" "ibr")
12661 (set_attr "modrm" "0")
12662 (set (attr "length")
12663 (if_then_else (and (ge (minus (match_dup 0) (pc))
12665 (lt (minus (match_dup 0) (pc))
12670 ;; In general it is not safe to assume too much about CCmode registers,
12671 ;; so simplify-rtx stops when it sees a second one. Under certain
12672 ;; conditions this is safe on x86, so help combine not create
12680 (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
12681 [(reg FLAGS_REG) (const_int 0)])
12683 (label_ref (match_operand 1 "" ""))
12687 (if_then_else (match_dup 0)
12688 (label_ref (match_dup 1))
12691 PUT_MODE (operands[0], VOIDmode);
12696 (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
12697 [(reg FLAGS_REG) (const_int 0)])
12699 (label_ref (match_operand 1 "" ""))
12703 (if_then_else (match_dup 0)
12704 (label_ref (match_dup 1))
12707 rtx new_op0 = copy_rtx (operands[0]);
12708 operands[0] = new_op0;
12709 PUT_MODE (new_op0, VOIDmode);
12710 PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0),
12711 GET_MODE (XEXP (new_op0, 0))));
12713 /* Make sure that (a) the CCmode we have for the flags is strong
12714 enough for the reversed compare or (b) we have a valid FP compare. */
12715 if (! ix86_comparison_operator (new_op0, VOIDmode))
12719 ;; Define combination compare-and-branch fp compare instructions to use
12720 ;; during early optimization. Splitting the operation apart early makes
12721 ;; for bad code when we want to reverse the operation.
12723 (define_insn "*fp_jcc_1_mixed"
12725 (if_then_else (match_operator 0 "comparison_operator"
12726 [(match_operand 1 "register_operand" "f#x,x#f")
12727 (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
12728 (label_ref (match_operand 3 "" ""))
12730 (clobber (reg:CCFP FPSR_REG))
12731 (clobber (reg:CCFP FLAGS_REG))]
12732 "TARGET_MIX_SSE_I387
12733 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
12734 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12735 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12738 (define_insn "*fp_jcc_1_sse"
12740 (if_then_else (match_operator 0 "comparison_operator"
12741 [(match_operand 1 "register_operand" "x")
12742 (match_operand 2 "nonimmediate_operand" "xm")])
12743 (label_ref (match_operand 3 "" ""))
12745 (clobber (reg:CCFP FPSR_REG))
12746 (clobber (reg:CCFP FLAGS_REG))]
12748 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
12749 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12750 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12753 (define_insn "*fp_jcc_1_387"
12755 (if_then_else (match_operator 0 "comparison_operator"
12756 [(match_operand 1 "register_operand" "f")
12757 (match_operand 2 "register_operand" "f")])
12758 (label_ref (match_operand 3 "" ""))
12760 (clobber (reg:CCFP FPSR_REG))
12761 (clobber (reg:CCFP FLAGS_REG))]
12762 "TARGET_CMOVE && TARGET_80387
12763 && FLOAT_MODE_P (GET_MODE (operands[1]))
12764 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12765 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12768 (define_insn "*fp_jcc_2_mixed"
12770 (if_then_else (match_operator 0 "comparison_operator"
12771 [(match_operand 1 "register_operand" "f#x,x#f")
12772 (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
12774 (label_ref (match_operand 3 "" ""))))
12775 (clobber (reg:CCFP FPSR_REG))
12776 (clobber (reg:CCFP FLAGS_REG))]
12777 "TARGET_MIX_SSE_I387
12778 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
12779 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12780 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12783 (define_insn "*fp_jcc_2_sse"
12785 (if_then_else (match_operator 0 "comparison_operator"
12786 [(match_operand 1 "register_operand" "x")
12787 (match_operand 2 "nonimmediate_operand" "xm")])
12789 (label_ref (match_operand 3 "" ""))))
12790 (clobber (reg:CCFP FPSR_REG))
12791 (clobber (reg:CCFP FLAGS_REG))]
12793 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
12794 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12795 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12798 (define_insn "*fp_jcc_2_387"
12800 (if_then_else (match_operator 0 "comparison_operator"
12801 [(match_operand 1 "register_operand" "f")
12802 (match_operand 2 "register_operand" "f")])
12804 (label_ref (match_operand 3 "" ""))))
12805 (clobber (reg:CCFP FPSR_REG))
12806 (clobber (reg:CCFP FLAGS_REG))]
12807 "TARGET_CMOVE && TARGET_80387
12808 && FLOAT_MODE_P (GET_MODE (operands[1]))
12809 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12810 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12813 (define_insn "*fp_jcc_3_387"
12815 (if_then_else (match_operator 0 "comparison_operator"
12816 [(match_operand 1 "register_operand" "f")
12817 (match_operand 2 "nonimmediate_operand" "fm")])
12818 (label_ref (match_operand 3 "" ""))
12820 (clobber (reg:CCFP FPSR_REG))
12821 (clobber (reg:CCFP FLAGS_REG))
12822 (clobber (match_scratch:HI 4 "=a"))]
12824 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
12825 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12826 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
12827 && SELECT_CC_MODE (GET_CODE (operands[0]),
12828 operands[1], operands[2]) == CCFPmode
12829 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12832 (define_insn "*fp_jcc_4_387"
12834 (if_then_else (match_operator 0 "comparison_operator"
12835 [(match_operand 1 "register_operand" "f")
12836 (match_operand 2 "nonimmediate_operand" "fm")])
12838 (label_ref (match_operand 3 "" ""))))
12839 (clobber (reg:CCFP FPSR_REG))
12840 (clobber (reg:CCFP FLAGS_REG))
12841 (clobber (match_scratch:HI 4 "=a"))]
12843 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
12844 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12845 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
12846 && SELECT_CC_MODE (GET_CODE (operands[0]),
12847 operands[1], operands[2]) == CCFPmode
12848 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12851 (define_insn "*fp_jcc_5_387"
12853 (if_then_else (match_operator 0 "comparison_operator"
12854 [(match_operand 1 "register_operand" "f")
12855 (match_operand 2 "register_operand" "f")])
12856 (label_ref (match_operand 3 "" ""))
12858 (clobber (reg:CCFP FPSR_REG))
12859 (clobber (reg:CCFP FLAGS_REG))
12860 (clobber (match_scratch:HI 4 "=a"))]
12862 && FLOAT_MODE_P (GET_MODE (operands[1]))
12863 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12864 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12867 (define_insn "*fp_jcc_6_387"
12869 (if_then_else (match_operator 0 "comparison_operator"
12870 [(match_operand 1 "register_operand" "f")
12871 (match_operand 2 "register_operand" "f")])
12873 (label_ref (match_operand 3 "" ""))))
12874 (clobber (reg:CCFP FPSR_REG))
12875 (clobber (reg:CCFP FLAGS_REG))
12876 (clobber (match_scratch:HI 4 "=a"))]
12878 && FLOAT_MODE_P (GET_MODE (operands[1]))
12879 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12880 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12883 (define_insn "*fp_jcc_7_387"
12885 (if_then_else (match_operator 0 "comparison_operator"
12886 [(match_operand 1 "register_operand" "f")
12887 (match_operand 2 "const0_operand" "X")])
12888 (label_ref (match_operand 3 "" ""))
12890 (clobber (reg:CCFP FPSR_REG))
12891 (clobber (reg:CCFP FLAGS_REG))
12892 (clobber (match_scratch:HI 4 "=a"))]
12894 && FLOAT_MODE_P (GET_MODE (operands[1]))
12895 && GET_MODE (operands[1]) == GET_MODE (operands[2])
12896 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
12897 && SELECT_CC_MODE (GET_CODE (operands[0]),
12898 operands[1], operands[2]) == CCFPmode
12899 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
12902 ;; The order of operands in *fp_jcc_8_387 is forced by combine in
12903 ;; simplify_comparison () function. Float operator is treated as RTX_OBJ
12904 ;; with a precedence over other operators and is always put in the first
12905 ;; place. Swap condition and operands to match ficom instruction.
12907 (define_insn "*fp_jcc_8<mode>_387"
12909 (if_then_else (match_operator 0 "comparison_operator"
12910 [(match_operator 1 "float_operator"
12911 [(match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r")])
12912 (match_operand 3 "register_operand" "f,f")])
12913 (label_ref (match_operand 4 "" ""))
12915 (clobber (reg:CCFP FPSR_REG))
12916 (clobber (reg:CCFP FLAGS_REG))
12917 (clobber (match_scratch:HI 5 "=a,a"))]
12918 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
12919 && FLOAT_MODE_P (GET_MODE (operands[3]))
12920 && GET_MODE (operands[1]) == GET_MODE (operands[3])
12921 && !ix86_use_fcomi_compare (swap_condition (GET_CODE (operands[0])))
12922 && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode
12923 && ix86_fp_jump_nontrivial_p (swap_condition (GET_CODE (operands[0])))"
12928 (if_then_else (match_operator 0 "comparison_operator"
12929 [(match_operand 1 "register_operand" "")
12930 (match_operand 2 "nonimmediate_operand" "")])
12931 (match_operand 3 "" "")
12932 (match_operand 4 "" "")))
12933 (clobber (reg:CCFP FPSR_REG))
12934 (clobber (reg:CCFP FLAGS_REG))]
12938 ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
12939 operands[3], operands[4], NULL_RTX, NULL_RTX);
12945 (if_then_else (match_operator 0 "comparison_operator"
12946 [(match_operand 1 "register_operand" "")
12947 (match_operand 2 "general_operand" "")])
12948 (match_operand 3 "" "")
12949 (match_operand 4 "" "")))
12950 (clobber (reg:CCFP FPSR_REG))
12951 (clobber (reg:CCFP FLAGS_REG))
12952 (clobber (match_scratch:HI 5 "=a"))]
12956 ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
12957 operands[3], operands[4], operands[5], NULL_RTX);
12963 (if_then_else (match_operator 0 "comparison_operator"
12964 [(match_operator 1 "float_operator"
12965 [(match_operand:X87MODEI12 2 "memory_operand" "")])
12966 (match_operand 3 "register_operand" "")])
12967 (match_operand 4 "" "")
12968 (match_operand 5 "" "")))
12969 (clobber (reg:CCFP FPSR_REG))
12970 (clobber (reg:CCFP FLAGS_REG))
12971 (clobber (match_scratch:HI 6 "=a"))]
12975 operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]);
12976 ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
12977 operands[3], operands[7],
12978 operands[4], operands[5], operands[6], NULL_RTX);
12982 ;; %%% Kill this when reload knows how to do it.
12985 (if_then_else (match_operator 0 "comparison_operator"
12986 [(match_operator 1 "float_operator"
12987 [(match_operand:X87MODEI12 2 "register_operand" "")])
12988 (match_operand 3 "register_operand" "")])
12989 (match_operand 4 "" "")
12990 (match_operand 5 "" "")))
12991 (clobber (reg:CCFP FPSR_REG))
12992 (clobber (reg:CCFP FLAGS_REG))
12993 (clobber (match_scratch:HI 6 "=a"))]
12997 operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
12998 operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]);
12999 ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
13000 operands[3], operands[7],
13001 operands[4], operands[5], operands[6], operands[2]);
13005 ;; Unconditional and other jump instructions
13007 (define_insn "jump"
13009 (label_ref (match_operand 0 "" "")))]
13012 [(set_attr "type" "ibr")
13013 (set (attr "length")
13014 (if_then_else (and (ge (minus (match_dup 0) (pc))
13016 (lt (minus (match_dup 0) (pc))
13020 (set_attr "modrm" "0")])
13022 (define_expand "indirect_jump"
13023 [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))]
13027 (define_insn "*indirect_jump"
13028 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))]
13031 [(set_attr "type" "ibr")
13032 (set_attr "length_immediate" "0")])
13034 (define_insn "*indirect_jump_rtx64"
13035 [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))]
13038 [(set_attr "type" "ibr")
13039 (set_attr "length_immediate" "0")])
13041 (define_expand "tablejump"
13042 [(parallel [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))
13043 (use (label_ref (match_operand 1 "" "")))])]
13046 /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
13047 relative. Convert the relative address to an absolute address. */
13051 enum rtx_code code;
13057 op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
13059 else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
13063 op1 = pic_offset_table_rtx;
13068 op0 = pic_offset_table_rtx;
13072 operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
13077 (define_insn "*tablejump_1"
13078 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))
13079 (use (label_ref (match_operand 1 "" "")))]
13082 [(set_attr "type" "ibr")
13083 (set_attr "length_immediate" "0")])
13085 (define_insn "*tablejump_1_rtx64"
13086 [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))
13087 (use (label_ref (match_operand 1 "" "")))]
13090 [(set_attr "type" "ibr")
13091 (set_attr "length_immediate" "0")])
13093 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
13096 [(set (reg FLAGS_REG) (match_operand 0 "" ""))
13097 (set (match_operand:QI 1 "register_operand" "")
13098 (match_operator:QI 2 "ix86_comparison_operator"
13099 [(reg FLAGS_REG) (const_int 0)]))
13100 (set (match_operand 3 "q_regs_operand" "")
13101 (zero_extend (match_dup 1)))]
13102 "(peep2_reg_dead_p (3, operands[1])
13103 || operands_match_p (operands[1], operands[3]))
13104 && ! reg_overlap_mentioned_p (operands[3], operands[0])"
13105 [(set (match_dup 4) (match_dup 0))
13106 (set (strict_low_part (match_dup 5))
13109 operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
13110 operands[5] = gen_lowpart (QImode, operands[3]);
13111 ix86_expand_clear (operands[3]);
13114 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
13117 [(set (reg FLAGS_REG) (match_operand 0 "" ""))
13118 (set (match_operand:QI 1 "register_operand" "")
13119 (match_operator:QI 2 "ix86_comparison_operator"
13120 [(reg FLAGS_REG) (const_int 0)]))
13121 (parallel [(set (match_operand 3 "q_regs_operand" "")
13122 (zero_extend (match_dup 1)))
13123 (clobber (reg:CC FLAGS_REG))])]
13124 "(peep2_reg_dead_p (3, operands[1])
13125 || operands_match_p (operands[1], operands[3]))
13126 && ! reg_overlap_mentioned_p (operands[3], operands[0])"
13127 [(set (match_dup 4) (match_dup 0))
13128 (set (strict_low_part (match_dup 5))
13131 operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
13132 operands[5] = gen_lowpart (QImode, operands[3]);
13133 ix86_expand_clear (operands[3]);
13136 ;; Call instructions.
13138 ;; The predicates normally associated with named expanders are not properly
13139 ;; checked for calls. This is a bug in the generic code, but it isn't that
13140 ;; easy to fix. Ignore it for now and be prepared to fix things up.
13142 ;; Call subroutine returning no value.
13144 (define_expand "call_pop"
13145 [(parallel [(call (match_operand:QI 0 "" "")
13146 (match_operand:SI 1 "" ""))
13147 (set (reg:SI SP_REG)
13148 (plus:SI (reg:SI SP_REG)
13149 (match_operand:SI 3 "" "")))])]
13152 ix86_expand_call (NULL, operands[0], operands[1], operands[2], operands[3], 0);
13156 (define_insn "*call_pop_0"
13157 [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" ""))
13158 (match_operand:SI 1 "" ""))
13159 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
13160 (match_operand:SI 2 "immediate_operand" "")))]
13163 if (SIBLING_CALL_P (insn))
13166 return "call\t%P0";
13168 [(set_attr "type" "call")])
13170 (define_insn "*call_pop_1"
13171 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
13172 (match_operand:SI 1 "" ""))
13173 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
13174 (match_operand:SI 2 "immediate_operand" "i")))]
13177 if (constant_call_address_operand (operands[0], Pmode))
13179 if (SIBLING_CALL_P (insn))
13182 return "call\t%P0";
13184 if (SIBLING_CALL_P (insn))
13187 return "call\t%A0";
13189 [(set_attr "type" "call")])
13191 (define_expand "call"
13192 [(call (match_operand:QI 0 "" "")
13193 (match_operand 1 "" ""))
13194 (use (match_operand 2 "" ""))]
13197 ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 0);
13201 (define_expand "sibcall"
13202 [(call (match_operand:QI 0 "" "")
13203 (match_operand 1 "" ""))
13204 (use (match_operand 2 "" ""))]
13207 ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 1);
13211 (define_insn "*call_0"
13212 [(call (mem:QI (match_operand 0 "constant_call_address_operand" ""))
13213 (match_operand 1 "" ""))]
13216 if (SIBLING_CALL_P (insn))
13219 return "call\t%P0";
13221 [(set_attr "type" "call")])
13223 (define_insn "*call_1"
13224 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
13225 (match_operand 1 "" ""))]
13226 "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
13228 if (constant_call_address_operand (operands[0], Pmode))
13229 return "call\t%P0";
13230 return "call\t%A0";
13232 [(set_attr "type" "call")])
13234 (define_insn "*sibcall_1"
13235 [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "s,c,d,a"))
13236 (match_operand 1 "" ""))]
13237 "SIBLING_CALL_P (insn) && !TARGET_64BIT"
13239 if (constant_call_address_operand (operands[0], Pmode))
13243 [(set_attr "type" "call")])
13245 (define_insn "*call_1_rex64"
13246 [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rsm"))
13247 (match_operand 1 "" ""))]
13248 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
13250 if (constant_call_address_operand (operands[0], Pmode))
13251 return "call\t%P0";
13252 return "call\t%A0";
13254 [(set_attr "type" "call")])
13256 (define_insn "*sibcall_1_rex64"
13257 [(call (mem:QI (match_operand:DI 0 "constant_call_address_operand" ""))
13258 (match_operand 1 "" ""))]
13259 "SIBLING_CALL_P (insn) && TARGET_64BIT"
13261 [(set_attr "type" "call")])
13263 (define_insn "*sibcall_1_rex64_v"
13264 [(call (mem:QI (reg:DI 40))
13265 (match_operand 0 "" ""))]
13266 "SIBLING_CALL_P (insn) && TARGET_64BIT"
13268 [(set_attr "type" "call")])
13271 ;; Call subroutine, returning value in operand 0
13273 (define_expand "call_value_pop"
13274 [(parallel [(set (match_operand 0 "" "")
13275 (call (match_operand:QI 1 "" "")
13276 (match_operand:SI 2 "" "")))
13277 (set (reg:SI SP_REG)
13278 (plus:SI (reg:SI SP_REG)
13279 (match_operand:SI 4 "" "")))])]
13282 ix86_expand_call (operands[0], operands[1], operands[2],
13283 operands[3], operands[4], 0);
13287 (define_expand "call_value"
13288 [(set (match_operand 0 "" "")
13289 (call (match_operand:QI 1 "" "")
13290 (match_operand:SI 2 "" "")))
13291 (use (match_operand:SI 3 "" ""))]
13292 ;; Operand 2 not used on the i386.
13295 ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 0);
13299 (define_expand "sibcall_value"
13300 [(set (match_operand 0 "" "")
13301 (call (match_operand:QI 1 "" "")
13302 (match_operand:SI 2 "" "")))
13303 (use (match_operand:SI 3 "" ""))]
13304 ;; Operand 2 not used on the i386.
13307 ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 1);
13311 ;; Call subroutine returning any type.
13313 (define_expand "untyped_call"
13314 [(parallel [(call (match_operand 0 "" "")
13316 (match_operand 1 "" "")
13317 (match_operand 2 "" "")])]
13322 /* In order to give reg-stack an easier job in validating two
13323 coprocessor registers as containing a possible return value,
13324 simply pretend the untyped call returns a complex long double
13327 ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
13328 ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
13329 operands[0], const0_rtx, GEN_INT (SSE_REGPARM_MAX - 1),
13332 for (i = 0; i < XVECLEN (operands[2], 0); i++)
13334 rtx set = XVECEXP (operands[2], 0, i);
13335 emit_move_insn (SET_DEST (set), SET_SRC (set));
13338 /* The optimizer does not know that the call sets the function value
13339 registers we stored in the result block. We avoid problems by
13340 claiming that all hard registers are used and clobbered at this
13342 emit_insn (gen_blockage (const0_rtx));
13347 ;; Prologue and epilogue instructions
13349 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
13350 ;; all of memory. This blocks insns from being moved across this point.
13352 (define_insn "blockage"
13353 [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_BLOCKAGE)]
13356 [(set_attr "length" "0")])
13358 ;; Insn emitted into the body of a function to return from a function.
13359 ;; This is only done if the function's epilogue is known to be simple.
13360 ;; See comments for ix86_can_use_return_insn_p in i386.c.
13362 (define_expand "return"
13364 "ix86_can_use_return_insn_p ()"
13366 if (current_function_pops_args)
13368 rtx popc = GEN_INT (current_function_pops_args);
13369 emit_jump_insn (gen_return_pop_internal (popc));
13374 (define_insn "return_internal"
13378 [(set_attr "length" "1")
13379 (set_attr "length_immediate" "0")
13380 (set_attr "modrm" "0")])
13382 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
13383 ;; instruction Athlon and K8 have.
13385 (define_insn "return_internal_long"
13387 (unspec [(const_int 0)] UNSPEC_REP)]
13390 [(set_attr "length" "1")
13391 (set_attr "length_immediate" "0")
13392 (set_attr "prefix_rep" "1")
13393 (set_attr "modrm" "0")])
13395 (define_insn "return_pop_internal"
13397 (use (match_operand:SI 0 "const_int_operand" ""))]
13400 [(set_attr "length" "3")
13401 (set_attr "length_immediate" "2")
13402 (set_attr "modrm" "0")])
13404 (define_insn "return_indirect_internal"
13406 (use (match_operand:SI 0 "register_operand" "r"))]
13409 [(set_attr "type" "ibr")
13410 (set_attr "length_immediate" "0")])
13416 [(set_attr "length" "1")
13417 (set_attr "length_immediate" "0")
13418 (set_attr "modrm" "0")])
13420 ;; Align to 16-byte boundary, max skip in op0. Used to avoid
13421 ;; branch prediction penalty for the third jump in a 16-byte
13424 (define_insn "align"
13425 [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
13428 #ifdef ASM_OUTPUT_MAX_SKIP_ALIGN
13429 ASM_OUTPUT_MAX_SKIP_ALIGN (asm_out_file, 4, (int)INTVAL (operands[0]));
13431 /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
13432 The align insn is used to avoid 3 jump instructions in the row to improve
13433 branch prediction and the benefits hardly outweight the cost of extra 8
13434 nops on the average inserted by full alignment pseudo operation. */
13438 [(set_attr "length" "16")])
13440 (define_expand "prologue"
13443 "ix86_expand_prologue (); DONE;")
13445 (define_insn "set_got"
13446 [(set (match_operand:SI 0 "register_operand" "=r")
13447 (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
13448 (clobber (reg:CC FLAGS_REG))]
13450 { return output_set_got (operands[0]); }
13451 [(set_attr "type" "multi")
13452 (set_attr "length" "12")])
13454 (define_expand "epilogue"
13457 "ix86_expand_epilogue (1); DONE;")
13459 (define_expand "sibcall_epilogue"
13462 "ix86_expand_epilogue (0); DONE;")
13464 (define_expand "eh_return"
13465 [(use (match_operand 0 "register_operand" ""))]
13468 rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
13470 /* Tricky bit: we write the address of the handler to which we will
13471 be returning into someone else's stack frame, one word below the
13472 stack address we wish to restore. */
13473 tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
13474 tmp = plus_constant (tmp, -UNITS_PER_WORD);
13475 tmp = gen_rtx_MEM (Pmode, tmp);
13476 emit_move_insn (tmp, ra);
13478 if (Pmode == SImode)
13479 emit_jump_insn (gen_eh_return_si (sa));
13481 emit_jump_insn (gen_eh_return_di (sa));
13486 (define_insn_and_split "eh_return_si"
13488 (unspec [(match_operand:SI 0 "register_operand" "c")]
13489 UNSPEC_EH_RETURN))]
13494 "ix86_expand_epilogue (2); DONE;")
13496 (define_insn_and_split "eh_return_di"
13498 (unspec [(match_operand:DI 0 "register_operand" "c")]
13499 UNSPEC_EH_RETURN))]
13504 "ix86_expand_epilogue (2); DONE;")
13506 (define_insn "leave"
13507 [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4)))
13508 (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG)))
13509 (clobber (mem:BLK (scratch)))]
13512 [(set_attr "type" "leave")])
13514 (define_insn "leave_rex64"
13515 [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8)))
13516 (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG)))
13517 (clobber (mem:BLK (scratch)))]
13520 [(set_attr "type" "leave")])
13522 (define_expand "ffssi2"
13524 [(set (match_operand:SI 0 "register_operand" "")
13525 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "")))
13526 (clobber (match_scratch:SI 2 ""))
13527 (clobber (reg:CC FLAGS_REG))])]
13531 (define_insn_and_split "*ffs_cmove"
13532 [(set (match_operand:SI 0 "register_operand" "=r")
13533 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
13534 (clobber (match_scratch:SI 2 "=&r"))
13535 (clobber (reg:CC FLAGS_REG))]
13538 "&& reload_completed"
13539 [(set (match_dup 2) (const_int -1))
13540 (parallel [(set (reg:CCZ FLAGS_REG) (compare:CCZ (match_dup 1) (const_int 0)))
13541 (set (match_dup 0) (ctz:SI (match_dup 1)))])
13542 (set (match_dup 0) (if_then_else:SI
13543 (eq (reg:CCZ FLAGS_REG) (const_int 0))
13546 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
13547 (clobber (reg:CC FLAGS_REG))])]
13550 (define_insn_and_split "*ffs_no_cmove"
13551 [(set (match_operand:SI 0 "nonimmediate_operand" "=r")
13552 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
13553 (clobber (match_scratch:SI 2 "=&q"))
13554 (clobber (reg:CC FLAGS_REG))]
13558 [(parallel [(set (reg:CCZ FLAGS_REG) (compare:CCZ (match_dup 1) (const_int 0)))
13559 (set (match_dup 0) (ctz:SI (match_dup 1)))])
13560 (set (strict_low_part (match_dup 3))
13561 (eq:QI (reg:CCZ FLAGS_REG) (const_int 0)))
13562 (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
13563 (clobber (reg:CC FLAGS_REG))])
13564 (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
13565 (clobber (reg:CC FLAGS_REG))])
13566 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
13567 (clobber (reg:CC FLAGS_REG))])]
13569 operands[3] = gen_lowpart (QImode, operands[2]);
13570 ix86_expand_clear (operands[2]);
13573 (define_insn "*ffssi_1"
13574 [(set (reg:CCZ FLAGS_REG)
13575 (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "rm")
13577 (set (match_operand:SI 0 "register_operand" "=r")
13578 (ctz:SI (match_dup 1)))]
13580 "bsf{l}\t{%1, %0|%0, %1}"
13581 [(set_attr "prefix_0f" "1")])
13583 (define_expand "ffsdi2"
13585 [(set (match_operand:DI 0 "register_operand" "")
13586 (ffs:DI (match_operand:DI 1 "nonimmediate_operand" "")))
13587 (clobber (match_scratch:DI 2 ""))
13588 (clobber (reg:CC FLAGS_REG))])]
13589 "TARGET_64BIT && TARGET_CMOVE"
13592 (define_insn_and_split "*ffs_rex64"
13593 [(set (match_operand:DI 0 "register_operand" "=r")
13594 (ffs:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
13595 (clobber (match_scratch:DI 2 "=&r"))
13596 (clobber (reg:CC FLAGS_REG))]
13597 "TARGET_64BIT && TARGET_CMOVE"
13599 "&& reload_completed"
13600 [(set (match_dup 2) (const_int -1))
13601 (parallel [(set (reg:CCZ FLAGS_REG)
13602 (compare:CCZ (match_dup 1) (const_int 0)))
13603 (set (match_dup 0) (ctz:DI (match_dup 1)))])
13604 (set (match_dup 0) (if_then_else:DI
13605 (eq (reg:CCZ FLAGS_REG) (const_int 0))
13608 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (const_int 1)))
13609 (clobber (reg:CC FLAGS_REG))])]
13612 (define_insn "*ffsdi_1"
13613 [(set (reg:CCZ FLAGS_REG)
13614 (compare:CCZ (match_operand:DI 1 "nonimmediate_operand" "rm")
13616 (set (match_operand:DI 0 "register_operand" "=r")
13617 (ctz:DI (match_dup 1)))]
13619 "bsf{q}\t{%1, %0|%0, %1}"
13620 [(set_attr "prefix_0f" "1")])
13622 (define_insn "ctzsi2"
13623 [(set (match_operand:SI 0 "register_operand" "=r")
13624 (ctz:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
13625 (clobber (reg:CC FLAGS_REG))]
13627 "bsf{l}\t{%1, %0|%0, %1}"
13628 [(set_attr "prefix_0f" "1")])
13630 (define_insn "ctzdi2"
13631 [(set (match_operand:DI 0 "register_operand" "=r")
13632 (ctz:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
13633 (clobber (reg:CC FLAGS_REG))]
13635 "bsf{q}\t{%1, %0|%0, %1}"
13636 [(set_attr "prefix_0f" "1")])
13638 (define_expand "clzsi2"
13640 [(set (match_operand:SI 0 "register_operand" "")
13641 (minus:SI (const_int 31)
13642 (clz:SI (match_operand:SI 1 "nonimmediate_operand" ""))))
13643 (clobber (reg:CC FLAGS_REG))])
13645 [(set (match_dup 0) (xor:SI (match_dup 0) (const_int 31)))
13646 (clobber (reg:CC FLAGS_REG))])]
13650 (define_insn "*bsr"
13651 [(set (match_operand:SI 0 "register_operand" "=r")
13652 (minus:SI (const_int 31)
13653 (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
13654 (clobber (reg:CC FLAGS_REG))]
13656 "bsr{l}\t{%1, %0|%0, %1}"
13657 [(set_attr "prefix_0f" "1")])
13659 (define_expand "clzdi2"
13661 [(set (match_operand:DI 0 "register_operand" "")
13662 (minus:DI (const_int 63)
13663 (clz:DI (match_operand:DI 1 "nonimmediate_operand" ""))))
13664 (clobber (reg:CC FLAGS_REG))])
13666 [(set (match_dup 0) (xor:DI (match_dup 0) (const_int 63)))
13667 (clobber (reg:CC FLAGS_REG))])]
13671 (define_insn "*bsr_rex64"
13672 [(set (match_operand:DI 0 "register_operand" "=r")
13673 (minus:DI (const_int 63)
13674 (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))))
13675 (clobber (reg:CC FLAGS_REG))]
13677 "bsr{q}\t{%1, %0|%0, %1}"
13678 [(set_attr "prefix_0f" "1")])
13680 ;; Thread-local storage patterns for ELF.
13682 ;; Note that these code sequences must appear exactly as shown
13683 ;; in order to allow linker relaxation.
13685 (define_insn "*tls_global_dynamic_32_gnu"
13686 [(set (match_operand:SI 0 "register_operand" "=a")
13687 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
13688 (match_operand:SI 2 "tls_symbolic_operand" "")
13689 (match_operand:SI 3 "call_insn_operand" "")]
13691 (clobber (match_scratch:SI 4 "=d"))
13692 (clobber (match_scratch:SI 5 "=c"))
13693 (clobber (reg:CC FLAGS_REG))]
13694 "!TARGET_64BIT && TARGET_GNU_TLS"
13695 "lea{l}\t{%a2@TLSGD(,%1,1), %0|%0, %a2@TLSGD[%1*1]}\;call\t%P3"
13696 [(set_attr "type" "multi")
13697 (set_attr "length" "12")])
13699 (define_insn "*tls_global_dynamic_32_sun"
13700 [(set (match_operand:SI 0 "register_operand" "=a")
13701 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
13702 (match_operand:SI 2 "tls_symbolic_operand" "")
13703 (match_operand:SI 3 "call_insn_operand" "")]
13705 (clobber (match_scratch:SI 4 "=d"))
13706 (clobber (match_scratch:SI 5 "=c"))
13707 (clobber (reg:CC FLAGS_REG))]
13708 "!TARGET_64BIT && TARGET_SUN_TLS"
13709 "lea{l}\t{%a2@DTLNDX(%1), %4|%4, %a2@DTLNDX[%1]}
13710 push{l}\t%4\;call\t%a2@TLSPLT\;pop{l}\t%4\;nop"
13711 [(set_attr "type" "multi")
13712 (set_attr "length" "14")])
13714 (define_expand "tls_global_dynamic_32"
13715 [(parallel [(set (match_operand:SI 0 "register_operand" "")
13718 (match_operand:SI 1 "tls_symbolic_operand" "")
13721 (clobber (match_scratch:SI 4 ""))
13722 (clobber (match_scratch:SI 5 ""))
13723 (clobber (reg:CC FLAGS_REG))])]
13727 operands[2] = pic_offset_table_rtx;
13730 operands[2] = gen_reg_rtx (Pmode);
13731 emit_insn (gen_set_got (operands[2]));
13733 operands[3] = ix86_tls_get_addr ();
13736 (define_insn "*tls_global_dynamic_64"
13737 [(set (match_operand:DI 0 "register_operand" "=a")
13738 (call (mem:QI (match_operand:DI 2 "call_insn_operand" ""))
13739 (match_operand:DI 3 "" "")))
13740 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
13743 ".byte\t0x66\;lea{q}\t{%a1@TLSGD(%%rip), %%rdi|%%rdi, %a1@TLSGD[%%rip]}\;.word\t0x6666\;rex64\;call\t%P2"
13744 [(set_attr "type" "multi")
13745 (set_attr "length" "16")])
13747 (define_expand "tls_global_dynamic_64"
13748 [(parallel [(set (match_operand:DI 0 "register_operand" "")
13749 (call (mem:QI (match_dup 2)) (const_int 0)))
13750 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
13754 operands[2] = ix86_tls_get_addr ();
13757 (define_insn "*tls_local_dynamic_base_32_gnu"
13758 [(set (match_operand:SI 0 "register_operand" "=a")
13759 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
13760 (match_operand:SI 2 "call_insn_operand" "")]
13761 UNSPEC_TLS_LD_BASE))
13762 (clobber (match_scratch:SI 3 "=d"))
13763 (clobber (match_scratch:SI 4 "=c"))
13764 (clobber (reg:CC FLAGS_REG))]
13765 "!TARGET_64BIT && TARGET_GNU_TLS"
13766 "lea{l}\t{%&@TLSLDM(%1), %0|%0, %&@TLSLDM[%1]}\;call\t%P2"
13767 [(set_attr "type" "multi")
13768 (set_attr "length" "11")])
13770 (define_insn "*tls_local_dynamic_base_32_sun"
13771 [(set (match_operand:SI 0 "register_operand" "=a")
13772 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
13773 (match_operand:SI 2 "call_insn_operand" "")]
13774 UNSPEC_TLS_LD_BASE))
13775 (clobber (match_scratch:SI 3 "=d"))
13776 (clobber (match_scratch:SI 4 "=c"))
13777 (clobber (reg:CC FLAGS_REG))]
13778 "!TARGET_64BIT && TARGET_SUN_TLS"
13779 "lea{l}\t{%&@TMDNX(%1), %3|%3, %&@TMDNX[%1]}
13780 push{l}\t%3\;call\t%&@TLSPLT\;pop{l}\t%3"
13781 [(set_attr "type" "multi")
13782 (set_attr "length" "13")])
13784 (define_expand "tls_local_dynamic_base_32"
13785 [(parallel [(set (match_operand:SI 0 "register_operand" "")
13786 (unspec:SI [(match_dup 1) (match_dup 2)]
13787 UNSPEC_TLS_LD_BASE))
13788 (clobber (match_scratch:SI 3 ""))
13789 (clobber (match_scratch:SI 4 ""))
13790 (clobber (reg:CC FLAGS_REG))])]
13794 operands[1] = pic_offset_table_rtx;
13797 operands[1] = gen_reg_rtx (Pmode);
13798 emit_insn (gen_set_got (operands[1]));
13800 operands[2] = ix86_tls_get_addr ();
13803 (define_insn "*tls_local_dynamic_base_64"
13804 [(set (match_operand:DI 0 "register_operand" "=a")
13805 (call (mem:QI (match_operand:DI 1 "call_insn_operand" ""))
13806 (match_operand:DI 2 "" "")))
13807 (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
13809 "lea{q}\t{%&@TLSLD(%%rip), %%rdi|%%rdi, %&@TLSLD[%%rip]}\;call\t%P1"
13810 [(set_attr "type" "multi")
13811 (set_attr "length" "12")])
13813 (define_expand "tls_local_dynamic_base_64"
13814 [(parallel [(set (match_operand:DI 0 "register_operand" "")
13815 (call (mem:QI (match_dup 1)) (const_int 0)))
13816 (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])]
13819 operands[1] = ix86_tls_get_addr ();
13822 ;; Local dynamic of a single variable is a lose. Show combine how
13823 ;; to convert that back to global dynamic.
13825 (define_insn_and_split "*tls_local_dynamic_32_once"
13826 [(set (match_operand:SI 0 "register_operand" "=a")
13827 (plus:SI (unspec:SI [(match_operand:SI 1 "register_operand" "b")
13828 (match_operand:SI 2 "call_insn_operand" "")]
13829 UNSPEC_TLS_LD_BASE)
13830 (const:SI (unspec:SI
13831 [(match_operand:SI 3 "tls_symbolic_operand" "")]
13833 (clobber (match_scratch:SI 4 "=d"))
13834 (clobber (match_scratch:SI 5 "=c"))
13835 (clobber (reg:CC FLAGS_REG))]
13839 [(parallel [(set (match_dup 0)
13840 (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
13842 (clobber (match_dup 4))
13843 (clobber (match_dup 5))
13844 (clobber (reg:CC FLAGS_REG))])]
13847 ;; Load and add the thread base pointer from %gs:0.
13849 (define_insn "*load_tp_si"
13850 [(set (match_operand:SI 0 "register_operand" "=r")
13851 (unspec:SI [(const_int 0)] UNSPEC_TP))]
13853 "mov{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}"
13854 [(set_attr "type" "imov")
13855 (set_attr "modrm" "0")
13856 (set_attr "length" "7")
13857 (set_attr "memory" "load")
13858 (set_attr "imm_disp" "false")])
13860 (define_insn "*add_tp_si"
13861 [(set (match_operand:SI 0 "register_operand" "=r")
13862 (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
13863 (match_operand:SI 1 "register_operand" "0")))
13864 (clobber (reg:CC FLAGS_REG))]
13866 "add{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}"
13867 [(set_attr "type" "alu")
13868 (set_attr "modrm" "0")
13869 (set_attr "length" "7")
13870 (set_attr "memory" "load")
13871 (set_attr "imm_disp" "false")])
13873 (define_insn "*load_tp_di"
13874 [(set (match_operand:DI 0 "register_operand" "=r")
13875 (unspec:DI [(const_int 0)] UNSPEC_TP))]
13877 "mov{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}"
13878 [(set_attr "type" "imov")
13879 (set_attr "modrm" "0")
13880 (set_attr "length" "7")
13881 (set_attr "memory" "load")
13882 (set_attr "imm_disp" "false")])
13884 (define_insn "*add_tp_di"
13885 [(set (match_operand:DI 0 "register_operand" "=r")
13886 (plus:DI (unspec:DI [(const_int 0)] UNSPEC_TP)
13887 (match_operand:DI 1 "register_operand" "0")))
13888 (clobber (reg:CC FLAGS_REG))]
13890 "add{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}"
13891 [(set_attr "type" "alu")
13892 (set_attr "modrm" "0")
13893 (set_attr "length" "7")
13894 (set_attr "memory" "load")
13895 (set_attr "imm_disp" "false")])
13897 ;; These patterns match the binary 387 instructions for addM3, subM3,
13898 ;; mulM3 and divM3. There are three patterns for each of DFmode and
13899 ;; SFmode. The first is the normal insn, the second the same insn but
13900 ;; with one operand a conversion, and the third the same insn but with
13901 ;; the other operand a conversion. The conversion may be SFmode or
13902 ;; SImode if the target mode DFmode, but only SImode if the target mode
13905 ;; Gcc is slightly more smart about handling normal two address instructions
13906 ;; so use special patterns for add and mull.
13908 (define_insn "*fop_sf_comm_mixed"
13909 [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
13910 (match_operator:SF 3 "binary_fp_operator"
13911 [(match_operand:SF 1 "nonimmediate_operand" "%0,0")
13912 (match_operand:SF 2 "nonimmediate_operand" "fm#x,xm#f")]))]
13913 "TARGET_MIX_SSE_I387
13914 && COMMUTATIVE_ARITH_P (operands[3])
13915 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
13916 "* return output_387_binary_op (insn, operands);"
13917 [(set (attr "type")
13918 (if_then_else (eq_attr "alternative" "1")
13919 (if_then_else (match_operand:SF 3 "mult_operator" "")
13920 (const_string "ssemul")
13921 (const_string "sseadd"))
13922 (if_then_else (match_operand:SF 3 "mult_operator" "")
13923 (const_string "fmul")
13924 (const_string "fop"))))
13925 (set_attr "mode" "SF")])
13927 (define_insn "*fop_sf_comm_sse"
13928 [(set (match_operand:SF 0 "register_operand" "=x")
13929 (match_operator:SF 3 "binary_fp_operator"
13930 [(match_operand:SF 1 "nonimmediate_operand" "%0")
13931 (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
13933 && COMMUTATIVE_ARITH_P (operands[3])
13934 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
13935 "* return output_387_binary_op (insn, operands);"
13936 [(set (attr "type")
13937 (if_then_else (match_operand:SF 3 "mult_operator" "")
13938 (const_string "ssemul")
13939 (const_string "sseadd")))
13940 (set_attr "mode" "SF")])
13942 (define_insn "*fop_sf_comm_i387"
13943 [(set (match_operand:SF 0 "register_operand" "=f")
13944 (match_operator:SF 3 "binary_fp_operator"
13945 [(match_operand:SF 1 "nonimmediate_operand" "%0")
13946 (match_operand:SF 2 "nonimmediate_operand" "fm")]))]
13948 && COMMUTATIVE_ARITH_P (operands[3])
13949 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
13950 "* return output_387_binary_op (insn, operands);"
13951 [(set (attr "type")
13952 (if_then_else (match_operand:SF 3 "mult_operator" "")
13953 (const_string "fmul")
13954 (const_string "fop")))
13955 (set_attr "mode" "SF")])
13957 (define_insn "*fop_sf_1_mixed"
13958 [(set (match_operand:SF 0 "register_operand" "=f,f,x")
13959 (match_operator:SF 3 "binary_fp_operator"
13960 [(match_operand:SF 1 "nonimmediate_operand" "0,fm,0")
13961 (match_operand:SF 2 "nonimmediate_operand" "fm,0,xm#f")]))]
13962 "TARGET_MIX_SSE_I387
13963 && !COMMUTATIVE_ARITH_P (operands[3])
13964 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
13965 "* return output_387_binary_op (insn, operands);"
13966 [(set (attr "type")
13967 (cond [(and (eq_attr "alternative" "2")
13968 (match_operand:SF 3 "mult_operator" ""))
13969 (const_string "ssemul")
13970 (and (eq_attr "alternative" "2")
13971 (match_operand:SF 3 "div_operator" ""))
13972 (const_string "ssediv")
13973 (eq_attr "alternative" "2")
13974 (const_string "sseadd")
13975 (match_operand:SF 3 "mult_operator" "")
13976 (const_string "fmul")
13977 (match_operand:SF 3 "div_operator" "")
13978 (const_string "fdiv")
13980 (const_string "fop")))
13981 (set_attr "mode" "SF")])
13983 (define_insn "*fop_sf_1_sse"
13984 [(set (match_operand:SF 0 "register_operand" "=x")
13985 (match_operator:SF 3 "binary_fp_operator"
13986 [(match_operand:SF 1 "register_operand" "0")
13987 (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
13989 && !COMMUTATIVE_ARITH_P (operands[3])"
13990 "* return output_387_binary_op (insn, operands);"
13991 [(set (attr "type")
13992 (cond [(match_operand:SF 3 "mult_operator" "")
13993 (const_string "ssemul")
13994 (match_operand:SF 3 "div_operator" "")
13995 (const_string "ssediv")
13997 (const_string "sseadd")))
13998 (set_attr "mode" "SF")])
14000 ;; This pattern is not fully shadowed by the pattern above.
14001 (define_insn "*fop_sf_1_i387"
14002 [(set (match_operand:SF 0 "register_operand" "=f,f")
14003 (match_operator:SF 3 "binary_fp_operator"
14004 [(match_operand:SF 1 "nonimmediate_operand" "0,fm")
14005 (match_operand:SF 2 "nonimmediate_operand" "fm,0")]))]
14006 "TARGET_80387 && !TARGET_SSE_MATH
14007 && !COMMUTATIVE_ARITH_P (operands[3])
14008 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14009 "* return output_387_binary_op (insn, operands);"
14010 [(set (attr "type")
14011 (cond [(match_operand:SF 3 "mult_operator" "")
14012 (const_string "fmul")
14013 (match_operand:SF 3 "div_operator" "")
14014 (const_string "fdiv")
14016 (const_string "fop")))
14017 (set_attr "mode" "SF")])
14019 ;; ??? Add SSE splitters for these!
14020 (define_insn "*fop_sf_2<mode>_i387"
14021 [(set (match_operand:SF 0 "register_operand" "=f,f")
14022 (match_operator:SF 3 "binary_fp_operator"
14023 [(float:SF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14024 (match_operand:SF 2 "register_operand" "0,0")]))]
14025 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH"
14026 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14027 [(set (attr "type")
14028 (cond [(match_operand:SF 3 "mult_operator" "")
14029 (const_string "fmul")
14030 (match_operand:SF 3 "div_operator" "")
14031 (const_string "fdiv")
14033 (const_string "fop")))
14034 (set_attr "fp_int_src" "true")
14035 (set_attr "mode" "<MODE>")])
14037 (define_insn "*fop_sf_3<mode>_i387"
14038 [(set (match_operand:SF 0 "register_operand" "=f,f")
14039 (match_operator:SF 3 "binary_fp_operator"
14040 [(match_operand:SF 1 "register_operand" "0,0")
14041 (float:SF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14042 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH"
14043 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14044 [(set (attr "type")
14045 (cond [(match_operand:SF 3 "mult_operator" "")
14046 (const_string "fmul")
14047 (match_operand:SF 3 "div_operator" "")
14048 (const_string "fdiv")
14050 (const_string "fop")))
14051 (set_attr "fp_int_src" "true")
14052 (set_attr "mode" "<MODE>")])
14054 (define_insn "*fop_df_comm_mixed"
14055 [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
14056 (match_operator:DF 3 "binary_fp_operator"
14057 [(match_operand:DF 1 "nonimmediate_operand" "%0,0")
14058 (match_operand:DF 2 "nonimmediate_operand" "fm#Y,Ym#f")]))]
14059 "TARGET_SSE2 && TARGET_MIX_SSE_I387
14060 && COMMUTATIVE_ARITH_P (operands[3])
14061 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14062 "* return output_387_binary_op (insn, operands);"
14063 [(set (attr "type")
14064 (if_then_else (eq_attr "alternative" "1")
14065 (if_then_else (match_operand:SF 3 "mult_operator" "")
14066 (const_string "ssemul")
14067 (const_string "sseadd"))
14068 (if_then_else (match_operand:SF 3 "mult_operator" "")
14069 (const_string "fmul")
14070 (const_string "fop"))))
14071 (set_attr "mode" "DF")])
14073 (define_insn "*fop_df_comm_sse"
14074 [(set (match_operand:DF 0 "register_operand" "=Y")
14075 (match_operator:DF 3 "binary_fp_operator"
14076 [(match_operand:DF 1 "nonimmediate_operand" "%0")
14077 (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
14078 "TARGET_SSE2 && TARGET_SSE_MATH
14079 && COMMUTATIVE_ARITH_P (operands[3])
14080 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14081 "* return output_387_binary_op (insn, operands);"
14082 [(set (attr "type")
14083 (if_then_else (match_operand:SF 3 "mult_operator" "")
14084 (const_string "ssemul")
14085 (const_string "sseadd")))
14086 (set_attr "mode" "DF")])
14088 (define_insn "*fop_df_comm_i387"
14089 [(set (match_operand:DF 0 "register_operand" "=f")
14090 (match_operator:DF 3 "binary_fp_operator"
14091 [(match_operand:DF 1 "nonimmediate_operand" "%0")
14092 (match_operand:DF 2 "nonimmediate_operand" "fm")]))]
14094 && COMMUTATIVE_ARITH_P (operands[3])
14095 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14096 "* return output_387_binary_op (insn, operands);"
14097 [(set (attr "type")
14098 (if_then_else (match_operand:SF 3 "mult_operator" "")
14099 (const_string "fmul")
14100 (const_string "fop")))
14101 (set_attr "mode" "DF")])
14103 (define_insn "*fop_df_1_mixed"
14104 [(set (match_operand:DF 0 "register_operand" "=f#Y,f#Y,Y#f")
14105 (match_operator:DF 3 "binary_fp_operator"
14106 [(match_operand:DF 1 "nonimmediate_operand" "0,fm,0")
14107 (match_operand:DF 2 "nonimmediate_operand" "fm,0,Ym#f")]))]
14108 "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
14109 && !COMMUTATIVE_ARITH_P (operands[3])
14110 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14111 "* return output_387_binary_op (insn, operands);"
14112 [(set (attr "type")
14113 (cond [(and (eq_attr "alternative" "2")
14114 (match_operand:SF 3 "mult_operator" ""))
14115 (const_string "ssemul")
14116 (and (eq_attr "alternative" "2")
14117 (match_operand:SF 3 "div_operator" ""))
14118 (const_string "ssediv")
14119 (eq_attr "alternative" "2")
14120 (const_string "sseadd")
14121 (match_operand:DF 3 "mult_operator" "")
14122 (const_string "fmul")
14123 (match_operand:DF 3 "div_operator" "")
14124 (const_string "fdiv")
14126 (const_string "fop")))
14127 (set_attr "mode" "DF")])
14129 (define_insn "*fop_df_1_sse"
14130 [(set (match_operand:DF 0 "register_operand" "=Y")
14131 (match_operator:DF 3 "binary_fp_operator"
14132 [(match_operand:DF 1 "register_operand" "0")
14133 (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
14134 "TARGET_SSE2 && TARGET_SSE_MATH
14135 && !COMMUTATIVE_ARITH_P (operands[3])"
14136 "* return output_387_binary_op (insn, operands);"
14137 [(set_attr "mode" "DF")
14139 (cond [(match_operand:SF 3 "mult_operator" "")
14140 (const_string "ssemul")
14141 (match_operand:SF 3 "div_operator" "")
14142 (const_string "ssediv")
14144 (const_string "sseadd")))])
14146 ;; This pattern is not fully shadowed by the pattern above.
14147 (define_insn "*fop_df_1_i387"
14148 [(set (match_operand:DF 0 "register_operand" "=f,f")
14149 (match_operator:DF 3 "binary_fp_operator"
14150 [(match_operand:DF 1 "nonimmediate_operand" "0,fm")
14151 (match_operand:DF 2 "nonimmediate_operand" "fm,0")]))]
14152 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
14153 && !COMMUTATIVE_ARITH_P (operands[3])
14154 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14155 "* return output_387_binary_op (insn, operands);"
14156 [(set (attr "type")
14157 (cond [(match_operand:DF 3 "mult_operator" "")
14158 (const_string "fmul")
14159 (match_operand:DF 3 "div_operator" "")
14160 (const_string "fdiv")
14162 (const_string "fop")))
14163 (set_attr "mode" "DF")])
14165 ;; ??? Add SSE splitters for these!
14166 (define_insn "*fop_df_2<mode>_i387"
14167 [(set (match_operand:DF 0 "register_operand" "=f,f")
14168 (match_operator:DF 3 "binary_fp_operator"
14169 [(float:DF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14170 (match_operand:DF 2 "register_operand" "0,0")]))]
14171 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
14172 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14173 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14174 [(set (attr "type")
14175 (cond [(match_operand:DF 3 "mult_operator" "")
14176 (const_string "fmul")
14177 (match_operand:DF 3 "div_operator" "")
14178 (const_string "fdiv")
14180 (const_string "fop")))
14181 (set_attr "fp_int_src" "true")
14182 (set_attr "mode" "<MODE>")])
14184 (define_insn "*fop_df_3<mode>_i387"
14185 [(set (match_operand:DF 0 "register_operand" "=f,f")
14186 (match_operator:DF 3 "binary_fp_operator"
14187 [(match_operand:DF 1 "register_operand" "0,0")
14188 (float:DF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14189 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
14190 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14191 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14192 [(set (attr "type")
14193 (cond [(match_operand:DF 3 "mult_operator" "")
14194 (const_string "fmul")
14195 (match_operand:DF 3 "div_operator" "")
14196 (const_string "fdiv")
14198 (const_string "fop")))
14199 (set_attr "fp_int_src" "true")
14200 (set_attr "mode" "<MODE>")])
14202 (define_insn "*fop_df_4_i387"
14203 [(set (match_operand:DF 0 "register_operand" "=f,f")
14204 (match_operator:DF 3 "binary_fp_operator"
14205 [(float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
14206 (match_operand:DF 2 "register_operand" "0,f")]))]
14207 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
14208 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14209 "* return output_387_binary_op (insn, operands);"
14210 [(set (attr "type")
14211 (cond [(match_operand:DF 3 "mult_operator" "")
14212 (const_string "fmul")
14213 (match_operand:DF 3 "div_operator" "")
14214 (const_string "fdiv")
14216 (const_string "fop")))
14217 (set_attr "mode" "SF")])
14219 (define_insn "*fop_df_5_i387"
14220 [(set (match_operand:DF 0 "register_operand" "=f,f")
14221 (match_operator:DF 3 "binary_fp_operator"
14222 [(match_operand:DF 1 "register_operand" "0,f")
14224 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
14225 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14226 "* return output_387_binary_op (insn, operands);"
14227 [(set (attr "type")
14228 (cond [(match_operand:DF 3 "mult_operator" "")
14229 (const_string "fmul")
14230 (match_operand:DF 3 "div_operator" "")
14231 (const_string "fdiv")
14233 (const_string "fop")))
14234 (set_attr "mode" "SF")])
14236 (define_insn "*fop_df_6_i387"
14237 [(set (match_operand:DF 0 "register_operand" "=f,f")
14238 (match_operator:DF 3 "binary_fp_operator"
14240 (match_operand:SF 1 "register_operand" "0,f"))
14242 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
14243 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14244 "* return output_387_binary_op (insn, operands);"
14245 [(set (attr "type")
14246 (cond [(match_operand:DF 3 "mult_operator" "")
14247 (const_string "fmul")
14248 (match_operand:DF 3 "div_operator" "")
14249 (const_string "fdiv")
14251 (const_string "fop")))
14252 (set_attr "mode" "SF")])
14254 (define_insn "*fop_xf_comm_i387"
14255 [(set (match_operand:XF 0 "register_operand" "=f")
14256 (match_operator:XF 3 "binary_fp_operator"
14257 [(match_operand:XF 1 "register_operand" "%0")
14258 (match_operand:XF 2 "register_operand" "f")]))]
14260 && COMMUTATIVE_ARITH_P (operands[3])"
14261 "* return output_387_binary_op (insn, operands);"
14262 [(set (attr "type")
14263 (if_then_else (match_operand:XF 3 "mult_operator" "")
14264 (const_string "fmul")
14265 (const_string "fop")))
14266 (set_attr "mode" "XF")])
14268 (define_insn "*fop_xf_1_i387"
14269 [(set (match_operand:XF 0 "register_operand" "=f,f")
14270 (match_operator:XF 3 "binary_fp_operator"
14271 [(match_operand:XF 1 "register_operand" "0,f")
14272 (match_operand:XF 2 "register_operand" "f,0")]))]
14274 && !COMMUTATIVE_ARITH_P (operands[3])"
14275 "* return output_387_binary_op (insn, operands);"
14276 [(set (attr "type")
14277 (cond [(match_operand:XF 3 "mult_operator" "")
14278 (const_string "fmul")
14279 (match_operand:XF 3 "div_operator" "")
14280 (const_string "fdiv")
14282 (const_string "fop")))
14283 (set_attr "mode" "XF")])
14285 (define_insn "*fop_xf_2<mode>_i387"
14286 [(set (match_operand:XF 0 "register_operand" "=f,f")
14287 (match_operator:XF 3 "binary_fp_operator"
14288 [(float:XF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14289 (match_operand:XF 2 "register_operand" "0,0")]))]
14290 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP"
14291 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14292 [(set (attr "type")
14293 (cond [(match_operand:XF 3 "mult_operator" "")
14294 (const_string "fmul")
14295 (match_operand:XF 3 "div_operator" "")
14296 (const_string "fdiv")
14298 (const_string "fop")))
14299 (set_attr "fp_int_src" "true")
14300 (set_attr "mode" "<MODE>")])
14302 (define_insn "*fop_xf_3<mode>_i387"
14303 [(set (match_operand:XF 0 "register_operand" "=f,f")
14304 (match_operator:XF 3 "binary_fp_operator"
14305 [(match_operand:XF 1 "register_operand" "0,0")
14306 (float:XF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14307 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP"
14308 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14309 [(set (attr "type")
14310 (cond [(match_operand:XF 3 "mult_operator" "")
14311 (const_string "fmul")
14312 (match_operand:XF 3 "div_operator" "")
14313 (const_string "fdiv")
14315 (const_string "fop")))
14316 (set_attr "fp_int_src" "true")
14317 (set_attr "mode" "<MODE>")])
14319 (define_insn "*fop_xf_4_i387"
14320 [(set (match_operand:XF 0 "register_operand" "=f,f")
14321 (match_operator:XF 3 "binary_fp_operator"
14322 [(float_extend:XF (match_operand 1 "nonimmediate_operand" "fm,0"))
14323 (match_operand:XF 2 "register_operand" "0,f")]))]
14325 "* return output_387_binary_op (insn, operands);"
14326 [(set (attr "type")
14327 (cond [(match_operand:XF 3 "mult_operator" "")
14328 (const_string "fmul")
14329 (match_operand:XF 3 "div_operator" "")
14330 (const_string "fdiv")
14332 (const_string "fop")))
14333 (set_attr "mode" "SF")])
14335 (define_insn "*fop_xf_5_i387"
14336 [(set (match_operand:XF 0 "register_operand" "=f,f")
14337 (match_operator:XF 3 "binary_fp_operator"
14338 [(match_operand:XF 1 "register_operand" "0,f")
14340 (match_operand 2 "nonimmediate_operand" "fm,0"))]))]
14342 "* return output_387_binary_op (insn, operands);"
14343 [(set (attr "type")
14344 (cond [(match_operand:XF 3 "mult_operator" "")
14345 (const_string "fmul")
14346 (match_operand:XF 3 "div_operator" "")
14347 (const_string "fdiv")
14349 (const_string "fop")))
14350 (set_attr "mode" "SF")])
14352 (define_insn "*fop_xf_6_i387"
14353 [(set (match_operand:XF 0 "register_operand" "=f,f")
14354 (match_operator:XF 3 "binary_fp_operator"
14356 (match_operand 1 "register_operand" "0,f"))
14358 (match_operand 2 "nonimmediate_operand" "fm,0"))]))]
14360 "* return output_387_binary_op (insn, operands);"
14361 [(set (attr "type")
14362 (cond [(match_operand:XF 3 "mult_operator" "")
14363 (const_string "fmul")
14364 (match_operand:XF 3 "div_operator" "")
14365 (const_string "fdiv")
14367 (const_string "fop")))
14368 (set_attr "mode" "SF")])
14371 [(set (match_operand 0 "register_operand" "")
14372 (match_operator 3 "binary_fp_operator"
14373 [(float (match_operand:X87MODEI12 1 "register_operand" ""))
14374 (match_operand 2 "register_operand" "")]))]
14375 "TARGET_80387 && reload_completed
14376 && FLOAT_MODE_P (GET_MODE (operands[0]))"
14379 operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
14380 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
14381 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
14382 gen_rtx_fmt_ee (GET_CODE (operands[3]),
14383 GET_MODE (operands[3]),
14386 ix86_free_from_memory (GET_MODE (operands[1]));
14391 [(set (match_operand 0 "register_operand" "")
14392 (match_operator 3 "binary_fp_operator"
14393 [(match_operand 1 "register_operand" "")
14394 (float (match_operand:X87MODEI12 2 "register_operand" ""))]))]
14395 "TARGET_80387 && reload_completed
14396 && FLOAT_MODE_P (GET_MODE (operands[0]))"
14399 operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
14400 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
14401 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
14402 gen_rtx_fmt_ee (GET_CODE (operands[3]),
14403 GET_MODE (operands[3]),
14406 ix86_free_from_memory (GET_MODE (operands[2]));
14410 ;; FPU special functions.
14412 (define_expand "sqrtsf2"
14413 [(set (match_operand:SF 0 "register_operand" "")
14414 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
14415 "TARGET_USE_FANCY_MATH_387 || TARGET_SSE_MATH"
14417 if (!TARGET_SSE_MATH)
14418 operands[1] = force_reg (SFmode, operands[1]);
14421 (define_insn "*sqrtsf2_mixed"
14422 [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
14423 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "0#x,xm#f")))]
14424 "TARGET_USE_FANCY_MATH_387 && TARGET_MIX_SSE_I387"
14427 sqrtss\t{%1, %0|%0, %1}"
14428 [(set_attr "type" "fpspc,sse")
14429 (set_attr "mode" "SF,SF")
14430 (set_attr "athlon_decode" "direct,*")])
14432 (define_insn "*sqrtsf2_sse"
14433 [(set (match_operand:SF 0 "register_operand" "=x")
14434 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
14436 "sqrtss\t{%1, %0|%0, %1}"
14437 [(set_attr "type" "sse")
14438 (set_attr "mode" "SF")
14439 (set_attr "athlon_decode" "*")])
14441 (define_insn "*sqrtsf2_i387"
14442 [(set (match_operand:SF 0 "register_operand" "=f")
14443 (sqrt:SF (match_operand:SF 1 "register_operand" "0")))]
14444 "TARGET_USE_FANCY_MATH_387"
14446 [(set_attr "type" "fpspc")
14447 (set_attr "mode" "SF")
14448 (set_attr "athlon_decode" "direct")])
14450 (define_expand "sqrtdf2"
14451 [(set (match_operand:DF 0 "register_operand" "")
14452 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
14453 "TARGET_USE_FANCY_MATH_387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
14455 if (!(TARGET_SSE2 && TARGET_SSE_MATH))
14456 operands[1] = force_reg (DFmode, operands[1]);
14459 (define_insn "*sqrtdf2_mixed"
14460 [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
14461 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "0#Y,Ym#f")))]
14462 "TARGET_USE_FANCY_MATH_387 && TARGET_SSE2 && TARGET_MIX_SSE_I387"
14465 sqrtsd\t{%1, %0|%0, %1}"
14466 [(set_attr "type" "fpspc,sse")
14467 (set_attr "mode" "DF,DF")
14468 (set_attr "athlon_decode" "direct,*")])
14470 (define_insn "*sqrtdf2_sse"
14471 [(set (match_operand:DF 0 "register_operand" "=Y")
14472 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
14473 "TARGET_SSE2 && TARGET_SSE_MATH"
14474 "sqrtsd\t{%1, %0|%0, %1}"
14475 [(set_attr "type" "sse")
14476 (set_attr "mode" "DF")
14477 (set_attr "athlon_decode" "*")])
14479 (define_insn "*sqrtdf2_i387"
14480 [(set (match_operand:DF 0 "register_operand" "=f")
14481 (sqrt:DF (match_operand:DF 1 "register_operand" "0")))]
14482 "TARGET_USE_FANCY_MATH_387"
14484 [(set_attr "type" "fpspc")
14485 (set_attr "mode" "DF")
14486 (set_attr "athlon_decode" "direct")])
14488 (define_insn "*sqrtextendsfdf2_i387"
14489 [(set (match_operand:DF 0 "register_operand" "=f")
14490 (sqrt:DF (float_extend:DF
14491 (match_operand:SF 1 "register_operand" "0"))))]
14492 "TARGET_USE_FANCY_MATH_387
14493 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)"
14495 [(set_attr "type" "fpspc")
14496 (set_attr "mode" "DF")
14497 (set_attr "athlon_decode" "direct")])
14499 (define_insn "sqrtxf2"
14500 [(set (match_operand:XF 0 "register_operand" "=f")
14501 (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
14502 "TARGET_USE_FANCY_MATH_387
14503 && (TARGET_IEEE_FP || flag_unsafe_math_optimizations) "
14505 [(set_attr "type" "fpspc")
14506 (set_attr "mode" "XF")
14507 (set_attr "athlon_decode" "direct")])
14509 (define_insn "*sqrtextendsfxf2_i387"
14510 [(set (match_operand:XF 0 "register_operand" "=f")
14511 (sqrt:XF (float_extend:XF
14512 (match_operand:SF 1 "register_operand" "0"))))]
14513 "TARGET_USE_FANCY_MATH_387"
14515 [(set_attr "type" "fpspc")
14516 (set_attr "mode" "XF")
14517 (set_attr "athlon_decode" "direct")])
14519 (define_insn "*sqrtextenddfxf2_i387"
14520 [(set (match_operand:XF 0 "register_operand" "=f")
14521 (sqrt:XF (float_extend:XF
14522 (match_operand:DF 1 "register_operand" "0"))))]
14523 "TARGET_USE_FANCY_MATH_387"
14525 [(set_attr "type" "fpspc")
14526 (set_attr "mode" "XF")
14527 (set_attr "athlon_decode" "direct")])
14529 (define_insn "fpremxf4"
14530 [(set (match_operand:XF 0 "register_operand" "=f")
14531 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
14532 (match_operand:XF 3 "register_operand" "1")]
14534 (set (match_operand:XF 1 "register_operand" "=u")
14535 (unspec:XF [(match_dup 2) (match_dup 3)]
14537 (set (reg:CCFP FPSR_REG)
14538 (unspec:CCFP [(const_int 0)] UNSPEC_NOP))]
14539 "TARGET_USE_FANCY_MATH_387
14540 && flag_unsafe_math_optimizations"
14542 [(set_attr "type" "fpspc")
14543 (set_attr "mode" "XF")])
14545 (define_expand "fmodsf3"
14546 [(use (match_operand:SF 0 "register_operand" ""))
14547 (use (match_operand:SF 1 "register_operand" ""))
14548 (use (match_operand:SF 2 "register_operand" ""))]
14549 "TARGET_USE_FANCY_MATH_387
14550 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14551 && flag_unsafe_math_optimizations"
14553 rtx label = gen_label_rtx ();
14555 rtx op1 = gen_reg_rtx (XFmode);
14556 rtx op2 = gen_reg_rtx (XFmode);
14558 emit_insn(gen_extendsfxf2 (op1, operands[1]));
14559 emit_insn(gen_extendsfxf2 (op2, operands[2]));
14561 emit_label (label);
14563 emit_insn (gen_fpremxf4 (op1, op2, op1, op2));
14564 ix86_emit_fp_unordered_jump (label);
14566 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op1));
14570 (define_expand "fmoddf3"
14571 [(use (match_operand:DF 0 "register_operand" ""))
14572 (use (match_operand:DF 1 "register_operand" ""))
14573 (use (match_operand:DF 2 "register_operand" ""))]
14574 "TARGET_USE_FANCY_MATH_387
14575 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14576 && flag_unsafe_math_optimizations"
14578 rtx label = gen_label_rtx ();
14580 rtx op1 = gen_reg_rtx (XFmode);
14581 rtx op2 = gen_reg_rtx (XFmode);
14583 emit_insn (gen_extenddfxf2 (op1, operands[1]));
14584 emit_insn (gen_extenddfxf2 (op2, operands[2]));
14586 emit_label (label);
14588 emit_insn (gen_fpremxf4 (op1, op2, op1, op2));
14589 ix86_emit_fp_unordered_jump (label);
14591 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op1));
14595 (define_expand "fmodxf3"
14596 [(use (match_operand:XF 0 "register_operand" ""))
14597 (use (match_operand:XF 1 "register_operand" ""))
14598 (use (match_operand:XF 2 "register_operand" ""))]
14599 "TARGET_USE_FANCY_MATH_387
14600 && flag_unsafe_math_optimizations"
14602 rtx label = gen_label_rtx ();
14604 emit_label (label);
14606 emit_insn (gen_fpremxf4 (operands[1], operands[2],
14607 operands[1], operands[2]));
14608 ix86_emit_fp_unordered_jump (label);
14610 emit_move_insn (operands[0], operands[1]);
14614 (define_insn "fprem1xf4"
14615 [(set (match_operand:XF 0 "register_operand" "=f")
14616 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
14617 (match_operand:XF 3 "register_operand" "1")]
14619 (set (match_operand:XF 1 "register_operand" "=u")
14620 (unspec:XF [(match_dup 2) (match_dup 3)]
14622 (set (reg:CCFP FPSR_REG)
14623 (unspec:CCFP [(const_int 0)] UNSPEC_NOP))]
14624 "TARGET_USE_FANCY_MATH_387
14625 && flag_unsafe_math_optimizations"
14627 [(set_attr "type" "fpspc")
14628 (set_attr "mode" "XF")])
14630 (define_expand "dremsf3"
14631 [(use (match_operand:SF 0 "register_operand" ""))
14632 (use (match_operand:SF 1 "register_operand" ""))
14633 (use (match_operand:SF 2 "register_operand" ""))]
14634 "TARGET_USE_FANCY_MATH_387
14635 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14636 && flag_unsafe_math_optimizations"
14638 rtx label = gen_label_rtx ();
14640 rtx op1 = gen_reg_rtx (XFmode);
14641 rtx op2 = gen_reg_rtx (XFmode);
14643 emit_insn(gen_extendsfxf2 (op1, operands[1]));
14644 emit_insn(gen_extendsfxf2 (op2, operands[2]));
14646 emit_label (label);
14648 emit_insn (gen_fprem1xf4 (op1, op2, op1, op2));
14649 ix86_emit_fp_unordered_jump (label);
14651 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op1));
14655 (define_expand "dremdf3"
14656 [(use (match_operand:DF 0 "register_operand" ""))
14657 (use (match_operand:DF 1 "register_operand" ""))
14658 (use (match_operand:DF 2 "register_operand" ""))]
14659 "TARGET_USE_FANCY_MATH_387
14660 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14661 && flag_unsafe_math_optimizations"
14663 rtx label = gen_label_rtx ();
14665 rtx op1 = gen_reg_rtx (XFmode);
14666 rtx op2 = gen_reg_rtx (XFmode);
14668 emit_insn (gen_extenddfxf2 (op1, operands[1]));
14669 emit_insn (gen_extenddfxf2 (op2, operands[2]));
14671 emit_label (label);
14673 emit_insn (gen_fprem1xf4 (op1, op2, op1, op2));
14674 ix86_emit_fp_unordered_jump (label);
14676 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op1));
14680 (define_expand "dremxf3"
14681 [(use (match_operand:XF 0 "register_operand" ""))
14682 (use (match_operand:XF 1 "register_operand" ""))
14683 (use (match_operand:XF 2 "register_operand" ""))]
14684 "TARGET_USE_FANCY_MATH_387
14685 && flag_unsafe_math_optimizations"
14687 rtx label = gen_label_rtx ();
14689 emit_label (label);
14691 emit_insn (gen_fprem1xf4 (operands[1], operands[2],
14692 operands[1], operands[2]));
14693 ix86_emit_fp_unordered_jump (label);
14695 emit_move_insn (operands[0], operands[1]);
14699 (define_insn "*sindf2"
14700 [(set (match_operand:DF 0 "register_operand" "=f")
14701 (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_SIN))]
14702 "TARGET_USE_FANCY_MATH_387
14703 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14704 && flag_unsafe_math_optimizations"
14706 [(set_attr "type" "fpspc")
14707 (set_attr "mode" "DF")])
14709 (define_insn "*sinsf2"
14710 [(set (match_operand:SF 0 "register_operand" "=f")
14711 (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_SIN))]
14712 "TARGET_USE_FANCY_MATH_387
14713 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14714 && flag_unsafe_math_optimizations"
14716 [(set_attr "type" "fpspc")
14717 (set_attr "mode" "SF")])
14719 (define_insn "*sinextendsfdf2"
14720 [(set (match_operand:DF 0 "register_operand" "=f")
14721 (unspec:DF [(float_extend:DF
14722 (match_operand:SF 1 "register_operand" "0"))]
14724 "TARGET_USE_FANCY_MATH_387
14725 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14726 && flag_unsafe_math_optimizations"
14728 [(set_attr "type" "fpspc")
14729 (set_attr "mode" "DF")])
14731 (define_insn "*sinxf2"
14732 [(set (match_operand:XF 0 "register_operand" "=f")
14733 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
14734 "TARGET_USE_FANCY_MATH_387
14735 && flag_unsafe_math_optimizations"
14737 [(set_attr "type" "fpspc")
14738 (set_attr "mode" "XF")])
14740 (define_insn "*cosdf2"
14741 [(set (match_operand:DF 0 "register_operand" "=f")
14742 (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_COS))]
14743 "TARGET_USE_FANCY_MATH_387
14744 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14745 && flag_unsafe_math_optimizations"
14747 [(set_attr "type" "fpspc")
14748 (set_attr "mode" "DF")])
14750 (define_insn "*cossf2"
14751 [(set (match_operand:SF 0 "register_operand" "=f")
14752 (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_COS))]
14753 "TARGET_USE_FANCY_MATH_387
14754 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14755 && flag_unsafe_math_optimizations"
14757 [(set_attr "type" "fpspc")
14758 (set_attr "mode" "SF")])
14760 (define_insn "*cosextendsfdf2"
14761 [(set (match_operand:DF 0 "register_operand" "=f")
14762 (unspec:DF [(float_extend:DF
14763 (match_operand:SF 1 "register_operand" "0"))]
14765 "TARGET_USE_FANCY_MATH_387
14766 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14767 && flag_unsafe_math_optimizations"
14769 [(set_attr "type" "fpspc")
14770 (set_attr "mode" "DF")])
14772 (define_insn "*cosxf2"
14773 [(set (match_operand:XF 0 "register_operand" "=f")
14774 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
14775 "TARGET_USE_FANCY_MATH_387
14776 && flag_unsafe_math_optimizations"
14778 [(set_attr "type" "fpspc")
14779 (set_attr "mode" "XF")])
14781 ;; With sincos pattern defined, sin and cos builtin function will be
14782 ;; expanded to sincos pattern with one of its outputs left unused.
14783 ;; Cse pass will detected, if two sincos patterns can be combined,
14784 ;; otherwise sincos pattern will be split back to sin or cos pattern,
14785 ;; depending on the unused output.
14787 (define_insn "sincosdf3"
14788 [(set (match_operand:DF 0 "register_operand" "=f")
14789 (unspec:DF [(match_operand:DF 2 "register_operand" "0")]
14790 UNSPEC_SINCOS_COS))
14791 (set (match_operand:DF 1 "register_operand" "=u")
14792 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14793 "TARGET_USE_FANCY_MATH_387
14794 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14795 && flag_unsafe_math_optimizations"
14797 [(set_attr "type" "fpspc")
14798 (set_attr "mode" "DF")])
14801 [(set (match_operand:DF 0 "register_operand" "")
14802 (unspec:DF [(match_operand:DF 2 "register_operand" "")]
14803 UNSPEC_SINCOS_COS))
14804 (set (match_operand:DF 1 "register_operand" "")
14805 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14806 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
14807 && !reload_completed && !reload_in_progress"
14808 [(set (match_dup 1) (unspec:DF [(match_dup 2)] UNSPEC_SIN))]
14812 [(set (match_operand:DF 0 "register_operand" "")
14813 (unspec:DF [(match_operand:DF 2 "register_operand" "")]
14814 UNSPEC_SINCOS_COS))
14815 (set (match_operand:DF 1 "register_operand" "")
14816 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14817 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
14818 && !reload_completed && !reload_in_progress"
14819 [(set (match_dup 0) (unspec:DF [(match_dup 2)] UNSPEC_COS))]
14822 (define_insn "sincossf3"
14823 [(set (match_operand:SF 0 "register_operand" "=f")
14824 (unspec:SF [(match_operand:SF 2 "register_operand" "0")]
14825 UNSPEC_SINCOS_COS))
14826 (set (match_operand:SF 1 "register_operand" "=u")
14827 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14828 "TARGET_USE_FANCY_MATH_387
14829 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14830 && flag_unsafe_math_optimizations"
14832 [(set_attr "type" "fpspc")
14833 (set_attr "mode" "SF")])
14836 [(set (match_operand:SF 0 "register_operand" "")
14837 (unspec:SF [(match_operand:SF 2 "register_operand" "")]
14838 UNSPEC_SINCOS_COS))
14839 (set (match_operand:SF 1 "register_operand" "")
14840 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14841 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
14842 && !reload_completed && !reload_in_progress"
14843 [(set (match_dup 1) (unspec:SF [(match_dup 2)] UNSPEC_SIN))]
14847 [(set (match_operand:SF 0 "register_operand" "")
14848 (unspec:SF [(match_operand:SF 2 "register_operand" "")]
14849 UNSPEC_SINCOS_COS))
14850 (set (match_operand:SF 1 "register_operand" "")
14851 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14852 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
14853 && !reload_completed && !reload_in_progress"
14854 [(set (match_dup 0) (unspec:SF [(match_dup 2)] UNSPEC_COS))]
14857 (define_insn "*sincosextendsfdf3"
14858 [(set (match_operand:DF 0 "register_operand" "=f")
14859 (unspec:DF [(float_extend:DF
14860 (match_operand:SF 2 "register_operand" "0"))]
14861 UNSPEC_SINCOS_COS))
14862 (set (match_operand:DF 1 "register_operand" "=u")
14863 (unspec:DF [(float_extend:DF
14864 (match_dup 2))] UNSPEC_SINCOS_SIN))]
14865 "TARGET_USE_FANCY_MATH_387
14866 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14867 && flag_unsafe_math_optimizations"
14869 [(set_attr "type" "fpspc")
14870 (set_attr "mode" "DF")])
14873 [(set (match_operand:DF 0 "register_operand" "")
14874 (unspec:DF [(float_extend:DF
14875 (match_operand:SF 2 "register_operand" ""))]
14876 UNSPEC_SINCOS_COS))
14877 (set (match_operand:DF 1 "register_operand" "")
14878 (unspec:DF [(float_extend:DF
14879 (match_dup 2))] UNSPEC_SINCOS_SIN))]
14880 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
14881 && !reload_completed && !reload_in_progress"
14882 [(set (match_dup 1) (unspec:DF [(float_extend:DF
14883 (match_dup 2))] UNSPEC_SIN))]
14887 [(set (match_operand:DF 0 "register_operand" "")
14888 (unspec:DF [(float_extend:DF
14889 (match_operand:SF 2 "register_operand" ""))]
14890 UNSPEC_SINCOS_COS))
14891 (set (match_operand:DF 1 "register_operand" "")
14892 (unspec:DF [(float_extend:DF
14893 (match_dup 2))] UNSPEC_SINCOS_SIN))]
14894 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
14895 && !reload_completed && !reload_in_progress"
14896 [(set (match_dup 0) (unspec:DF [(float_extend:DF
14897 (match_dup 2))] UNSPEC_COS))]
14900 (define_insn "sincosxf3"
14901 [(set (match_operand:XF 0 "register_operand" "=f")
14902 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
14903 UNSPEC_SINCOS_COS))
14904 (set (match_operand:XF 1 "register_operand" "=u")
14905 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14906 "TARGET_USE_FANCY_MATH_387
14907 && flag_unsafe_math_optimizations"
14909 [(set_attr "type" "fpspc")
14910 (set_attr "mode" "XF")])
14913 [(set (match_operand:XF 0 "register_operand" "")
14914 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
14915 UNSPEC_SINCOS_COS))
14916 (set (match_operand:XF 1 "register_operand" "")
14917 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14918 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
14919 && !reload_completed && !reload_in_progress"
14920 [(set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_SIN))]
14924 [(set (match_operand:XF 0 "register_operand" "")
14925 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
14926 UNSPEC_SINCOS_COS))
14927 (set (match_operand:XF 1 "register_operand" "")
14928 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
14929 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
14930 && !reload_completed && !reload_in_progress"
14931 [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))]
14934 (define_insn "*tandf3_1"
14935 [(set (match_operand:DF 0 "register_operand" "=f")
14936 (unspec:DF [(match_operand:DF 2 "register_operand" "0")]
14938 (set (match_operand:DF 1 "register_operand" "=u")
14939 (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))]
14940 "TARGET_USE_FANCY_MATH_387
14941 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14942 && flag_unsafe_math_optimizations"
14944 [(set_attr "type" "fpspc")
14945 (set_attr "mode" "DF")])
14947 ;; optimize sequence: fptan
14950 ;; into fptan insn.
14953 [(parallel[(set (match_operand:DF 0 "register_operand" "")
14954 (unspec:DF [(match_operand:DF 2 "register_operand" "")]
14956 (set (match_operand:DF 1 "register_operand" "")
14957 (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))])
14959 (match_operand:DF 3 "immediate_operand" ""))]
14960 "standard_80387_constant_p (operands[3]) == 2"
14961 [(parallel[(set (match_dup 0) (unspec:DF [(match_dup 2)] UNSPEC_TAN_ONE))
14962 (set (match_dup 1) (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))])]
14965 (define_expand "tandf2"
14966 [(parallel [(set (match_dup 2)
14967 (unspec:DF [(match_operand:DF 1 "register_operand" "")]
14969 (set (match_operand:DF 0 "register_operand" "")
14970 (unspec:DF [(match_dup 1)] UNSPEC_TAN_TAN))])]
14971 "TARGET_USE_FANCY_MATH_387
14972 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14973 && flag_unsafe_math_optimizations"
14975 operands[2] = gen_reg_rtx (DFmode);
14978 (define_insn "*tansf3_1"
14979 [(set (match_operand:SF 0 "register_operand" "=f")
14980 (unspec:SF [(match_operand:SF 2 "register_operand" "0")]
14982 (set (match_operand:SF 1 "register_operand" "=u")
14983 (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))]
14984 "TARGET_USE_FANCY_MATH_387
14985 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14986 && flag_unsafe_math_optimizations"
14988 [(set_attr "type" "fpspc")
14989 (set_attr "mode" "SF")])
14991 ;; optimize sequence: fptan
14994 ;; into fptan insn.
14997 [(parallel[(set (match_operand:SF 0 "register_operand" "")
14998 (unspec:SF [(match_operand:SF 2 "register_operand" "")]
15000 (set (match_operand:SF 1 "register_operand" "")
15001 (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))])
15003 (match_operand:SF 3 "immediate_operand" ""))]
15004 "standard_80387_constant_p (operands[3]) == 2"
15005 [(parallel[(set (match_dup 0) (unspec:SF [(match_dup 2)] UNSPEC_TAN_ONE))
15006 (set (match_dup 1) (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15009 (define_expand "tansf2"
15010 [(parallel [(set (match_dup 2)
15011 (unspec:SF [(match_operand:SF 1 "register_operand" "")]
15013 (set (match_operand:SF 0 "register_operand" "")
15014 (unspec:SF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15015 "TARGET_USE_FANCY_MATH_387
15016 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15017 && flag_unsafe_math_optimizations"
15019 operands[2] = gen_reg_rtx (SFmode);
15022 (define_insn "*tanxf3_1"
15023 [(set (match_operand:XF 0 "register_operand" "=f")
15024 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15026 (set (match_operand:XF 1 "register_operand" "=u")
15027 (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))]
15028 "TARGET_USE_FANCY_MATH_387
15029 && flag_unsafe_math_optimizations"
15031 [(set_attr "type" "fpspc")
15032 (set_attr "mode" "XF")])
15034 ;; optimize sequence: fptan
15037 ;; into fptan insn.
15040 [(parallel[(set (match_operand:XF 0 "register_operand" "")
15041 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
15043 (set (match_operand:XF 1 "register_operand" "")
15044 (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))])
15046 (match_operand:XF 3 "immediate_operand" ""))]
15047 "standard_80387_constant_p (operands[3]) == 2"
15048 [(parallel[(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_TAN_ONE))
15049 (set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15052 (define_expand "tanxf2"
15053 [(parallel [(set (match_dup 2)
15054 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15056 (set (match_operand:XF 0 "register_operand" "")
15057 (unspec:XF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15058 "TARGET_USE_FANCY_MATH_387
15059 && flag_unsafe_math_optimizations"
15061 operands[2] = gen_reg_rtx (XFmode);
15064 (define_insn "atan2df3_1"
15065 [(set (match_operand:DF 0 "register_operand" "=f")
15066 (unspec:DF [(match_operand:DF 2 "register_operand" "0")
15067 (match_operand:DF 1 "register_operand" "u")]
15069 (clobber (match_scratch:DF 3 "=1"))]
15070 "TARGET_USE_FANCY_MATH_387
15071 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15072 && flag_unsafe_math_optimizations"
15074 [(set_attr "type" "fpspc")
15075 (set_attr "mode" "DF")])
15077 (define_expand "atan2df3"
15078 [(use (match_operand:DF 0 "register_operand" ""))
15079 (use (match_operand:DF 2 "register_operand" ""))
15080 (use (match_operand:DF 1 "register_operand" ""))]
15081 "TARGET_USE_FANCY_MATH_387
15082 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15083 && flag_unsafe_math_optimizations"
15085 rtx copy = gen_reg_rtx (DFmode);
15086 emit_move_insn (copy, operands[1]);
15087 emit_insn (gen_atan2df3_1 (operands[0], copy, operands[2]));
15091 (define_expand "atandf2"
15092 [(parallel [(set (match_operand:DF 0 "register_operand" "")
15093 (unspec:DF [(match_dup 2)
15094 (match_operand:DF 1 "register_operand" "")]
15096 (clobber (match_scratch:DF 3 ""))])]
15097 "TARGET_USE_FANCY_MATH_387
15098 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15099 && flag_unsafe_math_optimizations"
15101 operands[2] = gen_reg_rtx (DFmode);
15102 emit_move_insn (operands[2], CONST1_RTX (DFmode)); /* fld1 */
15105 (define_insn "atan2sf3_1"
15106 [(set (match_operand:SF 0 "register_operand" "=f")
15107 (unspec:SF [(match_operand:SF 2 "register_operand" "0")
15108 (match_operand:SF 1 "register_operand" "u")]
15110 (clobber (match_scratch:SF 3 "=1"))]
15111 "TARGET_USE_FANCY_MATH_387
15112 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15113 && flag_unsafe_math_optimizations"
15115 [(set_attr "type" "fpspc")
15116 (set_attr "mode" "SF")])
15118 (define_expand "atan2sf3"
15119 [(use (match_operand:SF 0 "register_operand" ""))
15120 (use (match_operand:SF 2 "register_operand" ""))
15121 (use (match_operand:SF 1 "register_operand" ""))]
15122 "TARGET_USE_FANCY_MATH_387
15123 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15124 && flag_unsafe_math_optimizations"
15126 rtx copy = gen_reg_rtx (SFmode);
15127 emit_move_insn (copy, operands[1]);
15128 emit_insn (gen_atan2sf3_1 (operands[0], copy, operands[2]));
15132 (define_expand "atansf2"
15133 [(parallel [(set (match_operand:SF 0 "register_operand" "")
15134 (unspec:SF [(match_dup 2)
15135 (match_operand:SF 1 "register_operand" "")]
15137 (clobber (match_scratch:SF 3 ""))])]
15138 "TARGET_USE_FANCY_MATH_387
15139 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15140 && flag_unsafe_math_optimizations"
15142 operands[2] = gen_reg_rtx (SFmode);
15143 emit_move_insn (operands[2], CONST1_RTX (SFmode)); /* fld1 */
15146 (define_insn "atan2xf3_1"
15147 [(set (match_operand:XF 0 "register_operand" "=f")
15148 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15149 (match_operand:XF 1 "register_operand" "u")]
15151 (clobber (match_scratch:XF 3 "=1"))]
15152 "TARGET_USE_FANCY_MATH_387
15153 && flag_unsafe_math_optimizations"
15155 [(set_attr "type" "fpspc")
15156 (set_attr "mode" "XF")])
15158 (define_expand "atan2xf3"
15159 [(use (match_operand:XF 0 "register_operand" ""))
15160 (use (match_operand:XF 2 "register_operand" ""))
15161 (use (match_operand:XF 1 "register_operand" ""))]
15162 "TARGET_USE_FANCY_MATH_387
15163 && flag_unsafe_math_optimizations"
15165 rtx copy = gen_reg_rtx (XFmode);
15166 emit_move_insn (copy, operands[1]);
15167 emit_insn (gen_atan2xf3_1 (operands[0], copy, operands[2]));
15171 (define_expand "atanxf2"
15172 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15173 (unspec:XF [(match_dup 2)
15174 (match_operand:XF 1 "register_operand" "")]
15176 (clobber (match_scratch:XF 3 ""))])]
15177 "TARGET_USE_FANCY_MATH_387
15178 && flag_unsafe_math_optimizations"
15180 operands[2] = gen_reg_rtx (XFmode);
15181 emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
15184 (define_expand "asindf2"
15185 [(set (match_dup 2)
15186 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15187 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15188 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15189 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15190 (parallel [(set (match_dup 7)
15191 (unspec:XF [(match_dup 6) (match_dup 2)]
15193 (clobber (match_scratch:XF 8 ""))])
15194 (set (match_operand:DF 0 "register_operand" "")
15195 (float_truncate:DF (match_dup 7)))]
15196 "TARGET_USE_FANCY_MATH_387
15197 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15198 && flag_unsafe_math_optimizations"
15202 for (i=2; i<8; i++)
15203 operands[i] = gen_reg_rtx (XFmode);
15205 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15208 (define_expand "asinsf2"
15209 [(set (match_dup 2)
15210 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15211 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15212 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15213 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15214 (parallel [(set (match_dup 7)
15215 (unspec:XF [(match_dup 6) (match_dup 2)]
15217 (clobber (match_scratch:XF 8 ""))])
15218 (set (match_operand:SF 0 "register_operand" "")
15219 (float_truncate:SF (match_dup 7)))]
15220 "TARGET_USE_FANCY_MATH_387
15221 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15222 && flag_unsafe_math_optimizations"
15226 for (i=2; i<8; i++)
15227 operands[i] = gen_reg_rtx (XFmode);
15229 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15232 (define_expand "asinxf2"
15233 [(set (match_dup 2)
15234 (mult:XF (match_operand:XF 1 "register_operand" "")
15236 (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
15237 (set (match_dup 5) (sqrt:XF (match_dup 4)))
15238 (parallel [(set (match_operand:XF 0 "register_operand" "")
15239 (unspec:XF [(match_dup 5) (match_dup 1)]
15241 (clobber (match_scratch:XF 6 ""))])]
15242 "TARGET_USE_FANCY_MATH_387
15243 && flag_unsafe_math_optimizations"
15247 for (i=2; i<6; i++)
15248 operands[i] = gen_reg_rtx (XFmode);
15250 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15253 (define_expand "acosdf2"
15254 [(set (match_dup 2)
15255 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15256 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15257 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15258 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15259 (parallel [(set (match_dup 7)
15260 (unspec:XF [(match_dup 2) (match_dup 6)]
15262 (clobber (match_scratch:XF 8 ""))])
15263 (set (match_operand:DF 0 "register_operand" "")
15264 (float_truncate:DF (match_dup 7)))]
15265 "TARGET_USE_FANCY_MATH_387
15266 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15267 && flag_unsafe_math_optimizations"
15271 for (i=2; i<8; i++)
15272 operands[i] = gen_reg_rtx (XFmode);
15274 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15277 (define_expand "acossf2"
15278 [(set (match_dup 2)
15279 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15280 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15281 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15282 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15283 (parallel [(set (match_dup 7)
15284 (unspec:XF [(match_dup 2) (match_dup 6)]
15286 (clobber (match_scratch:XF 8 ""))])
15287 (set (match_operand:SF 0 "register_operand" "")
15288 (float_truncate:SF (match_dup 7)))]
15289 "TARGET_USE_FANCY_MATH_387
15290 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15291 && flag_unsafe_math_optimizations"
15295 for (i=2; i<8; i++)
15296 operands[i] = gen_reg_rtx (XFmode);
15298 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15301 (define_expand "acosxf2"
15302 [(set (match_dup 2)
15303 (mult:XF (match_operand:XF 1 "register_operand" "")
15305 (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
15306 (set (match_dup 5) (sqrt:XF (match_dup 4)))
15307 (parallel [(set (match_operand:XF 0 "register_operand" "")
15308 (unspec:XF [(match_dup 1) (match_dup 5)]
15310 (clobber (match_scratch:XF 6 ""))])]
15311 "TARGET_USE_FANCY_MATH_387
15312 && flag_unsafe_math_optimizations"
15316 for (i=2; i<6; i++)
15317 operands[i] = gen_reg_rtx (XFmode);
15319 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15322 (define_insn "fyl2x_xf3"
15323 [(set (match_operand:XF 0 "register_operand" "=f")
15324 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15325 (match_operand:XF 1 "register_operand" "u")]
15327 (clobber (match_scratch:XF 3 "=1"))]
15328 "TARGET_USE_FANCY_MATH_387
15329 && flag_unsafe_math_optimizations"
15331 [(set_attr "type" "fpspc")
15332 (set_attr "mode" "XF")])
15334 (define_expand "logsf2"
15335 [(set (match_dup 2)
15336 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15337 (parallel [(set (match_dup 4)
15338 (unspec:XF [(match_dup 2)
15339 (match_dup 3)] UNSPEC_FYL2X))
15340 (clobber (match_scratch:XF 5 ""))])
15341 (set (match_operand:SF 0 "register_operand" "")
15342 (float_truncate:SF (match_dup 4)))]
15343 "TARGET_USE_FANCY_MATH_387
15344 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15345 && flag_unsafe_math_optimizations"
15349 operands[2] = gen_reg_rtx (XFmode);
15350 operands[3] = gen_reg_rtx (XFmode);
15351 operands[4] = gen_reg_rtx (XFmode);
15353 temp = standard_80387_constant_rtx (4); /* fldln2 */
15354 emit_move_insn (operands[3], temp);
15357 (define_expand "logdf2"
15358 [(set (match_dup 2)
15359 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15360 (parallel [(set (match_dup 4)
15361 (unspec:XF [(match_dup 2)
15362 (match_dup 3)] UNSPEC_FYL2X))
15363 (clobber (match_scratch:XF 5 ""))])
15364 (set (match_operand:DF 0 "register_operand" "")
15365 (float_truncate:DF (match_dup 4)))]
15366 "TARGET_USE_FANCY_MATH_387
15367 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15368 && flag_unsafe_math_optimizations"
15372 operands[2] = gen_reg_rtx (XFmode);
15373 operands[3] = gen_reg_rtx (XFmode);
15374 operands[4] = gen_reg_rtx (XFmode);
15376 temp = standard_80387_constant_rtx (4); /* fldln2 */
15377 emit_move_insn (operands[3], temp);
15380 (define_expand "logxf2"
15381 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15382 (unspec:XF [(match_operand:XF 1 "register_operand" "")
15383 (match_dup 2)] UNSPEC_FYL2X))
15384 (clobber (match_scratch:XF 3 ""))])]
15385 "TARGET_USE_FANCY_MATH_387
15386 && flag_unsafe_math_optimizations"
15390 operands[2] = gen_reg_rtx (XFmode);
15391 temp = standard_80387_constant_rtx (4); /* fldln2 */
15392 emit_move_insn (operands[2], temp);
15395 (define_expand "log10sf2"
15396 [(set (match_dup 2)
15397 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15398 (parallel [(set (match_dup 4)
15399 (unspec:XF [(match_dup 2)
15400 (match_dup 3)] UNSPEC_FYL2X))
15401 (clobber (match_scratch:XF 5 ""))])
15402 (set (match_operand:SF 0 "register_operand" "")
15403 (float_truncate:SF (match_dup 4)))]
15404 "TARGET_USE_FANCY_MATH_387
15405 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15406 && flag_unsafe_math_optimizations"
15410 operands[2] = gen_reg_rtx (XFmode);
15411 operands[3] = gen_reg_rtx (XFmode);
15412 operands[4] = gen_reg_rtx (XFmode);
15414 temp = standard_80387_constant_rtx (3); /* fldlg2 */
15415 emit_move_insn (operands[3], temp);
15418 (define_expand "log10df2"
15419 [(set (match_dup 2)
15420 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15421 (parallel [(set (match_dup 4)
15422 (unspec:XF [(match_dup 2)
15423 (match_dup 3)] UNSPEC_FYL2X))
15424 (clobber (match_scratch:XF 5 ""))])
15425 (set (match_operand:DF 0 "register_operand" "")
15426 (float_truncate:DF (match_dup 4)))]
15427 "TARGET_USE_FANCY_MATH_387
15428 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15429 && flag_unsafe_math_optimizations"
15433 operands[2] = gen_reg_rtx (XFmode);
15434 operands[3] = gen_reg_rtx (XFmode);
15435 operands[4] = gen_reg_rtx (XFmode);
15437 temp = standard_80387_constant_rtx (3); /* fldlg2 */
15438 emit_move_insn (operands[3], temp);
15441 (define_expand "log10xf2"
15442 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15443 (unspec:XF [(match_operand:XF 1 "register_operand" "")
15444 (match_dup 2)] UNSPEC_FYL2X))
15445 (clobber (match_scratch:XF 3 ""))])]
15446 "TARGET_USE_FANCY_MATH_387
15447 && flag_unsafe_math_optimizations"
15451 operands[2] = gen_reg_rtx (XFmode);
15452 temp = standard_80387_constant_rtx (3); /* fldlg2 */
15453 emit_move_insn (operands[2], temp);
15456 (define_expand "log2sf2"
15457 [(set (match_dup 2)
15458 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15459 (parallel [(set (match_dup 4)
15460 (unspec:XF [(match_dup 2)
15461 (match_dup 3)] UNSPEC_FYL2X))
15462 (clobber (match_scratch:XF 5 ""))])
15463 (set (match_operand:SF 0 "register_operand" "")
15464 (float_truncate:SF (match_dup 4)))]
15465 "TARGET_USE_FANCY_MATH_387
15466 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15467 && flag_unsafe_math_optimizations"
15469 operands[2] = gen_reg_rtx (XFmode);
15470 operands[3] = gen_reg_rtx (XFmode);
15471 operands[4] = gen_reg_rtx (XFmode);
15473 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15476 (define_expand "log2df2"
15477 [(set (match_dup 2)
15478 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15479 (parallel [(set (match_dup 4)
15480 (unspec:XF [(match_dup 2)
15481 (match_dup 3)] UNSPEC_FYL2X))
15482 (clobber (match_scratch:XF 5 ""))])
15483 (set (match_operand:DF 0 "register_operand" "")
15484 (float_truncate:DF (match_dup 4)))]
15485 "TARGET_USE_FANCY_MATH_387
15486 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15487 && flag_unsafe_math_optimizations"
15489 operands[2] = gen_reg_rtx (XFmode);
15490 operands[3] = gen_reg_rtx (XFmode);
15491 operands[4] = gen_reg_rtx (XFmode);
15493 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15496 (define_expand "log2xf2"
15497 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15498 (unspec:XF [(match_operand:XF 1 "register_operand" "")
15499 (match_dup 2)] UNSPEC_FYL2X))
15500 (clobber (match_scratch:XF 3 ""))])]
15501 "TARGET_USE_FANCY_MATH_387
15502 && flag_unsafe_math_optimizations"
15504 operands[2] = gen_reg_rtx (XFmode);
15505 emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
15508 (define_insn "fyl2xp1_xf3"
15509 [(set (match_operand:XF 0 "register_operand" "=f")
15510 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15511 (match_operand:XF 1 "register_operand" "u")]
15513 (clobber (match_scratch:XF 3 "=1"))]
15514 "TARGET_USE_FANCY_MATH_387
15515 && flag_unsafe_math_optimizations"
15517 [(set_attr "type" "fpspc")
15518 (set_attr "mode" "XF")])
15520 (define_expand "log1psf2"
15521 [(use (match_operand:SF 0 "register_operand" ""))
15522 (use (match_operand:SF 1 "register_operand" ""))]
15523 "TARGET_USE_FANCY_MATH_387
15524 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15525 && flag_unsafe_math_optimizations"
15527 rtx op0 = gen_reg_rtx (XFmode);
15528 rtx op1 = gen_reg_rtx (XFmode);
15530 emit_insn (gen_extendsfxf2 (op1, operands[1]));
15531 ix86_emit_i387_log1p (op0, op1);
15532 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
15536 (define_expand "log1pdf2"
15537 [(use (match_operand:DF 0 "register_operand" ""))
15538 (use (match_operand:DF 1 "register_operand" ""))]
15539 "TARGET_USE_FANCY_MATH_387
15540 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15541 && flag_unsafe_math_optimizations"
15543 rtx op0 = gen_reg_rtx (XFmode);
15544 rtx op1 = gen_reg_rtx (XFmode);
15546 emit_insn (gen_extenddfxf2 (op1, operands[1]));
15547 ix86_emit_i387_log1p (op0, op1);
15548 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
15552 (define_expand "log1pxf2"
15553 [(use (match_operand:XF 0 "register_operand" ""))
15554 (use (match_operand:XF 1 "register_operand" ""))]
15555 "TARGET_USE_FANCY_MATH_387
15556 && flag_unsafe_math_optimizations"
15558 ix86_emit_i387_log1p (operands[0], operands[1]);
15562 (define_insn "*fxtractxf3"
15563 [(set (match_operand:XF 0 "register_operand" "=f")
15564 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15565 UNSPEC_XTRACT_FRACT))
15566 (set (match_operand:XF 1 "register_operand" "=u")
15567 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]
15568 "TARGET_USE_FANCY_MATH_387
15569 && flag_unsafe_math_optimizations"
15571 [(set_attr "type" "fpspc")
15572 (set_attr "mode" "XF")])
15574 (define_expand "logbsf2"
15575 [(set (match_dup 2)
15576 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15577 (parallel [(set (match_dup 3)
15578 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_FRACT))
15580 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))])
15581 (set (match_operand:SF 0 "register_operand" "")
15582 (float_truncate:SF (match_dup 4)))]
15583 "TARGET_USE_FANCY_MATH_387
15584 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15585 && flag_unsafe_math_optimizations"
15587 operands[2] = gen_reg_rtx (XFmode);
15588 operands[3] = gen_reg_rtx (XFmode);
15589 operands[4] = gen_reg_rtx (XFmode);
15592 (define_expand "logbdf2"
15593 [(set (match_dup 2)
15594 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15595 (parallel [(set (match_dup 3)
15596 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_FRACT))
15598 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))])
15599 (set (match_operand:DF 0 "register_operand" "")
15600 (float_truncate:DF (match_dup 4)))]
15601 "TARGET_USE_FANCY_MATH_387
15602 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15603 && flag_unsafe_math_optimizations"
15605 operands[2] = gen_reg_rtx (XFmode);
15606 operands[3] = gen_reg_rtx (XFmode);
15607 operands[4] = gen_reg_rtx (XFmode);
15610 (define_expand "logbxf2"
15611 [(parallel [(set (match_dup 2)
15612 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15613 UNSPEC_XTRACT_FRACT))
15614 (set (match_operand:XF 0 "register_operand" "")
15615 (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
15616 "TARGET_USE_FANCY_MATH_387
15617 && flag_unsafe_math_optimizations"
15619 operands[2] = gen_reg_rtx (XFmode);
15622 (define_expand "ilogbsi2"
15623 [(parallel [(set (match_dup 2)
15624 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15625 UNSPEC_XTRACT_FRACT))
15626 (set (match_operand:XF 3 "register_operand" "")
15627 (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])
15628 (parallel [(set (match_operand:SI 0 "register_operand" "")
15629 (fix:SI (match_dup 3)))
15630 (clobber (reg:CC FLAGS_REG))])]
15631 "TARGET_USE_FANCY_MATH_387
15632 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15633 && flag_unsafe_math_optimizations"
15635 operands[2] = gen_reg_rtx (XFmode);
15636 operands[3] = gen_reg_rtx (XFmode);
15639 (define_insn "*f2xm1xf2"
15640 [(set (match_operand:XF 0 "register_operand" "=f")
15641 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
15643 "TARGET_USE_FANCY_MATH_387
15644 && flag_unsafe_math_optimizations"
15646 [(set_attr "type" "fpspc")
15647 (set_attr "mode" "XF")])
15649 (define_insn "*fscalexf4"
15650 [(set (match_operand:XF 0 "register_operand" "=f")
15651 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15652 (match_operand:XF 3 "register_operand" "1")]
15653 UNSPEC_FSCALE_FRACT))
15654 (set (match_operand:XF 1 "register_operand" "=u")
15655 (unspec:XF [(match_dup 2) (match_dup 3)]
15656 UNSPEC_FSCALE_EXP))]
15657 "TARGET_USE_FANCY_MATH_387
15658 && flag_unsafe_math_optimizations"
15660 [(set_attr "type" "fpspc")
15661 (set_attr "mode" "XF")])
15663 (define_expand "expsf2"
15664 [(set (match_dup 2)
15665 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15666 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15667 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15668 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15669 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15670 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
15671 (parallel [(set (match_dup 10)
15672 (unspec:XF [(match_dup 9) (match_dup 5)]
15673 UNSPEC_FSCALE_FRACT))
15674 (set (match_dup 11)
15675 (unspec:XF [(match_dup 9) (match_dup 5)]
15676 UNSPEC_FSCALE_EXP))])
15677 (set (match_operand:SF 0 "register_operand" "")
15678 (float_truncate:SF (match_dup 10)))]
15679 "TARGET_USE_FANCY_MATH_387
15680 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15681 && flag_unsafe_math_optimizations"
15686 for (i=2; i<12; i++)
15687 operands[i] = gen_reg_rtx (XFmode);
15688 temp = standard_80387_constant_rtx (5); /* fldl2e */
15689 emit_move_insn (operands[3], temp);
15690 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
15693 (define_expand "expdf2"
15694 [(set (match_dup 2)
15695 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15696 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15697 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15698 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15699 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15700 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
15701 (parallel [(set (match_dup 10)
15702 (unspec:XF [(match_dup 9) (match_dup 5)]
15703 UNSPEC_FSCALE_FRACT))
15704 (set (match_dup 11)
15705 (unspec:XF [(match_dup 9) (match_dup 5)]
15706 UNSPEC_FSCALE_EXP))])
15707 (set (match_operand:DF 0 "register_operand" "")
15708 (float_truncate:DF (match_dup 10)))]
15709 "TARGET_USE_FANCY_MATH_387
15710 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15711 && flag_unsafe_math_optimizations"
15716 for (i=2; i<12; i++)
15717 operands[i] = gen_reg_rtx (XFmode);
15718 temp = standard_80387_constant_rtx (5); /* fldl2e */
15719 emit_move_insn (operands[3], temp);
15720 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
15723 (define_expand "expxf2"
15724 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
15726 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
15727 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
15728 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
15729 (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
15730 (parallel [(set (match_operand:XF 0 "register_operand" "")
15731 (unspec:XF [(match_dup 8) (match_dup 4)]
15732 UNSPEC_FSCALE_FRACT))
15734 (unspec:XF [(match_dup 8) (match_dup 4)]
15735 UNSPEC_FSCALE_EXP))])]
15736 "TARGET_USE_FANCY_MATH_387
15737 && flag_unsafe_math_optimizations"
15742 for (i=2; i<10; i++)
15743 operands[i] = gen_reg_rtx (XFmode);
15744 temp = standard_80387_constant_rtx (5); /* fldl2e */
15745 emit_move_insn (operands[2], temp);
15746 emit_move_insn (operands[7], CONST1_RTX (XFmode)); /* fld1 */
15749 (define_expand "exp10sf2"
15750 [(set (match_dup 2)
15751 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15752 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15753 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15754 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15755 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15756 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
15757 (parallel [(set (match_dup 10)
15758 (unspec:XF [(match_dup 9) (match_dup 5)]
15759 UNSPEC_FSCALE_FRACT))
15760 (set (match_dup 11)
15761 (unspec:XF [(match_dup 9) (match_dup 5)]
15762 UNSPEC_FSCALE_EXP))])
15763 (set (match_operand:SF 0 "register_operand" "")
15764 (float_truncate:SF (match_dup 10)))]
15765 "TARGET_USE_FANCY_MATH_387
15766 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15767 && flag_unsafe_math_optimizations"
15772 for (i=2; i<12; i++)
15773 operands[i] = gen_reg_rtx (XFmode);
15774 temp = standard_80387_constant_rtx (6); /* fldl2t */
15775 emit_move_insn (operands[3], temp);
15776 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
15779 (define_expand "exp10df2"
15780 [(set (match_dup 2)
15781 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15782 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15783 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15784 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15785 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15786 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
15787 (parallel [(set (match_dup 10)
15788 (unspec:XF [(match_dup 9) (match_dup 5)]
15789 UNSPEC_FSCALE_FRACT))
15790 (set (match_dup 11)
15791 (unspec:XF [(match_dup 9) (match_dup 5)]
15792 UNSPEC_FSCALE_EXP))])
15793 (set (match_operand:DF 0 "register_operand" "")
15794 (float_truncate:DF (match_dup 10)))]
15795 "TARGET_USE_FANCY_MATH_387
15796 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15797 && flag_unsafe_math_optimizations"
15802 for (i=2; i<12; i++)
15803 operands[i] = gen_reg_rtx (XFmode);
15804 temp = standard_80387_constant_rtx (6); /* fldl2t */
15805 emit_move_insn (operands[3], temp);
15806 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
15809 (define_expand "exp10xf2"
15810 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
15812 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
15813 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
15814 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
15815 (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
15816 (parallel [(set (match_operand:XF 0 "register_operand" "")
15817 (unspec:XF [(match_dup 8) (match_dup 4)]
15818 UNSPEC_FSCALE_FRACT))
15820 (unspec:XF [(match_dup 8) (match_dup 4)]
15821 UNSPEC_FSCALE_EXP))])]
15822 "TARGET_USE_FANCY_MATH_387
15823 && flag_unsafe_math_optimizations"
15828 for (i=2; i<10; i++)
15829 operands[i] = gen_reg_rtx (XFmode);
15830 temp = standard_80387_constant_rtx (6); /* fldl2t */
15831 emit_move_insn (operands[2], temp);
15832 emit_move_insn (operands[7], CONST1_RTX (XFmode)); /* fld1 */
15835 (define_expand "exp2sf2"
15836 [(set (match_dup 2)
15837 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15838 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
15839 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
15840 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
15841 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
15842 (parallel [(set (match_dup 8)
15843 (unspec:XF [(match_dup 7) (match_dup 3)]
15844 UNSPEC_FSCALE_FRACT))
15846 (unspec:XF [(match_dup 7) (match_dup 3)]
15847 UNSPEC_FSCALE_EXP))])
15848 (set (match_operand:SF 0 "register_operand" "")
15849 (float_truncate:SF (match_dup 8)))]
15850 "TARGET_USE_FANCY_MATH_387
15851 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15852 && flag_unsafe_math_optimizations"
15856 for (i=2; i<10; i++)
15857 operands[i] = gen_reg_rtx (XFmode);
15858 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */
15861 (define_expand "exp2df2"
15862 [(set (match_dup 2)
15863 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15864 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
15865 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
15866 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
15867 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
15868 (parallel [(set (match_dup 8)
15869 (unspec:XF [(match_dup 7) (match_dup 3)]
15870 UNSPEC_FSCALE_FRACT))
15872 (unspec:XF [(match_dup 7) (match_dup 3)]
15873 UNSPEC_FSCALE_EXP))])
15874 (set (match_operand:DF 0 "register_operand" "")
15875 (float_truncate:DF (match_dup 8)))]
15876 "TARGET_USE_FANCY_MATH_387
15877 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15878 && flag_unsafe_math_optimizations"
15882 for (i=2; i<10; i++)
15883 operands[i] = gen_reg_rtx (XFmode);
15884 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */
15887 (define_expand "exp2xf2"
15888 [(set (match_dup 2) (match_operand:XF 1 "register_operand" ""))
15889 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
15890 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
15891 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
15892 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
15893 (parallel [(set (match_operand:XF 0 "register_operand" "")
15894 (unspec:XF [(match_dup 7) (match_dup 3)]
15895 UNSPEC_FSCALE_FRACT))
15897 (unspec:XF [(match_dup 7) (match_dup 3)]
15898 UNSPEC_FSCALE_EXP))])]
15899 "TARGET_USE_FANCY_MATH_387
15900 && flag_unsafe_math_optimizations"
15904 for (i=2; i<9; i++)
15905 operands[i] = gen_reg_rtx (XFmode);
15906 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */
15909 (define_expand "expm1df2"
15910 [(set (match_dup 2)
15911 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15912 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15913 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15914 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15915 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15916 (parallel [(set (match_dup 8)
15917 (unspec:XF [(match_dup 7) (match_dup 5)]
15918 UNSPEC_FSCALE_FRACT))
15920 (unspec:XF [(match_dup 7) (match_dup 5)]
15921 UNSPEC_FSCALE_EXP))])
15922 (parallel [(set (match_dup 11)
15923 (unspec:XF [(match_dup 10) (match_dup 9)]
15924 UNSPEC_FSCALE_FRACT))
15925 (set (match_dup 12)
15926 (unspec:XF [(match_dup 10) (match_dup 9)]
15927 UNSPEC_FSCALE_EXP))])
15928 (set (match_dup 13) (minus:XF (match_dup 11) (match_dup 10)))
15929 (set (match_dup 14) (plus:XF (match_dup 13) (match_dup 8)))
15930 (set (match_operand:DF 0 "register_operand" "")
15931 (float_truncate:DF (match_dup 14)))]
15932 "TARGET_USE_FANCY_MATH_387
15933 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15934 && flag_unsafe_math_optimizations"
15939 for (i=2; i<15; i++)
15940 operands[i] = gen_reg_rtx (XFmode);
15941 temp = standard_80387_constant_rtx (5); /* fldl2e */
15942 emit_move_insn (operands[3], temp);
15943 emit_move_insn (operands[10], CONST1_RTX (XFmode)); /* fld1 */
15946 (define_expand "expm1sf2"
15947 [(set (match_dup 2)
15948 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15949 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
15950 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
15951 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
15952 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
15953 (parallel [(set (match_dup 8)
15954 (unspec:XF [(match_dup 7) (match_dup 5)]
15955 UNSPEC_FSCALE_FRACT))
15957 (unspec:XF [(match_dup 7) (match_dup 5)]
15958 UNSPEC_FSCALE_EXP))])
15959 (parallel [(set (match_dup 11)
15960 (unspec:XF [(match_dup 10) (match_dup 9)]
15961 UNSPEC_FSCALE_FRACT))
15962 (set (match_dup 12)
15963 (unspec:XF [(match_dup 10) (match_dup 9)]
15964 UNSPEC_FSCALE_EXP))])
15965 (set (match_dup 13) (minus:XF (match_dup 11) (match_dup 10)))
15966 (set (match_dup 14) (plus:XF (match_dup 13) (match_dup 8)))
15967 (set (match_operand:SF 0 "register_operand" "")
15968 (float_truncate:SF (match_dup 14)))]
15969 "TARGET_USE_FANCY_MATH_387
15970 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15971 && flag_unsafe_math_optimizations"
15976 for (i=2; i<15; i++)
15977 operands[i] = gen_reg_rtx (XFmode);
15978 temp = standard_80387_constant_rtx (5); /* fldl2e */
15979 emit_move_insn (operands[3], temp);
15980 emit_move_insn (operands[10], CONST1_RTX (XFmode)); /* fld1 */
15983 (define_expand "expm1xf2"
15984 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
15986 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
15987 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
15988 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
15989 (parallel [(set (match_dup 7)
15990 (unspec:XF [(match_dup 6) (match_dup 4)]
15991 UNSPEC_FSCALE_FRACT))
15993 (unspec:XF [(match_dup 6) (match_dup 4)]
15994 UNSPEC_FSCALE_EXP))])
15995 (parallel [(set (match_dup 10)
15996 (unspec:XF [(match_dup 9) (match_dup 8)]
15997 UNSPEC_FSCALE_FRACT))
15998 (set (match_dup 11)
15999 (unspec:XF [(match_dup 9) (match_dup 8)]
16000 UNSPEC_FSCALE_EXP))])
16001 (set (match_dup 12) (minus:XF (match_dup 10) (match_dup 9)))
16002 (set (match_operand:XF 0 "register_operand" "")
16003 (plus:XF (match_dup 12) (match_dup 7)))]
16004 "TARGET_USE_FANCY_MATH_387
16005 && flag_unsafe_math_optimizations"
16010 for (i=2; i<13; i++)
16011 operands[i] = gen_reg_rtx (XFmode);
16012 temp = standard_80387_constant_rtx (5); /* fldl2e */
16013 emit_move_insn (operands[2], temp);
16014 emit_move_insn (operands[9], CONST1_RTX (XFmode)); /* fld1 */
16017 (define_expand "ldexpdf3"
16018 [(set (match_dup 3)
16019 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16021 (float:XF (match_operand:SI 2 "register_operand" "")))
16022 (parallel [(set (match_dup 5)
16023 (unspec:XF [(match_dup 3) (match_dup 4)]
16024 UNSPEC_FSCALE_FRACT))
16026 (unspec:XF [(match_dup 3) (match_dup 4)]
16027 UNSPEC_FSCALE_EXP))])
16028 (set (match_operand:DF 0 "register_operand" "")
16029 (float_truncate:DF (match_dup 5)))]
16030 "TARGET_USE_FANCY_MATH_387
16031 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16032 && flag_unsafe_math_optimizations"
16036 for (i=3; i<7; i++)
16037 operands[i] = gen_reg_rtx (XFmode);
16040 (define_expand "ldexpsf3"
16041 [(set (match_dup 3)
16042 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16044 (float:XF (match_operand:SI 2 "register_operand" "")))
16045 (parallel [(set (match_dup 5)
16046 (unspec:XF [(match_dup 3) (match_dup 4)]
16047 UNSPEC_FSCALE_FRACT))
16049 (unspec:XF [(match_dup 3) (match_dup 4)]
16050 UNSPEC_FSCALE_EXP))])
16051 (set (match_operand:SF 0 "register_operand" "")
16052 (float_truncate:SF (match_dup 5)))]
16053 "TARGET_USE_FANCY_MATH_387
16054 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16055 && flag_unsafe_math_optimizations"
16059 for (i=3; i<7; i++)
16060 operands[i] = gen_reg_rtx (XFmode);
16063 (define_expand "ldexpxf3"
16064 [(set (match_dup 3)
16065 (float:XF (match_operand:SI 2 "register_operand" "")))
16066 (parallel [(set (match_operand:XF 0 " register_operand" "")
16067 (unspec:XF [(match_operand:XF 1 "register_operand" "")
16069 UNSPEC_FSCALE_FRACT))
16071 (unspec:XF [(match_dup 1) (match_dup 3)]
16072 UNSPEC_FSCALE_EXP))])]
16073 "TARGET_USE_FANCY_MATH_387
16074 && flag_unsafe_math_optimizations"
16078 for (i=3; i<5; i++)
16079 operands[i] = gen_reg_rtx (XFmode);
16083 (define_insn "frndintxf2"
16084 [(set (match_operand:XF 0 "register_operand" "=f")
16085 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16087 "TARGET_USE_FANCY_MATH_387
16088 && flag_unsafe_math_optimizations"
16090 [(set_attr "type" "fpspc")
16091 (set_attr "mode" "XF")])
16093 (define_expand "rintdf2"
16094 [(use (match_operand:DF 0 "register_operand" ""))
16095 (use (match_operand:DF 1 "register_operand" ""))]
16096 "TARGET_USE_FANCY_MATH_387
16097 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16098 && flag_unsafe_math_optimizations"
16100 rtx op0 = gen_reg_rtx (XFmode);
16101 rtx op1 = gen_reg_rtx (XFmode);
16103 emit_insn (gen_extenddfxf2 (op1, operands[1]));
16104 emit_insn (gen_frndintxf2 (op0, op1));
16106 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16110 (define_expand "rintsf2"
16111 [(use (match_operand:SF 0 "register_operand" ""))
16112 (use (match_operand:SF 1 "register_operand" ""))]
16113 "TARGET_USE_FANCY_MATH_387
16114 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16115 && flag_unsafe_math_optimizations"
16117 rtx op0 = gen_reg_rtx (XFmode);
16118 rtx op1 = gen_reg_rtx (XFmode);
16120 emit_insn (gen_extendsfxf2 (op1, operands[1]));
16121 emit_insn (gen_frndintxf2 (op0, op1));
16123 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16127 (define_expand "rintxf2"
16128 [(use (match_operand:XF 0 "register_operand" ""))
16129 (use (match_operand:XF 1 "register_operand" ""))]
16130 "TARGET_USE_FANCY_MATH_387
16131 && flag_unsafe_math_optimizations"
16133 emit_insn (gen_frndintxf2 (operands[0], operands[1]));
16137 (define_insn "fistdi2"
16138 [(set (match_operand:DI 0 "memory_operand" "=m")
16139 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
16141 (clobber (match_scratch:XF 2 "=&1f"))]
16142 "TARGET_USE_FANCY_MATH_387
16143 && flag_unsafe_math_optimizations"
16144 "* return output_fix_trunc (insn, operands, 0);"
16145 [(set_attr "type" "fpspc")
16146 (set_attr "mode" "DI")])
16148 (define_insn "fistdi2_with_temp"
16149 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
16150 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
16152 (clobber (match_operand:DI 2 "memory_operand" "=m,m"))
16153 (clobber (match_scratch:XF 3 "=&1f,&1f"))]
16154 "TARGET_USE_FANCY_MATH_387
16155 && flag_unsafe_math_optimizations"
16157 [(set_attr "type" "fpspc")
16158 (set_attr "mode" "DI")])
16161 [(set (match_operand:DI 0 "register_operand" "")
16162 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16164 (clobber (match_operand:DI 2 "memory_operand" ""))
16165 (clobber (match_scratch 3 ""))]
16167 [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
16168 (clobber (match_dup 3))])
16169 (set (match_dup 0) (match_dup 2))]
16173 [(set (match_operand:DI 0 "memory_operand" "")
16174 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16176 (clobber (match_operand:DI 2 "memory_operand" ""))
16177 (clobber (match_scratch 3 ""))]
16179 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
16180 (clobber (match_dup 3))])]
16183 (define_insn "fist<mode>2"
16184 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
16185 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16187 "TARGET_USE_FANCY_MATH_387
16188 && flag_unsafe_math_optimizations"
16189 "* return output_fix_trunc (insn, operands, 0);"
16190 [(set_attr "type" "fpspc")
16191 (set_attr "mode" "<MODE>")])
16193 (define_insn "fist<mode>2_with_temp"
16194 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
16195 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
16197 (clobber (match_operand:X87MODEI12 2 "memory_operand" "=m,m"))]
16198 "TARGET_USE_FANCY_MATH_387
16199 && flag_unsafe_math_optimizations"
16201 [(set_attr "type" "fpspc")
16202 (set_attr "mode" "<MODE>")])
16205 [(set (match_operand:X87MODEI12 0 "register_operand" "")
16206 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16208 (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
16210 [(set (match_dup 2) (unspec:X87MODEI12 [(match_dup 1)]
16212 (set (match_dup 0) (match_dup 2))]
16216 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
16217 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16219 (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
16221 [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
16225 (define_expand "lrint<mode>2"
16226 [(use (match_operand:X87MODEI 0 "nonimmediate_operand" ""))
16227 (use (match_operand:XF 1 "register_operand" ""))]
16228 "TARGET_USE_FANCY_MATH_387
16229 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16230 && flag_unsafe_math_optimizations"
16232 if (memory_operand (operands[0], VOIDmode))
16233 emit_insn (gen_fist<mode>2 (operands[0], operands[1]));
16236 operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
16237 emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1],
16243 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16244 (define_insn_and_split "frndintxf2_floor"
16245 [(set (match_operand:XF 0 "register_operand" "=f")
16246 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16247 UNSPEC_FRNDINT_FLOOR))
16248 (clobber (reg:CC FLAGS_REG))]
16249 "TARGET_USE_FANCY_MATH_387
16250 && flag_unsafe_math_optimizations
16251 && !(reload_completed || reload_in_progress)"
16256 ix86_optimize_mode_switching[I387_FLOOR] = 1;
16258 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16259 operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
16261 emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1],
16262 operands[2], operands[3]));
16265 [(set_attr "type" "frndint")
16266 (set_attr "i387_cw" "floor")
16267 (set_attr "mode" "XF")])
16269 (define_insn "frndintxf2_floor_i387"
16270 [(set (match_operand:XF 0 "register_operand" "=f")
16271 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16272 UNSPEC_FRNDINT_FLOOR))
16273 (use (match_operand:HI 2 "memory_operand" "m"))
16274 (use (match_operand:HI 3 "memory_operand" "m"))]
16275 "TARGET_USE_FANCY_MATH_387
16276 && flag_unsafe_math_optimizations"
16277 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
16278 [(set_attr "type" "frndint")
16279 (set_attr "i387_cw" "floor")
16280 (set_attr "mode" "XF")])
16282 (define_expand "floorxf2"
16283 [(use (match_operand:XF 0 "register_operand" ""))
16284 (use (match_operand:XF 1 "register_operand" ""))]
16285 "TARGET_USE_FANCY_MATH_387
16286 && flag_unsafe_math_optimizations"
16288 emit_insn (gen_frndintxf2_floor (operands[0], operands[1]));
16292 (define_expand "floordf2"
16293 [(use (match_operand:DF 0 "register_operand" ""))
16294 (use (match_operand:DF 1 "register_operand" ""))]
16295 "TARGET_USE_FANCY_MATH_387
16296 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16297 && flag_unsafe_math_optimizations"
16299 rtx op0 = gen_reg_rtx (XFmode);
16300 rtx op1 = gen_reg_rtx (XFmode);
16302 emit_insn (gen_extenddfxf2 (op1, operands[1]));
16303 emit_insn (gen_frndintxf2_floor (op0, op1));
16305 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16309 (define_expand "floorsf2"
16310 [(use (match_operand:SF 0 "register_operand" ""))
16311 (use (match_operand:SF 1 "register_operand" ""))]
16312 "TARGET_USE_FANCY_MATH_387
16313 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16314 && flag_unsafe_math_optimizations"
16316 rtx op0 = gen_reg_rtx (XFmode);
16317 rtx op1 = gen_reg_rtx (XFmode);
16319 emit_insn (gen_extendsfxf2 (op1, operands[1]));
16320 emit_insn (gen_frndintxf2_floor (op0, op1));
16322 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16326 (define_insn_and_split "*fist<mode>2_floor_1"
16327 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
16328 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "f,f")]
16329 UNSPEC_FIST_FLOOR))
16330 (clobber (reg:CC FLAGS_REG))]
16331 "TARGET_USE_FANCY_MATH_387
16332 && flag_unsafe_math_optimizations
16333 && !(reload_completed || reload_in_progress)"
16338 ix86_optimize_mode_switching[I387_FLOOR] = 1;
16340 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16341 operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
16342 if (memory_operand (operands[0], VOIDmode))
16343 emit_insn (gen_fist<mode>2_floor (operands[0], operands[1],
16344 operands[2], operands[3]));
16347 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
16348 emit_insn (gen_fist<mode>2_floor_with_temp (operands[0], operands[1],
16349 operands[2], operands[3],
16354 [(set_attr "type" "fistp")
16355 (set_attr "i387_cw" "floor")
16356 (set_attr "mode" "<MODE>")])
16358 (define_insn "fistdi2_floor"
16359 [(set (match_operand:DI 0 "memory_operand" "=m")
16360 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
16361 UNSPEC_FIST_FLOOR))
16362 (use (match_operand:HI 2 "memory_operand" "m"))
16363 (use (match_operand:HI 3 "memory_operand" "m"))
16364 (clobber (match_scratch:XF 4 "=&1f"))]
16365 "TARGET_USE_FANCY_MATH_387
16366 && flag_unsafe_math_optimizations"
16367 "* return output_fix_trunc (insn, operands, 0);"
16368 [(set_attr "type" "fistp")
16369 (set_attr "i387_cw" "floor")
16370 (set_attr "mode" "DI")])
16372 (define_insn "fistdi2_floor_with_temp"
16373 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
16374 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
16375 UNSPEC_FIST_FLOOR))
16376 (use (match_operand:HI 2 "memory_operand" "m,m"))
16377 (use (match_operand:HI 3 "memory_operand" "m,m"))
16378 (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
16379 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
16380 "TARGET_USE_FANCY_MATH_387
16381 && flag_unsafe_math_optimizations"
16383 [(set_attr "type" "fistp")
16384 (set_attr "i387_cw" "floor")
16385 (set_attr "mode" "DI")])
16388 [(set (match_operand:DI 0 "register_operand" "")
16389 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16390 UNSPEC_FIST_FLOOR))
16391 (use (match_operand:HI 2 "memory_operand" ""))
16392 (use (match_operand:HI 3 "memory_operand" ""))
16393 (clobber (match_operand:DI 4 "memory_operand" ""))
16394 (clobber (match_scratch 5 ""))]
16396 [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
16397 (use (match_dup 2))
16398 (use (match_dup 3))
16399 (clobber (match_dup 5))])
16400 (set (match_dup 0) (match_dup 4))]
16404 [(set (match_operand:DI 0 "memory_operand" "")
16405 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16406 UNSPEC_FIST_FLOOR))
16407 (use (match_operand:HI 2 "memory_operand" ""))
16408 (use (match_operand:HI 3 "memory_operand" ""))
16409 (clobber (match_operand:DI 4 "memory_operand" ""))
16410 (clobber (match_scratch 5 ""))]
16412 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
16413 (use (match_dup 2))
16414 (use (match_dup 3))
16415 (clobber (match_dup 5))])]
16418 (define_insn "fist<mode>2_floor"
16419 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
16420 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16421 UNSPEC_FIST_FLOOR))
16422 (use (match_operand:HI 2 "memory_operand" "m"))
16423 (use (match_operand:HI 3 "memory_operand" "m"))]
16424 "TARGET_USE_FANCY_MATH_387
16425 && flag_unsafe_math_optimizations"
16426 "* return output_fix_trunc (insn, operands, 0);"
16427 [(set_attr "type" "fistp")
16428 (set_attr "i387_cw" "floor")
16429 (set_attr "mode" "<MODE>")])
16431 (define_insn "fist<mode>2_floor_with_temp"
16432 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
16433 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
16434 UNSPEC_FIST_FLOOR))
16435 (use (match_operand:HI 2 "memory_operand" "m,m"))
16436 (use (match_operand:HI 3 "memory_operand" "m,m"))
16437 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
16438 "TARGET_USE_FANCY_MATH_387
16439 && flag_unsafe_math_optimizations"
16441 [(set_attr "type" "fistp")
16442 (set_attr "i387_cw" "floor")
16443 (set_attr "mode" "<MODE>")])
16446 [(set (match_operand:X87MODEI12 0 "register_operand" "")
16447 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16448 UNSPEC_FIST_FLOOR))
16449 (use (match_operand:HI 2 "memory_operand" ""))
16450 (use (match_operand:HI 3 "memory_operand" ""))
16451 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
16453 [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
16454 UNSPEC_FIST_FLOOR))
16455 (use (match_dup 2))
16456 (use (match_dup 3))])
16457 (set (match_dup 0) (match_dup 4))]
16461 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
16462 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16463 UNSPEC_FIST_FLOOR))
16464 (use (match_operand:HI 2 "memory_operand" ""))
16465 (use (match_operand:HI 3 "memory_operand" ""))
16466 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
16468 [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
16469 UNSPEC_FIST_FLOOR))
16470 (use (match_dup 2))
16471 (use (match_dup 3))])]
16474 (define_expand "lfloor<mode>2"
16475 [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
16476 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
16477 UNSPEC_FIST_FLOOR))
16478 (clobber (reg:CC FLAGS_REG))])]
16479 "TARGET_USE_FANCY_MATH_387
16480 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16481 && flag_unsafe_math_optimizations"
16484 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16485 (define_insn_and_split "frndintxf2_ceil"
16486 [(set (match_operand:XF 0 "register_operand" "=f")
16487 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16488 UNSPEC_FRNDINT_CEIL))
16489 (clobber (reg:CC FLAGS_REG))]
16490 "TARGET_USE_FANCY_MATH_387
16491 && flag_unsafe_math_optimizations
16492 && !(reload_completed || reload_in_progress)"
16497 ix86_optimize_mode_switching[I387_CEIL] = 1;
16499 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16500 operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
16502 emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1],
16503 operands[2], operands[3]));
16506 [(set_attr "type" "frndint")
16507 (set_attr "i387_cw" "ceil")
16508 (set_attr "mode" "XF")])
16510 (define_insn "frndintxf2_ceil_i387"
16511 [(set (match_operand:XF 0 "register_operand" "=f")
16512 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16513 UNSPEC_FRNDINT_CEIL))
16514 (use (match_operand:HI 2 "memory_operand" "m"))
16515 (use (match_operand:HI 3 "memory_operand" "m"))]
16516 "TARGET_USE_FANCY_MATH_387
16517 && flag_unsafe_math_optimizations"
16518 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
16519 [(set_attr "type" "frndint")
16520 (set_attr "i387_cw" "ceil")
16521 (set_attr "mode" "XF")])
16523 (define_expand "ceilxf2"
16524 [(use (match_operand:XF 0 "register_operand" ""))
16525 (use (match_operand:XF 1 "register_operand" ""))]
16526 "TARGET_USE_FANCY_MATH_387
16527 && flag_unsafe_math_optimizations"
16529 emit_insn (gen_frndintxf2_ceil (operands[0], operands[1]));
16533 (define_expand "ceildf2"
16534 [(use (match_operand:DF 0 "register_operand" ""))
16535 (use (match_operand:DF 1 "register_operand" ""))]
16536 "TARGET_USE_FANCY_MATH_387
16537 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16538 && flag_unsafe_math_optimizations"
16540 rtx op0 = gen_reg_rtx (XFmode);
16541 rtx op1 = gen_reg_rtx (XFmode);
16543 emit_insn (gen_extenddfxf2 (op1, operands[1]));
16544 emit_insn (gen_frndintxf2_ceil (op0, op1));
16546 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16550 (define_expand "ceilsf2"
16551 [(use (match_operand:SF 0 "register_operand" ""))
16552 (use (match_operand:SF 1 "register_operand" ""))]
16553 "TARGET_USE_FANCY_MATH_387
16554 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16555 && flag_unsafe_math_optimizations"
16557 rtx op0 = gen_reg_rtx (XFmode);
16558 rtx op1 = gen_reg_rtx (XFmode);
16560 emit_insn (gen_extendsfxf2 (op1, operands[1]));
16561 emit_insn (gen_frndintxf2_ceil (op0, op1));
16563 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16567 (define_insn_and_split "*fist<mode>2_ceil_1"
16568 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
16569 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "f,f")]
16571 (clobber (reg:CC FLAGS_REG))]
16572 "TARGET_USE_FANCY_MATH_387
16573 && flag_unsafe_math_optimizations
16574 && !(reload_completed || reload_in_progress)"
16579 ix86_optimize_mode_switching[I387_CEIL] = 1;
16581 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16582 operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
16583 if (memory_operand (operands[0], VOIDmode))
16584 emit_insn (gen_fist<mode>2_ceil (operands[0], operands[1],
16585 operands[2], operands[3]));
16588 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
16589 emit_insn (gen_fist<mode>2_ceil_with_temp (operands[0], operands[1],
16590 operands[2], operands[3],
16595 [(set_attr "type" "fistp")
16596 (set_attr "i387_cw" "ceil")
16597 (set_attr "mode" "<MODE>")])
16599 (define_insn "fistdi2_ceil"
16600 [(set (match_operand:DI 0 "memory_operand" "=m")
16601 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
16603 (use (match_operand:HI 2 "memory_operand" "m"))
16604 (use (match_operand:HI 3 "memory_operand" "m"))
16605 (clobber (match_scratch:XF 4 "=&1f"))]
16606 "TARGET_USE_FANCY_MATH_387
16607 && flag_unsafe_math_optimizations"
16608 "* return output_fix_trunc (insn, operands, 0);"
16609 [(set_attr "type" "fistp")
16610 (set_attr "i387_cw" "ceil")
16611 (set_attr "mode" "DI")])
16613 (define_insn "fistdi2_ceil_with_temp"
16614 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
16615 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
16617 (use (match_operand:HI 2 "memory_operand" "m,m"))
16618 (use (match_operand:HI 3 "memory_operand" "m,m"))
16619 (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
16620 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
16621 "TARGET_USE_FANCY_MATH_387
16622 && flag_unsafe_math_optimizations"
16624 [(set_attr "type" "fistp")
16625 (set_attr "i387_cw" "ceil")
16626 (set_attr "mode" "DI")])
16629 [(set (match_operand:DI 0 "register_operand" "")
16630 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16632 (use (match_operand:HI 2 "memory_operand" ""))
16633 (use (match_operand:HI 3 "memory_operand" ""))
16634 (clobber (match_operand:DI 4 "memory_operand" ""))
16635 (clobber (match_scratch 5 ""))]
16637 [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
16638 (use (match_dup 2))
16639 (use (match_dup 3))
16640 (clobber (match_dup 5))])
16641 (set (match_dup 0) (match_dup 4))]
16645 [(set (match_operand:DI 0 "memory_operand" "")
16646 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16648 (use (match_operand:HI 2 "memory_operand" ""))
16649 (use (match_operand:HI 3 "memory_operand" ""))
16650 (clobber (match_operand:DI 4 "memory_operand" ""))
16651 (clobber (match_scratch 5 ""))]
16653 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
16654 (use (match_dup 2))
16655 (use (match_dup 3))
16656 (clobber (match_dup 5))])]
16659 (define_insn "fist<mode>2_ceil"
16660 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
16661 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16663 (use (match_operand:HI 2 "memory_operand" "m"))
16664 (use (match_operand:HI 3 "memory_operand" "m"))]
16665 "TARGET_USE_FANCY_MATH_387
16666 && flag_unsafe_math_optimizations"
16667 "* return output_fix_trunc (insn, operands, 0);"
16668 [(set_attr "type" "fistp")
16669 (set_attr "i387_cw" "ceil")
16670 (set_attr "mode" "<MODE>")])
16672 (define_insn "fist<mode>2_ceil_with_temp"
16673 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
16674 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
16676 (use (match_operand:HI 2 "memory_operand" "m,m"))
16677 (use (match_operand:HI 3 "memory_operand" "m,m"))
16678 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
16679 "TARGET_USE_FANCY_MATH_387
16680 && flag_unsafe_math_optimizations"
16682 [(set_attr "type" "fistp")
16683 (set_attr "i387_cw" "ceil")
16684 (set_attr "mode" "<MODE>")])
16687 [(set (match_operand:X87MODEI12 0 "register_operand" "")
16688 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16690 (use (match_operand:HI 2 "memory_operand" ""))
16691 (use (match_operand:HI 3 "memory_operand" ""))
16692 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
16694 [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
16696 (use (match_dup 2))
16697 (use (match_dup 3))])
16698 (set (match_dup 0) (match_dup 4))]
16702 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
16703 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16705 (use (match_operand:HI 2 "memory_operand" ""))
16706 (use (match_operand:HI 3 "memory_operand" ""))
16707 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
16709 [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
16711 (use (match_dup 2))
16712 (use (match_dup 3))])]
16715 (define_expand "lceil<mode>2"
16716 [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
16717 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
16719 (clobber (reg:CC FLAGS_REG))])]
16720 "TARGET_USE_FANCY_MATH_387
16721 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16722 && flag_unsafe_math_optimizations"
16725 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16726 (define_insn_and_split "frndintxf2_trunc"
16727 [(set (match_operand:XF 0 "register_operand" "=f")
16728 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16729 UNSPEC_FRNDINT_TRUNC))
16730 (clobber (reg:CC FLAGS_REG))]
16731 "TARGET_USE_FANCY_MATH_387
16732 && flag_unsafe_math_optimizations
16733 && !(reload_completed || reload_in_progress)"
16738 ix86_optimize_mode_switching[I387_TRUNC] = 1;
16740 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16741 operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
16743 emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1],
16744 operands[2], operands[3]));
16747 [(set_attr "type" "frndint")
16748 (set_attr "i387_cw" "trunc")
16749 (set_attr "mode" "XF")])
16751 (define_insn "frndintxf2_trunc_i387"
16752 [(set (match_operand:XF 0 "register_operand" "=f")
16753 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16754 UNSPEC_FRNDINT_TRUNC))
16755 (use (match_operand:HI 2 "memory_operand" "m"))
16756 (use (match_operand:HI 3 "memory_operand" "m"))]
16757 "TARGET_USE_FANCY_MATH_387
16758 && flag_unsafe_math_optimizations"
16759 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
16760 [(set_attr "type" "frndint")
16761 (set_attr "i387_cw" "trunc")
16762 (set_attr "mode" "XF")])
16764 (define_expand "btruncxf2"
16765 [(use (match_operand:XF 0 "register_operand" ""))
16766 (use (match_operand:XF 1 "register_operand" ""))]
16767 "TARGET_USE_FANCY_MATH_387
16768 && flag_unsafe_math_optimizations"
16770 emit_insn (gen_frndintxf2_trunc (operands[0], operands[1]));
16774 (define_expand "btruncdf2"
16775 [(use (match_operand:DF 0 "register_operand" ""))
16776 (use (match_operand:DF 1 "register_operand" ""))]
16777 "TARGET_USE_FANCY_MATH_387
16778 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16779 && flag_unsafe_math_optimizations"
16781 rtx op0 = gen_reg_rtx (XFmode);
16782 rtx op1 = gen_reg_rtx (XFmode);
16784 emit_insn (gen_extenddfxf2 (op1, operands[1]));
16785 emit_insn (gen_frndintxf2_trunc (op0, op1));
16787 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16791 (define_expand "btruncsf2"
16792 [(use (match_operand:SF 0 "register_operand" ""))
16793 (use (match_operand:SF 1 "register_operand" ""))]
16794 "TARGET_USE_FANCY_MATH_387
16795 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16796 && flag_unsafe_math_optimizations"
16798 rtx op0 = gen_reg_rtx (XFmode);
16799 rtx op1 = gen_reg_rtx (XFmode);
16801 emit_insn (gen_extendsfxf2 (op1, operands[1]));
16802 emit_insn (gen_frndintxf2_trunc (op0, op1));
16804 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16808 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16809 (define_insn_and_split "frndintxf2_mask_pm"
16810 [(set (match_operand:XF 0 "register_operand" "=f")
16811 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16812 UNSPEC_FRNDINT_MASK_PM))
16813 (clobber (reg:CC FLAGS_REG))]
16814 "TARGET_USE_FANCY_MATH_387
16815 && flag_unsafe_math_optimizations
16816 && !(reload_completed || reload_in_progress)"
16821 ix86_optimize_mode_switching[I387_MASK_PM] = 1;
16823 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16824 operands[3] = assign_386_stack_local (HImode, SLOT_CW_MASK_PM);
16826 emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1],
16827 operands[2], operands[3]));
16830 [(set_attr "type" "frndint")
16831 (set_attr "i387_cw" "mask_pm")
16832 (set_attr "mode" "XF")])
16834 (define_insn "frndintxf2_mask_pm_i387"
16835 [(set (match_operand:XF 0 "register_operand" "=f")
16836 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16837 UNSPEC_FRNDINT_MASK_PM))
16838 (use (match_operand:HI 2 "memory_operand" "m"))
16839 (use (match_operand:HI 3 "memory_operand" "m"))]
16840 "TARGET_USE_FANCY_MATH_387
16841 && flag_unsafe_math_optimizations"
16842 "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2"
16843 [(set_attr "type" "frndint")
16844 (set_attr "i387_cw" "mask_pm")
16845 (set_attr "mode" "XF")])
16847 (define_expand "nearbyintxf2"
16848 [(use (match_operand:XF 0 "register_operand" ""))
16849 (use (match_operand:XF 1 "register_operand" ""))]
16850 "TARGET_USE_FANCY_MATH_387
16851 && flag_unsafe_math_optimizations"
16853 emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1]));
16858 (define_expand "nearbyintdf2"
16859 [(use (match_operand:DF 0 "register_operand" ""))
16860 (use (match_operand:DF 1 "register_operand" ""))]
16861 "TARGET_USE_FANCY_MATH_387
16862 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16863 && flag_unsafe_math_optimizations"
16865 rtx op0 = gen_reg_rtx (XFmode);
16866 rtx op1 = gen_reg_rtx (XFmode);
16868 emit_insn (gen_extenddfxf2 (op1, operands[1]));
16869 emit_insn (gen_frndintxf2_mask_pm (op0, op1));
16871 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16875 (define_expand "nearbyintsf2"
16876 [(use (match_operand:SF 0 "register_operand" ""))
16877 (use (match_operand:SF 1 "register_operand" ""))]
16878 "TARGET_USE_FANCY_MATH_387
16879 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16880 && flag_unsafe_math_optimizations"
16882 rtx op0 = gen_reg_rtx (XFmode);
16883 rtx op1 = gen_reg_rtx (XFmode);
16885 emit_insn (gen_extendsfxf2 (op1, operands[1]));
16886 emit_insn (gen_frndintxf2_mask_pm (op0, op1));
16888 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16893 ;; Block operation instructions
16896 [(set (reg:SI DIRFLAG_REG) (const_int 0))]
16899 [(set_attr "type" "cld")])
16901 (define_expand "movmemsi"
16902 [(use (match_operand:BLK 0 "memory_operand" ""))
16903 (use (match_operand:BLK 1 "memory_operand" ""))
16904 (use (match_operand:SI 2 "nonmemory_operand" ""))
16905 (use (match_operand:SI 3 "const_int_operand" ""))]
16906 "! optimize_size || TARGET_INLINE_ALL_STRINGOPS"
16908 if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3]))
16914 (define_expand "movmemdi"
16915 [(use (match_operand:BLK 0 "memory_operand" ""))
16916 (use (match_operand:BLK 1 "memory_operand" ""))
16917 (use (match_operand:DI 2 "nonmemory_operand" ""))
16918 (use (match_operand:DI 3 "const_int_operand" ""))]
16921 if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3]))
16927 ;; Most CPUs don't like single string operations
16928 ;; Handle this case here to simplify previous expander.
16930 (define_expand "strmov"
16931 [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
16932 (set (match_operand 1 "memory_operand" "") (match_dup 4))
16933 (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
16934 (clobber (reg:CC FLAGS_REG))])
16935 (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
16936 (clobber (reg:CC FLAGS_REG))])]
16939 rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
16941 /* If .md ever supports :P for Pmode, these can be directly
16942 in the pattern above. */
16943 operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
16944 operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
16946 if (TARGET_SINGLE_STRINGOP || optimize_size)
16948 emit_insn (gen_strmov_singleop (operands[0], operands[1],
16949 operands[2], operands[3],
16950 operands[5], operands[6]));
16954 operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
16957 (define_expand "strmov_singleop"
16958 [(parallel [(set (match_operand 1 "memory_operand" "")
16959 (match_operand 3 "memory_operand" ""))
16960 (set (match_operand 0 "register_operand" "")
16961 (match_operand 4 "" ""))
16962 (set (match_operand 2 "register_operand" "")
16963 (match_operand 5 "" ""))
16964 (use (reg:SI DIRFLAG_REG))])]
16965 "TARGET_SINGLE_STRINGOP || optimize_size"
16968 (define_insn "*strmovdi_rex_1"
16969 [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
16970 (mem:DI (match_operand:DI 3 "register_operand" "1")))
16971 (set (match_operand:DI 0 "register_operand" "=D")
16972 (plus:DI (match_dup 2)
16974 (set (match_operand:DI 1 "register_operand" "=S")
16975 (plus:DI (match_dup 3)
16977 (use (reg:SI DIRFLAG_REG))]
16978 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
16980 [(set_attr "type" "str")
16981 (set_attr "mode" "DI")
16982 (set_attr "memory" "both")])
16984 (define_insn "*strmovsi_1"
16985 [(set (mem:SI (match_operand:SI 2 "register_operand" "0"))
16986 (mem:SI (match_operand:SI 3 "register_operand" "1")))
16987 (set (match_operand:SI 0 "register_operand" "=D")
16988 (plus:SI (match_dup 2)
16990 (set (match_operand:SI 1 "register_operand" "=S")
16991 (plus:SI (match_dup 3)
16993 (use (reg:SI DIRFLAG_REG))]
16994 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
16996 [(set_attr "type" "str")
16997 (set_attr "mode" "SI")
16998 (set_attr "memory" "both")])
17000 (define_insn "*strmovsi_rex_1"
17001 [(set (mem:SI (match_operand:DI 2 "register_operand" "0"))
17002 (mem:SI (match_operand:DI 3 "register_operand" "1")))
17003 (set (match_operand:DI 0 "register_operand" "=D")
17004 (plus:DI (match_dup 2)
17006 (set (match_operand:DI 1 "register_operand" "=S")
17007 (plus:DI (match_dup 3)
17009 (use (reg:SI DIRFLAG_REG))]
17010 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17012 [(set_attr "type" "str")
17013 (set_attr "mode" "SI")
17014 (set_attr "memory" "both")])
17016 (define_insn "*strmovhi_1"
17017 [(set (mem:HI (match_operand:SI 2 "register_operand" "0"))
17018 (mem:HI (match_operand:SI 3 "register_operand" "1")))
17019 (set (match_operand:SI 0 "register_operand" "=D")
17020 (plus:SI (match_dup 2)
17022 (set (match_operand:SI 1 "register_operand" "=S")
17023 (plus:SI (match_dup 3)
17025 (use (reg:SI DIRFLAG_REG))]
17026 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17028 [(set_attr "type" "str")
17029 (set_attr "memory" "both")
17030 (set_attr "mode" "HI")])
17032 (define_insn "*strmovhi_rex_1"
17033 [(set (mem:HI (match_operand:DI 2 "register_operand" "0"))
17034 (mem:HI (match_operand:DI 3 "register_operand" "1")))
17035 (set (match_operand:DI 0 "register_operand" "=D")
17036 (plus:DI (match_dup 2)
17038 (set (match_operand:DI 1 "register_operand" "=S")
17039 (plus:DI (match_dup 3)
17041 (use (reg:SI DIRFLAG_REG))]
17042 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17044 [(set_attr "type" "str")
17045 (set_attr "memory" "both")
17046 (set_attr "mode" "HI")])
17048 (define_insn "*strmovqi_1"
17049 [(set (mem:QI (match_operand:SI 2 "register_operand" "0"))
17050 (mem:QI (match_operand:SI 3 "register_operand" "1")))
17051 (set (match_operand:SI 0 "register_operand" "=D")
17052 (plus:SI (match_dup 2)
17054 (set (match_operand:SI 1 "register_operand" "=S")
17055 (plus:SI (match_dup 3)
17057 (use (reg:SI DIRFLAG_REG))]
17058 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17060 [(set_attr "type" "str")
17061 (set_attr "memory" "both")
17062 (set_attr "mode" "QI")])
17064 (define_insn "*strmovqi_rex_1"
17065 [(set (mem:QI (match_operand:DI 2 "register_operand" "0"))
17066 (mem:QI (match_operand:DI 3 "register_operand" "1")))
17067 (set (match_operand:DI 0 "register_operand" "=D")
17068 (plus:DI (match_dup 2)
17070 (set (match_operand:DI 1 "register_operand" "=S")
17071 (plus:DI (match_dup 3)
17073 (use (reg:SI DIRFLAG_REG))]
17074 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17076 [(set_attr "type" "str")
17077 (set_attr "memory" "both")
17078 (set_attr "mode" "QI")])
17080 (define_expand "rep_mov"
17081 [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
17082 (set (match_operand 0 "register_operand" "")
17083 (match_operand 5 "" ""))
17084 (set (match_operand 2 "register_operand" "")
17085 (match_operand 6 "" ""))
17086 (set (match_operand 1 "memory_operand" "")
17087 (match_operand 3 "memory_operand" ""))
17088 (use (match_dup 4))
17089 (use (reg:SI DIRFLAG_REG))])]
17093 (define_insn "*rep_movdi_rex64"
17094 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
17095 (set (match_operand:DI 0 "register_operand" "=D")
17096 (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
17098 (match_operand:DI 3 "register_operand" "0")))
17099 (set (match_operand:DI 1 "register_operand" "=S")
17100 (plus:DI (ashift:DI (match_dup 5) (const_int 3))
17101 (match_operand:DI 4 "register_operand" "1")))
17102 (set (mem:BLK (match_dup 3))
17103 (mem:BLK (match_dup 4)))
17104 (use (match_dup 5))
17105 (use (reg:SI DIRFLAG_REG))]
17107 "{rep\;movsq|rep movsq}"
17108 [(set_attr "type" "str")
17109 (set_attr "prefix_rep" "1")
17110 (set_attr "memory" "both")
17111 (set_attr "mode" "DI")])
17113 (define_insn "*rep_movsi"
17114 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
17115 (set (match_operand:SI 0 "register_operand" "=D")
17116 (plus:SI (ashift:SI (match_operand:SI 5 "register_operand" "2")
17118 (match_operand:SI 3 "register_operand" "0")))
17119 (set (match_operand:SI 1 "register_operand" "=S")
17120 (plus:SI (ashift:SI (match_dup 5) (const_int 2))
17121 (match_operand:SI 4 "register_operand" "1")))
17122 (set (mem:BLK (match_dup 3))
17123 (mem:BLK (match_dup 4)))
17124 (use (match_dup 5))
17125 (use (reg:SI DIRFLAG_REG))]
17127 "{rep\;movsl|rep movsd}"
17128 [(set_attr "type" "str")
17129 (set_attr "prefix_rep" "1")
17130 (set_attr "memory" "both")
17131 (set_attr "mode" "SI")])
17133 (define_insn "*rep_movsi_rex64"
17134 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
17135 (set (match_operand:DI 0 "register_operand" "=D")
17136 (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
17138 (match_operand:DI 3 "register_operand" "0")))
17139 (set (match_operand:DI 1 "register_operand" "=S")
17140 (plus:DI (ashift:DI (match_dup 5) (const_int 2))
17141 (match_operand:DI 4 "register_operand" "1")))
17142 (set (mem:BLK (match_dup 3))
17143 (mem:BLK (match_dup 4)))
17144 (use (match_dup 5))
17145 (use (reg:SI DIRFLAG_REG))]
17147 "{rep\;movsl|rep movsd}"
17148 [(set_attr "type" "str")
17149 (set_attr "prefix_rep" "1")
17150 (set_attr "memory" "both")
17151 (set_attr "mode" "SI")])
17153 (define_insn "*rep_movqi"
17154 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
17155 (set (match_operand:SI 0 "register_operand" "=D")
17156 (plus:SI (match_operand:SI 3 "register_operand" "0")
17157 (match_operand:SI 5 "register_operand" "2")))
17158 (set (match_operand:SI 1 "register_operand" "=S")
17159 (plus:SI (match_operand:SI 4 "register_operand" "1") (match_dup 5)))
17160 (set (mem:BLK (match_dup 3))
17161 (mem:BLK (match_dup 4)))
17162 (use (match_dup 5))
17163 (use (reg:SI DIRFLAG_REG))]
17165 "{rep\;movsb|rep movsb}"
17166 [(set_attr "type" "str")
17167 (set_attr "prefix_rep" "1")
17168 (set_attr "memory" "both")
17169 (set_attr "mode" "SI")])
17171 (define_insn "*rep_movqi_rex64"
17172 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
17173 (set (match_operand:DI 0 "register_operand" "=D")
17174 (plus:DI (match_operand:DI 3 "register_operand" "0")
17175 (match_operand:DI 5 "register_operand" "2")))
17176 (set (match_operand:DI 1 "register_operand" "=S")
17177 (plus:DI (match_operand:DI 4 "register_operand" "1") (match_dup 5)))
17178 (set (mem:BLK (match_dup 3))
17179 (mem:BLK (match_dup 4)))
17180 (use (match_dup 5))
17181 (use (reg:SI DIRFLAG_REG))]
17183 "{rep\;movsb|rep movsb}"
17184 [(set_attr "type" "str")
17185 (set_attr "prefix_rep" "1")
17186 (set_attr "memory" "both")
17187 (set_attr "mode" "SI")])
17189 (define_expand "setmemsi"
17190 [(use (match_operand:BLK 0 "memory_operand" ""))
17191 (use (match_operand:SI 1 "nonmemory_operand" ""))
17192 (use (match_operand 2 "const_int_operand" ""))
17193 (use (match_operand 3 "const_int_operand" ""))]
17196 /* If value to set is not zero, use the library routine. */
17197 if (operands[2] != const0_rtx)
17200 if (ix86_expand_clrmem (operands[0], operands[1], operands[3]))
17206 (define_expand "setmemdi"
17207 [(use (match_operand:BLK 0 "memory_operand" ""))
17208 (use (match_operand:DI 1 "nonmemory_operand" ""))
17209 (use (match_operand 2 "const_int_operand" ""))
17210 (use (match_operand 3 "const_int_operand" ""))]
17213 /* If value to set is not zero, use the library routine. */
17214 if (operands[2] != const0_rtx)
17217 if (ix86_expand_clrmem (operands[0], operands[1], operands[3]))
17223 ;; Most CPUs don't like single string operations
17224 ;; Handle this case here to simplify previous expander.
17226 (define_expand "strset"
17227 [(set (match_operand 1 "memory_operand" "")
17228 (match_operand 2 "register_operand" ""))
17229 (parallel [(set (match_operand 0 "register_operand" "")
17231 (clobber (reg:CC FLAGS_REG))])]
17234 if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
17235 operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
17237 /* If .md ever supports :P for Pmode, this can be directly
17238 in the pattern above. */
17239 operands[3] = gen_rtx_PLUS (Pmode, operands[0],
17240 GEN_INT (GET_MODE_SIZE (GET_MODE
17242 if (TARGET_SINGLE_STRINGOP || optimize_size)
17244 emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
17250 (define_expand "strset_singleop"
17251 [(parallel [(set (match_operand 1 "memory_operand" "")
17252 (match_operand 2 "register_operand" ""))
17253 (set (match_operand 0 "register_operand" "")
17254 (match_operand 3 "" ""))
17255 (use (reg:SI DIRFLAG_REG))])]
17256 "TARGET_SINGLE_STRINGOP || optimize_size"
17259 (define_insn "*strsetdi_rex_1"
17260 [(set (mem:DI (match_operand:DI 1 "register_operand" "0"))
17261 (match_operand:DI 2 "register_operand" "a"))
17262 (set (match_operand:DI 0 "register_operand" "=D")
17263 (plus:DI (match_dup 1)
17265 (use (reg:SI DIRFLAG_REG))]
17266 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17268 [(set_attr "type" "str")
17269 (set_attr "memory" "store")
17270 (set_attr "mode" "DI")])
17272 (define_insn "*strsetsi_1"
17273 [(set (mem:SI (match_operand:SI 1 "register_operand" "0"))
17274 (match_operand:SI 2 "register_operand" "a"))
17275 (set (match_operand:SI 0 "register_operand" "=D")
17276 (plus:SI (match_dup 1)
17278 (use (reg:SI DIRFLAG_REG))]
17279 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17281 [(set_attr "type" "str")
17282 (set_attr "memory" "store")
17283 (set_attr "mode" "SI")])
17285 (define_insn "*strsetsi_rex_1"
17286 [(set (mem:SI (match_operand:DI 1 "register_operand" "0"))
17287 (match_operand:SI 2 "register_operand" "a"))
17288 (set (match_operand:DI 0 "register_operand" "=D")
17289 (plus:DI (match_dup 1)
17291 (use (reg:SI DIRFLAG_REG))]
17292 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17294 [(set_attr "type" "str")
17295 (set_attr "memory" "store")
17296 (set_attr "mode" "SI")])
17298 (define_insn "*strsethi_1"
17299 [(set (mem:HI (match_operand:SI 1 "register_operand" "0"))
17300 (match_operand:HI 2 "register_operand" "a"))
17301 (set (match_operand:SI 0 "register_operand" "=D")
17302 (plus:SI (match_dup 1)
17304 (use (reg:SI DIRFLAG_REG))]
17305 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17307 [(set_attr "type" "str")
17308 (set_attr "memory" "store")
17309 (set_attr "mode" "HI")])
17311 (define_insn "*strsethi_rex_1"
17312 [(set (mem:HI (match_operand:DI 1 "register_operand" "0"))
17313 (match_operand:HI 2 "register_operand" "a"))
17314 (set (match_operand:DI 0 "register_operand" "=D")
17315 (plus:DI (match_dup 1)
17317 (use (reg:SI DIRFLAG_REG))]
17318 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17320 [(set_attr "type" "str")
17321 (set_attr "memory" "store")
17322 (set_attr "mode" "HI")])
17324 (define_insn "*strsetqi_1"
17325 [(set (mem:QI (match_operand:SI 1 "register_operand" "0"))
17326 (match_operand:QI 2 "register_operand" "a"))
17327 (set (match_operand:SI 0 "register_operand" "=D")
17328 (plus:SI (match_dup 1)
17330 (use (reg:SI DIRFLAG_REG))]
17331 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17333 [(set_attr "type" "str")
17334 (set_attr "memory" "store")
17335 (set_attr "mode" "QI")])
17337 (define_insn "*strsetqi_rex_1"
17338 [(set (mem:QI (match_operand:DI 1 "register_operand" "0"))
17339 (match_operand:QI 2 "register_operand" "a"))
17340 (set (match_operand:DI 0 "register_operand" "=D")
17341 (plus:DI (match_dup 1)
17343 (use (reg:SI DIRFLAG_REG))]
17344 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17346 [(set_attr "type" "str")
17347 (set_attr "memory" "store")
17348 (set_attr "mode" "QI")])
17350 (define_expand "rep_stos"
17351 [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
17352 (set (match_operand 0 "register_operand" "")
17353 (match_operand 4 "" ""))
17354 (set (match_operand 2 "memory_operand" "") (const_int 0))
17355 (use (match_operand 3 "register_operand" ""))
17356 (use (match_dup 1))
17357 (use (reg:SI DIRFLAG_REG))])]
17361 (define_insn "*rep_stosdi_rex64"
17362 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17363 (set (match_operand:DI 0 "register_operand" "=D")
17364 (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
17366 (match_operand:DI 3 "register_operand" "0")))
17367 (set (mem:BLK (match_dup 3))
17369 (use (match_operand:DI 2 "register_operand" "a"))
17370 (use (match_dup 4))
17371 (use (reg:SI DIRFLAG_REG))]
17373 "{rep\;stosq|rep stosq}"
17374 [(set_attr "type" "str")
17375 (set_attr "prefix_rep" "1")
17376 (set_attr "memory" "store")
17377 (set_attr "mode" "DI")])
17379 (define_insn "*rep_stossi"
17380 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
17381 (set (match_operand:SI 0 "register_operand" "=D")
17382 (plus:SI (ashift:SI (match_operand:SI 4 "register_operand" "1")
17384 (match_operand:SI 3 "register_operand" "0")))
17385 (set (mem:BLK (match_dup 3))
17387 (use (match_operand:SI 2 "register_operand" "a"))
17388 (use (match_dup 4))
17389 (use (reg:SI DIRFLAG_REG))]
17391 "{rep\;stosl|rep stosd}"
17392 [(set_attr "type" "str")
17393 (set_attr "prefix_rep" "1")
17394 (set_attr "memory" "store")
17395 (set_attr "mode" "SI")])
17397 (define_insn "*rep_stossi_rex64"
17398 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17399 (set (match_operand:DI 0 "register_operand" "=D")
17400 (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
17402 (match_operand:DI 3 "register_operand" "0")))
17403 (set (mem:BLK (match_dup 3))
17405 (use (match_operand:SI 2 "register_operand" "a"))
17406 (use (match_dup 4))
17407 (use (reg:SI DIRFLAG_REG))]
17409 "{rep\;stosl|rep stosd}"
17410 [(set_attr "type" "str")
17411 (set_attr "prefix_rep" "1")
17412 (set_attr "memory" "store")
17413 (set_attr "mode" "SI")])
17415 (define_insn "*rep_stosqi"
17416 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
17417 (set (match_operand:SI 0 "register_operand" "=D")
17418 (plus:SI (match_operand:SI 3 "register_operand" "0")
17419 (match_operand:SI 4 "register_operand" "1")))
17420 (set (mem:BLK (match_dup 3))
17422 (use (match_operand:QI 2 "register_operand" "a"))
17423 (use (match_dup 4))
17424 (use (reg:SI DIRFLAG_REG))]
17426 "{rep\;stosb|rep stosb}"
17427 [(set_attr "type" "str")
17428 (set_attr "prefix_rep" "1")
17429 (set_attr "memory" "store")
17430 (set_attr "mode" "QI")])
17432 (define_insn "*rep_stosqi_rex64"
17433 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17434 (set (match_operand:DI 0 "register_operand" "=D")
17435 (plus:DI (match_operand:DI 3 "register_operand" "0")
17436 (match_operand:DI 4 "register_operand" "1")))
17437 (set (mem:BLK (match_dup 3))
17439 (use (match_operand:QI 2 "register_operand" "a"))
17440 (use (match_dup 4))
17441 (use (reg:SI DIRFLAG_REG))]
17443 "{rep\;stosb|rep stosb}"
17444 [(set_attr "type" "str")
17445 (set_attr "prefix_rep" "1")
17446 (set_attr "memory" "store")
17447 (set_attr "mode" "QI")])
17449 (define_expand "cmpstrsi"
17450 [(set (match_operand:SI 0 "register_operand" "")
17451 (compare:SI (match_operand:BLK 1 "general_operand" "")
17452 (match_operand:BLK 2 "general_operand" "")))
17453 (use (match_operand 3 "general_operand" ""))
17454 (use (match_operand 4 "immediate_operand" ""))]
17455 "! optimize_size || TARGET_INLINE_ALL_STRINGOPS"
17457 rtx addr1, addr2, out, outlow, count, countreg, align;
17459 /* Can't use this if the user has appropriated esi or edi. */
17460 if (global_regs[4] || global_regs[5])
17464 if (GET_CODE (out) != REG)
17465 out = gen_reg_rtx (SImode);
17467 addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
17468 addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
17469 if (addr1 != XEXP (operands[1], 0))
17470 operands[1] = replace_equiv_address_nv (operands[1], addr1);
17471 if (addr2 != XEXP (operands[2], 0))
17472 operands[2] = replace_equiv_address_nv (operands[2], addr2);
17474 count = operands[3];
17475 countreg = ix86_zero_extend_to_Pmode (count);
17477 /* %%% Iff we are testing strict equality, we can use known alignment
17478 to good advantage. This may be possible with combine, particularly
17479 once cc0 is dead. */
17480 align = operands[4];
17482 emit_insn (gen_cld ());
17483 if (GET_CODE (count) == CONST_INT)
17485 if (INTVAL (count) == 0)
17487 emit_move_insn (operands[0], const0_rtx);
17490 emit_insn (gen_cmpstrqi_nz_1 (addr1, addr2, countreg, align,
17491 operands[1], operands[2]));
17496 emit_insn (gen_cmpdi_1_rex64 (countreg, countreg));
17498 emit_insn (gen_cmpsi_1 (countreg, countreg));
17499 emit_insn (gen_cmpstrqi_1 (addr1, addr2, countreg, align,
17500 operands[1], operands[2]));
17503 outlow = gen_lowpart (QImode, out);
17504 emit_insn (gen_cmpintqi (outlow));
17505 emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
17507 if (operands[0] != out)
17508 emit_move_insn (operands[0], out);
17513 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
17515 (define_expand "cmpintqi"
17516 [(set (match_dup 1)
17517 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
17519 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
17520 (parallel [(set (match_operand:QI 0 "register_operand" "")
17521 (minus:QI (match_dup 1)
17523 (clobber (reg:CC FLAGS_REG))])]
17525 "operands[1] = gen_reg_rtx (QImode);
17526 operands[2] = gen_reg_rtx (QImode);")
17528 ;; memcmp recognizers. The `cmpsb' opcode does nothing if the count is
17529 ;; zero. Emit extra code to make sure that a zero-length compare is EQ.
17531 (define_expand "cmpstrqi_nz_1"
17532 [(parallel [(set (reg:CC FLAGS_REG)
17533 (compare:CC (match_operand 4 "memory_operand" "")
17534 (match_operand 5 "memory_operand" "")))
17535 (use (match_operand 2 "register_operand" ""))
17536 (use (match_operand:SI 3 "immediate_operand" ""))
17537 (use (reg:SI DIRFLAG_REG))
17538 (clobber (match_operand 0 "register_operand" ""))
17539 (clobber (match_operand 1 "register_operand" ""))
17540 (clobber (match_dup 2))])]
17544 (define_insn "*cmpstrqi_nz_1"
17545 [(set (reg:CC FLAGS_REG)
17546 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
17547 (mem:BLK (match_operand:SI 5 "register_operand" "1"))))
17548 (use (match_operand:SI 6 "register_operand" "2"))
17549 (use (match_operand:SI 3 "immediate_operand" "i"))
17550 (use (reg:SI DIRFLAG_REG))
17551 (clobber (match_operand:SI 0 "register_operand" "=S"))
17552 (clobber (match_operand:SI 1 "register_operand" "=D"))
17553 (clobber (match_operand:SI 2 "register_operand" "=c"))]
17556 [(set_attr "type" "str")
17557 (set_attr "mode" "QI")
17558 (set_attr "prefix_rep" "1")])
17560 (define_insn "*cmpstrqi_nz_rex_1"
17561 [(set (reg:CC FLAGS_REG)
17562 (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
17563 (mem:BLK (match_operand:DI 5 "register_operand" "1"))))
17564 (use (match_operand:DI 6 "register_operand" "2"))
17565 (use (match_operand:SI 3 "immediate_operand" "i"))
17566 (use (reg:SI DIRFLAG_REG))
17567 (clobber (match_operand:DI 0 "register_operand" "=S"))
17568 (clobber (match_operand:DI 1 "register_operand" "=D"))
17569 (clobber (match_operand:DI 2 "register_operand" "=c"))]
17572 [(set_attr "type" "str")
17573 (set_attr "mode" "QI")
17574 (set_attr "prefix_rep" "1")])
17576 ;; The same, but the count is not known to not be zero.
17578 (define_expand "cmpstrqi_1"
17579 [(parallel [(set (reg:CC FLAGS_REG)
17580 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
17582 (compare:CC (match_operand 4 "memory_operand" "")
17583 (match_operand 5 "memory_operand" ""))
17585 (use (match_operand:SI 3 "immediate_operand" ""))
17586 (use (reg:CC FLAGS_REG))
17587 (use (reg:SI DIRFLAG_REG))
17588 (clobber (match_operand 0 "register_operand" ""))
17589 (clobber (match_operand 1 "register_operand" ""))
17590 (clobber (match_dup 2))])]
17594 (define_insn "*cmpstrqi_1"
17595 [(set (reg:CC FLAGS_REG)
17596 (if_then_else:CC (ne (match_operand:SI 6 "register_operand" "2")
17598 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
17599 (mem:BLK (match_operand:SI 5 "register_operand" "1")))
17601 (use (match_operand:SI 3 "immediate_operand" "i"))
17602 (use (reg:CC FLAGS_REG))
17603 (use (reg:SI DIRFLAG_REG))
17604 (clobber (match_operand:SI 0 "register_operand" "=S"))
17605 (clobber (match_operand:SI 1 "register_operand" "=D"))
17606 (clobber (match_operand:SI 2 "register_operand" "=c"))]
17609 [(set_attr "type" "str")
17610 (set_attr "mode" "QI")
17611 (set_attr "prefix_rep" "1")])
17613 (define_insn "*cmpstrqi_rex_1"
17614 [(set (reg:CC FLAGS_REG)
17615 (if_then_else:CC (ne (match_operand:DI 6 "register_operand" "2")
17617 (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
17618 (mem:BLK (match_operand:DI 5 "register_operand" "1")))
17620 (use (match_operand:SI 3 "immediate_operand" "i"))
17621 (use (reg:CC FLAGS_REG))
17622 (use (reg:SI DIRFLAG_REG))
17623 (clobber (match_operand:DI 0 "register_operand" "=S"))
17624 (clobber (match_operand:DI 1 "register_operand" "=D"))
17625 (clobber (match_operand:DI 2 "register_operand" "=c"))]
17628 [(set_attr "type" "str")
17629 (set_attr "mode" "QI")
17630 (set_attr "prefix_rep" "1")])
17632 (define_expand "strlensi"
17633 [(set (match_operand:SI 0 "register_operand" "")
17634 (unspec:SI [(match_operand:BLK 1 "general_operand" "")
17635 (match_operand:QI 2 "immediate_operand" "")
17636 (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
17639 if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
17645 (define_expand "strlendi"
17646 [(set (match_operand:DI 0 "register_operand" "")
17647 (unspec:DI [(match_operand:BLK 1 "general_operand" "")
17648 (match_operand:QI 2 "immediate_operand" "")
17649 (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
17652 if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
17658 (define_expand "strlenqi_1"
17659 [(parallel [(set (match_operand 0 "register_operand" "") (match_operand 2 "" ""))
17660 (use (reg:SI DIRFLAG_REG))
17661 (clobber (match_operand 1 "register_operand" ""))
17662 (clobber (reg:CC FLAGS_REG))])]
17666 (define_insn "*strlenqi_1"
17667 [(set (match_operand:SI 0 "register_operand" "=&c")
17668 (unspec:SI [(mem:BLK (match_operand:SI 5 "register_operand" "1"))
17669 (match_operand:QI 2 "register_operand" "a")
17670 (match_operand:SI 3 "immediate_operand" "i")
17671 (match_operand:SI 4 "register_operand" "0")] UNSPEC_SCAS))
17672 (use (reg:SI DIRFLAG_REG))
17673 (clobber (match_operand:SI 1 "register_operand" "=D"))
17674 (clobber (reg:CC FLAGS_REG))]
17677 [(set_attr "type" "str")
17678 (set_attr "mode" "QI")
17679 (set_attr "prefix_rep" "1")])
17681 (define_insn "*strlenqi_rex_1"
17682 [(set (match_operand:DI 0 "register_operand" "=&c")
17683 (unspec:DI [(mem:BLK (match_operand:DI 5 "register_operand" "1"))
17684 (match_operand:QI 2 "register_operand" "a")
17685 (match_operand:DI 3 "immediate_operand" "i")
17686 (match_operand:DI 4 "register_operand" "0")] UNSPEC_SCAS))
17687 (use (reg:SI DIRFLAG_REG))
17688 (clobber (match_operand:DI 1 "register_operand" "=D"))
17689 (clobber (reg:CC FLAGS_REG))]
17692 [(set_attr "type" "str")
17693 (set_attr "mode" "QI")
17694 (set_attr "prefix_rep" "1")])
17696 ;; Peephole optimizations to clean up after cmpstr*. This should be
17697 ;; handled in combine, but it is not currently up to the task.
17698 ;; When used for their truth value, the cmpstr* expanders generate
17707 ;; The intermediate three instructions are unnecessary.
17709 ;; This one handles cmpstr*_nz_1...
17712 (set (reg:CC FLAGS_REG)
17713 (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
17714 (mem:BLK (match_operand 5 "register_operand" ""))))
17715 (use (match_operand 6 "register_operand" ""))
17716 (use (match_operand:SI 3 "immediate_operand" ""))
17717 (use (reg:SI DIRFLAG_REG))
17718 (clobber (match_operand 0 "register_operand" ""))
17719 (clobber (match_operand 1 "register_operand" ""))
17720 (clobber (match_operand 2 "register_operand" ""))])
17721 (set (match_operand:QI 7 "register_operand" "")
17722 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
17723 (set (match_operand:QI 8 "register_operand" "")
17724 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
17725 (set (reg FLAGS_REG)
17726 (compare (match_dup 7) (match_dup 8)))
17728 "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
17730 (set (reg:CC FLAGS_REG)
17731 (compare:CC (mem:BLK (match_dup 4))
17732 (mem:BLK (match_dup 5))))
17733 (use (match_dup 6))
17734 (use (match_dup 3))
17735 (use (reg:SI DIRFLAG_REG))
17736 (clobber (match_dup 0))
17737 (clobber (match_dup 1))
17738 (clobber (match_dup 2))])]
17741 ;; ...and this one handles cmpstr*_1.
17744 (set (reg:CC FLAGS_REG)
17745 (if_then_else:CC (ne (match_operand 6 "register_operand" "")
17747 (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
17748 (mem:BLK (match_operand 5 "register_operand" "")))
17750 (use (match_operand:SI 3 "immediate_operand" ""))
17751 (use (reg:CC FLAGS_REG))
17752 (use (reg:SI DIRFLAG_REG))
17753 (clobber (match_operand 0 "register_operand" ""))
17754 (clobber (match_operand 1 "register_operand" ""))
17755 (clobber (match_operand 2 "register_operand" ""))])
17756 (set (match_operand:QI 7 "register_operand" "")
17757 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
17758 (set (match_operand:QI 8 "register_operand" "")
17759 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
17760 (set (reg FLAGS_REG)
17761 (compare (match_dup 7) (match_dup 8)))
17763 "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
17765 (set (reg:CC FLAGS_REG)
17766 (if_then_else:CC (ne (match_dup 6)
17768 (compare:CC (mem:BLK (match_dup 4))
17769 (mem:BLK (match_dup 5)))
17771 (use (match_dup 3))
17772 (use (reg:CC FLAGS_REG))
17773 (use (reg:SI DIRFLAG_REG))
17774 (clobber (match_dup 0))
17775 (clobber (match_dup 1))
17776 (clobber (match_dup 2))])]
17781 ;; Conditional move instructions.
17783 (define_expand "movdicc"
17784 [(set (match_operand:DI 0 "register_operand" "")
17785 (if_then_else:DI (match_operand 1 "comparison_operator" "")
17786 (match_operand:DI 2 "general_operand" "")
17787 (match_operand:DI 3 "general_operand" "")))]
17789 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
17791 (define_insn "x86_movdicc_0_m1_rex64"
17792 [(set (match_operand:DI 0 "register_operand" "=r")
17793 (if_then_else:DI (match_operand 1 "ix86_carry_flag_operator" "")
17796 (clobber (reg:CC FLAGS_REG))]
17799 ; Since we don't have the proper number of operands for an alu insn,
17800 ; fill in all the blanks.
17801 [(set_attr "type" "alu")
17802 (set_attr "pent_pair" "pu")
17803 (set_attr "memory" "none")
17804 (set_attr "imm_disp" "false")
17805 (set_attr "mode" "DI")
17806 (set_attr "length_immediate" "0")])
17808 (define_insn "*movdicc_c_rex64"
17809 [(set (match_operand:DI 0 "register_operand" "=r,r")
17810 (if_then_else:DI (match_operator 1 "ix86_comparison_operator"
17811 [(reg FLAGS_REG) (const_int 0)])
17812 (match_operand:DI 2 "nonimmediate_operand" "rm,0")
17813 (match_operand:DI 3 "nonimmediate_operand" "0,rm")))]
17814 "TARGET_64BIT && TARGET_CMOVE
17815 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17817 cmov%O2%C1\t{%2, %0|%0, %2}
17818 cmov%O2%c1\t{%3, %0|%0, %3}"
17819 [(set_attr "type" "icmov")
17820 (set_attr "mode" "DI")])
17822 (define_expand "movsicc"
17823 [(set (match_operand:SI 0 "register_operand" "")
17824 (if_then_else:SI (match_operand 1 "comparison_operator" "")
17825 (match_operand:SI 2 "general_operand" "")
17826 (match_operand:SI 3 "general_operand" "")))]
17828 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
17830 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
17831 ;; the register first winds up with `sbbl $0,reg', which is also weird.
17832 ;; So just document what we're doing explicitly.
17834 (define_insn "x86_movsicc_0_m1"
17835 [(set (match_operand:SI 0 "register_operand" "=r")
17836 (if_then_else:SI (match_operand 1 "ix86_carry_flag_operator" "")
17839 (clobber (reg:CC FLAGS_REG))]
17842 ; Since we don't have the proper number of operands for an alu insn,
17843 ; fill in all the blanks.
17844 [(set_attr "type" "alu")
17845 (set_attr "pent_pair" "pu")
17846 (set_attr "memory" "none")
17847 (set_attr "imm_disp" "false")
17848 (set_attr "mode" "SI")
17849 (set_attr "length_immediate" "0")])
17851 (define_insn "*movsicc_noc"
17852 [(set (match_operand:SI 0 "register_operand" "=r,r")
17853 (if_then_else:SI (match_operator 1 "ix86_comparison_operator"
17854 [(reg FLAGS_REG) (const_int 0)])
17855 (match_operand:SI 2 "nonimmediate_operand" "rm,0")
17856 (match_operand:SI 3 "nonimmediate_operand" "0,rm")))]
17858 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17860 cmov%O2%C1\t{%2, %0|%0, %2}
17861 cmov%O2%c1\t{%3, %0|%0, %3}"
17862 [(set_attr "type" "icmov")
17863 (set_attr "mode" "SI")])
17865 (define_expand "movhicc"
17866 [(set (match_operand:HI 0 "register_operand" "")
17867 (if_then_else:HI (match_operand 1 "comparison_operator" "")
17868 (match_operand:HI 2 "general_operand" "")
17869 (match_operand:HI 3 "general_operand" "")))]
17870 "TARGET_HIMODE_MATH"
17871 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
17873 (define_insn "*movhicc_noc"
17874 [(set (match_operand:HI 0 "register_operand" "=r,r")
17875 (if_then_else:HI (match_operator 1 "ix86_comparison_operator"
17876 [(reg FLAGS_REG) (const_int 0)])
17877 (match_operand:HI 2 "nonimmediate_operand" "rm,0")
17878 (match_operand:HI 3 "nonimmediate_operand" "0,rm")))]
17880 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17882 cmov%O2%C1\t{%2, %0|%0, %2}
17883 cmov%O2%c1\t{%3, %0|%0, %3}"
17884 [(set_attr "type" "icmov")
17885 (set_attr "mode" "HI")])
17887 (define_expand "movqicc"
17888 [(set (match_operand:QI 0 "register_operand" "")
17889 (if_then_else:QI (match_operand 1 "comparison_operator" "")
17890 (match_operand:QI 2 "general_operand" "")
17891 (match_operand:QI 3 "general_operand" "")))]
17892 "TARGET_QIMODE_MATH"
17893 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
17895 (define_insn_and_split "*movqicc_noc"
17896 [(set (match_operand:QI 0 "register_operand" "=r,r")
17897 (if_then_else:QI (match_operator 1 "ix86_comparison_operator"
17898 [(match_operand 4 "flags_reg_operand" "")
17900 (match_operand:QI 2 "register_operand" "r,0")
17901 (match_operand:QI 3 "register_operand" "0,r")))]
17902 "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
17904 "&& reload_completed"
17905 [(set (match_dup 0)
17906 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
17909 "operands[0] = gen_lowpart (SImode, operands[0]);
17910 operands[2] = gen_lowpart (SImode, operands[2]);
17911 operands[3] = gen_lowpart (SImode, operands[3]);"
17912 [(set_attr "type" "icmov")
17913 (set_attr "mode" "SI")])
17915 (define_expand "movsfcc"
17916 [(set (match_operand:SF 0 "register_operand" "")
17917 (if_then_else:SF (match_operand 1 "comparison_operator" "")
17918 (match_operand:SF 2 "register_operand" "")
17919 (match_operand:SF 3 "register_operand" "")))]
17920 "(TARGET_80387 && TARGET_CMOVE) || TARGET_SSE_MATH"
17921 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
17923 (define_insn "*movsfcc_1_387"
17924 [(set (match_operand:SF 0 "register_operand" "=f#r,f#r,r#f,r#f")
17925 (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
17926 [(reg FLAGS_REG) (const_int 0)])
17927 (match_operand:SF 2 "nonimmediate_operand" "f#r,0,rm#f,0")
17928 (match_operand:SF 3 "nonimmediate_operand" "0,f#r,0,rm#f")))]
17929 "TARGET_80387 && TARGET_CMOVE
17930 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17932 fcmov%F1\t{%2, %0|%0, %2}
17933 fcmov%f1\t{%3, %0|%0, %3}
17934 cmov%O2%C1\t{%2, %0|%0, %2}
17935 cmov%O2%c1\t{%3, %0|%0, %3}"
17936 [(set_attr "type" "fcmov,fcmov,icmov,icmov")
17937 (set_attr "mode" "SF,SF,SI,SI")])
17939 (define_expand "movdfcc"
17940 [(set (match_operand:DF 0 "register_operand" "")
17941 (if_then_else:DF (match_operand 1 "comparison_operator" "")
17942 (match_operand:DF 2 "register_operand" "")
17943 (match_operand:DF 3 "register_operand" "")))]
17944 "(TARGET_80387 && TARGET_CMOVE) || (TARGET_SSE2 && TARGET_SSE_MATH)"
17945 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
17947 (define_insn "*movdfcc_1"
17948 [(set (match_operand:DF 0 "register_operand" "=f#r,f#r,&r#f,&r#f")
17949 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
17950 [(reg FLAGS_REG) (const_int 0)])
17951 (match_operand:DF 2 "nonimmediate_operand" "f#r,0,rm#f,0")
17952 (match_operand:DF 3 "nonimmediate_operand" "0,f#r,0,rm#f")))]
17953 "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
17954 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17956 fcmov%F1\t{%2, %0|%0, %2}
17957 fcmov%f1\t{%3, %0|%0, %3}
17960 [(set_attr "type" "fcmov,fcmov,multi,multi")
17961 (set_attr "mode" "DF")])
17963 (define_insn "*movdfcc_1_rex64"
17964 [(set (match_operand:DF 0 "register_operand" "=f#r,f#r,r#f,r#f")
17965 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
17966 [(reg FLAGS_REG) (const_int 0)])
17967 (match_operand:DF 2 "nonimmediate_operand" "f#r,0#r,rm#f,0#f")
17968 (match_operand:DF 3 "nonimmediate_operand" "0#r,f#r,0#f,rm#f")))]
17969 "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
17970 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
17972 fcmov%F1\t{%2, %0|%0, %2}
17973 fcmov%f1\t{%3, %0|%0, %3}
17974 cmov%O2%C1\t{%2, %0|%0, %2}
17975 cmov%O2%c1\t{%3, %0|%0, %3}"
17976 [(set_attr "type" "fcmov,fcmov,icmov,icmov")
17977 (set_attr "mode" "DF")])
17980 [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand" "")
17981 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
17982 [(match_operand 4 "flags_reg_operand" "")
17984 (match_operand:DF 2 "nonimmediate_operand" "")
17985 (match_operand:DF 3 "nonimmediate_operand" "")))]
17986 "!TARGET_64BIT && reload_completed"
17987 [(set (match_dup 2)
17988 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
17992 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
17995 "split_di (operands+2, 1, operands+5, operands+6);
17996 split_di (operands+3, 1, operands+7, operands+8);
17997 split_di (operands, 1, operands+2, operands+3);")
17999 (define_expand "movxfcc"
18000 [(set (match_operand:XF 0 "register_operand" "")
18001 (if_then_else:XF (match_operand 1 "comparison_operator" "")
18002 (match_operand:XF 2 "register_operand" "")
18003 (match_operand:XF 3 "register_operand" "")))]
18004 "TARGET_80387 && TARGET_CMOVE"
18005 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
18007 (define_insn "*movxfcc_1"
18008 [(set (match_operand:XF 0 "register_operand" "=f,f")
18009 (if_then_else:XF (match_operator 1 "fcmov_comparison_operator"
18010 [(reg FLAGS_REG) (const_int 0)])
18011 (match_operand:XF 2 "register_operand" "f,0")
18012 (match_operand:XF 3 "register_operand" "0,f")))]
18013 "TARGET_80387 && TARGET_CMOVE"
18015 fcmov%F1\t{%2, %0|%0, %2}
18016 fcmov%f1\t{%3, %0|%0, %3}"
18017 [(set_attr "type" "fcmov")
18018 (set_attr "mode" "XF")])
18020 ;; These versions of the min/max patterns are intentionally ignorant of
18021 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
18022 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
18023 ;; are undefined in this condition, we're certain this is correct.
18025 (define_insn "sminsf3"
18026 [(set (match_operand:SF 0 "register_operand" "=x")
18027 (smin:SF (match_operand:SF 1 "nonimmediate_operand" "%0")
18028 (match_operand:SF 2 "nonimmediate_operand" "xm")))]
18030 "minss\t{%2, %0|%0, %2}"
18031 [(set_attr "type" "sseadd")
18032 (set_attr "mode" "SF")])
18034 (define_insn "smaxsf3"
18035 [(set (match_operand:SF 0 "register_operand" "=x")
18036 (smax:SF (match_operand:SF 1 "nonimmediate_operand" "%0")
18037 (match_operand:SF 2 "nonimmediate_operand" "xm")))]
18039 "maxss\t{%2, %0|%0, %2}"
18040 [(set_attr "type" "sseadd")
18041 (set_attr "mode" "SF")])
18043 (define_insn "smindf3"
18044 [(set (match_operand:DF 0 "register_operand" "=x")
18045 (smin:DF (match_operand:DF 1 "nonimmediate_operand" "%0")
18046 (match_operand:DF 2 "nonimmediate_operand" "xm")))]
18047 "TARGET_SSE2 && TARGET_SSE_MATH"
18048 "minsd\t{%2, %0|%0, %2}"
18049 [(set_attr "type" "sseadd")
18050 (set_attr "mode" "DF")])
18052 (define_insn "smaxdf3"
18053 [(set (match_operand:DF 0 "register_operand" "=x")
18054 (smax:DF (match_operand:DF 1 "nonimmediate_operand" "%0")
18055 (match_operand:DF 2 "nonimmediate_operand" "xm")))]
18056 "TARGET_SSE2 && TARGET_SSE_MATH"
18057 "maxsd\t{%2, %0|%0, %2}"
18058 [(set_attr "type" "sseadd")
18059 (set_attr "mode" "DF")])
18061 ;; These versions of the min/max patterns implement exactly the operations
18062 ;; min = (op1 < op2 ? op1 : op2)
18063 ;; max = (!(op1 < op2) ? op1 : op2)
18064 ;; Their operands are not commutative, and thus they may be used in the
18065 ;; presence of -0.0 and NaN.
18067 (define_insn "*ieee_sminsf3"
18068 [(set (match_operand:SF 0 "register_operand" "=x")
18069 (unspec:SF [(match_operand:SF 1 "register_operand" "0")
18070 (match_operand:SF 2 "nonimmediate_operand" "xm")]
18073 "minss\t{%2, %0|%0, %2}"
18074 [(set_attr "type" "sseadd")
18075 (set_attr "mode" "SF")])
18077 (define_insn "*ieee_smaxsf3"
18078 [(set (match_operand:SF 0 "register_operand" "=x")
18079 (unspec:SF [(match_operand:SF 1 "register_operand" "0")
18080 (match_operand:SF 2 "nonimmediate_operand" "xm")]
18083 "maxss\t{%2, %0|%0, %2}"
18084 [(set_attr "type" "sseadd")
18085 (set_attr "mode" "SF")])
18087 (define_insn "*ieee_smindf3"
18088 [(set (match_operand:DF 0 "register_operand" "=x")
18089 (unspec:DF [(match_operand:DF 1 "register_operand" "0")
18090 (match_operand:DF 2 "nonimmediate_operand" "xm")]
18092 "TARGET_SSE2 && TARGET_SSE_MATH"
18093 "minsd\t{%2, %0|%0, %2}"
18094 [(set_attr "type" "sseadd")
18095 (set_attr "mode" "DF")])
18097 (define_insn "*ieee_smaxdf3"
18098 [(set (match_operand:DF 0 "register_operand" "=x")
18099 (unspec:DF [(match_operand:DF 1 "register_operand" "0")
18100 (match_operand:DF 2 "nonimmediate_operand" "xm")]
18102 "TARGET_SSE2 && TARGET_SSE_MATH"
18103 "maxsd\t{%2, %0|%0, %2}"
18104 [(set_attr "type" "sseadd")
18105 (set_attr "mode" "DF")])
18107 ;; Conditional addition patterns
18108 (define_expand "addqicc"
18109 [(match_operand:QI 0 "register_operand" "")
18110 (match_operand 1 "comparison_operator" "")
18111 (match_operand:QI 2 "register_operand" "")
18112 (match_operand:QI 3 "const_int_operand" "")]
18114 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18116 (define_expand "addhicc"
18117 [(match_operand:HI 0 "register_operand" "")
18118 (match_operand 1 "comparison_operator" "")
18119 (match_operand:HI 2 "register_operand" "")
18120 (match_operand:HI 3 "const_int_operand" "")]
18122 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18124 (define_expand "addsicc"
18125 [(match_operand:SI 0 "register_operand" "")
18126 (match_operand 1 "comparison_operator" "")
18127 (match_operand:SI 2 "register_operand" "")
18128 (match_operand:SI 3 "const_int_operand" "")]
18130 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18132 (define_expand "adddicc"
18133 [(match_operand:DI 0 "register_operand" "")
18134 (match_operand 1 "comparison_operator" "")
18135 (match_operand:DI 2 "register_operand" "")
18136 (match_operand:DI 3 "const_int_operand" "")]
18138 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18141 ;; Misc patterns (?)
18143 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
18144 ;; Otherwise there will be nothing to keep
18146 ;; [(set (reg ebp) (reg esp))]
18147 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
18148 ;; (clobber (eflags)]
18149 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
18151 ;; in proper program order.
18152 (define_insn "pro_epilogue_adjust_stack_1"
18153 [(set (match_operand:SI 0 "register_operand" "=r,r")
18154 (plus:SI (match_operand:SI 1 "register_operand" "0,r")
18155 (match_operand:SI 2 "immediate_operand" "i,i")))
18156 (clobber (reg:CC FLAGS_REG))
18157 (clobber (mem:BLK (scratch)))]
18160 switch (get_attr_type (insn))
18163 return "mov{l}\t{%1, %0|%0, %1}";
18166 if (GET_CODE (operands[2]) == CONST_INT
18167 && (INTVAL (operands[2]) == 128
18168 || (INTVAL (operands[2]) < 0
18169 && INTVAL (operands[2]) != -128)))
18171 operands[2] = GEN_INT (-INTVAL (operands[2]));
18172 return "sub{l}\t{%2, %0|%0, %2}";
18174 return "add{l}\t{%2, %0|%0, %2}";
18177 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
18178 return "lea{l}\t{%a2, %0|%0, %a2}";
18181 gcc_unreachable ();
18184 [(set (attr "type")
18185 (cond [(eq_attr "alternative" "0")
18186 (const_string "alu")
18187 (match_operand:SI 2 "const0_operand" "")
18188 (const_string "imov")
18190 (const_string "lea")))
18191 (set_attr "mode" "SI")])
18193 (define_insn "pro_epilogue_adjust_stack_rex64"
18194 [(set (match_operand:DI 0 "register_operand" "=r,r")
18195 (plus:DI (match_operand:DI 1 "register_operand" "0,r")
18196 (match_operand:DI 2 "x86_64_immediate_operand" "e,e")))
18197 (clobber (reg:CC FLAGS_REG))
18198 (clobber (mem:BLK (scratch)))]
18201 switch (get_attr_type (insn))
18204 return "mov{q}\t{%1, %0|%0, %1}";
18207 if (GET_CODE (operands[2]) == CONST_INT
18208 /* Avoid overflows. */
18209 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
18210 && (INTVAL (operands[2]) == 128
18211 || (INTVAL (operands[2]) < 0
18212 && INTVAL (operands[2]) != -128)))
18214 operands[2] = GEN_INT (-INTVAL (operands[2]));
18215 return "sub{q}\t{%2, %0|%0, %2}";
18217 return "add{q}\t{%2, %0|%0, %2}";
18220 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
18221 return "lea{q}\t{%a2, %0|%0, %a2}";
18224 gcc_unreachable ();
18227 [(set (attr "type")
18228 (cond [(eq_attr "alternative" "0")
18229 (const_string "alu")
18230 (match_operand:DI 2 "const0_operand" "")
18231 (const_string "imov")
18233 (const_string "lea")))
18234 (set_attr "mode" "DI")])
18236 (define_insn "pro_epilogue_adjust_stack_rex64_2"
18237 [(set (match_operand:DI 0 "register_operand" "=r,r")
18238 (plus:DI (match_operand:DI 1 "register_operand" "0,r")
18239 (match_operand:DI 3 "immediate_operand" "i,i")))
18240 (use (match_operand:DI 2 "register_operand" "r,r"))
18241 (clobber (reg:CC FLAGS_REG))
18242 (clobber (mem:BLK (scratch)))]
18245 switch (get_attr_type (insn))
18248 return "add{q}\t{%2, %0|%0, %2}";
18251 operands[2] = gen_rtx_PLUS (DImode, operands[1], operands[2]);
18252 return "lea{q}\t{%a2, %0|%0, %a2}";
18255 gcc_unreachable ();
18258 [(set_attr "type" "alu,lea")
18259 (set_attr "mode" "DI")])
18261 (define_expand "allocate_stack_worker"
18262 [(match_operand:SI 0 "register_operand" "")]
18263 "TARGET_STACK_PROBE"
18265 if (reload_completed)
18268 emit_insn (gen_allocate_stack_worker_rex64_postreload (operands[0]));
18270 emit_insn (gen_allocate_stack_worker_postreload (operands[0]));
18275 emit_insn (gen_allocate_stack_worker_rex64 (operands[0]));
18277 emit_insn (gen_allocate_stack_worker_1 (operands[0]));
18282 (define_insn "allocate_stack_worker_1"
18283 [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")]
18284 UNSPECV_STACK_PROBE)
18285 (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0)))
18286 (clobber (match_scratch:SI 1 "=0"))
18287 (clobber (reg:CC FLAGS_REG))]
18288 "!TARGET_64BIT && TARGET_STACK_PROBE"
18290 [(set_attr "type" "multi")
18291 (set_attr "length" "5")])
18293 (define_expand "allocate_stack_worker_postreload"
18294 [(parallel [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")]
18295 UNSPECV_STACK_PROBE)
18296 (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0)))
18297 (clobber (match_dup 0))
18298 (clobber (reg:CC FLAGS_REG))])]
18302 (define_insn "allocate_stack_worker_rex64"
18303 [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")]
18304 UNSPECV_STACK_PROBE)
18305 (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0)))
18306 (clobber (match_scratch:DI 1 "=0"))
18307 (clobber (reg:CC FLAGS_REG))]
18308 "TARGET_64BIT && TARGET_STACK_PROBE"
18310 [(set_attr "type" "multi")
18311 (set_attr "length" "5")])
18313 (define_expand "allocate_stack_worker_rex64_postreload"
18314 [(parallel [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")]
18315 UNSPECV_STACK_PROBE)
18316 (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0)))
18317 (clobber (match_dup 0))
18318 (clobber (reg:CC FLAGS_REG))])]
18322 (define_expand "allocate_stack"
18323 [(parallel [(set (match_operand:SI 0 "register_operand" "=r")
18324 (minus:SI (reg:SI SP_REG)
18325 (match_operand:SI 1 "general_operand" "")))
18326 (clobber (reg:CC FLAGS_REG))])
18327 (parallel [(set (reg:SI SP_REG)
18328 (minus:SI (reg:SI SP_REG) (match_dup 1)))
18329 (clobber (reg:CC FLAGS_REG))])]
18330 "TARGET_STACK_PROBE"
18332 #ifdef CHECK_STACK_LIMIT
18333 if (GET_CODE (operands[1]) == CONST_INT
18334 && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
18335 emit_insn (gen_subsi3 (stack_pointer_rtx, stack_pointer_rtx,
18339 emit_insn (gen_allocate_stack_worker (copy_to_mode_reg (SImode,
18342 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
18346 (define_expand "builtin_setjmp_receiver"
18347 [(label_ref (match_operand 0 "" ""))]
18348 "!TARGET_64BIT && flag_pic"
18350 emit_insn (gen_set_got (pic_offset_table_rtx));
18354 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
18357 [(set (match_operand 0 "register_operand" "")
18358 (match_operator 3 "promotable_binary_operator"
18359 [(match_operand 1 "register_operand" "")
18360 (match_operand 2 "aligned_operand" "")]))
18361 (clobber (reg:CC FLAGS_REG))]
18362 "! TARGET_PARTIAL_REG_STALL && reload_completed
18363 && ((GET_MODE (operands[0]) == HImode
18364 && ((!optimize_size && !TARGET_FAST_PREFIX)
18365 || GET_CODE (operands[2]) != CONST_INT
18366 || CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')))
18367 || (GET_MODE (operands[0]) == QImode
18368 && (TARGET_PROMOTE_QImode || optimize_size)))"
18369 [(parallel [(set (match_dup 0)
18370 (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
18371 (clobber (reg:CC FLAGS_REG))])]
18372 "operands[0] = gen_lowpart (SImode, operands[0]);
18373 operands[1] = gen_lowpart (SImode, operands[1]);
18374 if (GET_CODE (operands[3]) != ASHIFT)
18375 operands[2] = gen_lowpart (SImode, operands[2]);
18376 PUT_MODE (operands[3], SImode);")
18378 ; Promote the QImode tests, as i386 has encoding of the AND
18379 ; instruction with 32-bit sign-extended immediate and thus the
18380 ; instruction size is unchanged, except in the %eax case for
18381 ; which it is increased by one byte, hence the ! optimize_size.
18383 [(set (match_operand 0 "flags_reg_operand" "")
18384 (match_operator 2 "compare_operator"
18385 [(and (match_operand 3 "aligned_operand" "")
18386 (match_operand 4 "const_int_operand" ""))
18388 (set (match_operand 1 "register_operand" "")
18389 (and (match_dup 3) (match_dup 4)))]
18390 "! TARGET_PARTIAL_REG_STALL && reload_completed
18391 /* Ensure that the operand will remain sign-extended immediate. */
18392 && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)
18394 && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
18395 || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))"
18396 [(parallel [(set (match_dup 0)
18397 (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
18400 (and:SI (match_dup 3) (match_dup 4)))])]
18403 = gen_int_mode (INTVAL (operands[4])
18404 & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
18405 operands[1] = gen_lowpart (SImode, operands[1]);
18406 operands[3] = gen_lowpart (SImode, operands[3]);
18409 ; Don't promote the QImode tests, as i386 doesn't have encoding of
18410 ; the TEST instruction with 32-bit sign-extended immediate and thus
18411 ; the instruction size would at least double, which is not what we
18412 ; want even with ! optimize_size.
18414 [(set (match_operand 0 "flags_reg_operand" "")
18415 (match_operator 1 "compare_operator"
18416 [(and (match_operand:HI 2 "aligned_operand" "")
18417 (match_operand:HI 3 "const_int_operand" ""))
18419 "! TARGET_PARTIAL_REG_STALL && reload_completed
18420 /* Ensure that the operand will remain sign-extended immediate. */
18421 && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)
18422 && ! TARGET_FAST_PREFIX
18423 && ! optimize_size"
18424 [(set (match_dup 0)
18425 (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
18429 = gen_int_mode (INTVAL (operands[3])
18430 & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
18431 operands[2] = gen_lowpart (SImode, operands[2]);
18435 [(set (match_operand 0 "register_operand" "")
18436 (neg (match_operand 1 "register_operand" "")))
18437 (clobber (reg:CC FLAGS_REG))]
18438 "! TARGET_PARTIAL_REG_STALL && reload_completed
18439 && (GET_MODE (operands[0]) == HImode
18440 || (GET_MODE (operands[0]) == QImode
18441 && (TARGET_PROMOTE_QImode || optimize_size)))"
18442 [(parallel [(set (match_dup 0)
18443 (neg:SI (match_dup 1)))
18444 (clobber (reg:CC FLAGS_REG))])]
18445 "operands[0] = gen_lowpart (SImode, operands[0]);
18446 operands[1] = gen_lowpart (SImode, operands[1]);")
18449 [(set (match_operand 0 "register_operand" "")
18450 (not (match_operand 1 "register_operand" "")))]
18451 "! TARGET_PARTIAL_REG_STALL && reload_completed
18452 && (GET_MODE (operands[0]) == HImode
18453 || (GET_MODE (operands[0]) == QImode
18454 && (TARGET_PROMOTE_QImode || optimize_size)))"
18455 [(set (match_dup 0)
18456 (not:SI (match_dup 1)))]
18457 "operands[0] = gen_lowpart (SImode, operands[0]);
18458 operands[1] = gen_lowpart (SImode, operands[1]);")
18461 [(set (match_operand 0 "register_operand" "")
18462 (if_then_else (match_operator 1 "comparison_operator"
18463 [(reg FLAGS_REG) (const_int 0)])
18464 (match_operand 2 "register_operand" "")
18465 (match_operand 3 "register_operand" "")))]
18466 "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE
18467 && (GET_MODE (operands[0]) == HImode
18468 || (GET_MODE (operands[0]) == QImode
18469 && (TARGET_PROMOTE_QImode || optimize_size)))"
18470 [(set (match_dup 0)
18471 (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
18472 "operands[0] = gen_lowpart (SImode, operands[0]);
18473 operands[2] = gen_lowpart (SImode, operands[2]);
18474 operands[3] = gen_lowpart (SImode, operands[3]);")
18477 ;; RTL Peephole optimizations, run before sched2. These primarily look to
18478 ;; transform a complex memory operation into two memory to register operations.
18480 ;; Don't push memory operands
18482 [(set (match_operand:SI 0 "push_operand" "")
18483 (match_operand:SI 1 "memory_operand" ""))
18484 (match_scratch:SI 2 "r")]
18485 "! optimize_size && ! TARGET_PUSH_MEMORY"
18486 [(set (match_dup 2) (match_dup 1))
18487 (set (match_dup 0) (match_dup 2))]
18491 [(set (match_operand:DI 0 "push_operand" "")
18492 (match_operand:DI 1 "memory_operand" ""))
18493 (match_scratch:DI 2 "r")]
18494 "! optimize_size && ! TARGET_PUSH_MEMORY"
18495 [(set (match_dup 2) (match_dup 1))
18496 (set (match_dup 0) (match_dup 2))]
18499 ;; We need to handle SFmode only, because DFmode and XFmode is split to
18502 [(set (match_operand:SF 0 "push_operand" "")
18503 (match_operand:SF 1 "memory_operand" ""))
18504 (match_scratch:SF 2 "r")]
18505 "! optimize_size && ! TARGET_PUSH_MEMORY"
18506 [(set (match_dup 2) (match_dup 1))
18507 (set (match_dup 0) (match_dup 2))]
18511 [(set (match_operand:HI 0 "push_operand" "")
18512 (match_operand:HI 1 "memory_operand" ""))
18513 (match_scratch:HI 2 "r")]
18514 "! optimize_size && ! TARGET_PUSH_MEMORY"
18515 [(set (match_dup 2) (match_dup 1))
18516 (set (match_dup 0) (match_dup 2))]
18520 [(set (match_operand:QI 0 "push_operand" "")
18521 (match_operand:QI 1 "memory_operand" ""))
18522 (match_scratch:QI 2 "q")]
18523 "! optimize_size && ! TARGET_PUSH_MEMORY"
18524 [(set (match_dup 2) (match_dup 1))
18525 (set (match_dup 0) (match_dup 2))]
18528 ;; Don't move an immediate directly to memory when the instruction
18531 [(match_scratch:SI 1 "r")
18532 (set (match_operand:SI 0 "memory_operand" "")
18535 && ! TARGET_USE_MOV0
18536 && TARGET_SPLIT_LONG_MOVES
18537 && get_attr_length (insn) >= ix86_cost->large_insn
18538 && peep2_regno_dead_p (0, FLAGS_REG)"
18539 [(parallel [(set (match_dup 1) (const_int 0))
18540 (clobber (reg:CC FLAGS_REG))])
18541 (set (match_dup 0) (match_dup 1))]
18545 [(match_scratch:HI 1 "r")
18546 (set (match_operand:HI 0 "memory_operand" "")
18549 && ! TARGET_USE_MOV0
18550 && TARGET_SPLIT_LONG_MOVES
18551 && get_attr_length (insn) >= ix86_cost->large_insn
18552 && peep2_regno_dead_p (0, FLAGS_REG)"
18553 [(parallel [(set (match_dup 2) (const_int 0))
18554 (clobber (reg:CC FLAGS_REG))])
18555 (set (match_dup 0) (match_dup 1))]
18556 "operands[2] = gen_lowpart (SImode, operands[1]);")
18559 [(match_scratch:QI 1 "q")
18560 (set (match_operand:QI 0 "memory_operand" "")
18563 && ! TARGET_USE_MOV0
18564 && TARGET_SPLIT_LONG_MOVES
18565 && get_attr_length (insn) >= ix86_cost->large_insn
18566 && peep2_regno_dead_p (0, FLAGS_REG)"
18567 [(parallel [(set (match_dup 2) (const_int 0))
18568 (clobber (reg:CC FLAGS_REG))])
18569 (set (match_dup 0) (match_dup 1))]
18570 "operands[2] = gen_lowpart (SImode, operands[1]);")
18573 [(match_scratch:SI 2 "r")
18574 (set (match_operand:SI 0 "memory_operand" "")
18575 (match_operand:SI 1 "immediate_operand" ""))]
18577 && get_attr_length (insn) >= ix86_cost->large_insn
18578 && TARGET_SPLIT_LONG_MOVES"
18579 [(set (match_dup 2) (match_dup 1))
18580 (set (match_dup 0) (match_dup 2))]
18584 [(match_scratch:HI 2 "r")
18585 (set (match_operand:HI 0 "memory_operand" "")
18586 (match_operand:HI 1 "immediate_operand" ""))]
18587 "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
18588 && TARGET_SPLIT_LONG_MOVES"
18589 [(set (match_dup 2) (match_dup 1))
18590 (set (match_dup 0) (match_dup 2))]
18594 [(match_scratch:QI 2 "q")
18595 (set (match_operand:QI 0 "memory_operand" "")
18596 (match_operand:QI 1 "immediate_operand" ""))]
18597 "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
18598 && TARGET_SPLIT_LONG_MOVES"
18599 [(set (match_dup 2) (match_dup 1))
18600 (set (match_dup 0) (match_dup 2))]
18603 ;; Don't compare memory with zero, load and use a test instead.
18605 [(set (match_operand 0 "flags_reg_operand" "")
18606 (match_operator 1 "compare_operator"
18607 [(match_operand:SI 2 "memory_operand" "")
18609 (match_scratch:SI 3 "r")]
18610 "ix86_match_ccmode (insn, CCNOmode) && ! optimize_size"
18611 [(set (match_dup 3) (match_dup 2))
18612 (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))]
18615 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer.
18616 ;; Don't split NOTs with a displacement operand, because resulting XOR
18617 ;; will not be pairable anyway.
18619 ;; On AMD K6, NOT is vector decoded with memory operand that cannot be
18620 ;; represented using a modRM byte. The XOR replacement is long decoded,
18621 ;; so this split helps here as well.
18623 ;; Note: Can't do this as a regular split because we can't get proper
18624 ;; lifetime information then.
18627 [(set (match_operand:SI 0 "nonimmediate_operand" "")
18628 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
18630 && peep2_regno_dead_p (0, FLAGS_REG)
18631 && ((TARGET_PENTIUM
18632 && (GET_CODE (operands[0]) != MEM
18633 || !memory_displacement_operand (operands[0], SImode)))
18634 || (TARGET_K6 && long_memory_operand (operands[0], SImode)))"
18635 [(parallel [(set (match_dup 0)
18636 (xor:SI (match_dup 1) (const_int -1)))
18637 (clobber (reg:CC FLAGS_REG))])]
18641 [(set (match_operand:HI 0 "nonimmediate_operand" "")
18642 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
18644 && peep2_regno_dead_p (0, FLAGS_REG)
18645 && ((TARGET_PENTIUM
18646 && (GET_CODE (operands[0]) != MEM
18647 || !memory_displacement_operand (operands[0], HImode)))
18648 || (TARGET_K6 && long_memory_operand (operands[0], HImode)))"
18649 [(parallel [(set (match_dup 0)
18650 (xor:HI (match_dup 1) (const_int -1)))
18651 (clobber (reg:CC FLAGS_REG))])]
18655 [(set (match_operand:QI 0 "nonimmediate_operand" "")
18656 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
18658 && peep2_regno_dead_p (0, FLAGS_REG)
18659 && ((TARGET_PENTIUM
18660 && (GET_CODE (operands[0]) != MEM
18661 || !memory_displacement_operand (operands[0], QImode)))
18662 || (TARGET_K6 && long_memory_operand (operands[0], QImode)))"
18663 [(parallel [(set (match_dup 0)
18664 (xor:QI (match_dup 1) (const_int -1)))
18665 (clobber (reg:CC FLAGS_REG))])]
18668 ;; Non pairable "test imm, reg" instructions can be translated to
18669 ;; "and imm, reg" if reg dies. The "and" form is also shorter (one
18670 ;; byte opcode instead of two, have a short form for byte operands),
18671 ;; so do it for other CPUs as well. Given that the value was dead,
18672 ;; this should not create any new dependencies. Pass on the sub-word
18673 ;; versions if we're concerned about partial register stalls.
18676 [(set (match_operand 0 "flags_reg_operand" "")
18677 (match_operator 1 "compare_operator"
18678 [(and:SI (match_operand:SI 2 "register_operand" "")
18679 (match_operand:SI 3 "immediate_operand" ""))
18681 "ix86_match_ccmode (insn, CCNOmode)
18682 && (true_regnum (operands[2]) != 0
18683 || (GET_CODE (operands[3]) == CONST_INT
18684 && CONST_OK_FOR_LETTER_P (INTVAL (operands[3]), 'K')))
18685 && peep2_reg_dead_p (1, operands[2])"
18687 [(set (match_dup 0)
18688 (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
18691 (and:SI (match_dup 2) (match_dup 3)))])]
18694 ;; We don't need to handle HImode case, because it will be promoted to SImode
18695 ;; on ! TARGET_PARTIAL_REG_STALL
18698 [(set (match_operand 0 "flags_reg_operand" "")
18699 (match_operator 1 "compare_operator"
18700 [(and:QI (match_operand:QI 2 "register_operand" "")
18701 (match_operand:QI 3 "immediate_operand" ""))
18703 "! TARGET_PARTIAL_REG_STALL
18704 && ix86_match_ccmode (insn, CCNOmode)
18705 && true_regnum (operands[2]) != 0
18706 && peep2_reg_dead_p (1, operands[2])"
18708 [(set (match_dup 0)
18709 (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
18712 (and:QI (match_dup 2) (match_dup 3)))])]
18716 [(set (match_operand 0 "flags_reg_operand" "")
18717 (match_operator 1 "compare_operator"
18720 (match_operand 2 "ext_register_operand" "")
18723 (match_operand 3 "const_int_operand" ""))
18725 "! TARGET_PARTIAL_REG_STALL
18726 && ix86_match_ccmode (insn, CCNOmode)
18727 && true_regnum (operands[2]) != 0
18728 && peep2_reg_dead_p (1, operands[2])"
18729 [(parallel [(set (match_dup 0)
18738 (set (zero_extract:SI (match_dup 2)
18749 ;; Don't do logical operations with memory inputs.
18751 [(match_scratch:SI 2 "r")
18752 (parallel [(set (match_operand:SI 0 "register_operand" "")
18753 (match_operator:SI 3 "arith_or_logical_operator"
18755 (match_operand:SI 1 "memory_operand" "")]))
18756 (clobber (reg:CC FLAGS_REG))])]
18757 "! optimize_size && ! TARGET_READ_MODIFY"
18758 [(set (match_dup 2) (match_dup 1))
18759 (parallel [(set (match_dup 0)
18760 (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
18761 (clobber (reg:CC FLAGS_REG))])]
18765 [(match_scratch:SI 2 "r")
18766 (parallel [(set (match_operand:SI 0 "register_operand" "")
18767 (match_operator:SI 3 "arith_or_logical_operator"
18768 [(match_operand:SI 1 "memory_operand" "")
18770 (clobber (reg:CC FLAGS_REG))])]
18771 "! optimize_size && ! TARGET_READ_MODIFY"
18772 [(set (match_dup 2) (match_dup 1))
18773 (parallel [(set (match_dup 0)
18774 (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
18775 (clobber (reg:CC FLAGS_REG))])]
18778 ; Don't do logical operations with memory outputs
18780 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
18781 ; instruction into two 1-uop insns plus a 2-uop insn. That last has
18782 ; the same decoder scheduling characteristics as the original.
18785 [(match_scratch:SI 2 "r")
18786 (parallel [(set (match_operand:SI 0 "memory_operand" "")
18787 (match_operator:SI 3 "arith_or_logical_operator"
18789 (match_operand:SI 1 "nonmemory_operand" "")]))
18790 (clobber (reg:CC FLAGS_REG))])]
18791 "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
18792 [(set (match_dup 2) (match_dup 0))
18793 (parallel [(set (match_dup 2)
18794 (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
18795 (clobber (reg:CC FLAGS_REG))])
18796 (set (match_dup 0) (match_dup 2))]
18800 [(match_scratch:SI 2 "r")
18801 (parallel [(set (match_operand:SI 0 "memory_operand" "")
18802 (match_operator:SI 3 "arith_or_logical_operator"
18803 [(match_operand:SI 1 "nonmemory_operand" "")
18805 (clobber (reg:CC FLAGS_REG))])]
18806 "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
18807 [(set (match_dup 2) (match_dup 0))
18808 (parallel [(set (match_dup 2)
18809 (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
18810 (clobber (reg:CC FLAGS_REG))])
18811 (set (match_dup 0) (match_dup 2))]
18814 ;; Attempt to always use XOR for zeroing registers.
18816 [(set (match_operand 0 "register_operand" "")
18817 (match_operand 1 "const0_operand" ""))]
18818 "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD
18819 && (! TARGET_USE_MOV0 || optimize_size)
18820 && GENERAL_REG_P (operands[0])
18821 && peep2_regno_dead_p (0, FLAGS_REG)"
18822 [(parallel [(set (match_dup 0) (const_int 0))
18823 (clobber (reg:CC FLAGS_REG))])]
18825 operands[0] = gen_lowpart (word_mode, operands[0]);
18829 [(set (strict_low_part (match_operand 0 "register_operand" ""))
18831 "(GET_MODE (operands[0]) == QImode
18832 || GET_MODE (operands[0]) == HImode)
18833 && (! TARGET_USE_MOV0 || optimize_size)
18834 && peep2_regno_dead_p (0, FLAGS_REG)"
18835 [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
18836 (clobber (reg:CC FLAGS_REG))])])
18838 ;; For HI and SI modes, or $-1,reg is smaller than mov $-1,reg.
18840 [(set (match_operand 0 "register_operand" "")
18842 "(GET_MODE (operands[0]) == HImode
18843 || GET_MODE (operands[0]) == SImode
18844 || (GET_MODE (operands[0]) == DImode && TARGET_64BIT))
18845 && (optimize_size || TARGET_PENTIUM)
18846 && peep2_regno_dead_p (0, FLAGS_REG)"
18847 [(parallel [(set (match_dup 0) (const_int -1))
18848 (clobber (reg:CC FLAGS_REG))])]
18849 "operands[0] = gen_lowpart (GET_MODE (operands[0]) == DImode ? DImode : SImode,
18852 ;; Attempt to convert simple leas to adds. These can be created by
18855 [(set (match_operand:SI 0 "register_operand" "")
18856 (plus:SI (match_dup 0)
18857 (match_operand:SI 1 "nonmemory_operand" "")))]
18858 "peep2_regno_dead_p (0, FLAGS_REG)"
18859 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
18860 (clobber (reg:CC FLAGS_REG))])]
18864 [(set (match_operand:SI 0 "register_operand" "")
18865 (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
18866 (match_operand:DI 2 "nonmemory_operand" "")) 0))]
18867 "peep2_regno_dead_p (0, FLAGS_REG) && REGNO (operands[0]) == REGNO (operands[1])"
18868 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
18869 (clobber (reg:CC FLAGS_REG))])]
18870 "operands[2] = gen_lowpart (SImode, operands[2]);")
18873 [(set (match_operand:DI 0 "register_operand" "")
18874 (plus:DI (match_dup 0)
18875 (match_operand:DI 1 "x86_64_general_operand" "")))]
18876 "peep2_regno_dead_p (0, FLAGS_REG)"
18877 [(parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
18878 (clobber (reg:CC FLAGS_REG))])]
18882 [(set (match_operand:SI 0 "register_operand" "")
18883 (mult:SI (match_dup 0)
18884 (match_operand:SI 1 "const_int_operand" "")))]
18885 "exact_log2 (INTVAL (operands[1])) >= 0
18886 && peep2_regno_dead_p (0, FLAGS_REG)"
18887 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
18888 (clobber (reg:CC FLAGS_REG))])]
18889 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
18892 [(set (match_operand:DI 0 "register_operand" "")
18893 (mult:DI (match_dup 0)
18894 (match_operand:DI 1 "const_int_operand" "")))]
18895 "exact_log2 (INTVAL (operands[1])) >= 0
18896 && peep2_regno_dead_p (0, FLAGS_REG)"
18897 [(parallel [(set (match_dup 0) (ashift:DI (match_dup 0) (match_dup 2)))
18898 (clobber (reg:CC FLAGS_REG))])]
18899 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
18902 [(set (match_operand:SI 0 "register_operand" "")
18903 (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
18904 (match_operand:DI 2 "const_int_operand" "")) 0))]
18905 "exact_log2 (INTVAL (operands[2])) >= 0
18906 && REGNO (operands[0]) == REGNO (operands[1])
18907 && peep2_regno_dead_p (0, FLAGS_REG)"
18908 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
18909 (clobber (reg:CC FLAGS_REG))])]
18910 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
18912 ;; The ESP adjustments can be done by the push and pop instructions. Resulting
18913 ;; code is shorter, since push is only 1 byte, while add imm, %esp 3 bytes. On
18914 ;; many CPUs it is also faster, since special hardware to avoid esp
18915 ;; dependencies is present.
18917 ;; While some of these conversions may be done using splitters, we use peepholes
18918 ;; in order to allow combine_stack_adjustments pass to see nonobfuscated RTL.
18920 ;; Convert prologue esp subtractions to push.
18921 ;; We need register to push. In order to keep verify_flow_info happy we have
18923 ;; - use scratch and clobber it in order to avoid dependencies
18924 ;; - use already live register
18925 ;; We can't use the second way right now, since there is no reliable way how to
18926 ;; verify that given register is live. First choice will also most likely in
18927 ;; fewer dependencies. On the place of esp adjustments it is very likely that
18928 ;; call clobbered registers are dead. We may want to use base pointer as an
18929 ;; alternative when no register is available later.
18932 [(match_scratch:SI 0 "r")
18933 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
18934 (clobber (reg:CC FLAGS_REG))
18935 (clobber (mem:BLK (scratch)))])]
18936 "optimize_size || !TARGET_SUB_ESP_4"
18937 [(clobber (match_dup 0))
18938 (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
18939 (clobber (mem:BLK (scratch)))])])
18942 [(match_scratch:SI 0 "r")
18943 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
18944 (clobber (reg:CC FLAGS_REG))
18945 (clobber (mem:BLK (scratch)))])]
18946 "optimize_size || !TARGET_SUB_ESP_8"
18947 [(clobber (match_dup 0))
18948 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
18949 (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
18950 (clobber (mem:BLK (scratch)))])])
18952 ;; Convert esp subtractions to push.
18954 [(match_scratch:SI 0 "r")
18955 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
18956 (clobber (reg:CC FLAGS_REG))])]
18957 "optimize_size || !TARGET_SUB_ESP_4"
18958 [(clobber (match_dup 0))
18959 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
18962 [(match_scratch:SI 0 "r")
18963 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
18964 (clobber (reg:CC FLAGS_REG))])]
18965 "optimize_size || !TARGET_SUB_ESP_8"
18966 [(clobber (match_dup 0))
18967 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
18968 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
18970 ;; Convert epilogue deallocator to pop.
18972 [(match_scratch:SI 0 "r")
18973 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
18974 (clobber (reg:CC FLAGS_REG))
18975 (clobber (mem:BLK (scratch)))])]
18976 "optimize_size || !TARGET_ADD_ESP_4"
18977 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
18978 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
18979 (clobber (mem:BLK (scratch)))])]
18982 ;; Two pops case is tricky, since pop causes dependency on destination register.
18983 ;; We use two registers if available.
18985 [(match_scratch:SI 0 "r")
18986 (match_scratch:SI 1 "r")
18987 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
18988 (clobber (reg:CC FLAGS_REG))
18989 (clobber (mem:BLK (scratch)))])]
18990 "optimize_size || !TARGET_ADD_ESP_8"
18991 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
18992 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
18993 (clobber (mem:BLK (scratch)))])
18994 (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
18995 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
18999 [(match_scratch:SI 0 "r")
19000 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19001 (clobber (reg:CC FLAGS_REG))
19002 (clobber (mem:BLK (scratch)))])]
19004 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19005 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19006 (clobber (mem:BLK (scratch)))])
19007 (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19008 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19011 ;; Convert esp additions to pop.
19013 [(match_scratch:SI 0 "r")
19014 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19015 (clobber (reg:CC FLAGS_REG))])]
19017 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19018 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19021 ;; Two pops case is tricky, since pop causes dependency on destination register.
19022 ;; We use two registers if available.
19024 [(match_scratch:SI 0 "r")
19025 (match_scratch:SI 1 "r")
19026 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19027 (clobber (reg:CC FLAGS_REG))])]
19029 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19030 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
19031 (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
19032 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19036 [(match_scratch:SI 0 "r")
19037 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19038 (clobber (reg:CC FLAGS_REG))])]
19040 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19041 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
19042 (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19043 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19046 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
19047 ;; required and register dies. Similarly for 128 to plus -128.
19049 [(set (match_operand 0 "flags_reg_operand" "")
19050 (match_operator 1 "compare_operator"
19051 [(match_operand 2 "register_operand" "")
19052 (match_operand 3 "const_int_operand" "")]))]
19053 "(INTVAL (operands[3]) == -1
19054 || INTVAL (operands[3]) == 1
19055 || INTVAL (operands[3]) == 128)
19056 && ix86_match_ccmode (insn, CCGCmode)
19057 && peep2_reg_dead_p (1, operands[2])"
19058 [(parallel [(set (match_dup 0)
19059 (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
19060 (clobber (match_dup 2))])]
19064 [(match_scratch:DI 0 "r")
19065 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
19066 (clobber (reg:CC FLAGS_REG))
19067 (clobber (mem:BLK (scratch)))])]
19068 "optimize_size || !TARGET_SUB_ESP_4"
19069 [(clobber (match_dup 0))
19070 (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19071 (clobber (mem:BLK (scratch)))])])
19074 [(match_scratch:DI 0 "r")
19075 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
19076 (clobber (reg:CC FLAGS_REG))
19077 (clobber (mem:BLK (scratch)))])]
19078 "optimize_size || !TARGET_SUB_ESP_8"
19079 [(clobber (match_dup 0))
19080 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19081 (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19082 (clobber (mem:BLK (scratch)))])])
19084 ;; Convert esp subtractions to push.
19086 [(match_scratch:DI 0 "r")
19087 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
19088 (clobber (reg:CC FLAGS_REG))])]
19089 "optimize_size || !TARGET_SUB_ESP_4"
19090 [(clobber (match_dup 0))
19091 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
19094 [(match_scratch:DI 0 "r")
19095 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
19096 (clobber (reg:CC FLAGS_REG))])]
19097 "optimize_size || !TARGET_SUB_ESP_8"
19098 [(clobber (match_dup 0))
19099 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19100 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
19102 ;; Convert epilogue deallocator to pop.
19104 [(match_scratch:DI 0 "r")
19105 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19106 (clobber (reg:CC FLAGS_REG))
19107 (clobber (mem:BLK (scratch)))])]
19108 "optimize_size || !TARGET_ADD_ESP_4"
19109 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19110 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19111 (clobber (mem:BLK (scratch)))])]
19114 ;; Two pops case is tricky, since pop causes dependency on destination register.
19115 ;; We use two registers if available.
19117 [(match_scratch:DI 0 "r")
19118 (match_scratch:DI 1 "r")
19119 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19120 (clobber (reg:CC FLAGS_REG))
19121 (clobber (mem:BLK (scratch)))])]
19122 "optimize_size || !TARGET_ADD_ESP_8"
19123 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19124 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19125 (clobber (mem:BLK (scratch)))])
19126 (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
19127 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19131 [(match_scratch:DI 0 "r")
19132 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19133 (clobber (reg:CC FLAGS_REG))
19134 (clobber (mem:BLK (scratch)))])]
19136 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19137 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19138 (clobber (mem:BLK (scratch)))])
19139 (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19140 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19143 ;; Convert esp additions to pop.
19145 [(match_scratch:DI 0 "r")
19146 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19147 (clobber (reg:CC FLAGS_REG))])]
19149 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19150 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19153 ;; Two pops case is tricky, since pop causes dependency on destination register.
19154 ;; We use two registers if available.
19156 [(match_scratch:DI 0 "r")
19157 (match_scratch:DI 1 "r")
19158 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19159 (clobber (reg:CC FLAGS_REG))])]
19161 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19162 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
19163 (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
19164 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19168 [(match_scratch:DI 0 "r")
19169 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19170 (clobber (reg:CC FLAGS_REG))])]
19172 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19173 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
19174 (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19175 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19178 ;; Convert imul by three, five and nine into lea
19181 [(set (match_operand:SI 0 "register_operand" "")
19182 (mult:SI (match_operand:SI 1 "register_operand" "")
19183 (match_operand:SI 2 "const_int_operand" "")))
19184 (clobber (reg:CC FLAGS_REG))])]
19185 "INTVAL (operands[2]) == 3
19186 || INTVAL (operands[2]) == 5
19187 || INTVAL (operands[2]) == 9"
19188 [(set (match_dup 0)
19189 (plus:SI (mult:SI (match_dup 1) (match_dup 2))
19191 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19195 [(set (match_operand:SI 0 "register_operand" "")
19196 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
19197 (match_operand:SI 2 "const_int_operand" "")))
19198 (clobber (reg:CC FLAGS_REG))])]
19200 && (INTVAL (operands[2]) == 3
19201 || INTVAL (operands[2]) == 5
19202 || INTVAL (operands[2]) == 9)"
19203 [(set (match_dup 0) (match_dup 1))
19205 (plus:SI (mult:SI (match_dup 0) (match_dup 2))
19207 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19211 [(set (match_operand:DI 0 "register_operand" "")
19212 (mult:DI (match_operand:DI 1 "register_operand" "")
19213 (match_operand:DI 2 "const_int_operand" "")))
19214 (clobber (reg:CC FLAGS_REG))])]
19216 && (INTVAL (operands[2]) == 3
19217 || INTVAL (operands[2]) == 5
19218 || INTVAL (operands[2]) == 9)"
19219 [(set (match_dup 0)
19220 (plus:DI (mult:DI (match_dup 1) (match_dup 2))
19222 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19226 [(set (match_operand:DI 0 "register_operand" "")
19227 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
19228 (match_operand:DI 2 "const_int_operand" "")))
19229 (clobber (reg:CC FLAGS_REG))])]
19232 && (INTVAL (operands[2]) == 3
19233 || INTVAL (operands[2]) == 5
19234 || INTVAL (operands[2]) == 9)"
19235 [(set (match_dup 0) (match_dup 1))
19237 (plus:DI (mult:DI (match_dup 0) (match_dup 2))
19239 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19241 ;; Imul $32bit_imm, mem, reg is vector decoded, while
19242 ;; imul $32bit_imm, reg, reg is direct decoded.
19244 [(match_scratch:DI 3 "r")
19245 (parallel [(set (match_operand:DI 0 "register_operand" "")
19246 (mult:DI (match_operand:DI 1 "memory_operand" "")
19247 (match_operand:DI 2 "immediate_operand" "")))
19248 (clobber (reg:CC FLAGS_REG))])]
19249 "TARGET_K8 && !optimize_size
19250 && (GET_CODE (operands[2]) != CONST_INT
19251 || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19252 [(set (match_dup 3) (match_dup 1))
19253 (parallel [(set (match_dup 0) (mult:DI (match_dup 3) (match_dup 2)))
19254 (clobber (reg:CC FLAGS_REG))])]
19258 [(match_scratch:SI 3 "r")
19259 (parallel [(set (match_operand:SI 0 "register_operand" "")
19260 (mult:SI (match_operand:SI 1 "memory_operand" "")
19261 (match_operand:SI 2 "immediate_operand" "")))
19262 (clobber (reg:CC FLAGS_REG))])]
19263 "TARGET_K8 && !optimize_size
19264 && (GET_CODE (operands[2]) != CONST_INT
19265 || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19266 [(set (match_dup 3) (match_dup 1))
19267 (parallel [(set (match_dup 0) (mult:SI (match_dup 3) (match_dup 2)))
19268 (clobber (reg:CC FLAGS_REG))])]
19272 [(match_scratch:SI 3 "r")
19273 (parallel [(set (match_operand:DI 0 "register_operand" "")
19275 (mult:SI (match_operand:SI 1 "memory_operand" "")
19276 (match_operand:SI 2 "immediate_operand" ""))))
19277 (clobber (reg:CC FLAGS_REG))])]
19278 "TARGET_K8 && !optimize_size
19279 && (GET_CODE (operands[2]) != CONST_INT
19280 || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19281 [(set (match_dup 3) (match_dup 1))
19282 (parallel [(set (match_dup 0) (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
19283 (clobber (reg:CC FLAGS_REG))])]
19286 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
19287 ;; Convert it into imul reg, reg
19288 ;; It would be better to force assembler to encode instruction using long
19289 ;; immediate, but there is apparently no way to do so.
19291 [(parallel [(set (match_operand:DI 0 "register_operand" "")
19292 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
19293 (match_operand:DI 2 "const_int_operand" "")))
19294 (clobber (reg:CC FLAGS_REG))])
19295 (match_scratch:DI 3 "r")]
19296 "TARGET_K8 && !optimize_size
19297 && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')"
19298 [(set (match_dup 3) (match_dup 2))
19299 (parallel [(set (match_dup 0) (mult:DI (match_dup 0) (match_dup 3)))
19300 (clobber (reg:CC FLAGS_REG))])]
19302 if (!rtx_equal_p (operands[0], operands[1]))
19303 emit_move_insn (operands[0], operands[1]);
19307 [(parallel [(set (match_operand:SI 0 "register_operand" "")
19308 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
19309 (match_operand:SI 2 "const_int_operand" "")))
19310 (clobber (reg:CC FLAGS_REG))])
19311 (match_scratch:SI 3 "r")]
19312 "TARGET_K8 && !optimize_size
19313 && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')"
19314 [(set (match_dup 3) (match_dup 2))
19315 (parallel [(set (match_dup 0) (mult:SI (match_dup 0) (match_dup 3)))
19316 (clobber (reg:CC FLAGS_REG))])]
19318 if (!rtx_equal_p (operands[0], operands[1]))
19319 emit_move_insn (operands[0], operands[1]);
19323 [(parallel [(set (match_operand:HI 0 "register_operand" "")
19324 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "")
19325 (match_operand:HI 2 "immediate_operand" "")))
19326 (clobber (reg:CC FLAGS_REG))])
19327 (match_scratch:HI 3 "r")]
19328 "TARGET_K8 && !optimize_size"
19329 [(set (match_dup 3) (match_dup 2))
19330 (parallel [(set (match_dup 0) (mult:HI (match_dup 0) (match_dup 3)))
19331 (clobber (reg:CC FLAGS_REG))])]
19333 if (!rtx_equal_p (operands[0], operands[1]))
19334 emit_move_insn (operands[0], operands[1]);
19337 ;; Call-value patterns last so that the wildcard operand does not
19338 ;; disrupt insn-recog's switch tables.
19340 (define_insn "*call_value_pop_0"
19341 [(set (match_operand 0 "" "")
19342 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
19343 (match_operand:SI 2 "" "")))
19344 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
19345 (match_operand:SI 3 "immediate_operand" "")))]
19348 if (SIBLING_CALL_P (insn))
19351 return "call\t%P1";
19353 [(set_attr "type" "callv")])
19355 (define_insn "*call_value_pop_1"
19356 [(set (match_operand 0 "" "")
19357 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
19358 (match_operand:SI 2 "" "")))
19359 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
19360 (match_operand:SI 3 "immediate_operand" "i")))]
19363 if (constant_call_address_operand (operands[1], Pmode))
19365 if (SIBLING_CALL_P (insn))
19368 return "call\t%P1";
19370 if (SIBLING_CALL_P (insn))
19373 return "call\t%A1";
19375 [(set_attr "type" "callv")])
19377 (define_insn "*call_value_0"
19378 [(set (match_operand 0 "" "")
19379 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
19380 (match_operand:SI 2 "" "")))]
19383 if (SIBLING_CALL_P (insn))
19386 return "call\t%P1";
19388 [(set_attr "type" "callv")])
19390 (define_insn "*call_value_0_rex64"
19391 [(set (match_operand 0 "" "")
19392 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
19393 (match_operand:DI 2 "const_int_operand" "")))]
19396 if (SIBLING_CALL_P (insn))
19399 return "call\t%P1";
19401 [(set_attr "type" "callv")])
19403 (define_insn "*call_value_1"
19404 [(set (match_operand 0 "" "")
19405 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
19406 (match_operand:SI 2 "" "")))]
19407 "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
19409 if (constant_call_address_operand (operands[1], Pmode))
19410 return "call\t%P1";
19411 return "call\t%A1";
19413 [(set_attr "type" "callv")])
19415 (define_insn "*sibcall_value_1"
19416 [(set (match_operand 0 "" "")
19417 (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "s,c,d,a"))
19418 (match_operand:SI 2 "" "")))]
19419 "SIBLING_CALL_P (insn) && !TARGET_64BIT"
19421 if (constant_call_address_operand (operands[1], Pmode))
19425 [(set_attr "type" "callv")])
19427 (define_insn "*call_value_1_rex64"
19428 [(set (match_operand 0 "" "")
19429 (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rsm"))
19430 (match_operand:DI 2 "" "")))]
19431 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
19433 if (constant_call_address_operand (operands[1], Pmode))
19434 return "call\t%P1";
19435 return "call\t%A1";
19437 [(set_attr "type" "callv")])
19439 (define_insn "*sibcall_value_1_rex64"
19440 [(set (match_operand 0 "" "")
19441 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
19442 (match_operand:DI 2 "" "")))]
19443 "SIBLING_CALL_P (insn) && TARGET_64BIT"
19445 [(set_attr "type" "callv")])
19447 (define_insn "*sibcall_value_1_rex64_v"
19448 [(set (match_operand 0 "" "")
19449 (call (mem:QI (reg:DI 40))
19450 (match_operand:DI 1 "" "")))]
19451 "SIBLING_CALL_P (insn) && TARGET_64BIT"
19453 [(set_attr "type" "callv")])
19455 ;; We used to use "int $5", in honor of #BR which maps to interrupt vector 5.
19456 ;; That, however, is usually mapped by the OS to SIGSEGV, which is often
19457 ;; caught for use by garbage collectors and the like. Using an insn that
19458 ;; maps to SIGILL makes it more likely the program will rightfully die.
19459 ;; Keeping with tradition, "6" is in honor of #UD.
19460 (define_insn "trap"
19461 [(trap_if (const_int 1) (const_int 6))]
19464 [(set_attr "length" "2")])
19466 (define_expand "sse_prologue_save"
19467 [(parallel [(set (match_operand:BLK 0 "" "")
19468 (unspec:BLK [(reg:DI 21)
19475 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
19476 (use (match_operand:DI 1 "register_operand" ""))
19477 (use (match_operand:DI 2 "immediate_operand" ""))
19478 (use (label_ref:DI (match_operand 3 "" "")))])]
19482 (define_insn "*sse_prologue_save_insn"
19483 [(set (mem:BLK (plus:DI (match_operand:DI 0 "register_operand" "R")
19484 (match_operand:DI 4 "const_int_operand" "n")))
19485 (unspec:BLK [(reg:DI 21)
19492 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
19493 (use (match_operand:DI 1 "register_operand" "r"))
19494 (use (match_operand:DI 2 "const_int_operand" "i"))
19495 (use (label_ref:DI (match_operand 3 "" "X")))]
19497 && INTVAL (operands[4]) + SSE_REGPARM_MAX * 16 - 16 < 128
19498 && INTVAL (operands[4]) + INTVAL (operands[2]) * 16 >= -128"
19502 operands[0] = gen_rtx_MEM (Pmode,
19503 gen_rtx_PLUS (Pmode, operands[0], operands[4]));
19504 output_asm_insn (\"jmp\\t%A1\", operands);
19505 for (i = SSE_REGPARM_MAX - 1; i >= INTVAL (operands[2]); i--)
19507 operands[4] = adjust_address (operands[0], DImode, i*16);
19508 operands[5] = gen_rtx_REG (TImode, SSE_REGNO (i));
19509 PUT_MODE (operands[4], TImode);
19510 if (GET_CODE (XEXP (operands[0], 0)) != PLUS)
19511 output_asm_insn (\"rex\", operands);
19512 output_asm_insn (\"movaps\\t{%5, %4|%4, %5}\", operands);
19514 (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
19515 CODE_LABEL_NUMBER (operands[3]));
19519 [(set_attr "type" "other")
19520 (set_attr "length_immediate" "0")
19521 (set_attr "length_address" "0")
19522 (set_attr "length" "135")
19523 (set_attr "memory" "store")
19524 (set_attr "modrm" "0")
19525 (set_attr "mode" "DI")])
19527 (define_expand "prefetch"
19528 [(prefetch (match_operand 0 "address_operand" "")
19529 (match_operand:SI 1 "const_int_operand" "")
19530 (match_operand:SI 2 "const_int_operand" ""))]
19531 "TARGET_PREFETCH_SSE || TARGET_3DNOW"
19533 int rw = INTVAL (operands[1]);
19534 int locality = INTVAL (operands[2]);
19536 gcc_assert (rw == 0 || rw == 1);
19537 gcc_assert (locality >= 0 && locality <= 3);
19538 gcc_assert (GET_MODE (operands[0]) == Pmode
19539 || GET_MODE (operands[0]) == VOIDmode);
19541 /* Use 3dNOW prefetch in case we are asking for write prefetch not
19542 supported by SSE counterpart or the SSE prefetch is not available
19543 (K6 machines). Otherwise use SSE prefetch as it allows specifying
19545 if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
19546 operands[2] = GEN_INT (3);
19548 operands[1] = const0_rtx;
19551 (define_insn "*prefetch_sse"
19552 [(prefetch (match_operand:SI 0 "address_operand" "p")
19554 (match_operand:SI 1 "const_int_operand" ""))]
19555 "TARGET_PREFETCH_SSE && !TARGET_64BIT"
19557 static const char * const patterns[4] = {
19558 "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
19561 int locality = INTVAL (operands[1]);
19562 gcc_assert (locality >= 0 && locality <= 3);
19564 return patterns[locality];
19566 [(set_attr "type" "sse")
19567 (set_attr "memory" "none")])
19569 (define_insn "*prefetch_sse_rex"
19570 [(prefetch (match_operand:DI 0 "address_operand" "p")
19572 (match_operand:SI 1 "const_int_operand" ""))]
19573 "TARGET_PREFETCH_SSE && TARGET_64BIT"
19575 static const char * const patterns[4] = {
19576 "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
19579 int locality = INTVAL (operands[1]);
19580 gcc_assert (locality >= 0 && locality <= 3);
19582 return patterns[locality];
19584 [(set_attr "type" "sse")
19585 (set_attr "memory" "none")])
19587 (define_insn "*prefetch_3dnow"
19588 [(prefetch (match_operand:SI 0 "address_operand" "p")
19589 (match_operand:SI 1 "const_int_operand" "n")
19591 "TARGET_3DNOW && !TARGET_64BIT"
19593 if (INTVAL (operands[1]) == 0)
19594 return "prefetch\t%a0";
19596 return "prefetchw\t%a0";
19598 [(set_attr "type" "mmx")
19599 (set_attr "memory" "none")])
19601 (define_insn "*prefetch_3dnow_rex"
19602 [(prefetch (match_operand:DI 0 "address_operand" "p")
19603 (match_operand:SI 1 "const_int_operand" "n")
19605 "TARGET_3DNOW && TARGET_64BIT"
19607 if (INTVAL (operands[1]) == 0)
19608 return "prefetch\t%a0";
19610 return "prefetchw\t%a0";
19612 [(set_attr "type" "mmx")
19613 (set_attr "memory" "none")])
19615 (define_expand "stack_protect_set"
19616 [(match_operand 0 "memory_operand" "")
19617 (match_operand 1 "memory_operand" "")]
19620 #ifdef TARGET_THREAD_SSP_OFFSET
19622 emit_insn (gen_stack_tls_protect_set_di (operands[0],
19623 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
19625 emit_insn (gen_stack_tls_protect_set_si (operands[0],
19626 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
19629 emit_insn (gen_stack_protect_set_di (operands[0], operands[1]));
19631 emit_insn (gen_stack_protect_set_si (operands[0], operands[1]));
19636 (define_insn "stack_protect_set_si"
19637 [(set (match_operand:SI 0 "memory_operand" "=m")
19638 (unspec:SI [(match_operand:SI 1 "memory_operand" "m")] UNSPEC_SP_SET))
19639 (set (match_scratch:SI 2 "=&r") (const_int 0))
19640 (clobber (reg:CC FLAGS_REG))]
19642 "mov{l}\t{%1, %2|%2, %1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
19643 [(set_attr "type" "multi")])
19645 (define_insn "stack_protect_set_di"
19646 [(set (match_operand:DI 0 "memory_operand" "=m")
19647 (unspec:DI [(match_operand:DI 1 "memory_operand" "m")] UNSPEC_SP_SET))
19648 (set (match_scratch:DI 2 "=&r") (const_int 0))
19649 (clobber (reg:CC FLAGS_REG))]
19651 "mov{q}\t{%1, %2|%2, %1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
19652 [(set_attr "type" "multi")])
19654 (define_insn "stack_tls_protect_set_si"
19655 [(set (match_operand:SI 0 "memory_operand" "=m")
19656 (unspec:SI [(match_operand:SI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
19657 (set (match_scratch:SI 2 "=&r") (const_int 0))
19658 (clobber (reg:CC FLAGS_REG))]
19660 "mov{l}\t{%%gs:%P1, %2|%2, DWORD PTR %%gs:%P1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
19661 [(set_attr "type" "multi")])
19663 (define_insn "stack_tls_protect_set_di"
19664 [(set (match_operand:DI 0 "memory_operand" "=m")
19665 (unspec:DI [(match_operand:DI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
19666 (set (match_scratch:DI 2 "=&r") (const_int 0))
19667 (clobber (reg:CC FLAGS_REG))]
19669 "mov{q}\t{%%fs:%P1, %2|%2, QWORD PTR %%fs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
19670 [(set_attr "type" "multi")])
19672 (define_expand "stack_protect_test"
19673 [(match_operand 0 "memory_operand" "")
19674 (match_operand 1 "memory_operand" "")
19675 (match_operand 2 "" "")]
19678 rtx flags = gen_rtx_REG (CCZmode, FLAGS_REG);
19679 ix86_compare_op0 = operands[0];
19680 ix86_compare_op1 = operands[1];
19681 ix86_compare_emitted = flags;
19683 #ifdef TARGET_THREAD_SSP_OFFSET
19685 emit_insn (gen_stack_tls_protect_test_di (flags, operands[0],
19686 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
19688 emit_insn (gen_stack_tls_protect_test_si (flags, operands[0],
19689 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
19692 emit_insn (gen_stack_protect_test_di (flags, operands[0], operands[1]));
19694 emit_insn (gen_stack_protect_test_si (flags, operands[0], operands[1]));
19696 emit_jump_insn (gen_beq (operands[2]));
19700 (define_insn "stack_protect_test_si"
19701 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
19702 (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
19703 (match_operand:SI 2 "memory_operand" "m")]
19705 (clobber (match_scratch:SI 3 "=&r"))]
19707 "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%2, %3|%3, %2}"
19708 [(set_attr "type" "multi")])
19710 (define_insn "stack_protect_test_di"
19711 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
19712 (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
19713 (match_operand:DI 2 "memory_operand" "m")]
19715 (clobber (match_scratch:DI 3 "=&r"))]
19717 "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%2, %3|%3, %2}"
19718 [(set_attr "type" "multi")])
19720 (define_insn "stack_tls_protect_test_si"
19721 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
19722 (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
19723 (match_operand:SI 2 "const_int_operand" "i")]
19724 UNSPEC_SP_TLS_TEST))
19725 (clobber (match_scratch:SI 3 "=r"))]
19727 "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%%gs:%P2, %3|%3, DWORD PTR %%gs:%P2}"
19728 [(set_attr "type" "multi")])
19730 (define_insn "stack_tls_protect_test_di"
19731 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
19732 (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
19733 (match_operand:DI 2 "const_int_operand" "i")]
19734 UNSPEC_SP_TLS_TEST))
19735 (clobber (match_scratch:DI 3 "=r"))]
19737 "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%fs:%P2, %3|%3, QWORD PTR %%fs:%P2}"
19738 [(set_attr "type" "multi")])
19742 (include "sync.md")