1 ;; GCC machine description for IA-32 and x86-64.
2 ;; Copyright (C) 1988, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
3 ;; 2001, 2002, 2003, 2004, 2005
4 ;; Free Software Foundation, Inc.
5 ;; Mostly by William Schelter.
6 ;; x86_64 support added by Jan Hubicka
8 ;; This file is part of GCC.
10 ;; GCC is free software; you can redistribute it and/or modify
11 ;; it under the terms of the GNU General Public License as published by
12 ;; the Free Software Foundation; either version 2, or (at your option)
15 ;; GCC is distributed in the hope that it will be useful,
16 ;; but WITHOUT ANY WARRANTY; without even the implied warranty of
17 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 ;; GNU General Public License for more details.
20 ;; You should have received a copy of the GNU General Public License
21 ;; along with GCC; see the file COPYING. If not, write to
22 ;; the Free Software Foundation, 51 Franklin Street, Fifth Floor,
23 ;; Boston, MA 02110-1301, USA. */
25 ;; The original PO technology requires these to be ordered by speed,
26 ;; so that assigner will pick the fastest.
28 ;; See file "rtl.def" for documentation on define_insn, match_*, et. al.
30 ;; Macro REG_CLASS_FROM_LETTER in file i386.h defines the register
31 ;; constraint letters.
33 ;; The special asm out single letter directives following a '%' are:
34 ;; 'z' mov%z1 would be movl, movw, or movb depending on the mode of
36 ;; 'L' Print the opcode suffix for a 32-bit integer opcode.
37 ;; 'W' Print the opcode suffix for a 16-bit integer opcode.
38 ;; 'B' Print the opcode suffix for an 8-bit integer opcode.
39 ;; 'Q' Print the opcode suffix for a 64-bit float opcode.
40 ;; 'S' Print the opcode suffix for a 32-bit float opcode.
41 ;; 'T' Print the opcode suffix for an 80-bit extended real XFmode float opcode.
42 ;; 'J' Print the appropriate jump operand.
44 ;; 'b' Print the QImode name of the register for the indicated operand.
45 ;; %b0 would print %al if operands[0] is reg 0.
46 ;; 'w' Likewise, print the HImode name of the register.
47 ;; 'k' Likewise, print the SImode name of the register.
48 ;; 'h' Print the QImode name for a "high" register, either ah, bh, ch or dh.
49 ;; 'y' Print "st(0)" instead of "st" as a register.
54 [; Relocation specifiers
66 (UNSPEC_STACK_ALLOC 11)
68 (UNSPEC_SSE_PROLOGUE_SAVE 13)
75 (UNSPEC_TLS_LD_BASE 18)
77 ; Other random patterns
87 ; For SSE/MMX support:
88 (UNSPEC_FIX_NOTRUNC 30)
96 (UNSPEC_NOP 38) ; prevents combiner cleverness
107 ; Generic math support
109 (UNSPEC_IEEE_MIN 51) ; not commutative
110 (UNSPEC_IEEE_MAX 52) ; not commutative
123 (UNSPEC_FRNDINT_FLOOR 70)
124 (UNSPEC_FRNDINT_CEIL 71)
125 (UNSPEC_FRNDINT_TRUNC 72)
126 (UNSPEC_FRNDINT_MASK_PM 73)
127 (UNSPEC_FIST_FLOOR 74)
128 (UNSPEC_FIST_CEIL 75)
130 ; x87 Double output FP
131 (UNSPEC_SINCOS_COS 80)
132 (UNSPEC_SINCOS_SIN 81)
135 (UNSPEC_XTRACT_FRACT 84)
136 (UNSPEC_XTRACT_EXP 85)
137 (UNSPEC_FSCALE_FRACT 86)
138 (UNSPEC_FSCALE_EXP 87)
147 (UNSPEC_SP_TLS_SET 102)
148 (UNSPEC_SP_TLS_TEST 103)
152 [(UNSPECV_BLOCKAGE 0)
153 (UNSPECV_STACK_PROBE 1)
162 (UNSPECV_CMPXCHG_1 10)
163 (UNSPECV_CMPXCHG_2 11)
168 ;; Registers by name.
177 ;; Insns whose names begin with "x86_" are emitted by gen_FOO calls
180 ;; In C guard expressions, put expressions which may be compile-time
181 ;; constants first. This allows for better optimization. For
182 ;; example, write "TARGET_64BIT && reload_completed", not
183 ;; "reload_completed && TARGET_64BIT".
186 ;; Processor type. This attribute must exactly match the processor_type
187 ;; enumeration in i386.h.
188 (define_attr "cpu" "i386,i486,pentium,pentiumpro,k6,athlon,pentium4,k8,nocona"
189 (const (symbol_ref "ix86_tune")))
191 ;; A basic instruction type. Refinements due to arguments to be
192 ;; provided in other attributes.
195 alu,alu1,negnot,imov,imovx,lea,
196 incdec,ishift,ishift1,rotate,rotate1,imul,idiv,
197 icmp,test,ibr,setcc,icmov,
198 push,pop,call,callv,leave,
200 fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint,
201 sselog,sselog1,sseiadd,sseishft,sseimul,
202 sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv,
203 mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft"
204 (const_string "other"))
206 ;; Main data type used by the insn
208 "unknown,none,QI,HI,SI,DI,SF,DF,XF,TI,V4SF,V2DF,V2SF,V1DF"
209 (const_string "unknown"))
211 ;; The CPU unit operations uses.
212 (define_attr "unit" "integer,i387,sse,mmx,unknown"
213 (cond [(eq_attr "type" "fmov,fop,fsgn,fmul,fdiv,fpspc,fcmov,fcmp,fxch,fistp,fisttp,frndint")
214 (const_string "i387")
215 (eq_attr "type" "sselog,sselog1,sseiadd,sseishft,sseimul,
216 sse,ssemov,sseadd,ssemul,ssecmp,ssecomi,ssecvt,sseicvt,ssediv")
218 (eq_attr "type" "mmx,mmxmov,mmxadd,mmxmul,mmxcmp,mmxcvt,mmxshft")
220 (eq_attr "type" "other")
221 (const_string "unknown")]
222 (const_string "integer")))
224 ;; The (bounding maximum) length of an instruction immediate.
225 (define_attr "length_immediate" ""
226 (cond [(eq_attr "type" "incdec,setcc,icmov,str,cld,lea,other,multi,idiv,leave")
228 (eq_attr "unit" "i387,sse,mmx")
230 (eq_attr "type" "alu,alu1,negnot,imovx,ishift,rotate,ishift1,rotate1,
232 (symbol_ref "ix86_attr_length_immediate_default(insn,1)")
233 (eq_attr "type" "imov,test")
234 (symbol_ref "ix86_attr_length_immediate_default(insn,0)")
235 (eq_attr "type" "call")
236 (if_then_else (match_operand 0 "constant_call_address_operand" "")
239 (eq_attr "type" "callv")
240 (if_then_else (match_operand 1 "constant_call_address_operand" "")
243 ;; We don't know the size before shorten_branches. Expect
244 ;; the instruction to fit for better scheduling.
245 (eq_attr "type" "ibr")
248 (symbol_ref "/* Update immediate_length and other attributes! */
249 gcc_unreachable (),1")))
251 ;; The (bounding maximum) length of an instruction address.
252 (define_attr "length_address" ""
253 (cond [(eq_attr "type" "str,cld,other,multi,fxch")
255 (and (eq_attr "type" "call")
256 (match_operand 0 "constant_call_address_operand" ""))
258 (and (eq_attr "type" "callv")
259 (match_operand 1 "constant_call_address_operand" ""))
262 (symbol_ref "ix86_attr_length_address_default (insn)")))
264 ;; Set when length prefix is used.
265 (define_attr "prefix_data16" ""
266 (if_then_else (ior (eq_attr "mode" "HI")
267 (and (eq_attr "unit" "sse") (eq_attr "mode" "V2DF")))
271 ;; Set when string REP prefix is used.
272 (define_attr "prefix_rep" ""
273 (if_then_else (and (eq_attr "unit" "sse") (eq_attr "mode" "SF,DF"))
277 ;; Set when 0f opcode prefix is used.
278 (define_attr "prefix_0f" ""
280 (ior (eq_attr "type" "imovx,setcc,icmov")
281 (eq_attr "unit" "sse,mmx"))
285 ;; Set when REX opcode prefix is used.
286 (define_attr "prefix_rex" ""
287 (cond [(and (eq_attr "mode" "DI")
288 (eq_attr "type" "!push,pop,call,callv,leave,ibr"))
290 (and (eq_attr "mode" "QI")
291 (ne (symbol_ref "x86_extended_QIreg_mentioned_p (insn)")
294 (ne (symbol_ref "x86_extended_reg_mentioned_p (insn)")
300 ;; Set when modrm byte is used.
301 (define_attr "modrm" ""
302 (cond [(eq_attr "type" "str,cld,leave")
304 (eq_attr "unit" "i387")
306 (and (eq_attr "type" "incdec")
307 (ior (match_operand:SI 1 "register_operand" "")
308 (match_operand:HI 1 "register_operand" "")))
310 (and (eq_attr "type" "push")
311 (not (match_operand 1 "memory_operand" "")))
313 (and (eq_attr "type" "pop")
314 (not (match_operand 0 "memory_operand" "")))
316 (and (eq_attr "type" "imov")
317 (and (match_operand 0 "register_operand" "")
318 (match_operand 1 "immediate_operand" "")))
320 (and (eq_attr "type" "call")
321 (match_operand 0 "constant_call_address_operand" ""))
323 (and (eq_attr "type" "callv")
324 (match_operand 1 "constant_call_address_operand" ""))
329 ;; The (bounding maximum) length of an instruction in bytes.
330 ;; ??? fistp and frndint are in fact fldcw/{fistp,frndint}/fldcw sequences.
331 ;; Later we may want to split them and compute proper length as for
333 (define_attr "length" ""
334 (cond [(eq_attr "type" "other,multi,fistp,frndint")
336 (eq_attr "type" "fcmp")
338 (eq_attr "unit" "i387")
340 (plus (attr "prefix_data16")
341 (attr "length_address")))]
342 (plus (plus (attr "modrm")
343 (plus (attr "prefix_0f")
344 (plus (attr "prefix_rex")
346 (plus (attr "prefix_rep")
347 (plus (attr "prefix_data16")
348 (plus (attr "length_immediate")
349 (attr "length_address")))))))
351 ;; The `memory' attribute is `none' if no memory is referenced, `load' or
352 ;; `store' if there is a simple memory reference therein, or `unknown'
353 ;; if the instruction is complex.
355 (define_attr "memory" "none,load,store,both,unknown"
356 (cond [(eq_attr "type" "other,multi,str")
357 (const_string "unknown")
358 (eq_attr "type" "lea,fcmov,fpspc,cld")
359 (const_string "none")
360 (eq_attr "type" "fistp,leave")
361 (const_string "both")
362 (eq_attr "type" "frndint")
363 (const_string "load")
364 (eq_attr "type" "push")
365 (if_then_else (match_operand 1 "memory_operand" "")
366 (const_string "both")
367 (const_string "store"))
368 (eq_attr "type" "pop")
369 (if_then_else (match_operand 0 "memory_operand" "")
370 (const_string "both")
371 (const_string "load"))
372 (eq_attr "type" "setcc")
373 (if_then_else (match_operand 0 "memory_operand" "")
374 (const_string "store")
375 (const_string "none"))
376 (eq_attr "type" "icmp,test,ssecmp,ssecomi,mmxcmp,fcmp")
377 (if_then_else (ior (match_operand 0 "memory_operand" "")
378 (match_operand 1 "memory_operand" ""))
379 (const_string "load")
380 (const_string "none"))
381 (eq_attr "type" "ibr")
382 (if_then_else (match_operand 0 "memory_operand" "")
383 (const_string "load")
384 (const_string "none"))
385 (eq_attr "type" "call")
386 (if_then_else (match_operand 0 "constant_call_address_operand" "")
387 (const_string "none")
388 (const_string "load"))
389 (eq_attr "type" "callv")
390 (if_then_else (match_operand 1 "constant_call_address_operand" "")
391 (const_string "none")
392 (const_string "load"))
393 (and (eq_attr "type" "alu1,negnot,ishift1,sselog1")
394 (match_operand 1 "memory_operand" ""))
395 (const_string "both")
396 (and (match_operand 0 "memory_operand" "")
397 (match_operand 1 "memory_operand" ""))
398 (const_string "both")
399 (match_operand 0 "memory_operand" "")
400 (const_string "store")
401 (match_operand 1 "memory_operand" "")
402 (const_string "load")
404 "!alu1,negnot,ishift1,
405 imov,imovx,icmp,test,
407 sse,ssemov,ssecmp,ssecomi,ssecvt,sseicvt,sselog1,
408 mmx,mmxmov,mmxcmp,mmxcvt")
409 (match_operand 2 "memory_operand" ""))
410 (const_string "load")
411 (and (eq_attr "type" "icmov")
412 (match_operand 3 "memory_operand" ""))
413 (const_string "load")
415 (const_string "none")))
417 ;; Indicates if an instruction has both an immediate and a displacement.
419 (define_attr "imm_disp" "false,true,unknown"
420 (cond [(eq_attr "type" "other,multi")
421 (const_string "unknown")
422 (and (eq_attr "type" "icmp,test,imov,alu1,ishift1,rotate1")
423 (and (match_operand 0 "memory_displacement_operand" "")
424 (match_operand 1 "immediate_operand" "")))
425 (const_string "true")
426 (and (eq_attr "type" "alu,ishift,rotate,imul,idiv")
427 (and (match_operand 0 "memory_displacement_operand" "")
428 (match_operand 2 "immediate_operand" "")))
429 (const_string "true")
431 (const_string "false")))
433 ;; Indicates if an FP operation has an integer source.
435 (define_attr "fp_int_src" "false,true"
436 (const_string "false"))
438 ;; Defines rounding mode of an FP operation.
440 (define_attr "i387_cw" "trunc,floor,ceil,mask_pm,uninitialized,any"
441 (const_string "any"))
443 ;; Describe a user's asm statement.
444 (define_asm_attributes
445 [(set_attr "length" "128")
446 (set_attr "type" "multi")])
448 ;; All x87 floating point modes
449 (define_mode_macro X87MODEF [SF DF XF])
451 ;; All integer modes handled by x87 fisttp operator.
452 (define_mode_macro X87MODEI [HI SI DI])
454 ;; All integer modes handled by integer x87 operators.
455 (define_mode_macro X87MODEI12 [HI SI])
457 ;; All SSE floating point modes
458 (define_mode_macro SSEMODEF [SF DF])
460 ;; All integer modes handled by SSE cvtts?2si* operators.
461 (define_mode_macro SSEMODEI24 [SI DI])
464 ;; Scheduling descriptions
466 (include "pentium.md")
469 (include "athlon.md")
472 ;; Operand and operator predicates
474 (include "predicates.md")
477 ;; Compare instructions.
479 ;; All compare insns have expanders that save the operands away without
480 ;; actually generating RTL. The bCOND or sCOND (emitted immediately
481 ;; after the cmp) will actually emit the cmpM.
483 (define_expand "cmpti"
484 [(set (reg:CC FLAGS_REG)
485 (compare:CC (match_operand:TI 0 "nonimmediate_operand" "")
486 (match_operand:TI 1 "x86_64_general_operand" "")))]
489 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
490 operands[0] = force_reg (TImode, operands[0]);
491 ix86_compare_op0 = operands[0];
492 ix86_compare_op1 = operands[1];
496 (define_expand "cmpdi"
497 [(set (reg:CC FLAGS_REG)
498 (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
499 (match_operand:DI 1 "x86_64_general_operand" "")))]
502 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
503 operands[0] = force_reg (DImode, operands[0]);
504 ix86_compare_op0 = operands[0];
505 ix86_compare_op1 = operands[1];
509 (define_expand "cmpsi"
510 [(set (reg:CC FLAGS_REG)
511 (compare:CC (match_operand:SI 0 "cmpsi_operand" "")
512 (match_operand:SI 1 "general_operand" "")))]
515 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
516 operands[0] = force_reg (SImode, operands[0]);
517 ix86_compare_op0 = operands[0];
518 ix86_compare_op1 = operands[1];
522 (define_expand "cmphi"
523 [(set (reg:CC FLAGS_REG)
524 (compare:CC (match_operand:HI 0 "nonimmediate_operand" "")
525 (match_operand:HI 1 "general_operand" "")))]
528 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
529 operands[0] = force_reg (HImode, operands[0]);
530 ix86_compare_op0 = operands[0];
531 ix86_compare_op1 = operands[1];
535 (define_expand "cmpqi"
536 [(set (reg:CC FLAGS_REG)
537 (compare:CC (match_operand:QI 0 "nonimmediate_operand" "")
538 (match_operand:QI 1 "general_operand" "")))]
541 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
542 operands[0] = force_reg (QImode, operands[0]);
543 ix86_compare_op0 = operands[0];
544 ix86_compare_op1 = operands[1];
548 (define_insn "cmpdi_ccno_1_rex64"
549 [(set (reg FLAGS_REG)
550 (compare (match_operand:DI 0 "nonimmediate_operand" "r,?mr")
551 (match_operand:DI 1 "const0_operand" "n,n")))]
552 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
554 test{q}\t{%0, %0|%0, %0}
555 cmp{q}\t{%1, %0|%0, %1}"
556 [(set_attr "type" "test,icmp")
557 (set_attr "length_immediate" "0,1")
558 (set_attr "mode" "DI")])
560 (define_insn "*cmpdi_minus_1_rex64"
561 [(set (reg FLAGS_REG)
562 (compare (minus:DI (match_operand:DI 0 "nonimmediate_operand" "rm,r")
563 (match_operand:DI 1 "x86_64_general_operand" "re,mr"))
565 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)"
566 "cmp{q}\t{%1, %0|%0, %1}"
567 [(set_attr "type" "icmp")
568 (set_attr "mode" "DI")])
570 (define_expand "cmpdi_1_rex64"
571 [(set (reg:CC FLAGS_REG)
572 (compare:CC (match_operand:DI 0 "nonimmediate_operand" "")
573 (match_operand:DI 1 "general_operand" "")))]
577 (define_insn "cmpdi_1_insn_rex64"
578 [(set (reg FLAGS_REG)
579 (compare (match_operand:DI 0 "nonimmediate_operand" "mr,r")
580 (match_operand:DI 1 "x86_64_general_operand" "re,mr")))]
581 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
582 "cmp{q}\t{%1, %0|%0, %1}"
583 [(set_attr "type" "icmp")
584 (set_attr "mode" "DI")])
587 (define_insn "*cmpsi_ccno_1"
588 [(set (reg FLAGS_REG)
589 (compare (match_operand:SI 0 "nonimmediate_operand" "r,?mr")
590 (match_operand:SI 1 "const0_operand" "n,n")))]
591 "ix86_match_ccmode (insn, CCNOmode)"
593 test{l}\t{%0, %0|%0, %0}
594 cmp{l}\t{%1, %0|%0, %1}"
595 [(set_attr "type" "test,icmp")
596 (set_attr "length_immediate" "0,1")
597 (set_attr "mode" "SI")])
599 (define_insn "*cmpsi_minus_1"
600 [(set (reg FLAGS_REG)
601 (compare (minus:SI (match_operand:SI 0 "nonimmediate_operand" "rm,r")
602 (match_operand:SI 1 "general_operand" "ri,mr"))
604 "ix86_match_ccmode (insn, CCGOCmode)"
605 "cmp{l}\t{%1, %0|%0, %1}"
606 [(set_attr "type" "icmp")
607 (set_attr "mode" "SI")])
609 (define_expand "cmpsi_1"
610 [(set (reg:CC FLAGS_REG)
611 (compare:CC (match_operand:SI 0 "nonimmediate_operand" "rm,r")
612 (match_operand:SI 1 "general_operand" "ri,mr")))]
616 (define_insn "*cmpsi_1_insn"
617 [(set (reg FLAGS_REG)
618 (compare (match_operand:SI 0 "nonimmediate_operand" "rm,r")
619 (match_operand:SI 1 "general_operand" "ri,mr")))]
620 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
621 && ix86_match_ccmode (insn, CCmode)"
622 "cmp{l}\t{%1, %0|%0, %1}"
623 [(set_attr "type" "icmp")
624 (set_attr "mode" "SI")])
626 (define_insn "*cmphi_ccno_1"
627 [(set (reg FLAGS_REG)
628 (compare (match_operand:HI 0 "nonimmediate_operand" "r,?mr")
629 (match_operand:HI 1 "const0_operand" "n,n")))]
630 "ix86_match_ccmode (insn, CCNOmode)"
632 test{w}\t{%0, %0|%0, %0}
633 cmp{w}\t{%1, %0|%0, %1}"
634 [(set_attr "type" "test,icmp")
635 (set_attr "length_immediate" "0,1")
636 (set_attr "mode" "HI")])
638 (define_insn "*cmphi_minus_1"
639 [(set (reg FLAGS_REG)
640 (compare (minus:HI (match_operand:HI 0 "nonimmediate_operand" "rm,r")
641 (match_operand:HI 1 "general_operand" "ri,mr"))
643 "ix86_match_ccmode (insn, CCGOCmode)"
644 "cmp{w}\t{%1, %0|%0, %1}"
645 [(set_attr "type" "icmp")
646 (set_attr "mode" "HI")])
648 (define_insn "*cmphi_1"
649 [(set (reg FLAGS_REG)
650 (compare (match_operand:HI 0 "nonimmediate_operand" "rm,r")
651 (match_operand:HI 1 "general_operand" "ri,mr")))]
652 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
653 && ix86_match_ccmode (insn, CCmode)"
654 "cmp{w}\t{%1, %0|%0, %1}"
655 [(set_attr "type" "icmp")
656 (set_attr "mode" "HI")])
658 (define_insn "*cmpqi_ccno_1"
659 [(set (reg FLAGS_REG)
660 (compare (match_operand:QI 0 "nonimmediate_operand" "q,?mq")
661 (match_operand:QI 1 "const0_operand" "n,n")))]
662 "ix86_match_ccmode (insn, CCNOmode)"
664 test{b}\t{%0, %0|%0, %0}
665 cmp{b}\t{$0, %0|%0, 0}"
666 [(set_attr "type" "test,icmp")
667 (set_attr "length_immediate" "0,1")
668 (set_attr "mode" "QI")])
670 (define_insn "*cmpqi_1"
671 [(set (reg FLAGS_REG)
672 (compare (match_operand:QI 0 "nonimmediate_operand" "qm,q")
673 (match_operand:QI 1 "general_operand" "qi,mq")))]
674 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
675 && ix86_match_ccmode (insn, CCmode)"
676 "cmp{b}\t{%1, %0|%0, %1}"
677 [(set_attr "type" "icmp")
678 (set_attr "mode" "QI")])
680 (define_insn "*cmpqi_minus_1"
681 [(set (reg FLAGS_REG)
682 (compare (minus:QI (match_operand:QI 0 "nonimmediate_operand" "qm,q")
683 (match_operand:QI 1 "general_operand" "qi,mq"))
685 "ix86_match_ccmode (insn, CCGOCmode)"
686 "cmp{b}\t{%1, %0|%0, %1}"
687 [(set_attr "type" "icmp")
688 (set_attr "mode" "QI")])
690 (define_insn "*cmpqi_ext_1"
691 [(set (reg FLAGS_REG)
693 (match_operand:QI 0 "general_operand" "Qm")
696 (match_operand 1 "ext_register_operand" "Q")
699 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
700 "cmp{b}\t{%h1, %0|%0, %h1}"
701 [(set_attr "type" "icmp")
702 (set_attr "mode" "QI")])
704 (define_insn "*cmpqi_ext_1_rex64"
705 [(set (reg FLAGS_REG)
707 (match_operand:QI 0 "register_operand" "Q")
710 (match_operand 1 "ext_register_operand" "Q")
713 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
714 "cmp{b}\t{%h1, %0|%0, %h1}"
715 [(set_attr "type" "icmp")
716 (set_attr "mode" "QI")])
718 (define_insn "*cmpqi_ext_2"
719 [(set (reg FLAGS_REG)
723 (match_operand 0 "ext_register_operand" "Q")
726 (match_operand:QI 1 "const0_operand" "n")))]
727 "ix86_match_ccmode (insn, CCNOmode)"
729 [(set_attr "type" "test")
730 (set_attr "length_immediate" "0")
731 (set_attr "mode" "QI")])
733 (define_expand "cmpqi_ext_3"
734 [(set (reg:CC FLAGS_REG)
738 (match_operand 0 "ext_register_operand" "")
741 (match_operand:QI 1 "general_operand" "")))]
745 (define_insn "cmpqi_ext_3_insn"
746 [(set (reg FLAGS_REG)
750 (match_operand 0 "ext_register_operand" "Q")
753 (match_operand:QI 1 "general_operand" "Qmn")))]
754 "!TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
755 "cmp{b}\t{%1, %h0|%h0, %1}"
756 [(set_attr "type" "icmp")
757 (set_attr "mode" "QI")])
759 (define_insn "cmpqi_ext_3_insn_rex64"
760 [(set (reg FLAGS_REG)
764 (match_operand 0 "ext_register_operand" "Q")
767 (match_operand:QI 1 "nonmemory_operand" "Qn")))]
768 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)"
769 "cmp{b}\t{%1, %h0|%h0, %1}"
770 [(set_attr "type" "icmp")
771 (set_attr "mode" "QI")])
773 (define_insn "*cmpqi_ext_4"
774 [(set (reg FLAGS_REG)
778 (match_operand 0 "ext_register_operand" "Q")
783 (match_operand 1 "ext_register_operand" "Q")
786 "ix86_match_ccmode (insn, CCmode)"
787 "cmp{b}\t{%h1, %h0|%h0, %h1}"
788 [(set_attr "type" "icmp")
789 (set_attr "mode" "QI")])
791 ;; These implement float point compares.
792 ;; %%% See if we can get away with VOIDmode operands on the actual insns,
793 ;; which would allow mix and match FP modes on the compares. Which is what
794 ;; the old patterns did, but with many more of them.
796 (define_expand "cmpxf"
797 [(set (reg:CC FLAGS_REG)
798 (compare:CC (match_operand:XF 0 "nonmemory_operand" "")
799 (match_operand:XF 1 "nonmemory_operand" "")))]
802 ix86_compare_op0 = operands[0];
803 ix86_compare_op1 = operands[1];
807 (define_expand "cmpdf"
808 [(set (reg:CC FLAGS_REG)
809 (compare:CC (match_operand:DF 0 "cmp_fp_expander_operand" "")
810 (match_operand:DF 1 "cmp_fp_expander_operand" "")))]
811 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
813 ix86_compare_op0 = operands[0];
814 ix86_compare_op1 = operands[1];
818 (define_expand "cmpsf"
819 [(set (reg:CC FLAGS_REG)
820 (compare:CC (match_operand:SF 0 "cmp_fp_expander_operand" "")
821 (match_operand:SF 1 "cmp_fp_expander_operand" "")))]
822 "TARGET_80387 || TARGET_SSE_MATH"
824 ix86_compare_op0 = operands[0];
825 ix86_compare_op1 = operands[1];
829 ;; FP compares, step 1:
830 ;; Set the FP condition codes.
832 ;; CCFPmode compare with exceptions
833 ;; CCFPUmode compare with no exceptions
835 ;; We may not use "#" to split and emit these, since the REG_DEAD notes
836 ;; used to manage the reg stack popping would not be preserved.
838 (define_insn "*cmpfp_0"
839 [(set (match_operand:HI 0 "register_operand" "=a")
842 (match_operand 1 "register_operand" "f")
843 (match_operand 2 "const0_operand" "X"))]
846 && FLOAT_MODE_P (GET_MODE (operands[1]))
847 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
848 "* return output_fp_compare (insn, operands, 0, 0);"
849 [(set_attr "type" "multi")
850 (set_attr "unit" "i387")
852 (cond [(match_operand:SF 1 "" "")
854 (match_operand:DF 1 "" "")
857 (const_string "XF")))])
859 (define_insn "*cmpfp_sf"
860 [(set (match_operand:HI 0 "register_operand" "=a")
863 (match_operand:SF 1 "register_operand" "f")
864 (match_operand:SF 2 "nonimmediate_operand" "fm"))]
867 "* return output_fp_compare (insn, operands, 0, 0);"
868 [(set_attr "type" "multi")
869 (set_attr "unit" "i387")
870 (set_attr "mode" "SF")])
872 (define_insn "*cmpfp_df"
873 [(set (match_operand:HI 0 "register_operand" "=a")
876 (match_operand:DF 1 "register_operand" "f")
877 (match_operand:DF 2 "nonimmediate_operand" "fm"))]
880 "* return output_fp_compare (insn, operands, 0, 0);"
881 [(set_attr "type" "multi")
882 (set_attr "unit" "i387")
883 (set_attr "mode" "DF")])
885 (define_insn "*cmpfp_xf"
886 [(set (match_operand:HI 0 "register_operand" "=a")
889 (match_operand:XF 1 "register_operand" "f")
890 (match_operand:XF 2 "register_operand" "f"))]
893 "* return output_fp_compare (insn, operands, 0, 0);"
894 [(set_attr "type" "multi")
895 (set_attr "unit" "i387")
896 (set_attr "mode" "XF")])
898 (define_insn "*cmpfp_u"
899 [(set (match_operand:HI 0 "register_operand" "=a")
902 (match_operand 1 "register_operand" "f")
903 (match_operand 2 "register_operand" "f"))]
906 && FLOAT_MODE_P (GET_MODE (operands[1]))
907 && GET_MODE (operands[1]) == GET_MODE (operands[2])"
908 "* return output_fp_compare (insn, operands, 0, 1);"
909 [(set_attr "type" "multi")
910 (set_attr "unit" "i387")
912 (cond [(match_operand:SF 1 "" "")
914 (match_operand:DF 1 "" "")
917 (const_string "XF")))])
919 (define_insn "*cmpfp_<mode>"
920 [(set (match_operand:HI 0 "register_operand" "=a")
923 (match_operand 1 "register_operand" "f")
924 (match_operator 3 "float_operator"
925 [(match_operand:X87MODEI12 2 "memory_operand" "m")]))]
927 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
928 && FLOAT_MODE_P (GET_MODE (operands[1]))
929 && (GET_MODE (operands [3]) == GET_MODE (operands[1]))"
930 "* return output_fp_compare (insn, operands, 0, 0);"
931 [(set_attr "type" "multi")
932 (set_attr "unit" "i387")
933 (set_attr "fp_int_src" "true")
934 (set_attr "mode" "<MODE>")])
936 ;; FP compares, step 2
937 ;; Move the fpsw to ax.
939 (define_insn "x86_fnstsw_1"
940 [(set (match_operand:HI 0 "register_operand" "=a")
941 (unspec:HI [(reg:CCFP FPSR_REG)] UNSPEC_FNSTSW))]
944 [(set_attr "length" "2")
945 (set_attr "mode" "SI")
946 (set_attr "unit" "i387")])
948 ;; FP compares, step 3
949 ;; Get ax into flags, general case.
951 (define_insn "x86_sahf_1"
952 [(set (reg:CC FLAGS_REG)
953 (unspec:CC [(match_operand:HI 0 "register_operand" "a")] UNSPEC_SAHF))]
956 [(set_attr "length" "1")
957 (set_attr "athlon_decode" "vector")
958 (set_attr "mode" "SI")])
960 ;; Pentium Pro can do steps 1 through 3 in one go.
962 (define_insn "*cmpfp_i_mixed"
963 [(set (reg:CCFP FLAGS_REG)
964 (compare:CCFP (match_operand 0 "register_operand" "f#x,x#f")
965 (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
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" "fcmp,ssecomi")
972 (if_then_else (match_operand:SF 1 "" "")
974 (const_string "DF")))
975 (set_attr "athlon_decode" "vector")])
977 (define_insn "*cmpfp_i_sse"
978 [(set (reg:CCFP FLAGS_REG)
979 (compare:CCFP (match_operand 0 "register_operand" "x")
980 (match_operand 1 "nonimmediate_operand" "xm")))]
982 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
983 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
984 "* return output_fp_compare (insn, operands, 1, 0);"
985 [(set_attr "type" "ssecomi")
987 (if_then_else (match_operand:SF 1 "" "")
989 (const_string "DF")))
990 (set_attr "athlon_decode" "vector")])
992 (define_insn "*cmpfp_i_i387"
993 [(set (reg:CCFP FLAGS_REG)
994 (compare:CCFP (match_operand 0 "register_operand" "f")
995 (match_operand 1 "register_operand" "f")))]
996 "TARGET_80387 && TARGET_CMOVE
997 && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0])))
998 && FLOAT_MODE_P (GET_MODE (operands[0]))
999 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1000 "* return output_fp_compare (insn, operands, 1, 0);"
1001 [(set_attr "type" "fcmp")
1003 (cond [(match_operand:SF 1 "" "")
1005 (match_operand:DF 1 "" "")
1008 (const_string "XF")))
1009 (set_attr "athlon_decode" "vector")])
1011 (define_insn "*cmpfp_iu_mixed"
1012 [(set (reg:CCFPU FLAGS_REG)
1013 (compare:CCFPU (match_operand 0 "register_operand" "f#x,x#f")
1014 (match_operand 1 "nonimmediate_operand" "f#x,xm#f")))]
1015 "TARGET_MIX_SSE_I387
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" "fcmp,ssecomi")
1021 (if_then_else (match_operand:SF 1 "" "")
1023 (const_string "DF")))
1024 (set_attr "athlon_decode" "vector")])
1026 (define_insn "*cmpfp_iu_sse"
1027 [(set (reg:CCFPU FLAGS_REG)
1028 (compare:CCFPU (match_operand 0 "register_operand" "x")
1029 (match_operand 1 "nonimmediate_operand" "xm")))]
1031 && SSE_FLOAT_MODE_P (GET_MODE (operands[0]))
1032 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1033 "* return output_fp_compare (insn, operands, 1, 1);"
1034 [(set_attr "type" "ssecomi")
1036 (if_then_else (match_operand:SF 1 "" "")
1038 (const_string "DF")))
1039 (set_attr "athlon_decode" "vector")])
1041 (define_insn "*cmpfp_iu_387"
1042 [(set (reg:CCFPU FLAGS_REG)
1043 (compare:CCFPU (match_operand 0 "register_operand" "f")
1044 (match_operand 1 "register_operand" "f")))]
1045 "TARGET_80387 && TARGET_CMOVE
1046 && (!TARGET_SSE_MATH || !SSE_FLOAT_MODE_P (GET_MODE (operands[0])))
1047 && FLOAT_MODE_P (GET_MODE (operands[0]))
1048 && GET_MODE (operands[0]) == GET_MODE (operands[1])"
1049 "* return output_fp_compare (insn, operands, 1, 1);"
1050 [(set_attr "type" "fcmp")
1052 (cond [(match_operand:SF 1 "" "")
1054 (match_operand:DF 1 "" "")
1057 (const_string "XF")))
1058 (set_attr "athlon_decode" "vector")])
1060 ;; Move instructions.
1062 ;; General case of fullword move.
1064 (define_expand "movsi"
1065 [(set (match_operand:SI 0 "nonimmediate_operand" "")
1066 (match_operand:SI 1 "general_operand" ""))]
1068 "ix86_expand_move (SImode, operands); DONE;")
1070 ;; Push/pop instructions. They are separate since autoinc/dec is not a
1073 ;; %%% We don't use a post-inc memory reference because x86 is not a
1074 ;; general AUTO_INC_DEC host, which impacts how it is treated in flow.
1075 ;; Changing this impacts compiler performance on other non-AUTO_INC_DEC
1076 ;; targets without our curiosities, and it is just as easy to represent
1077 ;; this differently.
1079 (define_insn "*pushsi2"
1080 [(set (match_operand:SI 0 "push_operand" "=<")
1081 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))]
1084 [(set_attr "type" "push")
1085 (set_attr "mode" "SI")])
1087 ;; For 64BIT abi we always round up to 8 bytes.
1088 (define_insn "*pushsi2_rex64"
1089 [(set (match_operand:SI 0 "push_operand" "=X")
1090 (match_operand:SI 1 "nonmemory_no_elim_operand" "ri"))]
1093 [(set_attr "type" "push")
1094 (set_attr "mode" "SI")])
1096 (define_insn "*pushsi2_prologue"
1097 [(set (match_operand:SI 0 "push_operand" "=<")
1098 (match_operand:SI 1 "general_no_elim_operand" "ri*m"))
1099 (clobber (mem:BLK (scratch)))]
1102 [(set_attr "type" "push")
1103 (set_attr "mode" "SI")])
1105 (define_insn "*popsi1_epilogue"
1106 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1107 (mem:SI (reg:SI SP_REG)))
1108 (set (reg:SI SP_REG)
1109 (plus:SI (reg:SI SP_REG) (const_int 4)))
1110 (clobber (mem:BLK (scratch)))]
1113 [(set_attr "type" "pop")
1114 (set_attr "mode" "SI")])
1116 (define_insn "popsi1"
1117 [(set (match_operand:SI 0 "nonimmediate_operand" "=r*m")
1118 (mem:SI (reg:SI SP_REG)))
1119 (set (reg:SI SP_REG)
1120 (plus:SI (reg:SI SP_REG) (const_int 4)))]
1123 [(set_attr "type" "pop")
1124 (set_attr "mode" "SI")])
1126 (define_insn "*movsi_xor"
1127 [(set (match_operand:SI 0 "register_operand" "=r")
1128 (match_operand:SI 1 "const0_operand" "i"))
1129 (clobber (reg:CC FLAGS_REG))]
1130 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1131 "xor{l}\t{%0, %0|%0, %0}"
1132 [(set_attr "type" "alu1")
1133 (set_attr "mode" "SI")
1134 (set_attr "length_immediate" "0")])
1136 (define_insn "*movsi_or"
1137 [(set (match_operand:SI 0 "register_operand" "=r")
1138 (match_operand:SI 1 "immediate_operand" "i"))
1139 (clobber (reg:CC FLAGS_REG))]
1141 && operands[1] == constm1_rtx
1142 && (TARGET_PENTIUM || optimize_size)"
1144 operands[1] = constm1_rtx;
1145 return "or{l}\t{%1, %0|%0, %1}";
1147 [(set_attr "type" "alu1")
1148 (set_attr "mode" "SI")
1149 (set_attr "length_immediate" "1")])
1151 (define_insn "*movsi_1"
1152 [(set (match_operand:SI 0 "nonimmediate_operand"
1153 "=r ,m ,*y,*y,?rm,?*y,*x,*x,?r,m ,?*Y,*x")
1154 (match_operand:SI 1 "general_operand"
1155 "rinm,rin,C ,*y,*y ,rm ,C ,*x,*Y,*x,r ,m "))]
1156 "!(MEM_P (operands[0]) && MEM_P (operands[1]))"
1158 switch (get_attr_type (insn))
1161 if (get_attr_mode (insn) == MODE_TI)
1162 return "pxor\t%0, %0";
1163 return "xorps\t%0, %0";
1166 switch (get_attr_mode (insn))
1169 return "movdqa\t{%1, %0|%0, %1}";
1171 return "movaps\t{%1, %0|%0, %1}";
1173 return "movd\t{%1, %0|%0, %1}";
1175 return "movss\t{%1, %0|%0, %1}";
1181 return "pxor\t%0, %0";
1184 if (get_attr_mode (insn) == MODE_DI)
1185 return "movq\t{%1, %0|%0, %1}";
1186 return "movd\t{%1, %0|%0, %1}";
1189 return "lea{l}\t{%1, %0|%0, %1}";
1192 gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
1193 return "mov{l}\t{%1, %0|%0, %1}";
1197 (cond [(eq_attr "alternative" "2")
1198 (const_string "mmxadd")
1199 (eq_attr "alternative" "3,4,5")
1200 (const_string "mmxmov")
1201 (eq_attr "alternative" "6")
1202 (const_string "sselog1")
1203 (eq_attr "alternative" "7,8,9,10,11")
1204 (const_string "ssemov")
1205 (match_operand:DI 1 "pic_32bit_operand" "")
1206 (const_string "lea")
1208 (const_string "imov")))
1210 (cond [(eq_attr "alternative" "2,3")
1212 (eq_attr "alternative" "6,7")
1214 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
1215 (const_string "V4SF")
1216 (const_string "TI"))
1217 (and (eq_attr "alternative" "8,9,10,11")
1218 (eq (symbol_ref "TARGET_SSE2") (const_int 0)))
1221 (const_string "SI")))])
1223 ;; Stores and loads of ax to arbitrary constant address.
1224 ;; We fake an second form of instruction to force reload to load address
1225 ;; into register when rax is not available
1226 (define_insn "*movabssi_1_rex64"
1227 [(set (mem:SI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1228 (match_operand:SI 1 "nonmemory_operand" "a,er"))]
1229 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1231 movabs{l}\t{%1, %P0|%P0, %1}
1232 mov{l}\t{%1, %a0|%a0, %1}"
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" "store")
1238 (set_attr "mode" "SI")])
1240 (define_insn "*movabssi_2_rex64"
1241 [(set (match_operand:SI 0 "register_operand" "=a,r")
1242 (mem:SI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1243 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1245 movabs{l}\t{%P1, %0|%0, %P1}
1246 mov{l}\t{%a1, %0|%0, %a1}"
1247 [(set_attr "type" "imov")
1248 (set_attr "modrm" "0,*")
1249 (set_attr "length_address" "8,0")
1250 (set_attr "length_immediate" "0")
1251 (set_attr "memory" "load")
1252 (set_attr "mode" "SI")])
1254 (define_insn "*swapsi"
1255 [(set (match_operand:SI 0 "register_operand" "+r")
1256 (match_operand:SI 1 "register_operand" "+r"))
1261 [(set_attr "type" "imov")
1262 (set_attr "mode" "SI")
1263 (set_attr "pent_pair" "np")
1264 (set_attr "athlon_decode" "vector")])
1266 (define_expand "movhi"
1267 [(set (match_operand:HI 0 "nonimmediate_operand" "")
1268 (match_operand:HI 1 "general_operand" ""))]
1270 "ix86_expand_move (HImode, operands); DONE;")
1272 (define_insn "*pushhi2"
1273 [(set (match_operand:HI 0 "push_operand" "=X")
1274 (match_operand:HI 1 "nonmemory_no_elim_operand" "rn"))]
1277 [(set_attr "type" "push")
1278 (set_attr "mode" "SI")])
1280 ;; For 64BIT abi we always round up to 8 bytes.
1281 (define_insn "*pushhi2_rex64"
1282 [(set (match_operand:HI 0 "push_operand" "=X")
1283 (match_operand:HI 1 "nonmemory_no_elim_operand" "ri"))]
1286 [(set_attr "type" "push")
1287 (set_attr "mode" "DI")])
1289 (define_insn "*movhi_1"
1290 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,r,m")
1291 (match_operand:HI 1 "general_operand" "r,rn,rm,rn"))]
1292 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1294 switch (get_attr_type (insn))
1297 /* movzwl is faster than movw on p2 due to partial word stalls,
1298 though not as fast as an aligned movl. */
1299 return "movz{wl|x}\t{%1, %k0|%k0, %1}";
1301 if (get_attr_mode (insn) == MODE_SI)
1302 return "mov{l}\t{%k1, %k0|%k0, %k1}";
1304 return "mov{w}\t{%1, %0|%0, %1}";
1308 (cond [(ne (symbol_ref "optimize_size") (const_int 0))
1309 (const_string "imov")
1310 (and (eq_attr "alternative" "0")
1311 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1313 (eq (symbol_ref "TARGET_HIMODE_MATH")
1315 (const_string "imov")
1316 (and (eq_attr "alternative" "1,2")
1317 (match_operand:HI 1 "aligned_operand" ""))
1318 (const_string "imov")
1319 (and (ne (symbol_ref "TARGET_MOVX")
1321 (eq_attr "alternative" "0,2"))
1322 (const_string "imovx")
1324 (const_string "imov")))
1326 (cond [(eq_attr "type" "imovx")
1328 (and (eq_attr "alternative" "1,2")
1329 (match_operand:HI 1 "aligned_operand" ""))
1331 (and (eq_attr "alternative" "0")
1332 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1334 (eq (symbol_ref "TARGET_HIMODE_MATH")
1338 (const_string "HI")))])
1340 ;; Stores and loads of ax to arbitrary constant address.
1341 ;; We fake an second form of instruction to force reload to load address
1342 ;; into register when rax is not available
1343 (define_insn "*movabshi_1_rex64"
1344 [(set (mem:HI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1345 (match_operand:HI 1 "nonmemory_operand" "a,er"))]
1346 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1348 movabs{w}\t{%1, %P0|%P0, %1}
1349 mov{w}\t{%1, %a0|%a0, %1}"
1350 [(set_attr "type" "imov")
1351 (set_attr "modrm" "0,*")
1352 (set_attr "length_address" "8,0")
1353 (set_attr "length_immediate" "0,*")
1354 (set_attr "memory" "store")
1355 (set_attr "mode" "HI")])
1357 (define_insn "*movabshi_2_rex64"
1358 [(set (match_operand:HI 0 "register_operand" "=a,r")
1359 (mem:HI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1360 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1362 movabs{w}\t{%P1, %0|%0, %P1}
1363 mov{w}\t{%a1, %0|%0, %a1}"
1364 [(set_attr "type" "imov")
1365 (set_attr "modrm" "0,*")
1366 (set_attr "length_address" "8,0")
1367 (set_attr "length_immediate" "0")
1368 (set_attr "memory" "load")
1369 (set_attr "mode" "HI")])
1371 (define_insn "*swaphi_1"
1372 [(set (match_operand:HI 0 "register_operand" "+r")
1373 (match_operand:HI 1 "register_operand" "+r"))
1376 "!TARGET_PARTIAL_REG_STALL || optimize_size"
1378 [(set_attr "type" "imov")
1379 (set_attr "mode" "SI")
1380 (set_attr "pent_pair" "np")
1381 (set_attr "athlon_decode" "vector")])
1383 (define_insn "*swaphi_2"
1384 [(set (match_operand:HI 0 "register_operand" "+r")
1385 (match_operand:HI 1 "register_operand" "+r"))
1388 "TARGET_PARTIAL_REG_STALL"
1390 [(set_attr "type" "imov")
1391 (set_attr "mode" "HI")
1392 (set_attr "pent_pair" "np")
1393 (set_attr "athlon_decode" "vector")])
1395 (define_expand "movstricthi"
1396 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" ""))
1397 (match_operand:HI 1 "general_operand" ""))]
1398 "! TARGET_PARTIAL_REG_STALL || optimize_size"
1400 /* Don't generate memory->memory moves, go through a register */
1401 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1402 operands[1] = force_reg (HImode, operands[1]);
1405 (define_insn "*movstricthi_1"
1406 [(set (strict_low_part (match_operand:HI 0 "nonimmediate_operand" "+rm,r"))
1407 (match_operand:HI 1 "general_operand" "rn,m"))]
1408 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1409 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1410 "mov{w}\t{%1, %0|%0, %1}"
1411 [(set_attr "type" "imov")
1412 (set_attr "mode" "HI")])
1414 (define_insn "*movstricthi_xor"
1415 [(set (strict_low_part (match_operand:HI 0 "register_operand" "+r"))
1416 (match_operand:HI 1 "const0_operand" "i"))
1417 (clobber (reg:CC FLAGS_REG))]
1419 && ((!TARGET_USE_MOV0 && !TARGET_PARTIAL_REG_STALL) || optimize_size)"
1420 "xor{w}\t{%0, %0|%0, %0}"
1421 [(set_attr "type" "alu1")
1422 (set_attr "mode" "HI")
1423 (set_attr "length_immediate" "0")])
1425 (define_expand "movqi"
1426 [(set (match_operand:QI 0 "nonimmediate_operand" "")
1427 (match_operand:QI 1 "general_operand" ""))]
1429 "ix86_expand_move (QImode, operands); DONE;")
1431 ;; emit_push_insn when it calls move_by_pieces requires an insn to
1432 ;; "push a byte". But actually we use pushl, which has the effect
1433 ;; of rounding the amount pushed up to a word.
1435 (define_insn "*pushqi2"
1436 [(set (match_operand:QI 0 "push_operand" "=X")
1437 (match_operand:QI 1 "nonmemory_no_elim_operand" "rn"))]
1440 [(set_attr "type" "push")
1441 (set_attr "mode" "SI")])
1443 ;; For 64BIT abi we always round up to 8 bytes.
1444 (define_insn "*pushqi2_rex64"
1445 [(set (match_operand:QI 0 "push_operand" "=X")
1446 (match_operand:QI 1 "nonmemory_no_elim_operand" "qi"))]
1449 [(set_attr "type" "push")
1450 (set_attr "mode" "DI")])
1452 ;; Situation is quite tricky about when to choose full sized (SImode) move
1453 ;; over QImode moves. For Q_REG -> Q_REG move we use full size only for
1454 ;; partial register dependency machines (such as AMD Athlon), where QImode
1455 ;; moves issue extra dependency and for partial register stalls machines
1456 ;; that don't use QImode patterns (and QImode move cause stall on the next
1459 ;; For loads of Q_REG to NONQ_REG we use full sized moves except for partial
1460 ;; register stall machines with, where we use QImode instructions, since
1461 ;; partial register stall can be caused there. Then we use movzx.
1462 (define_insn "*movqi_1"
1463 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,q ,q ,r,r ,?r,m")
1464 (match_operand:QI 1 "general_operand" " q,qn,qm,q,rn,qm,qn"))]
1465 "GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM"
1467 switch (get_attr_type (insn))
1470 gcc_assert (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM);
1471 return "movz{bl|x}\t{%1, %k0|%k0, %1}";
1473 if (get_attr_mode (insn) == MODE_SI)
1474 return "mov{l}\t{%k1, %k0|%k0, %k1}";
1476 return "mov{b}\t{%1, %0|%0, %1}";
1480 (cond [(and (eq_attr "alternative" "5")
1481 (not (match_operand:QI 1 "aligned_operand" "")))
1482 (const_string "imovx")
1483 (ne (symbol_ref "optimize_size") (const_int 0))
1484 (const_string "imov")
1485 (and (eq_attr "alternative" "3")
1486 (ior (eq (symbol_ref "TARGET_PARTIAL_REG_STALL")
1488 (eq (symbol_ref "TARGET_QIMODE_MATH")
1490 (const_string "imov")
1491 (eq_attr "alternative" "3,5")
1492 (const_string "imovx")
1493 (and (ne (symbol_ref "TARGET_MOVX")
1495 (eq_attr "alternative" "2"))
1496 (const_string "imovx")
1498 (const_string "imov")))
1500 (cond [(eq_attr "alternative" "3,4,5")
1502 (eq_attr "alternative" "6")
1504 (eq_attr "type" "imovx")
1506 (and (eq_attr "type" "imov")
1507 (and (eq_attr "alternative" "0,1")
1508 (ne (symbol_ref "TARGET_PARTIAL_REG_DEPENDENCY")
1511 ;; Avoid partial register stalls when not using QImode arithmetic
1512 (and (eq_attr "type" "imov")
1513 (and (eq_attr "alternative" "0,1")
1514 (and (ne (symbol_ref "TARGET_PARTIAL_REG_STALL")
1516 (eq (symbol_ref "TARGET_QIMODE_MATH")
1520 (const_string "QI")))])
1522 (define_expand "reload_outqi"
1523 [(parallel [(match_operand:QI 0 "" "=m")
1524 (match_operand:QI 1 "register_operand" "r")
1525 (match_operand:QI 2 "register_operand" "=&q")])]
1529 op0 = operands[0]; op1 = operands[1]; op2 = operands[2];
1531 gcc_assert (!reg_overlap_mentioned_p (op2, op0));
1532 if (! q_regs_operand (op1, QImode))
1534 emit_insn (gen_movqi (op2, op1));
1537 emit_insn (gen_movqi (op0, op1));
1541 (define_insn "*swapqi_1"
1542 [(set (match_operand:QI 0 "register_operand" "+r")
1543 (match_operand:QI 1 "register_operand" "+r"))
1546 "!TARGET_PARTIAL_REG_STALL || optimize_size"
1548 [(set_attr "type" "imov")
1549 (set_attr "mode" "SI")
1550 (set_attr "pent_pair" "np")
1551 (set_attr "athlon_decode" "vector")])
1553 (define_insn "*swapqi_2"
1554 [(set (match_operand:QI 0 "register_operand" "+q")
1555 (match_operand:QI 1 "register_operand" "+q"))
1558 "TARGET_PARTIAL_REG_STALL"
1560 [(set_attr "type" "imov")
1561 (set_attr "mode" "QI")
1562 (set_attr "pent_pair" "np")
1563 (set_attr "athlon_decode" "vector")])
1565 (define_expand "movstrictqi"
1566 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
1567 (match_operand:QI 1 "general_operand" ""))]
1568 "! TARGET_PARTIAL_REG_STALL || optimize_size"
1570 /* Don't generate memory->memory moves, go through a register. */
1571 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
1572 operands[1] = force_reg (QImode, operands[1]);
1575 (define_insn "*movstrictqi_1"
1576 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
1577 (match_operand:QI 1 "general_operand" "*qn,m"))]
1578 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
1579 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
1580 "mov{b}\t{%1, %0|%0, %1}"
1581 [(set_attr "type" "imov")
1582 (set_attr "mode" "QI")])
1584 (define_insn "*movstrictqi_xor"
1585 [(set (strict_low_part (match_operand:QI 0 "q_regs_operand" "+q"))
1586 (match_operand:QI 1 "const0_operand" "i"))
1587 (clobber (reg:CC FLAGS_REG))]
1588 "reload_completed && (!TARGET_USE_MOV0 || optimize_size)"
1589 "xor{b}\t{%0, %0|%0, %0}"
1590 [(set_attr "type" "alu1")
1591 (set_attr "mode" "QI")
1592 (set_attr "length_immediate" "0")])
1594 (define_insn "*movsi_extv_1"
1595 [(set (match_operand:SI 0 "register_operand" "=R")
1596 (sign_extract:SI (match_operand 1 "ext_register_operand" "Q")
1600 "movs{bl|x}\t{%h1, %0|%0, %h1}"
1601 [(set_attr "type" "imovx")
1602 (set_attr "mode" "SI")])
1604 (define_insn "*movhi_extv_1"
1605 [(set (match_operand:HI 0 "register_operand" "=R")
1606 (sign_extract:HI (match_operand 1 "ext_register_operand" "Q")
1610 "movs{bl|x}\t{%h1, %k0|%k0, %h1}"
1611 [(set_attr "type" "imovx")
1612 (set_attr "mode" "SI")])
1614 (define_insn "*movqi_extv_1"
1615 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?r")
1616 (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1621 switch (get_attr_type (insn))
1624 return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1626 return "mov{b}\t{%h1, %0|%0, %h1}";
1630 (if_then_else (and (match_operand:QI 0 "register_operand" "")
1631 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1632 (ne (symbol_ref "TARGET_MOVX")
1634 (const_string "imovx")
1635 (const_string "imov")))
1637 (if_then_else (eq_attr "type" "imovx")
1639 (const_string "QI")))])
1641 (define_insn "*movqi_extv_1_rex64"
1642 [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1643 (sign_extract:QI (match_operand 1 "ext_register_operand" "Q,Q")
1648 switch (get_attr_type (insn))
1651 return "movs{bl|x}\t{%h1, %k0|%k0, %h1}";
1653 return "mov{b}\t{%h1, %0|%0, %h1}";
1657 (if_then_else (and (match_operand:QI 0 "register_operand" "")
1658 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1659 (ne (symbol_ref "TARGET_MOVX")
1661 (const_string "imovx")
1662 (const_string "imov")))
1664 (if_then_else (eq_attr "type" "imovx")
1666 (const_string "QI")))])
1668 ;; Stores and loads of ax to arbitrary constant address.
1669 ;; We fake an second form of instruction to force reload to load address
1670 ;; into register when rax is not available
1671 (define_insn "*movabsqi_1_rex64"
1672 [(set (mem:QI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
1673 (match_operand:QI 1 "nonmemory_operand" "a,er"))]
1674 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
1676 movabs{b}\t{%1, %P0|%P0, %1}
1677 mov{b}\t{%1, %a0|%a0, %1}"
1678 [(set_attr "type" "imov")
1679 (set_attr "modrm" "0,*")
1680 (set_attr "length_address" "8,0")
1681 (set_attr "length_immediate" "0,*")
1682 (set_attr "memory" "store")
1683 (set_attr "mode" "QI")])
1685 (define_insn "*movabsqi_2_rex64"
1686 [(set (match_operand:QI 0 "register_operand" "=a,r")
1687 (mem:QI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
1688 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
1690 movabs{b}\t{%P1, %0|%0, %P1}
1691 mov{b}\t{%a1, %0|%0, %a1}"
1692 [(set_attr "type" "imov")
1693 (set_attr "modrm" "0,*")
1694 (set_attr "length_address" "8,0")
1695 (set_attr "length_immediate" "0")
1696 (set_attr "memory" "load")
1697 (set_attr "mode" "QI")])
1699 (define_insn "*movdi_extzv_1"
1700 [(set (match_operand:DI 0 "register_operand" "=R")
1701 (zero_extract:DI (match_operand 1 "ext_register_operand" "Q")
1705 "movz{bl|x}\t{%h1, %k0|%k0, %h1}"
1706 [(set_attr "type" "imovx")
1707 (set_attr "mode" "DI")])
1709 (define_insn "*movsi_extzv_1"
1710 [(set (match_operand:SI 0 "register_operand" "=R")
1711 (zero_extract:SI (match_operand 1 "ext_register_operand" "Q")
1715 "movz{bl|x}\t{%h1, %0|%0, %h1}"
1716 [(set_attr "type" "imovx")
1717 (set_attr "mode" "SI")])
1719 (define_insn "*movqi_extzv_2"
1720 [(set (match_operand:QI 0 "nonimmediate_operand" "=Qm,?R")
1721 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1726 switch (get_attr_type (insn))
1729 return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1731 return "mov{b}\t{%h1, %0|%0, %h1}";
1735 (if_then_else (and (match_operand:QI 0 "register_operand" "")
1736 (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1737 (ne (symbol_ref "TARGET_MOVX")
1739 (const_string "imovx")
1740 (const_string "imov")))
1742 (if_then_else (eq_attr "type" "imovx")
1744 (const_string "QI")))])
1746 (define_insn "*movqi_extzv_2_rex64"
1747 [(set (match_operand:QI 0 "register_operand" "=Q,?R")
1748 (subreg:QI (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q")
1753 switch (get_attr_type (insn))
1756 return "movz{bl|x}\t{%h1, %k0|%k0, %h1}";
1758 return "mov{b}\t{%h1, %0|%0, %h1}";
1762 (if_then_else (ior (not (match_operand:QI 0 "q_regs_operand" ""))
1763 (ne (symbol_ref "TARGET_MOVX")
1765 (const_string "imovx")
1766 (const_string "imov")))
1768 (if_then_else (eq_attr "type" "imovx")
1770 (const_string "QI")))])
1772 (define_insn "movsi_insv_1"
1773 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
1776 (match_operand:SI 1 "general_operand" "Qmn"))]
1778 "mov{b}\t{%b1, %h0|%h0, %b1}"
1779 [(set_attr "type" "imov")
1780 (set_attr "mode" "QI")])
1782 (define_insn "movdi_insv_1_rex64"
1783 [(set (zero_extract:DI (match_operand 0 "ext_register_operand" "+Q")
1786 (match_operand:DI 1 "nonmemory_operand" "Qn"))]
1788 "mov{b}\t{%b1, %h0|%h0, %b1}"
1789 [(set_attr "type" "imov")
1790 (set_attr "mode" "QI")])
1792 (define_insn "*movqi_insv_2"
1793 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q")
1796 (lshiftrt:SI (match_operand:SI 1 "register_operand" "Q")
1799 "mov{b}\t{%h1, %h0|%h0, %h1}"
1800 [(set_attr "type" "imov")
1801 (set_attr "mode" "QI")])
1803 (define_expand "movdi"
1804 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1805 (match_operand:DI 1 "general_operand" ""))]
1807 "ix86_expand_move (DImode, operands); DONE;")
1809 (define_insn "*pushdi"
1810 [(set (match_operand:DI 0 "push_operand" "=<")
1811 (match_operand:DI 1 "general_no_elim_operand" "riF*m"))]
1815 (define_insn "*pushdi2_rex64"
1816 [(set (match_operand:DI 0 "push_operand" "=<,!<")
1817 (match_operand:DI 1 "general_no_elim_operand" "re*m,n"))]
1822 [(set_attr "type" "push,multi")
1823 (set_attr "mode" "DI")])
1825 ;; Convert impossible pushes of immediate to existing instructions.
1826 ;; First try to get scratch register and go through it. In case this
1827 ;; fails, push sign extended lower part first and then overwrite
1828 ;; upper part by 32bit move.
1830 [(match_scratch:DI 2 "r")
1831 (set (match_operand:DI 0 "push_operand" "")
1832 (match_operand:DI 1 "immediate_operand" ""))]
1833 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1834 && !x86_64_immediate_operand (operands[1], DImode)"
1835 [(set (match_dup 2) (match_dup 1))
1836 (set (match_dup 0) (match_dup 2))]
1839 ;; We need to define this as both peepholer and splitter for case
1840 ;; peephole2 pass is not run.
1841 ;; "&& 1" is needed to keep it from matching the previous pattern.
1843 [(set (match_operand:DI 0 "push_operand" "")
1844 (match_operand:DI 1 "immediate_operand" ""))]
1845 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
1846 && !x86_64_immediate_operand (operands[1], DImode) && 1"
1847 [(set (match_dup 0) (match_dup 1))
1848 (set (match_dup 2) (match_dup 3))]
1849 "split_di (operands + 1, 1, operands + 2, operands + 3);
1850 operands[1] = gen_lowpart (DImode, operands[2]);
1851 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1856 [(set (match_operand:DI 0 "push_operand" "")
1857 (match_operand:DI 1 "immediate_operand" ""))]
1858 "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
1859 ? flow2_completed : reload_completed)
1860 && !symbolic_operand (operands[1], DImode)
1861 && !x86_64_immediate_operand (operands[1], DImode)"
1862 [(set (match_dup 0) (match_dup 1))
1863 (set (match_dup 2) (match_dup 3))]
1864 "split_di (operands + 1, 1, operands + 2, operands + 3);
1865 operands[1] = gen_lowpart (DImode, operands[2]);
1866 operands[2] = gen_rtx_MEM (SImode, gen_rtx_PLUS (DImode, stack_pointer_rtx,
1870 (define_insn "*pushdi2_prologue_rex64"
1871 [(set (match_operand:DI 0 "push_operand" "=<")
1872 (match_operand:DI 1 "general_no_elim_operand" "re*m"))
1873 (clobber (mem:BLK (scratch)))]
1876 [(set_attr "type" "push")
1877 (set_attr "mode" "DI")])
1879 (define_insn "*popdi1_epilogue_rex64"
1880 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
1881 (mem:DI (reg:DI SP_REG)))
1882 (set (reg:DI SP_REG)
1883 (plus:DI (reg:DI SP_REG) (const_int 8)))
1884 (clobber (mem:BLK (scratch)))]
1887 [(set_attr "type" "pop")
1888 (set_attr "mode" "DI")])
1890 (define_insn "popdi1"
1891 [(set (match_operand:DI 0 "nonimmediate_operand" "=r*m")
1892 (mem:DI (reg:DI SP_REG)))
1893 (set (reg:DI SP_REG)
1894 (plus:DI (reg:DI SP_REG) (const_int 8)))]
1897 [(set_attr "type" "pop")
1898 (set_attr "mode" "DI")])
1900 (define_insn "*movdi_xor_rex64"
1901 [(set (match_operand:DI 0 "register_operand" "=r")
1902 (match_operand:DI 1 "const0_operand" "i"))
1903 (clobber (reg:CC FLAGS_REG))]
1904 "TARGET_64BIT && (!TARGET_USE_MOV0 || optimize_size)
1905 && reload_completed"
1906 "xor{l}\t{%k0, %k0|%k0, %k0}"
1907 [(set_attr "type" "alu1")
1908 (set_attr "mode" "SI")
1909 (set_attr "length_immediate" "0")])
1911 (define_insn "*movdi_or_rex64"
1912 [(set (match_operand:DI 0 "register_operand" "=r")
1913 (match_operand:DI 1 "const_int_operand" "i"))
1914 (clobber (reg:CC FLAGS_REG))]
1915 "TARGET_64BIT && (TARGET_PENTIUM || optimize_size)
1917 && operands[1] == constm1_rtx"
1919 operands[1] = constm1_rtx;
1920 return "or{q}\t{%1, %0|%0, %1}";
1922 [(set_attr "type" "alu1")
1923 (set_attr "mode" "DI")
1924 (set_attr "length_immediate" "1")])
1926 (define_insn "*movdi_2"
1927 [(set (match_operand:DI 0 "nonimmediate_operand"
1928 "=r ,o ,*y,m*y,*y,*Y,m ,*Y,*Y,*x,m ,*x,*x")
1929 (match_operand:DI 1 "general_operand"
1930 "riFo,riF,C ,*y ,m ,C ,*Y,*Y,m ,C ,*x,*x,m "))]
1931 "!TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1936 movq\t{%1, %0|%0, %1}
1937 movq\t{%1, %0|%0, %1}
1939 movq\t{%1, %0|%0, %1}
1940 movdqa\t{%1, %0|%0, %1}
1941 movq\t{%1, %0|%0, %1}
1943 movlps\t{%1, %0|%0, %1}
1944 movaps\t{%1, %0|%0, %1}
1945 movlps\t{%1, %0|%0, %1}"
1946 [(set_attr "type" "*,*,mmx,mmxmov,mmxmov,sselog1,ssemov,ssemov,ssemov,sselog1,ssemov,ssemov,ssemov")
1947 (set_attr "mode" "DI,DI,DI,DI,DI,TI,DI,TI,DI,V4SF,V2SF,V4SF,V2SF")])
1950 [(set (match_operand:DI 0 "push_operand" "")
1951 (match_operand:DI 1 "general_operand" ""))]
1952 "!TARGET_64BIT && reload_completed
1953 && (! MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
1955 "ix86_split_long_move (operands); DONE;")
1957 ;; %%% This multiword shite has got to go.
1959 [(set (match_operand:DI 0 "nonimmediate_operand" "")
1960 (match_operand:DI 1 "general_operand" ""))]
1961 "!TARGET_64BIT && reload_completed
1962 && (!MMX_REG_P (operands[0]) && !SSE_REG_P (operands[0]))
1963 && (!MMX_REG_P (operands[1]) && !SSE_REG_P (operands[1]))"
1965 "ix86_split_long_move (operands); DONE;")
1967 (define_insn "*movdi_1_rex64"
1968 [(set (match_operand:DI 0 "nonimmediate_operand"
1969 "=r,r ,r,m ,!m,*y,*y,?rm,?*y,*x,*x,?rm,?*x,?*x,?*y")
1970 (match_operand:DI 1 "general_operand"
1971 "Z ,rem,i,re,n ,C ,*y,*y ,rm ,C ,*x,*x ,rm ,*y ,*x"))]
1972 "TARGET_64BIT && !(MEM_P (operands[0]) && MEM_P (operands[1]))"
1974 switch (get_attr_type (insn))
1977 if (which_alternative == 13)
1978 return "movq2dq\t{%1, %0|%0, %1}";
1980 return "movdq2q\t{%1, %0|%0, %1}";
1982 if (get_attr_mode (insn) == MODE_TI)
1983 return "movdqa\t{%1, %0|%0, %1}";
1986 /* Moves from and into integer register is done using movd opcode with
1988 if (GENERAL_REG_P (operands[0]) || GENERAL_REG_P (operands[1]))
1989 return "movd\t{%1, %0|%0, %1}";
1990 return "movq\t{%1, %0|%0, %1}";
1993 return "pxor\t%0, %0";
1997 return "lea{q}\t{%a1, %0|%0, %a1}";
1999 gcc_assert (!flag_pic || LEGITIMATE_PIC_OPERAND_P (operands[1]));
2000 if (get_attr_mode (insn) == MODE_SI)
2001 return "mov{l}\t{%k1, %k0|%k0, %k1}";
2002 else if (which_alternative == 2)
2003 return "movabs{q}\t{%1, %0|%0, %1}";
2005 return "mov{q}\t{%1, %0|%0, %1}";
2009 (cond [(eq_attr "alternative" "5")
2010 (const_string "mmxadd")
2011 (eq_attr "alternative" "6,7,8")
2012 (const_string "mmxmov")
2013 (eq_attr "alternative" "9")
2014 (const_string "sselog1")
2015 (eq_attr "alternative" "10,11,12")
2016 (const_string "ssemov")
2017 (eq_attr "alternative" "13,14")
2018 (const_string "ssecvt")
2019 (eq_attr "alternative" "4")
2020 (const_string "multi")
2021 (match_operand:DI 1 "pic_32bit_operand" "")
2022 (const_string "lea")
2024 (const_string "imov")))
2025 (set_attr "modrm" "*,0,0,*,*,*,*,*,*,*,*,*,*,*,*")
2026 (set_attr "length_immediate" "*,4,8,*,*,*,*,*,*,*,*,*,*,*,*")
2027 (set_attr "mode" "SI,DI,DI,DI,SI,DI,DI,DI,DI,TI,TI,DI,DI,DI,DI")])
2029 ;; Stores and loads of ax to arbitrary constant address.
2030 ;; We fake an second form of instruction to force reload to load address
2031 ;; into register when rax is not available
2032 (define_insn "*movabsdi_1_rex64"
2033 [(set (mem:DI (match_operand:DI 0 "x86_64_movabs_operand" "i,r"))
2034 (match_operand:DI 1 "nonmemory_operand" "a,er"))]
2035 "TARGET_64BIT && ix86_check_movabs (insn, 0)"
2037 movabs{q}\t{%1, %P0|%P0, %1}
2038 mov{q}\t{%1, %a0|%a0, %1}"
2039 [(set_attr "type" "imov")
2040 (set_attr "modrm" "0,*")
2041 (set_attr "length_address" "8,0")
2042 (set_attr "length_immediate" "0,*")
2043 (set_attr "memory" "store")
2044 (set_attr "mode" "DI")])
2046 (define_insn "*movabsdi_2_rex64"
2047 [(set (match_operand:DI 0 "register_operand" "=a,r")
2048 (mem:DI (match_operand:DI 1 "x86_64_movabs_operand" "i,r")))]
2049 "TARGET_64BIT && ix86_check_movabs (insn, 1)"
2051 movabs{q}\t{%P1, %0|%0, %P1}
2052 mov{q}\t{%a1, %0|%0, %a1}"
2053 [(set_attr "type" "imov")
2054 (set_attr "modrm" "0,*")
2055 (set_attr "length_address" "8,0")
2056 (set_attr "length_immediate" "0")
2057 (set_attr "memory" "load")
2058 (set_attr "mode" "DI")])
2060 ;; Convert impossible stores of immediate to existing instructions.
2061 ;; First try to get scratch register and go through it. In case this
2062 ;; fails, move by 32bit parts.
2064 [(match_scratch:DI 2 "r")
2065 (set (match_operand:DI 0 "memory_operand" "")
2066 (match_operand:DI 1 "immediate_operand" ""))]
2067 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2068 && !x86_64_immediate_operand (operands[1], DImode)"
2069 [(set (match_dup 2) (match_dup 1))
2070 (set (match_dup 0) (match_dup 2))]
2073 ;; We need to define this as both peepholer and splitter for case
2074 ;; peephole2 pass is not run.
2075 ;; "&& 1" is needed to keep it from matching the previous pattern.
2077 [(set (match_operand:DI 0 "memory_operand" "")
2078 (match_operand:DI 1 "immediate_operand" ""))]
2079 "TARGET_64BIT && !symbolic_operand (operands[1], DImode)
2080 && !x86_64_immediate_operand (operands[1], DImode) && 1"
2081 [(set (match_dup 2) (match_dup 3))
2082 (set (match_dup 4) (match_dup 5))]
2083 "split_di (operands, 2, operands + 2, operands + 4);")
2086 [(set (match_operand:DI 0 "memory_operand" "")
2087 (match_operand:DI 1 "immediate_operand" ""))]
2088 "TARGET_64BIT && ((optimize > 0 && flag_peephole2)
2089 ? flow2_completed : reload_completed)
2090 && !symbolic_operand (operands[1], DImode)
2091 && !x86_64_immediate_operand (operands[1], DImode)"
2092 [(set (match_dup 2) (match_dup 3))
2093 (set (match_dup 4) (match_dup 5))]
2094 "split_di (operands, 2, operands + 2, operands + 4);")
2096 (define_insn "*swapdi_rex64"
2097 [(set (match_operand:DI 0 "register_operand" "+r")
2098 (match_operand:DI 1 "register_operand" "+r"))
2103 [(set_attr "type" "imov")
2104 (set_attr "mode" "DI")
2105 (set_attr "pent_pair" "np")
2106 (set_attr "athlon_decode" "vector")])
2108 (define_expand "movti"
2109 [(set (match_operand:TI 0 "nonimmediate_operand" "")
2110 (match_operand:TI 1 "nonimmediate_operand" ""))]
2111 "TARGET_SSE || TARGET_64BIT"
2114 ix86_expand_move (TImode, operands);
2116 ix86_expand_vector_move (TImode, operands);
2120 (define_insn "*movti_internal"
2121 [(set (match_operand:TI 0 "nonimmediate_operand" "=x,x,m")
2122 (match_operand:TI 1 "vector_move_operand" "C,xm,x"))]
2123 "TARGET_SSE && !TARGET_64BIT
2124 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2126 switch (which_alternative)
2129 if (get_attr_mode (insn) == MODE_V4SF)
2130 return "xorps\t%0, %0";
2132 return "pxor\t%0, %0";
2135 if (get_attr_mode (insn) == MODE_V4SF)
2136 return "movaps\t{%1, %0|%0, %1}";
2138 return "movdqa\t{%1, %0|%0, %1}";
2143 [(set_attr "type" "ssemov,ssemov,ssemov")
2145 (cond [(eq (symbol_ref "TARGET_SSE2") (const_int 0))
2146 (const_string "V4SF")
2148 (eq_attr "alternative" "0,1")
2150 (ne (symbol_ref "optimize_size")
2152 (const_string "V4SF")
2153 (const_string "TI"))
2154 (eq_attr "alternative" "2")
2156 (ne (symbol_ref "optimize_size")
2158 (const_string "V4SF")
2159 (const_string "TI"))]
2160 (const_string "TI")))])
2162 (define_insn "*movti_rex64"
2163 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o,x,x,xm")
2164 (match_operand:TI 1 "general_operand" "riFo,riF,C,xm,x"))]
2166 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2168 switch (which_alternative)
2174 if (get_attr_mode (insn) == MODE_V4SF)
2175 return "xorps\t%0, %0";
2177 return "pxor\t%0, %0";
2180 if (get_attr_mode (insn) == MODE_V4SF)
2181 return "movaps\t{%1, %0|%0, %1}";
2183 return "movdqa\t{%1, %0|%0, %1}";
2188 [(set_attr "type" "*,*,ssemov,ssemov,ssemov")
2190 (cond [(eq_attr "alternative" "2,3")
2192 (ne (symbol_ref "optimize_size")
2194 (const_string "V4SF")
2195 (const_string "TI"))
2196 (eq_attr "alternative" "4")
2198 (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2200 (ne (symbol_ref "optimize_size")
2202 (const_string "V4SF")
2203 (const_string "TI"))]
2204 (const_string "DI")))])
2207 [(set (match_operand:TI 0 "nonimmediate_operand" "")
2208 (match_operand:TI 1 "general_operand" ""))]
2209 "reload_completed && !SSE_REG_P (operands[0])
2210 && !SSE_REG_P (operands[1])"
2212 "ix86_split_long_move (operands); DONE;")
2214 (define_expand "movsf"
2215 [(set (match_operand:SF 0 "nonimmediate_operand" "")
2216 (match_operand:SF 1 "general_operand" ""))]
2218 "ix86_expand_move (SFmode, operands); DONE;")
2220 (define_insn "*pushsf"
2221 [(set (match_operand:SF 0 "push_operand" "=<,<,<")
2222 (match_operand:SF 1 "general_no_elim_operand" "f#rx,rFm#fx,x#rf"))]
2225 /* Anything else should be already split before reg-stack. */
2226 gcc_assert (which_alternative == 1);
2227 return "push{l}\t%1";
2229 [(set_attr "type" "multi,push,multi")
2230 (set_attr "unit" "i387,*,*")
2231 (set_attr "mode" "SF,SI,SF")])
2233 (define_insn "*pushsf_rex64"
2234 [(set (match_operand:SF 0 "push_operand" "=X,X,X")
2235 (match_operand:SF 1 "nonmemory_no_elim_operand" "f#rx,rF#fx,x#rf"))]
2238 /* Anything else should be already split before reg-stack. */
2239 gcc_assert (which_alternative == 1);
2240 return "push{q}\t%q1";
2242 [(set_attr "type" "multi,push,multi")
2243 (set_attr "unit" "i387,*,*")
2244 (set_attr "mode" "SF,DI,SF")])
2247 [(set (match_operand:SF 0 "push_operand" "")
2248 (match_operand:SF 1 "memory_operand" ""))]
2250 && GET_CODE (operands[1]) == MEM
2251 && constant_pool_reference_p (operands[1])"
2254 "operands[1] = avoid_constant_pool_reference (operands[1]);")
2257 ;; %%% Kill this when call knows how to work this out.
2259 [(set (match_operand:SF 0 "push_operand" "")
2260 (match_operand:SF 1 "any_fp_register_operand" ""))]
2262 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
2263 (set (mem:SF (reg:SI SP_REG)) (match_dup 1))])
2266 [(set (match_operand:SF 0 "push_operand" "")
2267 (match_operand:SF 1 "any_fp_register_operand" ""))]
2269 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2270 (set (mem:SF (reg:DI SP_REG)) (match_dup 1))])
2272 (define_insn "*movsf_1"
2273 [(set (match_operand:SF 0 "nonimmediate_operand"
2274 "=f#xr,m ,f#xr,r#xf ,m ,x#rf,x#rf,x#rf ,m ,!*y,!rm,!*y")
2275 (match_operand:SF 1 "general_operand"
2276 "fm#rx,f#rx,G ,rmF#fx,Fr#fx,C ,x ,xm#rf,x#rf,rm ,*y ,*y"))]
2277 "!(MEM_P (operands[0]) && MEM_P (operands[1]))
2278 && (reload_in_progress || reload_completed
2279 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2280 || GET_CODE (operands[1]) != CONST_DOUBLE
2281 || memory_operand (operands[0], SFmode))"
2283 switch (which_alternative)
2286 return output_387_reg_move (insn, operands);
2289 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2290 return "fstp%z0\t%y0";
2292 return "fst%z0\t%y0";
2295 return standard_80387_constant_opcode (operands[1]);
2299 return "mov{l}\t{%1, %0|%0, %1}";
2301 if (get_attr_mode (insn) == MODE_TI)
2302 return "pxor\t%0, %0";
2304 return "xorps\t%0, %0";
2306 if (get_attr_mode (insn) == MODE_V4SF)
2307 return "movaps\t{%1, %0|%0, %1}";
2309 return "movss\t{%1, %0|%0, %1}";
2312 return "movss\t{%1, %0|%0, %1}";
2316 return "movd\t{%1, %0|%0, %1}";
2319 return "movq\t{%1, %0|%0, %1}";
2325 [(set_attr "type" "fmov,fmov,fmov,imov,imov,ssemov,ssemov,ssemov,ssemov,mmxmov,mmxmov,mmxmov")
2327 (cond [(eq_attr "alternative" "3,4,9,10")
2329 (eq_attr "alternative" "5")
2331 (and (and (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2333 (ne (symbol_ref "TARGET_SSE2")
2335 (eq (symbol_ref "optimize_size")
2338 (const_string "V4SF"))
2339 /* For architectures resolving dependencies on
2340 whole SSE registers use APS move to break dependency
2341 chains, otherwise use short move to avoid extra work.
2343 Do the same for architectures resolving dependencies on
2344 the parts. While in DF mode it is better to always handle
2345 just register parts, the SF mode is different due to lack
2346 of instructions to load just part of the register. It is
2347 better to maintain the whole registers in single format
2348 to avoid problems on using packed logical operations. */
2349 (eq_attr "alternative" "6")
2351 (ior (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2353 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2355 (const_string "V4SF")
2356 (const_string "SF"))
2357 (eq_attr "alternative" "11")
2358 (const_string "DI")]
2359 (const_string "SF")))])
2361 (define_insn "*swapsf"
2362 [(set (match_operand:SF 0 "fp_register_operand" "+f")
2363 (match_operand:SF 1 "fp_register_operand" "+f"))
2366 "reload_completed || TARGET_80387"
2368 if (STACK_TOP_P (operands[0]))
2373 [(set_attr "type" "fxch")
2374 (set_attr "mode" "SF")])
2376 (define_expand "movdf"
2377 [(set (match_operand:DF 0 "nonimmediate_operand" "")
2378 (match_operand:DF 1 "general_operand" ""))]
2380 "ix86_expand_move (DFmode, operands); DONE;")
2382 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2383 ;; Size of pushdf using integer instructions is 2+2*memory operand size
2384 ;; On the average, pushdf using integers can be still shorter. Allow this
2385 ;; pattern for optimize_size too.
2387 (define_insn "*pushdf_nointeger"
2388 [(set (match_operand:DF 0 "push_operand" "=<,<,<,<")
2389 (match_operand:DF 1 "general_no_elim_operand" "f#Y,Fo#fY,*r#fY,Y#f"))]
2390 "!TARGET_64BIT && !TARGET_INTEGER_DFMODE_MOVES"
2392 /* This insn should be already split before reg-stack. */
2395 [(set_attr "type" "multi")
2396 (set_attr "unit" "i387,*,*,*")
2397 (set_attr "mode" "DF,SI,SI,DF")])
2399 (define_insn "*pushdf_integer"
2400 [(set (match_operand:DF 0 "push_operand" "=<,<,<")
2401 (match_operand:DF 1 "general_no_elim_operand" "f#rY,rFo#fY,Y#rf"))]
2402 "TARGET_64BIT || TARGET_INTEGER_DFMODE_MOVES"
2404 /* This insn should be already split before reg-stack. */
2407 [(set_attr "type" "multi")
2408 (set_attr "unit" "i387,*,*")
2409 (set_attr "mode" "DF,SI,DF")])
2411 ;; %%% Kill this when call knows how to work this out.
2413 [(set (match_operand:DF 0 "push_operand" "")
2414 (match_operand:DF 1 "any_fp_register_operand" ""))]
2415 "!TARGET_64BIT && reload_completed"
2416 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
2417 (set (mem:DF (reg:SI SP_REG)) (match_dup 1))]
2421 [(set (match_operand:DF 0 "push_operand" "")
2422 (match_operand:DF 1 "any_fp_register_operand" ""))]
2423 "TARGET_64BIT && reload_completed"
2424 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
2425 (set (mem:DF (reg:DI SP_REG)) (match_dup 1))]
2429 [(set (match_operand:DF 0 "push_operand" "")
2430 (match_operand:DF 1 "general_operand" ""))]
2433 "ix86_split_long_move (operands); DONE;")
2435 ;; Moving is usually shorter when only FP registers are used. This separate
2436 ;; movdf pattern avoids the use of integer registers for FP operations
2437 ;; when optimizing for size.
2439 (define_insn "*movdf_nointeger"
2440 [(set (match_operand:DF 0 "nonimmediate_operand"
2441 "=f#Y,m ,f#Y,*r ,o ,Y*x#f,Y*x#f,Y*x#f ,m ")
2442 (match_operand:DF 1 "general_operand"
2443 "fm#Y,f#Y,G ,*roF,F*r,C ,Y*x#f,HmY*x#f,Y*x#f"))]
2444 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2445 && ((optimize_size || !TARGET_INTEGER_DFMODE_MOVES) && !TARGET_64BIT)
2446 && (reload_in_progress || reload_completed
2447 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2448 || GET_CODE (operands[1]) != CONST_DOUBLE
2449 || memory_operand (operands[0], DFmode))"
2451 switch (which_alternative)
2454 return output_387_reg_move (insn, operands);
2457 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2458 return "fstp%z0\t%y0";
2460 return "fst%z0\t%y0";
2463 return standard_80387_constant_opcode (operands[1]);
2469 switch (get_attr_mode (insn))
2472 return "xorps\t%0, %0";
2474 return "xorpd\t%0, %0";
2476 return "pxor\t%0, %0";
2483 switch (get_attr_mode (insn))
2486 return "movaps\t{%1, %0|%0, %1}";
2488 return "movapd\t{%1, %0|%0, %1}";
2490 return "movdqa\t{%1, %0|%0, %1}";
2492 return "movq\t{%1, %0|%0, %1}";
2494 return "movsd\t{%1, %0|%0, %1}";
2496 return "movlpd\t{%1, %0|%0, %1}";
2498 return "movlps\t{%1, %0|%0, %1}";
2507 [(set_attr "type" "fmov,fmov,fmov,multi,multi,ssemov,ssemov,ssemov,ssemov")
2509 (cond [(eq_attr "alternative" "0,1,2")
2511 (eq_attr "alternative" "3,4")
2514 /* For SSE1, we have many fewer alternatives. */
2515 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2516 (cond [(eq_attr "alternative" "5,6")
2517 (const_string "V4SF")
2519 (const_string "V2SF"))
2521 /* xorps is one byte shorter. */
2522 (eq_attr "alternative" "5")
2523 (cond [(ne (symbol_ref "optimize_size")
2525 (const_string "V4SF")
2526 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2530 (const_string "V2DF"))
2532 /* For architectures resolving dependencies on
2533 whole SSE registers use APD move to break dependency
2534 chains, otherwise use short move to avoid extra work.
2536 movaps encodes one byte shorter. */
2537 (eq_attr "alternative" "6")
2539 [(ne (symbol_ref "optimize_size")
2541 (const_string "V4SF")
2542 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2544 (const_string "V2DF")
2546 (const_string "DF"))
2547 /* For architectures resolving dependencies on register
2548 parts we may avoid extra work to zero out upper part
2550 (eq_attr "alternative" "7")
2552 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2554 (const_string "V1DF")
2555 (const_string "DF"))
2557 (const_string "DF")))])
2559 (define_insn "*movdf_integer"
2560 [(set (match_operand:DF 0 "nonimmediate_operand"
2561 "=f#Yr,m ,f#Yr,r#Yf ,o ,Y*x#rf,Y*x#rf,Y*x#rf,m")
2562 (match_operand:DF 1 "general_operand"
2563 "fm#Yr,f#Yr,G ,roF#Yf,Fr#Yf,C ,Y*x#rf,m ,Y*x#rf"))]
2564 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2565 && ((!optimize_size && TARGET_INTEGER_DFMODE_MOVES) || TARGET_64BIT)
2566 && (reload_in_progress || reload_completed
2567 || (ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_LARGE)
2568 || GET_CODE (operands[1]) != CONST_DOUBLE
2569 || memory_operand (operands[0], DFmode))"
2571 switch (which_alternative)
2574 return output_387_reg_move (insn, operands);
2577 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2578 return "fstp%z0\t%y0";
2580 return "fst%z0\t%y0";
2583 return standard_80387_constant_opcode (operands[1]);
2590 switch (get_attr_mode (insn))
2593 return "xorps\t%0, %0";
2595 return "xorpd\t%0, %0";
2597 return "pxor\t%0, %0";
2604 switch (get_attr_mode (insn))
2607 return "movaps\t{%1, %0|%0, %1}";
2609 return "movapd\t{%1, %0|%0, %1}";
2611 return "movdqa\t{%1, %0|%0, %1}";
2613 return "movq\t{%1, %0|%0, %1}";
2615 return "movsd\t{%1, %0|%0, %1}";
2617 return "movlpd\t{%1, %0|%0, %1}";
2619 return "movlps\t{%1, %0|%0, %1}";
2628 [(set_attr "type" "fmov,fmov,fmov,multi,multi,ssemov,ssemov,ssemov,ssemov")
2630 (cond [(eq_attr "alternative" "0,1,2")
2632 (eq_attr "alternative" "3,4")
2635 /* For SSE1, we have many fewer alternatives. */
2636 (eq (symbol_ref "TARGET_SSE2") (const_int 0))
2637 (cond [(eq_attr "alternative" "5,6")
2638 (const_string "V4SF")
2640 (const_string "V2SF"))
2642 /* xorps is one byte shorter. */
2643 (eq_attr "alternative" "5")
2644 (cond [(ne (symbol_ref "optimize_size")
2646 (const_string "V4SF")
2647 (ne (symbol_ref "TARGET_SSE_LOAD0_BY_PXOR")
2651 (const_string "V2DF"))
2653 /* For architectures resolving dependencies on
2654 whole SSE registers use APD move to break dependency
2655 chains, otherwise use short move to avoid extra work.
2657 movaps encodes one byte shorter. */
2658 (eq_attr "alternative" "6")
2660 [(ne (symbol_ref "optimize_size")
2662 (const_string "V4SF")
2663 (ne (symbol_ref "TARGET_SSE_PARTIAL_REG_DEPENDENCY")
2665 (const_string "V2DF")
2667 (const_string "DF"))
2668 /* For architectures resolving dependencies on register
2669 parts we may avoid extra work to zero out upper part
2671 (eq_attr "alternative" "7")
2673 (ne (symbol_ref "TARGET_SSE_SPLIT_REGS")
2675 (const_string "V1DF")
2676 (const_string "DF"))
2678 (const_string "DF")))])
2681 [(set (match_operand:DF 0 "nonimmediate_operand" "")
2682 (match_operand:DF 1 "general_operand" ""))]
2684 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2685 && ! (ANY_FP_REG_P (operands[0]) ||
2686 (GET_CODE (operands[0]) == SUBREG
2687 && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2688 && ! (ANY_FP_REG_P (operands[1]) ||
2689 (GET_CODE (operands[1]) == SUBREG
2690 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2692 "ix86_split_long_move (operands); DONE;")
2694 (define_insn "*swapdf"
2695 [(set (match_operand:DF 0 "fp_register_operand" "+f")
2696 (match_operand:DF 1 "fp_register_operand" "+f"))
2699 "reload_completed || TARGET_80387"
2701 if (STACK_TOP_P (operands[0]))
2706 [(set_attr "type" "fxch")
2707 (set_attr "mode" "DF")])
2709 (define_expand "movxf"
2710 [(set (match_operand:XF 0 "nonimmediate_operand" "")
2711 (match_operand:XF 1 "general_operand" ""))]
2713 "ix86_expand_move (XFmode, operands); DONE;")
2715 ;; Size of pushdf is 3 (for sub) + 2 (for fstp) + memory operand size.
2716 ;; Size of pushdf using integer instructions is 3+3*memory operand size
2717 ;; Pushing using integer instructions is longer except for constants
2718 ;; and direct memory references.
2719 ;; (assuming that any given constant is pushed only once, but this ought to be
2720 ;; handled elsewhere).
2722 (define_insn "*pushxf_nointeger"
2723 [(set (match_operand:XF 0 "push_operand" "=X,X,X")
2724 (match_operand:XF 1 "general_no_elim_operand" "f,Fo,*r"))]
2727 /* This insn should be already split before reg-stack. */
2730 [(set_attr "type" "multi")
2731 (set_attr "unit" "i387,*,*")
2732 (set_attr "mode" "XF,SI,SI")])
2734 (define_insn "*pushxf_integer"
2735 [(set (match_operand:XF 0 "push_operand" "=<,<")
2736 (match_operand:XF 1 "general_no_elim_operand" "f#r,ro#f"))]
2739 /* This insn should be already split before reg-stack. */
2742 [(set_attr "type" "multi")
2743 (set_attr "unit" "i387,*")
2744 (set_attr "mode" "XF,SI")])
2747 [(set (match_operand 0 "push_operand" "")
2748 (match_operand 1 "general_operand" ""))]
2750 && (GET_MODE (operands[0]) == XFmode
2751 || GET_MODE (operands[0]) == DFmode)
2752 && !ANY_FP_REG_P (operands[1])"
2754 "ix86_split_long_move (operands); DONE;")
2757 [(set (match_operand:XF 0 "push_operand" "")
2758 (match_operand:XF 1 "any_fp_register_operand" ""))]
2760 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
2761 (set (mem:XF (reg:SI SP_REG)) (match_dup 1))]
2762 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
2765 [(set (match_operand:XF 0 "push_operand" "")
2766 (match_operand:XF 1 "any_fp_register_operand" ""))]
2768 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
2769 (set (mem:XF (reg:DI SP_REG)) (match_dup 1))]
2770 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
2772 ;; Do not use integer registers when optimizing for size
2773 (define_insn "*movxf_nointeger"
2774 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m,f,*r,o")
2775 (match_operand:XF 1 "general_operand" "fm,f,G,*roF,F*r"))]
2777 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2778 && (reload_in_progress || reload_completed
2779 || GET_CODE (operands[1]) != CONST_DOUBLE
2780 || memory_operand (operands[0], XFmode))"
2782 switch (which_alternative)
2785 return output_387_reg_move (insn, operands);
2788 /* There is no non-popping store to memory for XFmode. So if
2789 we need one, follow the store with a load. */
2790 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2791 return "fstp%z0\t%y0\;fld%z0\t%y0";
2793 return "fstp%z0\t%y0";
2796 return standard_80387_constant_opcode (operands[1]);
2804 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2805 (set_attr "mode" "XF,XF,XF,SI,SI")])
2807 (define_insn "*movxf_integer"
2808 [(set (match_operand:XF 0 "nonimmediate_operand" "=f#r,m,f#r,r#f,o")
2809 (match_operand:XF 1 "general_operand" "fm#r,f#r,G,roF#f,Fr#f"))]
2811 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2812 && (reload_in_progress || reload_completed
2813 || GET_CODE (operands[1]) != CONST_DOUBLE
2814 || memory_operand (operands[0], XFmode))"
2816 switch (which_alternative)
2819 return output_387_reg_move (insn, operands);
2822 /* There is no non-popping store to memory for XFmode. So if
2823 we need one, follow the store with a load. */
2824 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
2825 return "fstp%z0\t%y0\;fld%z0\t%y0";
2827 return "fstp%z0\t%y0";
2830 return standard_80387_constant_opcode (operands[1]);
2839 [(set_attr "type" "fmov,fmov,fmov,multi,multi")
2840 (set_attr "mode" "XF,XF,XF,SI,SI")])
2843 [(set (match_operand 0 "nonimmediate_operand" "")
2844 (match_operand 1 "general_operand" ""))]
2846 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
2847 && GET_MODE (operands[0]) == XFmode
2848 && ! (ANY_FP_REG_P (operands[0]) ||
2849 (GET_CODE (operands[0]) == SUBREG
2850 && ANY_FP_REG_P (SUBREG_REG (operands[0]))))
2851 && ! (ANY_FP_REG_P (operands[1]) ||
2852 (GET_CODE (operands[1]) == SUBREG
2853 && ANY_FP_REG_P (SUBREG_REG (operands[1]))))"
2855 "ix86_split_long_move (operands); DONE;")
2858 [(set (match_operand 0 "register_operand" "")
2859 (match_operand 1 "memory_operand" ""))]
2861 && GET_CODE (operands[1]) == MEM
2862 && (GET_MODE (operands[0]) == XFmode
2863 || GET_MODE (operands[0]) == SFmode || GET_MODE (operands[0]) == DFmode)
2864 && constant_pool_reference_p (operands[1])"
2865 [(set (match_dup 0) (match_dup 1))]
2867 rtx c = avoid_constant_pool_reference (operands[1]);
2868 rtx r = operands[0];
2870 if (GET_CODE (r) == SUBREG)
2875 if (!standard_sse_constant_p (c))
2878 else if (FP_REG_P (r))
2880 if (!standard_80387_constant_p (c))
2883 else if (MMX_REG_P (r))
2889 (define_insn "swapxf"
2890 [(set (match_operand:XF 0 "register_operand" "+f")
2891 (match_operand:XF 1 "register_operand" "+f"))
2896 if (STACK_TOP_P (operands[0]))
2901 [(set_attr "type" "fxch")
2902 (set_attr "mode" "XF")])
2904 (define_expand "movtf"
2905 [(set (match_operand:TF 0 "nonimmediate_operand" "")
2906 (match_operand:TF 1 "nonimmediate_operand" ""))]
2909 ix86_expand_move (TFmode, operands);
2913 (define_insn "*movtf_internal"
2914 [(set (match_operand:TF 0 "nonimmediate_operand" "=r,o,x,x,xm")
2915 (match_operand:TF 1 "general_operand" "riFo,riF,C,xm,x"))]
2917 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
2919 switch (which_alternative)
2925 if (get_attr_mode (insn) == MODE_V4SF)
2926 return "xorps\t%0, %0";
2928 return "pxor\t%0, %0";
2931 if (get_attr_mode (insn) == MODE_V4SF)
2932 return "movaps\t{%1, %0|%0, %1}";
2934 return "movdqa\t{%1, %0|%0, %1}";
2939 [(set_attr "type" "*,*,ssemov,ssemov,ssemov")
2941 (cond [(eq_attr "alternative" "2,3")
2943 (ne (symbol_ref "optimize_size")
2945 (const_string "V4SF")
2946 (const_string "TI"))
2947 (eq_attr "alternative" "4")
2949 (ior (ne (symbol_ref "TARGET_SSE_TYPELESS_STORES")
2951 (ne (symbol_ref "optimize_size")
2953 (const_string "V4SF")
2954 (const_string "TI"))]
2955 (const_string "DI")))])
2958 [(set (match_operand:TF 0 "nonimmediate_operand" "")
2959 (match_operand:TF 1 "general_operand" ""))]
2960 "reload_completed && !SSE_REG_P (operands[0])
2961 && !SSE_REG_P (operands[1])"
2963 "ix86_split_long_move (operands); DONE;")
2965 ;; Zero extension instructions
2967 (define_expand "zero_extendhisi2"
2968 [(set (match_operand:SI 0 "register_operand" "")
2969 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "")))]
2972 if (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
2974 operands[1] = force_reg (HImode, operands[1]);
2975 emit_insn (gen_zero_extendhisi2_and (operands[0], operands[1]));
2980 (define_insn "zero_extendhisi2_and"
2981 [(set (match_operand:SI 0 "register_operand" "=r")
2982 (zero_extend:SI (match_operand:HI 1 "register_operand" "0")))
2983 (clobber (reg:CC FLAGS_REG))]
2984 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
2986 [(set_attr "type" "alu1")
2987 (set_attr "mode" "SI")])
2990 [(set (match_operand:SI 0 "register_operand" "")
2991 (zero_extend:SI (match_operand:HI 1 "register_operand" "")))
2992 (clobber (reg:CC FLAGS_REG))]
2993 "reload_completed && TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
2994 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 65535)))
2995 (clobber (reg:CC FLAGS_REG))])]
2998 (define_insn "*zero_extendhisi2_movzwl"
2999 [(set (match_operand:SI 0 "register_operand" "=r")
3000 (zero_extend:SI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3001 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3002 "movz{wl|x}\t{%1, %0|%0, %1}"
3003 [(set_attr "type" "imovx")
3004 (set_attr "mode" "SI")])
3006 (define_expand "zero_extendqihi2"
3008 [(set (match_operand:HI 0 "register_operand" "")
3009 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3010 (clobber (reg:CC FLAGS_REG))])]
3014 (define_insn "*zero_extendqihi2_and"
3015 [(set (match_operand:HI 0 "register_operand" "=r,?&q")
3016 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3017 (clobber (reg:CC FLAGS_REG))]
3018 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3020 [(set_attr "type" "alu1")
3021 (set_attr "mode" "HI")])
3023 (define_insn "*zero_extendqihi2_movzbw_and"
3024 [(set (match_operand:HI 0 "register_operand" "=r,r")
3025 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3026 (clobber (reg:CC FLAGS_REG))]
3027 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3029 [(set_attr "type" "imovx,alu1")
3030 (set_attr "mode" "HI")])
3032 (define_insn "*zero_extendqihi2_movzbw"
3033 [(set (match_operand:HI 0 "register_operand" "=r")
3034 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3035 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3036 "movz{bw|x}\t{%1, %0|%0, %1}"
3037 [(set_attr "type" "imovx")
3038 (set_attr "mode" "HI")])
3040 ;; For the movzbw case strip only the clobber
3042 [(set (match_operand:HI 0 "register_operand" "")
3043 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3044 (clobber (reg:CC FLAGS_REG))]
3046 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3047 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3048 [(set (match_operand:HI 0 "register_operand" "")
3049 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))])
3051 ;; When source and destination does not overlap, clear destination
3052 ;; first and then do the movb
3054 [(set (match_operand:HI 0 "register_operand" "")
3055 (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "")))
3056 (clobber (reg:CC FLAGS_REG))]
3058 && ANY_QI_REG_P (operands[0])
3059 && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3060 && !reg_overlap_mentioned_p (operands[0], operands[1])"
3061 [(set (match_dup 0) (const_int 0))
3062 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3063 "operands[2] = gen_lowpart (QImode, operands[0]);")
3065 ;; Rest is handled by single and.
3067 [(set (match_operand:HI 0 "register_operand" "")
3068 (zero_extend:HI (match_operand:QI 1 "register_operand" "")))
3069 (clobber (reg:CC FLAGS_REG))]
3071 && true_regnum (operands[0]) == true_regnum (operands[1])"
3072 [(parallel [(set (match_dup 0) (and:HI (match_dup 0) (const_int 255)))
3073 (clobber (reg:CC FLAGS_REG))])]
3076 (define_expand "zero_extendqisi2"
3078 [(set (match_operand:SI 0 "register_operand" "")
3079 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3080 (clobber (reg:CC FLAGS_REG))])]
3084 (define_insn "*zero_extendqisi2_and"
3085 [(set (match_operand:SI 0 "register_operand" "=r,?&q")
3086 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "0,qm")))
3087 (clobber (reg:CC FLAGS_REG))]
3088 "TARGET_ZERO_EXTEND_WITH_AND && !optimize_size"
3090 [(set_attr "type" "alu1")
3091 (set_attr "mode" "SI")])
3093 (define_insn "*zero_extendqisi2_movzbw_and"
3094 [(set (match_operand:SI 0 "register_operand" "=r,r")
3095 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm,0")))
3096 (clobber (reg:CC FLAGS_REG))]
3097 "!TARGET_ZERO_EXTEND_WITH_AND || optimize_size"
3099 [(set_attr "type" "imovx,alu1")
3100 (set_attr "mode" "SI")])
3102 (define_insn "*zero_extendqisi2_movzbw"
3103 [(set (match_operand:SI 0 "register_operand" "=r")
3104 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3105 "(!TARGET_ZERO_EXTEND_WITH_AND || optimize_size) && reload_completed"
3106 "movz{bl|x}\t{%1, %0|%0, %1}"
3107 [(set_attr "type" "imovx")
3108 (set_attr "mode" "SI")])
3110 ;; For the movzbl case strip only the clobber
3112 [(set (match_operand:SI 0 "register_operand" "")
3113 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3114 (clobber (reg:CC FLAGS_REG))]
3116 && (!TARGET_ZERO_EXTEND_WITH_AND || optimize_size)
3117 && (!REG_P (operands[1]) || ANY_QI_REG_P (operands[1]))"
3119 (zero_extend:SI (match_dup 1)))])
3121 ;; When source and destination does not overlap, clear destination
3122 ;; first and then do the movb
3124 [(set (match_operand:SI 0 "register_operand" "")
3125 (zero_extend:SI (match_operand:QI 1 "nonimmediate_operand" "")))
3126 (clobber (reg:CC FLAGS_REG))]
3128 && ANY_QI_REG_P (operands[0])
3129 && (ANY_QI_REG_P (operands[1]) || GET_CODE (operands[1]) == MEM)
3130 && (TARGET_ZERO_EXTEND_WITH_AND && !optimize_size)
3131 && !reg_overlap_mentioned_p (operands[0], operands[1])"
3132 [(set (match_dup 0) (const_int 0))
3133 (set (strict_low_part (match_dup 2)) (match_dup 1))]
3134 "operands[2] = gen_lowpart (QImode, operands[0]);")
3136 ;; Rest is handled by single and.
3138 [(set (match_operand:SI 0 "register_operand" "")
3139 (zero_extend:SI (match_operand:QI 1 "register_operand" "")))
3140 (clobber (reg:CC FLAGS_REG))]
3142 && true_regnum (operands[0]) == true_regnum (operands[1])"
3143 [(parallel [(set (match_dup 0) (and:SI (match_dup 0) (const_int 255)))
3144 (clobber (reg:CC FLAGS_REG))])]
3147 ;; %%% Kill me once multi-word ops are sane.
3148 (define_expand "zero_extendsidi2"
3149 [(set (match_operand:DI 0 "register_operand" "=r")
3150 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm")))]
3154 emit_insn (gen_zero_extendsidi2_32 (operands[0], operands[1]));
3159 (define_insn "zero_extendsidi2_32"
3160 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,?r,?*o,?*y,?*Y")
3161 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "0,rm,r,rm,rm")))
3162 (clobber (reg:CC FLAGS_REG))]
3168 movd\t{%1, %0|%0, %1}
3169 movd\t{%1, %0|%0, %1}"
3170 [(set_attr "mode" "SI,SI,SI,DI,TI")
3171 (set_attr "type" "multi,multi,multi,mmxmov,ssemov")])
3173 (define_insn "zero_extendsidi2_rex64"
3174 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o,?*y,?*Y")
3175 (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "rm,0,rm,rm")))]
3178 mov\t{%k1, %k0|%k0, %k1}
3180 movd\t{%1, %0|%0, %1}
3181 movd\t{%1, %0|%0, %1}"
3182 [(set_attr "type" "imovx,imov,mmxmov,ssemov")
3183 (set_attr "mode" "SI,DI,SI,SI")])
3186 [(set (match_operand:DI 0 "memory_operand" "")
3187 (zero_extend:DI (match_dup 0)))]
3189 [(set (match_dup 4) (const_int 0))]
3190 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3193 [(set (match_operand:DI 0 "register_operand" "")
3194 (zero_extend:DI (match_operand:SI 1 "register_operand" "")))
3195 (clobber (reg:CC FLAGS_REG))]
3196 "!TARGET_64BIT && reload_completed
3197 && true_regnum (operands[0]) == true_regnum (operands[1])"
3198 [(set (match_dup 4) (const_int 0))]
3199 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3202 [(set (match_operand:DI 0 "nonimmediate_operand" "")
3203 (zero_extend:DI (match_operand:SI 1 "general_operand" "")))
3204 (clobber (reg:CC FLAGS_REG))]
3205 "!TARGET_64BIT && reload_completed
3206 && !SSE_REG_P (operands[0]) && !MMX_REG_P (operands[0])"
3207 [(set (match_dup 3) (match_dup 1))
3208 (set (match_dup 4) (const_int 0))]
3209 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3211 (define_insn "zero_extendhidi2"
3212 [(set (match_operand:DI 0 "register_operand" "=r")
3213 (zero_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3215 "movz{wl|x}\t{%1, %k0|%k0, %1}"
3216 [(set_attr "type" "imovx")
3217 (set_attr "mode" "DI")])
3219 (define_insn "zero_extendqidi2"
3220 [(set (match_operand:DI 0 "register_operand" "=r")
3221 (zero_extend:DI (match_operand:QI 1 "nonimmediate_operand" "rm")))]
3223 "movz{bl|x}\t{%1, %k0|%k0, %1}"
3224 [(set_attr "type" "imovx")
3225 (set_attr "mode" "DI")])
3227 ;; Sign extension instructions
3229 (define_expand "extendsidi2"
3230 [(parallel [(set (match_operand:DI 0 "register_operand" "")
3231 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3232 (clobber (reg:CC FLAGS_REG))
3233 (clobber (match_scratch:SI 2 ""))])]
3238 emit_insn (gen_extendsidi2_rex64 (operands[0], operands[1]));
3243 (define_insn "*extendsidi2_1"
3244 [(set (match_operand:DI 0 "nonimmediate_operand" "=*A,r,?r,?*o")
3245 (sign_extend:DI (match_operand:SI 1 "register_operand" "0,0,r,r")))
3246 (clobber (reg:CC FLAGS_REG))
3247 (clobber (match_scratch:SI 2 "=X,X,X,&r"))]
3251 (define_insn "extendsidi2_rex64"
3252 [(set (match_operand:DI 0 "register_operand" "=*a,r")
3253 (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "*0,rm")))]
3257 movs{lq|x}\t{%1,%0|%0, %1}"
3258 [(set_attr "type" "imovx")
3259 (set_attr "mode" "DI")
3260 (set_attr "prefix_0f" "0")
3261 (set_attr "modrm" "0,1")])
3263 (define_insn "extendhidi2"
3264 [(set (match_operand:DI 0 "register_operand" "=r")
3265 (sign_extend:DI (match_operand:HI 1 "nonimmediate_operand" "rm")))]
3267 "movs{wq|x}\t{%1,%0|%0, %1}"
3268 [(set_attr "type" "imovx")
3269 (set_attr "mode" "DI")])
3271 (define_insn "extendqidi2"
3272 [(set (match_operand:DI 0 "register_operand" "=r")
3273 (sign_extend:DI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3275 "movs{bq|x}\t{%1,%0|%0, %1}"
3276 [(set_attr "type" "imovx")
3277 (set_attr "mode" "DI")])
3279 ;; Extend to memory case when source register does die.
3281 [(set (match_operand:DI 0 "memory_operand" "")
3282 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3283 (clobber (reg:CC FLAGS_REG))
3284 (clobber (match_operand:SI 2 "register_operand" ""))]
3286 && dead_or_set_p (insn, operands[1])
3287 && !reg_mentioned_p (operands[1], operands[0]))"
3288 [(set (match_dup 3) (match_dup 1))
3289 (parallel [(set (match_dup 1) (ashiftrt:SI (match_dup 1) (const_int 31)))
3290 (clobber (reg:CC FLAGS_REG))])
3291 (set (match_dup 4) (match_dup 1))]
3292 "split_di (&operands[0], 1, &operands[3], &operands[4]);")
3294 ;; Extend to memory case when source register does not die.
3296 [(set (match_operand:DI 0 "memory_operand" "")
3297 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3298 (clobber (reg:CC FLAGS_REG))
3299 (clobber (match_operand:SI 2 "register_operand" ""))]
3303 split_di (&operands[0], 1, &operands[3], &operands[4]);
3305 emit_move_insn (operands[3], operands[1]);
3307 /* Generate a cltd if possible and doing so it profitable. */
3308 if (true_regnum (operands[1]) == 0
3309 && true_regnum (operands[2]) == 1
3310 && (optimize_size || TARGET_USE_CLTD))
3312 emit_insn (gen_ashrsi3_31 (operands[2], operands[1], GEN_INT (31)));
3316 emit_move_insn (operands[2], operands[1]);
3317 emit_insn (gen_ashrsi3_31 (operands[2], operands[2], GEN_INT (31)));
3319 emit_move_insn (operands[4], operands[2]);
3323 ;; Extend to register case. Optimize case where source and destination
3324 ;; registers match and cases where we can use cltd.
3326 [(set (match_operand:DI 0 "register_operand" "")
3327 (sign_extend:DI (match_operand:SI 1 "register_operand" "")))
3328 (clobber (reg:CC FLAGS_REG))
3329 (clobber (match_scratch:SI 2 ""))]
3333 split_di (&operands[0], 1, &operands[3], &operands[4]);
3335 if (true_regnum (operands[3]) != true_regnum (operands[1]))
3336 emit_move_insn (operands[3], operands[1]);
3338 /* Generate a cltd if possible and doing so it profitable. */
3339 if (true_regnum (operands[3]) == 0
3340 && (optimize_size || TARGET_USE_CLTD))
3342 emit_insn (gen_ashrsi3_31 (operands[4], operands[3], GEN_INT (31)));
3346 if (true_regnum (operands[4]) != true_regnum (operands[1]))
3347 emit_move_insn (operands[4], operands[1]);
3349 emit_insn (gen_ashrsi3_31 (operands[4], operands[4], GEN_INT (31)));
3353 (define_insn "extendhisi2"
3354 [(set (match_operand:SI 0 "register_operand" "=*a,r")
3355 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm")))]
3358 switch (get_attr_prefix_0f (insn))
3361 return "{cwtl|cwde}";
3363 return "movs{wl|x}\t{%1,%0|%0, %1}";
3366 [(set_attr "type" "imovx")
3367 (set_attr "mode" "SI")
3368 (set (attr "prefix_0f")
3369 ;; movsx is short decodable while cwtl is vector decoded.
3370 (if_then_else (and (eq_attr "cpu" "!k6")
3371 (eq_attr "alternative" "0"))
3373 (const_string "1")))
3375 (if_then_else (eq_attr "prefix_0f" "0")
3377 (const_string "1")))])
3379 (define_insn "*extendhisi2_zext"
3380 [(set (match_operand:DI 0 "register_operand" "=*a,r")
3382 (sign_extend:SI (match_operand:HI 1 "nonimmediate_operand" "*0,rm"))))]
3385 switch (get_attr_prefix_0f (insn))
3388 return "{cwtl|cwde}";
3390 return "movs{wl|x}\t{%1,%k0|%k0, %1}";
3393 [(set_attr "type" "imovx")
3394 (set_attr "mode" "SI")
3395 (set (attr "prefix_0f")
3396 ;; movsx is short decodable while cwtl is vector decoded.
3397 (if_then_else (and (eq_attr "cpu" "!k6")
3398 (eq_attr "alternative" "0"))
3400 (const_string "1")))
3402 (if_then_else (eq_attr "prefix_0f" "0")
3404 (const_string "1")))])
3406 (define_insn "extendqihi2"
3407 [(set (match_operand:HI 0 "register_operand" "=*a,r")
3408 (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "*0,qm")))]
3411 switch (get_attr_prefix_0f (insn))
3414 return "{cbtw|cbw}";
3416 return "movs{bw|x}\t{%1,%0|%0, %1}";
3419 [(set_attr "type" "imovx")
3420 (set_attr "mode" "HI")
3421 (set (attr "prefix_0f")
3422 ;; movsx is short decodable while cwtl is vector decoded.
3423 (if_then_else (and (eq_attr "cpu" "!k6")
3424 (eq_attr "alternative" "0"))
3426 (const_string "1")))
3428 (if_then_else (eq_attr "prefix_0f" "0")
3430 (const_string "1")))])
3432 (define_insn "extendqisi2"
3433 [(set (match_operand:SI 0 "register_operand" "=r")
3434 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm")))]
3436 "movs{bl|x}\t{%1,%0|%0, %1}"
3437 [(set_attr "type" "imovx")
3438 (set_attr "mode" "SI")])
3440 (define_insn "*extendqisi2_zext"
3441 [(set (match_operand:DI 0 "register_operand" "=r")
3443 (sign_extend:SI (match_operand:QI 1 "nonimmediate_operand" "qm"))))]
3445 "movs{bl|x}\t{%1,%k0|%k0, %1}"
3446 [(set_attr "type" "imovx")
3447 (set_attr "mode" "SI")])
3449 ;; Conversions between float and double.
3451 ;; These are all no-ops in the model used for the 80387. So just
3454 ;; %%% Kill these when call knows how to work out a DFmode push earlier.
3455 (define_insn "*dummy_extendsfdf2"
3456 [(set (match_operand:DF 0 "push_operand" "=<")
3457 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fY")))]
3462 [(set (match_operand:DF 0 "push_operand" "")
3463 (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3465 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
3466 (set (mem:DF (reg:SI SP_REG)) (float_extend:DF (match_dup 1)))])
3469 [(set (match_operand:DF 0 "push_operand" "")
3470 (float_extend:DF (match_operand:SF 1 "fp_register_operand" "")))]
3472 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
3473 (set (mem:DF (reg:DI SP_REG)) (float_extend:DF (match_dup 1)))])
3475 (define_insn "*dummy_extendsfxf2"
3476 [(set (match_operand:XF 0 "push_operand" "=<")
3477 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "f")))]
3482 [(set (match_operand:XF 0 "push_operand" "")
3483 (float_extend:XF (match_operand:SF 1 "fp_register_operand" "")))]
3485 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3486 (set (mem:XF (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:SF 1 "fp_register_operand" "")))]
3493 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3494 (set (mem:DF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))]
3495 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3498 [(set (match_operand:XF 0 "push_operand" "")
3499 (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3501 [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (match_dup 2)))
3502 (set (mem:DF (reg:SI SP_REG)) (float_extend:XF (match_dup 1)))]
3503 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3506 [(set (match_operand:XF 0 "push_operand" "")
3507 (float_extend:XF (match_operand:DF 1 "fp_register_operand" "")))]
3509 [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (match_dup 2)))
3510 (set (mem:XF (reg:DI SP_REG)) (float_extend:XF (match_dup 1)))]
3511 "operands[2] = GEN_INT (TARGET_128BIT_LONG_DOUBLE ? -16 : -12);")
3513 (define_expand "extendsfdf2"
3514 [(set (match_operand:DF 0 "nonimmediate_operand" "")
3515 (float_extend:DF (match_operand:SF 1 "general_operand" "")))]
3516 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3518 /* ??? Needed for compress_float_constant since all fp constants
3519 are LEGITIMATE_CONSTANT_P. */
3520 if (GET_CODE (operands[1]) == CONST_DOUBLE)
3521 operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3522 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3523 operands[1] = force_reg (SFmode, operands[1]);
3526 (define_insn "*extendsfdf2_mixed"
3527 [(set (match_operand:DF 0 "nonimmediate_operand" "=f#Y,m#fY,Y#f")
3528 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm#Y,f#Y,mY#f")))]
3529 "TARGET_SSE2 && TARGET_MIX_SSE_I387
3530 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3532 switch (which_alternative)
3535 return output_387_reg_move (insn, operands);
3538 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3539 return "fstp%z0\t%y0";
3541 return "fst%z0\t%y0";
3544 return "cvtss2sd\t{%1, %0|%0, %1}";
3550 [(set_attr "type" "fmov,fmov,ssecvt")
3551 (set_attr "mode" "SF,XF,DF")])
3553 (define_insn "*extendsfdf2_sse"
3554 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y")
3555 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "mY")))]
3556 "TARGET_SSE2 && TARGET_SSE_MATH
3557 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3558 "cvtss2sd\t{%1, %0|%0, %1}"
3559 [(set_attr "type" "ssecvt")
3560 (set_attr "mode" "DF")])
3562 (define_insn "*extendsfdf2_i387"
3563 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,m")
3564 (float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3566 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3568 switch (which_alternative)
3571 return output_387_reg_move (insn, operands);
3574 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3575 return "fstp%z0\t%y0";
3577 return "fst%z0\t%y0";
3583 [(set_attr "type" "fmov")
3584 (set_attr "mode" "SF,XF")])
3586 (define_expand "extendsfxf2"
3587 [(set (match_operand:XF 0 "nonimmediate_operand" "")
3588 (float_extend:XF (match_operand:SF 1 "general_operand" "")))]
3591 /* ??? Needed for compress_float_constant since all fp constants
3592 are LEGITIMATE_CONSTANT_P. */
3593 if (GET_CODE (operands[1]) == CONST_DOUBLE)
3594 operands[1] = validize_mem (force_const_mem (SFmode, operands[1]));
3595 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3596 operands[1] = force_reg (SFmode, operands[1]);
3599 (define_insn "*extendsfxf2_i387"
3600 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3601 (float_extend:XF (match_operand:SF 1 "nonimmediate_operand" "fm,f")))]
3603 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3605 switch (which_alternative)
3608 return output_387_reg_move (insn, operands);
3611 /* There is no non-popping store to memory for XFmode. So if
3612 we need one, follow the store with a load. */
3613 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3614 return "fstp%z0\t%y0";
3616 return "fstp%z0\t%y0\n\tfld%z0\t%y0";
3622 [(set_attr "type" "fmov")
3623 (set_attr "mode" "SF,XF")])
3625 (define_expand "extenddfxf2"
3626 [(set (match_operand:XF 0 "nonimmediate_operand" "")
3627 (float_extend:XF (match_operand:DF 1 "general_operand" "")))]
3630 /* ??? Needed for compress_float_constant since all fp constants
3631 are LEGITIMATE_CONSTANT_P. */
3632 if (GET_CODE (operands[1]) == CONST_DOUBLE)
3633 operands[1] = validize_mem (force_const_mem (DFmode, operands[1]));
3634 if (GET_CODE (operands[0]) == MEM && GET_CODE (operands[1]) == MEM)
3635 operands[1] = force_reg (DFmode, operands[1]);
3638 (define_insn "*extenddfxf2_i387"
3639 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,m")
3640 (float_extend:XF (match_operand:DF 1 "nonimmediate_operand" "fm,f")))]
3642 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
3644 switch (which_alternative)
3647 return output_387_reg_move (insn, operands);
3650 /* There is no non-popping store to memory for XFmode. So if
3651 we need one, follow the store with a load. */
3652 if (! find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3653 return "fstp%z0\t%y0\n\tfld%z0\t%y0";
3655 return "fstp%z0\t%y0";
3661 [(set_attr "type" "fmov")
3662 (set_attr "mode" "DF,XF")])
3664 ;; %%% This seems bad bad news.
3665 ;; This cannot output into an f-reg because there is no way to be sure
3666 ;; of truncating in that case. Otherwise this is just like a simple move
3667 ;; insn. So we pretend we can output to a reg in order to get better
3668 ;; register preferencing, but we really use a stack slot.
3670 ;; Conversion from DFmode to SFmode.
3672 (define_expand "truncdfsf2"
3673 [(set (match_operand:SF 0 "nonimmediate_operand" "")
3675 (match_operand:DF 1 "nonimmediate_operand" "")))]
3676 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
3678 if (MEM_P (operands[0]) && MEM_P (operands[1]))
3679 operands[1] = force_reg (DFmode, operands[1]);
3681 if (TARGET_SSE2 && TARGET_SSE_MATH && !TARGET_MIX_SSE_I387)
3683 else if (flag_unsafe_math_optimizations)
3687 rtx temp = assign_386_stack_local (SFmode, SLOT_TEMP);
3688 emit_insn (gen_truncdfsf2_with_temp (operands[0], operands[1], temp));
3693 (define_expand "truncdfsf2_with_temp"
3694 [(parallel [(set (match_operand:SF 0 "" "")
3695 (float_truncate:SF (match_operand:DF 1 "" "")))
3696 (clobber (match_operand:SF 2 "" ""))])]
3699 (define_insn "*truncdfsf_fast_mixed"
3700 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,f,Y")
3702 (match_operand:DF 1 "nonimmediate_operand" "f ,f,Ym")))]
3703 "TARGET_SSE2 && TARGET_MIX_SSE_I387 && flag_unsafe_math_optimizations"
3705 switch (which_alternative)
3708 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3709 return "fstp%z0\t%y0";
3711 return "fst%z0\t%y0";
3713 return output_387_reg_move (insn, operands);
3715 return "cvtsd2ss\t{%1, %0|%0, %1}";
3720 [(set_attr "type" "fmov,fmov,ssecvt")
3721 (set_attr "mode" "SF")])
3723 ;; Yes, this one doesn't depend on flag_unsafe_math_optimizations,
3724 ;; because nothing we do here is unsafe.
3725 (define_insn "*truncdfsf_fast_sse"
3726 [(set (match_operand:SF 0 "nonimmediate_operand" "=Y")
3728 (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
3729 "TARGET_SSE2 && TARGET_SSE_MATH"
3730 "cvtsd2ss\t{%1, %0|%0, %1}"
3731 [(set_attr "type" "ssecvt")
3732 (set_attr "mode" "SF")])
3734 (define_insn "*truncdfsf_fast_i387"
3735 [(set (match_operand:SF 0 "nonimmediate_operand" "=fm")
3737 (match_operand:DF 1 "nonimmediate_operand" "f")))]
3738 "TARGET_80387 && flag_unsafe_math_optimizations"
3739 "* return output_387_reg_move (insn, operands);"
3740 [(set_attr "type" "fmov")
3741 (set_attr "mode" "SF")])
3743 (define_insn "*truncdfsf_mixed"
3744 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r,Y")
3746 (match_operand:DF 1 "nonimmediate_operand" "f ,f ,Ym")))
3747 (clobber (match_operand:SF 2 "memory_operand" "=X,m ,X"))]
3748 "TARGET_MIX_SSE_I387"
3750 switch (which_alternative)
3753 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3754 return "fstp%z0\t%y0";
3756 return "fst%z0\t%y0";
3760 return "cvtsd2ss\t{%1, %0|%0, %1}";
3765 [(set_attr "type" "fmov,multi,ssecvt")
3766 (set_attr "unit" "*,i387,*")
3767 (set_attr "mode" "SF")])
3769 (define_insn "*truncdfsf_i387"
3770 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?fx*r")
3772 (match_operand:DF 1 "nonimmediate_operand" "f,f")))
3773 (clobber (match_operand:SF 2 "memory_operand" "=X,m"))]
3776 switch (which_alternative)
3779 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3780 return "fstp%z0\t%y0";
3782 return "fst%z0\t%y0";
3789 [(set_attr "type" "fmov,multi")
3790 (set_attr "unit" "*,i387")
3791 (set_attr "mode" "SF")])
3793 (define_insn "*truncdfsf2_i387_1"
3794 [(set (match_operand:SF 0 "memory_operand" "=m")
3796 (match_operand:DF 1 "register_operand" "f")))]
3798 && !(TARGET_SSE2 && TARGET_SSE_MATH)
3799 && !TARGET_MIX_SSE_I387"
3801 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3802 return "fstp%z0\t%y0";
3804 return "fst%z0\t%y0";
3806 [(set_attr "type" "fmov")
3807 (set_attr "mode" "SF")])
3810 [(set (match_operand:SF 0 "register_operand" "")
3812 (match_operand:DF 1 "fp_register_operand" "")))
3813 (clobber (match_operand 2 "" ""))]
3815 [(set (match_dup 2) (match_dup 1))
3816 (set (match_dup 0) (match_dup 2))]
3818 operands[1] = gen_rtx_REG (SFmode, true_regnum (operands[1]));
3821 ;; Conversion from XFmode to SFmode.
3823 (define_expand "truncxfsf2"
3824 [(parallel [(set (match_operand:SF 0 "nonimmediate_operand" "")
3826 (match_operand:XF 1 "register_operand" "")))
3827 (clobber (match_dup 2))])]
3830 if (flag_unsafe_math_optimizations)
3832 rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SFmode);
3833 emit_insn (gen_truncxfsf2_i387_noop (reg, operands[1]));
3834 if (reg != operands[0])
3835 emit_move_insn (operands[0], reg);
3839 operands[2] = assign_386_stack_local (SFmode, SLOT_TEMP);
3842 (define_insn "*truncxfsf2_mixed"
3843 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f#rx,?r#fx,?x#rf")
3845 (match_operand:XF 1 "register_operand" "f,f,f,f")))
3846 (clobber (match_operand:SF 2 "memory_operand" "=X,m,m,m"))]
3847 "TARGET_MIX_SSE_I387"
3849 gcc_assert (!which_alternative);
3850 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3851 return "fstp%z0\t%y0";
3853 return "fst%z0\t%y0";
3855 [(set_attr "type" "fmov,multi,multi,multi")
3856 (set_attr "unit" "*,i387,i387,i387")
3857 (set_attr "mode" "SF")])
3859 (define_insn "truncxfsf2_i387_noop"
3860 [(set (match_operand:SF 0 "register_operand" "=f")
3861 (float_truncate:SF (match_operand:XF 1 "register_operand" "f")))]
3862 "TARGET_80387 && flag_unsafe_math_optimizations"
3864 return output_387_reg_move (insn, operands);
3866 [(set_attr "type" "fmov")
3867 (set_attr "mode" "SF")])
3869 (define_insn "*truncxfsf2_i387"
3870 [(set (match_operand:SF 0 "nonimmediate_operand" "=m,?f#r,?r#f")
3872 (match_operand:XF 1 "register_operand" "f,f,f")))
3873 (clobber (match_operand:SF 2 "memory_operand" "=X,m,m"))]
3876 gcc_assert (!which_alternative);
3877 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3878 return "fstp%z0\t%y0";
3880 return "fst%z0\t%y0";
3882 [(set_attr "type" "fmov,multi,multi")
3883 (set_attr "unit" "*,i387,i387")
3884 (set_attr "mode" "SF")])
3886 (define_insn "*truncxfsf2_i387_1"
3887 [(set (match_operand:SF 0 "memory_operand" "=m")
3889 (match_operand:XF 1 "register_operand" "f")))]
3892 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3893 return "fstp%z0\t%y0";
3895 return "fst%z0\t%y0";
3897 [(set_attr "type" "fmov")
3898 (set_attr "mode" "SF")])
3901 [(set (match_operand:SF 0 "register_operand" "")
3903 (match_operand:XF 1 "register_operand" "")))
3904 (clobber (match_operand:SF 2 "memory_operand" ""))]
3905 "TARGET_80387 && reload_completed"
3906 [(set (match_dup 2) (float_truncate:SF (match_dup 1)))
3907 (set (match_dup 0) (match_dup 2))]
3911 [(set (match_operand:SF 0 "memory_operand" "")
3913 (match_operand:XF 1 "register_operand" "")))
3914 (clobber (match_operand:SF 2 "memory_operand" ""))]
3916 [(set (match_dup 0) (float_truncate:SF (match_dup 1)))]
3919 ;; Conversion from XFmode to DFmode.
3921 (define_expand "truncxfdf2"
3922 [(parallel [(set (match_operand:DF 0 "nonimmediate_operand" "")
3924 (match_operand:XF 1 "register_operand" "")))
3925 (clobber (match_dup 2))])]
3928 if (flag_unsafe_math_optimizations)
3930 rtx reg = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DFmode);
3931 emit_insn (gen_truncxfdf2_i387_noop (reg, operands[1]));
3932 if (reg != operands[0])
3933 emit_move_insn (operands[0], reg);
3937 operands[2] = assign_386_stack_local (DFmode, SLOT_TEMP);
3940 (define_insn "*truncxfdf2_mixed"
3941 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f#rY,?r#fY,?Y#rf")
3943 (match_operand:XF 1 "register_operand" "f,f,f,f")))
3944 (clobber (match_operand:DF 2 "memory_operand" "=X,m,m,m"))]
3945 "TARGET_SSE2 && TARGET_MIX_SSE_I387"
3947 gcc_assert (!which_alternative);
3948 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3949 return "fstp%z0\t%y0";
3951 return "fst%z0\t%y0";
3953 [(set_attr "type" "fmov,multi,multi,multi")
3954 (set_attr "unit" "*,i387,i387,i387")
3955 (set_attr "mode" "DF")])
3957 (define_insn "truncxfdf2_i387_noop"
3958 [(set (match_operand:DF 0 "register_operand" "=f")
3959 (float_truncate:DF (match_operand:XF 1 "register_operand" "f")))]
3960 "TARGET_80387 && flag_unsafe_math_optimizations"
3962 return output_387_reg_move (insn, operands);
3964 [(set_attr "type" "fmov")
3965 (set_attr "mode" "DF")])
3967 (define_insn "*truncxfdf2_i387"
3968 [(set (match_operand:DF 0 "nonimmediate_operand" "=m,?f#r,?r#f")
3970 (match_operand:XF 1 "register_operand" "f,f,f")))
3971 (clobber (match_operand:DF 2 "memory_operand" "=X,m,m"))]
3974 gcc_assert (!which_alternative);
3975 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3976 return "fstp%z0\t%y0";
3978 return "fst%z0\t%y0";
3980 [(set_attr "type" "fmov,multi,multi")
3981 (set_attr "unit" "*,i387,i387")
3982 (set_attr "mode" "DF")])
3984 (define_insn "*truncxfdf2_i387_1"
3985 [(set (match_operand:DF 0 "memory_operand" "=m")
3987 (match_operand:XF 1 "register_operand" "f")))]
3990 if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
3991 return "fstp%z0\t%y0";
3993 return "fst%z0\t%y0";
3995 [(set_attr "type" "fmov")
3996 (set_attr "mode" "DF")])
3999 [(set (match_operand:DF 0 "register_operand" "")
4001 (match_operand:XF 1 "register_operand" "")))
4002 (clobber (match_operand:DF 2 "memory_operand" ""))]
4003 "TARGET_80387 && reload_completed"
4004 [(set (match_dup 2) (float_truncate:DF (match_dup 1)))
4005 (set (match_dup 0) (match_dup 2))]
4009 [(set (match_operand:DF 0 "memory_operand" "")
4011 (match_operand:XF 1 "register_operand" "")))
4012 (clobber (match_operand:DF 2 "memory_operand" ""))]
4014 [(set (match_dup 0) (float_truncate:DF (match_dup 1)))]
4017 ;; Signed conversion to DImode.
4019 (define_expand "fix_truncxfdi2"
4020 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4021 (fix:DI (match_operand:XF 1 "register_operand" "")))
4022 (clobber (reg:CC FLAGS_REG))])]
4027 emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4032 (define_expand "fix_trunc<mode>di2"
4033 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
4034 (fix:DI (match_operand:SSEMODEF 1 "register_operand" "")))
4035 (clobber (reg:CC FLAGS_REG))])]
4036 "TARGET_80387 || (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))"
4039 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4041 emit_insn (gen_fix_truncdi_fisttp_i387_1 (operands[0], operands[1]));
4044 if (TARGET_64BIT && SSE_FLOAT_MODE_P (<MODE>mode))
4046 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (DImode);
4047 emit_insn (gen_fix_trunc<mode>di_sse (out, operands[1]));
4048 if (out != operands[0])
4049 emit_move_insn (operands[0], out);
4054 ;; Signed conversion to SImode.
4056 (define_expand "fix_truncxfsi2"
4057 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4058 (fix:SI (match_operand:XF 1 "register_operand" "")))
4059 (clobber (reg:CC FLAGS_REG))])]
4064 emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4069 (define_expand "fix_trunc<mode>si2"
4070 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4071 (fix:SI (match_operand:SSEMODEF 1 "register_operand" "")))
4072 (clobber (reg:CC FLAGS_REG))])]
4073 "TARGET_80387 || SSE_FLOAT_MODE_P (<MODE>mode)"
4076 && !(SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))
4078 emit_insn (gen_fix_truncsi_fisttp_i387_1 (operands[0], operands[1]));
4081 if (SSE_FLOAT_MODE_P (<MODE>mode))
4083 rtx out = REG_P (operands[0]) ? operands[0] : gen_reg_rtx (SImode);
4084 emit_insn (gen_fix_trunc<mode>si_sse (out, operands[1]));
4085 if (out != operands[0])
4086 emit_move_insn (operands[0], out);
4091 ;; Signed conversion to HImode.
4093 (define_expand "fix_trunc<mode>hi2"
4094 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
4095 (fix:HI (match_operand:X87MODEF 1 "register_operand" "")))
4096 (clobber (reg:CC FLAGS_REG))])]
4098 && !(SSE_FLOAT_MODE_P (<MODE>mode) && (!TARGET_FISTTP || TARGET_SSE_MATH))"
4102 emit_insn (gen_fix_trunchi_fisttp_i387_1 (operands[0], operands[1]));
4107 ;; When SSE is available, it is always faster to use it!
4108 (define_insn "fix_truncsfdi_sse"
4109 [(set (match_operand:DI 0 "register_operand" "=r,r")
4110 (fix:DI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))]
4111 "TARGET_64BIT && TARGET_SSE && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4112 "cvttss2si{q}\t{%1, %0|%0, %1}"
4113 [(set_attr "type" "sseicvt")
4114 (set_attr "mode" "SF")
4115 (set_attr "athlon_decode" "double,vector")])
4117 (define_insn "fix_truncdfdi_sse"
4118 [(set (match_operand:DI 0 "register_operand" "=r,r")
4119 (fix:DI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))]
4120 "TARGET_64BIT && TARGET_SSE2 && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4121 "cvttsd2si{q}\t{%1, %0|%0, %1}"
4122 [(set_attr "type" "sseicvt")
4123 (set_attr "mode" "DF")
4124 (set_attr "athlon_decode" "double,vector")])
4126 (define_insn "fix_truncsfsi_sse"
4127 [(set (match_operand:SI 0 "register_operand" "=r,r")
4128 (fix:SI (match_operand:SF 1 "nonimmediate_operand" "x,xm")))]
4129 "TARGET_SSE && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4130 "cvttss2si\t{%1, %0|%0, %1}"
4131 [(set_attr "type" "sseicvt")
4132 (set_attr "mode" "DF")
4133 (set_attr "athlon_decode" "double,vector")])
4135 (define_insn "fix_truncdfsi_sse"
4136 [(set (match_operand:SI 0 "register_operand" "=r,r")
4137 (fix:SI (match_operand:DF 1 "nonimmediate_operand" "Y,Ym")))]
4138 "TARGET_SSE2 && (!TARGET_FISTTP || TARGET_SSE_MATH)"
4139 "cvttsd2si\t{%1, %0|%0, %1}"
4140 [(set_attr "type" "sseicvt")
4141 (set_attr "mode" "DF")
4142 (set_attr "athlon_decode" "double,vector")])
4144 ;; Avoid vector decoded forms of the instruction.
4146 [(match_scratch:DF 2 "Y")
4147 (set (match_operand:SSEMODEI24 0 "register_operand" "")
4148 (fix:SSEMODEI24 (match_operand:DF 1 "memory_operand" "")))]
4149 "TARGET_K8 && !optimize_size"
4150 [(set (match_dup 2) (match_dup 1))
4151 (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4155 [(match_scratch:SF 2 "x")
4156 (set (match_operand:SSEMODEI24 0 "register_operand" "")
4157 (fix:SSEMODEI24 (match_operand:SF 1 "memory_operand" "")))]
4158 "TARGET_K8 && !optimize_size"
4159 [(set (match_dup 2) (match_dup 1))
4160 (set (match_dup 0) (fix:SSEMODEI24 (match_dup 2)))]
4163 (define_insn_and_split "fix_trunc<mode>_fisttp_i387_1"
4164 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4165 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))]
4167 && FLOAT_MODE_P (GET_MODE (operands[1]))
4168 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4169 && (TARGET_64BIT || <MODE>mode != DImode))
4171 && !(reload_completed || reload_in_progress)"
4176 if (memory_operand (operands[0], VOIDmode))
4177 emit_insn (gen_fix_trunc<mode>_i387_fisttp (operands[0], operands[1]));
4180 operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4181 emit_insn (gen_fix_trunc<mode>_i387_fisttp_with_temp (operands[0],
4187 [(set_attr "type" "fisttp")
4188 (set_attr "mode" "<MODE>")])
4190 (define_insn "fix_trunc<mode>_i387_fisttp"
4191 [(set (match_operand:X87MODEI 0 "memory_operand" "=m")
4192 (fix:X87MODEI (match_operand 1 "register_operand" "f")))
4193 (clobber (match_scratch:XF 2 "=&1f"))]
4195 && FLOAT_MODE_P (GET_MODE (operands[1]))
4196 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4197 && (TARGET_64BIT || <MODE>mode != DImode))
4198 && TARGET_SSE_MATH)"
4199 "* return output_fix_trunc (insn, operands, 1);"
4200 [(set_attr "type" "fisttp")
4201 (set_attr "mode" "<MODE>")])
4203 (define_insn "fix_trunc<mode>_i387_fisttp_with_temp"
4204 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4205 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
4206 (clobber (match_operand:X87MODEI 2 "memory_operand" "=m,m"))
4207 (clobber (match_scratch:XF 3 "=&1f,&1f"))]
4209 && FLOAT_MODE_P (GET_MODE (operands[1]))
4210 && !((SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4211 && (TARGET_64BIT || <MODE>mode != DImode))
4212 && TARGET_SSE_MATH)"
4214 [(set_attr "type" "fisttp")
4215 (set_attr "mode" "<MODE>")])
4218 [(set (match_operand:X87MODEI 0 "register_operand" "")
4219 (fix:X87MODEI (match_operand 1 "register_operand" "")))
4220 (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4221 (clobber (match_scratch 3 ""))]
4223 [(parallel [(set (match_dup 2) (fix:X87MODEI (match_dup 1)))
4224 (clobber (match_dup 3))])
4225 (set (match_dup 0) (match_dup 2))]
4229 [(set (match_operand:X87MODEI 0 "memory_operand" "")
4230 (fix:X87MODEI (match_operand 1 "register_operand" "")))
4231 (clobber (match_operand:X87MODEI 2 "memory_operand" ""))
4232 (clobber (match_scratch 3 ""))]
4234 [(parallel [(set (match_dup 0) (fix:X87MODEI (match_dup 1)))
4235 (clobber (match_dup 3))])]
4238 ;; See the comments in i386.h near OPTIMIZE_MODE_SWITCHING for the description
4239 ;; of the machinery. Please note the clobber of FLAGS_REG. In i387 control
4240 ;; word calculation (inserted by LCM in mode switching pass) a FLAGS_REG
4241 ;; clobbering insns can be used. Look at emit_i387_cw_initialization ()
4242 ;; function in i386.c.
4243 (define_insn_and_split "*fix_trunc<mode>_i387_1"
4244 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
4245 (fix:X87MODEI (match_operand 1 "register_operand" "f,f")))
4246 (clobber (reg:CC FLAGS_REG))]
4247 "TARGET_80387 && !TARGET_FISTTP
4248 && FLOAT_MODE_P (GET_MODE (operands[1]))
4249 && !(SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
4250 && (TARGET_64BIT || <MODE>mode != DImode))
4251 && !(reload_completed || reload_in_progress)"
4256 ix86_optimize_mode_switching[I387_TRUNC] = 1;
4258 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
4259 operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
4260 if (memory_operand (operands[0], VOIDmode))
4261 emit_insn (gen_fix_trunc<mode>_i387 (operands[0], operands[1],
4262 operands[2], operands[3]));
4265 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
4266 emit_insn (gen_fix_trunc<mode>_i387_with_temp (operands[0], operands[1],
4267 operands[2], operands[3],
4272 [(set_attr "type" "fistp")
4273 (set_attr "i387_cw" "trunc")
4274 (set_attr "mode" "<MODE>")])
4276 (define_insn "fix_truncdi_i387"
4277 [(set (match_operand:DI 0 "memory_operand" "=m")
4278 (fix:DI (match_operand 1 "register_operand" "f")))
4279 (use (match_operand:HI 2 "memory_operand" "m"))
4280 (use (match_operand:HI 3 "memory_operand" "m"))
4281 (clobber (match_scratch:XF 4 "=&1f"))]
4282 "TARGET_80387 && !TARGET_FISTTP
4283 && FLOAT_MODE_P (GET_MODE (operands[1]))
4284 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4285 "* return output_fix_trunc (insn, operands, 0);"
4286 [(set_attr "type" "fistp")
4287 (set_attr "i387_cw" "trunc")
4288 (set_attr "mode" "DI")])
4290 (define_insn "fix_truncdi_i387_with_temp"
4291 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
4292 (fix:DI (match_operand 1 "register_operand" "f,f")))
4293 (use (match_operand:HI 2 "memory_operand" "m,m"))
4294 (use (match_operand:HI 3 "memory_operand" "m,m"))
4295 (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
4296 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
4297 "TARGET_80387 && !TARGET_FISTTP
4298 && FLOAT_MODE_P (GET_MODE (operands[1]))
4299 && !(TARGET_64BIT && SSE_FLOAT_MODE_P (GET_MODE (operands[1])))"
4301 [(set_attr "type" "fistp")
4302 (set_attr "i387_cw" "trunc")
4303 (set_attr "mode" "DI")])
4306 [(set (match_operand:DI 0 "register_operand" "")
4307 (fix:DI (match_operand 1 "register_operand" "")))
4308 (use (match_operand:HI 2 "memory_operand" ""))
4309 (use (match_operand:HI 3 "memory_operand" ""))
4310 (clobber (match_operand:DI 4 "memory_operand" ""))
4311 (clobber (match_scratch 5 ""))]
4313 [(parallel [(set (match_dup 4) (fix:DI (match_dup 1)))
4316 (clobber (match_dup 5))])
4317 (set (match_dup 0) (match_dup 4))]
4321 [(set (match_operand:DI 0 "memory_operand" "")
4322 (fix:DI (match_operand 1 "register_operand" "")))
4323 (use (match_operand:HI 2 "memory_operand" ""))
4324 (use (match_operand:HI 3 "memory_operand" ""))
4325 (clobber (match_operand:DI 4 "memory_operand" ""))
4326 (clobber (match_scratch 5 ""))]
4328 [(parallel [(set (match_dup 0) (fix:DI (match_dup 1)))
4331 (clobber (match_dup 5))])]
4334 (define_insn "fix_trunc<mode>_i387"
4335 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
4336 (fix:X87MODEI12 (match_operand 1 "register_operand" "f")))
4337 (use (match_operand:HI 2 "memory_operand" "m"))
4338 (use (match_operand:HI 3 "memory_operand" "m"))]
4339 "TARGET_80387 && !TARGET_FISTTP
4340 && FLOAT_MODE_P (GET_MODE (operands[1]))
4341 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4342 "* return output_fix_trunc (insn, operands, 0);"
4343 [(set_attr "type" "fistp")
4344 (set_attr "i387_cw" "trunc")
4345 (set_attr "mode" "<MODE>")])
4347 (define_insn "fix_trunc<mode>_i387_with_temp"
4348 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
4349 (fix:X87MODEI12 (match_operand 1 "register_operand" "f,f")))
4350 (use (match_operand:HI 2 "memory_operand" "m,m"))
4351 (use (match_operand:HI 3 "memory_operand" "m,m"))
4352 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
4353 "TARGET_80387 && !TARGET_FISTTP
4354 && FLOAT_MODE_P (GET_MODE (operands[1]))
4355 && !SSE_FLOAT_MODE_P (GET_MODE (operands[1]))"
4357 [(set_attr "type" "fistp")
4358 (set_attr "i387_cw" "trunc")
4359 (set_attr "mode" "<MODE>")])
4362 [(set (match_operand:X87MODEI12 0 "register_operand" "")
4363 (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4364 (use (match_operand:HI 2 "memory_operand" ""))
4365 (use (match_operand:HI 3 "memory_operand" ""))
4366 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4368 [(parallel [(set (match_dup 4) (fix:X87MODEI12 (match_dup 1)))
4370 (use (match_dup 3))])
4371 (set (match_dup 0) (match_dup 4))]
4375 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
4376 (fix:X87MODEI12 (match_operand 1 "register_operand" "")))
4377 (use (match_operand:HI 2 "memory_operand" ""))
4378 (use (match_operand:HI 3 "memory_operand" ""))
4379 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
4381 [(parallel [(set (match_dup 0) (fix:X87MODEI12 (match_dup 1)))
4383 (use (match_dup 3))])]
4386 (define_insn "x86_fnstcw_1"
4387 [(set (match_operand:HI 0 "memory_operand" "=m")
4388 (unspec:HI [(reg:HI FPSR_REG)] UNSPEC_FSTCW))]
4391 [(set_attr "length" "2")
4392 (set_attr "mode" "HI")
4393 (set_attr "unit" "i387")])
4395 (define_insn "x86_fldcw_1"
4396 [(set (reg:HI FPSR_REG)
4397 (unspec:HI [(match_operand:HI 0 "memory_operand" "m")] UNSPEC_FLDCW))]
4400 [(set_attr "length" "2")
4401 (set_attr "mode" "HI")
4402 (set_attr "unit" "i387")
4403 (set_attr "athlon_decode" "vector")])
4405 ;; Conversion between fixed point and floating point.
4407 ;; Even though we only accept memory inputs, the backend _really_
4408 ;; wants to be able to do this between registers.
4410 (define_expand "floathisf2"
4411 [(set (match_operand:SF 0 "register_operand" "")
4412 (float:SF (match_operand:HI 1 "nonimmediate_operand" "")))]
4413 "TARGET_80387 || TARGET_SSE_MATH"
4415 if (TARGET_SSE_MATH)
4417 emit_insn (gen_floatsisf2 (operands[0],
4418 convert_to_mode (SImode, operands[1], 0)));
4423 (define_insn "*floathisf2_i387"
4424 [(set (match_operand:SF 0 "register_operand" "=f,f")
4425 (float:SF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4426 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
4430 [(set_attr "type" "fmov,multi")
4431 (set_attr "mode" "SF")
4432 (set_attr "unit" "*,i387")
4433 (set_attr "fp_int_src" "true")])
4435 (define_expand "floatsisf2"
4436 [(set (match_operand:SF 0 "register_operand" "")
4437 (float:SF (match_operand:SI 1 "nonimmediate_operand" "")))]
4438 "TARGET_80387 || TARGET_SSE_MATH"
4441 (define_insn "*floatsisf2_mixed"
4442 [(set (match_operand:SF 0 "register_operand" "=f#x,?f#x,x#f,x#f")
4443 (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))]
4444 "TARGET_MIX_SSE_I387"
4448 cvtsi2ss\t{%1, %0|%0, %1}
4449 cvtsi2ss\t{%1, %0|%0, %1}"
4450 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4451 (set_attr "mode" "SF")
4452 (set_attr "unit" "*,i387,*,*")
4453 (set_attr "athlon_decode" "*,*,vector,double")
4454 (set_attr "fp_int_src" "true")])
4456 (define_insn "*floatsisf2_sse"
4457 [(set (match_operand:SF 0 "register_operand" "=x,x")
4458 (float:SF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))]
4460 "cvtsi2ss\t{%1, %0|%0, %1}"
4461 [(set_attr "type" "sseicvt")
4462 (set_attr "mode" "SF")
4463 (set_attr "athlon_decode" "vector,double")
4464 (set_attr "fp_int_src" "true")])
4466 (define_insn "*floatsisf2_i387"
4467 [(set (match_operand:SF 0 "register_operand" "=f,f")
4468 (float:SF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4473 [(set_attr "type" "fmov,multi")
4474 (set_attr "mode" "SF")
4475 (set_attr "unit" "*,i387")
4476 (set_attr "fp_int_src" "true")])
4478 (define_expand "floatdisf2"
4479 [(set (match_operand:SF 0 "register_operand" "")
4480 (float:SF (match_operand:DI 1 "nonimmediate_operand" "")))]
4481 "TARGET_80387 || (TARGET_64BIT && TARGET_SSE_MATH)"
4484 (define_insn "*floatdisf2_mixed"
4485 [(set (match_operand:SF 0 "register_operand" "=f#x,?f#x,x#f,x#f")
4486 (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))]
4487 "TARGET_64BIT && TARGET_MIX_SSE_I387"
4491 cvtsi2ss{q}\t{%1, %0|%0, %1}
4492 cvtsi2ss{q}\t{%1, %0|%0, %1}"
4493 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4494 (set_attr "mode" "SF")
4495 (set_attr "unit" "*,i387,*,*")
4496 (set_attr "athlon_decode" "*,*,vector,double")
4497 (set_attr "fp_int_src" "true")])
4499 (define_insn "*floatdisf2_sse"
4500 [(set (match_operand:SF 0 "register_operand" "=x,x")
4501 (float:SF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))]
4502 "TARGET_64BIT && TARGET_SSE_MATH"
4503 "cvtsi2ss{q}\t{%1, %0|%0, %1}"
4504 [(set_attr "type" "sseicvt")
4505 (set_attr "mode" "SF")
4506 (set_attr "athlon_decode" "vector,double")
4507 (set_attr "fp_int_src" "true")])
4509 (define_insn "*floatdisf2_i387"
4510 [(set (match_operand:SF 0 "register_operand" "=f,f")
4511 (float:SF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4516 [(set_attr "type" "fmov,multi")
4517 (set_attr "mode" "SF")
4518 (set_attr "unit" "*,i387")
4519 (set_attr "fp_int_src" "true")])
4521 (define_expand "floathidf2"
4522 [(set (match_operand:DF 0 "register_operand" "")
4523 (float:DF (match_operand:HI 1 "nonimmediate_operand" "")))]
4524 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4526 if (TARGET_SSE2 && TARGET_SSE_MATH)
4528 emit_insn (gen_floatsidf2 (operands[0],
4529 convert_to_mode (SImode, operands[1], 0)));
4534 (define_insn "*floathidf2_i387"
4535 [(set (match_operand:DF 0 "register_operand" "=f,f")
4536 (float:DF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4537 "TARGET_80387 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)"
4541 [(set_attr "type" "fmov,multi")
4542 (set_attr "mode" "DF")
4543 (set_attr "unit" "*,i387")
4544 (set_attr "fp_int_src" "true")])
4546 (define_expand "floatsidf2"
4547 [(set (match_operand:DF 0 "register_operand" "")
4548 (float:DF (match_operand:SI 1 "nonimmediate_operand" "")))]
4549 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
4552 (define_insn "*floatsidf2_mixed"
4553 [(set (match_operand:DF 0 "register_operand" "=f#Y,?f#Y,Y#f,Y#f")
4554 (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,r,r,mr")))]
4555 "TARGET_SSE2 && TARGET_MIX_SSE_I387"
4559 cvtsi2sd\t{%1, %0|%0, %1}
4560 cvtsi2sd\t{%1, %0|%0, %1}"
4561 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4562 (set_attr "mode" "DF")
4563 (set_attr "unit" "*,i387,*,*")
4564 (set_attr "athlon_decode" "*,*,double,direct")
4565 (set_attr "fp_int_src" "true")])
4567 (define_insn "*floatsidf2_sse"
4568 [(set (match_operand:DF 0 "register_operand" "=Y,Y")
4569 (float:DF (match_operand:SI 1 "nonimmediate_operand" "r,mr")))]
4570 "TARGET_SSE2 && TARGET_SSE_MATH"
4571 "cvtsi2sd\t{%1, %0|%0, %1}"
4572 [(set_attr "type" "sseicvt")
4573 (set_attr "mode" "DF")
4574 (set_attr "athlon_decode" "double,direct")
4575 (set_attr "fp_int_src" "true")])
4577 (define_insn "*floatsidf2_i387"
4578 [(set (match_operand:DF 0 "register_operand" "=f,f")
4579 (float:DF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4584 [(set_attr "type" "fmov,multi")
4585 (set_attr "mode" "DF")
4586 (set_attr "unit" "*,i387")
4587 (set_attr "fp_int_src" "true")])
4589 (define_expand "floatdidf2"
4590 [(set (match_operand:DF 0 "register_operand" "")
4591 (float:DF (match_operand:DI 1 "nonimmediate_operand" "")))]
4592 "TARGET_80387 || (TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH)"
4595 (define_insn "*floatdidf2_mixed"
4596 [(set (match_operand:DF 0 "register_operand" "=f#Y,?f#Y,Y#f,Y#f")
4597 (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,r,r,mr")))]
4598 "TARGET_64BIT && TARGET_SSE2 && TARGET_MIX_SSE_I387"
4602 cvtsi2sd{q}\t{%1, %0|%0, %1}
4603 cvtsi2sd{q}\t{%1, %0|%0, %1}"
4604 [(set_attr "type" "fmov,multi,sseicvt,sseicvt")
4605 (set_attr "mode" "DF")
4606 (set_attr "unit" "*,i387,*,*")
4607 (set_attr "athlon_decode" "*,*,double,direct")
4608 (set_attr "fp_int_src" "true")])
4610 (define_insn "*floatdidf2_sse"
4611 [(set (match_operand:DF 0 "register_operand" "=Y,Y")
4612 (float:DF (match_operand:DI 1 "nonimmediate_operand" "r,mr")))]
4613 "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4614 "cvtsi2sd{q}\t{%1, %0|%0, %1}"
4615 [(set_attr "type" "sseicvt")
4616 (set_attr "mode" "DF")
4617 (set_attr "athlon_decode" "double,direct")
4618 (set_attr "fp_int_src" "true")])
4620 (define_insn "*floatdidf2_i387"
4621 [(set (match_operand:DF 0 "register_operand" "=f,f")
4622 (float:DF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4627 [(set_attr "type" "fmov,multi")
4628 (set_attr "mode" "DF")
4629 (set_attr "unit" "*,i387")
4630 (set_attr "fp_int_src" "true")])
4632 (define_insn "floathixf2"
4633 [(set (match_operand:XF 0 "register_operand" "=f,f")
4634 (float:XF (match_operand:HI 1 "nonimmediate_operand" "m,?r")))]
4639 [(set_attr "type" "fmov,multi")
4640 (set_attr "mode" "XF")
4641 (set_attr "unit" "*,i387")
4642 (set_attr "fp_int_src" "true")])
4644 (define_insn "floatsixf2"
4645 [(set (match_operand:XF 0 "register_operand" "=f,f")
4646 (float:XF (match_operand:SI 1 "nonimmediate_operand" "m,?r")))]
4651 [(set_attr "type" "fmov,multi")
4652 (set_attr "mode" "XF")
4653 (set_attr "unit" "*,i387")
4654 (set_attr "fp_int_src" "true")])
4656 (define_insn "floatdixf2"
4657 [(set (match_operand:XF 0 "register_operand" "=f,f")
4658 (float:XF (match_operand:DI 1 "nonimmediate_operand" "m,?r")))]
4663 [(set_attr "type" "fmov,multi")
4664 (set_attr "mode" "XF")
4665 (set_attr "unit" "*,i387")
4666 (set_attr "fp_int_src" "true")])
4668 ;; %%% Kill these when reload knows how to do it.
4670 [(set (match_operand 0 "fp_register_operand" "")
4671 (float (match_operand 1 "register_operand" "")))]
4674 && FLOAT_MODE_P (GET_MODE (operands[0]))"
4677 operands[2] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
4678 operands[2] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[2]);
4679 emit_insn (gen_rtx_SET (VOIDmode, operands[0], operands[2]));
4680 ix86_free_from_memory (GET_MODE (operands[1]));
4684 (define_expand "floatunssisf2"
4685 [(use (match_operand:SF 0 "register_operand" ""))
4686 (use (match_operand:SI 1 "register_operand" ""))]
4687 "!TARGET_64BIT && TARGET_SSE_MATH"
4688 "x86_emit_floatuns (operands); DONE;")
4690 (define_expand "floatunsdisf2"
4691 [(use (match_operand:SF 0 "register_operand" ""))
4692 (use (match_operand:DI 1 "register_operand" ""))]
4693 "TARGET_64BIT && TARGET_SSE_MATH"
4694 "x86_emit_floatuns (operands); DONE;")
4696 (define_expand "floatunsdidf2"
4697 [(use (match_operand:DF 0 "register_operand" ""))
4698 (use (match_operand:DI 1 "register_operand" ""))]
4699 "TARGET_64BIT && TARGET_SSE2 && TARGET_SSE_MATH"
4700 "x86_emit_floatuns (operands); DONE;")
4702 ;; SSE extract/set expanders
4707 ;; %%% splits for addditi3
4709 (define_expand "addti3"
4710 [(set (match_operand:TI 0 "nonimmediate_operand" "")
4711 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
4712 (match_operand:TI 2 "x86_64_general_operand" "")))
4713 (clobber (reg:CC FLAGS_REG))]
4715 "ix86_expand_binary_operator (PLUS, TImode, operands); DONE;")
4717 (define_insn "*addti3_1"
4718 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o")
4719 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "%0,0")
4720 (match_operand:TI 2 "general_operand" "roiF,riF")))
4721 (clobber (reg:CC FLAGS_REG))]
4722 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, TImode, operands)"
4726 [(set (match_operand:TI 0 "nonimmediate_operand" "")
4727 (plus:TI (match_operand:TI 1 "nonimmediate_operand" "")
4728 (match_operand:TI 2 "general_operand" "")))
4729 (clobber (reg:CC FLAGS_REG))]
4730 "TARGET_64BIT && reload_completed"
4731 [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
4733 (set (match_dup 0) (plus:DI (match_dup 1) (match_dup 2)))])
4734 (parallel [(set (match_dup 3)
4735 (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
4738 (clobber (reg:CC FLAGS_REG))])]
4739 "split_ti (operands+0, 1, operands+0, operands+3);
4740 split_ti (operands+1, 1, operands+1, operands+4);
4741 split_ti (operands+2, 1, operands+2, operands+5);")
4743 ;; %%% splits for addsidi3
4744 ; [(set (match_operand:DI 0 "nonimmediate_operand" "")
4745 ; (plus:DI (match_operand:DI 1 "general_operand" "")
4746 ; (zero_extend:DI (match_operand:SI 2 "general_operand" ""))))]
4748 (define_expand "adddi3"
4749 [(set (match_operand:DI 0 "nonimmediate_operand" "")
4750 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4751 (match_operand:DI 2 "x86_64_general_operand" "")))
4752 (clobber (reg:CC FLAGS_REG))]
4754 "ix86_expand_binary_operator (PLUS, DImode, operands); DONE;")
4756 (define_insn "*adddi3_1"
4757 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
4758 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
4759 (match_operand:DI 2 "general_operand" "roiF,riF")))
4760 (clobber (reg:CC FLAGS_REG))]
4761 "!TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4765 [(set (match_operand:DI 0 "nonimmediate_operand" "")
4766 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "")
4767 (match_operand:DI 2 "general_operand" "")))
4768 (clobber (reg:CC FLAGS_REG))]
4769 "!TARGET_64BIT && reload_completed"
4770 [(parallel [(set (reg:CC FLAGS_REG) (unspec:CC [(match_dup 1) (match_dup 2)]
4772 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 2)))])
4773 (parallel [(set (match_dup 3)
4774 (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
4777 (clobber (reg:CC FLAGS_REG))])]
4778 "split_di (operands+0, 1, operands+0, operands+3);
4779 split_di (operands+1, 1, operands+1, operands+4);
4780 split_di (operands+2, 1, operands+2, operands+5);")
4782 (define_insn "adddi3_carry_rex64"
4783 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
4784 (plus:DI (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
4785 (match_operand:DI 1 "nonimmediate_operand" "%0,0"))
4786 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
4787 (clobber (reg:CC FLAGS_REG))]
4788 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4789 "adc{q}\t{%2, %0|%0, %2}"
4790 [(set_attr "type" "alu")
4791 (set_attr "pent_pair" "pu")
4792 (set_attr "mode" "DI")])
4794 (define_insn "*adddi3_cc_rex64"
4795 [(set (reg:CC FLAGS_REG)
4796 (unspec:CC [(match_operand:DI 1 "nonimmediate_operand" "%0,0")
4797 (match_operand:DI 2 "x86_64_general_operand" "re,rm")]
4799 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
4800 (plus:DI (match_dup 1) (match_dup 2)))]
4801 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
4802 "add{q}\t{%2, %0|%0, %2}"
4803 [(set_attr "type" "alu")
4804 (set_attr "mode" "DI")])
4806 (define_insn "addqi3_carry"
4807 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
4808 (plus:QI (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
4809 (match_operand:QI 1 "nonimmediate_operand" "%0,0"))
4810 (match_operand:QI 2 "general_operand" "qi,qm")))
4811 (clobber (reg:CC FLAGS_REG))]
4812 "ix86_binary_operator_ok (PLUS, QImode, operands)"
4813 "adc{b}\t{%2, %0|%0, %2}"
4814 [(set_attr "type" "alu")
4815 (set_attr "pent_pair" "pu")
4816 (set_attr "mode" "QI")])
4818 (define_insn "addhi3_carry"
4819 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
4820 (plus:HI (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
4821 (match_operand:HI 1 "nonimmediate_operand" "%0,0"))
4822 (match_operand:HI 2 "general_operand" "ri,rm")))
4823 (clobber (reg:CC FLAGS_REG))]
4824 "ix86_binary_operator_ok (PLUS, HImode, operands)"
4825 "adc{w}\t{%2, %0|%0, %2}"
4826 [(set_attr "type" "alu")
4827 (set_attr "pent_pair" "pu")
4828 (set_attr "mode" "HI")])
4830 (define_insn "addsi3_carry"
4831 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
4832 (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
4833 (match_operand:SI 1 "nonimmediate_operand" "%0,0"))
4834 (match_operand:SI 2 "general_operand" "ri,rm")))
4835 (clobber (reg:CC FLAGS_REG))]
4836 "ix86_binary_operator_ok (PLUS, SImode, operands)"
4837 "adc{l}\t{%2, %0|%0, %2}"
4838 [(set_attr "type" "alu")
4839 (set_attr "pent_pair" "pu")
4840 (set_attr "mode" "SI")])
4842 (define_insn "*addsi3_carry_zext"
4843 [(set (match_operand:DI 0 "register_operand" "=r")
4845 (plus:SI (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
4846 (match_operand:SI 1 "nonimmediate_operand" "%0"))
4847 (match_operand:SI 2 "general_operand" "rim"))))
4848 (clobber (reg:CC FLAGS_REG))]
4849 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
4850 "adc{l}\t{%2, %k0|%k0, %2}"
4851 [(set_attr "type" "alu")
4852 (set_attr "pent_pair" "pu")
4853 (set_attr "mode" "SI")])
4855 (define_insn "*addsi3_cc"
4856 [(set (reg:CC FLAGS_REG)
4857 (unspec:CC [(match_operand:SI 1 "nonimmediate_operand" "%0,0")
4858 (match_operand:SI 2 "general_operand" "ri,rm")]
4860 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
4861 (plus:SI (match_dup 1) (match_dup 2)))]
4862 "ix86_binary_operator_ok (PLUS, SImode, operands)"
4863 "add{l}\t{%2, %0|%0, %2}"
4864 [(set_attr "type" "alu")
4865 (set_attr "mode" "SI")])
4867 (define_insn "addqi3_cc"
4868 [(set (reg:CC FLAGS_REG)
4869 (unspec:CC [(match_operand:QI 1 "nonimmediate_operand" "%0,0")
4870 (match_operand:QI 2 "general_operand" "qi,qm")]
4872 (set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
4873 (plus:QI (match_dup 1) (match_dup 2)))]
4874 "ix86_binary_operator_ok (PLUS, QImode, operands)"
4875 "add{b}\t{%2, %0|%0, %2}"
4876 [(set_attr "type" "alu")
4877 (set_attr "mode" "QI")])
4879 (define_expand "addsi3"
4880 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
4881 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "")
4882 (match_operand:SI 2 "general_operand" "")))
4883 (clobber (reg:CC FLAGS_REG))])]
4885 "ix86_expand_binary_operator (PLUS, SImode, operands); DONE;")
4887 (define_insn "*lea_1"
4888 [(set (match_operand:SI 0 "register_operand" "=r")
4889 (match_operand:SI 1 "no_seg_address_operand" "p"))]
4891 "lea{l}\t{%a1, %0|%0, %a1}"
4892 [(set_attr "type" "lea")
4893 (set_attr "mode" "SI")])
4895 (define_insn "*lea_1_rex64"
4896 [(set (match_operand:SI 0 "register_operand" "=r")
4897 (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0))]
4899 "lea{l}\t{%a1, %0|%0, %a1}"
4900 [(set_attr "type" "lea")
4901 (set_attr "mode" "SI")])
4903 (define_insn "*lea_1_zext"
4904 [(set (match_operand:DI 0 "register_operand" "=r")
4906 (subreg:SI (match_operand:DI 1 "no_seg_address_operand" "p") 0)))]
4908 "lea{l}\t{%a1, %k0|%k0, %a1}"
4909 [(set_attr "type" "lea")
4910 (set_attr "mode" "SI")])
4912 (define_insn "*lea_2_rex64"
4913 [(set (match_operand:DI 0 "register_operand" "=r")
4914 (match_operand:DI 1 "no_seg_address_operand" "p"))]
4916 "lea{q}\t{%a1, %0|%0, %a1}"
4917 [(set_attr "type" "lea")
4918 (set_attr "mode" "DI")])
4920 ;; The lea patterns for non-Pmodes needs to be matched by several
4921 ;; insns converted to real lea by splitters.
4923 (define_insn_and_split "*lea_general_1"
4924 [(set (match_operand 0 "register_operand" "=r")
4925 (plus (plus (match_operand 1 "index_register_operand" "l")
4926 (match_operand 2 "register_operand" "r"))
4927 (match_operand 3 "immediate_operand" "i")))]
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[2])
4933 && (GET_MODE (operands[0]) == GET_MODE (operands[3])
4934 || GET_MODE (operands[3]) == VOIDmode)"
4936 "&& reload_completed"
4940 operands[0] = gen_lowpart (SImode, operands[0]);
4941 operands[1] = gen_lowpart (Pmode, operands[1]);
4942 operands[2] = gen_lowpart (Pmode, operands[2]);
4943 operands[3] = gen_lowpart (Pmode, operands[3]);
4944 pat = gen_rtx_PLUS (Pmode, gen_rtx_PLUS (Pmode, operands[1], operands[2]),
4946 if (Pmode != SImode)
4947 pat = gen_rtx_SUBREG (SImode, pat, 0);
4948 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
4951 [(set_attr "type" "lea")
4952 (set_attr "mode" "SI")])
4954 (define_insn_and_split "*lea_general_1_zext"
4955 [(set (match_operand:DI 0 "register_operand" "=r")
4957 (plus:SI (plus:SI (match_operand:SI 1 "index_register_operand" "l")
4958 (match_operand:SI 2 "register_operand" "r"))
4959 (match_operand:SI 3 "immediate_operand" "i"))))]
4962 "&& reload_completed"
4964 (zero_extend:DI (subreg:SI (plus:DI (plus:DI (match_dup 1)
4966 (match_dup 3)) 0)))]
4968 operands[1] = gen_lowpart (Pmode, operands[1]);
4969 operands[2] = gen_lowpart (Pmode, operands[2]);
4970 operands[3] = gen_lowpart (Pmode, operands[3]);
4972 [(set_attr "type" "lea")
4973 (set_attr "mode" "SI")])
4975 (define_insn_and_split "*lea_general_2"
4976 [(set (match_operand 0 "register_operand" "=r")
4977 (plus (mult (match_operand 1 "index_register_operand" "l")
4978 (match_operand 2 "const248_operand" "i"))
4979 (match_operand 3 "nonmemory_operand" "ri")))]
4980 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
4981 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
4982 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
4983 && GET_MODE (operands[0]) == GET_MODE (operands[1])
4984 && (GET_MODE (operands[0]) == GET_MODE (operands[3])
4985 || GET_MODE (operands[3]) == VOIDmode)"
4987 "&& reload_completed"
4991 operands[0] = gen_lowpart (SImode, operands[0]);
4992 operands[1] = gen_lowpart (Pmode, operands[1]);
4993 operands[3] = gen_lowpart (Pmode, operands[3]);
4994 pat = gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1], operands[2]),
4996 if (Pmode != SImode)
4997 pat = gen_rtx_SUBREG (SImode, pat, 0);
4998 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5001 [(set_attr "type" "lea")
5002 (set_attr "mode" "SI")])
5004 (define_insn_and_split "*lea_general_2_zext"
5005 [(set (match_operand:DI 0 "register_operand" "=r")
5007 (plus:SI (mult:SI (match_operand:SI 1 "index_register_operand" "l")
5008 (match_operand:SI 2 "const248_operand" "n"))
5009 (match_operand:SI 3 "nonmemory_operand" "ri"))))]
5012 "&& reload_completed"
5014 (zero_extend:DI (subreg:SI (plus:DI (mult:DI (match_dup 1)
5016 (match_dup 3)) 0)))]
5018 operands[1] = gen_lowpart (Pmode, operands[1]);
5019 operands[3] = gen_lowpart (Pmode, operands[3]);
5021 [(set_attr "type" "lea")
5022 (set_attr "mode" "SI")])
5024 (define_insn_and_split "*lea_general_3"
5025 [(set (match_operand 0 "register_operand" "=r")
5026 (plus (plus (mult (match_operand 1 "index_register_operand" "l")
5027 (match_operand 2 "const248_operand" "i"))
5028 (match_operand 3 "register_operand" "r"))
5029 (match_operand 4 "immediate_operand" "i")))]
5030 "(GET_MODE (operands[0]) == QImode || GET_MODE (operands[0]) == HImode
5031 || (TARGET_64BIT && GET_MODE (operands[0]) == SImode))
5032 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
5033 && GET_MODE (operands[0]) == GET_MODE (operands[1])
5034 && GET_MODE (operands[0]) == GET_MODE (operands[3])"
5036 "&& reload_completed"
5040 operands[0] = gen_lowpart (SImode, operands[0]);
5041 operands[1] = gen_lowpart (Pmode, operands[1]);
5042 operands[3] = gen_lowpart (Pmode, operands[3]);
5043 operands[4] = gen_lowpart (Pmode, operands[4]);
5044 pat = gen_rtx_PLUS (Pmode,
5045 gen_rtx_PLUS (Pmode, gen_rtx_MULT (Pmode, operands[1],
5049 if (Pmode != SImode)
5050 pat = gen_rtx_SUBREG (SImode, pat, 0);
5051 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5054 [(set_attr "type" "lea")
5055 (set_attr "mode" "SI")])
5057 (define_insn_and_split "*lea_general_3_zext"
5058 [(set (match_operand:DI 0 "register_operand" "=r")
5060 (plus:SI (plus:SI (mult:SI
5061 (match_operand:SI 1 "index_register_operand" "l")
5062 (match_operand:SI 2 "const248_operand" "n"))
5063 (match_operand:SI 3 "register_operand" "r"))
5064 (match_operand:SI 4 "immediate_operand" "i"))))]
5067 "&& reload_completed"
5069 (zero_extend:DI (subreg:SI (plus:DI (plus:DI (mult:DI (match_dup 1)
5072 (match_dup 4)) 0)))]
5074 operands[1] = gen_lowpart (Pmode, operands[1]);
5075 operands[3] = gen_lowpart (Pmode, operands[3]);
5076 operands[4] = gen_lowpart (Pmode, operands[4]);
5078 [(set_attr "type" "lea")
5079 (set_attr "mode" "SI")])
5081 (define_insn "*adddi_1_rex64"
5082 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r")
5083 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,r")
5084 (match_operand:DI 2 "x86_64_general_operand" "rme,re,le")))
5085 (clobber (reg:CC FLAGS_REG))]
5086 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, DImode, operands)"
5088 switch (get_attr_type (insn))
5091 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5092 return "lea{q}\t{%a2, %0|%0, %a2}";
5095 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5096 if (operands[2] == const1_rtx)
5097 return "inc{q}\t%0";
5100 gcc_assert (operands[2] == constm1_rtx);
5101 return "dec{q}\t%0";
5105 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5107 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5108 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5109 if (GET_CODE (operands[2]) == CONST_INT
5110 /* Avoid overflows. */
5111 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5112 && (INTVAL (operands[2]) == 128
5113 || (INTVAL (operands[2]) < 0
5114 && INTVAL (operands[2]) != -128)))
5116 operands[2] = GEN_INT (-INTVAL (operands[2]));
5117 return "sub{q}\t{%2, %0|%0, %2}";
5119 return "add{q}\t{%2, %0|%0, %2}";
5123 (cond [(eq_attr "alternative" "2")
5124 (const_string "lea")
5125 ; Current assemblers are broken and do not allow @GOTOFF in
5126 ; ought but a memory context.
5127 (match_operand:DI 2 "pic_symbolic_operand" "")
5128 (const_string "lea")
5129 (match_operand:DI 2 "incdec_operand" "")
5130 (const_string "incdec")
5132 (const_string "alu")))
5133 (set_attr "mode" "DI")])
5135 ;; Convert lea to the lea pattern to avoid flags dependency.
5137 [(set (match_operand:DI 0 "register_operand" "")
5138 (plus:DI (match_operand:DI 1 "register_operand" "")
5139 (match_operand:DI 2 "x86_64_nonmemory_operand" "")))
5140 (clobber (reg:CC FLAGS_REG))]
5141 "TARGET_64BIT && reload_completed
5142 && true_regnum (operands[0]) != true_regnum (operands[1])"
5144 (plus:DI (match_dup 1)
5148 (define_insn "*adddi_2_rex64"
5149 [(set (reg FLAGS_REG)
5151 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
5152 (match_operand:DI 2 "x86_64_general_operand" "rme,re"))
5154 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
5155 (plus:DI (match_dup 1) (match_dup 2)))]
5156 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5157 && ix86_binary_operator_ok (PLUS, DImode, operands)
5158 /* Current assemblers are broken and do not allow @GOTOFF in
5159 ought but a memory context. */
5160 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5162 switch (get_attr_type (insn))
5165 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5166 if (operands[2] == const1_rtx)
5167 return "inc{q}\t%0";
5170 gcc_assert (operands[2] == constm1_rtx);
5171 return "dec{q}\t%0";
5175 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5176 /* ???? We ought to handle there the 32bit case too
5177 - do we need new constraint? */
5178 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5179 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5180 if (GET_CODE (operands[2]) == CONST_INT
5181 /* Avoid overflows. */
5182 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5183 && (INTVAL (operands[2]) == 128
5184 || (INTVAL (operands[2]) < 0
5185 && INTVAL (operands[2]) != -128)))
5187 operands[2] = GEN_INT (-INTVAL (operands[2]));
5188 return "sub{q}\t{%2, %0|%0, %2}";
5190 return "add{q}\t{%2, %0|%0, %2}";
5194 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5195 (const_string "incdec")
5196 (const_string "alu")))
5197 (set_attr "mode" "DI")])
5199 (define_insn "*adddi_3_rex64"
5200 [(set (reg FLAGS_REG)
5201 (compare (neg:DI (match_operand:DI 2 "x86_64_general_operand" "rme"))
5202 (match_operand:DI 1 "x86_64_general_operand" "%0")))
5203 (clobber (match_scratch:DI 0 "=r"))]
5205 && ix86_match_ccmode (insn, CCZmode)
5206 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5207 /* Current assemblers are broken and do not allow @GOTOFF in
5208 ought but a memory context. */
5209 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5211 switch (get_attr_type (insn))
5214 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5215 if (operands[2] == const1_rtx)
5216 return "inc{q}\t%0";
5219 gcc_assert (operands[2] == constm1_rtx);
5220 return "dec{q}\t%0";
5224 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5225 /* ???? We ought to handle there the 32bit case too
5226 - do we need new constraint? */
5227 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5228 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5229 if (GET_CODE (operands[2]) == CONST_INT
5230 /* Avoid overflows. */
5231 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5232 && (INTVAL (operands[2]) == 128
5233 || (INTVAL (operands[2]) < 0
5234 && INTVAL (operands[2]) != -128)))
5236 operands[2] = GEN_INT (-INTVAL (operands[2]));
5237 return "sub{q}\t{%2, %0|%0, %2}";
5239 return "add{q}\t{%2, %0|%0, %2}";
5243 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5244 (const_string "incdec")
5245 (const_string "alu")))
5246 (set_attr "mode" "DI")])
5248 ; For comparisons against 1, -1 and 128, we may generate better code
5249 ; by converting cmp to add, inc or dec as done by peephole2. This pattern
5250 ; is matched then. We can't accept general immediate, because for
5251 ; case of overflows, the result is messed up.
5252 ; This pattern also don't hold of 0x8000000000000000, since the value overflows
5254 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5255 ; only for comparisons not depending on it.
5256 (define_insn "*adddi_4_rex64"
5257 [(set (reg FLAGS_REG)
5258 (compare (match_operand:DI 1 "nonimmediate_operand" "0")
5259 (match_operand:DI 2 "x86_64_immediate_operand" "e")))
5260 (clobber (match_scratch:DI 0 "=rm"))]
5262 && ix86_match_ccmode (insn, CCGCmode)"
5264 switch (get_attr_type (insn))
5267 if (operands[2] == constm1_rtx)
5268 return "inc{q}\t%0";
5271 gcc_assert (operands[2] == const1_rtx);
5272 return "dec{q}\t%0";
5276 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5277 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5278 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5279 if ((INTVAL (operands[2]) == -128
5280 || (INTVAL (operands[2]) > 0
5281 && INTVAL (operands[2]) != 128))
5282 /* Avoid overflows. */
5283 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1))))
5284 return "sub{q}\t{%2, %0|%0, %2}";
5285 operands[2] = GEN_INT (-INTVAL (operands[2]));
5286 return "add{q}\t{%2, %0|%0, %2}";
5290 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5291 (const_string "incdec")
5292 (const_string "alu")))
5293 (set_attr "mode" "DI")])
5295 (define_insn "*adddi_5_rex64"
5296 [(set (reg FLAGS_REG)
5298 (plus:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
5299 (match_operand:DI 2 "x86_64_general_operand" "rme"))
5301 (clobber (match_scratch:DI 0 "=r"))]
5303 && ix86_match_ccmode (insn, CCGOCmode)
5304 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5305 /* Current assemblers are broken and do not allow @GOTOFF in
5306 ought but a memory context. */
5307 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5309 switch (get_attr_type (insn))
5312 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5313 if (operands[2] == const1_rtx)
5314 return "inc{q}\t%0";
5317 gcc_assert (operands[2] == constm1_rtx);
5318 return "dec{q}\t%0";
5322 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5323 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5324 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5325 if (GET_CODE (operands[2]) == CONST_INT
5326 /* Avoid overflows. */
5327 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
5328 && (INTVAL (operands[2]) == 128
5329 || (INTVAL (operands[2]) < 0
5330 && INTVAL (operands[2]) != -128)))
5332 operands[2] = GEN_INT (-INTVAL (operands[2]));
5333 return "sub{q}\t{%2, %0|%0, %2}";
5335 return "add{q}\t{%2, %0|%0, %2}";
5339 (if_then_else (match_operand:DI 2 "incdec_operand" "")
5340 (const_string "incdec")
5341 (const_string "alu")))
5342 (set_attr "mode" "DI")])
5345 (define_insn "*addsi_1"
5346 [(set (match_operand:SI 0 "nonimmediate_operand" "=r,rm,r")
5347 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,r")
5348 (match_operand:SI 2 "general_operand" "rmni,rni,lni")))
5349 (clobber (reg:CC FLAGS_REG))]
5350 "ix86_binary_operator_ok (PLUS, SImode, operands)"
5352 switch (get_attr_type (insn))
5355 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5356 return "lea{l}\t{%a2, %0|%0, %a2}";
5359 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5360 if (operands[2] == const1_rtx)
5361 return "inc{l}\t%0";
5364 gcc_assert (operands[2] == constm1_rtx);
5365 return "dec{l}\t%0";
5369 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5371 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5372 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5373 if (GET_CODE (operands[2]) == CONST_INT
5374 && (INTVAL (operands[2]) == 128
5375 || (INTVAL (operands[2]) < 0
5376 && INTVAL (operands[2]) != -128)))
5378 operands[2] = GEN_INT (-INTVAL (operands[2]));
5379 return "sub{l}\t{%2, %0|%0, %2}";
5381 return "add{l}\t{%2, %0|%0, %2}";
5385 (cond [(eq_attr "alternative" "2")
5386 (const_string "lea")
5387 ; Current assemblers are broken and do not allow @GOTOFF in
5388 ; ought but a memory context.
5389 (match_operand:SI 2 "pic_symbolic_operand" "")
5390 (const_string "lea")
5391 (match_operand:SI 2 "incdec_operand" "")
5392 (const_string "incdec")
5394 (const_string "alu")))
5395 (set_attr "mode" "SI")])
5397 ;; Convert lea to the lea pattern to avoid flags dependency.
5399 [(set (match_operand 0 "register_operand" "")
5400 (plus (match_operand 1 "register_operand" "")
5401 (match_operand 2 "nonmemory_operand" "")))
5402 (clobber (reg:CC FLAGS_REG))]
5404 && true_regnum (operands[0]) != true_regnum (operands[1])"
5408 /* In -fPIC mode the constructs like (const (unspec [symbol_ref]))
5409 may confuse gen_lowpart. */
5410 if (GET_MODE (operands[0]) != Pmode)
5412 operands[1] = gen_lowpart (Pmode, operands[1]);
5413 operands[2] = gen_lowpart (Pmode, operands[2]);
5415 operands[0] = gen_lowpart (SImode, operands[0]);
5416 pat = gen_rtx_PLUS (Pmode, operands[1], operands[2]);
5417 if (Pmode != SImode)
5418 pat = gen_rtx_SUBREG (SImode, pat, 0);
5419 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
5423 ;; It may seem that nonimmediate operand is proper one for operand 1.
5424 ;; The addsi_1 pattern allows nonimmediate operand at that place and
5425 ;; we take care in ix86_binary_operator_ok to not allow two memory
5426 ;; operands so proper swapping will be done in reload. This allow
5427 ;; patterns constructed from addsi_1 to match.
5428 (define_insn "addsi_1_zext"
5429 [(set (match_operand:DI 0 "register_operand" "=r,r")
5431 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,r")
5432 (match_operand:SI 2 "general_operand" "rmni,lni"))))
5433 (clobber (reg:CC FLAGS_REG))]
5434 "TARGET_64BIT && ix86_binary_operator_ok (PLUS, SImode, operands)"
5436 switch (get_attr_type (insn))
5439 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
5440 return "lea{l}\t{%a2, %k0|%k0, %a2}";
5443 if (operands[2] == const1_rtx)
5444 return "inc{l}\t%k0";
5447 gcc_assert (operands[2] == constm1_rtx);
5448 return "dec{l}\t%k0";
5452 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5453 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5454 if (GET_CODE (operands[2]) == CONST_INT
5455 && (INTVAL (operands[2]) == 128
5456 || (INTVAL (operands[2]) < 0
5457 && INTVAL (operands[2]) != -128)))
5459 operands[2] = GEN_INT (-INTVAL (operands[2]));
5460 return "sub{l}\t{%2, %k0|%k0, %2}";
5462 return "add{l}\t{%2, %k0|%k0, %2}";
5466 (cond [(eq_attr "alternative" "1")
5467 (const_string "lea")
5468 ; Current assemblers are broken and do not allow @GOTOFF in
5469 ; ought but a memory context.
5470 (match_operand:SI 2 "pic_symbolic_operand" "")
5471 (const_string "lea")
5472 (match_operand:SI 2 "incdec_operand" "")
5473 (const_string "incdec")
5475 (const_string "alu")))
5476 (set_attr "mode" "SI")])
5478 ;; Convert lea to the lea pattern to avoid flags dependency.
5480 [(set (match_operand:DI 0 "register_operand" "")
5482 (plus:SI (match_operand:SI 1 "register_operand" "")
5483 (match_operand:SI 2 "nonmemory_operand" ""))))
5484 (clobber (reg:CC FLAGS_REG))]
5485 "TARGET_64BIT && reload_completed
5486 && true_regnum (operands[0]) != true_regnum (operands[1])"
5488 (zero_extend:DI (subreg:SI (plus:DI (match_dup 1) (match_dup 2)) 0)))]
5490 operands[1] = gen_lowpart (Pmode, operands[1]);
5491 operands[2] = gen_lowpart (Pmode, operands[2]);
5494 (define_insn "*addsi_2"
5495 [(set (reg FLAGS_REG)
5497 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
5498 (match_operand:SI 2 "general_operand" "rmni,rni"))
5500 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
5501 (plus:SI (match_dup 1) (match_dup 2)))]
5502 "ix86_match_ccmode (insn, CCGOCmode)
5503 && ix86_binary_operator_ok (PLUS, SImode, operands)
5504 /* Current assemblers are broken and do not allow @GOTOFF in
5505 ought but a memory context. */
5506 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5508 switch (get_attr_type (insn))
5511 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5512 if (operands[2] == const1_rtx)
5513 return "inc{l}\t%0";
5516 gcc_assert (operands[2] == constm1_rtx);
5517 return "dec{l}\t%0";
5521 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5522 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5523 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5524 if (GET_CODE (operands[2]) == CONST_INT
5525 && (INTVAL (operands[2]) == 128
5526 || (INTVAL (operands[2]) < 0
5527 && INTVAL (operands[2]) != -128)))
5529 operands[2] = GEN_INT (-INTVAL (operands[2]));
5530 return "sub{l}\t{%2, %0|%0, %2}";
5532 return "add{l}\t{%2, %0|%0, %2}";
5536 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5537 (const_string "incdec")
5538 (const_string "alu")))
5539 (set_attr "mode" "SI")])
5541 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5542 (define_insn "*addsi_2_zext"
5543 [(set (reg FLAGS_REG)
5545 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5546 (match_operand:SI 2 "general_operand" "rmni"))
5548 (set (match_operand:DI 0 "register_operand" "=r")
5549 (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5550 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
5551 && ix86_binary_operator_ok (PLUS, SImode, operands)
5552 /* Current assemblers are broken and do not allow @GOTOFF in
5553 ought but a memory context. */
5554 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5556 switch (get_attr_type (insn))
5559 if (operands[2] == const1_rtx)
5560 return "inc{l}\t%k0";
5563 gcc_assert (operands[2] == constm1_rtx);
5564 return "dec{l}\t%k0";
5568 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5569 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5570 if (GET_CODE (operands[2]) == CONST_INT
5571 && (INTVAL (operands[2]) == 128
5572 || (INTVAL (operands[2]) < 0
5573 && INTVAL (operands[2]) != -128)))
5575 operands[2] = GEN_INT (-INTVAL (operands[2]));
5576 return "sub{l}\t{%2, %k0|%k0, %2}";
5578 return "add{l}\t{%2, %k0|%k0, %2}";
5582 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5583 (const_string "incdec")
5584 (const_string "alu")))
5585 (set_attr "mode" "SI")])
5587 (define_insn "*addsi_3"
5588 [(set (reg FLAGS_REG)
5589 (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5590 (match_operand:SI 1 "nonimmediate_operand" "%0")))
5591 (clobber (match_scratch:SI 0 "=r"))]
5592 "ix86_match_ccmode (insn, CCZmode)
5593 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5594 /* Current assemblers are broken and do not allow @GOTOFF in
5595 ought but a memory context. */
5596 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5598 switch (get_attr_type (insn))
5601 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5602 if (operands[2] == const1_rtx)
5603 return "inc{l}\t%0";
5606 gcc_assert (operands[2] == constm1_rtx);
5607 return "dec{l}\t%0";
5611 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5612 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5613 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5614 if (GET_CODE (operands[2]) == CONST_INT
5615 && (INTVAL (operands[2]) == 128
5616 || (INTVAL (operands[2]) < 0
5617 && INTVAL (operands[2]) != -128)))
5619 operands[2] = GEN_INT (-INTVAL (operands[2]));
5620 return "sub{l}\t{%2, %0|%0, %2}";
5622 return "add{l}\t{%2, %0|%0, %2}";
5626 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5627 (const_string "incdec")
5628 (const_string "alu")))
5629 (set_attr "mode" "SI")])
5631 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
5632 (define_insn "*addsi_3_zext"
5633 [(set (reg FLAGS_REG)
5634 (compare (neg:SI (match_operand:SI 2 "general_operand" "rmni"))
5635 (match_operand:SI 1 "nonimmediate_operand" "%0")))
5636 (set (match_operand:DI 0 "register_operand" "=r")
5637 (zero_extend:DI (plus:SI (match_dup 1) (match_dup 2))))]
5638 "TARGET_64BIT && ix86_match_ccmode (insn, CCZmode)
5639 && ix86_binary_operator_ok (PLUS, SImode, operands)
5640 /* Current assemblers are broken and do not allow @GOTOFF in
5641 ought but a memory context. */
5642 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5644 switch (get_attr_type (insn))
5647 if (operands[2] == const1_rtx)
5648 return "inc{l}\t%k0";
5651 gcc_assert (operands[2] == constm1_rtx);
5652 return "dec{l}\t%k0";
5656 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5657 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5658 if (GET_CODE (operands[2]) == CONST_INT
5659 && (INTVAL (operands[2]) == 128
5660 || (INTVAL (operands[2]) < 0
5661 && INTVAL (operands[2]) != -128)))
5663 operands[2] = GEN_INT (-INTVAL (operands[2]));
5664 return "sub{l}\t{%2, %k0|%k0, %2}";
5666 return "add{l}\t{%2, %k0|%k0, %2}";
5670 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5671 (const_string "incdec")
5672 (const_string "alu")))
5673 (set_attr "mode" "SI")])
5675 ; For comparisons against 1, -1 and 128, we may generate better code
5676 ; by converting cmp to add, inc or dec as done by peephole2. This pattern
5677 ; is matched then. We can't accept general immediate, because for
5678 ; case of overflows, the result is messed up.
5679 ; This pattern also don't hold of 0x80000000, since the value overflows
5681 ; Also carry flag is reversed compared to cmp, so this conversion is valid
5682 ; only for comparisons not depending on it.
5683 (define_insn "*addsi_4"
5684 [(set (reg FLAGS_REG)
5685 (compare (match_operand:SI 1 "nonimmediate_operand" "0")
5686 (match_operand:SI 2 "const_int_operand" "n")))
5687 (clobber (match_scratch:SI 0 "=rm"))]
5688 "ix86_match_ccmode (insn, CCGCmode)
5689 && (INTVAL (operands[2]) & 0xffffffff) != 0x80000000"
5691 switch (get_attr_type (insn))
5694 if (operands[2] == constm1_rtx)
5695 return "inc{l}\t%0";
5698 gcc_assert (operands[2] == const1_rtx);
5699 return "dec{l}\t%0";
5703 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5704 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5705 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5706 if ((INTVAL (operands[2]) == -128
5707 || (INTVAL (operands[2]) > 0
5708 && INTVAL (operands[2]) != 128)))
5709 return "sub{l}\t{%2, %0|%0, %2}";
5710 operands[2] = GEN_INT (-INTVAL (operands[2]));
5711 return "add{l}\t{%2, %0|%0, %2}";
5715 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5716 (const_string "incdec")
5717 (const_string "alu")))
5718 (set_attr "mode" "SI")])
5720 (define_insn "*addsi_5"
5721 [(set (reg FLAGS_REG)
5723 (plus:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
5724 (match_operand:SI 2 "general_operand" "rmni"))
5726 (clobber (match_scratch:SI 0 "=r"))]
5727 "ix86_match_ccmode (insn, CCGOCmode)
5728 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)
5729 /* Current assemblers are broken and do not allow @GOTOFF in
5730 ought but a memory context. */
5731 && ! pic_symbolic_operand (operands[2], VOIDmode)"
5733 switch (get_attr_type (insn))
5736 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5737 if (operands[2] == const1_rtx)
5738 return "inc{l}\t%0";
5741 gcc_assert (operands[2] == constm1_rtx);
5742 return "dec{l}\t%0";
5746 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5747 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5748 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5749 if (GET_CODE (operands[2]) == CONST_INT
5750 && (INTVAL (operands[2]) == 128
5751 || (INTVAL (operands[2]) < 0
5752 && INTVAL (operands[2]) != -128)))
5754 operands[2] = GEN_INT (-INTVAL (operands[2]));
5755 return "sub{l}\t{%2, %0|%0, %2}";
5757 return "add{l}\t{%2, %0|%0, %2}";
5761 (if_then_else (match_operand:SI 2 "incdec_operand" "")
5762 (const_string "incdec")
5763 (const_string "alu")))
5764 (set_attr "mode" "SI")])
5766 (define_expand "addhi3"
5767 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
5768 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "")
5769 (match_operand:HI 2 "general_operand" "")))
5770 (clobber (reg:CC FLAGS_REG))])]
5771 "TARGET_HIMODE_MATH"
5772 "ix86_expand_binary_operator (PLUS, HImode, operands); DONE;")
5774 ;; %%% After Dave's SUBREG_BYTE stuff goes in, re-enable incb %ah
5775 ;; type optimizations enabled by define-splits. This is not important
5776 ;; for PII, and in fact harmful because of partial register stalls.
5778 (define_insn "*addhi_1_lea"
5779 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
5780 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r")
5781 (match_operand:HI 2 "general_operand" "ri,rm,lni")))
5782 (clobber (reg:CC FLAGS_REG))]
5783 "!TARGET_PARTIAL_REG_STALL
5784 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5786 switch (get_attr_type (insn))
5791 if (operands[2] == const1_rtx)
5792 return "inc{w}\t%0";
5795 gcc_assert (operands[2] == constm1_rtx);
5796 return "dec{w}\t%0";
5800 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5801 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5802 if (GET_CODE (operands[2]) == CONST_INT
5803 && (INTVAL (operands[2]) == 128
5804 || (INTVAL (operands[2]) < 0
5805 && INTVAL (operands[2]) != -128)))
5807 operands[2] = GEN_INT (-INTVAL (operands[2]));
5808 return "sub{w}\t{%2, %0|%0, %2}";
5810 return "add{w}\t{%2, %0|%0, %2}";
5814 (if_then_else (eq_attr "alternative" "2")
5815 (const_string "lea")
5816 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5817 (const_string "incdec")
5818 (const_string "alu"))))
5819 (set_attr "mode" "HI,HI,SI")])
5821 (define_insn "*addhi_1"
5822 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
5823 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
5824 (match_operand:HI 2 "general_operand" "ri,rm")))
5825 (clobber (reg:CC FLAGS_REG))]
5826 "TARGET_PARTIAL_REG_STALL
5827 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5829 switch (get_attr_type (insn))
5832 if (operands[2] == const1_rtx)
5833 return "inc{w}\t%0";
5836 gcc_assert (operands[2] == constm1_rtx);
5837 return "dec{w}\t%0";
5841 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5842 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5843 if (GET_CODE (operands[2]) == CONST_INT
5844 && (INTVAL (operands[2]) == 128
5845 || (INTVAL (operands[2]) < 0
5846 && INTVAL (operands[2]) != -128)))
5848 operands[2] = GEN_INT (-INTVAL (operands[2]));
5849 return "sub{w}\t{%2, %0|%0, %2}";
5851 return "add{w}\t{%2, %0|%0, %2}";
5855 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5856 (const_string "incdec")
5857 (const_string "alu")))
5858 (set_attr "mode" "HI")])
5860 (define_insn "*addhi_2"
5861 [(set (reg FLAGS_REG)
5863 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
5864 (match_operand:HI 2 "general_operand" "rmni,rni"))
5866 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
5867 (plus:HI (match_dup 1) (match_dup 2)))]
5868 "ix86_match_ccmode (insn, CCGOCmode)
5869 && ix86_binary_operator_ok (PLUS, HImode, operands)"
5871 switch (get_attr_type (insn))
5874 if (operands[2] == const1_rtx)
5875 return "inc{w}\t%0";
5878 gcc_assert (operands[2] == constm1_rtx);
5879 return "dec{w}\t%0";
5883 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5884 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5885 if (GET_CODE (operands[2]) == CONST_INT
5886 && (INTVAL (operands[2]) == 128
5887 || (INTVAL (operands[2]) < 0
5888 && INTVAL (operands[2]) != -128)))
5890 operands[2] = GEN_INT (-INTVAL (operands[2]));
5891 return "sub{w}\t{%2, %0|%0, %2}";
5893 return "add{w}\t{%2, %0|%0, %2}";
5897 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5898 (const_string "incdec")
5899 (const_string "alu")))
5900 (set_attr "mode" "HI")])
5902 (define_insn "*addhi_3"
5903 [(set (reg FLAGS_REG)
5904 (compare (neg:HI (match_operand:HI 2 "general_operand" "rmni"))
5905 (match_operand:HI 1 "nonimmediate_operand" "%0")))
5906 (clobber (match_scratch:HI 0 "=r"))]
5907 "ix86_match_ccmode (insn, CCZmode)
5908 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5910 switch (get_attr_type (insn))
5913 if (operands[2] == const1_rtx)
5914 return "inc{w}\t%0";
5917 gcc_assert (operands[2] == constm1_rtx);
5918 return "dec{w}\t%0";
5922 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5923 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5924 if (GET_CODE (operands[2]) == CONST_INT
5925 && (INTVAL (operands[2]) == 128
5926 || (INTVAL (operands[2]) < 0
5927 && INTVAL (operands[2]) != -128)))
5929 operands[2] = GEN_INT (-INTVAL (operands[2]));
5930 return "sub{w}\t{%2, %0|%0, %2}";
5932 return "add{w}\t{%2, %0|%0, %2}";
5936 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5937 (const_string "incdec")
5938 (const_string "alu")))
5939 (set_attr "mode" "HI")])
5941 ; See comments above addsi_4 for details.
5942 (define_insn "*addhi_4"
5943 [(set (reg FLAGS_REG)
5944 (compare (match_operand:HI 1 "nonimmediate_operand" "0")
5945 (match_operand:HI 2 "const_int_operand" "n")))
5946 (clobber (match_scratch:HI 0 "=rm"))]
5947 "ix86_match_ccmode (insn, CCGCmode)
5948 && (INTVAL (operands[2]) & 0xffff) != 0x8000"
5950 switch (get_attr_type (insn))
5953 if (operands[2] == constm1_rtx)
5954 return "inc{w}\t%0";
5957 gcc_assert (operands[2] == const1_rtx);
5958 return "dec{w}\t%0";
5962 gcc_assert (rtx_equal_p (operands[0], operands[1]));
5963 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
5964 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
5965 if ((INTVAL (operands[2]) == -128
5966 || (INTVAL (operands[2]) > 0
5967 && INTVAL (operands[2]) != 128)))
5968 return "sub{w}\t{%2, %0|%0, %2}";
5969 operands[2] = GEN_INT (-INTVAL (operands[2]));
5970 return "add{w}\t{%2, %0|%0, %2}";
5974 (if_then_else (match_operand:HI 2 "incdec_operand" "")
5975 (const_string "incdec")
5976 (const_string "alu")))
5977 (set_attr "mode" "SI")])
5980 (define_insn "*addhi_5"
5981 [(set (reg FLAGS_REG)
5983 (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
5984 (match_operand:HI 2 "general_operand" "rmni"))
5986 (clobber (match_scratch:HI 0 "=r"))]
5987 "ix86_match_ccmode (insn, CCGOCmode)
5988 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
5990 switch (get_attr_type (insn))
5993 if (operands[2] == const1_rtx)
5994 return "inc{w}\t%0";
5997 gcc_assert (operands[2] == constm1_rtx);
5998 return "dec{w}\t%0";
6002 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6003 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6004 if (GET_CODE (operands[2]) == CONST_INT
6005 && (INTVAL (operands[2]) == 128
6006 || (INTVAL (operands[2]) < 0
6007 && INTVAL (operands[2]) != -128)))
6009 operands[2] = GEN_INT (-INTVAL (operands[2]));
6010 return "sub{w}\t{%2, %0|%0, %2}";
6012 return "add{w}\t{%2, %0|%0, %2}";
6016 (if_then_else (match_operand:HI 2 "incdec_operand" "")
6017 (const_string "incdec")
6018 (const_string "alu")))
6019 (set_attr "mode" "HI")])
6021 (define_expand "addqi3"
6022 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6023 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6024 (match_operand:QI 2 "general_operand" "")))
6025 (clobber (reg:CC FLAGS_REG))])]
6026 "TARGET_QIMODE_MATH"
6027 "ix86_expand_binary_operator (PLUS, QImode, operands); DONE;")
6029 ;; %%% Potential partial reg stall on alternative 2. What to do?
6030 (define_insn "*addqi_1_lea"
6031 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r,r")
6032 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0,r")
6033 (match_operand:QI 2 "general_operand" "qn,qmn,rn,ln")))
6034 (clobber (reg:CC FLAGS_REG))]
6035 "!TARGET_PARTIAL_REG_STALL
6036 && ix86_binary_operator_ok (PLUS, QImode, operands)"
6038 int widen = (which_alternative == 2);
6039 switch (get_attr_type (insn))
6044 if (operands[2] == const1_rtx)
6045 return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6048 gcc_assert (operands[2] == constm1_rtx);
6049 return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6053 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6054 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6055 if (GET_CODE (operands[2]) == CONST_INT
6056 && (INTVAL (operands[2]) == 128
6057 || (INTVAL (operands[2]) < 0
6058 && INTVAL (operands[2]) != -128)))
6060 operands[2] = GEN_INT (-INTVAL (operands[2]));
6062 return "sub{l}\t{%2, %k0|%k0, %2}";
6064 return "sub{b}\t{%2, %0|%0, %2}";
6067 return "add{l}\t{%k2, %k0|%k0, %k2}";
6069 return "add{b}\t{%2, %0|%0, %2}";
6073 (if_then_else (eq_attr "alternative" "3")
6074 (const_string "lea")
6075 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6076 (const_string "incdec")
6077 (const_string "alu"))))
6078 (set_attr "mode" "QI,QI,SI,SI")])
6080 (define_insn "*addqi_1"
6081 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
6082 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
6083 (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
6084 (clobber (reg:CC FLAGS_REG))]
6085 "TARGET_PARTIAL_REG_STALL
6086 && ix86_binary_operator_ok (PLUS, QImode, operands)"
6088 int widen = (which_alternative == 2);
6089 switch (get_attr_type (insn))
6092 if (operands[2] == const1_rtx)
6093 return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
6096 gcc_assert (operands[2] == constm1_rtx);
6097 return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
6101 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'.
6102 Exceptions: -128 encodes smaller than 128, so swap sign and op. */
6103 if (GET_CODE (operands[2]) == CONST_INT
6104 && (INTVAL (operands[2]) == 128
6105 || (INTVAL (operands[2]) < 0
6106 && INTVAL (operands[2]) != -128)))
6108 operands[2] = GEN_INT (-INTVAL (operands[2]));
6110 return "sub{l}\t{%2, %k0|%k0, %2}";
6112 return "sub{b}\t{%2, %0|%0, %2}";
6115 return "add{l}\t{%k2, %k0|%k0, %k2}";
6117 return "add{b}\t{%2, %0|%0, %2}";
6121 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6122 (const_string "incdec")
6123 (const_string "alu")))
6124 (set_attr "mode" "QI,QI,SI")])
6126 (define_insn "*addqi_1_slp"
6127 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6128 (plus:QI (match_dup 0)
6129 (match_operand:QI 1 "general_operand" "qn,qnm")))
6130 (clobber (reg:CC FLAGS_REG))]
6131 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6132 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
6134 switch (get_attr_type (insn))
6137 if (operands[1] == const1_rtx)
6138 return "inc{b}\t%0";
6141 gcc_assert (operands[1] == constm1_rtx);
6142 return "dec{b}\t%0";
6146 /* Make things pretty and `subl $4,%eax' rather than `addl $-4, %eax'. */
6147 if (GET_CODE (operands[1]) == CONST_INT
6148 && INTVAL (operands[1]) < 0)
6150 operands[1] = GEN_INT (-INTVAL (operands[1]));
6151 return "sub{b}\t{%1, %0|%0, %1}";
6153 return "add{b}\t{%1, %0|%0, %1}";
6157 (if_then_else (match_operand:QI 1 "incdec_operand" "")
6158 (const_string "incdec")
6159 (const_string "alu1")))
6160 (set (attr "memory")
6161 (if_then_else (match_operand 1 "memory_operand" "")
6162 (const_string "load")
6163 (const_string "none")))
6164 (set_attr "mode" "QI")])
6166 (define_insn "*addqi_2"
6167 [(set (reg FLAGS_REG)
6169 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
6170 (match_operand:QI 2 "general_operand" "qmni,qni"))
6172 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
6173 (plus:QI (match_dup 1) (match_dup 2)))]
6174 "ix86_match_ccmode (insn, CCGOCmode)
6175 && ix86_binary_operator_ok (PLUS, QImode, operands)"
6177 switch (get_attr_type (insn))
6180 if (operands[2] == const1_rtx)
6181 return "inc{b}\t%0";
6184 gcc_assert (operands[2] == constm1_rtx
6185 || (GET_CODE (operands[2]) == CONST_INT
6186 && INTVAL (operands[2]) == 255));
6187 return "dec{b}\t%0";
6191 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
6192 if (GET_CODE (operands[2]) == CONST_INT
6193 && INTVAL (operands[2]) < 0)
6195 operands[2] = GEN_INT (-INTVAL (operands[2]));
6196 return "sub{b}\t{%2, %0|%0, %2}";
6198 return "add{b}\t{%2, %0|%0, %2}";
6202 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6203 (const_string "incdec")
6204 (const_string "alu")))
6205 (set_attr "mode" "QI")])
6207 (define_insn "*addqi_3"
6208 [(set (reg FLAGS_REG)
6209 (compare (neg:QI (match_operand:QI 2 "general_operand" "qmni"))
6210 (match_operand:QI 1 "nonimmediate_operand" "%0")))
6211 (clobber (match_scratch:QI 0 "=q"))]
6212 "ix86_match_ccmode (insn, CCZmode)
6213 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6215 switch (get_attr_type (insn))
6218 if (operands[2] == const1_rtx)
6219 return "inc{b}\t%0";
6222 gcc_assert (operands[2] == constm1_rtx
6223 || (GET_CODE (operands[2]) == CONST_INT
6224 && INTVAL (operands[2]) == 255));
6225 return "dec{b}\t%0";
6229 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
6230 if (GET_CODE (operands[2]) == CONST_INT
6231 && INTVAL (operands[2]) < 0)
6233 operands[2] = GEN_INT (-INTVAL (operands[2]));
6234 return "sub{b}\t{%2, %0|%0, %2}";
6236 return "add{b}\t{%2, %0|%0, %2}";
6240 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6241 (const_string "incdec")
6242 (const_string "alu")))
6243 (set_attr "mode" "QI")])
6245 ; See comments above addsi_4 for details.
6246 (define_insn "*addqi_4"
6247 [(set (reg FLAGS_REG)
6248 (compare (match_operand:QI 1 "nonimmediate_operand" "0")
6249 (match_operand:QI 2 "const_int_operand" "n")))
6250 (clobber (match_scratch:QI 0 "=qm"))]
6251 "ix86_match_ccmode (insn, CCGCmode)
6252 && (INTVAL (operands[2]) & 0xff) != 0x80"
6254 switch (get_attr_type (insn))
6257 if (operands[2] == constm1_rtx
6258 || (GET_CODE (operands[2]) == CONST_INT
6259 && INTVAL (operands[2]) == 255))
6260 return "inc{b}\t%0";
6263 gcc_assert (operands[2] == const1_rtx);
6264 return "dec{b}\t%0";
6268 gcc_assert (rtx_equal_p (operands[0], operands[1]));
6269 if (INTVAL (operands[2]) < 0)
6271 operands[2] = GEN_INT (-INTVAL (operands[2]));
6272 return "add{b}\t{%2, %0|%0, %2}";
6274 return "sub{b}\t{%2, %0|%0, %2}";
6278 (if_then_else (match_operand:HI 2 "incdec_operand" "")
6279 (const_string "incdec")
6280 (const_string "alu")))
6281 (set_attr "mode" "QI")])
6284 (define_insn "*addqi_5"
6285 [(set (reg FLAGS_REG)
6287 (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6288 (match_operand:QI 2 "general_operand" "qmni"))
6290 (clobber (match_scratch:QI 0 "=q"))]
6291 "ix86_match_ccmode (insn, CCGOCmode)
6292 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6294 switch (get_attr_type (insn))
6297 if (operands[2] == const1_rtx)
6298 return "inc{b}\t%0";
6301 gcc_assert (operands[2] == constm1_rtx
6302 || (GET_CODE (operands[2]) == CONST_INT
6303 && INTVAL (operands[2]) == 255));
6304 return "dec{b}\t%0";
6308 /* Make things pretty and `subb $4,%al' rather than `addb $-4, %al'. */
6309 if (GET_CODE (operands[2]) == CONST_INT
6310 && INTVAL (operands[2]) < 0)
6312 operands[2] = GEN_INT (-INTVAL (operands[2]));
6313 return "sub{b}\t{%2, %0|%0, %2}";
6315 return "add{b}\t{%2, %0|%0, %2}";
6319 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6320 (const_string "incdec")
6321 (const_string "alu")))
6322 (set_attr "mode" "QI")])
6325 (define_insn "addqi_ext_1"
6326 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6331 (match_operand 1 "ext_register_operand" "0")
6334 (match_operand:QI 2 "general_operand" "Qmn")))
6335 (clobber (reg:CC FLAGS_REG))]
6338 switch (get_attr_type (insn))
6341 if (operands[2] == const1_rtx)
6342 return "inc{b}\t%h0";
6345 gcc_assert (operands[2] == constm1_rtx
6346 || (GET_CODE (operands[2]) == CONST_INT
6347 && INTVAL (operands[2]) == 255));
6348 return "dec{b}\t%h0";
6352 return "add{b}\t{%2, %h0|%h0, %2}";
6356 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6357 (const_string "incdec")
6358 (const_string "alu")))
6359 (set_attr "mode" "QI")])
6361 (define_insn "*addqi_ext_1_rex64"
6362 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6367 (match_operand 1 "ext_register_operand" "0")
6370 (match_operand:QI 2 "nonmemory_operand" "Qn")))
6371 (clobber (reg:CC FLAGS_REG))]
6374 switch (get_attr_type (insn))
6377 if (operands[2] == const1_rtx)
6378 return "inc{b}\t%h0";
6381 gcc_assert (operands[2] == constm1_rtx
6382 || (GET_CODE (operands[2]) == CONST_INT
6383 && INTVAL (operands[2]) == 255));
6384 return "dec{b}\t%h0";
6388 return "add{b}\t{%2, %h0|%h0, %2}";
6392 (if_then_else (match_operand:QI 2 "incdec_operand" "")
6393 (const_string "incdec")
6394 (const_string "alu")))
6395 (set_attr "mode" "QI")])
6397 (define_insn "*addqi_ext_2"
6398 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
6403 (match_operand 1 "ext_register_operand" "%0")
6407 (match_operand 2 "ext_register_operand" "Q")
6410 (clobber (reg:CC FLAGS_REG))]
6412 "add{b}\t{%h2, %h0|%h0, %h2}"
6413 [(set_attr "type" "alu")
6414 (set_attr "mode" "QI")])
6416 ;; The patterns that match these are at the end of this file.
6418 (define_expand "addxf3"
6419 [(set (match_operand:XF 0 "register_operand" "")
6420 (plus:XF (match_operand:XF 1 "register_operand" "")
6421 (match_operand:XF 2 "register_operand" "")))]
6425 (define_expand "adddf3"
6426 [(set (match_operand:DF 0 "register_operand" "")
6427 (plus:DF (match_operand:DF 1 "register_operand" "")
6428 (match_operand:DF 2 "nonimmediate_operand" "")))]
6429 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
6432 (define_expand "addsf3"
6433 [(set (match_operand:SF 0 "register_operand" "")
6434 (plus:SF (match_operand:SF 1 "register_operand" "")
6435 (match_operand:SF 2 "nonimmediate_operand" "")))]
6436 "TARGET_80387 || TARGET_SSE_MATH"
6439 ;; Subtract instructions
6441 ;; %%% splits for subditi3
6443 (define_expand "subti3"
6444 [(parallel [(set (match_operand:TI 0 "nonimmediate_operand" "")
6445 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "")
6446 (match_operand:TI 2 "x86_64_general_operand" "")))
6447 (clobber (reg:CC FLAGS_REG))])]
6449 "ix86_expand_binary_operator (MINUS, TImode, operands); DONE;")
6451 (define_insn "*subti3_1"
6452 [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o")
6453 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "0,0")
6454 (match_operand:TI 2 "general_operand" "roiF,riF")))
6455 (clobber (reg:CC FLAGS_REG))]
6456 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, TImode, operands)"
6460 [(set (match_operand:TI 0 "nonimmediate_operand" "")
6461 (minus:TI (match_operand:TI 1 "nonimmediate_operand" "")
6462 (match_operand:TI 2 "general_operand" "")))
6463 (clobber (reg:CC FLAGS_REG))]
6464 "TARGET_64BIT && reload_completed"
6465 [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
6466 (set (match_dup 0) (minus:DI (match_dup 1) (match_dup 2)))])
6467 (parallel [(set (match_dup 3)
6468 (minus:DI (match_dup 4)
6469 (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
6471 (clobber (reg:CC FLAGS_REG))])]
6472 "split_ti (operands+0, 1, operands+0, operands+3);
6473 split_ti (operands+1, 1, operands+1, operands+4);
6474 split_ti (operands+2, 1, operands+2, operands+5);")
6476 ;; %%% splits for subsidi3
6478 (define_expand "subdi3"
6479 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
6480 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6481 (match_operand:DI 2 "x86_64_general_operand" "")))
6482 (clobber (reg:CC FLAGS_REG))])]
6484 "ix86_expand_binary_operator (MINUS, DImode, operands); DONE;")
6486 (define_insn "*subdi3_1"
6487 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,o")
6488 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6489 (match_operand:DI 2 "general_operand" "roiF,riF")))
6490 (clobber (reg:CC FLAGS_REG))]
6491 "!TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6495 [(set (match_operand:DI 0 "nonimmediate_operand" "")
6496 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "")
6497 (match_operand:DI 2 "general_operand" "")))
6498 (clobber (reg:CC FLAGS_REG))]
6499 "!TARGET_64BIT && reload_completed"
6500 [(parallel [(set (reg:CC FLAGS_REG) (compare:CC (match_dup 1) (match_dup 2)))
6501 (set (match_dup 0) (minus:SI (match_dup 1) (match_dup 2)))])
6502 (parallel [(set (match_dup 3)
6503 (minus:SI (match_dup 4)
6504 (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
6506 (clobber (reg:CC FLAGS_REG))])]
6507 "split_di (operands+0, 1, operands+0, operands+3);
6508 split_di (operands+1, 1, operands+1, operands+4);
6509 split_di (operands+2, 1, operands+2, operands+5);")
6511 (define_insn "subdi3_carry_rex64"
6512 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6513 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6514 (plus:DI (match_operand:DI 3 "ix86_carry_flag_operator" "")
6515 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))))
6516 (clobber (reg:CC FLAGS_REG))]
6517 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6518 "sbb{q}\t{%2, %0|%0, %2}"
6519 [(set_attr "type" "alu")
6520 (set_attr "pent_pair" "pu")
6521 (set_attr "mode" "DI")])
6523 (define_insn "*subdi_1_rex64"
6524 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6525 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6526 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6527 (clobber (reg:CC FLAGS_REG))]
6528 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, DImode, operands)"
6529 "sub{q}\t{%2, %0|%0, %2}"
6530 [(set_attr "type" "alu")
6531 (set_attr "mode" "DI")])
6533 (define_insn "*subdi_2_rex64"
6534 [(set (reg FLAGS_REG)
6536 (minus:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
6537 (match_operand:DI 2 "x86_64_general_operand" "re,rm"))
6539 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6540 (minus:DI (match_dup 1) (match_dup 2)))]
6541 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6542 && ix86_binary_operator_ok (MINUS, DImode, operands)"
6543 "sub{q}\t{%2, %0|%0, %2}"
6544 [(set_attr "type" "alu")
6545 (set_attr "mode" "DI")])
6547 (define_insn "*subdi_3_rex63"
6548 [(set (reg FLAGS_REG)
6549 (compare (match_operand:DI 1 "nonimmediate_operand" "0,0")
6550 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
6551 (set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
6552 (minus:DI (match_dup 1) (match_dup 2)))]
6553 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6554 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6555 "sub{q}\t{%2, %0|%0, %2}"
6556 [(set_attr "type" "alu")
6557 (set_attr "mode" "DI")])
6559 (define_insn "subqi3_carry"
6560 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6561 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6562 (plus:QI (match_operand:QI 3 "ix86_carry_flag_operator" "")
6563 (match_operand:QI 2 "general_operand" "qi,qm"))))
6564 (clobber (reg:CC FLAGS_REG))]
6565 "ix86_binary_operator_ok (MINUS, QImode, operands)"
6566 "sbb{b}\t{%2, %0|%0, %2}"
6567 [(set_attr "type" "alu")
6568 (set_attr "pent_pair" "pu")
6569 (set_attr "mode" "QI")])
6571 (define_insn "subhi3_carry"
6572 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6573 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6574 (plus:HI (match_operand:HI 3 "ix86_carry_flag_operator" "")
6575 (match_operand:HI 2 "general_operand" "ri,rm"))))
6576 (clobber (reg:CC FLAGS_REG))]
6577 "ix86_binary_operator_ok (MINUS, HImode, operands)"
6578 "sbb{w}\t{%2, %0|%0, %2}"
6579 [(set_attr "type" "alu")
6580 (set_attr "pent_pair" "pu")
6581 (set_attr "mode" "HI")])
6583 (define_insn "subsi3_carry"
6584 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6585 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6586 (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6587 (match_operand:SI 2 "general_operand" "ri,rm"))))
6588 (clobber (reg:CC FLAGS_REG))]
6589 "ix86_binary_operator_ok (MINUS, SImode, operands)"
6590 "sbb{l}\t{%2, %0|%0, %2}"
6591 [(set_attr "type" "alu")
6592 (set_attr "pent_pair" "pu")
6593 (set_attr "mode" "SI")])
6595 (define_insn "subsi3_carry_zext"
6596 [(set (match_operand:DI 0 "register_operand" "=rm,r")
6598 (minus:SI (match_operand:SI 1 "register_operand" "0,0")
6599 (plus:SI (match_operand:SI 3 "ix86_carry_flag_operator" "")
6600 (match_operand:SI 2 "general_operand" "ri,rm")))))
6601 (clobber (reg:CC FLAGS_REG))]
6602 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6603 "sbb{l}\t{%2, %k0|%k0, %2}"
6604 [(set_attr "type" "alu")
6605 (set_attr "pent_pair" "pu")
6606 (set_attr "mode" "SI")])
6608 (define_expand "subsi3"
6609 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
6610 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "")
6611 (match_operand:SI 2 "general_operand" "")))
6612 (clobber (reg:CC FLAGS_REG))])]
6614 "ix86_expand_binary_operator (MINUS, SImode, operands); DONE;")
6616 (define_insn "*subsi_1"
6617 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6618 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6619 (match_operand:SI 2 "general_operand" "ri,rm")))
6620 (clobber (reg:CC FLAGS_REG))]
6621 "ix86_binary_operator_ok (MINUS, SImode, operands)"
6622 "sub{l}\t{%2, %0|%0, %2}"
6623 [(set_attr "type" "alu")
6624 (set_attr "mode" "SI")])
6626 (define_insn "*subsi_1_zext"
6627 [(set (match_operand:DI 0 "register_operand" "=r")
6629 (minus:SI (match_operand:SI 1 "register_operand" "0")
6630 (match_operand:SI 2 "general_operand" "rim"))))
6631 (clobber (reg:CC FLAGS_REG))]
6632 "TARGET_64BIT && ix86_binary_operator_ok (MINUS, SImode, operands)"
6633 "sub{l}\t{%2, %k0|%k0, %2}"
6634 [(set_attr "type" "alu")
6635 (set_attr "mode" "SI")])
6637 (define_insn "*subsi_2"
6638 [(set (reg FLAGS_REG)
6640 (minus:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
6641 (match_operand:SI 2 "general_operand" "ri,rm"))
6643 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6644 (minus:SI (match_dup 1) (match_dup 2)))]
6645 "ix86_match_ccmode (insn, CCGOCmode)
6646 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6647 "sub{l}\t{%2, %0|%0, %2}"
6648 [(set_attr "type" "alu")
6649 (set_attr "mode" "SI")])
6651 (define_insn "*subsi_2_zext"
6652 [(set (reg FLAGS_REG)
6654 (minus:SI (match_operand:SI 1 "register_operand" "0")
6655 (match_operand:SI 2 "general_operand" "rim"))
6657 (set (match_operand:DI 0 "register_operand" "=r")
6659 (minus:SI (match_dup 1)
6661 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
6662 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6663 "sub{l}\t{%2, %k0|%k0, %2}"
6664 [(set_attr "type" "alu")
6665 (set_attr "mode" "SI")])
6667 (define_insn "*subsi_3"
6668 [(set (reg FLAGS_REG)
6669 (compare (match_operand:SI 1 "nonimmediate_operand" "0,0")
6670 (match_operand:SI 2 "general_operand" "ri,rm")))
6671 (set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
6672 (minus:SI (match_dup 1) (match_dup 2)))]
6673 "ix86_match_ccmode (insn, CCmode)
6674 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6675 "sub{l}\t{%2, %0|%0, %2}"
6676 [(set_attr "type" "alu")
6677 (set_attr "mode" "SI")])
6679 (define_insn "*subsi_3_zext"
6680 [(set (reg FLAGS_REG)
6681 (compare (match_operand:SI 1 "register_operand" "0")
6682 (match_operand:SI 2 "general_operand" "rim")))
6683 (set (match_operand:DI 0 "register_operand" "=r")
6685 (minus:SI (match_dup 1)
6687 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
6688 && ix86_binary_operator_ok (MINUS, SImode, operands)"
6689 "sub{q}\t{%2, %0|%0, %2}"
6690 [(set_attr "type" "alu")
6691 (set_attr "mode" "DI")])
6693 (define_expand "subhi3"
6694 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
6695 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "")
6696 (match_operand:HI 2 "general_operand" "")))
6697 (clobber (reg:CC FLAGS_REG))])]
6698 "TARGET_HIMODE_MATH"
6699 "ix86_expand_binary_operator (MINUS, HImode, operands); DONE;")
6701 (define_insn "*subhi_1"
6702 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6703 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6704 (match_operand:HI 2 "general_operand" "ri,rm")))
6705 (clobber (reg:CC FLAGS_REG))]
6706 "ix86_binary_operator_ok (MINUS, HImode, operands)"
6707 "sub{w}\t{%2, %0|%0, %2}"
6708 [(set_attr "type" "alu")
6709 (set_attr "mode" "HI")])
6711 (define_insn "*subhi_2"
6712 [(set (reg FLAGS_REG)
6714 (minus:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
6715 (match_operand:HI 2 "general_operand" "ri,rm"))
6717 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6718 (minus:HI (match_dup 1) (match_dup 2)))]
6719 "ix86_match_ccmode (insn, CCGOCmode)
6720 && ix86_binary_operator_ok (MINUS, HImode, operands)"
6721 "sub{w}\t{%2, %0|%0, %2}"
6722 [(set_attr "type" "alu")
6723 (set_attr "mode" "HI")])
6725 (define_insn "*subhi_3"
6726 [(set (reg FLAGS_REG)
6727 (compare (match_operand:HI 1 "nonimmediate_operand" "0,0")
6728 (match_operand:HI 2 "general_operand" "ri,rm")))
6729 (set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
6730 (minus:HI (match_dup 1) (match_dup 2)))]
6731 "ix86_match_ccmode (insn, CCmode)
6732 && ix86_binary_operator_ok (MINUS, HImode, operands)"
6733 "sub{w}\t{%2, %0|%0, %2}"
6734 [(set_attr "type" "alu")
6735 (set_attr "mode" "HI")])
6737 (define_expand "subqi3"
6738 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
6739 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "")
6740 (match_operand:QI 2 "general_operand" "")))
6741 (clobber (reg:CC FLAGS_REG))])]
6742 "TARGET_QIMODE_MATH"
6743 "ix86_expand_binary_operator (MINUS, QImode, operands); DONE;")
6745 (define_insn "*subqi_1"
6746 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q")
6747 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6748 (match_operand:QI 2 "general_operand" "qn,qmn")))
6749 (clobber (reg:CC FLAGS_REG))]
6750 "ix86_binary_operator_ok (MINUS, QImode, operands)"
6751 "sub{b}\t{%2, %0|%0, %2}"
6752 [(set_attr "type" "alu")
6753 (set_attr "mode" "QI")])
6755 (define_insn "*subqi_1_slp"
6756 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
6757 (minus:QI (match_dup 0)
6758 (match_operand:QI 1 "general_operand" "qn,qmn")))
6759 (clobber (reg:CC FLAGS_REG))]
6760 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
6761 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
6762 "sub{b}\t{%1, %0|%0, %1}"
6763 [(set_attr "type" "alu1")
6764 (set_attr "mode" "QI")])
6766 (define_insn "*subqi_2"
6767 [(set (reg FLAGS_REG)
6769 (minus:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
6770 (match_operand:QI 2 "general_operand" "qi,qm"))
6772 (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6773 (minus:HI (match_dup 1) (match_dup 2)))]
6774 "ix86_match_ccmode (insn, CCGOCmode)
6775 && ix86_binary_operator_ok (MINUS, QImode, operands)"
6776 "sub{b}\t{%2, %0|%0, %2}"
6777 [(set_attr "type" "alu")
6778 (set_attr "mode" "QI")])
6780 (define_insn "*subqi_3"
6781 [(set (reg FLAGS_REG)
6782 (compare (match_operand:QI 1 "nonimmediate_operand" "0,0")
6783 (match_operand:QI 2 "general_operand" "qi,qm")))
6784 (set (match_operand:HI 0 "nonimmediate_operand" "=qm,q")
6785 (minus:HI (match_dup 1) (match_dup 2)))]
6786 "ix86_match_ccmode (insn, CCmode)
6787 && ix86_binary_operator_ok (MINUS, QImode, operands)"
6788 "sub{b}\t{%2, %0|%0, %2}"
6789 [(set_attr "type" "alu")
6790 (set_attr "mode" "QI")])
6792 ;; The patterns that match these are at the end of this file.
6794 (define_expand "subxf3"
6795 [(set (match_operand:XF 0 "register_operand" "")
6796 (minus:XF (match_operand:XF 1 "register_operand" "")
6797 (match_operand:XF 2 "register_operand" "")))]
6801 (define_expand "subdf3"
6802 [(set (match_operand:DF 0 "register_operand" "")
6803 (minus:DF (match_operand:DF 1 "register_operand" "")
6804 (match_operand:DF 2 "nonimmediate_operand" "")))]
6805 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
6808 (define_expand "subsf3"
6809 [(set (match_operand:SF 0 "register_operand" "")
6810 (minus:SF (match_operand:SF 1 "register_operand" "")
6811 (match_operand:SF 2 "nonimmediate_operand" "")))]
6812 "TARGET_80387 || TARGET_SSE_MATH"
6815 ;; Multiply instructions
6817 (define_expand "muldi3"
6818 [(parallel [(set (match_operand:DI 0 "register_operand" "")
6819 (mult:DI (match_operand:DI 1 "register_operand" "")
6820 (match_operand:DI 2 "x86_64_general_operand" "")))
6821 (clobber (reg:CC FLAGS_REG))])]
6825 (define_insn "*muldi3_1_rex64"
6826 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6827 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "%rm,rm,0")
6828 (match_operand:DI 2 "x86_64_general_operand" "K,e,mr")))
6829 (clobber (reg:CC FLAGS_REG))]
6831 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6833 imul{q}\t{%2, %1, %0|%0, %1, %2}
6834 imul{q}\t{%2, %1, %0|%0, %1, %2}
6835 imul{q}\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")
6842 (const_string "vector")
6843 (and (eq_attr "alternative" "2")
6844 (match_operand 1 "memory_operand" ""))
6845 (const_string "vector")]
6846 (const_string "direct")))
6847 (set_attr "mode" "DI")])
6849 (define_expand "mulsi3"
6850 [(parallel [(set (match_operand:SI 0 "register_operand" "")
6851 (mult:SI (match_operand:SI 1 "register_operand" "")
6852 (match_operand:SI 2 "general_operand" "")))
6853 (clobber (reg:CC FLAGS_REG))])]
6857 (define_insn "*mulsi3_1"
6858 [(set (match_operand:SI 0 "register_operand" "=r,r,r")
6859 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6860 (match_operand:SI 2 "general_operand" "K,i,mr")))
6861 (clobber (reg:CC FLAGS_REG))]
6862 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6864 imul{l}\t{%2, %1, %0|%0, %1, %2}
6865 imul{l}\t{%2, %1, %0|%0, %1, %2}
6866 imul{l}\t{%2, %0|%0, %2}"
6867 [(set_attr "type" "imul")
6868 (set_attr "prefix_0f" "0,0,1")
6869 (set (attr "athlon_decode")
6870 (cond [(eq_attr "cpu" "athlon")
6871 (const_string "vector")
6872 (eq_attr "alternative" "1")
6873 (const_string "vector")
6874 (and (eq_attr "alternative" "2")
6875 (match_operand 1 "memory_operand" ""))
6876 (const_string "vector")]
6877 (const_string "direct")))
6878 (set_attr "mode" "SI")])
6880 (define_insn "*mulsi3_1_zext"
6881 [(set (match_operand:DI 0 "register_operand" "=r,r,r")
6883 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "%rm,rm,0")
6884 (match_operand:SI 2 "general_operand" "K,i,mr"))))
6885 (clobber (reg:CC FLAGS_REG))]
6887 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6889 imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6890 imul{l}\t{%2, %1, %k0|%k0, %1, %2}
6891 imul{l}\t{%2, %k0|%k0, %2}"
6892 [(set_attr "type" "imul")
6893 (set_attr "prefix_0f" "0,0,1")
6894 (set (attr "athlon_decode")
6895 (cond [(eq_attr "cpu" "athlon")
6896 (const_string "vector")
6897 (eq_attr "alternative" "1")
6898 (const_string "vector")
6899 (and (eq_attr "alternative" "2")
6900 (match_operand 1 "memory_operand" ""))
6901 (const_string "vector")]
6902 (const_string "direct")))
6903 (set_attr "mode" "SI")])
6905 (define_expand "mulhi3"
6906 [(parallel [(set (match_operand:HI 0 "register_operand" "")
6907 (mult:HI (match_operand:HI 1 "register_operand" "")
6908 (match_operand:HI 2 "general_operand" "")))
6909 (clobber (reg:CC FLAGS_REG))])]
6910 "TARGET_HIMODE_MATH"
6913 (define_insn "*mulhi3_1"
6914 [(set (match_operand:HI 0 "register_operand" "=r,r,r")
6915 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "%rm,rm,0")
6916 (match_operand:HI 2 "general_operand" "K,i,mr")))
6917 (clobber (reg:CC FLAGS_REG))]
6918 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
6920 imul{w}\t{%2, %1, %0|%0, %1, %2}
6921 imul{w}\t{%2, %1, %0|%0, %1, %2}
6922 imul{w}\t{%2, %0|%0, %2}"
6923 [(set_attr "type" "imul")
6924 (set_attr "prefix_0f" "0,0,1")
6925 (set (attr "athlon_decode")
6926 (cond [(eq_attr "cpu" "athlon")
6927 (const_string "vector")
6928 (eq_attr "alternative" "1,2")
6929 (const_string "vector")]
6930 (const_string "direct")))
6931 (set_attr "mode" "HI")])
6933 (define_expand "mulqi3"
6934 [(parallel [(set (match_operand:QI 0 "register_operand" "")
6935 (mult:QI (match_operand:QI 1 "nonimmediate_operand" "")
6936 (match_operand:QI 2 "register_operand" "")))
6937 (clobber (reg:CC FLAGS_REG))])]
6938 "TARGET_QIMODE_MATH"
6941 (define_insn "*mulqi3_1"
6942 [(set (match_operand:QI 0 "register_operand" "=a")
6943 (mult:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
6944 (match_operand:QI 2 "nonimmediate_operand" "qm")))
6945 (clobber (reg:CC FLAGS_REG))]
6947 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6949 [(set_attr "type" "imul")
6950 (set_attr "length_immediate" "0")
6951 (set (attr "athlon_decode")
6952 (if_then_else (eq_attr "cpu" "athlon")
6953 (const_string "vector")
6954 (const_string "direct")))
6955 (set_attr "mode" "QI")])
6957 (define_expand "umulqihi3"
6958 [(parallel [(set (match_operand:HI 0 "register_operand" "")
6959 (mult:HI (zero_extend:HI
6960 (match_operand:QI 1 "nonimmediate_operand" ""))
6962 (match_operand:QI 2 "register_operand" ""))))
6963 (clobber (reg:CC FLAGS_REG))])]
6964 "TARGET_QIMODE_MATH"
6967 (define_insn "*umulqihi3_1"
6968 [(set (match_operand:HI 0 "register_operand" "=a")
6969 (mult:HI (zero_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
6970 (zero_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6971 (clobber (reg:CC FLAGS_REG))]
6973 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6975 [(set_attr "type" "imul")
6976 (set_attr "length_immediate" "0")
6977 (set (attr "athlon_decode")
6978 (if_then_else (eq_attr "cpu" "athlon")
6979 (const_string "vector")
6980 (const_string "direct")))
6981 (set_attr "mode" "QI")])
6983 (define_expand "mulqihi3"
6984 [(parallel [(set (match_operand:HI 0 "register_operand" "")
6985 (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" ""))
6986 (sign_extend:HI (match_operand:QI 2 "register_operand" ""))))
6987 (clobber (reg:CC FLAGS_REG))])]
6988 "TARGET_QIMODE_MATH"
6991 (define_insn "*mulqihi3_insn"
6992 [(set (match_operand:HI 0 "register_operand" "=a")
6993 (mult:HI (sign_extend:HI (match_operand:QI 1 "nonimmediate_operand" "%0"))
6994 (sign_extend:HI (match_operand:QI 2 "nonimmediate_operand" "qm"))))
6995 (clobber (reg:CC FLAGS_REG))]
6997 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
6999 [(set_attr "type" "imul")
7000 (set_attr "length_immediate" "0")
7001 (set (attr "athlon_decode")
7002 (if_then_else (eq_attr "cpu" "athlon")
7003 (const_string "vector")
7004 (const_string "direct")))
7005 (set_attr "mode" "QI")])
7007 (define_expand "umulditi3"
7008 [(parallel [(set (match_operand:TI 0 "register_operand" "")
7009 (mult:TI (zero_extend:TI
7010 (match_operand:DI 1 "nonimmediate_operand" ""))
7012 (match_operand:DI 2 "register_operand" ""))))
7013 (clobber (reg:CC FLAGS_REG))])]
7017 (define_insn "*umulditi3_insn"
7018 [(set (match_operand:TI 0 "register_operand" "=A")
7019 (mult:TI (zero_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
7020 (zero_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
7021 (clobber (reg:CC FLAGS_REG))]
7023 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7025 [(set_attr "type" "imul")
7026 (set_attr "length_immediate" "0")
7027 (set (attr "athlon_decode")
7028 (if_then_else (eq_attr "cpu" "athlon")
7029 (const_string "vector")
7030 (const_string "double")))
7031 (set_attr "mode" "DI")])
7033 ;; We can't use this pattern in 64bit mode, since it results in two separate 32bit registers
7034 (define_expand "umulsidi3"
7035 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7036 (mult:DI (zero_extend:DI
7037 (match_operand:SI 1 "nonimmediate_operand" ""))
7039 (match_operand:SI 2 "register_operand" ""))))
7040 (clobber (reg:CC FLAGS_REG))])]
7044 (define_insn "*umulsidi3_insn"
7045 [(set (match_operand:DI 0 "register_operand" "=A")
7046 (mult:DI (zero_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7047 (zero_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7048 (clobber (reg:CC FLAGS_REG))]
7050 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7052 [(set_attr "type" "imul")
7053 (set_attr "length_immediate" "0")
7054 (set (attr "athlon_decode")
7055 (if_then_else (eq_attr "cpu" "athlon")
7056 (const_string "vector")
7057 (const_string "double")))
7058 (set_attr "mode" "SI")])
7060 (define_expand "mulditi3"
7061 [(parallel [(set (match_operand:TI 0 "register_operand" "")
7062 (mult:TI (sign_extend:TI
7063 (match_operand:DI 1 "nonimmediate_operand" ""))
7065 (match_operand:DI 2 "register_operand" ""))))
7066 (clobber (reg:CC FLAGS_REG))])]
7070 (define_insn "*mulditi3_insn"
7071 [(set (match_operand:TI 0 "register_operand" "=A")
7072 (mult:TI (sign_extend:TI (match_operand:DI 1 "nonimmediate_operand" "%0"))
7073 (sign_extend:TI (match_operand:DI 2 "nonimmediate_operand" "rm"))))
7074 (clobber (reg:CC FLAGS_REG))]
7076 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7078 [(set_attr "type" "imul")
7079 (set_attr "length_immediate" "0")
7080 (set (attr "athlon_decode")
7081 (if_then_else (eq_attr "cpu" "athlon")
7082 (const_string "vector")
7083 (const_string "double")))
7084 (set_attr "mode" "DI")])
7086 (define_expand "mulsidi3"
7087 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7088 (mult:DI (sign_extend:DI
7089 (match_operand:SI 1 "nonimmediate_operand" ""))
7091 (match_operand:SI 2 "register_operand" ""))))
7092 (clobber (reg:CC FLAGS_REG))])]
7096 (define_insn "*mulsidi3_insn"
7097 [(set (match_operand:DI 0 "register_operand" "=A")
7098 (mult:DI (sign_extend:DI (match_operand:SI 1 "nonimmediate_operand" "%0"))
7099 (sign_extend:DI (match_operand:SI 2 "nonimmediate_operand" "rm"))))
7100 (clobber (reg:CC FLAGS_REG))]
7102 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7104 [(set_attr "type" "imul")
7105 (set_attr "length_immediate" "0")
7106 (set (attr "athlon_decode")
7107 (if_then_else (eq_attr "cpu" "athlon")
7108 (const_string "vector")
7109 (const_string "double")))
7110 (set_attr "mode" "SI")])
7112 (define_expand "umuldi3_highpart"
7113 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7116 (mult:TI (zero_extend:TI
7117 (match_operand:DI 1 "nonimmediate_operand" ""))
7119 (match_operand:DI 2 "register_operand" "")))
7121 (clobber (match_scratch:DI 3 ""))
7122 (clobber (reg:CC FLAGS_REG))])]
7126 (define_insn "*umuldi3_highpart_rex64"
7127 [(set (match_operand:DI 0 "register_operand" "=d")
7130 (mult:TI (zero_extend:TI
7131 (match_operand:DI 1 "nonimmediate_operand" "%a"))
7133 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7135 (clobber (match_scratch:DI 3 "=1"))
7136 (clobber (reg:CC FLAGS_REG))]
7138 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7140 [(set_attr "type" "imul")
7141 (set_attr "length_immediate" "0")
7142 (set (attr "athlon_decode")
7143 (if_then_else (eq_attr "cpu" "athlon")
7144 (const_string "vector")
7145 (const_string "double")))
7146 (set_attr "mode" "DI")])
7148 (define_expand "umulsi3_highpart"
7149 [(parallel [(set (match_operand:SI 0 "register_operand" "")
7152 (mult:DI (zero_extend:DI
7153 (match_operand:SI 1 "nonimmediate_operand" ""))
7155 (match_operand:SI 2 "register_operand" "")))
7157 (clobber (match_scratch:SI 3 ""))
7158 (clobber (reg:CC FLAGS_REG))])]
7162 (define_insn "*umulsi3_highpart_insn"
7163 [(set (match_operand:SI 0 "register_operand" "=d")
7166 (mult:DI (zero_extend:DI
7167 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7169 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7171 (clobber (match_scratch:SI 3 "=1"))
7172 (clobber (reg:CC FLAGS_REG))]
7173 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7175 [(set_attr "type" "imul")
7176 (set_attr "length_immediate" "0")
7177 (set (attr "athlon_decode")
7178 (if_then_else (eq_attr "cpu" "athlon")
7179 (const_string "vector")
7180 (const_string "double")))
7181 (set_attr "mode" "SI")])
7183 (define_insn "*umulsi3_highpart_zext"
7184 [(set (match_operand:DI 0 "register_operand" "=d")
7185 (zero_extend:DI (truncate:SI
7187 (mult:DI (zero_extend:DI
7188 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7190 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7192 (clobber (match_scratch:SI 3 "=1"))
7193 (clobber (reg:CC FLAGS_REG))]
7195 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7197 [(set_attr "type" "imul")
7198 (set_attr "length_immediate" "0")
7199 (set (attr "athlon_decode")
7200 (if_then_else (eq_attr "cpu" "athlon")
7201 (const_string "vector")
7202 (const_string "double")))
7203 (set_attr "mode" "SI")])
7205 (define_expand "smuldi3_highpart"
7206 [(parallel [(set (match_operand:DI 0 "register_operand" "=d")
7209 (mult:TI (sign_extend:TI
7210 (match_operand:DI 1 "nonimmediate_operand" ""))
7212 (match_operand:DI 2 "register_operand" "")))
7214 (clobber (match_scratch:DI 3 ""))
7215 (clobber (reg:CC FLAGS_REG))])]
7219 (define_insn "*smuldi3_highpart_rex64"
7220 [(set (match_operand:DI 0 "register_operand" "=d")
7223 (mult:TI (sign_extend:TI
7224 (match_operand:DI 1 "nonimmediate_operand" "%a"))
7226 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7228 (clobber (match_scratch:DI 3 "=1"))
7229 (clobber (reg:CC FLAGS_REG))]
7231 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7233 [(set_attr "type" "imul")
7234 (set (attr "athlon_decode")
7235 (if_then_else (eq_attr "cpu" "athlon")
7236 (const_string "vector")
7237 (const_string "double")))
7238 (set_attr "mode" "DI")])
7240 (define_expand "smulsi3_highpart"
7241 [(parallel [(set (match_operand:SI 0 "register_operand" "")
7244 (mult:DI (sign_extend:DI
7245 (match_operand:SI 1 "nonimmediate_operand" ""))
7247 (match_operand:SI 2 "register_operand" "")))
7249 (clobber (match_scratch:SI 3 ""))
7250 (clobber (reg:CC FLAGS_REG))])]
7254 (define_insn "*smulsi3_highpart_insn"
7255 [(set (match_operand:SI 0 "register_operand" "=d")
7258 (mult:DI (sign_extend:DI
7259 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7261 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7263 (clobber (match_scratch:SI 3 "=1"))
7264 (clobber (reg:CC FLAGS_REG))]
7265 "GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM"
7267 [(set_attr "type" "imul")
7268 (set (attr "athlon_decode")
7269 (if_then_else (eq_attr "cpu" "athlon")
7270 (const_string "vector")
7271 (const_string "double")))
7272 (set_attr "mode" "SI")])
7274 (define_insn "*smulsi3_highpart_zext"
7275 [(set (match_operand:DI 0 "register_operand" "=d")
7276 (zero_extend:DI (truncate:SI
7278 (mult:DI (sign_extend:DI
7279 (match_operand:SI 1 "nonimmediate_operand" "%a"))
7281 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7283 (clobber (match_scratch:SI 3 "=1"))
7284 (clobber (reg:CC FLAGS_REG))]
7286 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
7288 [(set_attr "type" "imul")
7289 (set (attr "athlon_decode")
7290 (if_then_else (eq_attr "cpu" "athlon")
7291 (const_string "vector")
7292 (const_string "double")))
7293 (set_attr "mode" "SI")])
7295 ;; The patterns that match these are at the end of this file.
7297 (define_expand "mulxf3"
7298 [(set (match_operand:XF 0 "register_operand" "")
7299 (mult:XF (match_operand:XF 1 "register_operand" "")
7300 (match_operand:XF 2 "register_operand" "")))]
7304 (define_expand "muldf3"
7305 [(set (match_operand:DF 0 "register_operand" "")
7306 (mult:DF (match_operand:DF 1 "register_operand" "")
7307 (match_operand:DF 2 "nonimmediate_operand" "")))]
7308 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
7311 (define_expand "mulsf3"
7312 [(set (match_operand:SF 0 "register_operand" "")
7313 (mult:SF (match_operand:SF 1 "register_operand" "")
7314 (match_operand:SF 2 "nonimmediate_operand" "")))]
7315 "TARGET_80387 || TARGET_SSE_MATH"
7318 ;; Divide instructions
7320 (define_insn "divqi3"
7321 [(set (match_operand:QI 0 "register_operand" "=a")
7322 (div:QI (match_operand:HI 1 "register_operand" "0")
7323 (match_operand:QI 2 "nonimmediate_operand" "qm")))
7324 (clobber (reg:CC FLAGS_REG))]
7325 "TARGET_QIMODE_MATH"
7327 [(set_attr "type" "idiv")
7328 (set_attr "mode" "QI")])
7330 (define_insn "udivqi3"
7331 [(set (match_operand:QI 0 "register_operand" "=a")
7332 (udiv:QI (match_operand:HI 1 "register_operand" "0")
7333 (match_operand:QI 2 "nonimmediate_operand" "qm")))
7334 (clobber (reg:CC FLAGS_REG))]
7335 "TARGET_QIMODE_MATH"
7337 [(set_attr "type" "idiv")
7338 (set_attr "mode" "QI")])
7340 ;; The patterns that match these are at the end of this file.
7342 (define_expand "divxf3"
7343 [(set (match_operand:XF 0 "register_operand" "")
7344 (div:XF (match_operand:XF 1 "register_operand" "")
7345 (match_operand:XF 2 "register_operand" "")))]
7349 (define_expand "divdf3"
7350 [(set (match_operand:DF 0 "register_operand" "")
7351 (div:DF (match_operand:DF 1 "register_operand" "")
7352 (match_operand:DF 2 "nonimmediate_operand" "")))]
7353 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
7356 (define_expand "divsf3"
7357 [(set (match_operand:SF 0 "register_operand" "")
7358 (div:SF (match_operand:SF 1 "register_operand" "")
7359 (match_operand:SF 2 "nonimmediate_operand" "")))]
7360 "TARGET_80387 || TARGET_SSE_MATH"
7363 ;; Remainder instructions.
7365 (define_expand "divmoddi4"
7366 [(parallel [(set (match_operand:DI 0 "register_operand" "")
7367 (div:DI (match_operand:DI 1 "register_operand" "")
7368 (match_operand:DI 2 "nonimmediate_operand" "")))
7369 (set (match_operand:DI 3 "register_operand" "")
7370 (mod:DI (match_dup 1) (match_dup 2)))
7371 (clobber (reg:CC FLAGS_REG))])]
7375 ;; Allow to come the parameter in eax or edx to avoid extra moves.
7376 ;; Penalize eax case slightly because it results in worse scheduling
7378 (define_insn "*divmoddi4_nocltd_rex64"
7379 [(set (match_operand:DI 0 "register_operand" "=&a,?a")
7380 (div:DI (match_operand:DI 2 "register_operand" "1,0")
7381 (match_operand:DI 3 "nonimmediate_operand" "rm,rm")))
7382 (set (match_operand:DI 1 "register_operand" "=&d,&d")
7383 (mod:DI (match_dup 2) (match_dup 3)))
7384 (clobber (reg:CC FLAGS_REG))]
7385 "TARGET_64BIT && !optimize_size && !TARGET_USE_CLTD"
7387 [(set_attr "type" "multi")])
7389 (define_insn "*divmoddi4_cltd_rex64"
7390 [(set (match_operand:DI 0 "register_operand" "=a")
7391 (div:DI (match_operand:DI 2 "register_operand" "a")
7392 (match_operand:DI 3 "nonimmediate_operand" "rm")))
7393 (set (match_operand:DI 1 "register_operand" "=&d")
7394 (mod:DI (match_dup 2) (match_dup 3)))
7395 (clobber (reg:CC FLAGS_REG))]
7396 "TARGET_64BIT && (optimize_size || TARGET_USE_CLTD)"
7398 [(set_attr "type" "multi")])
7400 (define_insn "*divmoddi_noext_rex64"
7401 [(set (match_operand:DI 0 "register_operand" "=a")
7402 (div:DI (match_operand:DI 1 "register_operand" "0")
7403 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7404 (set (match_operand:DI 3 "register_operand" "=d")
7405 (mod:DI (match_dup 1) (match_dup 2)))
7406 (use (match_operand:DI 4 "register_operand" "3"))
7407 (clobber (reg:CC FLAGS_REG))]
7410 [(set_attr "type" "idiv")
7411 (set_attr "mode" "DI")])
7414 [(set (match_operand:DI 0 "register_operand" "")
7415 (div:DI (match_operand:DI 1 "register_operand" "")
7416 (match_operand:DI 2 "nonimmediate_operand" "")))
7417 (set (match_operand:DI 3 "register_operand" "")
7418 (mod:DI (match_dup 1) (match_dup 2)))
7419 (clobber (reg:CC FLAGS_REG))]
7420 "TARGET_64BIT && reload_completed"
7421 [(parallel [(set (match_dup 3)
7422 (ashiftrt:DI (match_dup 4) (const_int 63)))
7423 (clobber (reg:CC FLAGS_REG))])
7424 (parallel [(set (match_dup 0)
7425 (div:DI (reg:DI 0) (match_dup 2)))
7427 (mod:DI (reg:DI 0) (match_dup 2)))
7429 (clobber (reg:CC FLAGS_REG))])]
7431 /* Avoid use of cltd in favor of a mov+shift. */
7432 if (!TARGET_USE_CLTD && !optimize_size)
7434 if (true_regnum (operands[1]))
7435 emit_move_insn (operands[0], operands[1]);
7437 emit_move_insn (operands[3], operands[1]);
7438 operands[4] = operands[3];
7442 gcc_assert (!true_regnum (operands[1]));
7443 operands[4] = operands[1];
7448 (define_expand "divmodsi4"
7449 [(parallel [(set (match_operand:SI 0 "register_operand" "")
7450 (div:SI (match_operand:SI 1 "register_operand" "")
7451 (match_operand:SI 2 "nonimmediate_operand" "")))
7452 (set (match_operand:SI 3 "register_operand" "")
7453 (mod:SI (match_dup 1) (match_dup 2)))
7454 (clobber (reg:CC FLAGS_REG))])]
7458 ;; Allow to come the parameter in eax or edx to avoid extra moves.
7459 ;; Penalize eax case slightly because it results in worse scheduling
7461 (define_insn "*divmodsi4_nocltd"
7462 [(set (match_operand:SI 0 "register_operand" "=&a,?a")
7463 (div:SI (match_operand:SI 2 "register_operand" "1,0")
7464 (match_operand:SI 3 "nonimmediate_operand" "rm,rm")))
7465 (set (match_operand:SI 1 "register_operand" "=&d,&d")
7466 (mod:SI (match_dup 2) (match_dup 3)))
7467 (clobber (reg:CC FLAGS_REG))]
7468 "!optimize_size && !TARGET_USE_CLTD"
7470 [(set_attr "type" "multi")])
7472 (define_insn "*divmodsi4_cltd"
7473 [(set (match_operand:SI 0 "register_operand" "=a")
7474 (div:SI (match_operand:SI 2 "register_operand" "a")
7475 (match_operand:SI 3 "nonimmediate_operand" "rm")))
7476 (set (match_operand:SI 1 "register_operand" "=&d")
7477 (mod:SI (match_dup 2) (match_dup 3)))
7478 (clobber (reg:CC FLAGS_REG))]
7479 "optimize_size || TARGET_USE_CLTD"
7481 [(set_attr "type" "multi")])
7483 (define_insn "*divmodsi_noext"
7484 [(set (match_operand:SI 0 "register_operand" "=a")
7485 (div:SI (match_operand:SI 1 "register_operand" "0")
7486 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7487 (set (match_operand:SI 3 "register_operand" "=d")
7488 (mod:SI (match_dup 1) (match_dup 2)))
7489 (use (match_operand:SI 4 "register_operand" "3"))
7490 (clobber (reg:CC FLAGS_REG))]
7493 [(set_attr "type" "idiv")
7494 (set_attr "mode" "SI")])
7497 [(set (match_operand:SI 0 "register_operand" "")
7498 (div:SI (match_operand:SI 1 "register_operand" "")
7499 (match_operand:SI 2 "nonimmediate_operand" "")))
7500 (set (match_operand:SI 3 "register_operand" "")
7501 (mod:SI (match_dup 1) (match_dup 2)))
7502 (clobber (reg:CC FLAGS_REG))]
7504 [(parallel [(set (match_dup 3)
7505 (ashiftrt:SI (match_dup 4) (const_int 31)))
7506 (clobber (reg:CC FLAGS_REG))])
7507 (parallel [(set (match_dup 0)
7508 (div:SI (reg:SI 0) (match_dup 2)))
7510 (mod:SI (reg:SI 0) (match_dup 2)))
7512 (clobber (reg:CC FLAGS_REG))])]
7514 /* Avoid use of cltd in favor of a mov+shift. */
7515 if (!TARGET_USE_CLTD && !optimize_size)
7517 if (true_regnum (operands[1]))
7518 emit_move_insn (operands[0], operands[1]);
7520 emit_move_insn (operands[3], operands[1]);
7521 operands[4] = operands[3];
7525 gcc_assert (!true_regnum (operands[1]));
7526 operands[4] = operands[1];
7530 (define_insn "divmodhi4"
7531 [(set (match_operand:HI 0 "register_operand" "=a")
7532 (div:HI (match_operand:HI 1 "register_operand" "0")
7533 (match_operand:HI 2 "nonimmediate_operand" "rm")))
7534 (set (match_operand:HI 3 "register_operand" "=&d")
7535 (mod:HI (match_dup 1) (match_dup 2)))
7536 (clobber (reg:CC FLAGS_REG))]
7537 "TARGET_HIMODE_MATH"
7539 [(set_attr "type" "multi")
7540 (set_attr "length_immediate" "0")
7541 (set_attr "mode" "SI")])
7543 (define_insn "udivmoddi4"
7544 [(set (match_operand:DI 0 "register_operand" "=a")
7545 (udiv:DI (match_operand:DI 1 "register_operand" "0")
7546 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7547 (set (match_operand:DI 3 "register_operand" "=&d")
7548 (umod:DI (match_dup 1) (match_dup 2)))
7549 (clobber (reg:CC FLAGS_REG))]
7551 "xor{q}\t%3, %3\;div{q}\t%2"
7552 [(set_attr "type" "multi")
7553 (set_attr "length_immediate" "0")
7554 (set_attr "mode" "DI")])
7556 (define_insn "*udivmoddi4_noext"
7557 [(set (match_operand:DI 0 "register_operand" "=a")
7558 (udiv:DI (match_operand:DI 1 "register_operand" "0")
7559 (match_operand:DI 2 "nonimmediate_operand" "rm")))
7560 (set (match_operand:DI 3 "register_operand" "=d")
7561 (umod:DI (match_dup 1) (match_dup 2)))
7563 (clobber (reg:CC FLAGS_REG))]
7566 [(set_attr "type" "idiv")
7567 (set_attr "mode" "DI")])
7570 [(set (match_operand:DI 0 "register_operand" "")
7571 (udiv:DI (match_operand:DI 1 "register_operand" "")
7572 (match_operand:DI 2 "nonimmediate_operand" "")))
7573 (set (match_operand:DI 3 "register_operand" "")
7574 (umod:DI (match_dup 1) (match_dup 2)))
7575 (clobber (reg:CC FLAGS_REG))]
7576 "TARGET_64BIT && reload_completed"
7577 [(set (match_dup 3) (const_int 0))
7578 (parallel [(set (match_dup 0)
7579 (udiv:DI (match_dup 1) (match_dup 2)))
7581 (umod:DI (match_dup 1) (match_dup 2)))
7583 (clobber (reg:CC FLAGS_REG))])]
7586 (define_insn "udivmodsi4"
7587 [(set (match_operand:SI 0 "register_operand" "=a")
7588 (udiv:SI (match_operand:SI 1 "register_operand" "0")
7589 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7590 (set (match_operand:SI 3 "register_operand" "=&d")
7591 (umod:SI (match_dup 1) (match_dup 2)))
7592 (clobber (reg:CC FLAGS_REG))]
7594 "xor{l}\t%3, %3\;div{l}\t%2"
7595 [(set_attr "type" "multi")
7596 (set_attr "length_immediate" "0")
7597 (set_attr "mode" "SI")])
7599 (define_insn "*udivmodsi4_noext"
7600 [(set (match_operand:SI 0 "register_operand" "=a")
7601 (udiv:SI (match_operand:SI 1 "register_operand" "0")
7602 (match_operand:SI 2 "nonimmediate_operand" "rm")))
7603 (set (match_operand:SI 3 "register_operand" "=d")
7604 (umod:SI (match_dup 1) (match_dup 2)))
7606 (clobber (reg:CC FLAGS_REG))]
7609 [(set_attr "type" "idiv")
7610 (set_attr "mode" "SI")])
7613 [(set (match_operand:SI 0 "register_operand" "")
7614 (udiv:SI (match_operand:SI 1 "register_operand" "")
7615 (match_operand:SI 2 "nonimmediate_operand" "")))
7616 (set (match_operand:SI 3 "register_operand" "")
7617 (umod:SI (match_dup 1) (match_dup 2)))
7618 (clobber (reg:CC FLAGS_REG))]
7620 [(set (match_dup 3) (const_int 0))
7621 (parallel [(set (match_dup 0)
7622 (udiv:SI (match_dup 1) (match_dup 2)))
7624 (umod:SI (match_dup 1) (match_dup 2)))
7626 (clobber (reg:CC FLAGS_REG))])]
7629 (define_expand "udivmodhi4"
7630 [(set (match_dup 4) (const_int 0))
7631 (parallel [(set (match_operand:HI 0 "register_operand" "")
7632 (udiv:HI (match_operand:HI 1 "register_operand" "")
7633 (match_operand:HI 2 "nonimmediate_operand" "")))
7634 (set (match_operand:HI 3 "register_operand" "")
7635 (umod:HI (match_dup 1) (match_dup 2)))
7637 (clobber (reg:CC FLAGS_REG))])]
7638 "TARGET_HIMODE_MATH"
7639 "operands[4] = gen_reg_rtx (HImode);")
7641 (define_insn "*udivmodhi_noext"
7642 [(set (match_operand:HI 0 "register_operand" "=a")
7643 (udiv:HI (match_operand:HI 1 "register_operand" "0")
7644 (match_operand:HI 2 "nonimmediate_operand" "rm")))
7645 (set (match_operand:HI 3 "register_operand" "=d")
7646 (umod:HI (match_dup 1) (match_dup 2)))
7647 (use (match_operand:HI 4 "register_operand" "3"))
7648 (clobber (reg:CC FLAGS_REG))]
7651 [(set_attr "type" "idiv")
7652 (set_attr "mode" "HI")])
7654 ;; We cannot use div/idiv for double division, because it causes
7655 ;; "division by zero" on the overflow and that's not what we expect
7656 ;; from truncate. Because true (non truncating) double division is
7657 ;; never generated, we can't create this insn anyway.
7660 ; [(set (match_operand:SI 0 "register_operand" "=a")
7662 ; (udiv:DI (match_operand:DI 1 "register_operand" "A")
7664 ; (match_operand:SI 2 "nonimmediate_operand" "rm")))))
7665 ; (set (match_operand:SI 3 "register_operand" "=d")
7667 ; (umod:DI (match_dup 1) (zero_extend:DI (match_dup 2)))))
7668 ; (clobber (reg:CC FLAGS_REG))]
7670 ; "div{l}\t{%2, %0|%0, %2}"
7671 ; [(set_attr "type" "idiv")])
7673 ;;- Logical AND instructions
7675 ;; On Pentium, "test imm, reg" is pairable only with eax, ax, and al.
7676 ;; Note that this excludes ah.
7678 (define_insn "*testdi_1_rex64"
7679 [(set (reg FLAGS_REG)
7681 (and:DI (match_operand:DI 0 "nonimmediate_operand" "%!*a,r,!*a,r,rm")
7682 (match_operand:DI 1 "x86_64_szext_general_operand" "Z,Z,e,e,re"))
7684 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7685 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7687 test{l}\t{%k1, %k0|%k0, %k1}
7688 test{l}\t{%k1, %k0|%k0, %k1}
7689 test{q}\t{%1, %0|%0, %1}
7690 test{q}\t{%1, %0|%0, %1}
7691 test{q}\t{%1, %0|%0, %1}"
7692 [(set_attr "type" "test")
7693 (set_attr "modrm" "0,1,0,1,1")
7694 (set_attr "mode" "SI,SI,DI,DI,DI")
7695 (set_attr "pent_pair" "uv,np,uv,np,uv")])
7697 (define_insn "testsi_1"
7698 [(set (reg FLAGS_REG)
7700 (and:SI (match_operand:SI 0 "nonimmediate_operand" "%!*a,r,rm")
7701 (match_operand:SI 1 "general_operand" "in,in,rin"))
7703 "ix86_match_ccmode (insn, CCNOmode)
7704 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7705 "test{l}\t{%1, %0|%0, %1}"
7706 [(set_attr "type" "test")
7707 (set_attr "modrm" "0,1,1")
7708 (set_attr "mode" "SI")
7709 (set_attr "pent_pair" "uv,np,uv")])
7711 (define_expand "testsi_ccno_1"
7712 [(set (reg:CCNO FLAGS_REG)
7714 (and:SI (match_operand:SI 0 "nonimmediate_operand" "")
7715 (match_operand:SI 1 "nonmemory_operand" ""))
7720 (define_insn "*testhi_1"
7721 [(set (reg FLAGS_REG)
7722 (compare (and:HI (match_operand:HI 0 "nonimmediate_operand" "%!*a,r,rm")
7723 (match_operand:HI 1 "general_operand" "n,n,rn"))
7725 "ix86_match_ccmode (insn, CCNOmode)
7726 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7727 "test{w}\t{%1, %0|%0, %1}"
7728 [(set_attr "type" "test")
7729 (set_attr "modrm" "0,1,1")
7730 (set_attr "mode" "HI")
7731 (set_attr "pent_pair" "uv,np,uv")])
7733 (define_expand "testqi_ccz_1"
7734 [(set (reg:CCZ FLAGS_REG)
7735 (compare:CCZ (and:QI (match_operand:QI 0 "nonimmediate_operand" "")
7736 (match_operand:QI 1 "nonmemory_operand" ""))
7741 (define_insn "*testqi_1_maybe_si"
7742 [(set (reg FLAGS_REG)
7745 (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm,r")
7746 (match_operand:QI 1 "general_operand" "n,n,qn,n"))
7748 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
7749 && ix86_match_ccmode (insn,
7750 GET_CODE (operands[1]) == CONST_INT
7751 && INTVAL (operands[1]) >= 0 ? CCNOmode : CCZmode)"
7753 if (which_alternative == 3)
7755 if (GET_CODE (operands[1]) == CONST_INT && INTVAL (operands[1]) < 0)
7756 operands[1] = GEN_INT (INTVAL (operands[1]) & 0xff);
7757 return "test{l}\t{%1, %k0|%k0, %1}";
7759 return "test{b}\t{%1, %0|%0, %1}";
7761 [(set_attr "type" "test")
7762 (set_attr "modrm" "0,1,1,1")
7763 (set_attr "mode" "QI,QI,QI,SI")
7764 (set_attr "pent_pair" "uv,np,uv,np")])
7766 (define_insn "*testqi_1"
7767 [(set (reg FLAGS_REG)
7770 (match_operand:QI 0 "nonimmediate_operand" "%!*a,q,qm")
7771 (match_operand:QI 1 "general_operand" "n,n,qn"))
7773 "(GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)
7774 && ix86_match_ccmode (insn, CCNOmode)"
7775 "test{b}\t{%1, %0|%0, %1}"
7776 [(set_attr "type" "test")
7777 (set_attr "modrm" "0,1,1")
7778 (set_attr "mode" "QI")
7779 (set_attr "pent_pair" "uv,np,uv")])
7781 (define_expand "testqi_ext_ccno_0"
7782 [(set (reg:CCNO FLAGS_REG)
7786 (match_operand 0 "ext_register_operand" "")
7789 (match_operand 1 "const_int_operand" ""))
7794 (define_insn "*testqi_ext_0"
7795 [(set (reg FLAGS_REG)
7799 (match_operand 0 "ext_register_operand" "Q")
7802 (match_operand 1 "const_int_operand" "n"))
7804 "ix86_match_ccmode (insn, CCNOmode)"
7805 "test{b}\t{%1, %h0|%h0, %1}"
7806 [(set_attr "type" "test")
7807 (set_attr "mode" "QI")
7808 (set_attr "length_immediate" "1")
7809 (set_attr "pent_pair" "np")])
7811 (define_insn "*testqi_ext_1"
7812 [(set (reg FLAGS_REG)
7816 (match_operand 0 "ext_register_operand" "Q")
7820 (match_operand:QI 1 "general_operand" "Qm")))
7822 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
7823 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
7824 "test{b}\t{%1, %h0|%h0, %1}"
7825 [(set_attr "type" "test")
7826 (set_attr "mode" "QI")])
7828 (define_insn "*testqi_ext_1_rex64"
7829 [(set (reg FLAGS_REG)
7833 (match_operand 0 "ext_register_operand" "Q")
7837 (match_operand:QI 1 "register_operand" "Q")))
7839 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
7840 "test{b}\t{%1, %h0|%h0, %1}"
7841 [(set_attr "type" "test")
7842 (set_attr "mode" "QI")])
7844 (define_insn "*testqi_ext_2"
7845 [(set (reg FLAGS_REG)
7849 (match_operand 0 "ext_register_operand" "Q")
7853 (match_operand 1 "ext_register_operand" "Q")
7857 "ix86_match_ccmode (insn, CCNOmode)"
7858 "test{b}\t{%h1, %h0|%h0, %h1}"
7859 [(set_attr "type" "test")
7860 (set_attr "mode" "QI")])
7862 ;; Combine likes to form bit extractions for some tests. Humor it.
7863 (define_insn "*testqi_ext_3"
7864 [(set (reg FLAGS_REG)
7865 (compare (zero_extract:SI
7866 (match_operand 0 "nonimmediate_operand" "rm")
7867 (match_operand:SI 1 "const_int_operand" "")
7868 (match_operand:SI 2 "const_int_operand" ""))
7870 "ix86_match_ccmode (insn, CCNOmode)
7871 && INTVAL (operands[1]) > 0
7872 && INTVAL (operands[2]) >= 0
7873 && INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7874 && (GET_MODE (operands[0]) == SImode
7875 || (TARGET_64BIT && GET_MODE (operands[0]) == DImode)
7876 || GET_MODE (operands[0]) == HImode
7877 || GET_MODE (operands[0]) == QImode)"
7880 (define_insn "*testqi_ext_3_rex64"
7881 [(set (reg FLAGS_REG)
7882 (compare (zero_extract:DI
7883 (match_operand 0 "nonimmediate_operand" "rm")
7884 (match_operand:DI 1 "const_int_operand" "")
7885 (match_operand:DI 2 "const_int_operand" ""))
7888 && ix86_match_ccmode (insn, CCNOmode)
7889 && INTVAL (operands[1]) > 0
7890 && INTVAL (operands[2]) >= 0
7891 /* Ensure that resulting mask is zero or sign extended operand. */
7892 && (INTVAL (operands[1]) + INTVAL (operands[2]) <= 32
7893 || (INTVAL (operands[1]) + INTVAL (operands[2]) == 64
7894 && INTVAL (operands[1]) > 32))
7895 && (GET_MODE (operands[0]) == SImode
7896 || GET_MODE (operands[0]) == DImode
7897 || GET_MODE (operands[0]) == HImode
7898 || GET_MODE (operands[0]) == QImode)"
7902 [(set (match_operand 0 "flags_reg_operand" "")
7903 (match_operator 1 "compare_operator"
7905 (match_operand 2 "nonimmediate_operand" "")
7906 (match_operand 3 "const_int_operand" "")
7907 (match_operand 4 "const_int_operand" ""))
7909 "ix86_match_ccmode (insn, CCNOmode)"
7910 [(set (match_dup 0) (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
7912 rtx val = operands[2];
7913 HOST_WIDE_INT len = INTVAL (operands[3]);
7914 HOST_WIDE_INT pos = INTVAL (operands[4]);
7916 enum machine_mode mode, submode;
7918 mode = GET_MODE (val);
7919 if (GET_CODE (val) == MEM)
7921 /* ??? Combine likes to put non-volatile mem extractions in QImode
7922 no matter the size of the test. So find a mode that works. */
7923 if (! MEM_VOLATILE_P (val))
7925 mode = smallest_mode_for_size (pos + len, MODE_INT);
7926 val = adjust_address (val, mode, 0);
7929 else if (GET_CODE (val) == SUBREG
7930 && (submode = GET_MODE (SUBREG_REG (val)),
7931 GET_MODE_BITSIZE (mode) > GET_MODE_BITSIZE (submode))
7932 && pos + len <= GET_MODE_BITSIZE (submode))
7934 /* Narrow a paradoxical subreg to prevent partial register stalls. */
7936 val = SUBREG_REG (val);
7938 else if (mode == HImode && pos + len <= 8)
7940 /* Small HImode tests can be converted to QImode. */
7942 val = gen_lowpart (QImode, val);
7945 if (len == HOST_BITS_PER_WIDE_INT)
7948 mask = ((HOST_WIDE_INT)1 << len) - 1;
7951 operands[2] = gen_rtx_AND (mode, val, gen_int_mode (mask, mode));
7954 ;; Convert HImode/SImode test instructions with immediate to QImode ones.
7955 ;; i386 does not allow to encode test with 8bit sign extended immediate, so
7956 ;; this is relatively important trick.
7957 ;; Do the conversion only post-reload to avoid limiting of the register class
7960 [(set (match_operand 0 "flags_reg_operand" "")
7961 (match_operator 1 "compare_operator"
7962 [(and (match_operand 2 "register_operand" "")
7963 (match_operand 3 "const_int_operand" ""))
7966 && QI_REG_P (operands[2])
7967 && GET_MODE (operands[2]) != QImode
7968 && ((ix86_match_ccmode (insn, CCZmode)
7969 && !(INTVAL (operands[3]) & ~(255 << 8)))
7970 || (ix86_match_ccmode (insn, CCNOmode)
7971 && !(INTVAL (operands[3]) & ~(127 << 8))))"
7974 [(and:SI (zero_extract:SI (match_dup 2) (const_int 8) (const_int 8))
7977 "operands[2] = gen_lowpart (SImode, operands[2]);
7978 operands[3] = gen_int_mode (INTVAL (operands[3]) >> 8, SImode);")
7981 [(set (match_operand 0 "flags_reg_operand" "")
7982 (match_operator 1 "compare_operator"
7983 [(and (match_operand 2 "nonimmediate_operand" "")
7984 (match_operand 3 "const_int_operand" ""))
7987 && GET_MODE (operands[2]) != QImode
7988 && (!REG_P (operands[2]) || ANY_QI_REG_P (operands[2]))
7989 && ((ix86_match_ccmode (insn, CCZmode)
7990 && !(INTVAL (operands[3]) & ~255))
7991 || (ix86_match_ccmode (insn, CCNOmode)
7992 && !(INTVAL (operands[3]) & ~127)))"
7994 (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
7996 "operands[2] = gen_lowpart (QImode, operands[2]);
7997 operands[3] = gen_lowpart (QImode, operands[3]);")
8000 ;; %%% This used to optimize known byte-wide and operations to memory,
8001 ;; and sometimes to QImode registers. If this is considered useful,
8002 ;; it should be done with splitters.
8004 (define_expand "anddi3"
8005 [(set (match_operand:DI 0 "nonimmediate_operand" "")
8006 (and:DI (match_operand:DI 1 "nonimmediate_operand" "")
8007 (match_operand:DI 2 "x86_64_szext_general_operand" "")))
8008 (clobber (reg:CC FLAGS_REG))]
8010 "ix86_expand_binary_operator (AND, DImode, operands); DONE;")
8012 (define_insn "*anddi_1_rex64"
8013 [(set (match_operand:DI 0 "nonimmediate_operand" "=r,rm,r,r")
8014 (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0,qm")
8015 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,re,rm,L")))
8016 (clobber (reg:CC FLAGS_REG))]
8017 "TARGET_64BIT && ix86_binary_operator_ok (AND, DImode, operands)"
8019 switch (get_attr_type (insn))
8023 enum machine_mode mode;
8025 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
8026 if (INTVAL (operands[2]) == 0xff)
8030 gcc_assert (INTVAL (operands[2]) == 0xffff);
8034 operands[1] = gen_lowpart (mode, operands[1]);
8036 return "movz{bq|x}\t{%1,%0|%0, %1}";
8038 return "movz{wq|x}\t{%1,%0|%0, %1}";
8042 gcc_assert (rtx_equal_p (operands[0], operands[1]));
8043 if (get_attr_mode (insn) == MODE_SI)
8044 return "and{l}\t{%k2, %k0|%k0, %k2}";
8046 return "and{q}\t{%2, %0|%0, %2}";
8049 [(set_attr "type" "alu,alu,alu,imovx")
8050 (set_attr "length_immediate" "*,*,*,0")
8051 (set_attr "mode" "SI,DI,DI,DI")])
8053 (define_insn "*anddi_2"
8054 [(set (reg FLAGS_REG)
8055 (compare (and:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0,0")
8056 (match_operand:DI 2 "x86_64_szext_general_operand" "Z,rem,re"))
8058 (set (match_operand:DI 0 "nonimmediate_operand" "=r,r,rm")
8059 (and:DI (match_dup 1) (match_dup 2)))]
8060 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8061 && ix86_binary_operator_ok (AND, DImode, operands)"
8063 and{l}\t{%k2, %k0|%k0, %k2}
8064 and{q}\t{%2, %0|%0, %2}
8065 and{q}\t{%2, %0|%0, %2}"
8066 [(set_attr "type" "alu")
8067 (set_attr "mode" "SI,DI,DI")])
8069 (define_expand "andsi3"
8070 [(set (match_operand:SI 0 "nonimmediate_operand" "")
8071 (and:SI (match_operand:SI 1 "nonimmediate_operand" "")
8072 (match_operand:SI 2 "general_operand" "")))
8073 (clobber (reg:CC FLAGS_REG))]
8075 "ix86_expand_binary_operator (AND, SImode, operands); DONE;")
8077 (define_insn "*andsi_1"
8078 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r,r")
8079 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0,qm")
8080 (match_operand:SI 2 "general_operand" "ri,rm,L")))
8081 (clobber (reg:CC FLAGS_REG))]
8082 "ix86_binary_operator_ok (AND, SImode, operands)"
8084 switch (get_attr_type (insn))
8088 enum machine_mode mode;
8090 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
8091 if (INTVAL (operands[2]) == 0xff)
8095 gcc_assert (INTVAL (operands[2]) == 0xffff);
8099 operands[1] = gen_lowpart (mode, operands[1]);
8101 return "movz{bl|x}\t{%1,%0|%0, %1}";
8103 return "movz{wl|x}\t{%1,%0|%0, %1}";
8107 gcc_assert (rtx_equal_p (operands[0], operands[1]));
8108 return "and{l}\t{%2, %0|%0, %2}";
8111 [(set_attr "type" "alu,alu,imovx")
8112 (set_attr "length_immediate" "*,*,0")
8113 (set_attr "mode" "SI")])
8116 [(set (match_operand 0 "register_operand" "")
8118 (const_int -65536)))
8119 (clobber (reg:CC FLAGS_REG))]
8120 "optimize_size || (TARGET_FAST_PREFIX && !TARGET_PARTIAL_REG_STALL)"
8121 [(set (strict_low_part (match_dup 1)) (const_int 0))]
8122 "operands[1] = gen_lowpart (HImode, operands[0]);")
8125 [(set (match_operand 0 "ext_register_operand" "")
8128 (clobber (reg:CC FLAGS_REG))]
8129 "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8130 [(set (strict_low_part (match_dup 1)) (const_int 0))]
8131 "operands[1] = gen_lowpart (QImode, operands[0]);")
8134 [(set (match_operand 0 "ext_register_operand" "")
8136 (const_int -65281)))
8137 (clobber (reg:CC FLAGS_REG))]
8138 "(optimize_size || !TARGET_PARTIAL_REG_STALL) && reload_completed"
8139 [(parallel [(set (zero_extract:SI (match_dup 0)
8143 (zero_extract:SI (match_dup 0)
8146 (zero_extract:SI (match_dup 0)
8149 (clobber (reg:CC FLAGS_REG))])]
8150 "operands[0] = gen_lowpart (SImode, operands[0]);")
8152 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8153 (define_insn "*andsi_1_zext"
8154 [(set (match_operand:DI 0 "register_operand" "=r")
8156 (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8157 (match_operand:SI 2 "general_operand" "rim"))))
8158 (clobber (reg:CC FLAGS_REG))]
8159 "TARGET_64BIT && ix86_binary_operator_ok (AND, SImode, operands)"
8160 "and{l}\t{%2, %k0|%k0, %2}"
8161 [(set_attr "type" "alu")
8162 (set_attr "mode" "SI")])
8164 (define_insn "*andsi_2"
8165 [(set (reg FLAGS_REG)
8166 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8167 (match_operand:SI 2 "general_operand" "rim,ri"))
8169 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8170 (and:SI (match_dup 1) (match_dup 2)))]
8171 "ix86_match_ccmode (insn, CCNOmode)
8172 && ix86_binary_operator_ok (AND, SImode, operands)"
8173 "and{l}\t{%2, %0|%0, %2}"
8174 [(set_attr "type" "alu")
8175 (set_attr "mode" "SI")])
8177 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8178 (define_insn "*andsi_2_zext"
8179 [(set (reg FLAGS_REG)
8180 (compare (and:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8181 (match_operand:SI 2 "general_operand" "rim"))
8183 (set (match_operand:DI 0 "register_operand" "=r")
8184 (zero_extend:DI (and:SI (match_dup 1) (match_dup 2))))]
8185 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8186 && ix86_binary_operator_ok (AND, SImode, operands)"
8187 "and{l}\t{%2, %k0|%k0, %2}"
8188 [(set_attr "type" "alu")
8189 (set_attr "mode" "SI")])
8191 (define_expand "andhi3"
8192 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8193 (and:HI (match_operand:HI 1 "nonimmediate_operand" "")
8194 (match_operand:HI 2 "general_operand" "")))
8195 (clobber (reg:CC FLAGS_REG))]
8196 "TARGET_HIMODE_MATH"
8197 "ix86_expand_binary_operator (AND, HImode, operands); DONE;")
8199 (define_insn "*andhi_1"
8200 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r")
8201 (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,qm")
8202 (match_operand:HI 2 "general_operand" "ri,rm,L")))
8203 (clobber (reg:CC FLAGS_REG))]
8204 "ix86_binary_operator_ok (AND, HImode, operands)"
8206 switch (get_attr_type (insn))
8209 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
8210 gcc_assert (INTVAL (operands[2]) == 0xff);
8211 return "movz{bl|x}\t{%b1, %k0|%k0, %b1}";
8214 gcc_assert (rtx_equal_p (operands[0], operands[1]));
8216 return "and{w}\t{%2, %0|%0, %2}";
8219 [(set_attr "type" "alu,alu,imovx")
8220 (set_attr "length_immediate" "*,*,0")
8221 (set_attr "mode" "HI,HI,SI")])
8223 (define_insn "*andhi_2"
8224 [(set (reg FLAGS_REG)
8225 (compare (and:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8226 (match_operand:HI 2 "general_operand" "rim,ri"))
8228 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8229 (and:HI (match_dup 1) (match_dup 2)))]
8230 "ix86_match_ccmode (insn, CCNOmode)
8231 && ix86_binary_operator_ok (AND, HImode, operands)"
8232 "and{w}\t{%2, %0|%0, %2}"
8233 [(set_attr "type" "alu")
8234 (set_attr "mode" "HI")])
8236 (define_expand "andqi3"
8237 [(set (match_operand:QI 0 "nonimmediate_operand" "")
8238 (and:QI (match_operand:QI 1 "nonimmediate_operand" "")
8239 (match_operand:QI 2 "general_operand" "")))
8240 (clobber (reg:CC FLAGS_REG))]
8241 "TARGET_QIMODE_MATH"
8242 "ix86_expand_binary_operator (AND, QImode, operands); DONE;")
8244 ;; %%% Potential partial reg stall on alternative 2. What to do?
8245 (define_insn "*andqi_1"
8246 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
8247 (and:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8248 (match_operand:QI 2 "general_operand" "qi,qmi,ri")))
8249 (clobber (reg:CC FLAGS_REG))]
8250 "ix86_binary_operator_ok (AND, QImode, operands)"
8252 and{b}\t{%2, %0|%0, %2}
8253 and{b}\t{%2, %0|%0, %2}
8254 and{l}\t{%k2, %k0|%k0, %k2}"
8255 [(set_attr "type" "alu")
8256 (set_attr "mode" "QI,QI,SI")])
8258 (define_insn "*andqi_1_slp"
8259 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
8260 (and:QI (match_dup 0)
8261 (match_operand:QI 1 "general_operand" "qi,qmi")))
8262 (clobber (reg:CC FLAGS_REG))]
8263 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8264 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8265 "and{b}\t{%1, %0|%0, %1}"
8266 [(set_attr "type" "alu1")
8267 (set_attr "mode" "QI")])
8269 (define_insn "*andqi_2_maybe_si"
8270 [(set (reg FLAGS_REG)
8272 (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8273 (match_operand:QI 2 "general_operand" "qim,qi,i"))
8275 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,*r")
8276 (and:QI (match_dup 1) (match_dup 2)))]
8277 "ix86_binary_operator_ok (AND, QImode, operands)
8278 && ix86_match_ccmode (insn,
8279 GET_CODE (operands[2]) == CONST_INT
8280 && INTVAL (operands[2]) >= 0 ? CCNOmode : CCZmode)"
8282 if (which_alternative == 2)
8284 if (GET_CODE (operands[2]) == CONST_INT && INTVAL (operands[2]) < 0)
8285 operands[2] = GEN_INT (INTVAL (operands[2]) & 0xff);
8286 return "and{l}\t{%2, %k0|%k0, %2}";
8288 return "and{b}\t{%2, %0|%0, %2}";
8290 [(set_attr "type" "alu")
8291 (set_attr "mode" "QI,QI,SI")])
8293 (define_insn "*andqi_2"
8294 [(set (reg FLAGS_REG)
8296 (match_operand:QI 1 "nonimmediate_operand" "%0,0")
8297 (match_operand:QI 2 "general_operand" "qim,qi"))
8299 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
8300 (and:QI (match_dup 1) (match_dup 2)))]
8301 "ix86_match_ccmode (insn, CCNOmode)
8302 && ix86_binary_operator_ok (AND, QImode, operands)"
8303 "and{b}\t{%2, %0|%0, %2}"
8304 [(set_attr "type" "alu")
8305 (set_attr "mode" "QI")])
8307 (define_insn "*andqi_2_slp"
8308 [(set (reg FLAGS_REG)
8310 (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8311 (match_operand:QI 1 "nonimmediate_operand" "qmi,qi"))
8313 (set (strict_low_part (match_dup 0))
8314 (and:QI (match_dup 0) (match_dup 1)))]
8315 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8316 && ix86_match_ccmode (insn, CCNOmode)
8317 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8318 "and{b}\t{%1, %0|%0, %1}"
8319 [(set_attr "type" "alu1")
8320 (set_attr "mode" "QI")])
8322 ;; ??? A bug in recog prevents it from recognizing a const_int as an
8323 ;; operand to zero_extend in andqi_ext_1. It was checking explicitly
8324 ;; for a QImode operand, which of course failed.
8326 (define_insn "andqi_ext_0"
8327 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8332 (match_operand 1 "ext_register_operand" "0")
8335 (match_operand 2 "const_int_operand" "n")))
8336 (clobber (reg:CC FLAGS_REG))]
8338 "and{b}\t{%2, %h0|%h0, %2}"
8339 [(set_attr "type" "alu")
8340 (set_attr "length_immediate" "1")
8341 (set_attr "mode" "QI")])
8343 ;; Generated by peephole translating test to and. This shows up
8344 ;; often in fp comparisons.
8346 (define_insn "*andqi_ext_0_cc"
8347 [(set (reg FLAGS_REG)
8351 (match_operand 1 "ext_register_operand" "0")
8354 (match_operand 2 "const_int_operand" "n"))
8356 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8365 "ix86_match_ccmode (insn, CCNOmode)"
8366 "and{b}\t{%2, %h0|%h0, %2}"
8367 [(set_attr "type" "alu")
8368 (set_attr "length_immediate" "1")
8369 (set_attr "mode" "QI")])
8371 (define_insn "*andqi_ext_1"
8372 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8377 (match_operand 1 "ext_register_operand" "0")
8381 (match_operand:QI 2 "general_operand" "Qm"))))
8382 (clobber (reg:CC FLAGS_REG))]
8384 "and{b}\t{%2, %h0|%h0, %2}"
8385 [(set_attr "type" "alu")
8386 (set_attr "length_immediate" "0")
8387 (set_attr "mode" "QI")])
8389 (define_insn "*andqi_ext_1_rex64"
8390 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8395 (match_operand 1 "ext_register_operand" "0")
8399 (match_operand 2 "ext_register_operand" "Q"))))
8400 (clobber (reg:CC FLAGS_REG))]
8402 "and{b}\t{%2, %h0|%h0, %2}"
8403 [(set_attr "type" "alu")
8404 (set_attr "length_immediate" "0")
8405 (set_attr "mode" "QI")])
8407 (define_insn "*andqi_ext_2"
8408 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8413 (match_operand 1 "ext_register_operand" "%0")
8417 (match_operand 2 "ext_register_operand" "Q")
8420 (clobber (reg:CC FLAGS_REG))]
8422 "and{b}\t{%h2, %h0|%h0, %h2}"
8423 [(set_attr "type" "alu")
8424 (set_attr "length_immediate" "0")
8425 (set_attr "mode" "QI")])
8427 ;; Convert wide AND instructions with immediate operand to shorter QImode
8428 ;; equivalents when possible.
8429 ;; Don't do the splitting with memory operands, since it introduces risk
8430 ;; of memory mismatch stalls. We may want to do the splitting for optimizing
8431 ;; for size, but that can (should?) be handled by generic code instead.
8433 [(set (match_operand 0 "register_operand" "")
8434 (and (match_operand 1 "register_operand" "")
8435 (match_operand 2 "const_int_operand" "")))
8436 (clobber (reg:CC FLAGS_REG))]
8438 && QI_REG_P (operands[0])
8439 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8440 && !(~INTVAL (operands[2]) & ~(255 << 8))
8441 && GET_MODE (operands[0]) != QImode"
8442 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8443 (and:SI (zero_extract:SI (match_dup 1)
8444 (const_int 8) (const_int 8))
8446 (clobber (reg:CC FLAGS_REG))])]
8447 "operands[0] = gen_lowpart (SImode, operands[0]);
8448 operands[1] = gen_lowpart (SImode, operands[1]);
8449 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8451 ;; Since AND can be encoded with sign extended immediate, this is only
8452 ;; profitable when 7th bit is not set.
8454 [(set (match_operand 0 "register_operand" "")
8455 (and (match_operand 1 "general_operand" "")
8456 (match_operand 2 "const_int_operand" "")))
8457 (clobber (reg:CC FLAGS_REG))]
8459 && ANY_QI_REG_P (operands[0])
8460 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8461 && !(~INTVAL (operands[2]) & ~255)
8462 && !(INTVAL (operands[2]) & 128)
8463 && GET_MODE (operands[0]) != QImode"
8464 [(parallel [(set (strict_low_part (match_dup 0))
8465 (and:QI (match_dup 1)
8467 (clobber (reg:CC FLAGS_REG))])]
8468 "operands[0] = gen_lowpart (QImode, operands[0]);
8469 operands[1] = gen_lowpart (QImode, operands[1]);
8470 operands[2] = gen_lowpart (QImode, operands[2]);")
8472 ;; Logical inclusive OR instructions
8474 ;; %%% This used to optimize known byte-wide and operations to memory.
8475 ;; If this is considered useful, it should be done with splitters.
8477 (define_expand "iordi3"
8478 [(set (match_operand:DI 0 "nonimmediate_operand" "")
8479 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "")
8480 (match_operand:DI 2 "x86_64_general_operand" "")))
8481 (clobber (reg:CC FLAGS_REG))]
8483 "ix86_expand_binary_operator (IOR, DImode, operands); DONE;")
8485 (define_insn "*iordi_1_rex64"
8486 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
8487 (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8488 (match_operand:DI 2 "x86_64_general_operand" "re,rme")))
8489 (clobber (reg:CC FLAGS_REG))]
8491 && ix86_binary_operator_ok (IOR, DImode, operands)"
8492 "or{q}\t{%2, %0|%0, %2}"
8493 [(set_attr "type" "alu")
8494 (set_attr "mode" "DI")])
8496 (define_insn "*iordi_2_rex64"
8497 [(set (reg FLAGS_REG)
8498 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8499 (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
8501 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
8502 (ior:DI (match_dup 1) (match_dup 2)))]
8504 && ix86_match_ccmode (insn, CCNOmode)
8505 && ix86_binary_operator_ok (IOR, DImode, operands)"
8506 "or{q}\t{%2, %0|%0, %2}"
8507 [(set_attr "type" "alu")
8508 (set_attr "mode" "DI")])
8510 (define_insn "*iordi_3_rex64"
8511 [(set (reg FLAGS_REG)
8512 (compare (ior:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
8513 (match_operand:DI 2 "x86_64_general_operand" "rem"))
8515 (clobber (match_scratch:DI 0 "=r"))]
8517 && ix86_match_ccmode (insn, CCNOmode)
8518 && ix86_binary_operator_ok (IOR, DImode, operands)"
8519 "or{q}\t{%2, %0|%0, %2}"
8520 [(set_attr "type" "alu")
8521 (set_attr "mode" "DI")])
8524 (define_expand "iorsi3"
8525 [(set (match_operand:SI 0 "nonimmediate_operand" "")
8526 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "")
8527 (match_operand:SI 2 "general_operand" "")))
8528 (clobber (reg:CC FLAGS_REG))]
8530 "ix86_expand_binary_operator (IOR, SImode, operands); DONE;")
8532 (define_insn "*iorsi_1"
8533 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
8534 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8535 (match_operand:SI 2 "general_operand" "ri,rmi")))
8536 (clobber (reg:CC FLAGS_REG))]
8537 "ix86_binary_operator_ok (IOR, SImode, operands)"
8538 "or{l}\t{%2, %0|%0, %2}"
8539 [(set_attr "type" "alu")
8540 (set_attr "mode" "SI")])
8542 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8543 (define_insn "*iorsi_1_zext"
8544 [(set (match_operand:DI 0 "register_operand" "=rm")
8546 (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8547 (match_operand:SI 2 "general_operand" "rim"))))
8548 (clobber (reg:CC FLAGS_REG))]
8549 "TARGET_64BIT && ix86_binary_operator_ok (IOR, SImode, operands)"
8550 "or{l}\t{%2, %k0|%k0, %2}"
8551 [(set_attr "type" "alu")
8552 (set_attr "mode" "SI")])
8554 (define_insn "*iorsi_1_zext_imm"
8555 [(set (match_operand:DI 0 "register_operand" "=rm")
8556 (ior:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8557 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8558 (clobber (reg:CC FLAGS_REG))]
8560 "or{l}\t{%2, %k0|%k0, %2}"
8561 [(set_attr "type" "alu")
8562 (set_attr "mode" "SI")])
8564 (define_insn "*iorsi_2"
8565 [(set (reg FLAGS_REG)
8566 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8567 (match_operand:SI 2 "general_operand" "rim,ri"))
8569 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8570 (ior:SI (match_dup 1) (match_dup 2)))]
8571 "ix86_match_ccmode (insn, CCNOmode)
8572 && ix86_binary_operator_ok (IOR, SImode, operands)"
8573 "or{l}\t{%2, %0|%0, %2}"
8574 [(set_attr "type" "alu")
8575 (set_attr "mode" "SI")])
8577 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8578 ;; ??? Special case for immediate operand is missing - it is tricky.
8579 (define_insn "*iorsi_2_zext"
8580 [(set (reg FLAGS_REG)
8581 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8582 (match_operand:SI 2 "general_operand" "rim"))
8584 (set (match_operand:DI 0 "register_operand" "=r")
8585 (zero_extend:DI (ior:SI (match_dup 1) (match_dup 2))))]
8586 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8587 && ix86_binary_operator_ok (IOR, SImode, operands)"
8588 "or{l}\t{%2, %k0|%k0, %2}"
8589 [(set_attr "type" "alu")
8590 (set_attr "mode" "SI")])
8592 (define_insn "*iorsi_2_zext_imm"
8593 [(set (reg FLAGS_REG)
8594 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8595 (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
8597 (set (match_operand:DI 0 "register_operand" "=r")
8598 (ior:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8599 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8600 && ix86_binary_operator_ok (IOR, SImode, operands)"
8601 "or{l}\t{%2, %k0|%k0, %2}"
8602 [(set_attr "type" "alu")
8603 (set_attr "mode" "SI")])
8605 (define_insn "*iorsi_3"
8606 [(set (reg FLAGS_REG)
8607 (compare (ior:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8608 (match_operand:SI 2 "general_operand" "rim"))
8610 (clobber (match_scratch:SI 0 "=r"))]
8611 "ix86_match_ccmode (insn, CCNOmode)
8612 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8613 "or{l}\t{%2, %0|%0, %2}"
8614 [(set_attr "type" "alu")
8615 (set_attr "mode" "SI")])
8617 (define_expand "iorhi3"
8618 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8619 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "")
8620 (match_operand:HI 2 "general_operand" "")))
8621 (clobber (reg:CC FLAGS_REG))]
8622 "TARGET_HIMODE_MATH"
8623 "ix86_expand_binary_operator (IOR, HImode, operands); DONE;")
8625 (define_insn "*iorhi_1"
8626 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
8627 (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8628 (match_operand:HI 2 "general_operand" "rmi,ri")))
8629 (clobber (reg:CC FLAGS_REG))]
8630 "ix86_binary_operator_ok (IOR, HImode, operands)"
8631 "or{w}\t{%2, %0|%0, %2}"
8632 [(set_attr "type" "alu")
8633 (set_attr "mode" "HI")])
8635 (define_insn "*iorhi_2"
8636 [(set (reg FLAGS_REG)
8637 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
8638 (match_operand:HI 2 "general_operand" "rim,ri"))
8640 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
8641 (ior:HI (match_dup 1) (match_dup 2)))]
8642 "ix86_match_ccmode (insn, CCNOmode)
8643 && ix86_binary_operator_ok (IOR, HImode, operands)"
8644 "or{w}\t{%2, %0|%0, %2}"
8645 [(set_attr "type" "alu")
8646 (set_attr "mode" "HI")])
8648 (define_insn "*iorhi_3"
8649 [(set (reg FLAGS_REG)
8650 (compare (ior:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
8651 (match_operand:HI 2 "general_operand" "rim"))
8653 (clobber (match_scratch:HI 0 "=r"))]
8654 "ix86_match_ccmode (insn, CCNOmode)
8655 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8656 "or{w}\t{%2, %0|%0, %2}"
8657 [(set_attr "type" "alu")
8658 (set_attr "mode" "HI")])
8660 (define_expand "iorqi3"
8661 [(set (match_operand:QI 0 "nonimmediate_operand" "")
8662 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "")
8663 (match_operand:QI 2 "general_operand" "")))
8664 (clobber (reg:CC FLAGS_REG))]
8665 "TARGET_QIMODE_MATH"
8666 "ix86_expand_binary_operator (IOR, QImode, operands); DONE;")
8668 ;; %%% Potential partial reg stall on alternative 2. What to do?
8669 (define_insn "*iorqi_1"
8670 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
8671 (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
8672 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
8673 (clobber (reg:CC FLAGS_REG))]
8674 "ix86_binary_operator_ok (IOR, QImode, operands)"
8676 or{b}\t{%2, %0|%0, %2}
8677 or{b}\t{%2, %0|%0, %2}
8678 or{l}\t{%k2, %k0|%k0, %k2}"
8679 [(set_attr "type" "alu")
8680 (set_attr "mode" "QI,QI,SI")])
8682 (define_insn "*iorqi_1_slp"
8683 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+q,m"))
8684 (ior:QI (match_dup 0)
8685 (match_operand:QI 1 "general_operand" "qmi,qi")))
8686 (clobber (reg:CC FLAGS_REG))]
8687 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8688 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8689 "or{b}\t{%1, %0|%0, %1}"
8690 [(set_attr "type" "alu1")
8691 (set_attr "mode" "QI")])
8693 (define_insn "*iorqi_2"
8694 [(set (reg FLAGS_REG)
8695 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
8696 (match_operand:QI 2 "general_operand" "qim,qi"))
8698 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
8699 (ior:QI (match_dup 1) (match_dup 2)))]
8700 "ix86_match_ccmode (insn, CCNOmode)
8701 && ix86_binary_operator_ok (IOR, QImode, operands)"
8702 "or{b}\t{%2, %0|%0, %2}"
8703 [(set_attr "type" "alu")
8704 (set_attr "mode" "QI")])
8706 (define_insn "*iorqi_2_slp"
8707 [(set (reg FLAGS_REG)
8708 (compare (ior:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
8709 (match_operand:QI 1 "general_operand" "qim,qi"))
8711 (set (strict_low_part (match_dup 0))
8712 (ior:QI (match_dup 0) (match_dup 1)))]
8713 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
8714 && ix86_match_ccmode (insn, CCNOmode)
8715 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
8716 "or{b}\t{%1, %0|%0, %1}"
8717 [(set_attr "type" "alu1")
8718 (set_attr "mode" "QI")])
8720 (define_insn "*iorqi_3"
8721 [(set (reg FLAGS_REG)
8722 (compare (ior:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
8723 (match_operand:QI 2 "general_operand" "qim"))
8725 (clobber (match_scratch:QI 0 "=q"))]
8726 "ix86_match_ccmode (insn, CCNOmode)
8727 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8728 "or{b}\t{%2, %0|%0, %2}"
8729 [(set_attr "type" "alu")
8730 (set_attr "mode" "QI")])
8732 (define_insn "iorqi_ext_0"
8733 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8738 (match_operand 1 "ext_register_operand" "0")
8741 (match_operand 2 "const_int_operand" "n")))
8742 (clobber (reg:CC FLAGS_REG))]
8743 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8744 "or{b}\t{%2, %h0|%h0, %2}"
8745 [(set_attr "type" "alu")
8746 (set_attr "length_immediate" "1")
8747 (set_attr "mode" "QI")])
8749 (define_insn "*iorqi_ext_1"
8750 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8755 (match_operand 1 "ext_register_operand" "0")
8759 (match_operand:QI 2 "general_operand" "Qm"))))
8760 (clobber (reg:CC FLAGS_REG))]
8762 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
8763 "or{b}\t{%2, %h0|%h0, %2}"
8764 [(set_attr "type" "alu")
8765 (set_attr "length_immediate" "0")
8766 (set_attr "mode" "QI")])
8768 (define_insn "*iorqi_ext_1_rex64"
8769 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8774 (match_operand 1 "ext_register_operand" "0")
8778 (match_operand 2 "ext_register_operand" "Q"))))
8779 (clobber (reg:CC FLAGS_REG))]
8781 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
8782 "or{b}\t{%2, %h0|%h0, %2}"
8783 [(set_attr "type" "alu")
8784 (set_attr "length_immediate" "0")
8785 (set_attr "mode" "QI")])
8787 (define_insn "*iorqi_ext_2"
8788 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
8792 (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
8795 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
8798 (clobber (reg:CC FLAGS_REG))]
8799 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
8800 "ior{b}\t{%h2, %h0|%h0, %h2}"
8801 [(set_attr "type" "alu")
8802 (set_attr "length_immediate" "0")
8803 (set_attr "mode" "QI")])
8806 [(set (match_operand 0 "register_operand" "")
8807 (ior (match_operand 1 "register_operand" "")
8808 (match_operand 2 "const_int_operand" "")))
8809 (clobber (reg:CC FLAGS_REG))]
8811 && QI_REG_P (operands[0])
8812 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8813 && !(INTVAL (operands[2]) & ~(255 << 8))
8814 && GET_MODE (operands[0]) != QImode"
8815 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
8816 (ior:SI (zero_extract:SI (match_dup 1)
8817 (const_int 8) (const_int 8))
8819 (clobber (reg:CC FLAGS_REG))])]
8820 "operands[0] = gen_lowpart (SImode, operands[0]);
8821 operands[1] = gen_lowpart (SImode, operands[1]);
8822 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
8824 ;; Since OR can be encoded with sign extended immediate, this is only
8825 ;; profitable when 7th bit is set.
8827 [(set (match_operand 0 "register_operand" "")
8828 (ior (match_operand 1 "general_operand" "")
8829 (match_operand 2 "const_int_operand" "")))
8830 (clobber (reg:CC FLAGS_REG))]
8832 && ANY_QI_REG_P (operands[0])
8833 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
8834 && !(INTVAL (operands[2]) & ~255)
8835 && (INTVAL (operands[2]) & 128)
8836 && GET_MODE (operands[0]) != QImode"
8837 [(parallel [(set (strict_low_part (match_dup 0))
8838 (ior:QI (match_dup 1)
8840 (clobber (reg:CC FLAGS_REG))])]
8841 "operands[0] = gen_lowpart (QImode, operands[0]);
8842 operands[1] = gen_lowpart (QImode, operands[1]);
8843 operands[2] = gen_lowpart (QImode, operands[2]);")
8845 ;; Logical XOR instructions
8847 ;; %%% This used to optimize known byte-wide and operations to memory.
8848 ;; If this is considered useful, it should be done with splitters.
8850 (define_expand "xordi3"
8851 [(set (match_operand:DI 0 "nonimmediate_operand" "")
8852 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "")
8853 (match_operand:DI 2 "x86_64_general_operand" "")))
8854 (clobber (reg:CC FLAGS_REG))]
8856 "ix86_expand_binary_operator (XOR, DImode, operands); DONE;")
8858 (define_insn "*xordi_1_rex64"
8859 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
8860 (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8861 (match_operand:DI 2 "x86_64_general_operand" "re,rm")))
8862 (clobber (reg:CC FLAGS_REG))]
8864 && ix86_binary_operator_ok (XOR, DImode, operands)"
8866 xor{q}\t{%2, %0|%0, %2}
8867 xor{q}\t{%2, %0|%0, %2}"
8868 [(set_attr "type" "alu")
8869 (set_attr "mode" "DI,DI")])
8871 (define_insn "*xordi_2_rex64"
8872 [(set (reg FLAGS_REG)
8873 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0,0")
8874 (match_operand:DI 2 "x86_64_general_operand" "rem,re"))
8876 (set (match_operand:DI 0 "nonimmediate_operand" "=r,rm")
8877 (xor:DI (match_dup 1) (match_dup 2)))]
8879 && ix86_match_ccmode (insn, CCNOmode)
8880 && ix86_binary_operator_ok (XOR, DImode, operands)"
8882 xor{q}\t{%2, %0|%0, %2}
8883 xor{q}\t{%2, %0|%0, %2}"
8884 [(set_attr "type" "alu")
8885 (set_attr "mode" "DI,DI")])
8887 (define_insn "*xordi_3_rex64"
8888 [(set (reg FLAGS_REG)
8889 (compare (xor:DI (match_operand:DI 1 "nonimmediate_operand" "%0")
8890 (match_operand:DI 2 "x86_64_general_operand" "rem"))
8892 (clobber (match_scratch:DI 0 "=r"))]
8894 && ix86_match_ccmode (insn, CCNOmode)
8895 && ix86_binary_operator_ok (XOR, DImode, operands)"
8896 "xor{q}\t{%2, %0|%0, %2}"
8897 [(set_attr "type" "alu")
8898 (set_attr "mode" "DI")])
8900 (define_expand "xorsi3"
8901 [(set (match_operand:SI 0 "nonimmediate_operand" "")
8902 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "")
8903 (match_operand:SI 2 "general_operand" "")))
8904 (clobber (reg:CC FLAGS_REG))]
8906 "ix86_expand_binary_operator (XOR, SImode, operands); DONE;")
8908 (define_insn "*xorsi_1"
8909 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
8910 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8911 (match_operand:SI 2 "general_operand" "ri,rm")))
8912 (clobber (reg:CC FLAGS_REG))]
8913 "ix86_binary_operator_ok (XOR, SImode, operands)"
8914 "xor{l}\t{%2, %0|%0, %2}"
8915 [(set_attr "type" "alu")
8916 (set_attr "mode" "SI")])
8918 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8919 ;; Add speccase for immediates
8920 (define_insn "*xorsi_1_zext"
8921 [(set (match_operand:DI 0 "register_operand" "=r")
8923 (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8924 (match_operand:SI 2 "general_operand" "rim"))))
8925 (clobber (reg:CC FLAGS_REG))]
8926 "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
8927 "xor{l}\t{%2, %k0|%k0, %2}"
8928 [(set_attr "type" "alu")
8929 (set_attr "mode" "SI")])
8931 (define_insn "*xorsi_1_zext_imm"
8932 [(set (match_operand:DI 0 "register_operand" "=r")
8933 (xor:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "%0"))
8934 (match_operand:DI 2 "x86_64_zext_immediate_operand" "Z")))
8935 (clobber (reg:CC FLAGS_REG))]
8936 "TARGET_64BIT && ix86_binary_operator_ok (XOR, SImode, operands)"
8937 "xor{l}\t{%2, %k0|%k0, %2}"
8938 [(set_attr "type" "alu")
8939 (set_attr "mode" "SI")])
8941 (define_insn "*xorsi_2"
8942 [(set (reg FLAGS_REG)
8943 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0,0")
8944 (match_operand:SI 2 "general_operand" "rim,ri"))
8946 (set (match_operand:SI 0 "nonimmediate_operand" "=r,rm")
8947 (xor:SI (match_dup 1) (match_dup 2)))]
8948 "ix86_match_ccmode (insn, CCNOmode)
8949 && ix86_binary_operator_ok (XOR, SImode, operands)"
8950 "xor{l}\t{%2, %0|%0, %2}"
8951 [(set_attr "type" "alu")
8952 (set_attr "mode" "SI")])
8954 ;; See comment for addsi_1_zext why we do use nonimmediate_operand
8955 ;; ??? Special case for immediate operand is missing - it is tricky.
8956 (define_insn "*xorsi_2_zext"
8957 [(set (reg FLAGS_REG)
8958 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8959 (match_operand:SI 2 "general_operand" "rim"))
8961 (set (match_operand:DI 0 "register_operand" "=r")
8962 (zero_extend:DI (xor:SI (match_dup 1) (match_dup 2))))]
8963 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8964 && ix86_binary_operator_ok (XOR, SImode, operands)"
8965 "xor{l}\t{%2, %k0|%k0, %2}"
8966 [(set_attr "type" "alu")
8967 (set_attr "mode" "SI")])
8969 (define_insn "*xorsi_2_zext_imm"
8970 [(set (reg FLAGS_REG)
8971 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8972 (match_operand 2 "x86_64_zext_immediate_operand" "Z"))
8974 (set (match_operand:DI 0 "register_operand" "=r")
8975 (xor:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
8976 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
8977 && ix86_binary_operator_ok (XOR, SImode, operands)"
8978 "xor{l}\t{%2, %k0|%k0, %2}"
8979 [(set_attr "type" "alu")
8980 (set_attr "mode" "SI")])
8982 (define_insn "*xorsi_3"
8983 [(set (reg FLAGS_REG)
8984 (compare (xor:SI (match_operand:SI 1 "nonimmediate_operand" "%0")
8985 (match_operand:SI 2 "general_operand" "rim"))
8987 (clobber (match_scratch:SI 0 "=r"))]
8988 "ix86_match_ccmode (insn, CCNOmode)
8989 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
8990 "xor{l}\t{%2, %0|%0, %2}"
8991 [(set_attr "type" "alu")
8992 (set_attr "mode" "SI")])
8994 (define_expand "xorhi3"
8995 [(set (match_operand:HI 0 "nonimmediate_operand" "")
8996 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "")
8997 (match_operand:HI 2 "general_operand" "")))
8998 (clobber (reg:CC FLAGS_REG))]
8999 "TARGET_HIMODE_MATH"
9000 "ix86_expand_binary_operator (XOR, HImode, operands); DONE;")
9002 (define_insn "*xorhi_1"
9003 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,m")
9004 (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9005 (match_operand:HI 2 "general_operand" "rmi,ri")))
9006 (clobber (reg:CC FLAGS_REG))]
9007 "ix86_binary_operator_ok (XOR, HImode, operands)"
9008 "xor{w}\t{%2, %0|%0, %2}"
9009 [(set_attr "type" "alu")
9010 (set_attr "mode" "HI")])
9012 (define_insn "*xorhi_2"
9013 [(set (reg FLAGS_REG)
9014 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
9015 (match_operand:HI 2 "general_operand" "rim,ri"))
9017 (set (match_operand:HI 0 "nonimmediate_operand" "=r,rm")
9018 (xor:HI (match_dup 1) (match_dup 2)))]
9019 "ix86_match_ccmode (insn, CCNOmode)
9020 && ix86_binary_operator_ok (XOR, HImode, operands)"
9021 "xor{w}\t{%2, %0|%0, %2}"
9022 [(set_attr "type" "alu")
9023 (set_attr "mode" "HI")])
9025 (define_insn "*xorhi_3"
9026 [(set (reg FLAGS_REG)
9027 (compare (xor:HI (match_operand:HI 1 "nonimmediate_operand" "%0")
9028 (match_operand:HI 2 "general_operand" "rim"))
9030 (clobber (match_scratch:HI 0 "=r"))]
9031 "ix86_match_ccmode (insn, CCNOmode)
9032 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
9033 "xor{w}\t{%2, %0|%0, %2}"
9034 [(set_attr "type" "alu")
9035 (set_attr "mode" "HI")])
9037 (define_expand "xorqi3"
9038 [(set (match_operand:QI 0 "nonimmediate_operand" "")
9039 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "")
9040 (match_operand:QI 2 "general_operand" "")))
9041 (clobber (reg:CC FLAGS_REG))]
9042 "TARGET_QIMODE_MATH"
9043 "ix86_expand_binary_operator (XOR, QImode, operands); DONE;")
9045 ;; %%% Potential partial reg stall on alternative 2. What to do?
9046 (define_insn "*xorqi_1"
9047 [(set (match_operand:QI 0 "nonimmediate_operand" "=q,m,r")
9048 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
9049 (match_operand:QI 2 "general_operand" "qmi,qi,ri")))
9050 (clobber (reg:CC FLAGS_REG))]
9051 "ix86_binary_operator_ok (XOR, QImode, operands)"
9053 xor{b}\t{%2, %0|%0, %2}
9054 xor{b}\t{%2, %0|%0, %2}
9055 xor{l}\t{%k2, %k0|%k0, %k2}"
9056 [(set_attr "type" "alu")
9057 (set_attr "mode" "QI,QI,SI")])
9059 (define_insn "*xorqi_1_slp"
9060 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,q"))
9061 (xor:QI (match_dup 0)
9062 (match_operand:QI 1 "general_operand" "qi,qmi")))
9063 (clobber (reg:CC FLAGS_REG))]
9064 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9065 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
9066 "xor{b}\t{%1, %0|%0, %1}"
9067 [(set_attr "type" "alu1")
9068 (set_attr "mode" "QI")])
9070 (define_insn "xorqi_ext_0"
9071 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9076 (match_operand 1 "ext_register_operand" "0")
9079 (match_operand 2 "const_int_operand" "n")))
9080 (clobber (reg:CC FLAGS_REG))]
9081 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9082 "xor{b}\t{%2, %h0|%h0, %2}"
9083 [(set_attr "type" "alu")
9084 (set_attr "length_immediate" "1")
9085 (set_attr "mode" "QI")])
9087 (define_insn "*xorqi_ext_1"
9088 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9093 (match_operand 1 "ext_register_operand" "0")
9097 (match_operand:QI 2 "general_operand" "Qm"))))
9098 (clobber (reg:CC FLAGS_REG))]
9100 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9101 "xor{b}\t{%2, %h0|%h0, %2}"
9102 [(set_attr "type" "alu")
9103 (set_attr "length_immediate" "0")
9104 (set_attr "mode" "QI")])
9106 (define_insn "*xorqi_ext_1_rex64"
9107 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9112 (match_operand 1 "ext_register_operand" "0")
9116 (match_operand 2 "ext_register_operand" "Q"))))
9117 (clobber (reg:CC FLAGS_REG))]
9119 && (!TARGET_PARTIAL_REG_STALL || optimize_size)"
9120 "xor{b}\t{%2, %h0|%h0, %2}"
9121 [(set_attr "type" "alu")
9122 (set_attr "length_immediate" "0")
9123 (set_attr "mode" "QI")])
9125 (define_insn "*xorqi_ext_2"
9126 [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9130 (zero_extract:SI (match_operand 1 "ext_register_operand" "0")
9133 (zero_extract:SI (match_operand 2 "ext_register_operand" "Q")
9136 (clobber (reg:CC FLAGS_REG))]
9137 "(!TARGET_PARTIAL_REG_STALL || optimize_size)"
9138 "xor{b}\t{%h2, %h0|%h0, %h2}"
9139 [(set_attr "type" "alu")
9140 (set_attr "length_immediate" "0")
9141 (set_attr "mode" "QI")])
9143 (define_insn "*xorqi_cc_1"
9144 [(set (reg FLAGS_REG)
9146 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0")
9147 (match_operand:QI 2 "general_operand" "qim,qi"))
9149 (set (match_operand:QI 0 "nonimmediate_operand" "=q,qm")
9150 (xor:QI (match_dup 1) (match_dup 2)))]
9151 "ix86_match_ccmode (insn, CCNOmode)
9152 && ix86_binary_operator_ok (XOR, QImode, operands)"
9153 "xor{b}\t{%2, %0|%0, %2}"
9154 [(set_attr "type" "alu")
9155 (set_attr "mode" "QI")])
9157 (define_insn "*xorqi_2_slp"
9158 [(set (reg FLAGS_REG)
9159 (compare (xor:QI (match_operand:QI 0 "nonimmediate_operand" "+q,qm")
9160 (match_operand:QI 1 "general_operand" "qim,qi"))
9162 (set (strict_low_part (match_dup 0))
9163 (xor:QI (match_dup 0) (match_dup 1)))]
9164 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
9165 && ix86_match_ccmode (insn, CCNOmode)
9166 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
9167 "xor{b}\t{%1, %0|%0, %1}"
9168 [(set_attr "type" "alu1")
9169 (set_attr "mode" "QI")])
9171 (define_insn "*xorqi_cc_2"
9172 [(set (reg FLAGS_REG)
9174 (xor:QI (match_operand:QI 1 "nonimmediate_operand" "%0")
9175 (match_operand:QI 2 "general_operand" "qim"))
9177 (clobber (match_scratch:QI 0 "=q"))]
9178 "ix86_match_ccmode (insn, CCNOmode)
9179 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
9180 "xor{b}\t{%2, %0|%0, %2}"
9181 [(set_attr "type" "alu")
9182 (set_attr "mode" "QI")])
9184 (define_insn "*xorqi_cc_ext_1"
9185 [(set (reg FLAGS_REG)
9189 (match_operand 1 "ext_register_operand" "0")
9192 (match_operand:QI 2 "general_operand" "qmn"))
9194 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=q")
9198 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9200 "!TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9201 "xor{b}\t{%2, %h0|%h0, %2}"
9202 [(set_attr "type" "alu")
9203 (set_attr "mode" "QI")])
9205 (define_insn "*xorqi_cc_ext_1_rex64"
9206 [(set (reg FLAGS_REG)
9210 (match_operand 1 "ext_register_operand" "0")
9213 (match_operand:QI 2 "nonmemory_operand" "Qn"))
9215 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "=Q")
9219 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9221 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
9222 "xor{b}\t{%2, %h0|%h0, %2}"
9223 [(set_attr "type" "alu")
9224 (set_attr "mode" "QI")])
9226 (define_expand "xorqi_cc_ext_1"
9228 (set (reg:CCNO FLAGS_REG)
9232 (match_operand 1 "ext_register_operand" "")
9235 (match_operand:QI 2 "general_operand" ""))
9237 (set (zero_extract:SI (match_operand 0 "ext_register_operand" "")
9241 (zero_extract:SI (match_dup 1) (const_int 8) (const_int 8))
9247 [(set (match_operand 0 "register_operand" "")
9248 (xor (match_operand 1 "register_operand" "")
9249 (match_operand 2 "const_int_operand" "")))
9250 (clobber (reg:CC FLAGS_REG))]
9252 && QI_REG_P (operands[0])
9253 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9254 && !(INTVAL (operands[2]) & ~(255 << 8))
9255 && GET_MODE (operands[0]) != QImode"
9256 [(parallel [(set (zero_extract:SI (match_dup 0) (const_int 8) (const_int 8))
9257 (xor:SI (zero_extract:SI (match_dup 1)
9258 (const_int 8) (const_int 8))
9260 (clobber (reg:CC FLAGS_REG))])]
9261 "operands[0] = gen_lowpart (SImode, operands[0]);
9262 operands[1] = gen_lowpart (SImode, operands[1]);
9263 operands[2] = gen_int_mode ((INTVAL (operands[2]) >> 8) & 0xff, SImode);")
9265 ;; Since XOR can be encoded with sign extended immediate, this is only
9266 ;; profitable when 7th bit is set.
9268 [(set (match_operand 0 "register_operand" "")
9269 (xor (match_operand 1 "general_operand" "")
9270 (match_operand 2 "const_int_operand" "")))
9271 (clobber (reg:CC FLAGS_REG))]
9273 && ANY_QI_REG_P (operands[0])
9274 && (!TARGET_PARTIAL_REG_STALL || optimize_size)
9275 && !(INTVAL (operands[2]) & ~255)
9276 && (INTVAL (operands[2]) & 128)
9277 && GET_MODE (operands[0]) != QImode"
9278 [(parallel [(set (strict_low_part (match_dup 0))
9279 (xor:QI (match_dup 1)
9281 (clobber (reg:CC FLAGS_REG))])]
9282 "operands[0] = gen_lowpart (QImode, operands[0]);
9283 operands[1] = gen_lowpart (QImode, operands[1]);
9284 operands[2] = gen_lowpart (QImode, operands[2]);")
9286 ;; Negation instructions
9288 (define_expand "negti2"
9289 [(parallel [(set (match_operand:TI 0 "nonimmediate_operand" "")
9290 (neg:TI (match_operand:TI 1 "nonimmediate_operand" "")))
9291 (clobber (reg:CC FLAGS_REG))])]
9293 "ix86_expand_unary_operator (NEG, TImode, operands); DONE;")
9295 (define_insn "*negti2_1"
9296 [(set (match_operand:TI 0 "nonimmediate_operand" "=ro")
9297 (neg:TI (match_operand:TI 1 "general_operand" "0")))
9298 (clobber (reg:CC FLAGS_REG))]
9300 && ix86_unary_operator_ok (NEG, TImode, operands)"
9304 [(set (match_operand:TI 0 "nonimmediate_operand" "")
9305 (neg:TI (match_operand:TI 1 "general_operand" "")))
9306 (clobber (reg:CC FLAGS_REG))]
9307 "TARGET_64BIT && reload_completed"
9309 [(set (reg:CCZ FLAGS_REG)
9310 (compare:CCZ (neg:DI (match_dup 2)) (const_int 0)))
9311 (set (match_dup 0) (neg:DI (match_dup 2)))])
9314 (plus:DI (plus:DI (ltu:DI (reg:CC FLAGS_REG) (const_int 0))
9317 (clobber (reg:CC FLAGS_REG))])
9320 (neg:DI (match_dup 1)))
9321 (clobber (reg:CC FLAGS_REG))])]
9322 "split_ti (operands+1, 1, operands+2, operands+3);
9323 split_ti (operands+0, 1, operands+0, operands+1);")
9325 (define_expand "negdi2"
9326 [(parallel [(set (match_operand:DI 0 "nonimmediate_operand" "")
9327 (neg:DI (match_operand:DI 1 "nonimmediate_operand" "")))
9328 (clobber (reg:CC FLAGS_REG))])]
9330 "ix86_expand_unary_operator (NEG, DImode, operands); DONE;")
9332 (define_insn "*negdi2_1"
9333 [(set (match_operand:DI 0 "nonimmediate_operand" "=ro")
9334 (neg:DI (match_operand:DI 1 "general_operand" "0")))
9335 (clobber (reg:CC FLAGS_REG))]
9337 && ix86_unary_operator_ok (NEG, DImode, operands)"
9341 [(set (match_operand:DI 0 "nonimmediate_operand" "")
9342 (neg:DI (match_operand:DI 1 "general_operand" "")))
9343 (clobber (reg:CC FLAGS_REG))]
9344 "!TARGET_64BIT && reload_completed"
9346 [(set (reg:CCZ FLAGS_REG)
9347 (compare:CCZ (neg:SI (match_dup 2)) (const_int 0)))
9348 (set (match_dup 0) (neg:SI (match_dup 2)))])
9351 (plus:SI (plus:SI (ltu:SI (reg:CC FLAGS_REG) (const_int 0))
9354 (clobber (reg:CC FLAGS_REG))])
9357 (neg:SI (match_dup 1)))
9358 (clobber (reg:CC FLAGS_REG))])]
9359 "split_di (operands+1, 1, operands+2, operands+3);
9360 split_di (operands+0, 1, operands+0, operands+1);")
9362 (define_insn "*negdi2_1_rex64"
9363 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9364 (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0")))
9365 (clobber (reg:CC FLAGS_REG))]
9366 "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
9368 [(set_attr "type" "negnot")
9369 (set_attr "mode" "DI")])
9371 ;; The problem with neg is that it does not perform (compare x 0),
9372 ;; it really performs (compare 0 x), which leaves us with the zero
9373 ;; flag being the only useful item.
9375 (define_insn "*negdi2_cmpz_rex64"
9376 [(set (reg:CCZ FLAGS_REG)
9377 (compare:CCZ (neg:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
9379 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9380 (neg:DI (match_dup 1)))]
9381 "TARGET_64BIT && ix86_unary_operator_ok (NEG, DImode, operands)"
9383 [(set_attr "type" "negnot")
9384 (set_attr "mode" "DI")])
9387 (define_expand "negsi2"
9388 [(parallel [(set (match_operand:SI 0 "nonimmediate_operand" "")
9389 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "")))
9390 (clobber (reg:CC FLAGS_REG))])]
9392 "ix86_expand_unary_operator (NEG, SImode, operands); DONE;")
9394 (define_insn "*negsi2_1"
9395 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9396 (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0")))
9397 (clobber (reg:CC FLAGS_REG))]
9398 "ix86_unary_operator_ok (NEG, SImode, operands)"
9400 [(set_attr "type" "negnot")
9401 (set_attr "mode" "SI")])
9403 ;; Combine is quite creative about this pattern.
9404 (define_insn "*negsi2_1_zext"
9405 [(set (match_operand:DI 0 "register_operand" "=r")
9406 (lshiftrt:DI (neg:DI (ashift:DI (match_operand:DI 1 "register_operand" "0")
9409 (clobber (reg:CC FLAGS_REG))]
9410 "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
9412 [(set_attr "type" "negnot")
9413 (set_attr "mode" "SI")])
9415 ;; The problem with neg is that it does not perform (compare x 0),
9416 ;; it really performs (compare 0 x), which leaves us with the zero
9417 ;; flag being the only useful item.
9419 (define_insn "*negsi2_cmpz"
9420 [(set (reg:CCZ FLAGS_REG)
9421 (compare:CCZ (neg:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
9423 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
9424 (neg:SI (match_dup 1)))]
9425 "ix86_unary_operator_ok (NEG, SImode, operands)"
9427 [(set_attr "type" "negnot")
9428 (set_attr "mode" "SI")])
9430 (define_insn "*negsi2_cmpz_zext"
9431 [(set (reg:CCZ FLAGS_REG)
9432 (compare:CCZ (lshiftrt:DI
9434 (match_operand:DI 1 "register_operand" "0")
9438 (set (match_operand:DI 0 "register_operand" "=r")
9439 (lshiftrt:DI (neg:DI (ashift:DI (match_dup 1)
9442 "TARGET_64BIT && ix86_unary_operator_ok (NEG, SImode, operands)"
9444 [(set_attr "type" "negnot")
9445 (set_attr "mode" "SI")])
9447 (define_expand "neghi2"
9448 [(parallel [(set (match_operand:HI 0 "nonimmediate_operand" "")
9449 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "")))
9450 (clobber (reg:CC FLAGS_REG))])]
9451 "TARGET_HIMODE_MATH"
9452 "ix86_expand_unary_operator (NEG, HImode, operands); DONE;")
9454 (define_insn "*neghi2_1"
9455 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9456 (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0")))
9457 (clobber (reg:CC FLAGS_REG))]
9458 "ix86_unary_operator_ok (NEG, HImode, operands)"
9460 [(set_attr "type" "negnot")
9461 (set_attr "mode" "HI")])
9463 (define_insn "*neghi2_cmpz"
9464 [(set (reg:CCZ FLAGS_REG)
9465 (compare:CCZ (neg:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
9467 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
9468 (neg:HI (match_dup 1)))]
9469 "ix86_unary_operator_ok (NEG, HImode, operands)"
9471 [(set_attr "type" "negnot")
9472 (set_attr "mode" "HI")])
9474 (define_expand "negqi2"
9475 [(parallel [(set (match_operand:QI 0 "nonimmediate_operand" "")
9476 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "")))
9477 (clobber (reg:CC FLAGS_REG))])]
9478 "TARGET_QIMODE_MATH"
9479 "ix86_expand_unary_operator (NEG, QImode, operands); DONE;")
9481 (define_insn "*negqi2_1"
9482 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9483 (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0")))
9484 (clobber (reg:CC FLAGS_REG))]
9485 "ix86_unary_operator_ok (NEG, QImode, operands)"
9487 [(set_attr "type" "negnot")
9488 (set_attr "mode" "QI")])
9490 (define_insn "*negqi2_cmpz"
9491 [(set (reg:CCZ FLAGS_REG)
9492 (compare:CCZ (neg:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
9494 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
9495 (neg:QI (match_dup 1)))]
9496 "ix86_unary_operator_ok (NEG, QImode, operands)"
9498 [(set_attr "type" "negnot")
9499 (set_attr "mode" "QI")])
9501 ;; Changing of sign for FP values is doable using integer unit too.
9503 (define_expand "negsf2"
9504 [(set (match_operand:SF 0 "nonimmediate_operand" "")
9505 (neg:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
9506 "TARGET_80387 || TARGET_SSE_MATH"
9507 "ix86_expand_fp_absneg_operator (NEG, SFmode, operands); DONE;")
9509 (define_expand "abssf2"
9510 [(set (match_operand:SF 0 "nonimmediate_operand" "")
9511 (abs:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
9512 "TARGET_80387 || TARGET_SSE_MATH"
9513 "ix86_expand_fp_absneg_operator (ABS, SFmode, operands); DONE;")
9515 (define_insn "*absnegsf2_mixed"
9516 [(set (match_operand:SF 0 "nonimmediate_operand" "=x#f,x#f,f#x,rm")
9517 (match_operator:SF 3 "absneg_operator"
9518 [(match_operand:SF 1 "nonimmediate_operand" "0 ,x#f,0 ,0")]))
9519 (use (match_operand:V4SF 2 "nonimmediate_operand" "xm ,0 ,X ,X"))
9520 (clobber (reg:CC FLAGS_REG))]
9521 "TARGET_SSE_MATH && TARGET_MIX_SSE_I387
9522 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9525 (define_insn "*absnegsf2_sse"
9526 [(set (match_operand:SF 0 "nonimmediate_operand" "=x,x,rm")
9527 (match_operator:SF 3 "absneg_operator"
9528 [(match_operand:SF 1 "nonimmediate_operand" "0 ,x,0")]))
9529 (use (match_operand:V4SF 2 "nonimmediate_operand" "xm,0,X"))
9530 (clobber (reg:CC FLAGS_REG))]
9532 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9535 (define_insn "*absnegsf2_i387"
9536 [(set (match_operand:SF 0 "nonimmediate_operand" "=f,rm")
9537 (match_operator:SF 3 "absneg_operator"
9538 [(match_operand:SF 1 "nonimmediate_operand" "0,0")]))
9539 (use (match_operand 2 "" ""))
9540 (clobber (reg:CC FLAGS_REG))]
9541 "TARGET_80387 && !TARGET_SSE_MATH
9542 && ix86_unary_operator_ok (GET_CODE (operands[3]), SFmode, operands)"
9545 (define_expand "copysignsf3"
9546 [(match_operand:SF 0 "register_operand" "")
9547 (match_operand:SF 1 "nonmemory_operand" "")
9548 (match_operand:SF 2 "register_operand" "")]
9551 ix86_expand_copysign (operands);
9555 (define_insn_and_split "copysignsf3_const"
9556 [(set (match_operand:SF 0 "register_operand" "=x")
9558 [(match_operand:V4SF 1 "vector_move_operand" "xmC")
9559 (match_operand:SF 2 "register_operand" "0")
9560 (match_operand:V4SF 3 "nonimmediate_operand" "xm")]
9564 "&& reload_completed"
9567 ix86_split_copysign_const (operands);
9571 (define_insn "copysignsf3_var"
9572 [(set (match_operand:SF 0 "register_operand" "=x, x, x, x,x")
9574 [(match_operand:SF 2 "register_operand" " x, 0, 0, x,x")
9575 (match_operand:SF 3 "register_operand" " 1, 1, x, 1,x")
9576 (match_operand:V4SF 4 "nonimmediate_operand" " X,xm,xm, 0,0")
9577 (match_operand:V4SF 5 "nonimmediate_operand" " 0,xm, 1,xm,1")]
9579 (clobber (match_scratch:V4SF 1 "=x, x, x, x,x"))]
9584 [(set (match_operand:SF 0 "register_operand" "")
9586 [(match_operand:SF 2 "register_operand" "")
9587 (match_operand:SF 3 "register_operand" "")
9588 (match_operand:V4SF 4 "" "")
9589 (match_operand:V4SF 5 "" "")]
9591 (clobber (match_scratch:V4SF 1 ""))]
9592 "TARGET_SSE_MATH && reload_completed"
9595 ix86_split_copysign_var (operands);
9599 (define_expand "negdf2"
9600 [(set (match_operand:DF 0 "nonimmediate_operand" "")
9601 (neg:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
9602 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
9603 "ix86_expand_fp_absneg_operator (NEG, DFmode, operands); DONE;")
9605 (define_expand "absdf2"
9606 [(set (match_operand:DF 0 "nonimmediate_operand" "")
9607 (abs:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
9608 "TARGET_80387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
9609 "ix86_expand_fp_absneg_operator (ABS, DFmode, operands); DONE;")
9611 (define_insn "*absnegdf2_mixed"
9612 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y#f,Y#f,f#Y,rm")
9613 (match_operator:DF 3 "absneg_operator"
9614 [(match_operand:DF 1 "nonimmediate_operand" "0 ,Y#f,0 ,0")]))
9615 (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym ,0 ,X ,X"))
9616 (clobber (reg:CC FLAGS_REG))]
9617 "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
9618 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9621 (define_insn "*absnegdf2_sse"
9622 [(set (match_operand:DF 0 "nonimmediate_operand" "=Y,Y,rm")
9623 (match_operator:DF 3 "absneg_operator"
9624 [(match_operand:DF 1 "nonimmediate_operand" "0 ,Y,0")]))
9625 (use (match_operand:V2DF 2 "nonimmediate_operand" "Ym,0,X"))
9626 (clobber (reg:CC FLAGS_REG))]
9627 "TARGET_SSE2 && TARGET_SSE_MATH
9628 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9631 (define_insn "*absnegdf2_i387"
9632 [(set (match_operand:DF 0 "nonimmediate_operand" "=f,rm")
9633 (match_operator:DF 3 "absneg_operator"
9634 [(match_operand:DF 1 "nonimmediate_operand" "0,0")]))
9635 (use (match_operand 2 "" ""))
9636 (clobber (reg:CC FLAGS_REG))]
9637 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
9638 && ix86_unary_operator_ok (GET_CODE (operands[3]), DFmode, operands)"
9641 (define_expand "copysigndf3"
9642 [(match_operand:DF 0 "register_operand" "")
9643 (match_operand:DF 1 "nonmemory_operand" "")
9644 (match_operand:DF 2 "register_operand" "")]
9645 "TARGET_SSE2 && TARGET_SSE_MATH"
9647 ix86_expand_copysign (operands);
9651 (define_insn_and_split "copysigndf3_const"
9652 [(set (match_operand:DF 0 "register_operand" "=x")
9654 [(match_operand:V2DF 1 "vector_move_operand" "xmC")
9655 (match_operand:DF 2 "register_operand" "0")
9656 (match_operand:V2DF 3 "nonimmediate_operand" "xm")]
9658 "TARGET_SSE2 && TARGET_SSE_MATH"
9660 "&& reload_completed"
9663 ix86_split_copysign_const (operands);
9667 (define_insn "copysigndf3_var"
9668 [(set (match_operand:DF 0 "register_operand" "=x, x, x, x,x")
9670 [(match_operand:DF 2 "register_operand" " x, 0, 0, x,x")
9671 (match_operand:DF 3 "register_operand" " 1, 1, x, 1,x")
9672 (match_operand:V2DF 4 "nonimmediate_operand" " X,xm,xm, 0,0")
9673 (match_operand:V2DF 5 "nonimmediate_operand" " 0,xm, 1,xm,1")]
9675 (clobber (match_scratch:V2DF 1 "=x, x, x, x,x"))]
9676 "TARGET_SSE2 && TARGET_SSE_MATH"
9680 [(set (match_operand:DF 0 "register_operand" "")
9682 [(match_operand:DF 2 "register_operand" "")
9683 (match_operand:DF 3 "register_operand" "")
9684 (match_operand:V2DF 4 "" "")
9685 (match_operand:V2DF 5 "" "")]
9687 (clobber (match_scratch:V2DF 1 ""))]
9688 "TARGET_SSE2 && TARGET_SSE_MATH && reload_completed"
9691 ix86_split_copysign_var (operands);
9695 (define_expand "negxf2"
9696 [(set (match_operand:XF 0 "nonimmediate_operand" "")
9697 (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))]
9699 "ix86_expand_fp_absneg_operator (NEG, XFmode, operands); DONE;")
9701 (define_expand "absxf2"
9702 [(set (match_operand:XF 0 "nonimmediate_operand" "")
9703 (neg:XF (match_operand:XF 1 "nonimmediate_operand" "")))]
9705 "ix86_expand_fp_absneg_operator (ABS, XFmode, operands); DONE;")
9707 (define_insn "*absnegxf2_i387"
9708 [(set (match_operand:XF 0 "nonimmediate_operand" "=f,?rm")
9709 (match_operator:XF 3 "absneg_operator"
9710 [(match_operand:XF 1 "nonimmediate_operand" "0,0")]))
9711 (use (match_operand 2 "" ""))
9712 (clobber (reg:CC FLAGS_REG))]
9714 && ix86_unary_operator_ok (GET_CODE (operands[3]), XFmode, operands)"
9717 ;; Splitters for fp abs and neg.
9720 [(set (match_operand 0 "fp_register_operand" "")
9721 (match_operator 1 "absneg_operator" [(match_dup 0)]))
9722 (use (match_operand 2 "" ""))
9723 (clobber (reg:CC FLAGS_REG))]
9725 [(set (match_dup 0) (match_op_dup 1 [(match_dup 0)]))])
9728 [(set (match_operand 0 "register_operand" "")
9729 (match_operator 3 "absneg_operator"
9730 [(match_operand 1 "register_operand" "")]))
9731 (use (match_operand 2 "nonimmediate_operand" ""))
9732 (clobber (reg:CC FLAGS_REG))]
9733 "reload_completed && SSE_REG_P (operands[0])"
9734 [(set (match_dup 0) (match_dup 3))]
9736 enum machine_mode mode = GET_MODE (operands[0]);
9737 enum machine_mode vmode = GET_MODE (operands[2]);
9740 operands[0] = simplify_gen_subreg (vmode, operands[0], mode, 0);
9741 operands[1] = simplify_gen_subreg (vmode, operands[1], mode, 0);
9742 if (operands_match_p (operands[0], operands[2]))
9745 operands[1] = operands[2];
9748 if (GET_CODE (operands[3]) == ABS)
9749 tmp = gen_rtx_AND (vmode, operands[1], operands[2]);
9751 tmp = gen_rtx_XOR (vmode, operands[1], operands[2]);
9756 [(set (match_operand:SF 0 "register_operand" "")
9757 (match_operator:SF 1 "absneg_operator" [(match_dup 0)]))
9758 (use (match_operand:V4SF 2 "" ""))
9759 (clobber (reg:CC FLAGS_REG))]
9761 [(parallel [(set (match_dup 0) (match_dup 1))
9762 (clobber (reg:CC FLAGS_REG))])]
9765 operands[0] = gen_lowpart (SImode, operands[0]);
9766 if (GET_CODE (operands[1]) == ABS)
9768 tmp = gen_int_mode (0x7fffffff, SImode);
9769 tmp = gen_rtx_AND (SImode, operands[0], tmp);
9773 tmp = gen_int_mode (0x80000000, SImode);
9774 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9780 [(set (match_operand:DF 0 "register_operand" "")
9781 (match_operator:DF 1 "absneg_operator" [(match_dup 0)]))
9782 (use (match_operand 2 "" ""))
9783 (clobber (reg:CC FLAGS_REG))]
9785 [(parallel [(set (match_dup 0) (match_dup 1))
9786 (clobber (reg:CC FLAGS_REG))])]
9791 tmp = gen_lowpart (DImode, operands[0]);
9792 tmp = gen_rtx_ZERO_EXTRACT (DImode, tmp, const1_rtx, GEN_INT (63));
9795 if (GET_CODE (operands[1]) == ABS)
9798 tmp = gen_rtx_NOT (DImode, tmp);
9802 operands[0] = gen_highpart (SImode, operands[0]);
9803 if (GET_CODE (operands[1]) == ABS)
9805 tmp = gen_int_mode (0x7fffffff, SImode);
9806 tmp = gen_rtx_AND (SImode, operands[0], tmp);
9810 tmp = gen_int_mode (0x80000000, SImode);
9811 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9818 [(set (match_operand:XF 0 "register_operand" "")
9819 (match_operator:XF 1 "absneg_operator" [(match_dup 0)]))
9820 (use (match_operand 2 "" ""))
9821 (clobber (reg:CC FLAGS_REG))]
9823 [(parallel [(set (match_dup 0) (match_dup 1))
9824 (clobber (reg:CC FLAGS_REG))])]
9827 operands[0] = gen_rtx_REG (SImode,
9828 true_regnum (operands[0])
9829 + (TARGET_64BIT ? 1 : 2));
9830 if (GET_CODE (operands[1]) == ABS)
9832 tmp = GEN_INT (0x7fff);
9833 tmp = gen_rtx_AND (SImode, operands[0], tmp);
9837 tmp = GEN_INT (0x8000);
9838 tmp = gen_rtx_XOR (SImode, operands[0], tmp);
9844 [(set (match_operand 0 "memory_operand" "")
9845 (match_operator 1 "absneg_operator" [(match_dup 0)]))
9846 (use (match_operand 2 "" ""))
9847 (clobber (reg:CC FLAGS_REG))]
9849 [(parallel [(set (match_dup 0) (match_dup 1))
9850 (clobber (reg:CC FLAGS_REG))])]
9852 enum machine_mode mode = GET_MODE (operands[0]);
9853 int size = mode == XFmode ? 10 : GET_MODE_SIZE (mode);
9856 operands[0] = adjust_address (operands[0], QImode, size - 1);
9857 if (GET_CODE (operands[1]) == ABS)
9859 tmp = gen_int_mode (0x7f, QImode);
9860 tmp = gen_rtx_AND (QImode, operands[0], tmp);
9864 tmp = gen_int_mode (0x80, QImode);
9865 tmp = gen_rtx_XOR (QImode, operands[0], tmp);
9870 ;; Conditionalize these after reload. If they match before reload, we
9871 ;; lose the clobber and ability to use integer instructions.
9873 (define_insn "*negsf2_1"
9874 [(set (match_operand:SF 0 "register_operand" "=f")
9875 (neg:SF (match_operand:SF 1 "register_operand" "0")))]
9876 "TARGET_80387 && reload_completed"
9878 [(set_attr "type" "fsgn")
9879 (set_attr "mode" "SF")])
9881 (define_insn "*negdf2_1"
9882 [(set (match_operand:DF 0 "register_operand" "=f")
9883 (neg:DF (match_operand:DF 1 "register_operand" "0")))]
9884 "TARGET_80387 && reload_completed"
9886 [(set_attr "type" "fsgn")
9887 (set_attr "mode" "DF")])
9889 (define_insn "*negxf2_1"
9890 [(set (match_operand:XF 0 "register_operand" "=f")
9891 (neg:XF (match_operand:XF 1 "register_operand" "0")))]
9892 "TARGET_80387 && reload_completed"
9894 [(set_attr "type" "fsgn")
9895 (set_attr "mode" "XF")])
9897 (define_insn "*abssf2_1"
9898 [(set (match_operand:SF 0 "register_operand" "=f")
9899 (abs:SF (match_operand:SF 1 "register_operand" "0")))]
9900 "TARGET_80387 && reload_completed"
9902 [(set_attr "type" "fsgn")
9903 (set_attr "mode" "SF")])
9905 (define_insn "*absdf2_1"
9906 [(set (match_operand:DF 0 "register_operand" "=f")
9907 (abs:DF (match_operand:DF 1 "register_operand" "0")))]
9908 "TARGET_80387 && reload_completed"
9910 [(set_attr "type" "fsgn")
9911 (set_attr "mode" "DF")])
9913 (define_insn "*absxf2_1"
9914 [(set (match_operand:XF 0 "register_operand" "=f")
9915 (abs:XF (match_operand:XF 1 "register_operand" "0")))]
9916 "TARGET_80387 && reload_completed"
9918 [(set_attr "type" "fsgn")
9919 (set_attr "mode" "DF")])
9921 (define_insn "*negextendsfdf2"
9922 [(set (match_operand:DF 0 "register_operand" "=f")
9923 (neg:DF (float_extend:DF
9924 (match_operand:SF 1 "register_operand" "0"))))]
9925 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
9927 [(set_attr "type" "fsgn")
9928 (set_attr "mode" "DF")])
9930 (define_insn "*negextenddfxf2"
9931 [(set (match_operand:XF 0 "register_operand" "=f")
9932 (neg:XF (float_extend:XF
9933 (match_operand:DF 1 "register_operand" "0"))))]
9936 [(set_attr "type" "fsgn")
9937 (set_attr "mode" "XF")])
9939 (define_insn "*negextendsfxf2"
9940 [(set (match_operand:XF 0 "register_operand" "=f")
9941 (neg:XF (float_extend:XF
9942 (match_operand:SF 1 "register_operand" "0"))))]
9945 [(set_attr "type" "fsgn")
9946 (set_attr "mode" "XF")])
9948 (define_insn "*absextendsfdf2"
9949 [(set (match_operand:DF 0 "register_operand" "=f")
9950 (abs:DF (float_extend:DF
9951 (match_operand:SF 1 "register_operand" "0"))))]
9952 "TARGET_80387 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)"
9954 [(set_attr "type" "fsgn")
9955 (set_attr "mode" "DF")])
9957 (define_insn "*absextenddfxf2"
9958 [(set (match_operand:XF 0 "register_operand" "=f")
9959 (abs:XF (float_extend:XF
9960 (match_operand:DF 1 "register_operand" "0"))))]
9963 [(set_attr "type" "fsgn")
9964 (set_attr "mode" "XF")])
9966 (define_insn "*absextendsfxf2"
9967 [(set (match_operand:XF 0 "register_operand" "=f")
9968 (abs:XF (float_extend:XF
9969 (match_operand:SF 1 "register_operand" "0"))))]
9972 [(set_attr "type" "fsgn")
9973 (set_attr "mode" "XF")])
9975 ;; One complement instructions
9977 (define_expand "one_cmpldi2"
9978 [(set (match_operand:DI 0 "nonimmediate_operand" "")
9979 (not:DI (match_operand:DI 1 "nonimmediate_operand" "")))]
9981 "ix86_expand_unary_operator (NOT, DImode, operands); DONE;")
9983 (define_insn "*one_cmpldi2_1_rex64"
9984 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9985 (not:DI (match_operand:DI 1 "nonimmediate_operand" "0")))]
9986 "TARGET_64BIT && ix86_unary_operator_ok (NOT, DImode, operands)"
9988 [(set_attr "type" "negnot")
9989 (set_attr "mode" "DI")])
9991 (define_insn "*one_cmpldi2_2_rex64"
9992 [(set (reg FLAGS_REG)
9993 (compare (not:DI (match_operand:DI 1 "nonimmediate_operand" "0"))
9995 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
9996 (not:DI (match_dup 1)))]
9997 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
9998 && ix86_unary_operator_ok (NOT, DImode, operands)"
10000 [(set_attr "type" "alu1")
10001 (set_attr "mode" "DI")])
10004 [(set (match_operand 0 "flags_reg_operand" "")
10005 (match_operator 2 "compare_operator"
10006 [(not:DI (match_operand:DI 3 "nonimmediate_operand" ""))
10008 (set (match_operand:DI 1 "nonimmediate_operand" "")
10009 (not:DI (match_dup 3)))]
10010 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)"
10011 [(parallel [(set (match_dup 0)
10013 [(xor:DI (match_dup 3) (const_int -1))
10016 (xor:DI (match_dup 3) (const_int -1)))])]
10019 (define_expand "one_cmplsi2"
10020 [(set (match_operand:SI 0 "nonimmediate_operand" "")
10021 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
10023 "ix86_expand_unary_operator (NOT, SImode, operands); DONE;")
10025 (define_insn "*one_cmplsi2_1"
10026 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10027 (not:SI (match_operand:SI 1 "nonimmediate_operand" "0")))]
10028 "ix86_unary_operator_ok (NOT, SImode, operands)"
10030 [(set_attr "type" "negnot")
10031 (set_attr "mode" "SI")])
10033 ;; ??? Currently never generated - xor is used instead.
10034 (define_insn "*one_cmplsi2_1_zext"
10035 [(set (match_operand:DI 0 "register_operand" "=r")
10036 (zero_extend:DI (not:SI (match_operand:SI 1 "register_operand" "0"))))]
10037 "TARGET_64BIT && ix86_unary_operator_ok (NOT, SImode, operands)"
10039 [(set_attr "type" "negnot")
10040 (set_attr "mode" "SI")])
10042 (define_insn "*one_cmplsi2_2"
10043 [(set (reg FLAGS_REG)
10044 (compare (not:SI (match_operand:SI 1 "nonimmediate_operand" "0"))
10046 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10047 (not:SI (match_dup 1)))]
10048 "ix86_match_ccmode (insn, CCNOmode)
10049 && ix86_unary_operator_ok (NOT, SImode, operands)"
10051 [(set_attr "type" "alu1")
10052 (set_attr "mode" "SI")])
10055 [(set (match_operand 0 "flags_reg_operand" "")
10056 (match_operator 2 "compare_operator"
10057 [(not:SI (match_operand:SI 3 "nonimmediate_operand" ""))
10059 (set (match_operand:SI 1 "nonimmediate_operand" "")
10060 (not:SI (match_dup 3)))]
10061 "ix86_match_ccmode (insn, CCNOmode)"
10062 [(parallel [(set (match_dup 0)
10063 (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
10066 (xor:SI (match_dup 3) (const_int -1)))])]
10069 ;; ??? Currently never generated - xor is used instead.
10070 (define_insn "*one_cmplsi2_2_zext"
10071 [(set (reg FLAGS_REG)
10072 (compare (not:SI (match_operand:SI 1 "register_operand" "0"))
10074 (set (match_operand:DI 0 "register_operand" "=r")
10075 (zero_extend:DI (not:SI (match_dup 1))))]
10076 "TARGET_64BIT && ix86_match_ccmode (insn, CCNOmode)
10077 && ix86_unary_operator_ok (NOT, SImode, operands)"
10079 [(set_attr "type" "alu1")
10080 (set_attr "mode" "SI")])
10083 [(set (match_operand 0 "flags_reg_operand" "")
10084 (match_operator 2 "compare_operator"
10085 [(not:SI (match_operand:SI 3 "register_operand" ""))
10087 (set (match_operand:DI 1 "register_operand" "")
10088 (zero_extend:DI (not:SI (match_dup 3))))]
10089 "ix86_match_ccmode (insn, CCNOmode)"
10090 [(parallel [(set (match_dup 0)
10091 (match_op_dup 2 [(xor:SI (match_dup 3) (const_int -1))
10094 (zero_extend:DI (xor:SI (match_dup 3) (const_int -1))))])]
10097 (define_expand "one_cmplhi2"
10098 [(set (match_operand:HI 0 "nonimmediate_operand" "")
10099 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
10100 "TARGET_HIMODE_MATH"
10101 "ix86_expand_unary_operator (NOT, HImode, operands); DONE;")
10103 (define_insn "*one_cmplhi2_1"
10104 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10105 (not:HI (match_operand:HI 1 "nonimmediate_operand" "0")))]
10106 "ix86_unary_operator_ok (NOT, HImode, operands)"
10108 [(set_attr "type" "negnot")
10109 (set_attr "mode" "HI")])
10111 (define_insn "*one_cmplhi2_2"
10112 [(set (reg FLAGS_REG)
10113 (compare (not:HI (match_operand:HI 1 "nonimmediate_operand" "0"))
10115 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10116 (not:HI (match_dup 1)))]
10117 "ix86_match_ccmode (insn, CCNOmode)
10118 && ix86_unary_operator_ok (NEG, HImode, operands)"
10120 [(set_attr "type" "alu1")
10121 (set_attr "mode" "HI")])
10124 [(set (match_operand 0 "flags_reg_operand" "")
10125 (match_operator 2 "compare_operator"
10126 [(not:HI (match_operand:HI 3 "nonimmediate_operand" ""))
10128 (set (match_operand:HI 1 "nonimmediate_operand" "")
10129 (not:HI (match_dup 3)))]
10130 "ix86_match_ccmode (insn, CCNOmode)"
10131 [(parallel [(set (match_dup 0)
10132 (match_op_dup 2 [(xor:HI (match_dup 3) (const_int -1))
10135 (xor:HI (match_dup 3) (const_int -1)))])]
10138 ;; %%% Potential partial reg stall on alternative 1. What to do?
10139 (define_expand "one_cmplqi2"
10140 [(set (match_operand:QI 0 "nonimmediate_operand" "")
10141 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
10142 "TARGET_QIMODE_MATH"
10143 "ix86_expand_unary_operator (NOT, QImode, operands); DONE;")
10145 (define_insn "*one_cmplqi2_1"
10146 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10147 (not:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")))]
10148 "ix86_unary_operator_ok (NOT, QImode, operands)"
10152 [(set_attr "type" "negnot")
10153 (set_attr "mode" "QI,SI")])
10155 (define_insn "*one_cmplqi2_2"
10156 [(set (reg FLAGS_REG)
10157 (compare (not:QI (match_operand:QI 1 "nonimmediate_operand" "0"))
10159 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10160 (not:QI (match_dup 1)))]
10161 "ix86_match_ccmode (insn, CCNOmode)
10162 && ix86_unary_operator_ok (NOT, QImode, operands)"
10164 [(set_attr "type" "alu1")
10165 (set_attr "mode" "QI")])
10168 [(set (match_operand 0 "flags_reg_operand" "")
10169 (match_operator 2 "compare_operator"
10170 [(not:QI (match_operand:QI 3 "nonimmediate_operand" ""))
10172 (set (match_operand:QI 1 "nonimmediate_operand" "")
10173 (not:QI (match_dup 3)))]
10174 "ix86_match_ccmode (insn, CCNOmode)"
10175 [(parallel [(set (match_dup 0)
10176 (match_op_dup 2 [(xor:QI (match_dup 3) (const_int -1))
10179 (xor:QI (match_dup 3) (const_int -1)))])]
10182 ;; Arithmetic shift instructions
10184 ;; DImode shifts are implemented using the i386 "shift double" opcode,
10185 ;; which is written as "sh[lr]d[lw] imm,reg,reg/mem". If the shift count
10186 ;; is variable, then the count is in %cl and the "imm" operand is dropped
10187 ;; from the assembler input.
10189 ;; This instruction shifts the target reg/mem as usual, but instead of
10190 ;; shifting in zeros, bits are shifted in from reg operand. If the insn
10191 ;; is a left shift double, bits are taken from the high order bits of
10192 ;; reg, else if the insn is a shift right double, bits are taken from the
10193 ;; low order bits of reg. So if %eax is "1234" and %edx is "5678",
10194 ;; "shldl $8,%edx,%eax" leaves %edx unchanged and sets %eax to "2345".
10196 ;; Since sh[lr]d does not change the `reg' operand, that is done
10197 ;; separately, making all shifts emit pairs of shift double and normal
10198 ;; shift. Since sh[lr]d does not shift more than 31 bits, and we wish to
10199 ;; support a 63 bit shift, each shift where the count is in a reg expands
10200 ;; to a pair of shifts, a branch, a shift by 32 and a label.
10202 ;; If the shift count is a constant, we need never emit more than one
10203 ;; shift pair, instead using moves and sign extension for counts greater
10206 (define_expand "ashlti3"
10207 [(parallel [(set (match_operand:TI 0 "register_operand" "")
10208 (ashift:TI (match_operand:TI 1 "register_operand" "")
10209 (match_operand:QI 2 "nonmemory_operand" "")))
10210 (clobber (reg:CC FLAGS_REG))])]
10213 if (! immediate_operand (operands[2], QImode))
10215 emit_insn (gen_ashlti3_1 (operands[0], operands[1], operands[2]));
10218 ix86_expand_binary_operator (ASHIFT, TImode, operands);
10222 (define_insn "ashlti3_1"
10223 [(set (match_operand:TI 0 "register_operand" "=r")
10224 (ashift:TI (match_operand:TI 1 "register_operand" "0")
10225 (match_operand:QI 2 "register_operand" "c")))
10226 (clobber (match_scratch:DI 3 "=&r"))
10227 (clobber (reg:CC FLAGS_REG))]
10230 [(set_attr "type" "multi")])
10232 (define_insn "*ashlti3_2"
10233 [(set (match_operand:TI 0 "register_operand" "=r")
10234 (ashift:TI (match_operand:TI 1 "register_operand" "0")
10235 (match_operand:QI 2 "immediate_operand" "O")))
10236 (clobber (reg:CC FLAGS_REG))]
10239 [(set_attr "type" "multi")])
10242 [(set (match_operand:TI 0 "register_operand" "")
10243 (ashift:TI (match_operand:TI 1 "nonmemory_operand" "")
10244 (match_operand:QI 2 "register_operand" "")))
10245 (clobber (match_scratch:DI 3 ""))
10246 (clobber (reg:CC FLAGS_REG))]
10247 "TARGET_64BIT && reload_completed"
10249 "ix86_split_ashl (operands, operands[3], TImode); DONE;")
10252 [(set (match_operand:TI 0 "register_operand" "")
10253 (ashift:TI (match_operand:TI 1 "register_operand" "")
10254 (match_operand:QI 2 "immediate_operand" "")))
10255 (clobber (reg:CC FLAGS_REG))]
10256 "TARGET_64BIT && reload_completed"
10258 "ix86_split_ashl (operands, NULL_RTX, TImode); DONE;")
10260 (define_insn "x86_64_shld"
10261 [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m,r*m")
10262 (ior:DI (ashift:DI (match_dup 0)
10263 (match_operand:QI 2 "nonmemory_operand" "J,c"))
10264 (lshiftrt:DI (match_operand:DI 1 "register_operand" "r,r")
10265 (minus:QI (const_int 64) (match_dup 2)))))
10266 (clobber (reg:CC FLAGS_REG))]
10269 shld{q}\t{%2, %1, %0|%0, %1, %2}
10270 shld{q}\t{%s2%1, %0|%0, %1, %2}"
10271 [(set_attr "type" "ishift")
10272 (set_attr "prefix_0f" "1")
10273 (set_attr "mode" "DI")
10274 (set_attr "athlon_decode" "vector")])
10276 (define_expand "x86_64_shift_adj"
10277 [(set (reg:CCZ FLAGS_REG)
10278 (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
10281 (set (match_operand:DI 0 "register_operand" "")
10282 (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10283 (match_operand:DI 1 "register_operand" "")
10286 (if_then_else:DI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10287 (match_operand:DI 3 "register_operand" "r")
10292 (define_expand "ashldi3"
10293 [(set (match_operand:DI 0 "shiftdi_operand" "")
10294 (ashift:DI (match_operand:DI 1 "ashldi_input_operand" "")
10295 (match_operand:QI 2 "nonmemory_operand" "")))]
10297 "ix86_expand_binary_operator (ASHIFT, DImode, operands); DONE;")
10299 (define_insn "*ashldi3_1_rex64"
10300 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,r")
10301 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0,l")
10302 (match_operand:QI 2 "nonmemory_operand" "cJ,M")))
10303 (clobber (reg:CC FLAGS_REG))]
10304 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10306 switch (get_attr_type (insn))
10309 gcc_assert (operands[2] == const1_rtx);
10310 gcc_assert (rtx_equal_p (operands[0], operands[1]));
10311 return "add{q}\t{%0, %0|%0, %0}";
10314 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
10315 gcc_assert ((unsigned HOST_WIDE_INT) INTVAL (operands[2]) <= 3);
10316 operands[1] = gen_rtx_MULT (DImode, operands[1],
10317 GEN_INT (1 << INTVAL (operands[2])));
10318 return "lea{q}\t{%a1, %0|%0, %a1}";
10321 if (REG_P (operands[2]))
10322 return "sal{q}\t{%b2, %0|%0, %b2}";
10323 else if (operands[2] == const1_rtx
10324 && (TARGET_SHIFT1 || optimize_size))
10325 return "sal{q}\t%0";
10327 return "sal{q}\t{%2, %0|%0, %2}";
10330 [(set (attr "type")
10331 (cond [(eq_attr "alternative" "1")
10332 (const_string "lea")
10333 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10335 (match_operand 0 "register_operand" ""))
10336 (match_operand 2 "const1_operand" ""))
10337 (const_string "alu")
10339 (const_string "ishift")))
10340 (set_attr "mode" "DI")])
10342 ;; Convert lea to the lea pattern to avoid flags dependency.
10344 [(set (match_operand:DI 0 "register_operand" "")
10345 (ashift:DI (match_operand:DI 1 "index_register_operand" "")
10346 (match_operand:QI 2 "immediate_operand" "")))
10347 (clobber (reg:CC FLAGS_REG))]
10348 "TARGET_64BIT && reload_completed
10349 && true_regnum (operands[0]) != true_regnum (operands[1])"
10350 [(set (match_dup 0)
10351 (mult:DI (match_dup 1)
10353 "operands[2] = gen_int_mode (1 << INTVAL (operands[2]), DImode);")
10355 ;; This pattern can't accept a variable shift count, since shifts by
10356 ;; zero don't affect the flags. We assume that shifts by constant
10357 ;; zero are optimized away.
10358 (define_insn "*ashldi3_cmp_rex64"
10359 [(set (reg FLAGS_REG)
10361 (ashift:DI (match_operand:DI 1 "nonimmediate_operand" "0")
10362 (match_operand:QI 2 "immediate_operand" "e"))
10364 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
10365 (ashift:DI (match_dup 1) (match_dup 2)))]
10366 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10367 && ix86_binary_operator_ok (ASHIFT, DImode, operands)"
10369 switch (get_attr_type (insn))
10372 gcc_assert (operands[2] == const1_rtx);
10373 return "add{q}\t{%0, %0|%0, %0}";
10376 if (REG_P (operands[2]))
10377 return "sal{q}\t{%b2, %0|%0, %b2}";
10378 else if (operands[2] == const1_rtx
10379 && (TARGET_SHIFT1 || optimize_size))
10380 return "sal{q}\t%0";
10382 return "sal{q}\t{%2, %0|%0, %2}";
10385 [(set (attr "type")
10386 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10388 (match_operand 0 "register_operand" ""))
10389 (match_operand 2 "const1_operand" ""))
10390 (const_string "alu")
10392 (const_string "ishift")))
10393 (set_attr "mode" "DI")])
10395 (define_insn "*ashldi3_1"
10396 [(set (match_operand:DI 0 "register_operand" "=&r,r")
10397 (ashift:DI (match_operand:DI 1 "reg_or_pm1_operand" "n,0")
10398 (match_operand:QI 2 "nonmemory_operand" "Jc,Jc")))
10399 (clobber (reg:CC FLAGS_REG))]
10402 [(set_attr "type" "multi")])
10404 ;; By default we don't ask for a scratch register, because when DImode
10405 ;; values are manipulated, registers are already at a premium. But if
10406 ;; we have one handy, we won't turn it away.
10408 [(match_scratch:SI 3 "r")
10409 (parallel [(set (match_operand:DI 0 "register_operand" "")
10410 (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
10411 (match_operand:QI 2 "nonmemory_operand" "")))
10412 (clobber (reg:CC FLAGS_REG))])
10414 "!TARGET_64BIT && TARGET_CMOVE"
10416 "ix86_split_ashl (operands, operands[3], DImode); DONE;")
10419 [(set (match_operand:DI 0 "register_operand" "")
10420 (ashift:DI (match_operand:DI 1 "nonmemory_operand" "")
10421 (match_operand:QI 2 "nonmemory_operand" "")))
10422 (clobber (reg:CC FLAGS_REG))]
10423 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
10424 ? flow2_completed : reload_completed)"
10426 "ix86_split_ashl (operands, NULL_RTX, DImode); DONE;")
10428 (define_insn "x86_shld_1"
10429 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
10430 (ior:SI (ashift:SI (match_dup 0)
10431 (match_operand:QI 2 "nonmemory_operand" "I,c"))
10432 (lshiftrt:SI (match_operand:SI 1 "register_operand" "r,r")
10433 (minus:QI (const_int 32) (match_dup 2)))))
10434 (clobber (reg:CC FLAGS_REG))]
10437 shld{l}\t{%2, %1, %0|%0, %1, %2}
10438 shld{l}\t{%s2%1, %0|%0, %1, %2}"
10439 [(set_attr "type" "ishift")
10440 (set_attr "prefix_0f" "1")
10441 (set_attr "mode" "SI")
10442 (set_attr "pent_pair" "np")
10443 (set_attr "athlon_decode" "vector")])
10445 (define_expand "x86_shift_adj_1"
10446 [(set (reg:CCZ FLAGS_REG)
10447 (compare:CCZ (and:QI (match_operand:QI 2 "register_operand" "")
10450 (set (match_operand:SI 0 "register_operand" "")
10451 (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10452 (match_operand:SI 1 "register_operand" "")
10455 (if_then_else:SI (ne (reg:CCZ FLAGS_REG) (const_int 0))
10456 (match_operand:SI 3 "register_operand" "r")
10461 (define_expand "x86_shift_adj_2"
10462 [(use (match_operand:SI 0 "register_operand" ""))
10463 (use (match_operand:SI 1 "register_operand" ""))
10464 (use (match_operand:QI 2 "register_operand" ""))]
10467 rtx label = gen_label_rtx ();
10470 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
10472 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
10473 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
10474 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
10475 gen_rtx_LABEL_REF (VOIDmode, label),
10477 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
10478 JUMP_LABEL (tmp) = label;
10480 emit_move_insn (operands[0], operands[1]);
10481 ix86_expand_clear (operands[1]);
10483 emit_label (label);
10484 LABEL_NUSES (label) = 1;
10489 (define_expand "ashlsi3"
10490 [(set (match_operand:SI 0 "nonimmediate_operand" "")
10491 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "")
10492 (match_operand:QI 2 "nonmemory_operand" "")))
10493 (clobber (reg:CC FLAGS_REG))]
10495 "ix86_expand_binary_operator (ASHIFT, SImode, operands); DONE;")
10497 (define_insn "*ashlsi3_1"
10498 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,r")
10499 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0,l")
10500 (match_operand:QI 2 "nonmemory_operand" "cI,M")))
10501 (clobber (reg:CC FLAGS_REG))]
10502 "ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10504 switch (get_attr_type (insn))
10507 gcc_assert (operands[2] == const1_rtx);
10508 gcc_assert (rtx_equal_p (operands[0], operands[1]));
10509 return "add{l}\t{%0, %0|%0, %0}";
10515 if (REG_P (operands[2]))
10516 return "sal{l}\t{%b2, %0|%0, %b2}";
10517 else if (operands[2] == const1_rtx
10518 && (TARGET_SHIFT1 || optimize_size))
10519 return "sal{l}\t%0";
10521 return "sal{l}\t{%2, %0|%0, %2}";
10524 [(set (attr "type")
10525 (cond [(eq_attr "alternative" "1")
10526 (const_string "lea")
10527 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10529 (match_operand 0 "register_operand" ""))
10530 (match_operand 2 "const1_operand" ""))
10531 (const_string "alu")
10533 (const_string "ishift")))
10534 (set_attr "mode" "SI")])
10536 ;; Convert lea to the lea pattern to avoid flags dependency.
10538 [(set (match_operand 0 "register_operand" "")
10539 (ashift (match_operand 1 "index_register_operand" "")
10540 (match_operand:QI 2 "const_int_operand" "")))
10541 (clobber (reg:CC FLAGS_REG))]
10543 && true_regnum (operands[0]) != true_regnum (operands[1])
10544 && GET_MODE_SIZE (GET_MODE (operands[0])) <= 4"
10548 enum machine_mode mode = GET_MODE (operands[0]);
10550 if (GET_MODE_SIZE (mode) < 4)
10551 operands[0] = gen_lowpart (SImode, operands[0]);
10553 operands[1] = gen_lowpart (Pmode, operands[1]);
10554 operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
10556 pat = gen_rtx_MULT (Pmode, operands[1], operands[2]);
10557 if (Pmode != SImode)
10558 pat = gen_rtx_SUBREG (SImode, pat, 0);
10559 emit_insn (gen_rtx_SET (VOIDmode, operands[0], pat));
10563 ;; Rare case of shifting RSP is handled by generating move and shift
10565 [(set (match_operand 0 "register_operand" "")
10566 (ashift (match_operand 1 "register_operand" "")
10567 (match_operand:QI 2 "const_int_operand" "")))
10568 (clobber (reg:CC FLAGS_REG))]
10570 && true_regnum (operands[0]) != true_regnum (operands[1])"
10574 emit_move_insn (operands[1], operands[0]);
10575 pat = gen_rtx_SET (VOIDmode, operands[0],
10576 gen_rtx_ASHIFT (GET_MODE (operands[0]),
10577 operands[0], operands[2]));
10578 clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
10579 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, pat, clob)));
10583 (define_insn "*ashlsi3_1_zext"
10584 [(set (match_operand:DI 0 "register_operand" "=r,r")
10585 (zero_extend:DI (ashift:SI (match_operand:SI 1 "register_operand" "0,l")
10586 (match_operand:QI 2 "nonmemory_operand" "cI,M"))))
10587 (clobber (reg:CC FLAGS_REG))]
10588 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10590 switch (get_attr_type (insn))
10593 gcc_assert (operands[2] == const1_rtx);
10594 return "add{l}\t{%k0, %k0|%k0, %k0}";
10600 if (REG_P (operands[2]))
10601 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10602 else if (operands[2] == const1_rtx
10603 && (TARGET_SHIFT1 || optimize_size))
10604 return "sal{l}\t%k0";
10606 return "sal{l}\t{%2, %k0|%k0, %2}";
10609 [(set (attr "type")
10610 (cond [(eq_attr "alternative" "1")
10611 (const_string "lea")
10612 (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10614 (match_operand 2 "const1_operand" ""))
10615 (const_string "alu")
10617 (const_string "ishift")))
10618 (set_attr "mode" "SI")])
10620 ;; Convert lea to the lea pattern to avoid flags dependency.
10622 [(set (match_operand:DI 0 "register_operand" "")
10623 (zero_extend:DI (ashift (match_operand 1 "register_operand" "")
10624 (match_operand:QI 2 "const_int_operand" ""))))
10625 (clobber (reg:CC FLAGS_REG))]
10626 "TARGET_64BIT && reload_completed
10627 && true_regnum (operands[0]) != true_regnum (operands[1])"
10628 [(set (match_dup 0) (zero_extend:DI
10629 (subreg:SI (mult:SI (match_dup 1)
10630 (match_dup 2)) 0)))]
10632 operands[1] = gen_lowpart (Pmode, operands[1]);
10633 operands[2] = gen_int_mode (1 << INTVAL (operands[2]), Pmode);
10636 ;; This pattern can't accept a variable shift count, since shifts by
10637 ;; zero don't affect the flags. We assume that shifts by constant
10638 ;; zero are optimized away.
10639 (define_insn "*ashlsi3_cmp"
10640 [(set (reg FLAGS_REG)
10642 (ashift:SI (match_operand:SI 1 "nonimmediate_operand" "0")
10643 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10645 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
10646 (ashift:SI (match_dup 1) (match_dup 2)))]
10647 "ix86_match_ccmode (insn, CCGOCmode)
10648 && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10650 switch (get_attr_type (insn))
10653 gcc_assert (operands[2] == const1_rtx);
10654 return "add{l}\t{%0, %0|%0, %0}";
10657 if (REG_P (operands[2]))
10658 return "sal{l}\t{%b2, %0|%0, %b2}";
10659 else if (operands[2] == const1_rtx
10660 && (TARGET_SHIFT1 || optimize_size))
10661 return "sal{l}\t%0";
10663 return "sal{l}\t{%2, %0|%0, %2}";
10666 [(set (attr "type")
10667 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10669 (match_operand 0 "register_operand" ""))
10670 (match_operand 2 "const1_operand" ""))
10671 (const_string "alu")
10673 (const_string "ishift")))
10674 (set_attr "mode" "SI")])
10676 (define_insn "*ashlsi3_cmp_zext"
10677 [(set (reg FLAGS_REG)
10679 (ashift:SI (match_operand:SI 1 "register_operand" "0")
10680 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10682 (set (match_operand:DI 0 "register_operand" "=r")
10683 (zero_extend:DI (ashift:SI (match_dup 1) (match_dup 2))))]
10684 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
10685 && ix86_binary_operator_ok (ASHIFT, SImode, operands)"
10687 switch (get_attr_type (insn))
10690 gcc_assert (operands[2] == const1_rtx);
10691 return "add{l}\t{%k0, %k0|%k0, %k0}";
10694 if (REG_P (operands[2]))
10695 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10696 else if (operands[2] == const1_rtx
10697 && (TARGET_SHIFT1 || optimize_size))
10698 return "sal{l}\t%k0";
10700 return "sal{l}\t{%2, %k0|%k0, %2}";
10703 [(set (attr "type")
10704 (cond [(and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10706 (match_operand 2 "const1_operand" ""))
10707 (const_string "alu")
10709 (const_string "ishift")))
10710 (set_attr "mode" "SI")])
10712 (define_expand "ashlhi3"
10713 [(set (match_operand:HI 0 "nonimmediate_operand" "")
10714 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "")
10715 (match_operand:QI 2 "nonmemory_operand" "")))
10716 (clobber (reg:CC FLAGS_REG))]
10717 "TARGET_HIMODE_MATH"
10718 "ix86_expand_binary_operator (ASHIFT, HImode, operands); DONE;")
10720 (define_insn "*ashlhi3_1_lea"
10721 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
10722 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
10723 (match_operand:QI 2 "nonmemory_operand" "cI,M")))
10724 (clobber (reg:CC FLAGS_REG))]
10725 "!TARGET_PARTIAL_REG_STALL
10726 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10728 switch (get_attr_type (insn))
10733 gcc_assert (operands[2] == const1_rtx);
10734 return "add{w}\t{%0, %0|%0, %0}";
10737 if (REG_P (operands[2]))
10738 return "sal{w}\t{%b2, %0|%0, %b2}";
10739 else if (operands[2] == const1_rtx
10740 && (TARGET_SHIFT1 || optimize_size))
10741 return "sal{w}\t%0";
10743 return "sal{w}\t{%2, %0|%0, %2}";
10746 [(set (attr "type")
10747 (cond [(eq_attr "alternative" "1")
10748 (const_string "lea")
10749 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10751 (match_operand 0 "register_operand" ""))
10752 (match_operand 2 "const1_operand" ""))
10753 (const_string "alu")
10755 (const_string "ishift")))
10756 (set_attr "mode" "HI,SI")])
10758 (define_insn "*ashlhi3_1"
10759 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10760 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
10761 (match_operand:QI 2 "nonmemory_operand" "cI")))
10762 (clobber (reg:CC FLAGS_REG))]
10763 "TARGET_PARTIAL_REG_STALL
10764 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10766 switch (get_attr_type (insn))
10769 gcc_assert (operands[2] == const1_rtx);
10770 return "add{w}\t{%0, %0|%0, %0}";
10773 if (REG_P (operands[2]))
10774 return "sal{w}\t{%b2, %0|%0, %b2}";
10775 else if (operands[2] == const1_rtx
10776 && (TARGET_SHIFT1 || optimize_size))
10777 return "sal{w}\t%0";
10779 return "sal{w}\t{%2, %0|%0, %2}";
10782 [(set (attr "type")
10783 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10785 (match_operand 0 "register_operand" ""))
10786 (match_operand 2 "const1_operand" ""))
10787 (const_string "alu")
10789 (const_string "ishift")))
10790 (set_attr "mode" "HI")])
10792 ;; This pattern can't accept a variable shift count, since shifts by
10793 ;; zero don't affect the flags. We assume that shifts by constant
10794 ;; zero are optimized away.
10795 (define_insn "*ashlhi3_cmp"
10796 [(set (reg FLAGS_REG)
10798 (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
10799 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10801 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
10802 (ashift:HI (match_dup 1) (match_dup 2)))]
10803 "ix86_match_ccmode (insn, CCGOCmode)
10804 && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
10806 switch (get_attr_type (insn))
10809 gcc_assert (operands[2] == const1_rtx);
10810 return "add{w}\t{%0, %0|%0, %0}";
10813 if (REG_P (operands[2]))
10814 return "sal{w}\t{%b2, %0|%0, %b2}";
10815 else if (operands[2] == const1_rtx
10816 && (TARGET_SHIFT1 || optimize_size))
10817 return "sal{w}\t%0";
10819 return "sal{w}\t{%2, %0|%0, %2}";
10822 [(set (attr "type")
10823 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10825 (match_operand 0 "register_operand" ""))
10826 (match_operand 2 "const1_operand" ""))
10827 (const_string "alu")
10829 (const_string "ishift")))
10830 (set_attr "mode" "HI")])
10832 (define_expand "ashlqi3"
10833 [(set (match_operand:QI 0 "nonimmediate_operand" "")
10834 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "")
10835 (match_operand:QI 2 "nonmemory_operand" "")))
10836 (clobber (reg:CC FLAGS_REG))]
10837 "TARGET_QIMODE_MATH"
10838 "ix86_expand_binary_operator (ASHIFT, QImode, operands); DONE;")
10840 ;; %%% Potential partial reg stall on alternative 2. What to do?
10842 (define_insn "*ashlqi3_1_lea"
10843 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r")
10844 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
10845 (match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
10846 (clobber (reg:CC FLAGS_REG))]
10847 "!TARGET_PARTIAL_REG_STALL
10848 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10850 switch (get_attr_type (insn))
10855 gcc_assert (operands[2] == const1_rtx);
10856 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
10857 return "add{l}\t{%k0, %k0|%k0, %k0}";
10859 return "add{b}\t{%0, %0|%0, %0}";
10862 if (REG_P (operands[2]))
10864 if (get_attr_mode (insn) == MODE_SI)
10865 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10867 return "sal{b}\t{%b2, %0|%0, %b2}";
10869 else if (operands[2] == const1_rtx
10870 && (TARGET_SHIFT1 || optimize_size))
10872 if (get_attr_mode (insn) == MODE_SI)
10873 return "sal{l}\t%0";
10875 return "sal{b}\t%0";
10879 if (get_attr_mode (insn) == MODE_SI)
10880 return "sal{l}\t{%2, %k0|%k0, %2}";
10882 return "sal{b}\t{%2, %0|%0, %2}";
10886 [(set (attr "type")
10887 (cond [(eq_attr "alternative" "2")
10888 (const_string "lea")
10889 (and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10891 (match_operand 0 "register_operand" ""))
10892 (match_operand 2 "const1_operand" ""))
10893 (const_string "alu")
10895 (const_string "ishift")))
10896 (set_attr "mode" "QI,SI,SI")])
10898 (define_insn "*ashlqi3_1"
10899 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
10900 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
10901 (match_operand:QI 2 "nonmemory_operand" "cI,cI")))
10902 (clobber (reg:CC FLAGS_REG))]
10903 "TARGET_PARTIAL_REG_STALL
10904 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10906 switch (get_attr_type (insn))
10909 gcc_assert (operands[2] == const1_rtx);
10910 if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
10911 return "add{l}\t{%k0, %k0|%k0, %k0}";
10913 return "add{b}\t{%0, %0|%0, %0}";
10916 if (REG_P (operands[2]))
10918 if (get_attr_mode (insn) == MODE_SI)
10919 return "sal{l}\t{%b2, %k0|%k0, %b2}";
10921 return "sal{b}\t{%b2, %0|%0, %b2}";
10923 else if (operands[2] == const1_rtx
10924 && (TARGET_SHIFT1 || optimize_size))
10926 if (get_attr_mode (insn) == MODE_SI)
10927 return "sal{l}\t%0";
10929 return "sal{b}\t%0";
10933 if (get_attr_mode (insn) == MODE_SI)
10934 return "sal{l}\t{%2, %k0|%k0, %2}";
10936 return "sal{b}\t{%2, %0|%0, %2}";
10940 [(set (attr "type")
10941 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10943 (match_operand 0 "register_operand" ""))
10944 (match_operand 2 "const1_operand" ""))
10945 (const_string "alu")
10947 (const_string "ishift")))
10948 (set_attr "mode" "QI,SI")])
10950 ;; This pattern can't accept a variable shift count, since shifts by
10951 ;; zero don't affect the flags. We assume that shifts by constant
10952 ;; zero are optimized away.
10953 (define_insn "*ashlqi3_cmp"
10954 [(set (reg FLAGS_REG)
10956 (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0")
10957 (match_operand:QI 2 "const_1_to_31_operand" "I"))
10959 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
10960 (ashift:QI (match_dup 1) (match_dup 2)))]
10961 "ix86_match_ccmode (insn, CCGOCmode)
10962 && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
10964 switch (get_attr_type (insn))
10967 gcc_assert (operands[2] == const1_rtx);
10968 return "add{b}\t{%0, %0|%0, %0}";
10971 if (REG_P (operands[2]))
10972 return "sal{b}\t{%b2, %0|%0, %b2}";
10973 else if (operands[2] == const1_rtx
10974 && (TARGET_SHIFT1 || optimize_size))
10975 return "sal{b}\t%0";
10977 return "sal{b}\t{%2, %0|%0, %2}";
10980 [(set (attr "type")
10981 (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
10983 (match_operand 0 "register_operand" ""))
10984 (match_operand 2 "const1_operand" ""))
10985 (const_string "alu")
10987 (const_string "ishift")))
10988 (set_attr "mode" "QI")])
10990 ;; See comment above `ashldi3' about how this works.
10992 (define_expand "ashrti3"
10993 [(parallel [(set (match_operand:TI 0 "register_operand" "")
10994 (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
10995 (match_operand:QI 2 "nonmemory_operand" "")))
10996 (clobber (reg:CC FLAGS_REG))])]
10999 if (! immediate_operand (operands[2], QImode))
11001 emit_insn (gen_ashrti3_1 (operands[0], operands[1], operands[2]));
11004 ix86_expand_binary_operator (ASHIFTRT, TImode, operands);
11008 (define_insn "ashrti3_1"
11009 [(set (match_operand:TI 0 "register_operand" "=r")
11010 (ashiftrt:TI (match_operand:TI 1 "register_operand" "0")
11011 (match_operand:QI 2 "register_operand" "c")))
11012 (clobber (match_scratch:DI 3 "=&r"))
11013 (clobber (reg:CC FLAGS_REG))]
11016 [(set_attr "type" "multi")])
11018 (define_insn "*ashrti3_2"
11019 [(set (match_operand:TI 0 "register_operand" "=r")
11020 (ashiftrt:TI (match_operand:TI 1 "register_operand" "0")
11021 (match_operand:QI 2 "immediate_operand" "O")))
11022 (clobber (reg:CC FLAGS_REG))]
11025 [(set_attr "type" "multi")])
11028 [(set (match_operand:TI 0 "register_operand" "")
11029 (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
11030 (match_operand:QI 2 "register_operand" "")))
11031 (clobber (match_scratch:DI 3 ""))
11032 (clobber (reg:CC FLAGS_REG))]
11033 "TARGET_64BIT && reload_completed"
11035 "ix86_split_ashr (operands, operands[3], TImode); DONE;")
11038 [(set (match_operand:TI 0 "register_operand" "")
11039 (ashiftrt:TI (match_operand:TI 1 "register_operand" "")
11040 (match_operand:QI 2 "immediate_operand" "")))
11041 (clobber (reg:CC FLAGS_REG))]
11042 "TARGET_64BIT && reload_completed"
11044 "ix86_split_ashr (operands, NULL_RTX, TImode); DONE;")
11046 (define_insn "x86_64_shrd"
11047 [(set (match_operand:DI 0 "nonimmediate_operand" "+r*m,r*m")
11048 (ior:DI (ashiftrt:DI (match_dup 0)
11049 (match_operand:QI 2 "nonmemory_operand" "J,c"))
11050 (ashift:DI (match_operand:DI 1 "register_operand" "r,r")
11051 (minus:QI (const_int 64) (match_dup 2)))))
11052 (clobber (reg:CC FLAGS_REG))]
11055 shrd{q}\t{%2, %1, %0|%0, %1, %2}
11056 shrd{q}\t{%s2%1, %0|%0, %1, %2}"
11057 [(set_attr "type" "ishift")
11058 (set_attr "prefix_0f" "1")
11059 (set_attr "mode" "DI")
11060 (set_attr "athlon_decode" "vector")])
11062 (define_expand "ashrdi3"
11063 [(set (match_operand:DI 0 "shiftdi_operand" "")
11064 (ashiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
11065 (match_operand:QI 2 "nonmemory_operand" "")))]
11067 "ix86_expand_binary_operator (ASHIFTRT, DImode, operands); DONE;")
11069 (define_insn "*ashrdi3_63_rex64"
11070 [(set (match_operand:DI 0 "nonimmediate_operand" "=*d,rm")
11071 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "*a,0")
11072 (match_operand:DI 2 "const_int_operand" "i,i")))
11073 (clobber (reg:CC FLAGS_REG))]
11074 "TARGET_64BIT && INTVAL (operands[2]) == 63
11075 && (TARGET_USE_CLTD || optimize_size)
11076 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11079 sar{q}\t{%2, %0|%0, %2}"
11080 [(set_attr "type" "imovx,ishift")
11081 (set_attr "prefix_0f" "0,*")
11082 (set_attr "length_immediate" "0,*")
11083 (set_attr "modrm" "0,1")
11084 (set_attr "mode" "DI")])
11086 (define_insn "*ashrdi3_1_one_bit_rex64"
11087 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11088 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11089 (match_operand:QI 2 "const1_operand" "")))
11090 (clobber (reg:CC FLAGS_REG))]
11091 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)
11092 && (TARGET_SHIFT1 || optimize_size)"
11094 [(set_attr "type" "ishift")
11095 (set (attr "length")
11096 (if_then_else (match_operand:DI 0 "register_operand" "")
11098 (const_string "*")))])
11100 (define_insn "*ashrdi3_1_rex64"
11101 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11102 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11103 (match_operand:QI 2 "nonmemory_operand" "J,c")))
11104 (clobber (reg:CC FLAGS_REG))]
11105 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11107 sar{q}\t{%2, %0|%0, %2}
11108 sar{q}\t{%b2, %0|%0, %b2}"
11109 [(set_attr "type" "ishift")
11110 (set_attr "mode" "DI")])
11112 ;; This pattern can't accept a variable shift count, since shifts by
11113 ;; zero don't affect the flags. We assume that shifts by constant
11114 ;; zero are optimized away.
11115 (define_insn "*ashrdi3_one_bit_cmp_rex64"
11116 [(set (reg FLAGS_REG)
11118 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11119 (match_operand:QI 2 "const1_operand" ""))
11121 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11122 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
11123 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11124 && (TARGET_SHIFT1 || optimize_size)
11125 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11127 [(set_attr "type" "ishift")
11128 (set (attr "length")
11129 (if_then_else (match_operand:DI 0 "register_operand" "")
11131 (const_string "*")))])
11133 ;; This pattern can't accept a variable shift count, since shifts by
11134 ;; zero don't affect the flags. We assume that shifts by constant
11135 ;; zero are optimized away.
11136 (define_insn "*ashrdi3_cmp_rex64"
11137 [(set (reg FLAGS_REG)
11139 (ashiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11140 (match_operand:QI 2 "const_int_operand" "n"))
11142 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11143 (ashiftrt:DI (match_dup 1) (match_dup 2)))]
11144 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11145 && ix86_binary_operator_ok (ASHIFTRT, DImode, operands)"
11146 "sar{q}\t{%2, %0|%0, %2}"
11147 [(set_attr "type" "ishift")
11148 (set_attr "mode" "DI")])
11150 (define_insn "*ashrdi3_1"
11151 [(set (match_operand:DI 0 "register_operand" "=r")
11152 (ashiftrt:DI (match_operand:DI 1 "register_operand" "0")
11153 (match_operand:QI 2 "nonmemory_operand" "Jc")))
11154 (clobber (reg:CC FLAGS_REG))]
11157 [(set_attr "type" "multi")])
11159 ;; By default we don't ask for a scratch register, because when DImode
11160 ;; values are manipulated, registers are already at a premium. But if
11161 ;; we have one handy, we won't turn it away.
11163 [(match_scratch:SI 3 "r")
11164 (parallel [(set (match_operand:DI 0 "register_operand" "")
11165 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
11166 (match_operand:QI 2 "nonmemory_operand" "")))
11167 (clobber (reg:CC FLAGS_REG))])
11169 "!TARGET_64BIT && TARGET_CMOVE"
11171 "ix86_split_ashr (operands, operands[3], DImode); DONE;")
11174 [(set (match_operand:DI 0 "register_operand" "")
11175 (ashiftrt:DI (match_operand:DI 1 "register_operand" "")
11176 (match_operand:QI 2 "nonmemory_operand" "")))
11177 (clobber (reg:CC FLAGS_REG))]
11178 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
11179 ? flow2_completed : reload_completed)"
11181 "ix86_split_ashr (operands, NULL_RTX, DImode); DONE;")
11183 (define_insn "x86_shrd_1"
11184 [(set (match_operand:SI 0 "nonimmediate_operand" "+r*m,r*m")
11185 (ior:SI (ashiftrt:SI (match_dup 0)
11186 (match_operand:QI 2 "nonmemory_operand" "I,c"))
11187 (ashift:SI (match_operand:SI 1 "register_operand" "r,r")
11188 (minus:QI (const_int 32) (match_dup 2)))))
11189 (clobber (reg:CC FLAGS_REG))]
11192 shrd{l}\t{%2, %1, %0|%0, %1, %2}
11193 shrd{l}\t{%s2%1, %0|%0, %1, %2}"
11194 [(set_attr "type" "ishift")
11195 (set_attr "prefix_0f" "1")
11196 (set_attr "pent_pair" "np")
11197 (set_attr "mode" "SI")])
11199 (define_expand "x86_shift_adj_3"
11200 [(use (match_operand:SI 0 "register_operand" ""))
11201 (use (match_operand:SI 1 "register_operand" ""))
11202 (use (match_operand:QI 2 "register_operand" ""))]
11205 rtx label = gen_label_rtx ();
11208 emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (32)));
11210 tmp = gen_rtx_REG (CCZmode, FLAGS_REG);
11211 tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
11212 tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
11213 gen_rtx_LABEL_REF (VOIDmode, label),
11215 tmp = emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx, tmp));
11216 JUMP_LABEL (tmp) = label;
11218 emit_move_insn (operands[0], operands[1]);
11219 emit_insn (gen_ashrsi3_31 (operands[1], operands[1], GEN_INT (31)));
11221 emit_label (label);
11222 LABEL_NUSES (label) = 1;
11227 (define_insn "ashrsi3_31"
11228 [(set (match_operand:SI 0 "nonimmediate_operand" "=*d,rm")
11229 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "*a,0")
11230 (match_operand:SI 2 "const_int_operand" "i,i")))
11231 (clobber (reg:CC FLAGS_REG))]
11232 "INTVAL (operands[2]) == 31 && (TARGET_USE_CLTD || optimize_size)
11233 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11236 sar{l}\t{%2, %0|%0, %2}"
11237 [(set_attr "type" "imovx,ishift")
11238 (set_attr "prefix_0f" "0,*")
11239 (set_attr "length_immediate" "0,*")
11240 (set_attr "modrm" "0,1")
11241 (set_attr "mode" "SI")])
11243 (define_insn "*ashrsi3_31_zext"
11244 [(set (match_operand:DI 0 "register_operand" "=*d,r")
11245 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "*a,0")
11246 (match_operand:SI 2 "const_int_operand" "i,i"))))
11247 (clobber (reg:CC FLAGS_REG))]
11248 "TARGET_64BIT && (TARGET_USE_CLTD || optimize_size)
11249 && INTVAL (operands[2]) == 31
11250 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11253 sar{l}\t{%2, %k0|%k0, %2}"
11254 [(set_attr "type" "imovx,ishift")
11255 (set_attr "prefix_0f" "0,*")
11256 (set_attr "length_immediate" "0,*")
11257 (set_attr "modrm" "0,1")
11258 (set_attr "mode" "SI")])
11260 (define_expand "ashrsi3"
11261 [(set (match_operand:SI 0 "nonimmediate_operand" "")
11262 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
11263 (match_operand:QI 2 "nonmemory_operand" "")))
11264 (clobber (reg:CC FLAGS_REG))]
11266 "ix86_expand_binary_operator (ASHIFTRT, SImode, operands); DONE;")
11268 (define_insn "*ashrsi3_1_one_bit"
11269 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11270 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11271 (match_operand:QI 2 "const1_operand" "")))
11272 (clobber (reg:CC FLAGS_REG))]
11273 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
11274 && (TARGET_SHIFT1 || optimize_size)"
11276 [(set_attr "type" "ishift")
11277 (set (attr "length")
11278 (if_then_else (match_operand:SI 0 "register_operand" "")
11280 (const_string "*")))])
11282 (define_insn "*ashrsi3_1_one_bit_zext"
11283 [(set (match_operand:DI 0 "register_operand" "=r")
11284 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11285 (match_operand:QI 2 "const1_operand" ""))))
11286 (clobber (reg:CC FLAGS_REG))]
11287 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)
11288 && (TARGET_SHIFT1 || optimize_size)"
11290 [(set_attr "type" "ishift")
11291 (set_attr "length" "2")])
11293 (define_insn "*ashrsi3_1"
11294 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11295 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11296 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11297 (clobber (reg:CC FLAGS_REG))]
11298 "ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11300 sar{l}\t{%2, %0|%0, %2}
11301 sar{l}\t{%b2, %0|%0, %b2}"
11302 [(set_attr "type" "ishift")
11303 (set_attr "mode" "SI")])
11305 (define_insn "*ashrsi3_1_zext"
11306 [(set (match_operand:DI 0 "register_operand" "=r,r")
11307 (zero_extend:DI (ashiftrt:SI (match_operand:SI 1 "register_operand" "0,0")
11308 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11309 (clobber (reg:CC FLAGS_REG))]
11310 "TARGET_64BIT && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11312 sar{l}\t{%2, %k0|%k0, %2}
11313 sar{l}\t{%b2, %k0|%k0, %b2}"
11314 [(set_attr "type" "ishift")
11315 (set_attr "mode" "SI")])
11317 ;; This pattern can't accept a variable shift count, since shifts by
11318 ;; zero don't affect the flags. We assume that shifts by constant
11319 ;; zero are optimized away.
11320 (define_insn "*ashrsi3_one_bit_cmp"
11321 [(set (reg FLAGS_REG)
11323 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11324 (match_operand:QI 2 "const1_operand" ""))
11326 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11327 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
11328 "ix86_match_ccmode (insn, CCGOCmode)
11329 && (TARGET_SHIFT1 || optimize_size)
11330 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11332 [(set_attr "type" "ishift")
11333 (set (attr "length")
11334 (if_then_else (match_operand:SI 0 "register_operand" "")
11336 (const_string "*")))])
11338 (define_insn "*ashrsi3_one_bit_cmp_zext"
11339 [(set (reg FLAGS_REG)
11341 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11342 (match_operand:QI 2 "const1_operand" ""))
11344 (set (match_operand:DI 0 "register_operand" "=r")
11345 (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
11346 "TARGET_64BIT && ix86_match_ccmode (insn, CCmode)
11347 && (TARGET_SHIFT1 || optimize_size)
11348 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11350 [(set_attr "type" "ishift")
11351 (set_attr "length" "2")])
11353 ;; This pattern can't accept a variable shift count, since shifts by
11354 ;; zero don't affect the flags. We assume that shifts by constant
11355 ;; zero are optimized away.
11356 (define_insn "*ashrsi3_cmp"
11357 [(set (reg FLAGS_REG)
11359 (ashiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11360 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11362 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11363 (ashiftrt:SI (match_dup 1) (match_dup 2)))]
11364 "ix86_match_ccmode (insn, CCGOCmode)
11365 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11366 "sar{l}\t{%2, %0|%0, %2}"
11367 [(set_attr "type" "ishift")
11368 (set_attr "mode" "SI")])
11370 (define_insn "*ashrsi3_cmp_zext"
11371 [(set (reg FLAGS_REG)
11373 (ashiftrt:SI (match_operand:SI 1 "register_operand" "0")
11374 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11376 (set (match_operand:DI 0 "register_operand" "=r")
11377 (zero_extend:DI (ashiftrt:SI (match_dup 1) (match_dup 2))))]
11378 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11379 && ix86_binary_operator_ok (ASHIFTRT, SImode, operands)"
11380 "sar{l}\t{%2, %k0|%k0, %2}"
11381 [(set_attr "type" "ishift")
11382 (set_attr "mode" "SI")])
11384 (define_expand "ashrhi3"
11385 [(set (match_operand:HI 0 "nonimmediate_operand" "")
11386 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
11387 (match_operand:QI 2 "nonmemory_operand" "")))
11388 (clobber (reg:CC FLAGS_REG))]
11389 "TARGET_HIMODE_MATH"
11390 "ix86_expand_binary_operator (ASHIFTRT, HImode, operands); DONE;")
11392 (define_insn "*ashrhi3_1_one_bit"
11393 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11394 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11395 (match_operand:QI 2 "const1_operand" "")))
11396 (clobber (reg:CC FLAGS_REG))]
11397 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)
11398 && (TARGET_SHIFT1 || optimize_size)"
11400 [(set_attr "type" "ishift")
11401 (set (attr "length")
11402 (if_then_else (match_operand 0 "register_operand" "")
11404 (const_string "*")))])
11406 (define_insn "*ashrhi3_1"
11407 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11408 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11409 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11410 (clobber (reg:CC FLAGS_REG))]
11411 "ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11413 sar{w}\t{%2, %0|%0, %2}
11414 sar{w}\t{%b2, %0|%0, %b2}"
11415 [(set_attr "type" "ishift")
11416 (set_attr "mode" "HI")])
11418 ;; This pattern can't accept a variable shift count, since shifts by
11419 ;; zero don't affect the flags. We assume that shifts by constant
11420 ;; zero are optimized away.
11421 (define_insn "*ashrhi3_one_bit_cmp"
11422 [(set (reg FLAGS_REG)
11424 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11425 (match_operand:QI 2 "const1_operand" ""))
11427 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11428 (ashiftrt:HI (match_dup 1) (match_dup 2)))]
11429 "ix86_match_ccmode (insn, CCGOCmode)
11430 && (TARGET_SHIFT1 || optimize_size)
11431 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11433 [(set_attr "type" "ishift")
11434 (set (attr "length")
11435 (if_then_else (match_operand 0 "register_operand" "")
11437 (const_string "*")))])
11439 ;; This pattern can't accept a variable shift count, since shifts by
11440 ;; zero don't affect the flags. We assume that shifts by constant
11441 ;; zero are optimized away.
11442 (define_insn "*ashrhi3_cmp"
11443 [(set (reg FLAGS_REG)
11445 (ashiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11446 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11448 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11449 (ashiftrt:HI (match_dup 1) (match_dup 2)))]
11450 "ix86_match_ccmode (insn, CCGOCmode)
11451 && ix86_binary_operator_ok (ASHIFTRT, HImode, operands)"
11452 "sar{w}\t{%2, %0|%0, %2}"
11453 [(set_attr "type" "ishift")
11454 (set_attr "mode" "HI")])
11456 (define_expand "ashrqi3"
11457 [(set (match_operand:QI 0 "nonimmediate_operand" "")
11458 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
11459 (match_operand:QI 2 "nonmemory_operand" "")))
11460 (clobber (reg:CC FLAGS_REG))]
11461 "TARGET_QIMODE_MATH"
11462 "ix86_expand_binary_operator (ASHIFTRT, QImode, operands); DONE;")
11464 (define_insn "*ashrqi3_1_one_bit"
11465 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11466 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11467 (match_operand:QI 2 "const1_operand" "")))
11468 (clobber (reg:CC FLAGS_REG))]
11469 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
11470 && (TARGET_SHIFT1 || optimize_size)"
11472 [(set_attr "type" "ishift")
11473 (set (attr "length")
11474 (if_then_else (match_operand 0 "register_operand" "")
11476 (const_string "*")))])
11478 (define_insn "*ashrqi3_1_one_bit_slp"
11479 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11480 (ashiftrt:QI (match_dup 0)
11481 (match_operand:QI 1 "const1_operand" "")))
11482 (clobber (reg:CC FLAGS_REG))]
11483 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)
11484 && (! TARGET_PARTIAL_REG_STALL || optimize_size)
11485 && (TARGET_SHIFT1 || optimize_size)"
11487 [(set_attr "type" "ishift1")
11488 (set (attr "length")
11489 (if_then_else (match_operand 0 "register_operand" "")
11491 (const_string "*")))])
11493 (define_insn "*ashrqi3_1"
11494 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11495 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11496 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11497 (clobber (reg:CC FLAGS_REG))]
11498 "ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11500 sar{b}\t{%2, %0|%0, %2}
11501 sar{b}\t{%b2, %0|%0, %b2}"
11502 [(set_attr "type" "ishift")
11503 (set_attr "mode" "QI")])
11505 (define_insn "*ashrqi3_1_slp"
11506 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11507 (ashiftrt:QI (match_dup 0)
11508 (match_operand:QI 1 "nonmemory_operand" "I,c")))
11509 (clobber (reg:CC FLAGS_REG))]
11510 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11511 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11513 sar{b}\t{%1, %0|%0, %1}
11514 sar{b}\t{%b1, %0|%0, %b1}"
11515 [(set_attr "type" "ishift1")
11516 (set_attr "mode" "QI")])
11518 ;; This pattern can't accept a variable shift count, since shifts by
11519 ;; zero don't affect the flags. We assume that shifts by constant
11520 ;; zero are optimized away.
11521 (define_insn "*ashrqi3_one_bit_cmp"
11522 [(set (reg FLAGS_REG)
11524 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11525 (match_operand:QI 2 "const1_operand" "I"))
11527 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11528 (ashiftrt:QI (match_dup 1) (match_dup 2)))]
11529 "ix86_match_ccmode (insn, CCGOCmode)
11530 && (TARGET_SHIFT1 || optimize_size)
11531 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11533 [(set_attr "type" "ishift")
11534 (set (attr "length")
11535 (if_then_else (match_operand 0 "register_operand" "")
11537 (const_string "*")))])
11539 ;; This pattern can't accept a variable shift count, since shifts by
11540 ;; zero don't affect the flags. We assume that shifts by constant
11541 ;; zero are optimized away.
11542 (define_insn "*ashrqi3_cmp"
11543 [(set (reg FLAGS_REG)
11545 (ashiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11546 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11548 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11549 (ashiftrt:QI (match_dup 1) (match_dup 2)))]
11550 "ix86_match_ccmode (insn, CCGOCmode)
11551 && ix86_binary_operator_ok (ASHIFTRT, QImode, operands)"
11552 "sar{b}\t{%2, %0|%0, %2}"
11553 [(set_attr "type" "ishift")
11554 (set_attr "mode" "QI")])
11556 ;; Logical shift instructions
11558 ;; See comment above `ashldi3' about how this works.
11560 (define_expand "lshrti3"
11561 [(parallel [(set (match_operand:TI 0 "register_operand" "")
11562 (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
11563 (match_operand:QI 2 "nonmemory_operand" "")))
11564 (clobber (reg:CC FLAGS_REG))])]
11567 if (! immediate_operand (operands[2], QImode))
11569 emit_insn (gen_lshrti3_1 (operands[0], operands[1], operands[2]));
11572 ix86_expand_binary_operator (LSHIFTRT, TImode, operands);
11576 (define_insn "lshrti3_1"
11577 [(set (match_operand:TI 0 "register_operand" "=r")
11578 (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
11579 (match_operand:QI 2 "register_operand" "c")))
11580 (clobber (match_scratch:DI 3 "=&r"))
11581 (clobber (reg:CC FLAGS_REG))]
11584 [(set_attr "type" "multi")])
11586 (define_insn "*lshrti3_2"
11587 [(set (match_operand:TI 0 "register_operand" "=r")
11588 (lshiftrt:TI (match_operand:TI 1 "register_operand" "0")
11589 (match_operand:QI 2 "immediate_operand" "O")))
11590 (clobber (reg:CC FLAGS_REG))]
11593 [(set_attr "type" "multi")])
11596 [(set (match_operand:TI 0 "register_operand" "")
11597 (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
11598 (match_operand:QI 2 "register_operand" "")))
11599 (clobber (match_scratch:DI 3 ""))
11600 (clobber (reg:CC FLAGS_REG))]
11601 "TARGET_64BIT && reload_completed"
11603 "ix86_split_lshr (operands, operands[3], TImode); DONE;")
11606 [(set (match_operand:TI 0 "register_operand" "")
11607 (lshiftrt:TI (match_operand:TI 1 "register_operand" "")
11608 (match_operand:QI 2 "immediate_operand" "")))
11609 (clobber (reg:CC FLAGS_REG))]
11610 "TARGET_64BIT && reload_completed"
11612 "ix86_split_lshr (operands, NULL_RTX, TImode); DONE;")
11614 (define_expand "lshrdi3"
11615 [(set (match_operand:DI 0 "shiftdi_operand" "")
11616 (lshiftrt:DI (match_operand:DI 1 "shiftdi_operand" "")
11617 (match_operand:QI 2 "nonmemory_operand" "")))]
11619 "ix86_expand_binary_operator (LSHIFTRT, DImode, operands); DONE;")
11621 (define_insn "*lshrdi3_1_one_bit_rex64"
11622 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11623 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11624 (match_operand:QI 2 "const1_operand" "")))
11625 (clobber (reg:CC FLAGS_REG))]
11626 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11627 && (TARGET_SHIFT1 || optimize_size)"
11629 [(set_attr "type" "ishift")
11630 (set (attr "length")
11631 (if_then_else (match_operand:DI 0 "register_operand" "")
11633 (const_string "*")))])
11635 (define_insn "*lshrdi3_1_rex64"
11636 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
11637 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
11638 (match_operand:QI 2 "nonmemory_operand" "J,c")))
11639 (clobber (reg:CC FLAGS_REG))]
11640 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11642 shr{q}\t{%2, %0|%0, %2}
11643 shr{q}\t{%b2, %0|%0, %b2}"
11644 [(set_attr "type" "ishift")
11645 (set_attr "mode" "DI")])
11647 ;; This pattern can't accept a variable shift count, since shifts by
11648 ;; zero don't affect the flags. We assume that shifts by constant
11649 ;; zero are optimized away.
11650 (define_insn "*lshrdi3_cmp_one_bit_rex64"
11651 [(set (reg FLAGS_REG)
11653 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11654 (match_operand:QI 2 "const1_operand" ""))
11656 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11657 (lshiftrt:DI (match_dup 1) (match_dup 2)))]
11658 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11659 && (TARGET_SHIFT1 || optimize_size)
11660 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11662 [(set_attr "type" "ishift")
11663 (set (attr "length")
11664 (if_then_else (match_operand:DI 0 "register_operand" "")
11666 (const_string "*")))])
11668 ;; This pattern can't accept a variable shift count, since shifts by
11669 ;; zero don't affect the flags. We assume that shifts by constant
11670 ;; zero are optimized away.
11671 (define_insn "*lshrdi3_cmp_rex64"
11672 [(set (reg FLAGS_REG)
11674 (lshiftrt:DI (match_operand:DI 1 "nonimmediate_operand" "0")
11675 (match_operand:QI 2 "const_int_operand" "e"))
11677 (set (match_operand:DI 0 "nonimmediate_operand" "=rm")
11678 (lshiftrt:DI (match_dup 1) (match_dup 2)))]
11679 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11680 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11681 "shr{q}\t{%2, %0|%0, %2}"
11682 [(set_attr "type" "ishift")
11683 (set_attr "mode" "DI")])
11685 (define_insn "*lshrdi3_1"
11686 [(set (match_operand:DI 0 "register_operand" "=r")
11687 (lshiftrt:DI (match_operand:DI 1 "register_operand" "0")
11688 (match_operand:QI 2 "nonmemory_operand" "Jc")))
11689 (clobber (reg:CC FLAGS_REG))]
11692 [(set_attr "type" "multi")])
11694 ;; By default we don't ask for a scratch register, because when DImode
11695 ;; values are manipulated, registers are already at a premium. But if
11696 ;; we have one handy, we won't turn it away.
11698 [(match_scratch:SI 3 "r")
11699 (parallel [(set (match_operand:DI 0 "register_operand" "")
11700 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
11701 (match_operand:QI 2 "nonmemory_operand" "")))
11702 (clobber (reg:CC FLAGS_REG))])
11704 "!TARGET_64BIT && TARGET_CMOVE"
11706 "ix86_split_lshr (operands, operands[3], DImode); DONE;")
11709 [(set (match_operand:DI 0 "register_operand" "")
11710 (lshiftrt:DI (match_operand:DI 1 "register_operand" "")
11711 (match_operand:QI 2 "nonmemory_operand" "")))
11712 (clobber (reg:CC FLAGS_REG))]
11713 "!TARGET_64BIT && ((optimize > 0 && flag_peephole2)
11714 ? flow2_completed : reload_completed)"
11716 "ix86_split_lshr (operands, NULL_RTX, DImode); DONE;")
11718 (define_expand "lshrsi3"
11719 [(set (match_operand:SI 0 "nonimmediate_operand" "")
11720 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "")
11721 (match_operand:QI 2 "nonmemory_operand" "")))
11722 (clobber (reg:CC FLAGS_REG))]
11724 "ix86_expand_binary_operator (LSHIFTRT, SImode, operands); DONE;")
11726 (define_insn "*lshrsi3_1_one_bit"
11727 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11728 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11729 (match_operand:QI 2 "const1_operand" "")))
11730 (clobber (reg:CC FLAGS_REG))]
11731 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11732 && (TARGET_SHIFT1 || optimize_size)"
11734 [(set_attr "type" "ishift")
11735 (set (attr "length")
11736 (if_then_else (match_operand:SI 0 "register_operand" "")
11738 (const_string "*")))])
11740 (define_insn "*lshrsi3_1_one_bit_zext"
11741 [(set (match_operand:DI 0 "register_operand" "=r")
11742 (lshiftrt:DI (zero_extend:DI (match_operand:SI 1 "register_operand" "0"))
11743 (match_operand:QI 2 "const1_operand" "")))
11744 (clobber (reg:CC FLAGS_REG))]
11745 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11746 && (TARGET_SHIFT1 || optimize_size)"
11748 [(set_attr "type" "ishift")
11749 (set_attr "length" "2")])
11751 (define_insn "*lshrsi3_1"
11752 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
11753 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11754 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11755 (clobber (reg:CC FLAGS_REG))]
11756 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11758 shr{l}\t{%2, %0|%0, %2}
11759 shr{l}\t{%b2, %0|%0, %b2}"
11760 [(set_attr "type" "ishift")
11761 (set_attr "mode" "SI")])
11763 (define_insn "*lshrsi3_1_zext"
11764 [(set (match_operand:DI 0 "register_operand" "=r,r")
11766 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
11767 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
11768 (clobber (reg:CC FLAGS_REG))]
11769 "TARGET_64BIT && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11771 shr{l}\t{%2, %k0|%k0, %2}
11772 shr{l}\t{%b2, %k0|%k0, %b2}"
11773 [(set_attr "type" "ishift")
11774 (set_attr "mode" "SI")])
11776 ;; This pattern can't accept a variable shift count, since shifts by
11777 ;; zero don't affect the flags. We assume that shifts by constant
11778 ;; zero are optimized away.
11779 (define_insn "*lshrsi3_one_bit_cmp"
11780 [(set (reg FLAGS_REG)
11782 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11783 (match_operand:QI 2 "const1_operand" ""))
11785 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11786 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
11787 "ix86_match_ccmode (insn, CCGOCmode)
11788 && (TARGET_SHIFT1 || optimize_size)
11789 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11791 [(set_attr "type" "ishift")
11792 (set (attr "length")
11793 (if_then_else (match_operand:SI 0 "register_operand" "")
11795 (const_string "*")))])
11797 (define_insn "*lshrsi3_cmp_one_bit_zext"
11798 [(set (reg FLAGS_REG)
11800 (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
11801 (match_operand:QI 2 "const1_operand" ""))
11803 (set (match_operand:DI 0 "register_operand" "=r")
11804 (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
11805 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11806 && (TARGET_SHIFT1 || optimize_size)
11807 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11809 [(set_attr "type" "ishift")
11810 (set_attr "length" "2")])
11812 ;; This pattern can't accept a variable shift count, since shifts by
11813 ;; zero don't affect the flags. We assume that shifts by constant
11814 ;; zero are optimized away.
11815 (define_insn "*lshrsi3_cmp"
11816 [(set (reg FLAGS_REG)
11818 (lshiftrt:SI (match_operand:SI 1 "nonimmediate_operand" "0")
11819 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11821 (set (match_operand:SI 0 "nonimmediate_operand" "=rm")
11822 (lshiftrt:SI (match_dup 1) (match_dup 2)))]
11823 "ix86_match_ccmode (insn, CCGOCmode)
11824 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11825 "shr{l}\t{%2, %0|%0, %2}"
11826 [(set_attr "type" "ishift")
11827 (set_attr "mode" "SI")])
11829 (define_insn "*lshrsi3_cmp_zext"
11830 [(set (reg FLAGS_REG)
11832 (lshiftrt:SI (match_operand:SI 1 "register_operand" "0")
11833 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11835 (set (match_operand:DI 0 "register_operand" "=r")
11836 (lshiftrt:DI (zero_extend:DI (match_dup 1)) (match_dup 2)))]
11837 "TARGET_64BIT && ix86_match_ccmode (insn, CCGOCmode)
11838 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11839 "shr{l}\t{%2, %k0|%k0, %2}"
11840 [(set_attr "type" "ishift")
11841 (set_attr "mode" "SI")])
11843 (define_expand "lshrhi3"
11844 [(set (match_operand:HI 0 "nonimmediate_operand" "")
11845 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "")
11846 (match_operand:QI 2 "nonmemory_operand" "")))
11847 (clobber (reg:CC FLAGS_REG))]
11848 "TARGET_HIMODE_MATH"
11849 "ix86_expand_binary_operator (LSHIFTRT, HImode, operands); DONE;")
11851 (define_insn "*lshrhi3_1_one_bit"
11852 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11853 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11854 (match_operand:QI 2 "const1_operand" "")))
11855 (clobber (reg:CC FLAGS_REG))]
11856 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)
11857 && (TARGET_SHIFT1 || optimize_size)"
11859 [(set_attr "type" "ishift")
11860 (set (attr "length")
11861 (if_then_else (match_operand 0 "register_operand" "")
11863 (const_string "*")))])
11865 (define_insn "*lshrhi3_1"
11866 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
11867 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
11868 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11869 (clobber (reg:CC FLAGS_REG))]
11870 "ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11872 shr{w}\t{%2, %0|%0, %2}
11873 shr{w}\t{%b2, %0|%0, %b2}"
11874 [(set_attr "type" "ishift")
11875 (set_attr "mode" "HI")])
11877 ;; This pattern can't accept a variable shift count, since shifts by
11878 ;; zero don't affect the flags. We assume that shifts by constant
11879 ;; zero are optimized away.
11880 (define_insn "*lshrhi3_one_bit_cmp"
11881 [(set (reg FLAGS_REG)
11883 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11884 (match_operand:QI 2 "const1_operand" ""))
11886 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11887 (lshiftrt:HI (match_dup 1) (match_dup 2)))]
11888 "ix86_match_ccmode (insn, CCGOCmode)
11889 && (TARGET_SHIFT1 || optimize_size)
11890 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11892 [(set_attr "type" "ishift")
11893 (set (attr "length")
11894 (if_then_else (match_operand:SI 0 "register_operand" "")
11896 (const_string "*")))])
11898 ;; This pattern can't accept a variable shift count, since shifts by
11899 ;; zero don't affect the flags. We assume that shifts by constant
11900 ;; zero are optimized away.
11901 (define_insn "*lshrhi3_cmp"
11902 [(set (reg FLAGS_REG)
11904 (lshiftrt:HI (match_operand:HI 1 "nonimmediate_operand" "0")
11905 (match_operand:QI 2 "const_1_to_31_operand" "I"))
11907 (set (match_operand:HI 0 "nonimmediate_operand" "=rm")
11908 (lshiftrt:HI (match_dup 1) (match_dup 2)))]
11909 "ix86_match_ccmode (insn, CCGOCmode)
11910 && ix86_binary_operator_ok (LSHIFTRT, HImode, operands)"
11911 "shr{w}\t{%2, %0|%0, %2}"
11912 [(set_attr "type" "ishift")
11913 (set_attr "mode" "HI")])
11915 (define_expand "lshrqi3"
11916 [(set (match_operand:QI 0 "nonimmediate_operand" "")
11917 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "")
11918 (match_operand:QI 2 "nonmemory_operand" "")))
11919 (clobber (reg:CC FLAGS_REG))]
11920 "TARGET_QIMODE_MATH"
11921 "ix86_expand_binary_operator (LSHIFTRT, QImode, operands); DONE;")
11923 (define_insn "*lshrqi3_1_one_bit"
11924 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11925 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11926 (match_operand:QI 2 "const1_operand" "")))
11927 (clobber (reg:CC FLAGS_REG))]
11928 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)
11929 && (TARGET_SHIFT1 || optimize_size)"
11931 [(set_attr "type" "ishift")
11932 (set (attr "length")
11933 (if_then_else (match_operand 0 "register_operand" "")
11935 (const_string "*")))])
11937 (define_insn "*lshrqi3_1_one_bit_slp"
11938 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
11939 (lshiftrt:QI (match_dup 0)
11940 (match_operand:QI 1 "const1_operand" "")))
11941 (clobber (reg:CC FLAGS_REG))]
11942 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11943 && (TARGET_SHIFT1 || optimize_size)"
11945 [(set_attr "type" "ishift1")
11946 (set (attr "length")
11947 (if_then_else (match_operand 0 "register_operand" "")
11949 (const_string "*")))])
11951 (define_insn "*lshrqi3_1"
11952 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
11953 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
11954 (match_operand:QI 2 "nonmemory_operand" "I,c")))
11955 (clobber (reg:CC FLAGS_REG))]
11956 "ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
11958 shr{b}\t{%2, %0|%0, %2}
11959 shr{b}\t{%b2, %0|%0, %b2}"
11960 [(set_attr "type" "ishift")
11961 (set_attr "mode" "QI")])
11963 (define_insn "*lshrqi3_1_slp"
11964 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
11965 (lshiftrt:QI (match_dup 0)
11966 (match_operand:QI 1 "nonmemory_operand" "I,c")))
11967 (clobber (reg:CC FLAGS_REG))]
11968 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
11969 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
11971 shr{b}\t{%1, %0|%0, %1}
11972 shr{b}\t{%b1, %0|%0, %b1}"
11973 [(set_attr "type" "ishift1")
11974 (set_attr "mode" "QI")])
11976 ;; This pattern can't accept a variable shift count, since shifts by
11977 ;; zero don't affect the flags. We assume that shifts by constant
11978 ;; zero are optimized away.
11979 (define_insn "*lshrqi2_one_bit_cmp"
11980 [(set (reg FLAGS_REG)
11982 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
11983 (match_operand:QI 2 "const1_operand" ""))
11985 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
11986 (lshiftrt:QI (match_dup 1) (match_dup 2)))]
11987 "ix86_match_ccmode (insn, CCGOCmode)
11988 && (TARGET_SHIFT1 || optimize_size)
11989 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
11991 [(set_attr "type" "ishift")
11992 (set (attr "length")
11993 (if_then_else (match_operand:SI 0 "register_operand" "")
11995 (const_string "*")))])
11997 ;; This pattern can't accept a variable shift count, since shifts by
11998 ;; zero don't affect the flags. We assume that shifts by constant
11999 ;; zero are optimized away.
12000 (define_insn "*lshrqi2_cmp"
12001 [(set (reg FLAGS_REG)
12003 (lshiftrt:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12004 (match_operand:QI 2 "const_1_to_31_operand" "I"))
12006 (set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12007 (lshiftrt:QI (match_dup 1) (match_dup 2)))]
12008 "ix86_match_ccmode (insn, CCGOCmode)
12009 && ix86_binary_operator_ok (LSHIFTRT, QImode, operands)"
12010 "shr{b}\t{%2, %0|%0, %2}"
12011 [(set_attr "type" "ishift")
12012 (set_attr "mode" "QI")])
12014 ;; Rotate instructions
12016 (define_expand "rotldi3"
12017 [(set (match_operand:DI 0 "shiftdi_operand" "")
12018 (rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
12019 (match_operand:QI 2 "nonmemory_operand" "")))
12020 (clobber (reg:CC FLAGS_REG))]
12025 ix86_expand_binary_operator (ROTATE, DImode, operands);
12028 if (!const_1_to_31_operand (operands[2], VOIDmode))
12030 emit_insn (gen_ix86_rotldi3 (operands[0], operands[1], operands[2]));
12034 ;; Implement rotation using two double-precision shift instructions
12035 ;; and a scratch register.
12036 (define_insn_and_split "ix86_rotldi3"
12037 [(set (match_operand:DI 0 "register_operand" "=r")
12038 (rotate:DI (match_operand:DI 1 "register_operand" "0")
12039 (match_operand:QI 2 "const_1_to_31_operand" "I")))
12040 (clobber (reg:CC FLAGS_REG))
12041 (clobber (match_scratch:SI 3 "=&r"))]
12044 "&& reload_completed"
12045 [(set (match_dup 3) (match_dup 4))
12047 [(set (match_dup 4)
12048 (ior:SI (ashift:SI (match_dup 4) (match_dup 2))
12049 (lshiftrt:SI (match_dup 5)
12050 (minus:QI (const_int 32) (match_dup 2)))))
12051 (clobber (reg:CC FLAGS_REG))])
12053 [(set (match_dup 5)
12054 (ior:SI (ashift:SI (match_dup 5) (match_dup 2))
12055 (lshiftrt:SI (match_dup 3)
12056 (minus:QI (const_int 32) (match_dup 2)))))
12057 (clobber (reg:CC FLAGS_REG))])]
12058 "split_di (operands, 1, operands + 4, operands + 5);")
12060 (define_insn "*rotlsi3_1_one_bit_rex64"
12061 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12062 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12063 (match_operand:QI 2 "const1_operand" "")))
12064 (clobber (reg:CC FLAGS_REG))]
12065 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)
12066 && (TARGET_SHIFT1 || optimize_size)"
12068 [(set_attr "type" "rotate")
12069 (set (attr "length")
12070 (if_then_else (match_operand:DI 0 "register_operand" "")
12072 (const_string "*")))])
12074 (define_insn "*rotldi3_1_rex64"
12075 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
12076 (rotate:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
12077 (match_operand:QI 2 "nonmemory_operand" "e,c")))
12078 (clobber (reg:CC FLAGS_REG))]
12079 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, DImode, operands)"
12081 rol{q}\t{%2, %0|%0, %2}
12082 rol{q}\t{%b2, %0|%0, %b2}"
12083 [(set_attr "type" "rotate")
12084 (set_attr "mode" "DI")])
12086 (define_expand "rotlsi3"
12087 [(set (match_operand:SI 0 "nonimmediate_operand" "")
12088 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "")
12089 (match_operand:QI 2 "nonmemory_operand" "")))
12090 (clobber (reg:CC FLAGS_REG))]
12092 "ix86_expand_binary_operator (ROTATE, SImode, operands); DONE;")
12094 (define_insn "*rotlsi3_1_one_bit"
12095 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12096 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12097 (match_operand:QI 2 "const1_operand" "")))
12098 (clobber (reg:CC FLAGS_REG))]
12099 "ix86_binary_operator_ok (ROTATE, SImode, operands)
12100 && (TARGET_SHIFT1 || optimize_size)"
12102 [(set_attr "type" "rotate")
12103 (set (attr "length")
12104 (if_then_else (match_operand:SI 0 "register_operand" "")
12106 (const_string "*")))])
12108 (define_insn "*rotlsi3_1_one_bit_zext"
12109 [(set (match_operand:DI 0 "register_operand" "=r")
12111 (rotate:SI (match_operand:SI 1 "register_operand" "0")
12112 (match_operand:QI 2 "const1_operand" ""))))
12113 (clobber (reg:CC FLAGS_REG))]
12114 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)
12115 && (TARGET_SHIFT1 || optimize_size)"
12117 [(set_attr "type" "rotate")
12118 (set_attr "length" "2")])
12120 (define_insn "*rotlsi3_1"
12121 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12122 (rotate:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12123 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12124 (clobber (reg:CC FLAGS_REG))]
12125 "ix86_binary_operator_ok (ROTATE, SImode, operands)"
12127 rol{l}\t{%2, %0|%0, %2}
12128 rol{l}\t{%b2, %0|%0, %b2}"
12129 [(set_attr "type" "rotate")
12130 (set_attr "mode" "SI")])
12132 (define_insn "*rotlsi3_1_zext"
12133 [(set (match_operand:DI 0 "register_operand" "=r,r")
12135 (rotate:SI (match_operand:SI 1 "register_operand" "0,0")
12136 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12137 (clobber (reg:CC FLAGS_REG))]
12138 "TARGET_64BIT && ix86_binary_operator_ok (ROTATE, SImode, operands)"
12140 rol{l}\t{%2, %k0|%k0, %2}
12141 rol{l}\t{%b2, %k0|%k0, %b2}"
12142 [(set_attr "type" "rotate")
12143 (set_attr "mode" "SI")])
12145 (define_expand "rotlhi3"
12146 [(set (match_operand:HI 0 "nonimmediate_operand" "")
12147 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "")
12148 (match_operand:QI 2 "nonmemory_operand" "")))
12149 (clobber (reg:CC FLAGS_REG))]
12150 "TARGET_HIMODE_MATH"
12151 "ix86_expand_binary_operator (ROTATE, HImode, operands); DONE;")
12153 (define_insn "*rotlhi3_1_one_bit"
12154 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12155 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12156 (match_operand:QI 2 "const1_operand" "")))
12157 (clobber (reg:CC FLAGS_REG))]
12158 "ix86_binary_operator_ok (ROTATE, HImode, operands)
12159 && (TARGET_SHIFT1 || optimize_size)"
12161 [(set_attr "type" "rotate")
12162 (set (attr "length")
12163 (if_then_else (match_operand 0 "register_operand" "")
12165 (const_string "*")))])
12167 (define_insn "*rotlhi3_1"
12168 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12169 (rotate:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12170 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12171 (clobber (reg:CC FLAGS_REG))]
12172 "ix86_binary_operator_ok (ROTATE, HImode, operands)"
12174 rol{w}\t{%2, %0|%0, %2}
12175 rol{w}\t{%b2, %0|%0, %b2}"
12176 [(set_attr "type" "rotate")
12177 (set_attr "mode" "HI")])
12179 (define_expand "rotlqi3"
12180 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12181 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "")
12182 (match_operand:QI 2 "nonmemory_operand" "")))
12183 (clobber (reg:CC FLAGS_REG))]
12184 "TARGET_QIMODE_MATH"
12185 "ix86_expand_binary_operator (ROTATE, QImode, operands); DONE;")
12187 (define_insn "*rotlqi3_1_one_bit_slp"
12188 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12189 (rotate:QI (match_dup 0)
12190 (match_operand:QI 1 "const1_operand" "")))
12191 (clobber (reg:CC FLAGS_REG))]
12192 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12193 && (TARGET_SHIFT1 || optimize_size)"
12195 [(set_attr "type" "rotate1")
12196 (set (attr "length")
12197 (if_then_else (match_operand 0 "register_operand" "")
12199 (const_string "*")))])
12201 (define_insn "*rotlqi3_1_one_bit"
12202 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12203 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12204 (match_operand:QI 2 "const1_operand" "")))
12205 (clobber (reg:CC FLAGS_REG))]
12206 "ix86_binary_operator_ok (ROTATE, QImode, operands)
12207 && (TARGET_SHIFT1 || optimize_size)"
12209 [(set_attr "type" "rotate")
12210 (set (attr "length")
12211 (if_then_else (match_operand 0 "register_operand" "")
12213 (const_string "*")))])
12215 (define_insn "*rotlqi3_1_slp"
12216 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12217 (rotate:QI (match_dup 0)
12218 (match_operand:QI 1 "nonmemory_operand" "I,c")))
12219 (clobber (reg:CC FLAGS_REG))]
12220 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12221 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
12223 rol{b}\t{%1, %0|%0, %1}
12224 rol{b}\t{%b1, %0|%0, %b1}"
12225 [(set_attr "type" "rotate1")
12226 (set_attr "mode" "QI")])
12228 (define_insn "*rotlqi3_1"
12229 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12230 (rotate:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12231 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12232 (clobber (reg:CC FLAGS_REG))]
12233 "ix86_binary_operator_ok (ROTATE, QImode, operands)"
12235 rol{b}\t{%2, %0|%0, %2}
12236 rol{b}\t{%b2, %0|%0, %b2}"
12237 [(set_attr "type" "rotate")
12238 (set_attr "mode" "QI")])
12240 (define_expand "rotrdi3"
12241 [(set (match_operand:DI 0 "shiftdi_operand" "")
12242 (rotate:DI (match_operand:DI 1 "shiftdi_operand" "")
12243 (match_operand:QI 2 "nonmemory_operand" "")))
12244 (clobber (reg:CC FLAGS_REG))]
12249 ix86_expand_binary_operator (ROTATERT, DImode, operands);
12252 if (!const_1_to_31_operand (operands[2], VOIDmode))
12254 emit_insn (gen_ix86_rotrdi3 (operands[0], operands[1], operands[2]));
12258 ;; Implement rotation using two double-precision shift instructions
12259 ;; and a scratch register.
12260 (define_insn_and_split "ix86_rotrdi3"
12261 [(set (match_operand:DI 0 "register_operand" "=r")
12262 (rotatert:DI (match_operand:DI 1 "register_operand" "0")
12263 (match_operand:QI 2 "const_1_to_31_operand" "I")))
12264 (clobber (reg:CC FLAGS_REG))
12265 (clobber (match_scratch:SI 3 "=&r"))]
12268 "&& reload_completed"
12269 [(set (match_dup 3) (match_dup 4))
12271 [(set (match_dup 4)
12272 (ior:SI (ashiftrt:SI (match_dup 4) (match_dup 2))
12273 (ashift:SI (match_dup 5)
12274 (minus:QI (const_int 32) (match_dup 2)))))
12275 (clobber (reg:CC FLAGS_REG))])
12277 [(set (match_dup 5)
12278 (ior:SI (ashiftrt:SI (match_dup 5) (match_dup 2))
12279 (ashift:SI (match_dup 3)
12280 (minus:QI (const_int 32) (match_dup 2)))))
12281 (clobber (reg:CC FLAGS_REG))])]
12282 "split_di (operands, 1, operands + 4, operands + 5);")
12284 (define_insn "*rotrdi3_1_one_bit_rex64"
12285 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm")
12286 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0")
12287 (match_operand:QI 2 "const1_operand" "")))
12288 (clobber (reg:CC FLAGS_REG))]
12289 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)
12290 && (TARGET_SHIFT1 || optimize_size)"
12292 [(set_attr "type" "rotate")
12293 (set (attr "length")
12294 (if_then_else (match_operand:DI 0 "register_operand" "")
12296 (const_string "*")))])
12298 (define_insn "*rotrdi3_1_rex64"
12299 [(set (match_operand:DI 0 "nonimmediate_operand" "=rm,rm")
12300 (rotatert:DI (match_operand:DI 1 "nonimmediate_operand" "0,0")
12301 (match_operand:QI 2 "nonmemory_operand" "J,c")))
12302 (clobber (reg:CC FLAGS_REG))]
12303 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, DImode, operands)"
12305 ror{q}\t{%2, %0|%0, %2}
12306 ror{q}\t{%b2, %0|%0, %b2}"
12307 [(set_attr "type" "rotate")
12308 (set_attr "mode" "DI")])
12310 (define_expand "rotrsi3"
12311 [(set (match_operand:SI 0 "nonimmediate_operand" "")
12312 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "")
12313 (match_operand:QI 2 "nonmemory_operand" "")))
12314 (clobber (reg:CC FLAGS_REG))]
12316 "ix86_expand_binary_operator (ROTATERT, SImode, operands); DONE;")
12318 (define_insn "*rotrsi3_1_one_bit"
12319 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
12320 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0")
12321 (match_operand:QI 2 "const1_operand" "")))
12322 (clobber (reg:CC FLAGS_REG))]
12323 "ix86_binary_operator_ok (ROTATERT, SImode, operands)
12324 && (TARGET_SHIFT1 || optimize_size)"
12326 [(set_attr "type" "rotate")
12327 (set (attr "length")
12328 (if_then_else (match_operand:SI 0 "register_operand" "")
12330 (const_string "*")))])
12332 (define_insn "*rotrsi3_1_one_bit_zext"
12333 [(set (match_operand:DI 0 "register_operand" "=r")
12335 (rotatert:SI (match_operand:SI 1 "register_operand" "0")
12336 (match_operand:QI 2 "const1_operand" ""))))
12337 (clobber (reg:CC FLAGS_REG))]
12338 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)
12339 && (TARGET_SHIFT1 || optimize_size)"
12341 [(set_attr "type" "rotate")
12342 (set (attr "length")
12343 (if_then_else (match_operand:SI 0 "register_operand" "")
12345 (const_string "*")))])
12347 (define_insn "*rotrsi3_1"
12348 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm,rm")
12349 (rotatert:SI (match_operand:SI 1 "nonimmediate_operand" "0,0")
12350 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12351 (clobber (reg:CC FLAGS_REG))]
12352 "ix86_binary_operator_ok (ROTATERT, SImode, operands)"
12354 ror{l}\t{%2, %0|%0, %2}
12355 ror{l}\t{%b2, %0|%0, %b2}"
12356 [(set_attr "type" "rotate")
12357 (set_attr "mode" "SI")])
12359 (define_insn "*rotrsi3_1_zext"
12360 [(set (match_operand:DI 0 "register_operand" "=r,r")
12362 (rotatert:SI (match_operand:SI 1 "register_operand" "0,0")
12363 (match_operand:QI 2 "nonmemory_operand" "I,c"))))
12364 (clobber (reg:CC FLAGS_REG))]
12365 "TARGET_64BIT && ix86_binary_operator_ok (ROTATERT, SImode, operands)"
12367 ror{l}\t{%2, %k0|%k0, %2}
12368 ror{l}\t{%b2, %k0|%k0, %b2}"
12369 [(set_attr "type" "rotate")
12370 (set_attr "mode" "SI")])
12372 (define_expand "rotrhi3"
12373 [(set (match_operand:HI 0 "nonimmediate_operand" "")
12374 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "")
12375 (match_operand:QI 2 "nonmemory_operand" "")))
12376 (clobber (reg:CC FLAGS_REG))]
12377 "TARGET_HIMODE_MATH"
12378 "ix86_expand_binary_operator (ROTATERT, HImode, operands); DONE;")
12380 (define_insn "*rotrhi3_one_bit"
12381 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
12382 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0")
12383 (match_operand:QI 2 "const1_operand" "")))
12384 (clobber (reg:CC FLAGS_REG))]
12385 "ix86_binary_operator_ok (ROTATERT, HImode, operands)
12386 && (TARGET_SHIFT1 || optimize_size)"
12388 [(set_attr "type" "rotate")
12389 (set (attr "length")
12390 (if_then_else (match_operand 0 "register_operand" "")
12392 (const_string "*")))])
12394 (define_insn "*rotrhi3"
12395 [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,rm")
12396 (rotatert:HI (match_operand:HI 1 "nonimmediate_operand" "0,0")
12397 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12398 (clobber (reg:CC FLAGS_REG))]
12399 "ix86_binary_operator_ok (ROTATERT, HImode, operands)"
12401 ror{w}\t{%2, %0|%0, %2}
12402 ror{w}\t{%b2, %0|%0, %b2}"
12403 [(set_attr "type" "rotate")
12404 (set_attr "mode" "HI")])
12406 (define_expand "rotrqi3"
12407 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12408 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "")
12409 (match_operand:QI 2 "nonmemory_operand" "")))
12410 (clobber (reg:CC FLAGS_REG))]
12411 "TARGET_QIMODE_MATH"
12412 "ix86_expand_binary_operator (ROTATERT, QImode, operands); DONE;")
12414 (define_insn "*rotrqi3_1_one_bit"
12415 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12416 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0")
12417 (match_operand:QI 2 "const1_operand" "")))
12418 (clobber (reg:CC FLAGS_REG))]
12419 "ix86_binary_operator_ok (ROTATERT, QImode, operands)
12420 && (TARGET_SHIFT1 || optimize_size)"
12422 [(set_attr "type" "rotate")
12423 (set (attr "length")
12424 (if_then_else (match_operand 0 "register_operand" "")
12426 (const_string "*")))])
12428 (define_insn "*rotrqi3_1_one_bit_slp"
12429 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12430 (rotatert:QI (match_dup 0)
12431 (match_operand:QI 1 "const1_operand" "")))
12432 (clobber (reg:CC FLAGS_REG))]
12433 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12434 && (TARGET_SHIFT1 || optimize_size)"
12436 [(set_attr "type" "rotate1")
12437 (set (attr "length")
12438 (if_then_else (match_operand 0 "register_operand" "")
12440 (const_string "*")))])
12442 (define_insn "*rotrqi3_1"
12443 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,qm")
12444 (rotatert:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
12445 (match_operand:QI 2 "nonmemory_operand" "I,c")))
12446 (clobber (reg:CC FLAGS_REG))]
12447 "ix86_binary_operator_ok (ROTATERT, QImode, operands)"
12449 ror{b}\t{%2, %0|%0, %2}
12450 ror{b}\t{%b2, %0|%0, %b2}"
12451 [(set_attr "type" "rotate")
12452 (set_attr "mode" "QI")])
12454 (define_insn "*rotrqi3_1_slp"
12455 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm,qm"))
12456 (rotatert:QI (match_dup 0)
12457 (match_operand:QI 1 "nonmemory_operand" "I,c")))
12458 (clobber (reg:CC FLAGS_REG))]
12459 "(! TARGET_PARTIAL_REG_STALL || optimize_size)
12460 && (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
12462 ror{b}\t{%1, %0|%0, %1}
12463 ror{b}\t{%b1, %0|%0, %b1}"
12464 [(set_attr "type" "rotate1")
12465 (set_attr "mode" "QI")])
12467 ;; Bit set / bit test instructions
12469 (define_expand "extv"
12470 [(set (match_operand:SI 0 "register_operand" "")
12471 (sign_extract:SI (match_operand:SI 1 "register_operand" "")
12472 (match_operand:SI 2 "const8_operand" "")
12473 (match_operand:SI 3 "const8_operand" "")))]
12476 /* Handle extractions from %ah et al. */
12477 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
12480 /* From mips.md: extract_bit_field doesn't verify that our source
12481 matches the predicate, so check it again here. */
12482 if (! ext_register_operand (operands[1], VOIDmode))
12486 (define_expand "extzv"
12487 [(set (match_operand:SI 0 "register_operand" "")
12488 (zero_extract:SI (match_operand 1 "ext_register_operand" "")
12489 (match_operand:SI 2 "const8_operand" "")
12490 (match_operand:SI 3 "const8_operand" "")))]
12493 /* Handle extractions from %ah et al. */
12494 if (INTVAL (operands[2]) != 8 || INTVAL (operands[3]) != 8)
12497 /* From mips.md: extract_bit_field doesn't verify that our source
12498 matches the predicate, so check it again here. */
12499 if (! ext_register_operand (operands[1], VOIDmode))
12503 (define_expand "insv"
12504 [(set (zero_extract (match_operand 0 "ext_register_operand" "")
12505 (match_operand 1 "const8_operand" "")
12506 (match_operand 2 "const8_operand" ""))
12507 (match_operand 3 "register_operand" ""))]
12510 /* Handle insertions to %ah et al. */
12511 if (INTVAL (operands[1]) != 8 || INTVAL (operands[2]) != 8)
12514 /* From mips.md: insert_bit_field doesn't verify that our source
12515 matches the predicate, so check it again here. */
12516 if (! ext_register_operand (operands[0], VOIDmode))
12520 emit_insn (gen_movdi_insv_1_rex64 (operands[0], operands[3]));
12522 emit_insn (gen_movsi_insv_1 (operands[0], operands[3]));
12527 ;; %%% bts, btr, btc, bt.
12528 ;; In general these instructions are *slow* when applied to memory,
12529 ;; since they enforce atomic operation. When applied to registers,
12530 ;; it depends on the cpu implementation. They're never faster than
12531 ;; the corresponding and/ior/xor operations, so with 32-bit there's
12532 ;; no point. But in 64-bit, we can't hold the relevant immediates
12533 ;; within the instruction itself, so operating on bits in the high
12534 ;; 32-bits of a register becomes easier.
12536 ;; These are slow on Nocona, but fast on Athlon64. We do require the use
12537 ;; of btrq and btcq for corner cases of post-reload expansion of absdf and
12538 ;; negdf respectively, so they can never be disabled entirely.
12540 (define_insn "*btsq"
12541 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12543 (match_operand:DI 1 "const_0_to_63_operand" ""))
12545 (clobber (reg:CC FLAGS_REG))]
12546 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12548 [(set_attr "type" "alu1")])
12550 (define_insn "*btrq"
12551 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12553 (match_operand:DI 1 "const_0_to_63_operand" ""))
12555 (clobber (reg:CC FLAGS_REG))]
12556 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12558 [(set_attr "type" "alu1")])
12560 (define_insn "*btcq"
12561 [(set (zero_extract:DI (match_operand:DI 0 "register_operand" "+r")
12563 (match_operand:DI 1 "const_0_to_63_operand" ""))
12564 (not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
12565 (clobber (reg:CC FLAGS_REG))]
12566 "TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
12568 [(set_attr "type" "alu1")])
12570 ;; Allow Nocona to avoid these instructions if a register is available.
12573 [(match_scratch:DI 2 "r")
12574 (parallel [(set (zero_extract:DI
12575 (match_operand:DI 0 "register_operand" "")
12577 (match_operand:DI 1 "const_0_to_63_operand" ""))
12579 (clobber (reg:CC FLAGS_REG))])]
12580 "TARGET_64BIT && !TARGET_USE_BT"
12583 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12586 if (HOST_BITS_PER_WIDE_INT >= 64)
12587 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12588 else if (i < HOST_BITS_PER_WIDE_INT)
12589 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12591 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12593 op1 = immed_double_const (lo, hi, DImode);
12596 emit_move_insn (operands[2], op1);
12600 emit_insn (gen_iordi3 (operands[0], operands[0], op1));
12605 [(match_scratch:DI 2 "r")
12606 (parallel [(set (zero_extract:DI
12607 (match_operand:DI 0 "register_operand" "")
12609 (match_operand:DI 1 "const_0_to_63_operand" ""))
12611 (clobber (reg:CC FLAGS_REG))])]
12612 "TARGET_64BIT && !TARGET_USE_BT"
12615 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12618 if (HOST_BITS_PER_WIDE_INT >= 64)
12619 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12620 else if (i < HOST_BITS_PER_WIDE_INT)
12621 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12623 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12625 op1 = immed_double_const (~lo, ~hi, DImode);
12628 emit_move_insn (operands[2], op1);
12632 emit_insn (gen_anddi3 (operands[0], operands[0], op1));
12637 [(match_scratch:DI 2 "r")
12638 (parallel [(set (zero_extract:DI
12639 (match_operand:DI 0 "register_operand" "")
12641 (match_operand:DI 1 "const_0_to_63_operand" ""))
12642 (not:DI (zero_extract:DI
12643 (match_dup 0) (const_int 1) (match_dup 1))))
12644 (clobber (reg:CC FLAGS_REG))])]
12645 "TARGET_64BIT && !TARGET_USE_BT"
12648 HOST_WIDE_INT i = INTVAL (operands[1]), hi, lo;
12651 if (HOST_BITS_PER_WIDE_INT >= 64)
12652 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12653 else if (i < HOST_BITS_PER_WIDE_INT)
12654 lo = (HOST_WIDE_INT)1 << i, hi = 0;
12656 lo = 0, hi = (HOST_WIDE_INT)1 << (i - HOST_BITS_PER_WIDE_INT);
12658 op1 = immed_double_const (lo, hi, DImode);
12661 emit_move_insn (operands[2], op1);
12665 emit_insn (gen_xordi3 (operands[0], operands[0], op1));
12669 ;; Store-flag instructions.
12671 ;; For all sCOND expanders, also expand the compare or test insn that
12672 ;; generates cc0. Generate an equality comparison if `seq' or `sne'.
12674 ;; %%% Do the expansion to SImode. If PII, do things the xor+setcc way
12675 ;; to avoid partial register stalls. Otherwise do things the setcc+movzx
12676 ;; way, which can later delete the movzx if only QImode is needed.
12678 (define_expand "seq"
12679 [(set (match_operand:QI 0 "register_operand" "")
12680 (eq:QI (reg:CC FLAGS_REG) (const_int 0)))]
12682 "if (ix86_expand_setcc (EQ, operands[0])) DONE; else FAIL;")
12684 (define_expand "sne"
12685 [(set (match_operand:QI 0 "register_operand" "")
12686 (ne:QI (reg:CC FLAGS_REG) (const_int 0)))]
12688 "if (ix86_expand_setcc (NE, operands[0])) DONE; else FAIL;")
12690 (define_expand "sgt"
12691 [(set (match_operand:QI 0 "register_operand" "")
12692 (gt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12694 "if (ix86_expand_setcc (GT, operands[0])) DONE; else FAIL;")
12696 (define_expand "sgtu"
12697 [(set (match_operand:QI 0 "register_operand" "")
12698 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12700 "if (ix86_expand_setcc (GTU, operands[0])) DONE; else FAIL;")
12702 (define_expand "slt"
12703 [(set (match_operand:QI 0 "register_operand" "")
12704 (lt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12706 "if (ix86_expand_setcc (LT, operands[0])) DONE; else FAIL;")
12708 (define_expand "sltu"
12709 [(set (match_operand:QI 0 "register_operand" "")
12710 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12712 "if (ix86_expand_setcc (LTU, operands[0])) DONE; else FAIL;")
12714 (define_expand "sge"
12715 [(set (match_operand:QI 0 "register_operand" "")
12716 (ge:QI (reg:CC FLAGS_REG) (const_int 0)))]
12718 "if (ix86_expand_setcc (GE, operands[0])) DONE; else FAIL;")
12720 (define_expand "sgeu"
12721 [(set (match_operand:QI 0 "register_operand" "")
12722 (geu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12724 "if (ix86_expand_setcc (GEU, operands[0])) DONE; else FAIL;")
12726 (define_expand "sle"
12727 [(set (match_operand:QI 0 "register_operand" "")
12728 (le:QI (reg:CC FLAGS_REG) (const_int 0)))]
12730 "if (ix86_expand_setcc (LE, operands[0])) DONE; else FAIL;")
12732 (define_expand "sleu"
12733 [(set (match_operand:QI 0 "register_operand" "")
12734 (leu:QI (reg:CC FLAGS_REG) (const_int 0)))]
12736 "if (ix86_expand_setcc (LEU, operands[0])) DONE; else FAIL;")
12738 (define_expand "sunordered"
12739 [(set (match_operand:QI 0 "register_operand" "")
12740 (unordered:QI (reg:CC FLAGS_REG) (const_int 0)))]
12741 "TARGET_80387 || TARGET_SSE"
12742 "if (ix86_expand_setcc (UNORDERED, operands[0])) DONE; else FAIL;")
12744 (define_expand "sordered"
12745 [(set (match_operand:QI 0 "register_operand" "")
12746 (ordered:QI (reg:CC FLAGS_REG) (const_int 0)))]
12748 "if (ix86_expand_setcc (ORDERED, operands[0])) DONE; else FAIL;")
12750 (define_expand "suneq"
12751 [(set (match_operand:QI 0 "register_operand" "")
12752 (uneq:QI (reg:CC FLAGS_REG) (const_int 0)))]
12753 "TARGET_80387 || TARGET_SSE"
12754 "if (ix86_expand_setcc (UNEQ, operands[0])) DONE; else FAIL;")
12756 (define_expand "sunge"
12757 [(set (match_operand:QI 0 "register_operand" "")
12758 (unge:QI (reg:CC FLAGS_REG) (const_int 0)))]
12759 "TARGET_80387 || TARGET_SSE"
12760 "if (ix86_expand_setcc (UNGE, operands[0])) DONE; else FAIL;")
12762 (define_expand "sungt"
12763 [(set (match_operand:QI 0 "register_operand" "")
12764 (ungt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12765 "TARGET_80387 || TARGET_SSE"
12766 "if (ix86_expand_setcc (UNGT, operands[0])) DONE; else FAIL;")
12768 (define_expand "sunle"
12769 [(set (match_operand:QI 0 "register_operand" "")
12770 (unle:QI (reg:CC FLAGS_REG) (const_int 0)))]
12771 "TARGET_80387 || TARGET_SSE"
12772 "if (ix86_expand_setcc (UNLE, operands[0])) DONE; else FAIL;")
12774 (define_expand "sunlt"
12775 [(set (match_operand:QI 0 "register_operand" "")
12776 (unlt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12777 "TARGET_80387 || TARGET_SSE"
12778 "if (ix86_expand_setcc (UNLT, operands[0])) DONE; else FAIL;")
12780 (define_expand "sltgt"
12781 [(set (match_operand:QI 0 "register_operand" "")
12782 (ltgt:QI (reg:CC FLAGS_REG) (const_int 0)))]
12783 "TARGET_80387 || TARGET_SSE"
12784 "if (ix86_expand_setcc (LTGT, operands[0])) DONE; else FAIL;")
12786 (define_insn "*setcc_1"
12787 [(set (match_operand:QI 0 "nonimmediate_operand" "=qm")
12788 (match_operator:QI 1 "ix86_comparison_operator"
12789 [(reg FLAGS_REG) (const_int 0)]))]
12792 [(set_attr "type" "setcc")
12793 (set_attr "mode" "QI")])
12795 (define_insn "*setcc_2"
12796 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" "+qm"))
12797 (match_operator:QI 1 "ix86_comparison_operator"
12798 [(reg FLAGS_REG) (const_int 0)]))]
12801 [(set_attr "type" "setcc")
12802 (set_attr "mode" "QI")])
12804 ;; In general it is not safe to assume too much about CCmode registers,
12805 ;; so simplify-rtx stops when it sees a second one. Under certain
12806 ;; conditions this is safe on x86, so help combine not create
12813 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12814 (ne:QI (match_operator 1 "ix86_comparison_operator"
12815 [(reg FLAGS_REG) (const_int 0)])
12818 [(set (match_dup 0) (match_dup 1))]
12820 PUT_MODE (operands[1], QImode);
12824 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
12825 (ne:QI (match_operator 1 "ix86_comparison_operator"
12826 [(reg FLAGS_REG) (const_int 0)])
12829 [(set (match_dup 0) (match_dup 1))]
12831 PUT_MODE (operands[1], QImode);
12835 [(set (match_operand:QI 0 "nonimmediate_operand" "")
12836 (eq:QI (match_operator 1 "ix86_comparison_operator"
12837 [(reg FLAGS_REG) (const_int 0)])
12840 [(set (match_dup 0) (match_dup 1))]
12842 rtx new_op1 = copy_rtx (operands[1]);
12843 operands[1] = new_op1;
12844 PUT_MODE (new_op1, QImode);
12845 PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
12846 GET_MODE (XEXP (new_op1, 0))));
12848 /* Make sure that (a) the CCmode we have for the flags is strong
12849 enough for the reversed compare or (b) we have a valid FP compare. */
12850 if (! ix86_comparison_operator (new_op1, VOIDmode))
12855 [(set (strict_low_part (match_operand:QI 0 "nonimmediate_operand" ""))
12856 (eq:QI (match_operator 1 "ix86_comparison_operator"
12857 [(reg FLAGS_REG) (const_int 0)])
12860 [(set (match_dup 0) (match_dup 1))]
12862 rtx new_op1 = copy_rtx (operands[1]);
12863 operands[1] = new_op1;
12864 PUT_MODE (new_op1, QImode);
12865 PUT_CODE (new_op1, ix86_reverse_condition (GET_CODE (new_op1),
12866 GET_MODE (XEXP (new_op1, 0))));
12868 /* Make sure that (a) the CCmode we have for the flags is strong
12869 enough for the reversed compare or (b) we have a valid FP compare. */
12870 if (! ix86_comparison_operator (new_op1, VOIDmode))
12874 ;; The SSE store flag instructions saves 0 or 0xffffffff to the result.
12875 ;; subsequent logical operations are used to imitate conditional moves.
12876 ;; 0xffffffff is NaN, but not in normalized form, so we can't represent
12879 (define_insn "*sse_setccsf"
12880 [(set (match_operand:SF 0 "register_operand" "=x")
12881 (match_operator:SF 1 "sse_comparison_operator"
12882 [(match_operand:SF 2 "register_operand" "0")
12883 (match_operand:SF 3 "nonimmediate_operand" "xm")]))]
12885 "cmp%D1ss\t{%3, %0|%0, %3}"
12886 [(set_attr "type" "ssecmp")
12887 (set_attr "mode" "SF")])
12889 (define_insn "*sse_setccdf"
12890 [(set (match_operand:DF 0 "register_operand" "=Y")
12891 (match_operator:DF 1 "sse_comparison_operator"
12892 [(match_operand:DF 2 "register_operand" "0")
12893 (match_operand:DF 3 "nonimmediate_operand" "Ym")]))]
12895 "cmp%D1sd\t{%3, %0|%0, %3}"
12896 [(set_attr "type" "ssecmp")
12897 (set_attr "mode" "DF")])
12899 ;; Basic conditional jump instructions.
12900 ;; We ignore the overflow flag for signed branch instructions.
12902 ;; For all bCOND expanders, also expand the compare or test insn that
12903 ;; generates reg FLAGS_REG. Generate an equality comparison if `beq' or `bne'.
12905 (define_expand "beq"
12907 (if_then_else (match_dup 1)
12908 (label_ref (match_operand 0 "" ""))
12911 "ix86_expand_branch (EQ, operands[0]); DONE;")
12913 (define_expand "bne"
12915 (if_then_else (match_dup 1)
12916 (label_ref (match_operand 0 "" ""))
12919 "ix86_expand_branch (NE, operands[0]); DONE;")
12921 (define_expand "bgt"
12923 (if_then_else (match_dup 1)
12924 (label_ref (match_operand 0 "" ""))
12927 "ix86_expand_branch (GT, operands[0]); DONE;")
12929 (define_expand "bgtu"
12931 (if_then_else (match_dup 1)
12932 (label_ref (match_operand 0 "" ""))
12935 "ix86_expand_branch (GTU, operands[0]); DONE;")
12937 (define_expand "blt"
12939 (if_then_else (match_dup 1)
12940 (label_ref (match_operand 0 "" ""))
12943 "ix86_expand_branch (LT, operands[0]); DONE;")
12945 (define_expand "bltu"
12947 (if_then_else (match_dup 1)
12948 (label_ref (match_operand 0 "" ""))
12951 "ix86_expand_branch (LTU, operands[0]); DONE;")
12953 (define_expand "bge"
12955 (if_then_else (match_dup 1)
12956 (label_ref (match_operand 0 "" ""))
12959 "ix86_expand_branch (GE, operands[0]); DONE;")
12961 (define_expand "bgeu"
12963 (if_then_else (match_dup 1)
12964 (label_ref (match_operand 0 "" ""))
12967 "ix86_expand_branch (GEU, operands[0]); DONE;")
12969 (define_expand "ble"
12971 (if_then_else (match_dup 1)
12972 (label_ref (match_operand 0 "" ""))
12975 "ix86_expand_branch (LE, operands[0]); DONE;")
12977 (define_expand "bleu"
12979 (if_then_else (match_dup 1)
12980 (label_ref (match_operand 0 "" ""))
12983 "ix86_expand_branch (LEU, operands[0]); DONE;")
12985 (define_expand "bunordered"
12987 (if_then_else (match_dup 1)
12988 (label_ref (match_operand 0 "" ""))
12990 "TARGET_80387 || TARGET_SSE_MATH"
12991 "ix86_expand_branch (UNORDERED, operands[0]); DONE;")
12993 (define_expand "bordered"
12995 (if_then_else (match_dup 1)
12996 (label_ref (match_operand 0 "" ""))
12998 "TARGET_80387 || TARGET_SSE_MATH"
12999 "ix86_expand_branch (ORDERED, operands[0]); DONE;")
13001 (define_expand "buneq"
13003 (if_then_else (match_dup 1)
13004 (label_ref (match_operand 0 "" ""))
13006 "TARGET_80387 || TARGET_SSE_MATH"
13007 "ix86_expand_branch (UNEQ, operands[0]); DONE;")
13009 (define_expand "bunge"
13011 (if_then_else (match_dup 1)
13012 (label_ref (match_operand 0 "" ""))
13014 "TARGET_80387 || TARGET_SSE_MATH"
13015 "ix86_expand_branch (UNGE, operands[0]); DONE;")
13017 (define_expand "bungt"
13019 (if_then_else (match_dup 1)
13020 (label_ref (match_operand 0 "" ""))
13022 "TARGET_80387 || TARGET_SSE_MATH"
13023 "ix86_expand_branch (UNGT, operands[0]); DONE;")
13025 (define_expand "bunle"
13027 (if_then_else (match_dup 1)
13028 (label_ref (match_operand 0 "" ""))
13030 "TARGET_80387 || TARGET_SSE_MATH"
13031 "ix86_expand_branch (UNLE, operands[0]); DONE;")
13033 (define_expand "bunlt"
13035 (if_then_else (match_dup 1)
13036 (label_ref (match_operand 0 "" ""))
13038 "TARGET_80387 || TARGET_SSE_MATH"
13039 "ix86_expand_branch (UNLT, operands[0]); DONE;")
13041 (define_expand "bltgt"
13043 (if_then_else (match_dup 1)
13044 (label_ref (match_operand 0 "" ""))
13046 "TARGET_80387 || TARGET_SSE_MATH"
13047 "ix86_expand_branch (LTGT, operands[0]); DONE;")
13049 (define_insn "*jcc_1"
13051 (if_then_else (match_operator 1 "ix86_comparison_operator"
13052 [(reg FLAGS_REG) (const_int 0)])
13053 (label_ref (match_operand 0 "" ""))
13057 [(set_attr "type" "ibr")
13058 (set_attr "modrm" "0")
13059 (set (attr "length")
13060 (if_then_else (and (ge (minus (match_dup 0) (pc))
13062 (lt (minus (match_dup 0) (pc))
13067 (define_insn "*jcc_2"
13069 (if_then_else (match_operator 1 "ix86_comparison_operator"
13070 [(reg FLAGS_REG) (const_int 0)])
13072 (label_ref (match_operand 0 "" ""))))]
13075 [(set_attr "type" "ibr")
13076 (set_attr "modrm" "0")
13077 (set (attr "length")
13078 (if_then_else (and (ge (minus (match_dup 0) (pc))
13080 (lt (minus (match_dup 0) (pc))
13085 ;; In general it is not safe to assume too much about CCmode registers,
13086 ;; so simplify-rtx stops when it sees a second one. Under certain
13087 ;; conditions this is safe on x86, so help combine not create
13095 (if_then_else (ne (match_operator 0 "ix86_comparison_operator"
13096 [(reg FLAGS_REG) (const_int 0)])
13098 (label_ref (match_operand 1 "" ""))
13102 (if_then_else (match_dup 0)
13103 (label_ref (match_dup 1))
13106 PUT_MODE (operands[0], VOIDmode);
13111 (if_then_else (eq (match_operator 0 "ix86_comparison_operator"
13112 [(reg FLAGS_REG) (const_int 0)])
13114 (label_ref (match_operand 1 "" ""))
13118 (if_then_else (match_dup 0)
13119 (label_ref (match_dup 1))
13122 rtx new_op0 = copy_rtx (operands[0]);
13123 operands[0] = new_op0;
13124 PUT_MODE (new_op0, VOIDmode);
13125 PUT_CODE (new_op0, ix86_reverse_condition (GET_CODE (new_op0),
13126 GET_MODE (XEXP (new_op0, 0))));
13128 /* Make sure that (a) the CCmode we have for the flags is strong
13129 enough for the reversed compare or (b) we have a valid FP compare. */
13130 if (! ix86_comparison_operator (new_op0, VOIDmode))
13134 ;; Define combination compare-and-branch fp compare instructions to use
13135 ;; during early optimization. Splitting the operation apart early makes
13136 ;; for bad code when we want to reverse the operation.
13138 (define_insn "*fp_jcc_1_mixed"
13140 (if_then_else (match_operator 0 "comparison_operator"
13141 [(match_operand 1 "register_operand" "f#x,x#f")
13142 (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
13143 (label_ref (match_operand 3 "" ""))
13145 (clobber (reg:CCFP FPSR_REG))
13146 (clobber (reg:CCFP FLAGS_REG))]
13147 "TARGET_MIX_SSE_I387
13148 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13149 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13150 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13153 (define_insn "*fp_jcc_1_sse"
13155 (if_then_else (match_operator 0 "comparison_operator"
13156 [(match_operand 1 "register_operand" "x")
13157 (match_operand 2 "nonimmediate_operand" "xm")])
13158 (label_ref (match_operand 3 "" ""))
13160 (clobber (reg:CCFP FPSR_REG))
13161 (clobber (reg:CCFP FLAGS_REG))]
13163 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13164 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13165 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13168 (define_insn "*fp_jcc_1_387"
13170 (if_then_else (match_operator 0 "comparison_operator"
13171 [(match_operand 1 "register_operand" "f")
13172 (match_operand 2 "register_operand" "f")])
13173 (label_ref (match_operand 3 "" ""))
13175 (clobber (reg:CCFP FPSR_REG))
13176 (clobber (reg:CCFP FLAGS_REG))]
13177 "TARGET_CMOVE && TARGET_80387
13178 && FLOAT_MODE_P (GET_MODE (operands[1]))
13179 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13180 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13183 (define_insn "*fp_jcc_2_mixed"
13185 (if_then_else (match_operator 0 "comparison_operator"
13186 [(match_operand 1 "register_operand" "f#x,x#f")
13187 (match_operand 2 "nonimmediate_operand" "f#x,xm#f")])
13189 (label_ref (match_operand 3 "" ""))))
13190 (clobber (reg:CCFP FPSR_REG))
13191 (clobber (reg:CCFP FLAGS_REG))]
13192 "TARGET_MIX_SSE_I387
13193 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13194 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13195 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13198 (define_insn "*fp_jcc_2_sse"
13200 (if_then_else (match_operator 0 "comparison_operator"
13201 [(match_operand 1 "register_operand" "x")
13202 (match_operand 2 "nonimmediate_operand" "xm")])
13204 (label_ref (match_operand 3 "" ""))))
13205 (clobber (reg:CCFP FPSR_REG))
13206 (clobber (reg:CCFP FLAGS_REG))]
13208 && SSE_FLOAT_MODE_P (GET_MODE (operands[1]))
13209 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13210 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13213 (define_insn "*fp_jcc_2_387"
13215 (if_then_else (match_operator 0 "comparison_operator"
13216 [(match_operand 1 "register_operand" "f")
13217 (match_operand 2 "register_operand" "f")])
13219 (label_ref (match_operand 3 "" ""))))
13220 (clobber (reg:CCFP FPSR_REG))
13221 (clobber (reg:CCFP FLAGS_REG))]
13222 "TARGET_CMOVE && TARGET_80387
13223 && FLOAT_MODE_P (GET_MODE (operands[1]))
13224 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13225 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13228 (define_insn "*fp_jcc_3_387"
13230 (if_then_else (match_operator 0 "comparison_operator"
13231 [(match_operand 1 "register_operand" "f")
13232 (match_operand 2 "nonimmediate_operand" "fm")])
13233 (label_ref (match_operand 3 "" ""))
13235 (clobber (reg:CCFP FPSR_REG))
13236 (clobber (reg:CCFP FLAGS_REG))
13237 (clobber (match_scratch:HI 4 "=a"))]
13239 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
13240 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13241 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
13242 && SELECT_CC_MODE (GET_CODE (operands[0]),
13243 operands[1], operands[2]) == CCFPmode
13244 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13247 (define_insn "*fp_jcc_4_387"
13249 (if_then_else (match_operator 0 "comparison_operator"
13250 [(match_operand 1 "register_operand" "f")
13251 (match_operand 2 "nonimmediate_operand" "fm")])
13253 (label_ref (match_operand 3 "" ""))))
13254 (clobber (reg:CCFP FPSR_REG))
13255 (clobber (reg:CCFP FLAGS_REG))
13256 (clobber (match_scratch:HI 4 "=a"))]
13258 && (GET_MODE (operands[1]) == SFmode || GET_MODE (operands[1]) == DFmode)
13259 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13260 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
13261 && SELECT_CC_MODE (GET_CODE (operands[0]),
13262 operands[1], operands[2]) == CCFPmode
13263 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13266 (define_insn "*fp_jcc_5_387"
13268 (if_then_else (match_operator 0 "comparison_operator"
13269 [(match_operand 1 "register_operand" "f")
13270 (match_operand 2 "register_operand" "f")])
13271 (label_ref (match_operand 3 "" ""))
13273 (clobber (reg:CCFP FPSR_REG))
13274 (clobber (reg:CCFP FLAGS_REG))
13275 (clobber (match_scratch:HI 4 "=a"))]
13277 && FLOAT_MODE_P (GET_MODE (operands[1]))
13278 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13279 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13282 (define_insn "*fp_jcc_6_387"
13284 (if_then_else (match_operator 0 "comparison_operator"
13285 [(match_operand 1 "register_operand" "f")
13286 (match_operand 2 "register_operand" "f")])
13288 (label_ref (match_operand 3 "" ""))))
13289 (clobber (reg:CCFP FPSR_REG))
13290 (clobber (reg:CCFP FLAGS_REG))
13291 (clobber (match_scratch:HI 4 "=a"))]
13293 && FLOAT_MODE_P (GET_MODE (operands[1]))
13294 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13295 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13298 (define_insn "*fp_jcc_7_387"
13300 (if_then_else (match_operator 0 "comparison_operator"
13301 [(match_operand 1 "register_operand" "f")
13302 (match_operand 2 "const0_operand" "X")])
13303 (label_ref (match_operand 3 "" ""))
13305 (clobber (reg:CCFP FPSR_REG))
13306 (clobber (reg:CCFP FLAGS_REG))
13307 (clobber (match_scratch:HI 4 "=a"))]
13309 && FLOAT_MODE_P (GET_MODE (operands[1]))
13310 && GET_MODE (operands[1]) == GET_MODE (operands[2])
13311 && !ix86_use_fcomi_compare (GET_CODE (operands[0]))
13312 && SELECT_CC_MODE (GET_CODE (operands[0]),
13313 operands[1], operands[2]) == CCFPmode
13314 && ix86_fp_jump_nontrivial_p (GET_CODE (operands[0]))"
13317 ;; The order of operands in *fp_jcc_8_387 is forced by combine in
13318 ;; simplify_comparison () function. Float operator is treated as RTX_OBJ
13319 ;; with a precedence over other operators and is always put in the first
13320 ;; place. Swap condition and operands to match ficom instruction.
13322 (define_insn "*fp_jcc_8<mode>_387"
13324 (if_then_else (match_operator 0 "comparison_operator"
13325 [(match_operator 1 "float_operator"
13326 [(match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r")])
13327 (match_operand 3 "register_operand" "f,f")])
13328 (label_ref (match_operand 4 "" ""))
13330 (clobber (reg:CCFP FPSR_REG))
13331 (clobber (reg:CCFP FLAGS_REG))
13332 (clobber (match_scratch:HI 5 "=a,a"))]
13333 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
13334 && FLOAT_MODE_P (GET_MODE (operands[3]))
13335 && GET_MODE (operands[1]) == GET_MODE (operands[3])
13336 && !ix86_use_fcomi_compare (swap_condition (GET_CODE (operands[0])))
13337 && ix86_fp_compare_mode (swap_condition (GET_CODE (operands[0]))) == CCFPmode
13338 && ix86_fp_jump_nontrivial_p (swap_condition (GET_CODE (operands[0])))"
13343 (if_then_else (match_operator 0 "comparison_operator"
13344 [(match_operand 1 "register_operand" "")
13345 (match_operand 2 "nonimmediate_operand" "")])
13346 (match_operand 3 "" "")
13347 (match_operand 4 "" "")))
13348 (clobber (reg:CCFP FPSR_REG))
13349 (clobber (reg:CCFP FLAGS_REG))]
13353 ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
13354 operands[3], operands[4], NULL_RTX, NULL_RTX);
13360 (if_then_else (match_operator 0 "comparison_operator"
13361 [(match_operand 1 "register_operand" "")
13362 (match_operand 2 "general_operand" "")])
13363 (match_operand 3 "" "")
13364 (match_operand 4 "" "")))
13365 (clobber (reg:CCFP FPSR_REG))
13366 (clobber (reg:CCFP FLAGS_REG))
13367 (clobber (match_scratch:HI 5 "=a"))]
13371 ix86_split_fp_branch (GET_CODE (operands[0]), operands[1], operands[2],
13372 operands[3], operands[4], operands[5], NULL_RTX);
13378 (if_then_else (match_operator 0 "comparison_operator"
13379 [(match_operator 1 "float_operator"
13380 [(match_operand:X87MODEI12 2 "memory_operand" "")])
13381 (match_operand 3 "register_operand" "")])
13382 (match_operand 4 "" "")
13383 (match_operand 5 "" "")))
13384 (clobber (reg:CCFP FPSR_REG))
13385 (clobber (reg:CCFP FLAGS_REG))
13386 (clobber (match_scratch:HI 6 "=a"))]
13390 operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[2]);
13391 ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
13392 operands[3], operands[7],
13393 operands[4], operands[5], operands[6], NULL_RTX);
13397 ;; %%% Kill this when reload knows how to do it.
13400 (if_then_else (match_operator 0 "comparison_operator"
13401 [(match_operator 1 "float_operator"
13402 [(match_operand:X87MODEI12 2 "register_operand" "")])
13403 (match_operand 3 "register_operand" "")])
13404 (match_operand 4 "" "")
13405 (match_operand 5 "" "")))
13406 (clobber (reg:CCFP FPSR_REG))
13407 (clobber (reg:CCFP FLAGS_REG))
13408 (clobber (match_scratch:HI 6 "=a"))]
13412 operands[7] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
13413 operands[7] = gen_rtx_FLOAT (GET_MODE (operands[1]), operands[7]);
13414 ix86_split_fp_branch (swap_condition (GET_CODE (operands[0])),
13415 operands[3], operands[7],
13416 operands[4], operands[5], operands[6], operands[2]);
13420 ;; Unconditional and other jump instructions
13422 (define_insn "jump"
13424 (label_ref (match_operand 0 "" "")))]
13427 [(set_attr "type" "ibr")
13428 (set (attr "length")
13429 (if_then_else (and (ge (minus (match_dup 0) (pc))
13431 (lt (minus (match_dup 0) (pc))
13435 (set_attr "modrm" "0")])
13437 (define_expand "indirect_jump"
13438 [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))]
13442 (define_insn "*indirect_jump"
13443 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))]
13446 [(set_attr "type" "ibr")
13447 (set_attr "length_immediate" "0")])
13449 (define_insn "*indirect_jump_rtx64"
13450 [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))]
13453 [(set_attr "type" "ibr")
13454 (set_attr "length_immediate" "0")])
13456 (define_expand "tablejump"
13457 [(parallel [(set (pc) (match_operand 0 "nonimmediate_operand" "rm"))
13458 (use (label_ref (match_operand 1 "" "")))])]
13461 /* In PIC mode, the table entries are stored GOT (32-bit) or PC (64-bit)
13462 relative. Convert the relative address to an absolute address. */
13466 enum rtx_code code;
13472 op1 = gen_rtx_LABEL_REF (Pmode, operands[1]);
13474 else if (TARGET_MACHO || HAVE_AS_GOTOFF_IN_DATA)
13478 op1 = pic_offset_table_rtx;
13483 op0 = pic_offset_table_rtx;
13487 operands[0] = expand_simple_binop (Pmode, code, op0, op1, NULL_RTX, 0,
13492 (define_insn "*tablejump_1"
13493 [(set (pc) (match_operand:SI 0 "nonimmediate_operand" "rm"))
13494 (use (label_ref (match_operand 1 "" "")))]
13497 [(set_attr "type" "ibr")
13498 (set_attr "length_immediate" "0")])
13500 (define_insn "*tablejump_1_rtx64"
13501 [(set (pc) (match_operand:DI 0 "nonimmediate_operand" "rm"))
13502 (use (label_ref (match_operand 1 "" "")))]
13505 [(set_attr "type" "ibr")
13506 (set_attr "length_immediate" "0")])
13508 ;; Convert setcc + movzbl to xor + setcc if operands don't overlap.
13511 [(set (reg FLAGS_REG) (match_operand 0 "" ""))
13512 (set (match_operand:QI 1 "register_operand" "")
13513 (match_operator:QI 2 "ix86_comparison_operator"
13514 [(reg FLAGS_REG) (const_int 0)]))
13515 (set (match_operand 3 "q_regs_operand" "")
13516 (zero_extend (match_dup 1)))]
13517 "(peep2_reg_dead_p (3, operands[1])
13518 || operands_match_p (operands[1], operands[3]))
13519 && ! reg_overlap_mentioned_p (operands[3], operands[0])"
13520 [(set (match_dup 4) (match_dup 0))
13521 (set (strict_low_part (match_dup 5))
13524 operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
13525 operands[5] = gen_lowpart (QImode, operands[3]);
13526 ix86_expand_clear (operands[3]);
13529 ;; Similar, but match zero_extendhisi2_and, which adds a clobber.
13532 [(set (reg FLAGS_REG) (match_operand 0 "" ""))
13533 (set (match_operand:QI 1 "register_operand" "")
13534 (match_operator:QI 2 "ix86_comparison_operator"
13535 [(reg FLAGS_REG) (const_int 0)]))
13536 (parallel [(set (match_operand 3 "q_regs_operand" "")
13537 (zero_extend (match_dup 1)))
13538 (clobber (reg:CC FLAGS_REG))])]
13539 "(peep2_reg_dead_p (3, operands[1])
13540 || operands_match_p (operands[1], operands[3]))
13541 && ! reg_overlap_mentioned_p (operands[3], operands[0])"
13542 [(set (match_dup 4) (match_dup 0))
13543 (set (strict_low_part (match_dup 5))
13546 operands[4] = gen_rtx_REG (GET_MODE (operands[0]), FLAGS_REG);
13547 operands[5] = gen_lowpart (QImode, operands[3]);
13548 ix86_expand_clear (operands[3]);
13551 ;; Call instructions.
13553 ;; The predicates normally associated with named expanders are not properly
13554 ;; checked for calls. This is a bug in the generic code, but it isn't that
13555 ;; easy to fix. Ignore it for now and be prepared to fix things up.
13557 ;; Call subroutine returning no value.
13559 (define_expand "call_pop"
13560 [(parallel [(call (match_operand:QI 0 "" "")
13561 (match_operand:SI 1 "" ""))
13562 (set (reg:SI SP_REG)
13563 (plus:SI (reg:SI SP_REG)
13564 (match_operand:SI 3 "" "")))])]
13567 ix86_expand_call (NULL, operands[0], operands[1], operands[2], operands[3], 0);
13571 (define_insn "*call_pop_0"
13572 [(call (mem:QI (match_operand:SI 0 "constant_call_address_operand" ""))
13573 (match_operand:SI 1 "" ""))
13574 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
13575 (match_operand:SI 2 "immediate_operand" "")))]
13578 if (SIBLING_CALL_P (insn))
13581 return "call\t%P0";
13583 [(set_attr "type" "call")])
13585 (define_insn "*call_pop_1"
13586 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
13587 (match_operand:SI 1 "" ""))
13588 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
13589 (match_operand:SI 2 "immediate_operand" "i")))]
13592 if (constant_call_address_operand (operands[0], Pmode))
13594 if (SIBLING_CALL_P (insn))
13597 return "call\t%P0";
13599 if (SIBLING_CALL_P (insn))
13602 return "call\t%A0";
13604 [(set_attr "type" "call")])
13606 (define_expand "call"
13607 [(call (match_operand:QI 0 "" "")
13608 (match_operand 1 "" ""))
13609 (use (match_operand 2 "" ""))]
13612 ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 0);
13616 (define_expand "sibcall"
13617 [(call (match_operand:QI 0 "" "")
13618 (match_operand 1 "" ""))
13619 (use (match_operand 2 "" ""))]
13622 ix86_expand_call (NULL, operands[0], operands[1], operands[2], NULL, 1);
13626 (define_insn "*call_0"
13627 [(call (mem:QI (match_operand 0 "constant_call_address_operand" ""))
13628 (match_operand 1 "" ""))]
13631 if (SIBLING_CALL_P (insn))
13634 return "call\t%P0";
13636 [(set_attr "type" "call")])
13638 (define_insn "*call_1"
13639 [(call (mem:QI (match_operand:SI 0 "call_insn_operand" "rsm"))
13640 (match_operand 1 "" ""))]
13641 "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
13643 if (constant_call_address_operand (operands[0], Pmode))
13644 return "call\t%P0";
13645 return "call\t%A0";
13647 [(set_attr "type" "call")])
13649 (define_insn "*sibcall_1"
13650 [(call (mem:QI (match_operand:SI 0 "sibcall_insn_operand" "s,c,d,a"))
13651 (match_operand 1 "" ""))]
13652 "SIBLING_CALL_P (insn) && !TARGET_64BIT"
13654 if (constant_call_address_operand (operands[0], Pmode))
13658 [(set_attr "type" "call")])
13660 (define_insn "*call_1_rex64"
13661 [(call (mem:QI (match_operand:DI 0 "call_insn_operand" "rsm"))
13662 (match_operand 1 "" ""))]
13663 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
13665 if (constant_call_address_operand (operands[0], Pmode))
13666 return "call\t%P0";
13667 return "call\t%A0";
13669 [(set_attr "type" "call")])
13671 (define_insn "*sibcall_1_rex64"
13672 [(call (mem:QI (match_operand:DI 0 "constant_call_address_operand" ""))
13673 (match_operand 1 "" ""))]
13674 "SIBLING_CALL_P (insn) && TARGET_64BIT"
13676 [(set_attr "type" "call")])
13678 (define_insn "*sibcall_1_rex64_v"
13679 [(call (mem:QI (reg:DI 40))
13680 (match_operand 0 "" ""))]
13681 "SIBLING_CALL_P (insn) && TARGET_64BIT"
13683 [(set_attr "type" "call")])
13686 ;; Call subroutine, returning value in operand 0
13688 (define_expand "call_value_pop"
13689 [(parallel [(set (match_operand 0 "" "")
13690 (call (match_operand:QI 1 "" "")
13691 (match_operand:SI 2 "" "")))
13692 (set (reg:SI SP_REG)
13693 (plus:SI (reg:SI SP_REG)
13694 (match_operand:SI 4 "" "")))])]
13697 ix86_expand_call (operands[0], operands[1], operands[2],
13698 operands[3], operands[4], 0);
13702 (define_expand "call_value"
13703 [(set (match_operand 0 "" "")
13704 (call (match_operand:QI 1 "" "")
13705 (match_operand:SI 2 "" "")))
13706 (use (match_operand:SI 3 "" ""))]
13707 ;; Operand 2 not used on the i386.
13710 ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 0);
13714 (define_expand "sibcall_value"
13715 [(set (match_operand 0 "" "")
13716 (call (match_operand:QI 1 "" "")
13717 (match_operand:SI 2 "" "")))
13718 (use (match_operand:SI 3 "" ""))]
13719 ;; Operand 2 not used on the i386.
13722 ix86_expand_call (operands[0], operands[1], operands[2], operands[3], NULL, 1);
13726 ;; Call subroutine returning any type.
13728 (define_expand "untyped_call"
13729 [(parallel [(call (match_operand 0 "" "")
13731 (match_operand 1 "" "")
13732 (match_operand 2 "" "")])]
13737 /* In order to give reg-stack an easier job in validating two
13738 coprocessor registers as containing a possible return value,
13739 simply pretend the untyped call returns a complex long double
13742 ix86_expand_call ((TARGET_FLOAT_RETURNS_IN_80387
13743 ? gen_rtx_REG (XCmode, FIRST_FLOAT_REG) : NULL),
13744 operands[0], const0_rtx, GEN_INT (SSE_REGPARM_MAX - 1),
13747 for (i = 0; i < XVECLEN (operands[2], 0); i++)
13749 rtx set = XVECEXP (operands[2], 0, i);
13750 emit_move_insn (SET_DEST (set), SET_SRC (set));
13753 /* The optimizer does not know that the call sets the function value
13754 registers we stored in the result block. We avoid problems by
13755 claiming that all hard registers are used and clobbered at this
13757 emit_insn (gen_blockage (const0_rtx));
13762 ;; Prologue and epilogue instructions
13764 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
13765 ;; all of memory. This blocks insns from being moved across this point.
13767 (define_insn "blockage"
13768 [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_BLOCKAGE)]
13771 [(set_attr "length" "0")])
13773 ;; Insn emitted into the body of a function to return from a function.
13774 ;; This is only done if the function's epilogue is known to be simple.
13775 ;; See comments for ix86_can_use_return_insn_p in i386.c.
13777 (define_expand "return"
13779 "ix86_can_use_return_insn_p ()"
13781 if (current_function_pops_args)
13783 rtx popc = GEN_INT (current_function_pops_args);
13784 emit_jump_insn (gen_return_pop_internal (popc));
13789 (define_insn "return_internal"
13793 [(set_attr "length" "1")
13794 (set_attr "length_immediate" "0")
13795 (set_attr "modrm" "0")])
13797 ;; Used by x86_machine_dependent_reorg to avoid penalty on single byte RET
13798 ;; instruction Athlon and K8 have.
13800 (define_insn "return_internal_long"
13802 (unspec [(const_int 0)] UNSPEC_REP)]
13805 [(set_attr "length" "1")
13806 (set_attr "length_immediate" "0")
13807 (set_attr "prefix_rep" "1")
13808 (set_attr "modrm" "0")])
13810 (define_insn "return_pop_internal"
13812 (use (match_operand:SI 0 "const_int_operand" ""))]
13815 [(set_attr "length" "3")
13816 (set_attr "length_immediate" "2")
13817 (set_attr "modrm" "0")])
13819 (define_insn "return_indirect_internal"
13821 (use (match_operand:SI 0 "register_operand" "r"))]
13824 [(set_attr "type" "ibr")
13825 (set_attr "length_immediate" "0")])
13831 [(set_attr "length" "1")
13832 (set_attr "length_immediate" "0")
13833 (set_attr "modrm" "0")])
13835 ;; Align to 16-byte boundary, max skip in op0. Used to avoid
13836 ;; branch prediction penalty for the third jump in a 16-byte
13839 (define_insn "align"
13840 [(unspec_volatile [(match_operand 0 "" "")] UNSPECV_ALIGN)]
13843 #ifdef ASM_OUTPUT_MAX_SKIP_ALIGN
13844 ASM_OUTPUT_MAX_SKIP_ALIGN (asm_out_file, 4, (int)INTVAL (operands[0]));
13846 /* It is tempting to use ASM_OUTPUT_ALIGN here, but we don't want to do that.
13847 The align insn is used to avoid 3 jump instructions in the row to improve
13848 branch prediction and the benefits hardly outweight the cost of extra 8
13849 nops on the average inserted by full alignment pseudo operation. */
13853 [(set_attr "length" "16")])
13855 (define_expand "prologue"
13858 "ix86_expand_prologue (); DONE;")
13860 (define_insn "set_got"
13861 [(set (match_operand:SI 0 "register_operand" "=r")
13862 (unspec:SI [(const_int 0)] UNSPEC_SET_GOT))
13863 (clobber (reg:CC FLAGS_REG))]
13865 { return output_set_got (operands[0]); }
13866 [(set_attr "type" "multi")
13867 (set_attr "length" "12")])
13869 (define_insn "set_got_rex64"
13870 [(set (match_operand:DI 0 "register_operand" "=r")
13871 (unspec:DI [(const_int 0)] UNSPEC_SET_GOT))]
13873 "lea{q}\t_GLOBAL_OFFSET_TABLE_(%%rip), %0"
13874 [(set_attr "type" "lea")
13875 (set_attr "length" "6")])
13877 (define_expand "epilogue"
13880 "ix86_expand_epilogue (1); DONE;")
13882 (define_expand "sibcall_epilogue"
13885 "ix86_expand_epilogue (0); DONE;")
13887 (define_expand "eh_return"
13888 [(use (match_operand 0 "register_operand" ""))]
13891 rtx tmp, sa = EH_RETURN_STACKADJ_RTX, ra = operands[0];
13893 /* Tricky bit: we write the address of the handler to which we will
13894 be returning into someone else's stack frame, one word below the
13895 stack address we wish to restore. */
13896 tmp = gen_rtx_PLUS (Pmode, arg_pointer_rtx, sa);
13897 tmp = plus_constant (tmp, -UNITS_PER_WORD);
13898 tmp = gen_rtx_MEM (Pmode, tmp);
13899 emit_move_insn (tmp, ra);
13901 if (Pmode == SImode)
13902 emit_jump_insn (gen_eh_return_si (sa));
13904 emit_jump_insn (gen_eh_return_di (sa));
13909 (define_insn_and_split "eh_return_si"
13911 (unspec [(match_operand:SI 0 "register_operand" "c")]
13912 UNSPEC_EH_RETURN))]
13917 "ix86_expand_epilogue (2); DONE;")
13919 (define_insn_and_split "eh_return_di"
13921 (unspec [(match_operand:DI 0 "register_operand" "c")]
13922 UNSPEC_EH_RETURN))]
13927 "ix86_expand_epilogue (2); DONE;")
13929 (define_insn "leave"
13930 [(set (reg:SI SP_REG) (plus:SI (reg:SI BP_REG) (const_int 4)))
13931 (set (reg:SI BP_REG) (mem:SI (reg:SI BP_REG)))
13932 (clobber (mem:BLK (scratch)))]
13935 [(set_attr "type" "leave")])
13937 (define_insn "leave_rex64"
13938 [(set (reg:DI SP_REG) (plus:DI (reg:DI BP_REG) (const_int 8)))
13939 (set (reg:DI BP_REG) (mem:DI (reg:DI BP_REG)))
13940 (clobber (mem:BLK (scratch)))]
13943 [(set_attr "type" "leave")])
13945 (define_expand "ffssi2"
13947 [(set (match_operand:SI 0 "register_operand" "")
13948 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "")))
13949 (clobber (match_scratch:SI 2 ""))
13950 (clobber (reg:CC FLAGS_REG))])]
13954 (define_insn_and_split "*ffs_cmove"
13955 [(set (match_operand:SI 0 "register_operand" "=r")
13956 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
13957 (clobber (match_scratch:SI 2 "=&r"))
13958 (clobber (reg:CC FLAGS_REG))]
13961 "&& reload_completed"
13962 [(set (match_dup 2) (const_int -1))
13963 (parallel [(set (reg:CCZ FLAGS_REG) (compare:CCZ (match_dup 1) (const_int 0)))
13964 (set (match_dup 0) (ctz:SI (match_dup 1)))])
13965 (set (match_dup 0) (if_then_else:SI
13966 (eq (reg:CCZ FLAGS_REG) (const_int 0))
13969 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
13970 (clobber (reg:CC FLAGS_REG))])]
13973 (define_insn_and_split "*ffs_no_cmove"
13974 [(set (match_operand:SI 0 "nonimmediate_operand" "=r")
13975 (ffs:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
13976 (clobber (match_scratch:SI 2 "=&q"))
13977 (clobber (reg:CC FLAGS_REG))]
13981 [(parallel [(set (reg:CCZ FLAGS_REG) (compare:CCZ (match_dup 1) (const_int 0)))
13982 (set (match_dup 0) (ctz:SI (match_dup 1)))])
13983 (set (strict_low_part (match_dup 3))
13984 (eq:QI (reg:CCZ FLAGS_REG) (const_int 0)))
13985 (parallel [(set (match_dup 2) (neg:SI (match_dup 2)))
13986 (clobber (reg:CC FLAGS_REG))])
13987 (parallel [(set (match_dup 0) (ior:SI (match_dup 0) (match_dup 2)))
13988 (clobber (reg:CC FLAGS_REG))])
13989 (parallel [(set (match_dup 0) (plus:SI (match_dup 0) (const_int 1)))
13990 (clobber (reg:CC FLAGS_REG))])]
13992 operands[3] = gen_lowpart (QImode, operands[2]);
13993 ix86_expand_clear (operands[2]);
13996 (define_insn "*ffssi_1"
13997 [(set (reg:CCZ FLAGS_REG)
13998 (compare:CCZ (match_operand:SI 1 "nonimmediate_operand" "rm")
14000 (set (match_operand:SI 0 "register_operand" "=r")
14001 (ctz:SI (match_dup 1)))]
14003 "bsf{l}\t{%1, %0|%0, %1}"
14004 [(set_attr "prefix_0f" "1")])
14006 (define_expand "ffsdi2"
14008 [(set (match_operand:DI 0 "register_operand" "")
14009 (ffs:DI (match_operand:DI 1 "nonimmediate_operand" "")))
14010 (clobber (match_scratch:DI 2 ""))
14011 (clobber (reg:CC FLAGS_REG))])]
14012 "TARGET_64BIT && TARGET_CMOVE"
14015 (define_insn_and_split "*ffs_rex64"
14016 [(set (match_operand:DI 0 "register_operand" "=r")
14017 (ffs:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
14018 (clobber (match_scratch:DI 2 "=&r"))
14019 (clobber (reg:CC FLAGS_REG))]
14020 "TARGET_64BIT && TARGET_CMOVE"
14022 "&& reload_completed"
14023 [(set (match_dup 2) (const_int -1))
14024 (parallel [(set (reg:CCZ FLAGS_REG)
14025 (compare:CCZ (match_dup 1) (const_int 0)))
14026 (set (match_dup 0) (ctz:DI (match_dup 1)))])
14027 (set (match_dup 0) (if_then_else:DI
14028 (eq (reg:CCZ FLAGS_REG) (const_int 0))
14031 (parallel [(set (match_dup 0) (plus:DI (match_dup 0) (const_int 1)))
14032 (clobber (reg:CC FLAGS_REG))])]
14035 (define_insn "*ffsdi_1"
14036 [(set (reg:CCZ FLAGS_REG)
14037 (compare:CCZ (match_operand:DI 1 "nonimmediate_operand" "rm")
14039 (set (match_operand:DI 0 "register_operand" "=r")
14040 (ctz:DI (match_dup 1)))]
14042 "bsf{q}\t{%1, %0|%0, %1}"
14043 [(set_attr "prefix_0f" "1")])
14045 (define_insn "ctzsi2"
14046 [(set (match_operand:SI 0 "register_operand" "=r")
14047 (ctz:SI (match_operand:SI 1 "nonimmediate_operand" "rm")))
14048 (clobber (reg:CC FLAGS_REG))]
14050 "bsf{l}\t{%1, %0|%0, %1}"
14051 [(set_attr "prefix_0f" "1")])
14053 (define_insn "ctzdi2"
14054 [(set (match_operand:DI 0 "register_operand" "=r")
14055 (ctz:DI (match_operand:DI 1 "nonimmediate_operand" "rm")))
14056 (clobber (reg:CC FLAGS_REG))]
14058 "bsf{q}\t{%1, %0|%0, %1}"
14059 [(set_attr "prefix_0f" "1")])
14061 (define_expand "clzsi2"
14063 [(set (match_operand:SI 0 "register_operand" "")
14064 (minus:SI (const_int 31)
14065 (clz:SI (match_operand:SI 1 "nonimmediate_operand" ""))))
14066 (clobber (reg:CC FLAGS_REG))])
14068 [(set (match_dup 0) (xor:SI (match_dup 0) (const_int 31)))
14069 (clobber (reg:CC FLAGS_REG))])]
14073 (define_insn "*bsr"
14074 [(set (match_operand:SI 0 "register_operand" "=r")
14075 (minus:SI (const_int 31)
14076 (clz:SI (match_operand:SI 1 "nonimmediate_operand" "rm"))))
14077 (clobber (reg:CC FLAGS_REG))]
14079 "bsr{l}\t{%1, %0|%0, %1}"
14080 [(set_attr "prefix_0f" "1")])
14082 (define_expand "clzdi2"
14084 [(set (match_operand:DI 0 "register_operand" "")
14085 (minus:DI (const_int 63)
14086 (clz:DI (match_operand:DI 1 "nonimmediate_operand" ""))))
14087 (clobber (reg:CC FLAGS_REG))])
14089 [(set (match_dup 0) (xor:DI (match_dup 0) (const_int 63)))
14090 (clobber (reg:CC FLAGS_REG))])]
14094 (define_insn "*bsr_rex64"
14095 [(set (match_operand:DI 0 "register_operand" "=r")
14096 (minus:DI (const_int 63)
14097 (clz:DI (match_operand:DI 1 "nonimmediate_operand" "rm"))))
14098 (clobber (reg:CC FLAGS_REG))]
14100 "bsr{q}\t{%1, %0|%0, %1}"
14101 [(set_attr "prefix_0f" "1")])
14103 ;; Thread-local storage patterns for ELF.
14105 ;; Note that these code sequences must appear exactly as shown
14106 ;; in order to allow linker relaxation.
14108 (define_insn "*tls_global_dynamic_32_gnu"
14109 [(set (match_operand:SI 0 "register_operand" "=a")
14110 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14111 (match_operand:SI 2 "tls_symbolic_operand" "")
14112 (match_operand:SI 3 "call_insn_operand" "")]
14114 (clobber (match_scratch:SI 4 "=d"))
14115 (clobber (match_scratch:SI 5 "=c"))
14116 (clobber (reg:CC FLAGS_REG))]
14117 "!TARGET_64BIT && TARGET_GNU_TLS"
14118 "lea{l}\t{%a2@TLSGD(,%1,1), %0|%0, %a2@TLSGD[%1*1]}\;call\t%P3"
14119 [(set_attr "type" "multi")
14120 (set_attr "length" "12")])
14122 (define_insn "*tls_global_dynamic_32_sun"
14123 [(set (match_operand:SI 0 "register_operand" "=a")
14124 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14125 (match_operand:SI 2 "tls_symbolic_operand" "")
14126 (match_operand:SI 3 "call_insn_operand" "")]
14128 (clobber (match_scratch:SI 4 "=d"))
14129 (clobber (match_scratch:SI 5 "=c"))
14130 (clobber (reg:CC FLAGS_REG))]
14131 "!TARGET_64BIT && TARGET_SUN_TLS"
14132 "lea{l}\t{%a2@DTLNDX(%1), %4|%4, %a2@DTLNDX[%1]}
14133 push{l}\t%4\;call\t%a2@TLSPLT\;pop{l}\t%4\;nop"
14134 [(set_attr "type" "multi")
14135 (set_attr "length" "14")])
14137 (define_expand "tls_global_dynamic_32"
14138 [(parallel [(set (match_operand:SI 0 "register_operand" "")
14141 (match_operand:SI 1 "tls_symbolic_operand" "")
14144 (clobber (match_scratch:SI 4 ""))
14145 (clobber (match_scratch:SI 5 ""))
14146 (clobber (reg:CC FLAGS_REG))])]
14150 operands[2] = pic_offset_table_rtx;
14153 operands[2] = gen_reg_rtx (Pmode);
14154 emit_insn (gen_set_got (operands[2]));
14156 operands[3] = ix86_tls_get_addr ();
14159 (define_insn "*tls_global_dynamic_64"
14160 [(set (match_operand:DI 0 "register_operand" "=a")
14161 (call:DI (mem:QI (match_operand:DI 2 "call_insn_operand" ""))
14162 (match_operand:DI 3 "" "")))
14163 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
14166 ".byte\t0x66\;lea{q}\t{%a1@TLSGD(%%rip), %%rdi|%%rdi, %a1@TLSGD[%%rip]}\;.word\t0x6666\;rex64\;call\t%P2"
14167 [(set_attr "type" "multi")
14168 (set_attr "length" "16")])
14170 (define_expand "tls_global_dynamic_64"
14171 [(parallel [(set (match_operand:DI 0 "register_operand" "")
14172 (call:DI (mem:QI (match_dup 2)) (const_int 0)))
14173 (unspec:DI [(match_operand:DI 1 "tls_symbolic_operand" "")]
14177 operands[2] = ix86_tls_get_addr ();
14180 (define_insn "*tls_local_dynamic_base_32_gnu"
14181 [(set (match_operand:SI 0 "register_operand" "=a")
14182 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14183 (match_operand:SI 2 "call_insn_operand" "")]
14184 UNSPEC_TLS_LD_BASE))
14185 (clobber (match_scratch:SI 3 "=d"))
14186 (clobber (match_scratch:SI 4 "=c"))
14187 (clobber (reg:CC FLAGS_REG))]
14188 "!TARGET_64BIT && TARGET_GNU_TLS"
14189 "lea{l}\t{%&@TLSLDM(%1), %0|%0, %&@TLSLDM[%1]}\;call\t%P2"
14190 [(set_attr "type" "multi")
14191 (set_attr "length" "11")])
14193 (define_insn "*tls_local_dynamic_base_32_sun"
14194 [(set (match_operand:SI 0 "register_operand" "=a")
14195 (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14196 (match_operand:SI 2 "call_insn_operand" "")]
14197 UNSPEC_TLS_LD_BASE))
14198 (clobber (match_scratch:SI 3 "=d"))
14199 (clobber (match_scratch:SI 4 "=c"))
14200 (clobber (reg:CC FLAGS_REG))]
14201 "!TARGET_64BIT && TARGET_SUN_TLS"
14202 "lea{l}\t{%&@TMDNX(%1), %3|%3, %&@TMDNX[%1]}
14203 push{l}\t%3\;call\t%&@TLSPLT\;pop{l}\t%3"
14204 [(set_attr "type" "multi")
14205 (set_attr "length" "13")])
14207 (define_expand "tls_local_dynamic_base_32"
14208 [(parallel [(set (match_operand:SI 0 "register_operand" "")
14209 (unspec:SI [(match_dup 1) (match_dup 2)]
14210 UNSPEC_TLS_LD_BASE))
14211 (clobber (match_scratch:SI 3 ""))
14212 (clobber (match_scratch:SI 4 ""))
14213 (clobber (reg:CC FLAGS_REG))])]
14217 operands[1] = pic_offset_table_rtx;
14220 operands[1] = gen_reg_rtx (Pmode);
14221 emit_insn (gen_set_got (operands[1]));
14223 operands[2] = ix86_tls_get_addr ();
14226 (define_insn "*tls_local_dynamic_base_64"
14227 [(set (match_operand:DI 0 "register_operand" "=a")
14228 (call:DI (mem:QI (match_operand:DI 1 "call_insn_operand" ""))
14229 (match_operand:DI 2 "" "")))
14230 (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)]
14232 "lea{q}\t{%&@TLSLD(%%rip), %%rdi|%%rdi, %&@TLSLD[%%rip]}\;call\t%P1"
14233 [(set_attr "type" "multi")
14234 (set_attr "length" "12")])
14236 (define_expand "tls_local_dynamic_base_64"
14237 [(parallel [(set (match_operand:DI 0 "register_operand" "")
14238 (call:DI (mem:QI (match_dup 1)) (const_int 0)))
14239 (unspec:DI [(const_int 0)] UNSPEC_TLS_LD_BASE)])]
14242 operands[1] = ix86_tls_get_addr ();
14245 ;; Local dynamic of a single variable is a lose. Show combine how
14246 ;; to convert that back to global dynamic.
14248 (define_insn_and_split "*tls_local_dynamic_32_once"
14249 [(set (match_operand:SI 0 "register_operand" "=a")
14250 (plus:SI (unspec:SI [(match_operand:SI 1 "register_operand" "b")
14251 (match_operand:SI 2 "call_insn_operand" "")]
14252 UNSPEC_TLS_LD_BASE)
14253 (const:SI (unspec:SI
14254 [(match_operand:SI 3 "tls_symbolic_operand" "")]
14256 (clobber (match_scratch:SI 4 "=d"))
14257 (clobber (match_scratch:SI 5 "=c"))
14258 (clobber (reg:CC FLAGS_REG))]
14262 [(parallel [(set (match_dup 0)
14263 (unspec:SI [(match_dup 1) (match_dup 3) (match_dup 2)]
14265 (clobber (match_dup 4))
14266 (clobber (match_dup 5))
14267 (clobber (reg:CC FLAGS_REG))])]
14270 ;; Load and add the thread base pointer from %gs:0.
14272 (define_insn "*load_tp_si"
14273 [(set (match_operand:SI 0 "register_operand" "=r")
14274 (unspec:SI [(const_int 0)] UNSPEC_TP))]
14276 "mov{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}"
14277 [(set_attr "type" "imov")
14278 (set_attr "modrm" "0")
14279 (set_attr "length" "7")
14280 (set_attr "memory" "load")
14281 (set_attr "imm_disp" "false")])
14283 (define_insn "*add_tp_si"
14284 [(set (match_operand:SI 0 "register_operand" "=r")
14285 (plus:SI (unspec:SI [(const_int 0)] UNSPEC_TP)
14286 (match_operand:SI 1 "register_operand" "0")))
14287 (clobber (reg:CC FLAGS_REG))]
14289 "add{l}\t{%%gs:0, %0|%0, DWORD PTR %%gs:0}"
14290 [(set_attr "type" "alu")
14291 (set_attr "modrm" "0")
14292 (set_attr "length" "7")
14293 (set_attr "memory" "load")
14294 (set_attr "imm_disp" "false")])
14296 (define_insn "*load_tp_di"
14297 [(set (match_operand:DI 0 "register_operand" "=r")
14298 (unspec:DI [(const_int 0)] UNSPEC_TP))]
14300 "mov{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}"
14301 [(set_attr "type" "imov")
14302 (set_attr "modrm" "0")
14303 (set_attr "length" "7")
14304 (set_attr "memory" "load")
14305 (set_attr "imm_disp" "false")])
14307 (define_insn "*add_tp_di"
14308 [(set (match_operand:DI 0 "register_operand" "=r")
14309 (plus:DI (unspec:DI [(const_int 0)] UNSPEC_TP)
14310 (match_operand:DI 1 "register_operand" "0")))
14311 (clobber (reg:CC FLAGS_REG))]
14313 "add{q}\t{%%fs:0, %0|%0, QWORD PTR %%fs:0}"
14314 [(set_attr "type" "alu")
14315 (set_attr "modrm" "0")
14316 (set_attr "length" "7")
14317 (set_attr "memory" "load")
14318 (set_attr "imm_disp" "false")])
14320 ;; These patterns match the binary 387 instructions for addM3, subM3,
14321 ;; mulM3 and divM3. There are three patterns for each of DFmode and
14322 ;; SFmode. The first is the normal insn, the second the same insn but
14323 ;; with one operand a conversion, and the third the same insn but with
14324 ;; the other operand a conversion. The conversion may be SFmode or
14325 ;; SImode if the target mode DFmode, but only SImode if the target mode
14328 ;; Gcc is slightly more smart about handling normal two address instructions
14329 ;; so use special patterns for add and mull.
14331 (define_insn "*fop_sf_comm_mixed"
14332 [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
14333 (match_operator:SF 3 "binary_fp_operator"
14334 [(match_operand:SF 1 "nonimmediate_operand" "%0,0")
14335 (match_operand:SF 2 "nonimmediate_operand" "fm#x,xm#f")]))]
14336 "TARGET_MIX_SSE_I387
14337 && COMMUTATIVE_ARITH_P (operands[3])
14338 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14339 "* return output_387_binary_op (insn, operands);"
14340 [(set (attr "type")
14341 (if_then_else (eq_attr "alternative" "1")
14342 (if_then_else (match_operand:SF 3 "mult_operator" "")
14343 (const_string "ssemul")
14344 (const_string "sseadd"))
14345 (if_then_else (match_operand:SF 3 "mult_operator" "")
14346 (const_string "fmul")
14347 (const_string "fop"))))
14348 (set_attr "mode" "SF")])
14350 (define_insn "*fop_sf_comm_sse"
14351 [(set (match_operand:SF 0 "register_operand" "=x")
14352 (match_operator:SF 3 "binary_fp_operator"
14353 [(match_operand:SF 1 "nonimmediate_operand" "%0")
14354 (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
14356 && COMMUTATIVE_ARITH_P (operands[3])
14357 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14358 "* return output_387_binary_op (insn, operands);"
14359 [(set (attr "type")
14360 (if_then_else (match_operand:SF 3 "mult_operator" "")
14361 (const_string "ssemul")
14362 (const_string "sseadd")))
14363 (set_attr "mode" "SF")])
14365 (define_insn "*fop_sf_comm_i387"
14366 [(set (match_operand:SF 0 "register_operand" "=f")
14367 (match_operator:SF 3 "binary_fp_operator"
14368 [(match_operand:SF 1 "nonimmediate_operand" "%0")
14369 (match_operand:SF 2 "nonimmediate_operand" "fm")]))]
14371 && COMMUTATIVE_ARITH_P (operands[3])
14372 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14373 "* return output_387_binary_op (insn, operands);"
14374 [(set (attr "type")
14375 (if_then_else (match_operand:SF 3 "mult_operator" "")
14376 (const_string "fmul")
14377 (const_string "fop")))
14378 (set_attr "mode" "SF")])
14380 (define_insn "*fop_sf_1_mixed"
14381 [(set (match_operand:SF 0 "register_operand" "=f,f,x")
14382 (match_operator:SF 3 "binary_fp_operator"
14383 [(match_operand:SF 1 "nonimmediate_operand" "0,fm,0")
14384 (match_operand:SF 2 "nonimmediate_operand" "fm,0,xm#f")]))]
14385 "TARGET_MIX_SSE_I387
14386 && !COMMUTATIVE_ARITH_P (operands[3])
14387 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14388 "* return output_387_binary_op (insn, operands);"
14389 [(set (attr "type")
14390 (cond [(and (eq_attr "alternative" "2")
14391 (match_operand:SF 3 "mult_operator" ""))
14392 (const_string "ssemul")
14393 (and (eq_attr "alternative" "2")
14394 (match_operand:SF 3 "div_operator" ""))
14395 (const_string "ssediv")
14396 (eq_attr "alternative" "2")
14397 (const_string "sseadd")
14398 (match_operand:SF 3 "mult_operator" "")
14399 (const_string "fmul")
14400 (match_operand:SF 3 "div_operator" "")
14401 (const_string "fdiv")
14403 (const_string "fop")))
14404 (set_attr "mode" "SF")])
14406 (define_insn "*fop_sf_1_sse"
14407 [(set (match_operand:SF 0 "register_operand" "=x")
14408 (match_operator:SF 3 "binary_fp_operator"
14409 [(match_operand:SF 1 "register_operand" "0")
14410 (match_operand:SF 2 "nonimmediate_operand" "xm")]))]
14412 && !COMMUTATIVE_ARITH_P (operands[3])"
14413 "* return output_387_binary_op (insn, operands);"
14414 [(set (attr "type")
14415 (cond [(match_operand:SF 3 "mult_operator" "")
14416 (const_string "ssemul")
14417 (match_operand:SF 3 "div_operator" "")
14418 (const_string "ssediv")
14420 (const_string "sseadd")))
14421 (set_attr "mode" "SF")])
14423 ;; This pattern is not fully shadowed by the pattern above.
14424 (define_insn "*fop_sf_1_i387"
14425 [(set (match_operand:SF 0 "register_operand" "=f,f")
14426 (match_operator:SF 3 "binary_fp_operator"
14427 [(match_operand:SF 1 "nonimmediate_operand" "0,fm")
14428 (match_operand:SF 2 "nonimmediate_operand" "fm,0")]))]
14429 "TARGET_80387 && !TARGET_SSE_MATH
14430 && !COMMUTATIVE_ARITH_P (operands[3])
14431 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14432 "* return output_387_binary_op (insn, operands);"
14433 [(set (attr "type")
14434 (cond [(match_operand:SF 3 "mult_operator" "")
14435 (const_string "fmul")
14436 (match_operand:SF 3 "div_operator" "")
14437 (const_string "fdiv")
14439 (const_string "fop")))
14440 (set_attr "mode" "SF")])
14442 ;; ??? Add SSE splitters for these!
14443 (define_insn "*fop_sf_2<mode>_i387"
14444 [(set (match_operand:SF 0 "register_operand" "=f,f")
14445 (match_operator:SF 3 "binary_fp_operator"
14446 [(float:SF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14447 (match_operand:SF 2 "register_operand" "0,0")]))]
14448 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH"
14449 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14450 [(set (attr "type")
14451 (cond [(match_operand:SF 3 "mult_operator" "")
14452 (const_string "fmul")
14453 (match_operand:SF 3 "div_operator" "")
14454 (const_string "fdiv")
14456 (const_string "fop")))
14457 (set_attr "fp_int_src" "true")
14458 (set_attr "mode" "<MODE>")])
14460 (define_insn "*fop_sf_3<mode>_i387"
14461 [(set (match_operand:SF 0 "register_operand" "=f,f")
14462 (match_operator:SF 3 "binary_fp_operator"
14463 [(match_operand:SF 1 "register_operand" "0,0")
14464 (float:SF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14465 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP && !TARGET_SSE_MATH"
14466 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14467 [(set (attr "type")
14468 (cond [(match_operand:SF 3 "mult_operator" "")
14469 (const_string "fmul")
14470 (match_operand:SF 3 "div_operator" "")
14471 (const_string "fdiv")
14473 (const_string "fop")))
14474 (set_attr "fp_int_src" "true")
14475 (set_attr "mode" "<MODE>")])
14477 (define_insn "*fop_df_comm_mixed"
14478 [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
14479 (match_operator:DF 3 "binary_fp_operator"
14480 [(match_operand:DF 1 "nonimmediate_operand" "%0,0")
14481 (match_operand:DF 2 "nonimmediate_operand" "fm#Y,Ym#f")]))]
14482 "TARGET_SSE2 && TARGET_MIX_SSE_I387
14483 && COMMUTATIVE_ARITH_P (operands[3])
14484 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14485 "* return output_387_binary_op (insn, operands);"
14486 [(set (attr "type")
14487 (if_then_else (eq_attr "alternative" "1")
14488 (if_then_else (match_operand:SF 3 "mult_operator" "")
14489 (const_string "ssemul")
14490 (const_string "sseadd"))
14491 (if_then_else (match_operand:SF 3 "mult_operator" "")
14492 (const_string "fmul")
14493 (const_string "fop"))))
14494 (set_attr "mode" "DF")])
14496 (define_insn "*fop_df_comm_sse"
14497 [(set (match_operand:DF 0 "register_operand" "=Y")
14498 (match_operator:DF 3 "binary_fp_operator"
14499 [(match_operand:DF 1 "nonimmediate_operand" "%0")
14500 (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
14501 "TARGET_SSE2 && TARGET_SSE_MATH
14502 && COMMUTATIVE_ARITH_P (operands[3])
14503 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14504 "* return output_387_binary_op (insn, operands);"
14505 [(set (attr "type")
14506 (if_then_else (match_operand:SF 3 "mult_operator" "")
14507 (const_string "ssemul")
14508 (const_string "sseadd")))
14509 (set_attr "mode" "DF")])
14511 (define_insn "*fop_df_comm_i387"
14512 [(set (match_operand:DF 0 "register_operand" "=f")
14513 (match_operator:DF 3 "binary_fp_operator"
14514 [(match_operand:DF 1 "nonimmediate_operand" "%0")
14515 (match_operand:DF 2 "nonimmediate_operand" "fm")]))]
14517 && COMMUTATIVE_ARITH_P (operands[3])
14518 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14519 "* return output_387_binary_op (insn, operands);"
14520 [(set (attr "type")
14521 (if_then_else (match_operand:SF 3 "mult_operator" "")
14522 (const_string "fmul")
14523 (const_string "fop")))
14524 (set_attr "mode" "DF")])
14526 (define_insn "*fop_df_1_mixed"
14527 [(set (match_operand:DF 0 "register_operand" "=f#Y,f#Y,Y#f")
14528 (match_operator:DF 3 "binary_fp_operator"
14529 [(match_operand:DF 1 "nonimmediate_operand" "0,fm,0")
14530 (match_operand:DF 2 "nonimmediate_operand" "fm,0,Ym#f")]))]
14531 "TARGET_SSE2 && TARGET_SSE_MATH && TARGET_MIX_SSE_I387
14532 && !COMMUTATIVE_ARITH_P (operands[3])
14533 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14534 "* return output_387_binary_op (insn, operands);"
14535 [(set (attr "type")
14536 (cond [(and (eq_attr "alternative" "2")
14537 (match_operand:SF 3 "mult_operator" ""))
14538 (const_string "ssemul")
14539 (and (eq_attr "alternative" "2")
14540 (match_operand:SF 3 "div_operator" ""))
14541 (const_string "ssediv")
14542 (eq_attr "alternative" "2")
14543 (const_string "sseadd")
14544 (match_operand:DF 3 "mult_operator" "")
14545 (const_string "fmul")
14546 (match_operand:DF 3 "div_operator" "")
14547 (const_string "fdiv")
14549 (const_string "fop")))
14550 (set_attr "mode" "DF")])
14552 (define_insn "*fop_df_1_sse"
14553 [(set (match_operand:DF 0 "register_operand" "=Y")
14554 (match_operator:DF 3 "binary_fp_operator"
14555 [(match_operand:DF 1 "register_operand" "0")
14556 (match_operand:DF 2 "nonimmediate_operand" "Ym")]))]
14557 "TARGET_SSE2 && TARGET_SSE_MATH
14558 && !COMMUTATIVE_ARITH_P (operands[3])"
14559 "* return output_387_binary_op (insn, operands);"
14560 [(set_attr "mode" "DF")
14562 (cond [(match_operand:SF 3 "mult_operator" "")
14563 (const_string "ssemul")
14564 (match_operand:SF 3 "div_operator" "")
14565 (const_string "ssediv")
14567 (const_string "sseadd")))])
14569 ;; This pattern is not fully shadowed by the pattern above.
14570 (define_insn "*fop_df_1_i387"
14571 [(set (match_operand:DF 0 "register_operand" "=f,f")
14572 (match_operator:DF 3 "binary_fp_operator"
14573 [(match_operand:DF 1 "nonimmediate_operand" "0,fm")
14574 (match_operand:DF 2 "nonimmediate_operand" "fm,0")]))]
14575 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
14576 && !COMMUTATIVE_ARITH_P (operands[3])
14577 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14578 "* return output_387_binary_op (insn, operands);"
14579 [(set (attr "type")
14580 (cond [(match_operand:DF 3 "mult_operator" "")
14581 (const_string "fmul")
14582 (match_operand:DF 3 "div_operator" "")
14583 (const_string "fdiv")
14585 (const_string "fop")))
14586 (set_attr "mode" "DF")])
14588 ;; ??? Add SSE splitters for these!
14589 (define_insn "*fop_df_2<mode>_i387"
14590 [(set (match_operand:DF 0 "register_operand" "=f,f")
14591 (match_operator:DF 3 "binary_fp_operator"
14592 [(float:DF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14593 (match_operand:DF 2 "register_operand" "0,0")]))]
14594 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
14595 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14596 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14597 [(set (attr "type")
14598 (cond [(match_operand:DF 3 "mult_operator" "")
14599 (const_string "fmul")
14600 (match_operand:DF 3 "div_operator" "")
14601 (const_string "fdiv")
14603 (const_string "fop")))
14604 (set_attr "fp_int_src" "true")
14605 (set_attr "mode" "<MODE>")])
14607 (define_insn "*fop_df_3<mode>_i387"
14608 [(set (match_operand:DF 0 "register_operand" "=f,f")
14609 (match_operator:DF 3 "binary_fp_operator"
14610 [(match_operand:DF 1 "register_operand" "0,0")
14611 (float:DF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14612 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP
14613 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14614 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14615 [(set (attr "type")
14616 (cond [(match_operand:DF 3 "mult_operator" "")
14617 (const_string "fmul")
14618 (match_operand:DF 3 "div_operator" "")
14619 (const_string "fdiv")
14621 (const_string "fop")))
14622 (set_attr "fp_int_src" "true")
14623 (set_attr "mode" "<MODE>")])
14625 (define_insn "*fop_df_4_i387"
14626 [(set (match_operand:DF 0 "register_operand" "=f,f")
14627 (match_operator:DF 3 "binary_fp_operator"
14628 [(float_extend:DF (match_operand:SF 1 "nonimmediate_operand" "fm,0"))
14629 (match_operand:DF 2 "register_operand" "0,f")]))]
14630 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)
14631 && (GET_CODE (operands[1]) != MEM || GET_CODE (operands[2]) != MEM)"
14632 "* return output_387_binary_op (insn, operands);"
14633 [(set (attr "type")
14634 (cond [(match_operand:DF 3 "mult_operator" "")
14635 (const_string "fmul")
14636 (match_operand:DF 3 "div_operator" "")
14637 (const_string "fdiv")
14639 (const_string "fop")))
14640 (set_attr "mode" "SF")])
14642 (define_insn "*fop_df_5_i387"
14643 [(set (match_operand:DF 0 "register_operand" "=f,f")
14644 (match_operator:DF 3 "binary_fp_operator"
14645 [(match_operand:DF 1 "register_operand" "0,f")
14647 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
14648 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14649 "* return output_387_binary_op (insn, operands);"
14650 [(set (attr "type")
14651 (cond [(match_operand:DF 3 "mult_operator" "")
14652 (const_string "fmul")
14653 (match_operand:DF 3 "div_operator" "")
14654 (const_string "fdiv")
14656 (const_string "fop")))
14657 (set_attr "mode" "SF")])
14659 (define_insn "*fop_df_6_i387"
14660 [(set (match_operand:DF 0 "register_operand" "=f,f")
14661 (match_operator:DF 3 "binary_fp_operator"
14663 (match_operand:SF 1 "register_operand" "0,f"))
14665 (match_operand:SF 2 "nonimmediate_operand" "fm,0"))]))]
14666 "TARGET_80387 && !(TARGET_SSE2 && TARGET_SSE_MATH)"
14667 "* return output_387_binary_op (insn, operands);"
14668 [(set (attr "type")
14669 (cond [(match_operand:DF 3 "mult_operator" "")
14670 (const_string "fmul")
14671 (match_operand:DF 3 "div_operator" "")
14672 (const_string "fdiv")
14674 (const_string "fop")))
14675 (set_attr "mode" "SF")])
14677 (define_insn "*fop_xf_comm_i387"
14678 [(set (match_operand:XF 0 "register_operand" "=f")
14679 (match_operator:XF 3 "binary_fp_operator"
14680 [(match_operand:XF 1 "register_operand" "%0")
14681 (match_operand:XF 2 "register_operand" "f")]))]
14683 && COMMUTATIVE_ARITH_P (operands[3])"
14684 "* return output_387_binary_op (insn, operands);"
14685 [(set (attr "type")
14686 (if_then_else (match_operand:XF 3 "mult_operator" "")
14687 (const_string "fmul")
14688 (const_string "fop")))
14689 (set_attr "mode" "XF")])
14691 (define_insn "*fop_xf_1_i387"
14692 [(set (match_operand:XF 0 "register_operand" "=f,f")
14693 (match_operator:XF 3 "binary_fp_operator"
14694 [(match_operand:XF 1 "register_operand" "0,f")
14695 (match_operand:XF 2 "register_operand" "f,0")]))]
14697 && !COMMUTATIVE_ARITH_P (operands[3])"
14698 "* return output_387_binary_op (insn, operands);"
14699 [(set (attr "type")
14700 (cond [(match_operand:XF 3 "mult_operator" "")
14701 (const_string "fmul")
14702 (match_operand:XF 3 "div_operator" "")
14703 (const_string "fdiv")
14705 (const_string "fop")))
14706 (set_attr "mode" "XF")])
14708 (define_insn "*fop_xf_2<mode>_i387"
14709 [(set (match_operand:XF 0 "register_operand" "=f,f")
14710 (match_operator:XF 3 "binary_fp_operator"
14711 [(float:XF (match_operand:X87MODEI12 1 "nonimmediate_operand" "m,?r"))
14712 (match_operand:XF 2 "register_operand" "0,0")]))]
14713 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP"
14714 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14715 [(set (attr "type")
14716 (cond [(match_operand:XF 3 "mult_operator" "")
14717 (const_string "fmul")
14718 (match_operand:XF 3 "div_operator" "")
14719 (const_string "fdiv")
14721 (const_string "fop")))
14722 (set_attr "fp_int_src" "true")
14723 (set_attr "mode" "<MODE>")])
14725 (define_insn "*fop_xf_3<mode>_i387"
14726 [(set (match_operand:XF 0 "register_operand" "=f,f")
14727 (match_operator:XF 3 "binary_fp_operator"
14728 [(match_operand:XF 1 "register_operand" "0,0")
14729 (float:XF (match_operand:X87MODEI12 2 "nonimmediate_operand" "m,?r"))]))]
14730 "TARGET_80387 && TARGET_USE_<MODE>MODE_FIOP"
14731 "* return which_alternative ? \"#\" : output_387_binary_op (insn, operands);"
14732 [(set (attr "type")
14733 (cond [(match_operand:XF 3 "mult_operator" "")
14734 (const_string "fmul")
14735 (match_operand:XF 3 "div_operator" "")
14736 (const_string "fdiv")
14738 (const_string "fop")))
14739 (set_attr "fp_int_src" "true")
14740 (set_attr "mode" "<MODE>")])
14742 (define_insn "*fop_xf_4_i387"
14743 [(set (match_operand:XF 0 "register_operand" "=f,f")
14744 (match_operator:XF 3 "binary_fp_operator"
14745 [(float_extend:XF (match_operand 1 "nonimmediate_operand" "fm,0"))
14746 (match_operand:XF 2 "register_operand" "0,f")]))]
14748 "* return output_387_binary_op (insn, operands);"
14749 [(set (attr "type")
14750 (cond [(match_operand:XF 3 "mult_operator" "")
14751 (const_string "fmul")
14752 (match_operand:XF 3 "div_operator" "")
14753 (const_string "fdiv")
14755 (const_string "fop")))
14756 (set_attr "mode" "SF")])
14758 (define_insn "*fop_xf_5_i387"
14759 [(set (match_operand:XF 0 "register_operand" "=f,f")
14760 (match_operator:XF 3 "binary_fp_operator"
14761 [(match_operand:XF 1 "register_operand" "0,f")
14763 (match_operand 2 "nonimmediate_operand" "fm,0"))]))]
14765 "* return output_387_binary_op (insn, operands);"
14766 [(set (attr "type")
14767 (cond [(match_operand:XF 3 "mult_operator" "")
14768 (const_string "fmul")
14769 (match_operand:XF 3 "div_operator" "")
14770 (const_string "fdiv")
14772 (const_string "fop")))
14773 (set_attr "mode" "SF")])
14775 (define_insn "*fop_xf_6_i387"
14776 [(set (match_operand:XF 0 "register_operand" "=f,f")
14777 (match_operator:XF 3 "binary_fp_operator"
14779 (match_operand 1 "register_operand" "0,f"))
14781 (match_operand 2 "nonimmediate_operand" "fm,0"))]))]
14783 "* return output_387_binary_op (insn, operands);"
14784 [(set (attr "type")
14785 (cond [(match_operand:XF 3 "mult_operator" "")
14786 (const_string "fmul")
14787 (match_operand:XF 3 "div_operator" "")
14788 (const_string "fdiv")
14790 (const_string "fop")))
14791 (set_attr "mode" "SF")])
14794 [(set (match_operand 0 "register_operand" "")
14795 (match_operator 3 "binary_fp_operator"
14796 [(float (match_operand:X87MODEI12 1 "register_operand" ""))
14797 (match_operand 2 "register_operand" "")]))]
14798 "TARGET_80387 && reload_completed
14799 && FLOAT_MODE_P (GET_MODE (operands[0]))"
14802 operands[4] = ix86_force_to_memory (GET_MODE (operands[1]), operands[1]);
14803 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
14804 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
14805 gen_rtx_fmt_ee (GET_CODE (operands[3]),
14806 GET_MODE (operands[3]),
14809 ix86_free_from_memory (GET_MODE (operands[1]));
14814 [(set (match_operand 0 "register_operand" "")
14815 (match_operator 3 "binary_fp_operator"
14816 [(match_operand 1 "register_operand" "")
14817 (float (match_operand:X87MODEI12 2 "register_operand" ""))]))]
14818 "TARGET_80387 && reload_completed
14819 && FLOAT_MODE_P (GET_MODE (operands[0]))"
14822 operands[4] = ix86_force_to_memory (GET_MODE (operands[2]), operands[2]);
14823 operands[4] = gen_rtx_FLOAT (GET_MODE (operands[0]), operands[4]);
14824 emit_insn (gen_rtx_SET (VOIDmode, operands[0],
14825 gen_rtx_fmt_ee (GET_CODE (operands[3]),
14826 GET_MODE (operands[3]),
14829 ix86_free_from_memory (GET_MODE (operands[2]));
14833 ;; FPU special functions.
14835 (define_expand "sqrtsf2"
14836 [(set (match_operand:SF 0 "register_operand" "")
14837 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "")))]
14838 "TARGET_USE_FANCY_MATH_387 || TARGET_SSE_MATH"
14840 if (!TARGET_SSE_MATH)
14841 operands[1] = force_reg (SFmode, operands[1]);
14844 (define_insn "*sqrtsf2_mixed"
14845 [(set (match_operand:SF 0 "register_operand" "=f#x,x#f")
14846 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "0#x,xm#f")))]
14847 "TARGET_USE_FANCY_MATH_387 && TARGET_MIX_SSE_I387"
14850 sqrtss\t{%1, %0|%0, %1}"
14851 [(set_attr "type" "fpspc,sse")
14852 (set_attr "mode" "SF,SF")
14853 (set_attr "athlon_decode" "direct,*")])
14855 (define_insn "*sqrtsf2_sse"
14856 [(set (match_operand:SF 0 "register_operand" "=x")
14857 (sqrt:SF (match_operand:SF 1 "nonimmediate_operand" "xm")))]
14859 "sqrtss\t{%1, %0|%0, %1}"
14860 [(set_attr "type" "sse")
14861 (set_attr "mode" "SF")
14862 (set_attr "athlon_decode" "*")])
14864 (define_insn "*sqrtsf2_i387"
14865 [(set (match_operand:SF 0 "register_operand" "=f")
14866 (sqrt:SF (match_operand:SF 1 "register_operand" "0")))]
14867 "TARGET_USE_FANCY_MATH_387"
14869 [(set_attr "type" "fpspc")
14870 (set_attr "mode" "SF")
14871 (set_attr "athlon_decode" "direct")])
14873 (define_expand "sqrtdf2"
14874 [(set (match_operand:DF 0 "register_operand" "")
14875 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "")))]
14876 "TARGET_USE_FANCY_MATH_387 || (TARGET_SSE2 && TARGET_SSE_MATH)"
14878 if (!(TARGET_SSE2 && TARGET_SSE_MATH))
14879 operands[1] = force_reg (DFmode, operands[1]);
14882 (define_insn "*sqrtdf2_mixed"
14883 [(set (match_operand:DF 0 "register_operand" "=f#Y,Y#f")
14884 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "0#Y,Ym#f")))]
14885 "TARGET_USE_FANCY_MATH_387 && TARGET_SSE2 && TARGET_MIX_SSE_I387"
14888 sqrtsd\t{%1, %0|%0, %1}"
14889 [(set_attr "type" "fpspc,sse")
14890 (set_attr "mode" "DF,DF")
14891 (set_attr "athlon_decode" "direct,*")])
14893 (define_insn "*sqrtdf2_sse"
14894 [(set (match_operand:DF 0 "register_operand" "=Y")
14895 (sqrt:DF (match_operand:DF 1 "nonimmediate_operand" "Ym")))]
14896 "TARGET_SSE2 && TARGET_SSE_MATH"
14897 "sqrtsd\t{%1, %0|%0, %1}"
14898 [(set_attr "type" "sse")
14899 (set_attr "mode" "DF")
14900 (set_attr "athlon_decode" "*")])
14902 (define_insn "*sqrtdf2_i387"
14903 [(set (match_operand:DF 0 "register_operand" "=f")
14904 (sqrt:DF (match_operand:DF 1 "register_operand" "0")))]
14905 "TARGET_USE_FANCY_MATH_387"
14907 [(set_attr "type" "fpspc")
14908 (set_attr "mode" "DF")
14909 (set_attr "athlon_decode" "direct")])
14911 (define_insn "*sqrtextendsfdf2_i387"
14912 [(set (match_operand:DF 0 "register_operand" "=f")
14913 (sqrt:DF (float_extend:DF
14914 (match_operand:SF 1 "register_operand" "0"))))]
14915 "TARGET_USE_FANCY_MATH_387
14916 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)"
14918 [(set_attr "type" "fpspc")
14919 (set_attr "mode" "DF")
14920 (set_attr "athlon_decode" "direct")])
14922 (define_insn "sqrtxf2"
14923 [(set (match_operand:XF 0 "register_operand" "=f")
14924 (sqrt:XF (match_operand:XF 1 "register_operand" "0")))]
14925 "TARGET_USE_FANCY_MATH_387
14926 && (TARGET_IEEE_FP || flag_unsafe_math_optimizations) "
14928 [(set_attr "type" "fpspc")
14929 (set_attr "mode" "XF")
14930 (set_attr "athlon_decode" "direct")])
14932 (define_insn "*sqrtextendsfxf2_i387"
14933 [(set (match_operand:XF 0 "register_operand" "=f")
14934 (sqrt:XF (float_extend:XF
14935 (match_operand:SF 1 "register_operand" "0"))))]
14936 "TARGET_USE_FANCY_MATH_387"
14938 [(set_attr "type" "fpspc")
14939 (set_attr "mode" "XF")
14940 (set_attr "athlon_decode" "direct")])
14942 (define_insn "*sqrtextenddfxf2_i387"
14943 [(set (match_operand:XF 0 "register_operand" "=f")
14944 (sqrt:XF (float_extend:XF
14945 (match_operand:DF 1 "register_operand" "0"))))]
14946 "TARGET_USE_FANCY_MATH_387"
14948 [(set_attr "type" "fpspc")
14949 (set_attr "mode" "XF")
14950 (set_attr "athlon_decode" "direct")])
14952 (define_insn "fpremxf4"
14953 [(set (match_operand:XF 0 "register_operand" "=f")
14954 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
14955 (match_operand:XF 3 "register_operand" "1")]
14957 (set (match_operand:XF 1 "register_operand" "=u")
14958 (unspec:XF [(match_dup 2) (match_dup 3)]
14960 (set (reg:CCFP FPSR_REG)
14961 (unspec:CCFP [(const_int 0)] UNSPEC_NOP))]
14962 "TARGET_USE_FANCY_MATH_387
14963 && flag_unsafe_math_optimizations"
14965 [(set_attr "type" "fpspc")
14966 (set_attr "mode" "XF")])
14968 (define_expand "fmodsf3"
14969 [(use (match_operand:SF 0 "register_operand" ""))
14970 (use (match_operand:SF 1 "register_operand" ""))
14971 (use (match_operand:SF 2 "register_operand" ""))]
14972 "TARGET_USE_FANCY_MATH_387
14973 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
14974 && flag_unsafe_math_optimizations"
14976 rtx label = gen_label_rtx ();
14978 rtx op1 = gen_reg_rtx (XFmode);
14979 rtx op2 = gen_reg_rtx (XFmode);
14981 emit_insn(gen_extendsfxf2 (op1, operands[1]));
14982 emit_insn(gen_extendsfxf2 (op2, operands[2]));
14984 emit_label (label);
14986 emit_insn (gen_fpremxf4 (op1, op2, op1, op2));
14987 ix86_emit_fp_unordered_jump (label);
14989 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op1));
14993 (define_expand "fmoddf3"
14994 [(use (match_operand:DF 0 "register_operand" ""))
14995 (use (match_operand:DF 1 "register_operand" ""))
14996 (use (match_operand:DF 2 "register_operand" ""))]
14997 "TARGET_USE_FANCY_MATH_387
14998 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
14999 && flag_unsafe_math_optimizations"
15001 rtx label = gen_label_rtx ();
15003 rtx op1 = gen_reg_rtx (XFmode);
15004 rtx op2 = gen_reg_rtx (XFmode);
15006 emit_insn (gen_extenddfxf2 (op1, operands[1]));
15007 emit_insn (gen_extenddfxf2 (op2, operands[2]));
15009 emit_label (label);
15011 emit_insn (gen_fpremxf4 (op1, op2, op1, op2));
15012 ix86_emit_fp_unordered_jump (label);
15014 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op1));
15018 (define_expand "fmodxf3"
15019 [(use (match_operand:XF 0 "register_operand" ""))
15020 (use (match_operand:XF 1 "register_operand" ""))
15021 (use (match_operand:XF 2 "register_operand" ""))]
15022 "TARGET_USE_FANCY_MATH_387
15023 && flag_unsafe_math_optimizations"
15025 rtx label = gen_label_rtx ();
15027 emit_label (label);
15029 emit_insn (gen_fpremxf4 (operands[1], operands[2],
15030 operands[1], operands[2]));
15031 ix86_emit_fp_unordered_jump (label);
15033 emit_move_insn (operands[0], operands[1]);
15037 (define_insn "fprem1xf4"
15038 [(set (match_operand:XF 0 "register_operand" "=f")
15039 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15040 (match_operand:XF 3 "register_operand" "1")]
15042 (set (match_operand:XF 1 "register_operand" "=u")
15043 (unspec:XF [(match_dup 2) (match_dup 3)]
15045 (set (reg:CCFP FPSR_REG)
15046 (unspec:CCFP [(const_int 0)] UNSPEC_NOP))]
15047 "TARGET_USE_FANCY_MATH_387
15048 && flag_unsafe_math_optimizations"
15050 [(set_attr "type" "fpspc")
15051 (set_attr "mode" "XF")])
15053 (define_expand "dremsf3"
15054 [(use (match_operand:SF 0 "register_operand" ""))
15055 (use (match_operand:SF 1 "register_operand" ""))
15056 (use (match_operand:SF 2 "register_operand" ""))]
15057 "TARGET_USE_FANCY_MATH_387
15058 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15059 && flag_unsafe_math_optimizations"
15061 rtx label = gen_label_rtx ();
15063 rtx op1 = gen_reg_rtx (XFmode);
15064 rtx op2 = gen_reg_rtx (XFmode);
15066 emit_insn(gen_extendsfxf2 (op1, operands[1]));
15067 emit_insn(gen_extendsfxf2 (op2, operands[2]));
15069 emit_label (label);
15071 emit_insn (gen_fprem1xf4 (op1, op2, op1, op2));
15072 ix86_emit_fp_unordered_jump (label);
15074 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op1));
15078 (define_expand "dremdf3"
15079 [(use (match_operand:DF 0 "register_operand" ""))
15080 (use (match_operand:DF 1 "register_operand" ""))
15081 (use (match_operand:DF 2 "register_operand" ""))]
15082 "TARGET_USE_FANCY_MATH_387
15083 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15084 && flag_unsafe_math_optimizations"
15086 rtx label = gen_label_rtx ();
15088 rtx op1 = gen_reg_rtx (XFmode);
15089 rtx op2 = gen_reg_rtx (XFmode);
15091 emit_insn (gen_extenddfxf2 (op1, operands[1]));
15092 emit_insn (gen_extenddfxf2 (op2, operands[2]));
15094 emit_label (label);
15096 emit_insn (gen_fprem1xf4 (op1, op2, op1, op2));
15097 ix86_emit_fp_unordered_jump (label);
15099 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op1));
15103 (define_expand "dremxf3"
15104 [(use (match_operand:XF 0 "register_operand" ""))
15105 (use (match_operand:XF 1 "register_operand" ""))
15106 (use (match_operand:XF 2 "register_operand" ""))]
15107 "TARGET_USE_FANCY_MATH_387
15108 && flag_unsafe_math_optimizations"
15110 rtx label = gen_label_rtx ();
15112 emit_label (label);
15114 emit_insn (gen_fprem1xf4 (operands[1], operands[2],
15115 operands[1], operands[2]));
15116 ix86_emit_fp_unordered_jump (label);
15118 emit_move_insn (operands[0], operands[1]);
15122 (define_insn "*sindf2"
15123 [(set (match_operand:DF 0 "register_operand" "=f")
15124 (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_SIN))]
15125 "TARGET_USE_FANCY_MATH_387
15126 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15127 && flag_unsafe_math_optimizations"
15129 [(set_attr "type" "fpspc")
15130 (set_attr "mode" "DF")])
15132 (define_insn "*sinsf2"
15133 [(set (match_operand:SF 0 "register_operand" "=f")
15134 (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_SIN))]
15135 "TARGET_USE_FANCY_MATH_387
15136 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15137 && flag_unsafe_math_optimizations"
15139 [(set_attr "type" "fpspc")
15140 (set_attr "mode" "SF")])
15142 (define_insn "*sinextendsfdf2"
15143 [(set (match_operand:DF 0 "register_operand" "=f")
15144 (unspec:DF [(float_extend:DF
15145 (match_operand:SF 1 "register_operand" "0"))]
15147 "TARGET_USE_FANCY_MATH_387
15148 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15149 && flag_unsafe_math_optimizations"
15151 [(set_attr "type" "fpspc")
15152 (set_attr "mode" "DF")])
15154 (define_insn "*sinxf2"
15155 [(set (match_operand:XF 0 "register_operand" "=f")
15156 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_SIN))]
15157 "TARGET_USE_FANCY_MATH_387
15158 && flag_unsafe_math_optimizations"
15160 [(set_attr "type" "fpspc")
15161 (set_attr "mode" "XF")])
15163 (define_insn "*cosdf2"
15164 [(set (match_operand:DF 0 "register_operand" "=f")
15165 (unspec:DF [(match_operand:DF 1 "register_operand" "0")] UNSPEC_COS))]
15166 "TARGET_USE_FANCY_MATH_387
15167 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15168 && flag_unsafe_math_optimizations"
15170 [(set_attr "type" "fpspc")
15171 (set_attr "mode" "DF")])
15173 (define_insn "*cossf2"
15174 [(set (match_operand:SF 0 "register_operand" "=f")
15175 (unspec:SF [(match_operand:SF 1 "register_operand" "0")] UNSPEC_COS))]
15176 "TARGET_USE_FANCY_MATH_387
15177 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15178 && flag_unsafe_math_optimizations"
15180 [(set_attr "type" "fpspc")
15181 (set_attr "mode" "SF")])
15183 (define_insn "*cosextendsfdf2"
15184 [(set (match_operand:DF 0 "register_operand" "=f")
15185 (unspec:DF [(float_extend:DF
15186 (match_operand:SF 1 "register_operand" "0"))]
15188 "TARGET_USE_FANCY_MATH_387
15189 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15190 && flag_unsafe_math_optimizations"
15192 [(set_attr "type" "fpspc")
15193 (set_attr "mode" "DF")])
15195 (define_insn "*cosxf2"
15196 [(set (match_operand:XF 0 "register_operand" "=f")
15197 (unspec:XF [(match_operand:XF 1 "register_operand" "0")] UNSPEC_COS))]
15198 "TARGET_USE_FANCY_MATH_387
15199 && flag_unsafe_math_optimizations"
15201 [(set_attr "type" "fpspc")
15202 (set_attr "mode" "XF")])
15204 ;; With sincos pattern defined, sin and cos builtin function will be
15205 ;; expanded to sincos pattern with one of its outputs left unused.
15206 ;; Cse pass will detected, if two sincos patterns can be combined,
15207 ;; otherwise sincos pattern will be split back to sin or cos pattern,
15208 ;; depending on the unused output.
15210 (define_insn "sincosdf3"
15211 [(set (match_operand:DF 0 "register_operand" "=f")
15212 (unspec:DF [(match_operand:DF 2 "register_operand" "0")]
15213 UNSPEC_SINCOS_COS))
15214 (set (match_operand:DF 1 "register_operand" "=u")
15215 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15216 "TARGET_USE_FANCY_MATH_387
15217 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15218 && flag_unsafe_math_optimizations"
15220 [(set_attr "type" "fpspc")
15221 (set_attr "mode" "DF")])
15224 [(set (match_operand:DF 0 "register_operand" "")
15225 (unspec:DF [(match_operand:DF 2 "register_operand" "")]
15226 UNSPEC_SINCOS_COS))
15227 (set (match_operand:DF 1 "register_operand" "")
15228 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15229 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
15230 && !reload_completed && !reload_in_progress"
15231 [(set (match_dup 1) (unspec:DF [(match_dup 2)] UNSPEC_SIN))]
15235 [(set (match_operand:DF 0 "register_operand" "")
15236 (unspec:DF [(match_operand:DF 2 "register_operand" "")]
15237 UNSPEC_SINCOS_COS))
15238 (set (match_operand:DF 1 "register_operand" "")
15239 (unspec:DF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15240 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
15241 && !reload_completed && !reload_in_progress"
15242 [(set (match_dup 0) (unspec:DF [(match_dup 2)] UNSPEC_COS))]
15245 (define_insn "sincossf3"
15246 [(set (match_operand:SF 0 "register_operand" "=f")
15247 (unspec:SF [(match_operand:SF 2 "register_operand" "0")]
15248 UNSPEC_SINCOS_COS))
15249 (set (match_operand:SF 1 "register_operand" "=u")
15250 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15251 "TARGET_USE_FANCY_MATH_387
15252 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15253 && flag_unsafe_math_optimizations"
15255 [(set_attr "type" "fpspc")
15256 (set_attr "mode" "SF")])
15259 [(set (match_operand:SF 0 "register_operand" "")
15260 (unspec:SF [(match_operand:SF 2 "register_operand" "")]
15261 UNSPEC_SINCOS_COS))
15262 (set (match_operand:SF 1 "register_operand" "")
15263 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15264 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
15265 && !reload_completed && !reload_in_progress"
15266 [(set (match_dup 1) (unspec:SF [(match_dup 2)] UNSPEC_SIN))]
15270 [(set (match_operand:SF 0 "register_operand" "")
15271 (unspec:SF [(match_operand:SF 2 "register_operand" "")]
15272 UNSPEC_SINCOS_COS))
15273 (set (match_operand:SF 1 "register_operand" "")
15274 (unspec:SF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15275 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
15276 && !reload_completed && !reload_in_progress"
15277 [(set (match_dup 0) (unspec:SF [(match_dup 2)] UNSPEC_COS))]
15280 (define_insn "*sincosextendsfdf3"
15281 [(set (match_operand:DF 0 "register_operand" "=f")
15282 (unspec:DF [(float_extend:DF
15283 (match_operand:SF 2 "register_operand" "0"))]
15284 UNSPEC_SINCOS_COS))
15285 (set (match_operand:DF 1 "register_operand" "=u")
15286 (unspec:DF [(float_extend:DF
15287 (match_dup 2))] UNSPEC_SINCOS_SIN))]
15288 "TARGET_USE_FANCY_MATH_387
15289 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15290 && flag_unsafe_math_optimizations"
15292 [(set_attr "type" "fpspc")
15293 (set_attr "mode" "DF")])
15296 [(set (match_operand:DF 0 "register_operand" "")
15297 (unspec:DF [(float_extend:DF
15298 (match_operand:SF 2 "register_operand" ""))]
15299 UNSPEC_SINCOS_COS))
15300 (set (match_operand:DF 1 "register_operand" "")
15301 (unspec:DF [(float_extend:DF
15302 (match_dup 2))] UNSPEC_SINCOS_SIN))]
15303 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
15304 && !reload_completed && !reload_in_progress"
15305 [(set (match_dup 1) (unspec:DF [(float_extend:DF
15306 (match_dup 2))] UNSPEC_SIN))]
15310 [(set (match_operand:DF 0 "register_operand" "")
15311 (unspec:DF [(float_extend:DF
15312 (match_operand:SF 2 "register_operand" ""))]
15313 UNSPEC_SINCOS_COS))
15314 (set (match_operand:DF 1 "register_operand" "")
15315 (unspec:DF [(float_extend:DF
15316 (match_dup 2))] UNSPEC_SINCOS_SIN))]
15317 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
15318 && !reload_completed && !reload_in_progress"
15319 [(set (match_dup 0) (unspec:DF [(float_extend:DF
15320 (match_dup 2))] UNSPEC_COS))]
15323 (define_insn "sincosxf3"
15324 [(set (match_operand:XF 0 "register_operand" "=f")
15325 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15326 UNSPEC_SINCOS_COS))
15327 (set (match_operand:XF 1 "register_operand" "=u")
15328 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15329 "TARGET_USE_FANCY_MATH_387
15330 && flag_unsafe_math_optimizations"
15332 [(set_attr "type" "fpspc")
15333 (set_attr "mode" "XF")])
15336 [(set (match_operand:XF 0 "register_operand" "")
15337 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
15338 UNSPEC_SINCOS_COS))
15339 (set (match_operand:XF 1 "register_operand" "")
15340 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15341 "find_regno_note (insn, REG_UNUSED, REGNO (operands[0]))
15342 && !reload_completed && !reload_in_progress"
15343 [(set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_SIN))]
15347 [(set (match_operand:XF 0 "register_operand" "")
15348 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
15349 UNSPEC_SINCOS_COS))
15350 (set (match_operand:XF 1 "register_operand" "")
15351 (unspec:XF [(match_dup 2)] UNSPEC_SINCOS_SIN))]
15352 "find_regno_note (insn, REG_UNUSED, REGNO (operands[1]))
15353 && !reload_completed && !reload_in_progress"
15354 [(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_COS))]
15357 (define_insn "*tandf3_1"
15358 [(set (match_operand:DF 0 "register_operand" "=f")
15359 (unspec:DF [(match_operand:DF 2 "register_operand" "0")]
15361 (set (match_operand:DF 1 "register_operand" "=u")
15362 (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))]
15363 "TARGET_USE_FANCY_MATH_387
15364 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15365 && flag_unsafe_math_optimizations"
15367 [(set_attr "type" "fpspc")
15368 (set_attr "mode" "DF")])
15370 ;; optimize sequence: fptan
15373 ;; into fptan insn.
15376 [(parallel[(set (match_operand:DF 0 "register_operand" "")
15377 (unspec:DF [(match_operand:DF 2 "register_operand" "")]
15379 (set (match_operand:DF 1 "register_operand" "")
15380 (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))])
15382 (match_operand:DF 3 "immediate_operand" ""))]
15383 "standard_80387_constant_p (operands[3]) == 2"
15384 [(parallel[(set (match_dup 0) (unspec:DF [(match_dup 2)] UNSPEC_TAN_ONE))
15385 (set (match_dup 1) (unspec:DF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15388 (define_expand "tandf2"
15389 [(parallel [(set (match_dup 2)
15390 (unspec:DF [(match_operand:DF 1 "register_operand" "")]
15392 (set (match_operand:DF 0 "register_operand" "")
15393 (unspec:DF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15394 "TARGET_USE_FANCY_MATH_387
15395 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15396 && flag_unsafe_math_optimizations"
15398 operands[2] = gen_reg_rtx (DFmode);
15401 (define_insn "*tansf3_1"
15402 [(set (match_operand:SF 0 "register_operand" "=f")
15403 (unspec:SF [(match_operand:SF 2 "register_operand" "0")]
15405 (set (match_operand:SF 1 "register_operand" "=u")
15406 (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))]
15407 "TARGET_USE_FANCY_MATH_387
15408 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15409 && flag_unsafe_math_optimizations"
15411 [(set_attr "type" "fpspc")
15412 (set_attr "mode" "SF")])
15414 ;; optimize sequence: fptan
15417 ;; into fptan insn.
15420 [(parallel[(set (match_operand:SF 0 "register_operand" "")
15421 (unspec:SF [(match_operand:SF 2 "register_operand" "")]
15423 (set (match_operand:SF 1 "register_operand" "")
15424 (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))])
15426 (match_operand:SF 3 "immediate_operand" ""))]
15427 "standard_80387_constant_p (operands[3]) == 2"
15428 [(parallel[(set (match_dup 0) (unspec:SF [(match_dup 2)] UNSPEC_TAN_ONE))
15429 (set (match_dup 1) (unspec:SF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15432 (define_expand "tansf2"
15433 [(parallel [(set (match_dup 2)
15434 (unspec:SF [(match_operand:SF 1 "register_operand" "")]
15436 (set (match_operand:SF 0 "register_operand" "")
15437 (unspec:SF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15438 "TARGET_USE_FANCY_MATH_387
15439 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15440 && flag_unsafe_math_optimizations"
15442 operands[2] = gen_reg_rtx (SFmode);
15445 (define_insn "*tanxf3_1"
15446 [(set (match_operand:XF 0 "register_operand" "=f")
15447 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15449 (set (match_operand:XF 1 "register_operand" "=u")
15450 (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))]
15451 "TARGET_USE_FANCY_MATH_387
15452 && flag_unsafe_math_optimizations"
15454 [(set_attr "type" "fpspc")
15455 (set_attr "mode" "XF")])
15457 ;; optimize sequence: fptan
15460 ;; into fptan insn.
15463 [(parallel[(set (match_operand:XF 0 "register_operand" "")
15464 (unspec:XF [(match_operand:XF 2 "register_operand" "")]
15466 (set (match_operand:XF 1 "register_operand" "")
15467 (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))])
15469 (match_operand:XF 3 "immediate_operand" ""))]
15470 "standard_80387_constant_p (operands[3]) == 2"
15471 [(parallel[(set (match_dup 0) (unspec:XF [(match_dup 2)] UNSPEC_TAN_ONE))
15472 (set (match_dup 1) (unspec:XF [(match_dup 2)] UNSPEC_TAN_TAN))])]
15475 (define_expand "tanxf2"
15476 [(parallel [(set (match_dup 2)
15477 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
15479 (set (match_operand:XF 0 "register_operand" "")
15480 (unspec:XF [(match_dup 1)] UNSPEC_TAN_TAN))])]
15481 "TARGET_USE_FANCY_MATH_387
15482 && flag_unsafe_math_optimizations"
15484 operands[2] = gen_reg_rtx (XFmode);
15487 (define_insn "atan2df3_1"
15488 [(set (match_operand:DF 0 "register_operand" "=f")
15489 (unspec:DF [(match_operand:DF 2 "register_operand" "0")
15490 (match_operand:DF 1 "register_operand" "u")]
15492 (clobber (match_scratch:DF 3 "=1"))]
15493 "TARGET_USE_FANCY_MATH_387
15494 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15495 && flag_unsafe_math_optimizations"
15497 [(set_attr "type" "fpspc")
15498 (set_attr "mode" "DF")])
15500 (define_expand "atan2df3"
15501 [(use (match_operand:DF 0 "register_operand" ""))
15502 (use (match_operand:DF 2 "register_operand" ""))
15503 (use (match_operand:DF 1 "register_operand" ""))]
15504 "TARGET_USE_FANCY_MATH_387
15505 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15506 && flag_unsafe_math_optimizations"
15508 rtx copy = gen_reg_rtx (DFmode);
15509 emit_move_insn (copy, operands[1]);
15510 emit_insn (gen_atan2df3_1 (operands[0], copy, operands[2]));
15514 (define_expand "atandf2"
15515 [(parallel [(set (match_operand:DF 0 "register_operand" "")
15516 (unspec:DF [(match_dup 2)
15517 (match_operand:DF 1 "register_operand" "")]
15519 (clobber (match_scratch:DF 3 ""))])]
15520 "TARGET_USE_FANCY_MATH_387
15521 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15522 && flag_unsafe_math_optimizations"
15524 operands[2] = gen_reg_rtx (DFmode);
15525 emit_move_insn (operands[2], CONST1_RTX (DFmode)); /* fld1 */
15528 (define_insn "atan2sf3_1"
15529 [(set (match_operand:SF 0 "register_operand" "=f")
15530 (unspec:SF [(match_operand:SF 2 "register_operand" "0")
15531 (match_operand:SF 1 "register_operand" "u")]
15533 (clobber (match_scratch:SF 3 "=1"))]
15534 "TARGET_USE_FANCY_MATH_387
15535 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15536 && flag_unsafe_math_optimizations"
15538 [(set_attr "type" "fpspc")
15539 (set_attr "mode" "SF")])
15541 (define_expand "atan2sf3"
15542 [(use (match_operand:SF 0 "register_operand" ""))
15543 (use (match_operand:SF 2 "register_operand" ""))
15544 (use (match_operand:SF 1 "register_operand" ""))]
15545 "TARGET_USE_FANCY_MATH_387
15546 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15547 && flag_unsafe_math_optimizations"
15549 rtx copy = gen_reg_rtx (SFmode);
15550 emit_move_insn (copy, operands[1]);
15551 emit_insn (gen_atan2sf3_1 (operands[0], copy, operands[2]));
15555 (define_expand "atansf2"
15556 [(parallel [(set (match_operand:SF 0 "register_operand" "")
15557 (unspec:SF [(match_dup 2)
15558 (match_operand:SF 1 "register_operand" "")]
15560 (clobber (match_scratch:SF 3 ""))])]
15561 "TARGET_USE_FANCY_MATH_387
15562 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15563 && flag_unsafe_math_optimizations"
15565 operands[2] = gen_reg_rtx (SFmode);
15566 emit_move_insn (operands[2], CONST1_RTX (SFmode)); /* fld1 */
15569 (define_insn "atan2xf3_1"
15570 [(set (match_operand:XF 0 "register_operand" "=f")
15571 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15572 (match_operand:XF 1 "register_operand" "u")]
15574 (clobber (match_scratch:XF 3 "=1"))]
15575 "TARGET_USE_FANCY_MATH_387
15576 && flag_unsafe_math_optimizations"
15578 [(set_attr "type" "fpspc")
15579 (set_attr "mode" "XF")])
15581 (define_expand "atan2xf3"
15582 [(use (match_operand:XF 0 "register_operand" ""))
15583 (use (match_operand:XF 2 "register_operand" ""))
15584 (use (match_operand:XF 1 "register_operand" ""))]
15585 "TARGET_USE_FANCY_MATH_387
15586 && flag_unsafe_math_optimizations"
15588 rtx copy = gen_reg_rtx (XFmode);
15589 emit_move_insn (copy, operands[1]);
15590 emit_insn (gen_atan2xf3_1 (operands[0], copy, operands[2]));
15594 (define_expand "atanxf2"
15595 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15596 (unspec:XF [(match_dup 2)
15597 (match_operand:XF 1 "register_operand" "")]
15599 (clobber (match_scratch:XF 3 ""))])]
15600 "TARGET_USE_FANCY_MATH_387
15601 && flag_unsafe_math_optimizations"
15603 operands[2] = gen_reg_rtx (XFmode);
15604 emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
15607 (define_expand "asindf2"
15608 [(set (match_dup 2)
15609 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15610 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15611 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15612 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15613 (parallel [(set (match_dup 7)
15614 (unspec:XF [(match_dup 6) (match_dup 2)]
15616 (clobber (match_scratch:XF 8 ""))])
15617 (set (match_operand:DF 0 "register_operand" "")
15618 (float_truncate:DF (match_dup 7)))]
15619 "TARGET_USE_FANCY_MATH_387
15620 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15621 && flag_unsafe_math_optimizations"
15625 for (i=2; i<8; i++)
15626 operands[i] = gen_reg_rtx (XFmode);
15628 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15631 (define_expand "asinsf2"
15632 [(set (match_dup 2)
15633 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15634 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15635 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15636 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15637 (parallel [(set (match_dup 7)
15638 (unspec:XF [(match_dup 6) (match_dup 2)]
15640 (clobber (match_scratch:XF 8 ""))])
15641 (set (match_operand:SF 0 "register_operand" "")
15642 (float_truncate:SF (match_dup 7)))]
15643 "TARGET_USE_FANCY_MATH_387
15644 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15645 && flag_unsafe_math_optimizations"
15649 for (i=2; i<8; i++)
15650 operands[i] = gen_reg_rtx (XFmode);
15652 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15655 (define_expand "asinxf2"
15656 [(set (match_dup 2)
15657 (mult:XF (match_operand:XF 1 "register_operand" "")
15659 (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
15660 (set (match_dup 5) (sqrt:XF (match_dup 4)))
15661 (parallel [(set (match_operand:XF 0 "register_operand" "")
15662 (unspec:XF [(match_dup 5) (match_dup 1)]
15664 (clobber (match_scratch:XF 6 ""))])]
15665 "TARGET_USE_FANCY_MATH_387
15666 && flag_unsafe_math_optimizations"
15670 for (i=2; i<6; i++)
15671 operands[i] = gen_reg_rtx (XFmode);
15673 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15676 (define_expand "acosdf2"
15677 [(set (match_dup 2)
15678 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15679 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15680 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15681 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15682 (parallel [(set (match_dup 7)
15683 (unspec:XF [(match_dup 2) (match_dup 6)]
15685 (clobber (match_scratch:XF 8 ""))])
15686 (set (match_operand:DF 0 "register_operand" "")
15687 (float_truncate:DF (match_dup 7)))]
15688 "TARGET_USE_FANCY_MATH_387
15689 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15690 && flag_unsafe_math_optimizations"
15694 for (i=2; i<8; i++)
15695 operands[i] = gen_reg_rtx (XFmode);
15697 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15700 (define_expand "acossf2"
15701 [(set (match_dup 2)
15702 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15703 (set (match_dup 3) (mult:XF (match_dup 2) (match_dup 2)))
15704 (set (match_dup 5) (minus:XF (match_dup 4) (match_dup 3)))
15705 (set (match_dup 6) (sqrt:XF (match_dup 5)))
15706 (parallel [(set (match_dup 7)
15707 (unspec:XF [(match_dup 2) (match_dup 6)]
15709 (clobber (match_scratch:XF 8 ""))])
15710 (set (match_operand:SF 0 "register_operand" "")
15711 (float_truncate:SF (match_dup 7)))]
15712 "TARGET_USE_FANCY_MATH_387
15713 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15714 && flag_unsafe_math_optimizations"
15718 for (i=2; i<8; i++)
15719 operands[i] = gen_reg_rtx (XFmode);
15721 emit_move_insn (operands[4], CONST1_RTX (XFmode)); /* fld1 */
15724 (define_expand "acosxf2"
15725 [(set (match_dup 2)
15726 (mult:XF (match_operand:XF 1 "register_operand" "")
15728 (set (match_dup 4) (minus:XF (match_dup 3) (match_dup 2)))
15729 (set (match_dup 5) (sqrt:XF (match_dup 4)))
15730 (parallel [(set (match_operand:XF 0 "register_operand" "")
15731 (unspec:XF [(match_dup 1) (match_dup 5)]
15733 (clobber (match_scratch:XF 6 ""))])]
15734 "TARGET_USE_FANCY_MATH_387
15735 && flag_unsafe_math_optimizations"
15739 for (i=2; i<6; i++)
15740 operands[i] = gen_reg_rtx (XFmode);
15742 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15745 (define_insn "fyl2x_xf3"
15746 [(set (match_operand:XF 0 "register_operand" "=f")
15747 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15748 (match_operand:XF 1 "register_operand" "u")]
15750 (clobber (match_scratch:XF 3 "=1"))]
15751 "TARGET_USE_FANCY_MATH_387
15752 && flag_unsafe_math_optimizations"
15754 [(set_attr "type" "fpspc")
15755 (set_attr "mode" "XF")])
15757 (define_expand "logsf2"
15758 [(set (match_dup 2)
15759 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15760 (parallel [(set (match_dup 4)
15761 (unspec:XF [(match_dup 2)
15762 (match_dup 3)] UNSPEC_FYL2X))
15763 (clobber (match_scratch:XF 5 ""))])
15764 (set (match_operand:SF 0 "register_operand" "")
15765 (float_truncate:SF (match_dup 4)))]
15766 "TARGET_USE_FANCY_MATH_387
15767 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15768 && flag_unsafe_math_optimizations"
15772 operands[2] = gen_reg_rtx (XFmode);
15773 operands[3] = gen_reg_rtx (XFmode);
15774 operands[4] = gen_reg_rtx (XFmode);
15776 temp = standard_80387_constant_rtx (4); /* fldln2 */
15777 emit_move_insn (operands[3], temp);
15780 (define_expand "logdf2"
15781 [(set (match_dup 2)
15782 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15783 (parallel [(set (match_dup 4)
15784 (unspec:XF [(match_dup 2)
15785 (match_dup 3)] UNSPEC_FYL2X))
15786 (clobber (match_scratch:XF 5 ""))])
15787 (set (match_operand:DF 0 "register_operand" "")
15788 (float_truncate:DF (match_dup 4)))]
15789 "TARGET_USE_FANCY_MATH_387
15790 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15791 && flag_unsafe_math_optimizations"
15795 operands[2] = gen_reg_rtx (XFmode);
15796 operands[3] = gen_reg_rtx (XFmode);
15797 operands[4] = gen_reg_rtx (XFmode);
15799 temp = standard_80387_constant_rtx (4); /* fldln2 */
15800 emit_move_insn (operands[3], temp);
15803 (define_expand "logxf2"
15804 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15805 (unspec:XF [(match_operand:XF 1 "register_operand" "")
15806 (match_dup 2)] UNSPEC_FYL2X))
15807 (clobber (match_scratch:XF 3 ""))])]
15808 "TARGET_USE_FANCY_MATH_387
15809 && flag_unsafe_math_optimizations"
15813 operands[2] = gen_reg_rtx (XFmode);
15814 temp = standard_80387_constant_rtx (4); /* fldln2 */
15815 emit_move_insn (operands[2], temp);
15818 (define_expand "log10sf2"
15819 [(set (match_dup 2)
15820 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15821 (parallel [(set (match_dup 4)
15822 (unspec:XF [(match_dup 2)
15823 (match_dup 3)] UNSPEC_FYL2X))
15824 (clobber (match_scratch:XF 5 ""))])
15825 (set (match_operand:SF 0 "register_operand" "")
15826 (float_truncate:SF (match_dup 4)))]
15827 "TARGET_USE_FANCY_MATH_387
15828 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15829 && flag_unsafe_math_optimizations"
15833 operands[2] = gen_reg_rtx (XFmode);
15834 operands[3] = gen_reg_rtx (XFmode);
15835 operands[4] = gen_reg_rtx (XFmode);
15837 temp = standard_80387_constant_rtx (3); /* fldlg2 */
15838 emit_move_insn (operands[3], temp);
15841 (define_expand "log10df2"
15842 [(set (match_dup 2)
15843 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15844 (parallel [(set (match_dup 4)
15845 (unspec:XF [(match_dup 2)
15846 (match_dup 3)] UNSPEC_FYL2X))
15847 (clobber (match_scratch:XF 5 ""))])
15848 (set (match_operand:DF 0 "register_operand" "")
15849 (float_truncate:DF (match_dup 4)))]
15850 "TARGET_USE_FANCY_MATH_387
15851 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15852 && flag_unsafe_math_optimizations"
15856 operands[2] = gen_reg_rtx (XFmode);
15857 operands[3] = gen_reg_rtx (XFmode);
15858 operands[4] = gen_reg_rtx (XFmode);
15860 temp = standard_80387_constant_rtx (3); /* fldlg2 */
15861 emit_move_insn (operands[3], temp);
15864 (define_expand "log10xf2"
15865 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15866 (unspec:XF [(match_operand:XF 1 "register_operand" "")
15867 (match_dup 2)] UNSPEC_FYL2X))
15868 (clobber (match_scratch:XF 3 ""))])]
15869 "TARGET_USE_FANCY_MATH_387
15870 && flag_unsafe_math_optimizations"
15874 operands[2] = gen_reg_rtx (XFmode);
15875 temp = standard_80387_constant_rtx (3); /* fldlg2 */
15876 emit_move_insn (operands[2], temp);
15879 (define_expand "log2sf2"
15880 [(set (match_dup 2)
15881 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
15882 (parallel [(set (match_dup 4)
15883 (unspec:XF [(match_dup 2)
15884 (match_dup 3)] UNSPEC_FYL2X))
15885 (clobber (match_scratch:XF 5 ""))])
15886 (set (match_operand:SF 0 "register_operand" "")
15887 (float_truncate:SF (match_dup 4)))]
15888 "TARGET_USE_FANCY_MATH_387
15889 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15890 && flag_unsafe_math_optimizations"
15892 operands[2] = gen_reg_rtx (XFmode);
15893 operands[3] = gen_reg_rtx (XFmode);
15894 operands[4] = gen_reg_rtx (XFmode);
15896 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15899 (define_expand "log2df2"
15900 [(set (match_dup 2)
15901 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
15902 (parallel [(set (match_dup 4)
15903 (unspec:XF [(match_dup 2)
15904 (match_dup 3)] UNSPEC_FYL2X))
15905 (clobber (match_scratch:XF 5 ""))])
15906 (set (match_operand:DF 0 "register_operand" "")
15907 (float_truncate:DF (match_dup 4)))]
15908 "TARGET_USE_FANCY_MATH_387
15909 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15910 && flag_unsafe_math_optimizations"
15912 operands[2] = gen_reg_rtx (XFmode);
15913 operands[3] = gen_reg_rtx (XFmode);
15914 operands[4] = gen_reg_rtx (XFmode);
15916 emit_move_insn (operands[3], CONST1_RTX (XFmode)); /* fld1 */
15919 (define_expand "log2xf2"
15920 [(parallel [(set (match_operand:XF 0 "register_operand" "")
15921 (unspec:XF [(match_operand:XF 1 "register_operand" "")
15922 (match_dup 2)] UNSPEC_FYL2X))
15923 (clobber (match_scratch:XF 3 ""))])]
15924 "TARGET_USE_FANCY_MATH_387
15925 && flag_unsafe_math_optimizations"
15927 operands[2] = gen_reg_rtx (XFmode);
15928 emit_move_insn (operands[2], CONST1_RTX (XFmode)); /* fld1 */
15931 (define_insn "fyl2xp1_xf3"
15932 [(set (match_operand:XF 0 "register_operand" "=f")
15933 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
15934 (match_operand:XF 1 "register_operand" "u")]
15936 (clobber (match_scratch:XF 3 "=1"))]
15937 "TARGET_USE_FANCY_MATH_387
15938 && flag_unsafe_math_optimizations"
15940 [(set_attr "type" "fpspc")
15941 (set_attr "mode" "XF")])
15943 (define_expand "log1psf2"
15944 [(use (match_operand:SF 0 "register_operand" ""))
15945 (use (match_operand:SF 1 "register_operand" ""))]
15946 "TARGET_USE_FANCY_MATH_387
15947 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
15948 && flag_unsafe_math_optimizations"
15950 rtx op0 = gen_reg_rtx (XFmode);
15951 rtx op1 = gen_reg_rtx (XFmode);
15953 emit_insn (gen_extendsfxf2 (op1, operands[1]));
15954 ix86_emit_i387_log1p (op0, op1);
15955 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
15959 (define_expand "log1pdf2"
15960 [(use (match_operand:DF 0 "register_operand" ""))
15961 (use (match_operand:DF 1 "register_operand" ""))]
15962 "TARGET_USE_FANCY_MATH_387
15963 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
15964 && flag_unsafe_math_optimizations"
15966 rtx op0 = gen_reg_rtx (XFmode);
15967 rtx op1 = gen_reg_rtx (XFmode);
15969 emit_insn (gen_extenddfxf2 (op1, operands[1]));
15970 ix86_emit_i387_log1p (op0, op1);
15971 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
15975 (define_expand "log1pxf2"
15976 [(use (match_operand:XF 0 "register_operand" ""))
15977 (use (match_operand:XF 1 "register_operand" ""))]
15978 "TARGET_USE_FANCY_MATH_387
15979 && flag_unsafe_math_optimizations"
15981 ix86_emit_i387_log1p (operands[0], operands[1]);
15985 (define_insn "*fxtractxf3"
15986 [(set (match_operand:XF 0 "register_operand" "=f")
15987 (unspec:XF [(match_operand:XF 2 "register_operand" "0")]
15988 UNSPEC_XTRACT_FRACT))
15989 (set (match_operand:XF 1 "register_operand" "=u")
15990 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))]
15991 "TARGET_USE_FANCY_MATH_387
15992 && flag_unsafe_math_optimizations"
15994 [(set_attr "type" "fpspc")
15995 (set_attr "mode" "XF")])
15997 (define_expand "logbsf2"
15998 [(set (match_dup 2)
15999 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16000 (parallel [(set (match_dup 3)
16001 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_FRACT))
16003 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))])
16004 (set (match_operand:SF 0 "register_operand" "")
16005 (float_truncate:SF (match_dup 4)))]
16006 "TARGET_USE_FANCY_MATH_387
16007 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16008 && flag_unsafe_math_optimizations"
16010 operands[2] = gen_reg_rtx (XFmode);
16011 operands[3] = gen_reg_rtx (XFmode);
16012 operands[4] = gen_reg_rtx (XFmode);
16015 (define_expand "logbdf2"
16016 [(set (match_dup 2)
16017 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16018 (parallel [(set (match_dup 3)
16019 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_FRACT))
16021 (unspec:XF [(match_dup 2)] UNSPEC_XTRACT_EXP))])
16022 (set (match_operand:DF 0 "register_operand" "")
16023 (float_truncate:DF (match_dup 4)))]
16024 "TARGET_USE_FANCY_MATH_387
16025 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16026 && flag_unsafe_math_optimizations"
16028 operands[2] = gen_reg_rtx (XFmode);
16029 operands[3] = gen_reg_rtx (XFmode);
16030 operands[4] = gen_reg_rtx (XFmode);
16033 (define_expand "logbxf2"
16034 [(parallel [(set (match_dup 2)
16035 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
16036 UNSPEC_XTRACT_FRACT))
16037 (set (match_operand:XF 0 "register_operand" "")
16038 (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])]
16039 "TARGET_USE_FANCY_MATH_387
16040 && flag_unsafe_math_optimizations"
16042 operands[2] = gen_reg_rtx (XFmode);
16045 (define_expand "ilogbsi2"
16046 [(parallel [(set (match_dup 2)
16047 (unspec:XF [(match_operand:XF 1 "register_operand" "")]
16048 UNSPEC_XTRACT_FRACT))
16049 (set (match_operand:XF 3 "register_operand" "")
16050 (unspec:XF [(match_dup 1)] UNSPEC_XTRACT_EXP))])
16051 (parallel [(set (match_operand:SI 0 "register_operand" "")
16052 (fix:SI (match_dup 3)))
16053 (clobber (reg:CC FLAGS_REG))])]
16054 "TARGET_USE_FANCY_MATH_387
16055 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16056 && flag_unsafe_math_optimizations"
16058 operands[2] = gen_reg_rtx (XFmode);
16059 operands[3] = gen_reg_rtx (XFmode);
16062 (define_insn "*f2xm1xf2"
16063 [(set (match_operand:XF 0 "register_operand" "=f")
16064 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16066 "TARGET_USE_FANCY_MATH_387
16067 && flag_unsafe_math_optimizations"
16069 [(set_attr "type" "fpspc")
16070 (set_attr "mode" "XF")])
16072 (define_insn "*fscalexf4"
16073 [(set (match_operand:XF 0 "register_operand" "=f")
16074 (unspec:XF [(match_operand:XF 2 "register_operand" "0")
16075 (match_operand:XF 3 "register_operand" "1")]
16076 UNSPEC_FSCALE_FRACT))
16077 (set (match_operand:XF 1 "register_operand" "=u")
16078 (unspec:XF [(match_dup 2) (match_dup 3)]
16079 UNSPEC_FSCALE_EXP))]
16080 "TARGET_USE_FANCY_MATH_387
16081 && flag_unsafe_math_optimizations"
16083 [(set_attr "type" "fpspc")
16084 (set_attr "mode" "XF")])
16086 (define_expand "expsf2"
16087 [(set (match_dup 2)
16088 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16089 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16090 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16091 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16092 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16093 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
16094 (parallel [(set (match_dup 10)
16095 (unspec:XF [(match_dup 9) (match_dup 5)]
16096 UNSPEC_FSCALE_FRACT))
16097 (set (match_dup 11)
16098 (unspec:XF [(match_dup 9) (match_dup 5)]
16099 UNSPEC_FSCALE_EXP))])
16100 (set (match_operand:SF 0 "register_operand" "")
16101 (float_truncate:SF (match_dup 10)))]
16102 "TARGET_USE_FANCY_MATH_387
16103 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16104 && flag_unsafe_math_optimizations"
16109 for (i=2; i<12; i++)
16110 operands[i] = gen_reg_rtx (XFmode);
16111 temp = standard_80387_constant_rtx (5); /* fldl2e */
16112 emit_move_insn (operands[3], temp);
16113 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
16116 (define_expand "expdf2"
16117 [(set (match_dup 2)
16118 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16119 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16120 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16121 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16122 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16123 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
16124 (parallel [(set (match_dup 10)
16125 (unspec:XF [(match_dup 9) (match_dup 5)]
16126 UNSPEC_FSCALE_FRACT))
16127 (set (match_dup 11)
16128 (unspec:XF [(match_dup 9) (match_dup 5)]
16129 UNSPEC_FSCALE_EXP))])
16130 (set (match_operand:DF 0 "register_operand" "")
16131 (float_truncate:DF (match_dup 10)))]
16132 "TARGET_USE_FANCY_MATH_387
16133 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16134 && flag_unsafe_math_optimizations"
16139 for (i=2; i<12; i++)
16140 operands[i] = gen_reg_rtx (XFmode);
16141 temp = standard_80387_constant_rtx (5); /* fldl2e */
16142 emit_move_insn (operands[3], temp);
16143 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
16146 (define_expand "expxf2"
16147 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
16149 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
16150 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
16151 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
16152 (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
16153 (parallel [(set (match_operand:XF 0 "register_operand" "")
16154 (unspec:XF [(match_dup 8) (match_dup 4)]
16155 UNSPEC_FSCALE_FRACT))
16157 (unspec:XF [(match_dup 8) (match_dup 4)]
16158 UNSPEC_FSCALE_EXP))])]
16159 "TARGET_USE_FANCY_MATH_387
16160 && flag_unsafe_math_optimizations"
16165 for (i=2; i<10; i++)
16166 operands[i] = gen_reg_rtx (XFmode);
16167 temp = standard_80387_constant_rtx (5); /* fldl2e */
16168 emit_move_insn (operands[2], temp);
16169 emit_move_insn (operands[7], CONST1_RTX (XFmode)); /* fld1 */
16172 (define_expand "exp10sf2"
16173 [(set (match_dup 2)
16174 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16175 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16176 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16177 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16178 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16179 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
16180 (parallel [(set (match_dup 10)
16181 (unspec:XF [(match_dup 9) (match_dup 5)]
16182 UNSPEC_FSCALE_FRACT))
16183 (set (match_dup 11)
16184 (unspec:XF [(match_dup 9) (match_dup 5)]
16185 UNSPEC_FSCALE_EXP))])
16186 (set (match_operand:SF 0 "register_operand" "")
16187 (float_truncate:SF (match_dup 10)))]
16188 "TARGET_USE_FANCY_MATH_387
16189 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16190 && flag_unsafe_math_optimizations"
16195 for (i=2; i<12; i++)
16196 operands[i] = gen_reg_rtx (XFmode);
16197 temp = standard_80387_constant_rtx (6); /* fldl2t */
16198 emit_move_insn (operands[3], temp);
16199 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
16202 (define_expand "exp10df2"
16203 [(set (match_dup 2)
16204 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16205 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16206 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16207 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16208 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16209 (set (match_dup 9) (plus:XF (match_dup 7) (match_dup 8)))
16210 (parallel [(set (match_dup 10)
16211 (unspec:XF [(match_dup 9) (match_dup 5)]
16212 UNSPEC_FSCALE_FRACT))
16213 (set (match_dup 11)
16214 (unspec:XF [(match_dup 9) (match_dup 5)]
16215 UNSPEC_FSCALE_EXP))])
16216 (set (match_operand:DF 0 "register_operand" "")
16217 (float_truncate:DF (match_dup 10)))]
16218 "TARGET_USE_FANCY_MATH_387
16219 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16220 && flag_unsafe_math_optimizations"
16225 for (i=2; i<12; i++)
16226 operands[i] = gen_reg_rtx (XFmode);
16227 temp = standard_80387_constant_rtx (6); /* fldl2t */
16228 emit_move_insn (operands[3], temp);
16229 emit_move_insn (operands[8], CONST1_RTX (XFmode)); /* fld1 */
16232 (define_expand "exp10xf2"
16233 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
16235 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
16236 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
16237 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
16238 (set (match_dup 8) (plus:XF (match_dup 6) (match_dup 7)))
16239 (parallel [(set (match_operand:XF 0 "register_operand" "")
16240 (unspec:XF [(match_dup 8) (match_dup 4)]
16241 UNSPEC_FSCALE_FRACT))
16243 (unspec:XF [(match_dup 8) (match_dup 4)]
16244 UNSPEC_FSCALE_EXP))])]
16245 "TARGET_USE_FANCY_MATH_387
16246 && flag_unsafe_math_optimizations"
16251 for (i=2; i<10; i++)
16252 operands[i] = gen_reg_rtx (XFmode);
16253 temp = standard_80387_constant_rtx (6); /* fldl2t */
16254 emit_move_insn (operands[2], temp);
16255 emit_move_insn (operands[7], CONST1_RTX (XFmode)); /* fld1 */
16258 (define_expand "exp2sf2"
16259 [(set (match_dup 2)
16260 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16261 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
16262 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
16263 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
16264 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
16265 (parallel [(set (match_dup 8)
16266 (unspec:XF [(match_dup 7) (match_dup 3)]
16267 UNSPEC_FSCALE_FRACT))
16269 (unspec:XF [(match_dup 7) (match_dup 3)]
16270 UNSPEC_FSCALE_EXP))])
16271 (set (match_operand:SF 0 "register_operand" "")
16272 (float_truncate:SF (match_dup 8)))]
16273 "TARGET_USE_FANCY_MATH_387
16274 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16275 && flag_unsafe_math_optimizations"
16279 for (i=2; i<10; i++)
16280 operands[i] = gen_reg_rtx (XFmode);
16281 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */
16284 (define_expand "exp2df2"
16285 [(set (match_dup 2)
16286 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16287 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
16288 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
16289 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
16290 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
16291 (parallel [(set (match_dup 8)
16292 (unspec:XF [(match_dup 7) (match_dup 3)]
16293 UNSPEC_FSCALE_FRACT))
16295 (unspec:XF [(match_dup 7) (match_dup 3)]
16296 UNSPEC_FSCALE_EXP))])
16297 (set (match_operand:DF 0 "register_operand" "")
16298 (float_truncate:DF (match_dup 8)))]
16299 "TARGET_USE_FANCY_MATH_387
16300 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16301 && flag_unsafe_math_optimizations"
16305 for (i=2; i<10; i++)
16306 operands[i] = gen_reg_rtx (XFmode);
16307 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */
16310 (define_expand "exp2xf2"
16311 [(set (match_dup 2) (match_operand:XF 1 "register_operand" ""))
16312 (set (match_dup 3) (unspec:XF [(match_dup 2)] UNSPEC_FRNDINT))
16313 (set (match_dup 4) (minus:XF (match_dup 2) (match_dup 3)))
16314 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_F2XM1))
16315 (set (match_dup 7) (plus:XF (match_dup 5) (match_dup 6)))
16316 (parallel [(set (match_operand:XF 0 "register_operand" "")
16317 (unspec:XF [(match_dup 7) (match_dup 3)]
16318 UNSPEC_FSCALE_FRACT))
16320 (unspec:XF [(match_dup 7) (match_dup 3)]
16321 UNSPEC_FSCALE_EXP))])]
16322 "TARGET_USE_FANCY_MATH_387
16323 && flag_unsafe_math_optimizations"
16327 for (i=2; i<9; i++)
16328 operands[i] = gen_reg_rtx (XFmode);
16329 emit_move_insn (operands[6], CONST1_RTX (XFmode)); /* fld1 */
16332 (define_expand "expm1df2"
16333 [(set (match_dup 2)
16334 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16335 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16336 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16337 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16338 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16339 (parallel [(set (match_dup 8)
16340 (unspec:XF [(match_dup 7) (match_dup 5)]
16341 UNSPEC_FSCALE_FRACT))
16343 (unspec:XF [(match_dup 7) (match_dup 5)]
16344 UNSPEC_FSCALE_EXP))])
16345 (parallel [(set (match_dup 11)
16346 (unspec:XF [(match_dup 10) (match_dup 9)]
16347 UNSPEC_FSCALE_FRACT))
16348 (set (match_dup 12)
16349 (unspec:XF [(match_dup 10) (match_dup 9)]
16350 UNSPEC_FSCALE_EXP))])
16351 (set (match_dup 13) (minus:XF (match_dup 11) (match_dup 10)))
16352 (set (match_dup 14) (plus:XF (match_dup 13) (match_dup 8)))
16353 (set (match_operand:DF 0 "register_operand" "")
16354 (float_truncate:DF (match_dup 14)))]
16355 "TARGET_USE_FANCY_MATH_387
16356 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16357 && flag_unsafe_math_optimizations"
16362 for (i=2; i<15; i++)
16363 operands[i] = gen_reg_rtx (XFmode);
16364 temp = standard_80387_constant_rtx (5); /* fldl2e */
16365 emit_move_insn (operands[3], temp);
16366 emit_move_insn (operands[10], CONST1_RTX (XFmode)); /* fld1 */
16369 (define_expand "expm1sf2"
16370 [(set (match_dup 2)
16371 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16372 (set (match_dup 4) (mult:XF (match_dup 2) (match_dup 3)))
16373 (set (match_dup 5) (unspec:XF [(match_dup 4)] UNSPEC_FRNDINT))
16374 (set (match_dup 6) (minus:XF (match_dup 4) (match_dup 5)))
16375 (set (match_dup 7) (unspec:XF [(match_dup 6)] UNSPEC_F2XM1))
16376 (parallel [(set (match_dup 8)
16377 (unspec:XF [(match_dup 7) (match_dup 5)]
16378 UNSPEC_FSCALE_FRACT))
16380 (unspec:XF [(match_dup 7) (match_dup 5)]
16381 UNSPEC_FSCALE_EXP))])
16382 (parallel [(set (match_dup 11)
16383 (unspec:XF [(match_dup 10) (match_dup 9)]
16384 UNSPEC_FSCALE_FRACT))
16385 (set (match_dup 12)
16386 (unspec:XF [(match_dup 10) (match_dup 9)]
16387 UNSPEC_FSCALE_EXP))])
16388 (set (match_dup 13) (minus:XF (match_dup 11) (match_dup 10)))
16389 (set (match_dup 14) (plus:XF (match_dup 13) (match_dup 8)))
16390 (set (match_operand:SF 0 "register_operand" "")
16391 (float_truncate:SF (match_dup 14)))]
16392 "TARGET_USE_FANCY_MATH_387
16393 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16394 && flag_unsafe_math_optimizations"
16399 for (i=2; i<15; i++)
16400 operands[i] = gen_reg_rtx (XFmode);
16401 temp = standard_80387_constant_rtx (5); /* fldl2e */
16402 emit_move_insn (operands[3], temp);
16403 emit_move_insn (operands[10], CONST1_RTX (XFmode)); /* fld1 */
16406 (define_expand "expm1xf2"
16407 [(set (match_dup 3) (mult:XF (match_operand:XF 1 "register_operand" "")
16409 (set (match_dup 4) (unspec:XF [(match_dup 3)] UNSPEC_FRNDINT))
16410 (set (match_dup 5) (minus:XF (match_dup 3) (match_dup 4)))
16411 (set (match_dup 6) (unspec:XF [(match_dup 5)] UNSPEC_F2XM1))
16412 (parallel [(set (match_dup 7)
16413 (unspec:XF [(match_dup 6) (match_dup 4)]
16414 UNSPEC_FSCALE_FRACT))
16416 (unspec:XF [(match_dup 6) (match_dup 4)]
16417 UNSPEC_FSCALE_EXP))])
16418 (parallel [(set (match_dup 10)
16419 (unspec:XF [(match_dup 9) (match_dup 8)]
16420 UNSPEC_FSCALE_FRACT))
16421 (set (match_dup 11)
16422 (unspec:XF [(match_dup 9) (match_dup 8)]
16423 UNSPEC_FSCALE_EXP))])
16424 (set (match_dup 12) (minus:XF (match_dup 10) (match_dup 9)))
16425 (set (match_operand:XF 0 "register_operand" "")
16426 (plus:XF (match_dup 12) (match_dup 7)))]
16427 "TARGET_USE_FANCY_MATH_387
16428 && flag_unsafe_math_optimizations"
16433 for (i=2; i<13; i++)
16434 operands[i] = gen_reg_rtx (XFmode);
16435 temp = standard_80387_constant_rtx (5); /* fldl2e */
16436 emit_move_insn (operands[2], temp);
16437 emit_move_insn (operands[9], CONST1_RTX (XFmode)); /* fld1 */
16440 (define_expand "ldexpdf3"
16441 [(set (match_dup 3)
16442 (float_extend:XF (match_operand:DF 1 "register_operand" "")))
16444 (float:XF (match_operand:SI 2 "register_operand" "")))
16445 (parallel [(set (match_dup 5)
16446 (unspec:XF [(match_dup 3) (match_dup 4)]
16447 UNSPEC_FSCALE_FRACT))
16449 (unspec:XF [(match_dup 3) (match_dup 4)]
16450 UNSPEC_FSCALE_EXP))])
16451 (set (match_operand:DF 0 "register_operand" "")
16452 (float_truncate:DF (match_dup 5)))]
16453 "TARGET_USE_FANCY_MATH_387
16454 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16455 && flag_unsafe_math_optimizations"
16459 for (i=3; i<7; i++)
16460 operands[i] = gen_reg_rtx (XFmode);
16463 (define_expand "ldexpsf3"
16464 [(set (match_dup 3)
16465 (float_extend:XF (match_operand:SF 1 "register_operand" "")))
16467 (float:XF (match_operand:SI 2 "register_operand" "")))
16468 (parallel [(set (match_dup 5)
16469 (unspec:XF [(match_dup 3) (match_dup 4)]
16470 UNSPEC_FSCALE_FRACT))
16472 (unspec:XF [(match_dup 3) (match_dup 4)]
16473 UNSPEC_FSCALE_EXP))])
16474 (set (match_operand:SF 0 "register_operand" "")
16475 (float_truncate:SF (match_dup 5)))]
16476 "TARGET_USE_FANCY_MATH_387
16477 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16478 && flag_unsafe_math_optimizations"
16482 for (i=3; i<7; i++)
16483 operands[i] = gen_reg_rtx (XFmode);
16486 (define_expand "ldexpxf3"
16487 [(set (match_dup 3)
16488 (float:XF (match_operand:SI 2 "register_operand" "")))
16489 (parallel [(set (match_operand:XF 0 " register_operand" "")
16490 (unspec:XF [(match_operand:XF 1 "register_operand" "")
16492 UNSPEC_FSCALE_FRACT))
16494 (unspec:XF [(match_dup 1) (match_dup 3)]
16495 UNSPEC_FSCALE_EXP))])]
16496 "TARGET_USE_FANCY_MATH_387
16497 && flag_unsafe_math_optimizations"
16501 for (i=3; i<5; i++)
16502 operands[i] = gen_reg_rtx (XFmode);
16506 (define_insn "frndintxf2"
16507 [(set (match_operand:XF 0 "register_operand" "=f")
16508 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16510 "TARGET_USE_FANCY_MATH_387
16511 && flag_unsafe_math_optimizations"
16513 [(set_attr "type" "fpspc")
16514 (set_attr "mode" "XF")])
16516 (define_expand "rintdf2"
16517 [(use (match_operand:DF 0 "register_operand" ""))
16518 (use (match_operand:DF 1 "register_operand" ""))]
16519 "TARGET_USE_FANCY_MATH_387
16520 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16521 && flag_unsafe_math_optimizations"
16523 rtx op0 = gen_reg_rtx (XFmode);
16524 rtx op1 = gen_reg_rtx (XFmode);
16526 emit_insn (gen_extenddfxf2 (op1, operands[1]));
16527 emit_insn (gen_frndintxf2 (op0, op1));
16529 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16533 (define_expand "rintsf2"
16534 [(use (match_operand:SF 0 "register_operand" ""))
16535 (use (match_operand:SF 1 "register_operand" ""))]
16536 "TARGET_USE_FANCY_MATH_387
16537 && (!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_extendsfxf2 (op1, operands[1]));
16544 emit_insn (gen_frndintxf2 (op0, op1));
16546 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16550 (define_expand "rintxf2"
16551 [(use (match_operand:XF 0 "register_operand" ""))
16552 (use (match_operand:XF 1 "register_operand" ""))]
16553 "TARGET_USE_FANCY_MATH_387
16554 && flag_unsafe_math_optimizations"
16556 emit_insn (gen_frndintxf2 (operands[0], operands[1]));
16560 (define_insn_and_split "*fistdi2_1"
16561 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
16562 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
16564 "TARGET_USE_FANCY_MATH_387
16565 && flag_unsafe_math_optimizations
16566 && !(reload_completed || reload_in_progress)"
16571 if (memory_operand (operands[0], VOIDmode))
16572 emit_insn (gen_fistdi2 (operands[0], operands[1]));
16575 operands[2] = assign_386_stack_local (DImode, SLOT_TEMP);
16576 emit_insn (gen_fistdi2_with_temp (operands[0], operands[1],
16581 [(set_attr "type" "fpspc")
16582 (set_attr "mode" "DI")])
16584 (define_insn "fistdi2"
16585 [(set (match_operand:DI 0 "memory_operand" "=m")
16586 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
16588 (clobber (match_scratch:XF 2 "=&1f"))]
16589 "TARGET_USE_FANCY_MATH_387
16590 && flag_unsafe_math_optimizations"
16591 "* return output_fix_trunc (insn, operands, 0);"
16592 [(set_attr "type" "fpspc")
16593 (set_attr "mode" "DI")])
16595 (define_insn "fistdi2_with_temp"
16596 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
16597 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
16599 (clobber (match_operand:DI 2 "memory_operand" "=m,m"))
16600 (clobber (match_scratch:XF 3 "=&1f,&1f"))]
16601 "TARGET_USE_FANCY_MATH_387
16602 && flag_unsafe_math_optimizations"
16604 [(set_attr "type" "fpspc")
16605 (set_attr "mode" "DI")])
16608 [(set (match_operand:DI 0 "register_operand" "")
16609 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16611 (clobber (match_operand:DI 2 "memory_operand" ""))
16612 (clobber (match_scratch 3 ""))]
16614 [(parallel [(set (match_dup 2) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
16615 (clobber (match_dup 3))])
16616 (set (match_dup 0) (match_dup 2))]
16620 [(set (match_operand:DI 0 "memory_operand" "")
16621 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16623 (clobber (match_operand:DI 2 "memory_operand" ""))
16624 (clobber (match_scratch 3 ""))]
16626 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST))
16627 (clobber (match_dup 3))])]
16630 (define_insn_and_split "*fist<mode>2_1"
16631 [(set (match_operand:X87MODEI12 0 "register_operand" "=r")
16632 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16634 "TARGET_USE_FANCY_MATH_387
16635 && flag_unsafe_math_optimizations
16636 && !(reload_completed || reload_in_progress)"
16641 operands[2] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
16642 emit_insn (gen_fist<mode>2_with_temp (operands[0], operands[1],
16646 [(set_attr "type" "fpspc")
16647 (set_attr "mode" "<MODE>")])
16649 (define_insn "fist<mode>2"
16650 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
16651 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16653 "TARGET_USE_FANCY_MATH_387
16654 && flag_unsafe_math_optimizations"
16655 "* return output_fix_trunc (insn, operands, 0);"
16656 [(set_attr "type" "fpspc")
16657 (set_attr "mode" "<MODE>")])
16659 (define_insn "fist<mode>2_with_temp"
16660 [(set (match_operand:X87MODEI12 0 "register_operand" "=r")
16661 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16663 (clobber (match_operand:X87MODEI12 2 "memory_operand" "=m"))]
16664 "TARGET_USE_FANCY_MATH_387
16665 && flag_unsafe_math_optimizations"
16667 [(set_attr "type" "fpspc")
16668 (set_attr "mode" "<MODE>")])
16671 [(set (match_operand:X87MODEI12 0 "register_operand" "")
16672 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16674 (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
16676 [(set (match_dup 2) (unspec:X87MODEI12 [(match_dup 1)]
16678 (set (match_dup 0) (match_dup 2))]
16682 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
16683 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16685 (clobber (match_operand:X87MODEI12 2 "memory_operand" ""))]
16687 [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
16691 (define_expand "lrint<mode>2"
16692 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
16693 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
16695 "TARGET_USE_FANCY_MATH_387
16696 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16697 && flag_unsafe_math_optimizations"
16700 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16701 (define_insn_and_split "frndintxf2_floor"
16702 [(set (match_operand:XF 0 "register_operand" "=f")
16703 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16704 UNSPEC_FRNDINT_FLOOR))
16705 (clobber (reg:CC FLAGS_REG))]
16706 "TARGET_USE_FANCY_MATH_387
16707 && flag_unsafe_math_optimizations
16708 && !(reload_completed || reload_in_progress)"
16713 ix86_optimize_mode_switching[I387_FLOOR] = 1;
16715 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16716 operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
16718 emit_insn (gen_frndintxf2_floor_i387 (operands[0], operands[1],
16719 operands[2], operands[3]));
16722 [(set_attr "type" "frndint")
16723 (set_attr "i387_cw" "floor")
16724 (set_attr "mode" "XF")])
16726 (define_insn "frndintxf2_floor_i387"
16727 [(set (match_operand:XF 0 "register_operand" "=f")
16728 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16729 UNSPEC_FRNDINT_FLOOR))
16730 (use (match_operand:HI 2 "memory_operand" "m"))
16731 (use (match_operand:HI 3 "memory_operand" "m"))]
16732 "TARGET_USE_FANCY_MATH_387
16733 && flag_unsafe_math_optimizations"
16734 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
16735 [(set_attr "type" "frndint")
16736 (set_attr "i387_cw" "floor")
16737 (set_attr "mode" "XF")])
16739 (define_expand "floorxf2"
16740 [(use (match_operand:XF 0 "register_operand" ""))
16741 (use (match_operand:XF 1 "register_operand" ""))]
16742 "TARGET_USE_FANCY_MATH_387
16743 && flag_unsafe_math_optimizations"
16745 emit_insn (gen_frndintxf2_floor (operands[0], operands[1]));
16749 (define_expand "floordf2"
16750 [(use (match_operand:DF 0 "register_operand" ""))
16751 (use (match_operand:DF 1 "register_operand" ""))]
16752 "TARGET_USE_FANCY_MATH_387
16753 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16754 && flag_unsafe_math_optimizations"
16756 rtx op0 = gen_reg_rtx (XFmode);
16757 rtx op1 = gen_reg_rtx (XFmode);
16759 emit_insn (gen_extenddfxf2 (op1, operands[1]));
16760 emit_insn (gen_frndintxf2_floor (op0, op1));
16762 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
16766 (define_expand "floorsf2"
16767 [(use (match_operand:SF 0 "register_operand" ""))
16768 (use (match_operand:SF 1 "register_operand" ""))]
16769 "TARGET_USE_FANCY_MATH_387
16770 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16771 && flag_unsafe_math_optimizations"
16773 rtx op0 = gen_reg_rtx (XFmode);
16774 rtx op1 = gen_reg_rtx (XFmode);
16776 emit_insn (gen_extendsfxf2 (op1, operands[1]));
16777 emit_insn (gen_frndintxf2_floor (op0, op1));
16779 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
16783 (define_insn_and_split "*fist<mode>2_floor_1"
16784 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
16785 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "f,f")]
16786 UNSPEC_FIST_FLOOR))
16787 (clobber (reg:CC FLAGS_REG))]
16788 "TARGET_USE_FANCY_MATH_387
16789 && flag_unsafe_math_optimizations
16790 && !(reload_completed || reload_in_progress)"
16795 ix86_optimize_mode_switching[I387_FLOOR] = 1;
16797 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16798 operands[3] = assign_386_stack_local (HImode, SLOT_CW_FLOOR);
16799 if (memory_operand (operands[0], VOIDmode))
16800 emit_insn (gen_fist<mode>2_floor (operands[0], operands[1],
16801 operands[2], operands[3]));
16804 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
16805 emit_insn (gen_fist<mode>2_floor_with_temp (operands[0], operands[1],
16806 operands[2], operands[3],
16811 [(set_attr "type" "fistp")
16812 (set_attr "i387_cw" "floor")
16813 (set_attr "mode" "<MODE>")])
16815 (define_insn "fistdi2_floor"
16816 [(set (match_operand:DI 0 "memory_operand" "=m")
16817 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
16818 UNSPEC_FIST_FLOOR))
16819 (use (match_operand:HI 2 "memory_operand" "m"))
16820 (use (match_operand:HI 3 "memory_operand" "m"))
16821 (clobber (match_scratch:XF 4 "=&1f"))]
16822 "TARGET_USE_FANCY_MATH_387
16823 && flag_unsafe_math_optimizations"
16824 "* return output_fix_trunc (insn, operands, 0);"
16825 [(set_attr "type" "fistp")
16826 (set_attr "i387_cw" "floor")
16827 (set_attr "mode" "DI")])
16829 (define_insn "fistdi2_floor_with_temp"
16830 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
16831 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
16832 UNSPEC_FIST_FLOOR))
16833 (use (match_operand:HI 2 "memory_operand" "m,m"))
16834 (use (match_operand:HI 3 "memory_operand" "m,m"))
16835 (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
16836 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
16837 "TARGET_USE_FANCY_MATH_387
16838 && flag_unsafe_math_optimizations"
16840 [(set_attr "type" "fistp")
16841 (set_attr "i387_cw" "floor")
16842 (set_attr "mode" "DI")])
16845 [(set (match_operand:DI 0 "register_operand" "")
16846 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16847 UNSPEC_FIST_FLOOR))
16848 (use (match_operand:HI 2 "memory_operand" ""))
16849 (use (match_operand:HI 3 "memory_operand" ""))
16850 (clobber (match_operand:DI 4 "memory_operand" ""))
16851 (clobber (match_scratch 5 ""))]
16853 [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
16854 (use (match_dup 2))
16855 (use (match_dup 3))
16856 (clobber (match_dup 5))])
16857 (set (match_dup 0) (match_dup 4))]
16861 [(set (match_operand:DI 0 "memory_operand" "")
16862 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
16863 UNSPEC_FIST_FLOOR))
16864 (use (match_operand:HI 2 "memory_operand" ""))
16865 (use (match_operand:HI 3 "memory_operand" ""))
16866 (clobber (match_operand:DI 4 "memory_operand" ""))
16867 (clobber (match_scratch 5 ""))]
16869 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_FLOOR))
16870 (use (match_dup 2))
16871 (use (match_dup 3))
16872 (clobber (match_dup 5))])]
16875 (define_insn "fist<mode>2_floor"
16876 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
16877 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
16878 UNSPEC_FIST_FLOOR))
16879 (use (match_operand:HI 2 "memory_operand" "m"))
16880 (use (match_operand:HI 3 "memory_operand" "m"))]
16881 "TARGET_USE_FANCY_MATH_387
16882 && flag_unsafe_math_optimizations"
16883 "* return output_fix_trunc (insn, operands, 0);"
16884 [(set_attr "type" "fistp")
16885 (set_attr "i387_cw" "floor")
16886 (set_attr "mode" "<MODE>")])
16888 (define_insn "fist<mode>2_floor_with_temp"
16889 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
16890 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
16891 UNSPEC_FIST_FLOOR))
16892 (use (match_operand:HI 2 "memory_operand" "m,m"))
16893 (use (match_operand:HI 3 "memory_operand" "m,m"))
16894 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
16895 "TARGET_USE_FANCY_MATH_387
16896 && flag_unsafe_math_optimizations"
16898 [(set_attr "type" "fistp")
16899 (set_attr "i387_cw" "floor")
16900 (set_attr "mode" "<MODE>")])
16903 [(set (match_operand:X87MODEI12 0 "register_operand" "")
16904 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16905 UNSPEC_FIST_FLOOR))
16906 (use (match_operand:HI 2 "memory_operand" ""))
16907 (use (match_operand:HI 3 "memory_operand" ""))
16908 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
16910 [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
16911 UNSPEC_FIST_FLOOR))
16912 (use (match_dup 2))
16913 (use (match_dup 3))])
16914 (set (match_dup 0) (match_dup 4))]
16918 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
16919 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
16920 UNSPEC_FIST_FLOOR))
16921 (use (match_operand:HI 2 "memory_operand" ""))
16922 (use (match_operand:HI 3 "memory_operand" ""))
16923 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
16925 [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
16926 UNSPEC_FIST_FLOOR))
16927 (use (match_dup 2))
16928 (use (match_dup 3))])]
16931 (define_expand "lfloor<mode>2"
16932 [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
16933 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
16934 UNSPEC_FIST_FLOOR))
16935 (clobber (reg:CC FLAGS_REG))])]
16936 "TARGET_USE_FANCY_MATH_387
16937 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
16938 && flag_unsafe_math_optimizations"
16941 ;; Rounding mode control word calculation could clobber FLAGS_REG.
16942 (define_insn_and_split "frndintxf2_ceil"
16943 [(set (match_operand:XF 0 "register_operand" "=f")
16944 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16945 UNSPEC_FRNDINT_CEIL))
16946 (clobber (reg:CC FLAGS_REG))]
16947 "TARGET_USE_FANCY_MATH_387
16948 && flag_unsafe_math_optimizations
16949 && !(reload_completed || reload_in_progress)"
16954 ix86_optimize_mode_switching[I387_CEIL] = 1;
16956 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
16957 operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
16959 emit_insn (gen_frndintxf2_ceil_i387 (operands[0], operands[1],
16960 operands[2], operands[3]));
16963 [(set_attr "type" "frndint")
16964 (set_attr "i387_cw" "ceil")
16965 (set_attr "mode" "XF")])
16967 (define_insn "frndintxf2_ceil_i387"
16968 [(set (match_operand:XF 0 "register_operand" "=f")
16969 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
16970 UNSPEC_FRNDINT_CEIL))
16971 (use (match_operand:HI 2 "memory_operand" "m"))
16972 (use (match_operand:HI 3 "memory_operand" "m"))]
16973 "TARGET_USE_FANCY_MATH_387
16974 && flag_unsafe_math_optimizations"
16975 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
16976 [(set_attr "type" "frndint")
16977 (set_attr "i387_cw" "ceil")
16978 (set_attr "mode" "XF")])
16980 (define_expand "ceilxf2"
16981 [(use (match_operand:XF 0 "register_operand" ""))
16982 (use (match_operand:XF 1 "register_operand" ""))]
16983 "TARGET_USE_FANCY_MATH_387
16984 && flag_unsafe_math_optimizations"
16986 emit_insn (gen_frndintxf2_ceil (operands[0], operands[1]));
16990 (define_expand "ceildf2"
16991 [(use (match_operand:DF 0 "register_operand" ""))
16992 (use (match_operand:DF 1 "register_operand" ""))]
16993 "TARGET_USE_FANCY_MATH_387
16994 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
16995 && flag_unsafe_math_optimizations"
16997 rtx op0 = gen_reg_rtx (XFmode);
16998 rtx op1 = gen_reg_rtx (XFmode);
17000 emit_insn (gen_extenddfxf2 (op1, operands[1]));
17001 emit_insn (gen_frndintxf2_ceil (op0, op1));
17003 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
17007 (define_expand "ceilsf2"
17008 [(use (match_operand:SF 0 "register_operand" ""))
17009 (use (match_operand:SF 1 "register_operand" ""))]
17010 "TARGET_USE_FANCY_MATH_387
17011 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
17012 && flag_unsafe_math_optimizations"
17014 rtx op0 = gen_reg_rtx (XFmode);
17015 rtx op1 = gen_reg_rtx (XFmode);
17017 emit_insn (gen_extendsfxf2 (op1, operands[1]));
17018 emit_insn (gen_frndintxf2_ceil (op0, op1));
17020 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
17024 (define_insn_and_split "*fist<mode>2_ceil_1"
17025 [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "=m,?r")
17026 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "f,f")]
17028 (clobber (reg:CC FLAGS_REG))]
17029 "TARGET_USE_FANCY_MATH_387
17030 && flag_unsafe_math_optimizations
17031 && !(reload_completed || reload_in_progress)"
17036 ix86_optimize_mode_switching[I387_CEIL] = 1;
17038 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17039 operands[3] = assign_386_stack_local (HImode, SLOT_CW_CEIL);
17040 if (memory_operand (operands[0], VOIDmode))
17041 emit_insn (gen_fist<mode>2_ceil (operands[0], operands[1],
17042 operands[2], operands[3]));
17045 operands[4] = assign_386_stack_local (<MODE>mode, SLOT_TEMP);
17046 emit_insn (gen_fist<mode>2_ceil_with_temp (operands[0], operands[1],
17047 operands[2], operands[3],
17052 [(set_attr "type" "fistp")
17053 (set_attr "i387_cw" "ceil")
17054 (set_attr "mode" "<MODE>")])
17056 (define_insn "fistdi2_ceil"
17057 [(set (match_operand:DI 0 "memory_operand" "=m")
17058 (unspec:DI [(match_operand:XF 1 "register_operand" "f")]
17060 (use (match_operand:HI 2 "memory_operand" "m"))
17061 (use (match_operand:HI 3 "memory_operand" "m"))
17062 (clobber (match_scratch:XF 4 "=&1f"))]
17063 "TARGET_USE_FANCY_MATH_387
17064 && flag_unsafe_math_optimizations"
17065 "* return output_fix_trunc (insn, operands, 0);"
17066 [(set_attr "type" "fistp")
17067 (set_attr "i387_cw" "ceil")
17068 (set_attr "mode" "DI")])
17070 (define_insn "fistdi2_ceil_with_temp"
17071 [(set (match_operand:DI 0 "nonimmediate_operand" "=m,?r")
17072 (unspec:DI [(match_operand:XF 1 "register_operand" "f,f")]
17074 (use (match_operand:HI 2 "memory_operand" "m,m"))
17075 (use (match_operand:HI 3 "memory_operand" "m,m"))
17076 (clobber (match_operand:DI 4 "memory_operand" "=m,m"))
17077 (clobber (match_scratch:XF 5 "=&1f,&1f"))]
17078 "TARGET_USE_FANCY_MATH_387
17079 && flag_unsafe_math_optimizations"
17081 [(set_attr "type" "fistp")
17082 (set_attr "i387_cw" "ceil")
17083 (set_attr "mode" "DI")])
17086 [(set (match_operand:DI 0 "register_operand" "")
17087 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17089 (use (match_operand:HI 2 "memory_operand" ""))
17090 (use (match_operand:HI 3 "memory_operand" ""))
17091 (clobber (match_operand:DI 4 "memory_operand" ""))
17092 (clobber (match_scratch 5 ""))]
17094 [(parallel [(set (match_dup 4) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
17095 (use (match_dup 2))
17096 (use (match_dup 3))
17097 (clobber (match_dup 5))])
17098 (set (match_dup 0) (match_dup 4))]
17102 [(set (match_operand:DI 0 "memory_operand" "")
17103 (unspec:DI [(match_operand:XF 1 "register_operand" "")]
17105 (use (match_operand:HI 2 "memory_operand" ""))
17106 (use (match_operand:HI 3 "memory_operand" ""))
17107 (clobber (match_operand:DI 4 "memory_operand" ""))
17108 (clobber (match_scratch 5 ""))]
17110 [(parallel [(set (match_dup 0) (unspec:DI [(match_dup 1)] UNSPEC_FIST_CEIL))
17111 (use (match_dup 2))
17112 (use (match_dup 3))
17113 (clobber (match_dup 5))])]
17116 (define_insn "fist<mode>2_ceil"
17117 [(set (match_operand:X87MODEI12 0 "memory_operand" "=m")
17118 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f")]
17120 (use (match_operand:HI 2 "memory_operand" "m"))
17121 (use (match_operand:HI 3 "memory_operand" "m"))]
17122 "TARGET_USE_FANCY_MATH_387
17123 && flag_unsafe_math_optimizations"
17124 "* return output_fix_trunc (insn, operands, 0);"
17125 [(set_attr "type" "fistp")
17126 (set_attr "i387_cw" "ceil")
17127 (set_attr "mode" "<MODE>")])
17129 (define_insn "fist<mode>2_ceil_with_temp"
17130 [(set (match_operand:X87MODEI12 0 "nonimmediate_operand" "=m,?r")
17131 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "f,f")]
17133 (use (match_operand:HI 2 "memory_operand" "m,m"))
17134 (use (match_operand:HI 3 "memory_operand" "m,m"))
17135 (clobber (match_operand:X87MODEI12 4 "memory_operand" "=m,m"))]
17136 "TARGET_USE_FANCY_MATH_387
17137 && flag_unsafe_math_optimizations"
17139 [(set_attr "type" "fistp")
17140 (set_attr "i387_cw" "ceil")
17141 (set_attr "mode" "<MODE>")])
17144 [(set (match_operand:X87MODEI12 0 "register_operand" "")
17145 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17147 (use (match_operand:HI 2 "memory_operand" ""))
17148 (use (match_operand:HI 3 "memory_operand" ""))
17149 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
17151 [(parallel [(set (match_dup 4) (unspec:X87MODEI12 [(match_dup 1)]
17153 (use (match_dup 2))
17154 (use (match_dup 3))])
17155 (set (match_dup 0) (match_dup 4))]
17159 [(set (match_operand:X87MODEI12 0 "memory_operand" "")
17160 (unspec:X87MODEI12 [(match_operand:XF 1 "register_operand" "")]
17162 (use (match_operand:HI 2 "memory_operand" ""))
17163 (use (match_operand:HI 3 "memory_operand" ""))
17164 (clobber (match_operand:X87MODEI12 4 "memory_operand" ""))]
17166 [(parallel [(set (match_dup 0) (unspec:X87MODEI12 [(match_dup 1)]
17168 (use (match_dup 2))
17169 (use (match_dup 3))])]
17172 (define_expand "lceil<mode>2"
17173 [(parallel [(set (match_operand:X87MODEI 0 "nonimmediate_operand" "")
17174 (unspec:X87MODEI [(match_operand:XF 1 "register_operand" "")]
17176 (clobber (reg:CC FLAGS_REG))])]
17177 "TARGET_USE_FANCY_MATH_387
17178 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
17179 && flag_unsafe_math_optimizations"
17182 ;; Rounding mode control word calculation could clobber FLAGS_REG.
17183 (define_insn_and_split "frndintxf2_trunc"
17184 [(set (match_operand:XF 0 "register_operand" "=f")
17185 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17186 UNSPEC_FRNDINT_TRUNC))
17187 (clobber (reg:CC FLAGS_REG))]
17188 "TARGET_USE_FANCY_MATH_387
17189 && flag_unsafe_math_optimizations
17190 && !(reload_completed || reload_in_progress)"
17195 ix86_optimize_mode_switching[I387_TRUNC] = 1;
17197 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17198 operands[3] = assign_386_stack_local (HImode, SLOT_CW_TRUNC);
17200 emit_insn (gen_frndintxf2_trunc_i387 (operands[0], operands[1],
17201 operands[2], operands[3]));
17204 [(set_attr "type" "frndint")
17205 (set_attr "i387_cw" "trunc")
17206 (set_attr "mode" "XF")])
17208 (define_insn "frndintxf2_trunc_i387"
17209 [(set (match_operand:XF 0 "register_operand" "=f")
17210 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17211 UNSPEC_FRNDINT_TRUNC))
17212 (use (match_operand:HI 2 "memory_operand" "m"))
17213 (use (match_operand:HI 3 "memory_operand" "m"))]
17214 "TARGET_USE_FANCY_MATH_387
17215 && flag_unsafe_math_optimizations"
17216 "fldcw\t%3\n\tfrndint\n\tfldcw\t%2"
17217 [(set_attr "type" "frndint")
17218 (set_attr "i387_cw" "trunc")
17219 (set_attr "mode" "XF")])
17221 (define_expand "btruncxf2"
17222 [(use (match_operand:XF 0 "register_operand" ""))
17223 (use (match_operand:XF 1 "register_operand" ""))]
17224 "TARGET_USE_FANCY_MATH_387
17225 && flag_unsafe_math_optimizations"
17227 emit_insn (gen_frndintxf2_trunc (operands[0], operands[1]));
17231 (define_expand "btruncdf2"
17232 [(use (match_operand:DF 0 "register_operand" ""))
17233 (use (match_operand:DF 1 "register_operand" ""))]
17234 "TARGET_USE_FANCY_MATH_387
17235 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
17236 && flag_unsafe_math_optimizations"
17238 rtx op0 = gen_reg_rtx (XFmode);
17239 rtx op1 = gen_reg_rtx (XFmode);
17241 emit_insn (gen_extenddfxf2 (op1, operands[1]));
17242 emit_insn (gen_frndintxf2_trunc (op0, op1));
17244 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
17248 (define_expand "btruncsf2"
17249 [(use (match_operand:SF 0 "register_operand" ""))
17250 (use (match_operand:SF 1 "register_operand" ""))]
17251 "TARGET_USE_FANCY_MATH_387
17252 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
17253 && flag_unsafe_math_optimizations"
17255 rtx op0 = gen_reg_rtx (XFmode);
17256 rtx op1 = gen_reg_rtx (XFmode);
17258 emit_insn (gen_extendsfxf2 (op1, operands[1]));
17259 emit_insn (gen_frndintxf2_trunc (op0, op1));
17261 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
17265 ;; Rounding mode control word calculation could clobber FLAGS_REG.
17266 (define_insn_and_split "frndintxf2_mask_pm"
17267 [(set (match_operand:XF 0 "register_operand" "=f")
17268 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17269 UNSPEC_FRNDINT_MASK_PM))
17270 (clobber (reg:CC FLAGS_REG))]
17271 "TARGET_USE_FANCY_MATH_387
17272 && flag_unsafe_math_optimizations
17273 && !(reload_completed || reload_in_progress)"
17278 ix86_optimize_mode_switching[I387_MASK_PM] = 1;
17280 operands[2] = assign_386_stack_local (HImode, SLOT_CW_STORED);
17281 operands[3] = assign_386_stack_local (HImode, SLOT_CW_MASK_PM);
17283 emit_insn (gen_frndintxf2_mask_pm_i387 (operands[0], operands[1],
17284 operands[2], operands[3]));
17287 [(set_attr "type" "frndint")
17288 (set_attr "i387_cw" "mask_pm")
17289 (set_attr "mode" "XF")])
17291 (define_insn "frndintxf2_mask_pm_i387"
17292 [(set (match_operand:XF 0 "register_operand" "=f")
17293 (unspec:XF [(match_operand:XF 1 "register_operand" "0")]
17294 UNSPEC_FRNDINT_MASK_PM))
17295 (use (match_operand:HI 2 "memory_operand" "m"))
17296 (use (match_operand:HI 3 "memory_operand" "m"))]
17297 "TARGET_USE_FANCY_MATH_387
17298 && flag_unsafe_math_optimizations"
17299 "fldcw\t%3\n\tfrndint\n\tfclex\n\tfldcw\t%2"
17300 [(set_attr "type" "frndint")
17301 (set_attr "i387_cw" "mask_pm")
17302 (set_attr "mode" "XF")])
17304 (define_expand "nearbyintxf2"
17305 [(use (match_operand:XF 0 "register_operand" ""))
17306 (use (match_operand:XF 1 "register_operand" ""))]
17307 "TARGET_USE_FANCY_MATH_387
17308 && flag_unsafe_math_optimizations"
17310 emit_insn (gen_frndintxf2_mask_pm (operands[0], operands[1]));
17315 (define_expand "nearbyintdf2"
17316 [(use (match_operand:DF 0 "register_operand" ""))
17317 (use (match_operand:DF 1 "register_operand" ""))]
17318 "TARGET_USE_FANCY_MATH_387
17319 && (!(TARGET_SSE2 && TARGET_SSE_MATH) || TARGET_MIX_SSE_I387)
17320 && flag_unsafe_math_optimizations"
17322 rtx op0 = gen_reg_rtx (XFmode);
17323 rtx op1 = gen_reg_rtx (XFmode);
17325 emit_insn (gen_extenddfxf2 (op1, operands[1]));
17326 emit_insn (gen_frndintxf2_mask_pm (op0, op1));
17328 emit_insn (gen_truncxfdf2_i387_noop (operands[0], op0));
17332 (define_expand "nearbyintsf2"
17333 [(use (match_operand:SF 0 "register_operand" ""))
17334 (use (match_operand:SF 1 "register_operand" ""))]
17335 "TARGET_USE_FANCY_MATH_387
17336 && (!TARGET_SSE_MATH || TARGET_MIX_SSE_I387)
17337 && flag_unsafe_math_optimizations"
17339 rtx op0 = gen_reg_rtx (XFmode);
17340 rtx op1 = gen_reg_rtx (XFmode);
17342 emit_insn (gen_extendsfxf2 (op1, operands[1]));
17343 emit_insn (gen_frndintxf2_mask_pm (op0, op1));
17345 emit_insn (gen_truncxfsf2_i387_noop (operands[0], op0));
17350 ;; Block operation instructions
17353 [(set (reg:SI DIRFLAG_REG) (const_int 0))]
17356 [(set_attr "type" "cld")])
17358 (define_expand "movmemsi"
17359 [(use (match_operand:BLK 0 "memory_operand" ""))
17360 (use (match_operand:BLK 1 "memory_operand" ""))
17361 (use (match_operand:SI 2 "nonmemory_operand" ""))
17362 (use (match_operand:SI 3 "const_int_operand" ""))]
17363 "! optimize_size || TARGET_INLINE_ALL_STRINGOPS"
17365 if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3]))
17371 (define_expand "movmemdi"
17372 [(use (match_operand:BLK 0 "memory_operand" ""))
17373 (use (match_operand:BLK 1 "memory_operand" ""))
17374 (use (match_operand:DI 2 "nonmemory_operand" ""))
17375 (use (match_operand:DI 3 "const_int_operand" ""))]
17378 if (ix86_expand_movmem (operands[0], operands[1], operands[2], operands[3]))
17384 ;; Most CPUs don't like single string operations
17385 ;; Handle this case here to simplify previous expander.
17387 (define_expand "strmov"
17388 [(set (match_dup 4) (match_operand 3 "memory_operand" ""))
17389 (set (match_operand 1 "memory_operand" "") (match_dup 4))
17390 (parallel [(set (match_operand 0 "register_operand" "") (match_dup 5))
17391 (clobber (reg:CC FLAGS_REG))])
17392 (parallel [(set (match_operand 2 "register_operand" "") (match_dup 6))
17393 (clobber (reg:CC FLAGS_REG))])]
17396 rtx adjust = GEN_INT (GET_MODE_SIZE (GET_MODE (operands[1])));
17398 /* If .md ever supports :P for Pmode, these can be directly
17399 in the pattern above. */
17400 operands[5] = gen_rtx_PLUS (Pmode, operands[0], adjust);
17401 operands[6] = gen_rtx_PLUS (Pmode, operands[2], adjust);
17403 if (TARGET_SINGLE_STRINGOP || optimize_size)
17405 emit_insn (gen_strmov_singleop (operands[0], operands[1],
17406 operands[2], operands[3],
17407 operands[5], operands[6]));
17411 operands[4] = gen_reg_rtx (GET_MODE (operands[1]));
17414 (define_expand "strmov_singleop"
17415 [(parallel [(set (match_operand 1 "memory_operand" "")
17416 (match_operand 3 "memory_operand" ""))
17417 (set (match_operand 0 "register_operand" "")
17418 (match_operand 4 "" ""))
17419 (set (match_operand 2 "register_operand" "")
17420 (match_operand 5 "" ""))
17421 (use (reg:SI DIRFLAG_REG))])]
17422 "TARGET_SINGLE_STRINGOP || optimize_size"
17425 (define_insn "*strmovdi_rex_1"
17426 [(set (mem:DI (match_operand:DI 2 "register_operand" "0"))
17427 (mem:DI (match_operand:DI 3 "register_operand" "1")))
17428 (set (match_operand:DI 0 "register_operand" "=D")
17429 (plus:DI (match_dup 2)
17431 (set (match_operand:DI 1 "register_operand" "=S")
17432 (plus:DI (match_dup 3)
17434 (use (reg:SI DIRFLAG_REG))]
17435 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17437 [(set_attr "type" "str")
17438 (set_attr "mode" "DI")
17439 (set_attr "memory" "both")])
17441 (define_insn "*strmovsi_1"
17442 [(set (mem:SI (match_operand:SI 2 "register_operand" "0"))
17443 (mem:SI (match_operand:SI 3 "register_operand" "1")))
17444 (set (match_operand:SI 0 "register_operand" "=D")
17445 (plus:SI (match_dup 2)
17447 (set (match_operand:SI 1 "register_operand" "=S")
17448 (plus:SI (match_dup 3)
17450 (use (reg:SI DIRFLAG_REG))]
17451 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17453 [(set_attr "type" "str")
17454 (set_attr "mode" "SI")
17455 (set_attr "memory" "both")])
17457 (define_insn "*strmovsi_rex_1"
17458 [(set (mem:SI (match_operand:DI 2 "register_operand" "0"))
17459 (mem:SI (match_operand:DI 3 "register_operand" "1")))
17460 (set (match_operand:DI 0 "register_operand" "=D")
17461 (plus:DI (match_dup 2)
17463 (set (match_operand:DI 1 "register_operand" "=S")
17464 (plus:DI (match_dup 3)
17466 (use (reg:SI DIRFLAG_REG))]
17467 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17469 [(set_attr "type" "str")
17470 (set_attr "mode" "SI")
17471 (set_attr "memory" "both")])
17473 (define_insn "*strmovhi_1"
17474 [(set (mem:HI (match_operand:SI 2 "register_operand" "0"))
17475 (mem:HI (match_operand:SI 3 "register_operand" "1")))
17476 (set (match_operand:SI 0 "register_operand" "=D")
17477 (plus:SI (match_dup 2)
17479 (set (match_operand:SI 1 "register_operand" "=S")
17480 (plus:SI (match_dup 3)
17482 (use (reg:SI DIRFLAG_REG))]
17483 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17485 [(set_attr "type" "str")
17486 (set_attr "memory" "both")
17487 (set_attr "mode" "HI")])
17489 (define_insn "*strmovhi_rex_1"
17490 [(set (mem:HI (match_operand:DI 2 "register_operand" "0"))
17491 (mem:HI (match_operand:DI 3 "register_operand" "1")))
17492 (set (match_operand:DI 0 "register_operand" "=D")
17493 (plus:DI (match_dup 2)
17495 (set (match_operand:DI 1 "register_operand" "=S")
17496 (plus:DI (match_dup 3)
17498 (use (reg:SI DIRFLAG_REG))]
17499 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17501 [(set_attr "type" "str")
17502 (set_attr "memory" "both")
17503 (set_attr "mode" "HI")])
17505 (define_insn "*strmovqi_1"
17506 [(set (mem:QI (match_operand:SI 2 "register_operand" "0"))
17507 (mem:QI (match_operand:SI 3 "register_operand" "1")))
17508 (set (match_operand:SI 0 "register_operand" "=D")
17509 (plus:SI (match_dup 2)
17511 (set (match_operand:SI 1 "register_operand" "=S")
17512 (plus:SI (match_dup 3)
17514 (use (reg:SI DIRFLAG_REG))]
17515 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17517 [(set_attr "type" "str")
17518 (set_attr "memory" "both")
17519 (set_attr "mode" "QI")])
17521 (define_insn "*strmovqi_rex_1"
17522 [(set (mem:QI (match_operand:DI 2 "register_operand" "0"))
17523 (mem:QI (match_operand:DI 3 "register_operand" "1")))
17524 (set (match_operand:DI 0 "register_operand" "=D")
17525 (plus:DI (match_dup 2)
17527 (set (match_operand:DI 1 "register_operand" "=S")
17528 (plus:DI (match_dup 3)
17530 (use (reg:SI DIRFLAG_REG))]
17531 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17533 [(set_attr "type" "str")
17534 (set_attr "memory" "both")
17535 (set_attr "mode" "QI")])
17537 (define_expand "rep_mov"
17538 [(parallel [(set (match_operand 4 "register_operand" "") (const_int 0))
17539 (set (match_operand 0 "register_operand" "")
17540 (match_operand 5 "" ""))
17541 (set (match_operand 2 "register_operand" "")
17542 (match_operand 6 "" ""))
17543 (set (match_operand 1 "memory_operand" "")
17544 (match_operand 3 "memory_operand" ""))
17545 (use (match_dup 4))
17546 (use (reg:SI DIRFLAG_REG))])]
17550 (define_insn "*rep_movdi_rex64"
17551 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
17552 (set (match_operand:DI 0 "register_operand" "=D")
17553 (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
17555 (match_operand:DI 3 "register_operand" "0")))
17556 (set (match_operand:DI 1 "register_operand" "=S")
17557 (plus:DI (ashift:DI (match_dup 5) (const_int 3))
17558 (match_operand:DI 4 "register_operand" "1")))
17559 (set (mem:BLK (match_dup 3))
17560 (mem:BLK (match_dup 4)))
17561 (use (match_dup 5))
17562 (use (reg:SI DIRFLAG_REG))]
17564 "{rep\;movsq|rep movsq}"
17565 [(set_attr "type" "str")
17566 (set_attr "prefix_rep" "1")
17567 (set_attr "memory" "both")
17568 (set_attr "mode" "DI")])
17570 (define_insn "*rep_movsi"
17571 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
17572 (set (match_operand:SI 0 "register_operand" "=D")
17573 (plus:SI (ashift:SI (match_operand:SI 5 "register_operand" "2")
17575 (match_operand:SI 3 "register_operand" "0")))
17576 (set (match_operand:SI 1 "register_operand" "=S")
17577 (plus:SI (ashift:SI (match_dup 5) (const_int 2))
17578 (match_operand:SI 4 "register_operand" "1")))
17579 (set (mem:BLK (match_dup 3))
17580 (mem:BLK (match_dup 4)))
17581 (use (match_dup 5))
17582 (use (reg:SI DIRFLAG_REG))]
17584 "{rep\;movsl|rep movsd}"
17585 [(set_attr "type" "str")
17586 (set_attr "prefix_rep" "1")
17587 (set_attr "memory" "both")
17588 (set_attr "mode" "SI")])
17590 (define_insn "*rep_movsi_rex64"
17591 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
17592 (set (match_operand:DI 0 "register_operand" "=D")
17593 (plus:DI (ashift:DI (match_operand:DI 5 "register_operand" "2")
17595 (match_operand:DI 3 "register_operand" "0")))
17596 (set (match_operand:DI 1 "register_operand" "=S")
17597 (plus:DI (ashift:DI (match_dup 5) (const_int 2))
17598 (match_operand:DI 4 "register_operand" "1")))
17599 (set (mem:BLK (match_dup 3))
17600 (mem:BLK (match_dup 4)))
17601 (use (match_dup 5))
17602 (use (reg:SI DIRFLAG_REG))]
17604 "{rep\;movsl|rep movsd}"
17605 [(set_attr "type" "str")
17606 (set_attr "prefix_rep" "1")
17607 (set_attr "memory" "both")
17608 (set_attr "mode" "SI")])
17610 (define_insn "*rep_movqi"
17611 [(set (match_operand:SI 2 "register_operand" "=c") (const_int 0))
17612 (set (match_operand:SI 0 "register_operand" "=D")
17613 (plus:SI (match_operand:SI 3 "register_operand" "0")
17614 (match_operand:SI 5 "register_operand" "2")))
17615 (set (match_operand:SI 1 "register_operand" "=S")
17616 (plus:SI (match_operand:SI 4 "register_operand" "1") (match_dup 5)))
17617 (set (mem:BLK (match_dup 3))
17618 (mem:BLK (match_dup 4)))
17619 (use (match_dup 5))
17620 (use (reg:SI DIRFLAG_REG))]
17622 "{rep\;movsb|rep movsb}"
17623 [(set_attr "type" "str")
17624 (set_attr "prefix_rep" "1")
17625 (set_attr "memory" "both")
17626 (set_attr "mode" "SI")])
17628 (define_insn "*rep_movqi_rex64"
17629 [(set (match_operand:DI 2 "register_operand" "=c") (const_int 0))
17630 (set (match_operand:DI 0 "register_operand" "=D")
17631 (plus:DI (match_operand:DI 3 "register_operand" "0")
17632 (match_operand:DI 5 "register_operand" "2")))
17633 (set (match_operand:DI 1 "register_operand" "=S")
17634 (plus:DI (match_operand:DI 4 "register_operand" "1") (match_dup 5)))
17635 (set (mem:BLK (match_dup 3))
17636 (mem:BLK (match_dup 4)))
17637 (use (match_dup 5))
17638 (use (reg:SI DIRFLAG_REG))]
17640 "{rep\;movsb|rep movsb}"
17641 [(set_attr "type" "str")
17642 (set_attr "prefix_rep" "1")
17643 (set_attr "memory" "both")
17644 (set_attr "mode" "SI")])
17646 (define_expand "setmemsi"
17647 [(use (match_operand:BLK 0 "memory_operand" ""))
17648 (use (match_operand:SI 1 "nonmemory_operand" ""))
17649 (use (match_operand 2 "const_int_operand" ""))
17650 (use (match_operand 3 "const_int_operand" ""))]
17653 /* If value to set is not zero, use the library routine. */
17654 if (operands[2] != const0_rtx)
17657 if (ix86_expand_clrmem (operands[0], operands[1], operands[3]))
17663 (define_expand "setmemdi"
17664 [(use (match_operand:BLK 0 "memory_operand" ""))
17665 (use (match_operand:DI 1 "nonmemory_operand" ""))
17666 (use (match_operand 2 "const_int_operand" ""))
17667 (use (match_operand 3 "const_int_operand" ""))]
17670 /* If value to set is not zero, use the library routine. */
17671 if (operands[2] != const0_rtx)
17674 if (ix86_expand_clrmem (operands[0], operands[1], operands[3]))
17680 ;; Most CPUs don't like single string operations
17681 ;; Handle this case here to simplify previous expander.
17683 (define_expand "strset"
17684 [(set (match_operand 1 "memory_operand" "")
17685 (match_operand 2 "register_operand" ""))
17686 (parallel [(set (match_operand 0 "register_operand" "")
17688 (clobber (reg:CC FLAGS_REG))])]
17691 if (GET_MODE (operands[1]) != GET_MODE (operands[2]))
17692 operands[1] = adjust_address_nv (operands[1], GET_MODE (operands[2]), 0);
17694 /* If .md ever supports :P for Pmode, this can be directly
17695 in the pattern above. */
17696 operands[3] = gen_rtx_PLUS (Pmode, operands[0],
17697 GEN_INT (GET_MODE_SIZE (GET_MODE
17699 if (TARGET_SINGLE_STRINGOP || optimize_size)
17701 emit_insn (gen_strset_singleop (operands[0], operands[1], operands[2],
17707 (define_expand "strset_singleop"
17708 [(parallel [(set (match_operand 1 "memory_operand" "")
17709 (match_operand 2 "register_operand" ""))
17710 (set (match_operand 0 "register_operand" "")
17711 (match_operand 3 "" ""))
17712 (use (reg:SI DIRFLAG_REG))])]
17713 "TARGET_SINGLE_STRINGOP || optimize_size"
17716 (define_insn "*strsetdi_rex_1"
17717 [(set (mem:DI (match_operand:DI 1 "register_operand" "0"))
17718 (match_operand:DI 2 "register_operand" "a"))
17719 (set (match_operand:DI 0 "register_operand" "=D")
17720 (plus:DI (match_dup 1)
17722 (use (reg:SI DIRFLAG_REG))]
17723 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17725 [(set_attr "type" "str")
17726 (set_attr "memory" "store")
17727 (set_attr "mode" "DI")])
17729 (define_insn "*strsetsi_1"
17730 [(set (mem:SI (match_operand:SI 1 "register_operand" "0"))
17731 (match_operand:SI 2 "register_operand" "a"))
17732 (set (match_operand:SI 0 "register_operand" "=D")
17733 (plus:SI (match_dup 1)
17735 (use (reg:SI DIRFLAG_REG))]
17736 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17738 [(set_attr "type" "str")
17739 (set_attr "memory" "store")
17740 (set_attr "mode" "SI")])
17742 (define_insn "*strsetsi_rex_1"
17743 [(set (mem:SI (match_operand:DI 1 "register_operand" "0"))
17744 (match_operand:SI 2 "register_operand" "a"))
17745 (set (match_operand:DI 0 "register_operand" "=D")
17746 (plus:DI (match_dup 1)
17748 (use (reg:SI DIRFLAG_REG))]
17749 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17751 [(set_attr "type" "str")
17752 (set_attr "memory" "store")
17753 (set_attr "mode" "SI")])
17755 (define_insn "*strsethi_1"
17756 [(set (mem:HI (match_operand:SI 1 "register_operand" "0"))
17757 (match_operand:HI 2 "register_operand" "a"))
17758 (set (match_operand:SI 0 "register_operand" "=D")
17759 (plus:SI (match_dup 1)
17761 (use (reg:SI DIRFLAG_REG))]
17762 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17764 [(set_attr "type" "str")
17765 (set_attr "memory" "store")
17766 (set_attr "mode" "HI")])
17768 (define_insn "*strsethi_rex_1"
17769 [(set (mem:HI (match_operand:DI 1 "register_operand" "0"))
17770 (match_operand:HI 2 "register_operand" "a"))
17771 (set (match_operand:DI 0 "register_operand" "=D")
17772 (plus:DI (match_dup 1)
17774 (use (reg:SI DIRFLAG_REG))]
17775 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17777 [(set_attr "type" "str")
17778 (set_attr "memory" "store")
17779 (set_attr "mode" "HI")])
17781 (define_insn "*strsetqi_1"
17782 [(set (mem:QI (match_operand:SI 1 "register_operand" "0"))
17783 (match_operand:QI 2 "register_operand" "a"))
17784 (set (match_operand:SI 0 "register_operand" "=D")
17785 (plus:SI (match_dup 1)
17787 (use (reg:SI DIRFLAG_REG))]
17788 "!TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17790 [(set_attr "type" "str")
17791 (set_attr "memory" "store")
17792 (set_attr "mode" "QI")])
17794 (define_insn "*strsetqi_rex_1"
17795 [(set (mem:QI (match_operand:DI 1 "register_operand" "0"))
17796 (match_operand:QI 2 "register_operand" "a"))
17797 (set (match_operand:DI 0 "register_operand" "=D")
17798 (plus:DI (match_dup 1)
17800 (use (reg:SI DIRFLAG_REG))]
17801 "TARGET_64BIT && (TARGET_SINGLE_STRINGOP || optimize_size)"
17803 [(set_attr "type" "str")
17804 (set_attr "memory" "store")
17805 (set_attr "mode" "QI")])
17807 (define_expand "rep_stos"
17808 [(parallel [(set (match_operand 1 "register_operand" "") (const_int 0))
17809 (set (match_operand 0 "register_operand" "")
17810 (match_operand 4 "" ""))
17811 (set (match_operand 2 "memory_operand" "") (const_int 0))
17812 (use (match_operand 3 "register_operand" ""))
17813 (use (match_dup 1))
17814 (use (reg:SI DIRFLAG_REG))])]
17818 (define_insn "*rep_stosdi_rex64"
17819 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17820 (set (match_operand:DI 0 "register_operand" "=D")
17821 (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
17823 (match_operand:DI 3 "register_operand" "0")))
17824 (set (mem:BLK (match_dup 3))
17826 (use (match_operand:DI 2 "register_operand" "a"))
17827 (use (match_dup 4))
17828 (use (reg:SI DIRFLAG_REG))]
17830 "{rep\;stosq|rep stosq}"
17831 [(set_attr "type" "str")
17832 (set_attr "prefix_rep" "1")
17833 (set_attr "memory" "store")
17834 (set_attr "mode" "DI")])
17836 (define_insn "*rep_stossi"
17837 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
17838 (set (match_operand:SI 0 "register_operand" "=D")
17839 (plus:SI (ashift:SI (match_operand:SI 4 "register_operand" "1")
17841 (match_operand:SI 3 "register_operand" "0")))
17842 (set (mem:BLK (match_dup 3))
17844 (use (match_operand:SI 2 "register_operand" "a"))
17845 (use (match_dup 4))
17846 (use (reg:SI DIRFLAG_REG))]
17848 "{rep\;stosl|rep stosd}"
17849 [(set_attr "type" "str")
17850 (set_attr "prefix_rep" "1")
17851 (set_attr "memory" "store")
17852 (set_attr "mode" "SI")])
17854 (define_insn "*rep_stossi_rex64"
17855 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17856 (set (match_operand:DI 0 "register_operand" "=D")
17857 (plus:DI (ashift:DI (match_operand:DI 4 "register_operand" "1")
17859 (match_operand:DI 3 "register_operand" "0")))
17860 (set (mem:BLK (match_dup 3))
17862 (use (match_operand:SI 2 "register_operand" "a"))
17863 (use (match_dup 4))
17864 (use (reg:SI DIRFLAG_REG))]
17866 "{rep\;stosl|rep stosd}"
17867 [(set_attr "type" "str")
17868 (set_attr "prefix_rep" "1")
17869 (set_attr "memory" "store")
17870 (set_attr "mode" "SI")])
17872 (define_insn "*rep_stosqi"
17873 [(set (match_operand:SI 1 "register_operand" "=c") (const_int 0))
17874 (set (match_operand:SI 0 "register_operand" "=D")
17875 (plus:SI (match_operand:SI 3 "register_operand" "0")
17876 (match_operand:SI 4 "register_operand" "1")))
17877 (set (mem:BLK (match_dup 3))
17879 (use (match_operand:QI 2 "register_operand" "a"))
17880 (use (match_dup 4))
17881 (use (reg:SI DIRFLAG_REG))]
17883 "{rep\;stosb|rep stosb}"
17884 [(set_attr "type" "str")
17885 (set_attr "prefix_rep" "1")
17886 (set_attr "memory" "store")
17887 (set_attr "mode" "QI")])
17889 (define_insn "*rep_stosqi_rex64"
17890 [(set (match_operand:DI 1 "register_operand" "=c") (const_int 0))
17891 (set (match_operand:DI 0 "register_operand" "=D")
17892 (plus:DI (match_operand:DI 3 "register_operand" "0")
17893 (match_operand:DI 4 "register_operand" "1")))
17894 (set (mem:BLK (match_dup 3))
17896 (use (match_operand:QI 2 "register_operand" "a"))
17897 (use (match_dup 4))
17898 (use (reg:SI DIRFLAG_REG))]
17900 "{rep\;stosb|rep stosb}"
17901 [(set_attr "type" "str")
17902 (set_attr "prefix_rep" "1")
17903 (set_attr "memory" "store")
17904 (set_attr "mode" "QI")])
17906 (define_expand "cmpstrnsi"
17907 [(set (match_operand:SI 0 "register_operand" "")
17908 (compare:SI (match_operand:BLK 1 "general_operand" "")
17909 (match_operand:BLK 2 "general_operand" "")))
17910 (use (match_operand 3 "general_operand" ""))
17911 (use (match_operand 4 "immediate_operand" ""))]
17912 "! optimize_size || TARGET_INLINE_ALL_STRINGOPS"
17914 rtx addr1, addr2, out, outlow, count, countreg, align;
17916 /* Can't use this if the user has appropriated esi or edi. */
17917 if (global_regs[4] || global_regs[5])
17921 if (GET_CODE (out) != REG)
17922 out = gen_reg_rtx (SImode);
17924 addr1 = copy_to_mode_reg (Pmode, XEXP (operands[1], 0));
17925 addr2 = copy_to_mode_reg (Pmode, XEXP (operands[2], 0));
17926 if (addr1 != XEXP (operands[1], 0))
17927 operands[1] = replace_equiv_address_nv (operands[1], addr1);
17928 if (addr2 != XEXP (operands[2], 0))
17929 operands[2] = replace_equiv_address_nv (operands[2], addr2);
17931 count = operands[3];
17932 countreg = ix86_zero_extend_to_Pmode (count);
17934 /* %%% Iff we are testing strict equality, we can use known alignment
17935 to good advantage. This may be possible with combine, particularly
17936 once cc0 is dead. */
17937 align = operands[4];
17939 emit_insn (gen_cld ());
17940 if (GET_CODE (count) == CONST_INT)
17942 if (INTVAL (count) == 0)
17944 emit_move_insn (operands[0], const0_rtx);
17947 emit_insn (gen_cmpstrnqi_nz_1 (addr1, addr2, countreg, align,
17948 operands[1], operands[2]));
17953 emit_insn (gen_cmpdi_1_rex64 (countreg, countreg));
17955 emit_insn (gen_cmpsi_1 (countreg, countreg));
17956 emit_insn (gen_cmpstrnqi_1 (addr1, addr2, countreg, align,
17957 operands[1], operands[2]));
17960 outlow = gen_lowpart (QImode, out);
17961 emit_insn (gen_cmpintqi (outlow));
17962 emit_move_insn (out, gen_rtx_SIGN_EXTEND (SImode, outlow));
17964 if (operands[0] != out)
17965 emit_move_insn (operands[0], out);
17970 ;; Produce a tri-state integer (-1, 0, 1) from condition codes.
17972 (define_expand "cmpintqi"
17973 [(set (match_dup 1)
17974 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
17976 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
17977 (parallel [(set (match_operand:QI 0 "register_operand" "")
17978 (minus:QI (match_dup 1)
17980 (clobber (reg:CC FLAGS_REG))])]
17982 "operands[1] = gen_reg_rtx (QImode);
17983 operands[2] = gen_reg_rtx (QImode);")
17985 ;; memcmp recognizers. The `cmpsb' opcode does nothing if the count is
17986 ;; zero. Emit extra code to make sure that a zero-length compare is EQ.
17988 (define_expand "cmpstrnqi_nz_1"
17989 [(parallel [(set (reg:CC FLAGS_REG)
17990 (compare:CC (match_operand 4 "memory_operand" "")
17991 (match_operand 5 "memory_operand" "")))
17992 (use (match_operand 2 "register_operand" ""))
17993 (use (match_operand:SI 3 "immediate_operand" ""))
17994 (use (reg:SI DIRFLAG_REG))
17995 (clobber (match_operand 0 "register_operand" ""))
17996 (clobber (match_operand 1 "register_operand" ""))
17997 (clobber (match_dup 2))])]
18001 (define_insn "*cmpstrnqi_nz_1"
18002 [(set (reg:CC FLAGS_REG)
18003 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
18004 (mem:BLK (match_operand:SI 5 "register_operand" "1"))))
18005 (use (match_operand:SI 6 "register_operand" "2"))
18006 (use (match_operand:SI 3 "immediate_operand" "i"))
18007 (use (reg:SI DIRFLAG_REG))
18008 (clobber (match_operand:SI 0 "register_operand" "=S"))
18009 (clobber (match_operand:SI 1 "register_operand" "=D"))
18010 (clobber (match_operand:SI 2 "register_operand" "=c"))]
18013 [(set_attr "type" "str")
18014 (set_attr "mode" "QI")
18015 (set_attr "prefix_rep" "1")])
18017 (define_insn "*cmpstrnqi_nz_rex_1"
18018 [(set (reg:CC FLAGS_REG)
18019 (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
18020 (mem:BLK (match_operand:DI 5 "register_operand" "1"))))
18021 (use (match_operand:DI 6 "register_operand" "2"))
18022 (use (match_operand:SI 3 "immediate_operand" "i"))
18023 (use (reg:SI DIRFLAG_REG))
18024 (clobber (match_operand:DI 0 "register_operand" "=S"))
18025 (clobber (match_operand:DI 1 "register_operand" "=D"))
18026 (clobber (match_operand:DI 2 "register_operand" "=c"))]
18029 [(set_attr "type" "str")
18030 (set_attr "mode" "QI")
18031 (set_attr "prefix_rep" "1")])
18033 ;; The same, but the count is not known to not be zero.
18035 (define_expand "cmpstrnqi_1"
18036 [(parallel [(set (reg:CC FLAGS_REG)
18037 (if_then_else:CC (ne (match_operand 2 "register_operand" "")
18039 (compare:CC (match_operand 4 "memory_operand" "")
18040 (match_operand 5 "memory_operand" ""))
18042 (use (match_operand:SI 3 "immediate_operand" ""))
18043 (use (reg:CC FLAGS_REG))
18044 (use (reg:SI DIRFLAG_REG))
18045 (clobber (match_operand 0 "register_operand" ""))
18046 (clobber (match_operand 1 "register_operand" ""))
18047 (clobber (match_dup 2))])]
18051 (define_insn "*cmpstrnqi_1"
18052 [(set (reg:CC FLAGS_REG)
18053 (if_then_else:CC (ne (match_operand:SI 6 "register_operand" "2")
18055 (compare:CC (mem:BLK (match_operand:SI 4 "register_operand" "0"))
18056 (mem:BLK (match_operand:SI 5 "register_operand" "1")))
18058 (use (match_operand:SI 3 "immediate_operand" "i"))
18059 (use (reg:CC FLAGS_REG))
18060 (use (reg:SI DIRFLAG_REG))
18061 (clobber (match_operand:SI 0 "register_operand" "=S"))
18062 (clobber (match_operand:SI 1 "register_operand" "=D"))
18063 (clobber (match_operand:SI 2 "register_operand" "=c"))]
18066 [(set_attr "type" "str")
18067 (set_attr "mode" "QI")
18068 (set_attr "prefix_rep" "1")])
18070 (define_insn "*cmpstrnqi_rex_1"
18071 [(set (reg:CC FLAGS_REG)
18072 (if_then_else:CC (ne (match_operand:DI 6 "register_operand" "2")
18074 (compare:CC (mem:BLK (match_operand:DI 4 "register_operand" "0"))
18075 (mem:BLK (match_operand:DI 5 "register_operand" "1")))
18077 (use (match_operand:SI 3 "immediate_operand" "i"))
18078 (use (reg:CC FLAGS_REG))
18079 (use (reg:SI DIRFLAG_REG))
18080 (clobber (match_operand:DI 0 "register_operand" "=S"))
18081 (clobber (match_operand:DI 1 "register_operand" "=D"))
18082 (clobber (match_operand:DI 2 "register_operand" "=c"))]
18085 [(set_attr "type" "str")
18086 (set_attr "mode" "QI")
18087 (set_attr "prefix_rep" "1")])
18089 (define_expand "strlensi"
18090 [(set (match_operand:SI 0 "register_operand" "")
18091 (unspec:SI [(match_operand:BLK 1 "general_operand" "")
18092 (match_operand:QI 2 "immediate_operand" "")
18093 (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
18096 if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
18102 (define_expand "strlendi"
18103 [(set (match_operand:DI 0 "register_operand" "")
18104 (unspec:DI [(match_operand:BLK 1 "general_operand" "")
18105 (match_operand:QI 2 "immediate_operand" "")
18106 (match_operand 3 "immediate_operand" "")] UNSPEC_SCAS))]
18109 if (ix86_expand_strlen (operands[0], operands[1], operands[2], operands[3]))
18115 (define_expand "strlenqi_1"
18116 [(parallel [(set (match_operand 0 "register_operand" "") (match_operand 2 "" ""))
18117 (use (reg:SI DIRFLAG_REG))
18118 (clobber (match_operand 1 "register_operand" ""))
18119 (clobber (reg:CC FLAGS_REG))])]
18123 (define_insn "*strlenqi_1"
18124 [(set (match_operand:SI 0 "register_operand" "=&c")
18125 (unspec:SI [(mem:BLK (match_operand:SI 5 "register_operand" "1"))
18126 (match_operand:QI 2 "register_operand" "a")
18127 (match_operand:SI 3 "immediate_operand" "i")
18128 (match_operand:SI 4 "register_operand" "0")] UNSPEC_SCAS))
18129 (use (reg:SI DIRFLAG_REG))
18130 (clobber (match_operand:SI 1 "register_operand" "=D"))
18131 (clobber (reg:CC FLAGS_REG))]
18134 [(set_attr "type" "str")
18135 (set_attr "mode" "QI")
18136 (set_attr "prefix_rep" "1")])
18138 (define_insn "*strlenqi_rex_1"
18139 [(set (match_operand:DI 0 "register_operand" "=&c")
18140 (unspec:DI [(mem:BLK (match_operand:DI 5 "register_operand" "1"))
18141 (match_operand:QI 2 "register_operand" "a")
18142 (match_operand:DI 3 "immediate_operand" "i")
18143 (match_operand:DI 4 "register_operand" "0")] UNSPEC_SCAS))
18144 (use (reg:SI DIRFLAG_REG))
18145 (clobber (match_operand:DI 1 "register_operand" "=D"))
18146 (clobber (reg:CC FLAGS_REG))]
18149 [(set_attr "type" "str")
18150 (set_attr "mode" "QI")
18151 (set_attr "prefix_rep" "1")])
18153 ;; Peephole optimizations to clean up after cmpstrn*. This should be
18154 ;; handled in combine, but it is not currently up to the task.
18155 ;; When used for their truth value, the cmpstrn* expanders generate
18164 ;; The intermediate three instructions are unnecessary.
18166 ;; This one handles cmpstrn*_nz_1...
18169 (set (reg:CC FLAGS_REG)
18170 (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
18171 (mem:BLK (match_operand 5 "register_operand" ""))))
18172 (use (match_operand 6 "register_operand" ""))
18173 (use (match_operand:SI 3 "immediate_operand" ""))
18174 (use (reg:SI DIRFLAG_REG))
18175 (clobber (match_operand 0 "register_operand" ""))
18176 (clobber (match_operand 1 "register_operand" ""))
18177 (clobber (match_operand 2 "register_operand" ""))])
18178 (set (match_operand:QI 7 "register_operand" "")
18179 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
18180 (set (match_operand:QI 8 "register_operand" "")
18181 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
18182 (set (reg FLAGS_REG)
18183 (compare (match_dup 7) (match_dup 8)))
18185 "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
18187 (set (reg:CC FLAGS_REG)
18188 (compare:CC (mem:BLK (match_dup 4))
18189 (mem:BLK (match_dup 5))))
18190 (use (match_dup 6))
18191 (use (match_dup 3))
18192 (use (reg:SI DIRFLAG_REG))
18193 (clobber (match_dup 0))
18194 (clobber (match_dup 1))
18195 (clobber (match_dup 2))])]
18198 ;; ...and this one handles cmpstrn*_1.
18201 (set (reg:CC FLAGS_REG)
18202 (if_then_else:CC (ne (match_operand 6 "register_operand" "")
18204 (compare:CC (mem:BLK (match_operand 4 "register_operand" ""))
18205 (mem:BLK (match_operand 5 "register_operand" "")))
18207 (use (match_operand:SI 3 "immediate_operand" ""))
18208 (use (reg:CC FLAGS_REG))
18209 (use (reg:SI DIRFLAG_REG))
18210 (clobber (match_operand 0 "register_operand" ""))
18211 (clobber (match_operand 1 "register_operand" ""))
18212 (clobber (match_operand 2 "register_operand" ""))])
18213 (set (match_operand:QI 7 "register_operand" "")
18214 (gtu:QI (reg:CC FLAGS_REG) (const_int 0)))
18215 (set (match_operand:QI 8 "register_operand" "")
18216 (ltu:QI (reg:CC FLAGS_REG) (const_int 0)))
18217 (set (reg FLAGS_REG)
18218 (compare (match_dup 7) (match_dup 8)))
18220 "peep2_reg_dead_p (4, operands[7]) && peep2_reg_dead_p (4, operands[8])"
18222 (set (reg:CC FLAGS_REG)
18223 (if_then_else:CC (ne (match_dup 6)
18225 (compare:CC (mem:BLK (match_dup 4))
18226 (mem:BLK (match_dup 5)))
18228 (use (match_dup 3))
18229 (use (reg:CC FLAGS_REG))
18230 (use (reg:SI DIRFLAG_REG))
18231 (clobber (match_dup 0))
18232 (clobber (match_dup 1))
18233 (clobber (match_dup 2))])]
18238 ;; Conditional move instructions.
18240 (define_expand "movdicc"
18241 [(set (match_operand:DI 0 "register_operand" "")
18242 (if_then_else:DI (match_operand 1 "comparison_operator" "")
18243 (match_operand:DI 2 "general_operand" "")
18244 (match_operand:DI 3 "general_operand" "")))]
18246 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
18248 (define_insn "x86_movdicc_0_m1_rex64"
18249 [(set (match_operand:DI 0 "register_operand" "=r")
18250 (if_then_else:DI (match_operand 1 "ix86_carry_flag_operator" "")
18253 (clobber (reg:CC FLAGS_REG))]
18256 ; Since we don't have the proper number of operands for an alu insn,
18257 ; fill in all the blanks.
18258 [(set_attr "type" "alu")
18259 (set_attr "pent_pair" "pu")
18260 (set_attr "memory" "none")
18261 (set_attr "imm_disp" "false")
18262 (set_attr "mode" "DI")
18263 (set_attr "length_immediate" "0")])
18265 (define_insn "*movdicc_c_rex64"
18266 [(set (match_operand:DI 0 "register_operand" "=r,r")
18267 (if_then_else:DI (match_operator 1 "ix86_comparison_operator"
18268 [(reg FLAGS_REG) (const_int 0)])
18269 (match_operand:DI 2 "nonimmediate_operand" "rm,0")
18270 (match_operand:DI 3 "nonimmediate_operand" "0,rm")))]
18271 "TARGET_64BIT && TARGET_CMOVE
18272 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18274 cmov%O2%C1\t{%2, %0|%0, %2}
18275 cmov%O2%c1\t{%3, %0|%0, %3}"
18276 [(set_attr "type" "icmov")
18277 (set_attr "mode" "DI")])
18279 (define_expand "movsicc"
18280 [(set (match_operand:SI 0 "register_operand" "")
18281 (if_then_else:SI (match_operand 1 "comparison_operator" "")
18282 (match_operand:SI 2 "general_operand" "")
18283 (match_operand:SI 3 "general_operand" "")))]
18285 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
18287 ;; Data flow gets confused by our desire for `sbbl reg,reg', and clearing
18288 ;; the register first winds up with `sbbl $0,reg', which is also weird.
18289 ;; So just document what we're doing explicitly.
18291 (define_insn "x86_movsicc_0_m1"
18292 [(set (match_operand:SI 0 "register_operand" "=r")
18293 (if_then_else:SI (match_operand 1 "ix86_carry_flag_operator" "")
18296 (clobber (reg:CC FLAGS_REG))]
18299 ; Since we don't have the proper number of operands for an alu insn,
18300 ; fill in all the blanks.
18301 [(set_attr "type" "alu")
18302 (set_attr "pent_pair" "pu")
18303 (set_attr "memory" "none")
18304 (set_attr "imm_disp" "false")
18305 (set_attr "mode" "SI")
18306 (set_attr "length_immediate" "0")])
18308 (define_insn "*movsicc_noc"
18309 [(set (match_operand:SI 0 "register_operand" "=r,r")
18310 (if_then_else:SI (match_operator 1 "ix86_comparison_operator"
18311 [(reg FLAGS_REG) (const_int 0)])
18312 (match_operand:SI 2 "nonimmediate_operand" "rm,0")
18313 (match_operand:SI 3 "nonimmediate_operand" "0,rm")))]
18315 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18317 cmov%O2%C1\t{%2, %0|%0, %2}
18318 cmov%O2%c1\t{%3, %0|%0, %3}"
18319 [(set_attr "type" "icmov")
18320 (set_attr "mode" "SI")])
18322 (define_expand "movhicc"
18323 [(set (match_operand:HI 0 "register_operand" "")
18324 (if_then_else:HI (match_operand 1 "comparison_operator" "")
18325 (match_operand:HI 2 "general_operand" "")
18326 (match_operand:HI 3 "general_operand" "")))]
18327 "TARGET_HIMODE_MATH"
18328 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
18330 (define_insn "*movhicc_noc"
18331 [(set (match_operand:HI 0 "register_operand" "=r,r")
18332 (if_then_else:HI (match_operator 1 "ix86_comparison_operator"
18333 [(reg FLAGS_REG) (const_int 0)])
18334 (match_operand:HI 2 "nonimmediate_operand" "rm,0")
18335 (match_operand:HI 3 "nonimmediate_operand" "0,rm")))]
18337 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18339 cmov%O2%C1\t{%2, %0|%0, %2}
18340 cmov%O2%c1\t{%3, %0|%0, %3}"
18341 [(set_attr "type" "icmov")
18342 (set_attr "mode" "HI")])
18344 (define_expand "movqicc"
18345 [(set (match_operand:QI 0 "register_operand" "")
18346 (if_then_else:QI (match_operand 1 "comparison_operator" "")
18347 (match_operand:QI 2 "general_operand" "")
18348 (match_operand:QI 3 "general_operand" "")))]
18349 "TARGET_QIMODE_MATH"
18350 "if (!ix86_expand_int_movcc (operands)) FAIL; DONE;")
18352 (define_insn_and_split "*movqicc_noc"
18353 [(set (match_operand:QI 0 "register_operand" "=r,r")
18354 (if_then_else:QI (match_operator 1 "ix86_comparison_operator"
18355 [(match_operand 4 "flags_reg_operand" "")
18357 (match_operand:QI 2 "register_operand" "r,0")
18358 (match_operand:QI 3 "register_operand" "0,r")))]
18359 "TARGET_CMOVE && !TARGET_PARTIAL_REG_STALL"
18361 "&& reload_completed"
18362 [(set (match_dup 0)
18363 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
18366 "operands[0] = gen_lowpart (SImode, operands[0]);
18367 operands[2] = gen_lowpart (SImode, operands[2]);
18368 operands[3] = gen_lowpart (SImode, operands[3]);"
18369 [(set_attr "type" "icmov")
18370 (set_attr "mode" "SI")])
18372 (define_expand "movsfcc"
18373 [(set (match_operand:SF 0 "register_operand" "")
18374 (if_then_else:SF (match_operand 1 "comparison_operator" "")
18375 (match_operand:SF 2 "register_operand" "")
18376 (match_operand:SF 3 "register_operand" "")))]
18377 "(TARGET_80387 && TARGET_CMOVE) || TARGET_SSE_MATH"
18378 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
18380 (define_insn "*movsfcc_1_387"
18381 [(set (match_operand:SF 0 "register_operand" "=f#r,f#r,r#f,r#f")
18382 (if_then_else:SF (match_operator 1 "fcmov_comparison_operator"
18383 [(reg FLAGS_REG) (const_int 0)])
18384 (match_operand:SF 2 "nonimmediate_operand" "f#r,0,rm#f,0")
18385 (match_operand:SF 3 "nonimmediate_operand" "0,f#r,0,rm#f")))]
18386 "TARGET_80387 && TARGET_CMOVE
18387 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18389 fcmov%F1\t{%2, %0|%0, %2}
18390 fcmov%f1\t{%3, %0|%0, %3}
18391 cmov%O2%C1\t{%2, %0|%0, %2}
18392 cmov%O2%c1\t{%3, %0|%0, %3}"
18393 [(set_attr "type" "fcmov,fcmov,icmov,icmov")
18394 (set_attr "mode" "SF,SF,SI,SI")])
18396 (define_expand "movdfcc"
18397 [(set (match_operand:DF 0 "register_operand" "")
18398 (if_then_else:DF (match_operand 1 "comparison_operator" "")
18399 (match_operand:DF 2 "register_operand" "")
18400 (match_operand:DF 3 "register_operand" "")))]
18401 "(TARGET_80387 && TARGET_CMOVE) || (TARGET_SSE2 && TARGET_SSE_MATH)"
18402 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
18404 (define_insn "*movdfcc_1"
18405 [(set (match_operand:DF 0 "register_operand" "=f#r,f#r,&r#f,&r#f")
18406 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
18407 [(reg FLAGS_REG) (const_int 0)])
18408 (match_operand:DF 2 "nonimmediate_operand" "f#r,0,rm#f,0")
18409 (match_operand:DF 3 "nonimmediate_operand" "0,f#r,0,rm#f")))]
18410 "!TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
18411 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18413 fcmov%F1\t{%2, %0|%0, %2}
18414 fcmov%f1\t{%3, %0|%0, %3}
18417 [(set_attr "type" "fcmov,fcmov,multi,multi")
18418 (set_attr "mode" "DF")])
18420 (define_insn "*movdfcc_1_rex64"
18421 [(set (match_operand:DF 0 "register_operand" "=f#r,f#r,r#f,r#f")
18422 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
18423 [(reg FLAGS_REG) (const_int 0)])
18424 (match_operand:DF 2 "nonimmediate_operand" "f#r,0#r,rm#f,0#f")
18425 (match_operand:DF 3 "nonimmediate_operand" "0#r,f#r,0#f,rm#f")))]
18426 "TARGET_64BIT && TARGET_80387 && TARGET_CMOVE
18427 && (GET_CODE (operands[2]) != MEM || GET_CODE (operands[3]) != MEM)"
18429 fcmov%F1\t{%2, %0|%0, %2}
18430 fcmov%f1\t{%3, %0|%0, %3}
18431 cmov%O2%C1\t{%2, %0|%0, %2}
18432 cmov%O2%c1\t{%3, %0|%0, %3}"
18433 [(set_attr "type" "fcmov,fcmov,icmov,icmov")
18434 (set_attr "mode" "DF")])
18437 [(set (match_operand:DF 0 "register_and_not_any_fp_reg_operand" "")
18438 (if_then_else:DF (match_operator 1 "fcmov_comparison_operator"
18439 [(match_operand 4 "flags_reg_operand" "")
18441 (match_operand:DF 2 "nonimmediate_operand" "")
18442 (match_operand:DF 3 "nonimmediate_operand" "")))]
18443 "!TARGET_64BIT && reload_completed"
18444 [(set (match_dup 2)
18445 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
18449 (if_then_else:SI (match_op_dup 1 [(match_dup 4) (const_int 0)])
18452 "split_di (operands+2, 1, operands+5, operands+6);
18453 split_di (operands+3, 1, operands+7, operands+8);
18454 split_di (operands, 1, operands+2, operands+3);")
18456 (define_expand "movxfcc"
18457 [(set (match_operand:XF 0 "register_operand" "")
18458 (if_then_else:XF (match_operand 1 "comparison_operator" "")
18459 (match_operand:XF 2 "register_operand" "")
18460 (match_operand:XF 3 "register_operand" "")))]
18461 "TARGET_80387 && TARGET_CMOVE"
18462 "if (! ix86_expand_fp_movcc (operands)) FAIL; DONE;")
18464 (define_insn "*movxfcc_1"
18465 [(set (match_operand:XF 0 "register_operand" "=f,f")
18466 (if_then_else:XF (match_operator 1 "fcmov_comparison_operator"
18467 [(reg FLAGS_REG) (const_int 0)])
18468 (match_operand:XF 2 "register_operand" "f,0")
18469 (match_operand:XF 3 "register_operand" "0,f")))]
18470 "TARGET_80387 && TARGET_CMOVE"
18472 fcmov%F1\t{%2, %0|%0, %2}
18473 fcmov%f1\t{%3, %0|%0, %3}"
18474 [(set_attr "type" "fcmov")
18475 (set_attr "mode" "XF")])
18477 ;; These versions of the min/max patterns are intentionally ignorant of
18478 ;; their behavior wrt -0.0 and NaN (via the commutative operand mark).
18479 ;; Since both the tree-level MAX_EXPR and the rtl-level SMAX operator
18480 ;; are undefined in this condition, we're certain this is correct.
18482 (define_insn "sminsf3"
18483 [(set (match_operand:SF 0 "register_operand" "=x")
18484 (smin:SF (match_operand:SF 1 "nonimmediate_operand" "%0")
18485 (match_operand:SF 2 "nonimmediate_operand" "xm")))]
18487 "minss\t{%2, %0|%0, %2}"
18488 [(set_attr "type" "sseadd")
18489 (set_attr "mode" "SF")])
18491 (define_insn "smaxsf3"
18492 [(set (match_operand:SF 0 "register_operand" "=x")
18493 (smax:SF (match_operand:SF 1 "nonimmediate_operand" "%0")
18494 (match_operand:SF 2 "nonimmediate_operand" "xm")))]
18496 "maxss\t{%2, %0|%0, %2}"
18497 [(set_attr "type" "sseadd")
18498 (set_attr "mode" "SF")])
18500 (define_insn "smindf3"
18501 [(set (match_operand:DF 0 "register_operand" "=x")
18502 (smin:DF (match_operand:DF 1 "nonimmediate_operand" "%0")
18503 (match_operand:DF 2 "nonimmediate_operand" "xm")))]
18504 "TARGET_SSE2 && TARGET_SSE_MATH"
18505 "minsd\t{%2, %0|%0, %2}"
18506 [(set_attr "type" "sseadd")
18507 (set_attr "mode" "DF")])
18509 (define_insn "smaxdf3"
18510 [(set (match_operand:DF 0 "register_operand" "=x")
18511 (smax:DF (match_operand:DF 1 "nonimmediate_operand" "%0")
18512 (match_operand:DF 2 "nonimmediate_operand" "xm")))]
18513 "TARGET_SSE2 && TARGET_SSE_MATH"
18514 "maxsd\t{%2, %0|%0, %2}"
18515 [(set_attr "type" "sseadd")
18516 (set_attr "mode" "DF")])
18518 ;; These versions of the min/max patterns implement exactly the operations
18519 ;; min = (op1 < op2 ? op1 : op2)
18520 ;; max = (!(op1 < op2) ? op1 : op2)
18521 ;; Their operands are not commutative, and thus they may be used in the
18522 ;; presence of -0.0 and NaN.
18524 (define_insn "*ieee_sminsf3"
18525 [(set (match_operand:SF 0 "register_operand" "=x")
18526 (unspec:SF [(match_operand:SF 1 "register_operand" "0")
18527 (match_operand:SF 2 "nonimmediate_operand" "xm")]
18530 "minss\t{%2, %0|%0, %2}"
18531 [(set_attr "type" "sseadd")
18532 (set_attr "mode" "SF")])
18534 (define_insn "*ieee_smaxsf3"
18535 [(set (match_operand:SF 0 "register_operand" "=x")
18536 (unspec:SF [(match_operand:SF 1 "register_operand" "0")
18537 (match_operand:SF 2 "nonimmediate_operand" "xm")]
18540 "maxss\t{%2, %0|%0, %2}"
18541 [(set_attr "type" "sseadd")
18542 (set_attr "mode" "SF")])
18544 (define_insn "*ieee_smindf3"
18545 [(set (match_operand:DF 0 "register_operand" "=x")
18546 (unspec:DF [(match_operand:DF 1 "register_operand" "0")
18547 (match_operand:DF 2 "nonimmediate_operand" "xm")]
18549 "TARGET_SSE2 && TARGET_SSE_MATH"
18550 "minsd\t{%2, %0|%0, %2}"
18551 [(set_attr "type" "sseadd")
18552 (set_attr "mode" "DF")])
18554 (define_insn "*ieee_smaxdf3"
18555 [(set (match_operand:DF 0 "register_operand" "=x")
18556 (unspec:DF [(match_operand:DF 1 "register_operand" "0")
18557 (match_operand:DF 2 "nonimmediate_operand" "xm")]
18559 "TARGET_SSE2 && TARGET_SSE_MATH"
18560 "maxsd\t{%2, %0|%0, %2}"
18561 [(set_attr "type" "sseadd")
18562 (set_attr "mode" "DF")])
18564 ;; Conditional addition patterns
18565 (define_expand "addqicc"
18566 [(match_operand:QI 0 "register_operand" "")
18567 (match_operand 1 "comparison_operator" "")
18568 (match_operand:QI 2 "register_operand" "")
18569 (match_operand:QI 3 "const_int_operand" "")]
18571 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18573 (define_expand "addhicc"
18574 [(match_operand:HI 0 "register_operand" "")
18575 (match_operand 1 "comparison_operator" "")
18576 (match_operand:HI 2 "register_operand" "")
18577 (match_operand:HI 3 "const_int_operand" "")]
18579 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18581 (define_expand "addsicc"
18582 [(match_operand:SI 0 "register_operand" "")
18583 (match_operand 1 "comparison_operator" "")
18584 (match_operand:SI 2 "register_operand" "")
18585 (match_operand:SI 3 "const_int_operand" "")]
18587 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18589 (define_expand "adddicc"
18590 [(match_operand:DI 0 "register_operand" "")
18591 (match_operand 1 "comparison_operator" "")
18592 (match_operand:DI 2 "register_operand" "")
18593 (match_operand:DI 3 "const_int_operand" "")]
18595 "if (!ix86_expand_int_addcc (operands)) FAIL; DONE;")
18598 ;; Misc patterns (?)
18600 ;; This pattern exists to put a dependency on all ebp-based memory accesses.
18601 ;; Otherwise there will be nothing to keep
18603 ;; [(set (reg ebp) (reg esp))]
18604 ;; [(set (reg esp) (plus (reg esp) (const_int -160000)))
18605 ;; (clobber (eflags)]
18606 ;; [(set (mem (plus (reg ebp) (const_int -160000))) (const_int 0))]
18608 ;; in proper program order.
18609 (define_insn "pro_epilogue_adjust_stack_1"
18610 [(set (match_operand:SI 0 "register_operand" "=r,r")
18611 (plus:SI (match_operand:SI 1 "register_operand" "0,r")
18612 (match_operand:SI 2 "immediate_operand" "i,i")))
18613 (clobber (reg:CC FLAGS_REG))
18614 (clobber (mem:BLK (scratch)))]
18617 switch (get_attr_type (insn))
18620 return "mov{l}\t{%1, %0|%0, %1}";
18623 if (GET_CODE (operands[2]) == CONST_INT
18624 && (INTVAL (operands[2]) == 128
18625 || (INTVAL (operands[2]) < 0
18626 && INTVAL (operands[2]) != -128)))
18628 operands[2] = GEN_INT (-INTVAL (operands[2]));
18629 return "sub{l}\t{%2, %0|%0, %2}";
18631 return "add{l}\t{%2, %0|%0, %2}";
18634 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
18635 return "lea{l}\t{%a2, %0|%0, %a2}";
18638 gcc_unreachable ();
18641 [(set (attr "type")
18642 (cond [(eq_attr "alternative" "0")
18643 (const_string "alu")
18644 (match_operand:SI 2 "const0_operand" "")
18645 (const_string "imov")
18647 (const_string "lea")))
18648 (set_attr "mode" "SI")])
18650 (define_insn "pro_epilogue_adjust_stack_rex64"
18651 [(set (match_operand:DI 0 "register_operand" "=r,r")
18652 (plus:DI (match_operand:DI 1 "register_operand" "0,r")
18653 (match_operand:DI 2 "x86_64_immediate_operand" "e,e")))
18654 (clobber (reg:CC FLAGS_REG))
18655 (clobber (mem:BLK (scratch)))]
18658 switch (get_attr_type (insn))
18661 return "mov{q}\t{%1, %0|%0, %1}";
18664 if (GET_CODE (operands[2]) == CONST_INT
18665 /* Avoid overflows. */
18666 && ((INTVAL (operands[2]) & ((((unsigned int) 1) << 31) - 1)))
18667 && (INTVAL (operands[2]) == 128
18668 || (INTVAL (operands[2]) < 0
18669 && INTVAL (operands[2]) != -128)))
18671 operands[2] = GEN_INT (-INTVAL (operands[2]));
18672 return "sub{q}\t{%2, %0|%0, %2}";
18674 return "add{q}\t{%2, %0|%0, %2}";
18677 operands[2] = SET_SRC (XVECEXP (PATTERN (insn), 0, 0));
18678 return "lea{q}\t{%a2, %0|%0, %a2}";
18681 gcc_unreachable ();
18684 [(set (attr "type")
18685 (cond [(eq_attr "alternative" "0")
18686 (const_string "alu")
18687 (match_operand:DI 2 "const0_operand" "")
18688 (const_string "imov")
18690 (const_string "lea")))
18691 (set_attr "mode" "DI")])
18693 (define_insn "pro_epilogue_adjust_stack_rex64_2"
18694 [(set (match_operand:DI 0 "register_operand" "=r,r")
18695 (plus:DI (match_operand:DI 1 "register_operand" "0,r")
18696 (match_operand:DI 3 "immediate_operand" "i,i")))
18697 (use (match_operand:DI 2 "register_operand" "r,r"))
18698 (clobber (reg:CC FLAGS_REG))
18699 (clobber (mem:BLK (scratch)))]
18702 switch (get_attr_type (insn))
18705 return "add{q}\t{%2, %0|%0, %2}";
18708 operands[2] = gen_rtx_PLUS (DImode, operands[1], operands[2]);
18709 return "lea{q}\t{%a2, %0|%0, %a2}";
18712 gcc_unreachable ();
18715 [(set_attr "type" "alu,lea")
18716 (set_attr "mode" "DI")])
18718 (define_expand "allocate_stack_worker"
18719 [(match_operand:SI 0 "register_operand" "")]
18720 "TARGET_STACK_PROBE"
18722 if (reload_completed)
18725 emit_insn (gen_allocate_stack_worker_rex64_postreload (operands[0]));
18727 emit_insn (gen_allocate_stack_worker_postreload (operands[0]));
18732 emit_insn (gen_allocate_stack_worker_rex64 (operands[0]));
18734 emit_insn (gen_allocate_stack_worker_1 (operands[0]));
18739 (define_insn "allocate_stack_worker_1"
18740 [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")]
18741 UNSPECV_STACK_PROBE)
18742 (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0)))
18743 (clobber (match_scratch:SI 1 "=0"))
18744 (clobber (reg:CC FLAGS_REG))]
18745 "!TARGET_64BIT && TARGET_STACK_PROBE"
18747 [(set_attr "type" "multi")
18748 (set_attr "length" "5")])
18750 (define_expand "allocate_stack_worker_postreload"
18751 [(parallel [(unspec_volatile:SI [(match_operand:SI 0 "register_operand" "a")]
18752 UNSPECV_STACK_PROBE)
18753 (set (reg:SI SP_REG) (minus:SI (reg:SI SP_REG) (match_dup 0)))
18754 (clobber (match_dup 0))
18755 (clobber (reg:CC FLAGS_REG))])]
18759 (define_insn "allocate_stack_worker_rex64"
18760 [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")]
18761 UNSPECV_STACK_PROBE)
18762 (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0)))
18763 (clobber (match_scratch:DI 1 "=0"))
18764 (clobber (reg:CC FLAGS_REG))]
18765 "TARGET_64BIT && TARGET_STACK_PROBE"
18767 [(set_attr "type" "multi")
18768 (set_attr "length" "5")])
18770 (define_expand "allocate_stack_worker_rex64_postreload"
18771 [(parallel [(unspec_volatile:DI [(match_operand:DI 0 "register_operand" "a")]
18772 UNSPECV_STACK_PROBE)
18773 (set (reg:DI SP_REG) (minus:DI (reg:DI SP_REG) (match_dup 0)))
18774 (clobber (match_dup 0))
18775 (clobber (reg:CC FLAGS_REG))])]
18779 (define_expand "allocate_stack"
18780 [(parallel [(set (match_operand:SI 0 "register_operand" "=r")
18781 (minus:SI (reg:SI SP_REG)
18782 (match_operand:SI 1 "general_operand" "")))
18783 (clobber (reg:CC FLAGS_REG))])
18784 (parallel [(set (reg:SI SP_REG)
18785 (minus:SI (reg:SI SP_REG) (match_dup 1)))
18786 (clobber (reg:CC FLAGS_REG))])]
18787 "TARGET_STACK_PROBE"
18789 #ifdef CHECK_STACK_LIMIT
18790 if (GET_CODE (operands[1]) == CONST_INT
18791 && INTVAL (operands[1]) < CHECK_STACK_LIMIT)
18792 emit_insn (gen_subsi3 (stack_pointer_rtx, stack_pointer_rtx,
18796 emit_insn (gen_allocate_stack_worker (copy_to_mode_reg (SImode,
18799 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
18803 (define_expand "builtin_setjmp_receiver"
18804 [(label_ref (match_operand 0 "" ""))]
18805 "!TARGET_64BIT && flag_pic"
18807 emit_insn (gen_set_got (pic_offset_table_rtx));
18811 ;; Avoid redundant prefixes by splitting HImode arithmetic to SImode.
18814 [(set (match_operand 0 "register_operand" "")
18815 (match_operator 3 "promotable_binary_operator"
18816 [(match_operand 1 "register_operand" "")
18817 (match_operand 2 "aligned_operand" "")]))
18818 (clobber (reg:CC FLAGS_REG))]
18819 "! TARGET_PARTIAL_REG_STALL && reload_completed
18820 && ((GET_MODE (operands[0]) == HImode
18821 && ((!optimize_size && !TARGET_FAST_PREFIX)
18822 || GET_CODE (operands[2]) != CONST_INT
18823 || CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')))
18824 || (GET_MODE (operands[0]) == QImode
18825 && (TARGET_PROMOTE_QImode || optimize_size)))"
18826 [(parallel [(set (match_dup 0)
18827 (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
18828 (clobber (reg:CC FLAGS_REG))])]
18829 "operands[0] = gen_lowpart (SImode, operands[0]);
18830 operands[1] = gen_lowpart (SImode, operands[1]);
18831 if (GET_CODE (operands[3]) != ASHIFT)
18832 operands[2] = gen_lowpart (SImode, operands[2]);
18833 PUT_MODE (operands[3], SImode);")
18835 ; Promote the QImode tests, as i386 has encoding of the AND
18836 ; instruction with 32-bit sign-extended immediate and thus the
18837 ; instruction size is unchanged, except in the %eax case for
18838 ; which it is increased by one byte, hence the ! optimize_size.
18840 [(set (match_operand 0 "flags_reg_operand" "")
18841 (match_operator 2 "compare_operator"
18842 [(and (match_operand 3 "aligned_operand" "")
18843 (match_operand 4 "const_int_operand" ""))
18845 (set (match_operand 1 "register_operand" "")
18846 (and (match_dup 3) (match_dup 4)))]
18847 "! TARGET_PARTIAL_REG_STALL && reload_completed
18848 /* Ensure that the operand will remain sign-extended immediate. */
18849 && ix86_match_ccmode (insn, INTVAL (operands[4]) >= 0 ? CCNOmode : CCZmode)
18851 && ((GET_MODE (operands[1]) == HImode && ! TARGET_FAST_PREFIX)
18852 || (GET_MODE (operands[1]) == QImode && TARGET_PROMOTE_QImode))"
18853 [(parallel [(set (match_dup 0)
18854 (match_op_dup 2 [(and:SI (match_dup 3) (match_dup 4))
18857 (and:SI (match_dup 3) (match_dup 4)))])]
18860 = gen_int_mode (INTVAL (operands[4])
18861 & GET_MODE_MASK (GET_MODE (operands[1])), SImode);
18862 operands[1] = gen_lowpart (SImode, operands[1]);
18863 operands[3] = gen_lowpart (SImode, operands[3]);
18866 ; Don't promote the QImode tests, as i386 doesn't have encoding of
18867 ; the TEST instruction with 32-bit sign-extended immediate and thus
18868 ; the instruction size would at least double, which is not what we
18869 ; want even with ! optimize_size.
18871 [(set (match_operand 0 "flags_reg_operand" "")
18872 (match_operator 1 "compare_operator"
18873 [(and (match_operand:HI 2 "aligned_operand" "")
18874 (match_operand:HI 3 "const_int_operand" ""))
18876 "! TARGET_PARTIAL_REG_STALL && reload_completed
18877 /* Ensure that the operand will remain sign-extended immediate. */
18878 && ix86_match_ccmode (insn, INTVAL (operands[3]) >= 0 ? CCNOmode : CCZmode)
18879 && ! TARGET_FAST_PREFIX
18880 && ! optimize_size"
18881 [(set (match_dup 0)
18882 (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
18886 = gen_int_mode (INTVAL (operands[3])
18887 & GET_MODE_MASK (GET_MODE (operands[2])), SImode);
18888 operands[2] = gen_lowpart (SImode, operands[2]);
18892 [(set (match_operand 0 "register_operand" "")
18893 (neg (match_operand 1 "register_operand" "")))
18894 (clobber (reg:CC FLAGS_REG))]
18895 "! TARGET_PARTIAL_REG_STALL && reload_completed
18896 && (GET_MODE (operands[0]) == HImode
18897 || (GET_MODE (operands[0]) == QImode
18898 && (TARGET_PROMOTE_QImode || optimize_size)))"
18899 [(parallel [(set (match_dup 0)
18900 (neg:SI (match_dup 1)))
18901 (clobber (reg:CC FLAGS_REG))])]
18902 "operands[0] = gen_lowpart (SImode, operands[0]);
18903 operands[1] = gen_lowpart (SImode, operands[1]);")
18906 [(set (match_operand 0 "register_operand" "")
18907 (not (match_operand 1 "register_operand" "")))]
18908 "! TARGET_PARTIAL_REG_STALL && reload_completed
18909 && (GET_MODE (operands[0]) == HImode
18910 || (GET_MODE (operands[0]) == QImode
18911 && (TARGET_PROMOTE_QImode || optimize_size)))"
18912 [(set (match_dup 0)
18913 (not:SI (match_dup 1)))]
18914 "operands[0] = gen_lowpart (SImode, operands[0]);
18915 operands[1] = gen_lowpart (SImode, operands[1]);")
18918 [(set (match_operand 0 "register_operand" "")
18919 (if_then_else (match_operator 1 "comparison_operator"
18920 [(reg FLAGS_REG) (const_int 0)])
18921 (match_operand 2 "register_operand" "")
18922 (match_operand 3 "register_operand" "")))]
18923 "! TARGET_PARTIAL_REG_STALL && TARGET_CMOVE
18924 && (GET_MODE (operands[0]) == HImode
18925 || (GET_MODE (operands[0]) == QImode
18926 && (TARGET_PROMOTE_QImode || optimize_size)))"
18927 [(set (match_dup 0)
18928 (if_then_else:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
18929 "operands[0] = gen_lowpart (SImode, operands[0]);
18930 operands[2] = gen_lowpart (SImode, operands[2]);
18931 operands[3] = gen_lowpart (SImode, operands[3]);")
18934 ;; RTL Peephole optimizations, run before sched2. These primarily look to
18935 ;; transform a complex memory operation into two memory to register operations.
18937 ;; Don't push memory operands
18939 [(set (match_operand:SI 0 "push_operand" "")
18940 (match_operand:SI 1 "memory_operand" ""))
18941 (match_scratch:SI 2 "r")]
18942 "!optimize_size && !TARGET_PUSH_MEMORY
18943 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
18944 [(set (match_dup 2) (match_dup 1))
18945 (set (match_dup 0) (match_dup 2))]
18949 [(set (match_operand:DI 0 "push_operand" "")
18950 (match_operand:DI 1 "memory_operand" ""))
18951 (match_scratch:DI 2 "r")]
18952 "!optimize_size && !TARGET_PUSH_MEMORY
18953 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
18954 [(set (match_dup 2) (match_dup 1))
18955 (set (match_dup 0) (match_dup 2))]
18958 ;; We need to handle SFmode only, because DFmode and XFmode is split to
18961 [(set (match_operand:SF 0 "push_operand" "")
18962 (match_operand:SF 1 "memory_operand" ""))
18963 (match_scratch:SF 2 "r")]
18964 "!optimize_size && !TARGET_PUSH_MEMORY
18965 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
18966 [(set (match_dup 2) (match_dup 1))
18967 (set (match_dup 0) (match_dup 2))]
18971 [(set (match_operand:HI 0 "push_operand" "")
18972 (match_operand:HI 1 "memory_operand" ""))
18973 (match_scratch:HI 2 "r")]
18974 "!optimize_size && !TARGET_PUSH_MEMORY
18975 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
18976 [(set (match_dup 2) (match_dup 1))
18977 (set (match_dup 0) (match_dup 2))]
18981 [(set (match_operand:QI 0 "push_operand" "")
18982 (match_operand:QI 1 "memory_operand" ""))
18983 (match_scratch:QI 2 "q")]
18984 "!optimize_size && !TARGET_PUSH_MEMORY
18985 && !RTX_FRAME_RELATED_P (peep2_next_insn (0))"
18986 [(set (match_dup 2) (match_dup 1))
18987 (set (match_dup 0) (match_dup 2))]
18990 ;; Don't move an immediate directly to memory when the instruction
18993 [(match_scratch:SI 1 "r")
18994 (set (match_operand:SI 0 "memory_operand" "")
18997 && ! TARGET_USE_MOV0
18998 && TARGET_SPLIT_LONG_MOVES
18999 && get_attr_length (insn) >= ix86_cost->large_insn
19000 && peep2_regno_dead_p (0, FLAGS_REG)"
19001 [(parallel [(set (match_dup 1) (const_int 0))
19002 (clobber (reg:CC FLAGS_REG))])
19003 (set (match_dup 0) (match_dup 1))]
19007 [(match_scratch:HI 1 "r")
19008 (set (match_operand:HI 0 "memory_operand" "")
19011 && ! TARGET_USE_MOV0
19012 && TARGET_SPLIT_LONG_MOVES
19013 && get_attr_length (insn) >= ix86_cost->large_insn
19014 && peep2_regno_dead_p (0, FLAGS_REG)"
19015 [(parallel [(set (match_dup 2) (const_int 0))
19016 (clobber (reg:CC FLAGS_REG))])
19017 (set (match_dup 0) (match_dup 1))]
19018 "operands[2] = gen_lowpart (SImode, operands[1]);")
19021 [(match_scratch:QI 1 "q")
19022 (set (match_operand:QI 0 "memory_operand" "")
19025 && ! TARGET_USE_MOV0
19026 && TARGET_SPLIT_LONG_MOVES
19027 && get_attr_length (insn) >= ix86_cost->large_insn
19028 && peep2_regno_dead_p (0, FLAGS_REG)"
19029 [(parallel [(set (match_dup 2) (const_int 0))
19030 (clobber (reg:CC FLAGS_REG))])
19031 (set (match_dup 0) (match_dup 1))]
19032 "operands[2] = gen_lowpart (SImode, operands[1]);")
19035 [(match_scratch:SI 2 "r")
19036 (set (match_operand:SI 0 "memory_operand" "")
19037 (match_operand:SI 1 "immediate_operand" ""))]
19039 && get_attr_length (insn) >= ix86_cost->large_insn
19040 && TARGET_SPLIT_LONG_MOVES"
19041 [(set (match_dup 2) (match_dup 1))
19042 (set (match_dup 0) (match_dup 2))]
19046 [(match_scratch:HI 2 "r")
19047 (set (match_operand:HI 0 "memory_operand" "")
19048 (match_operand:HI 1 "immediate_operand" ""))]
19049 "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
19050 && TARGET_SPLIT_LONG_MOVES"
19051 [(set (match_dup 2) (match_dup 1))
19052 (set (match_dup 0) (match_dup 2))]
19056 [(match_scratch:QI 2 "q")
19057 (set (match_operand:QI 0 "memory_operand" "")
19058 (match_operand:QI 1 "immediate_operand" ""))]
19059 "! optimize_size && get_attr_length (insn) >= ix86_cost->large_insn
19060 && TARGET_SPLIT_LONG_MOVES"
19061 [(set (match_dup 2) (match_dup 1))
19062 (set (match_dup 0) (match_dup 2))]
19065 ;; Don't compare memory with zero, load and use a test instead.
19067 [(set (match_operand 0 "flags_reg_operand" "")
19068 (match_operator 1 "compare_operator"
19069 [(match_operand:SI 2 "memory_operand" "")
19071 (match_scratch:SI 3 "r")]
19072 "ix86_match_ccmode (insn, CCNOmode) && ! optimize_size"
19073 [(set (match_dup 3) (match_dup 2))
19074 (set (match_dup 0) (match_op_dup 1 [(match_dup 3) (const_int 0)]))]
19077 ;; NOT is not pairable on Pentium, while XOR is, but one byte longer.
19078 ;; Don't split NOTs with a displacement operand, because resulting XOR
19079 ;; will not be pairable anyway.
19081 ;; On AMD K6, NOT is vector decoded with memory operand that cannot be
19082 ;; represented using a modRM byte. The XOR replacement is long decoded,
19083 ;; so this split helps here as well.
19085 ;; Note: Can't do this as a regular split because we can't get proper
19086 ;; lifetime information then.
19089 [(set (match_operand:SI 0 "nonimmediate_operand" "")
19090 (not:SI (match_operand:SI 1 "nonimmediate_operand" "")))]
19092 && peep2_regno_dead_p (0, FLAGS_REG)
19093 && ((TARGET_PENTIUM
19094 && (GET_CODE (operands[0]) != MEM
19095 || !memory_displacement_operand (operands[0], SImode)))
19096 || (TARGET_K6 && long_memory_operand (operands[0], SImode)))"
19097 [(parallel [(set (match_dup 0)
19098 (xor:SI (match_dup 1) (const_int -1)))
19099 (clobber (reg:CC FLAGS_REG))])]
19103 [(set (match_operand:HI 0 "nonimmediate_operand" "")
19104 (not:HI (match_operand:HI 1 "nonimmediate_operand" "")))]
19106 && peep2_regno_dead_p (0, FLAGS_REG)
19107 && ((TARGET_PENTIUM
19108 && (GET_CODE (operands[0]) != MEM
19109 || !memory_displacement_operand (operands[0], HImode)))
19110 || (TARGET_K6 && long_memory_operand (operands[0], HImode)))"
19111 [(parallel [(set (match_dup 0)
19112 (xor:HI (match_dup 1) (const_int -1)))
19113 (clobber (reg:CC FLAGS_REG))])]
19117 [(set (match_operand:QI 0 "nonimmediate_operand" "")
19118 (not:QI (match_operand:QI 1 "nonimmediate_operand" "")))]
19120 && peep2_regno_dead_p (0, FLAGS_REG)
19121 && ((TARGET_PENTIUM
19122 && (GET_CODE (operands[0]) != MEM
19123 || !memory_displacement_operand (operands[0], QImode)))
19124 || (TARGET_K6 && long_memory_operand (operands[0], QImode)))"
19125 [(parallel [(set (match_dup 0)
19126 (xor:QI (match_dup 1) (const_int -1)))
19127 (clobber (reg:CC FLAGS_REG))])]
19130 ;; Non pairable "test imm, reg" instructions can be translated to
19131 ;; "and imm, reg" if reg dies. The "and" form is also shorter (one
19132 ;; byte opcode instead of two, have a short form for byte operands),
19133 ;; so do it for other CPUs as well. Given that the value was dead,
19134 ;; this should not create any new dependencies. Pass on the sub-word
19135 ;; versions if we're concerned about partial register stalls.
19138 [(set (match_operand 0 "flags_reg_operand" "")
19139 (match_operator 1 "compare_operator"
19140 [(and:SI (match_operand:SI 2 "register_operand" "")
19141 (match_operand:SI 3 "immediate_operand" ""))
19143 "ix86_match_ccmode (insn, CCNOmode)
19144 && (true_regnum (operands[2]) != 0
19145 || (GET_CODE (operands[3]) == CONST_INT
19146 && CONST_OK_FOR_LETTER_P (INTVAL (operands[3]), 'K')))
19147 && peep2_reg_dead_p (1, operands[2])"
19149 [(set (match_dup 0)
19150 (match_op_dup 1 [(and:SI (match_dup 2) (match_dup 3))
19153 (and:SI (match_dup 2) (match_dup 3)))])]
19156 ;; We don't need to handle HImode case, because it will be promoted to SImode
19157 ;; on ! TARGET_PARTIAL_REG_STALL
19160 [(set (match_operand 0 "flags_reg_operand" "")
19161 (match_operator 1 "compare_operator"
19162 [(and:QI (match_operand:QI 2 "register_operand" "")
19163 (match_operand:QI 3 "immediate_operand" ""))
19165 "! TARGET_PARTIAL_REG_STALL
19166 && ix86_match_ccmode (insn, CCNOmode)
19167 && true_regnum (operands[2]) != 0
19168 && peep2_reg_dead_p (1, operands[2])"
19170 [(set (match_dup 0)
19171 (match_op_dup 1 [(and:QI (match_dup 2) (match_dup 3))
19174 (and:QI (match_dup 2) (match_dup 3)))])]
19178 [(set (match_operand 0 "flags_reg_operand" "")
19179 (match_operator 1 "compare_operator"
19182 (match_operand 2 "ext_register_operand" "")
19185 (match_operand 3 "const_int_operand" ""))
19187 "! TARGET_PARTIAL_REG_STALL
19188 && ix86_match_ccmode (insn, CCNOmode)
19189 && true_regnum (operands[2]) != 0
19190 && peep2_reg_dead_p (1, operands[2])"
19191 [(parallel [(set (match_dup 0)
19200 (set (zero_extract:SI (match_dup 2)
19211 ;; Don't do logical operations with memory inputs.
19213 [(match_scratch:SI 2 "r")
19214 (parallel [(set (match_operand:SI 0 "register_operand" "")
19215 (match_operator:SI 3 "arith_or_logical_operator"
19217 (match_operand:SI 1 "memory_operand" "")]))
19218 (clobber (reg:CC FLAGS_REG))])]
19219 "! optimize_size && ! TARGET_READ_MODIFY"
19220 [(set (match_dup 2) (match_dup 1))
19221 (parallel [(set (match_dup 0)
19222 (match_op_dup 3 [(match_dup 0) (match_dup 2)]))
19223 (clobber (reg:CC FLAGS_REG))])]
19227 [(match_scratch:SI 2 "r")
19228 (parallel [(set (match_operand:SI 0 "register_operand" "")
19229 (match_operator:SI 3 "arith_or_logical_operator"
19230 [(match_operand:SI 1 "memory_operand" "")
19232 (clobber (reg:CC FLAGS_REG))])]
19233 "! optimize_size && ! TARGET_READ_MODIFY"
19234 [(set (match_dup 2) (match_dup 1))
19235 (parallel [(set (match_dup 0)
19236 (match_op_dup 3 [(match_dup 2) (match_dup 0)]))
19237 (clobber (reg:CC FLAGS_REG))])]
19240 ; Don't do logical operations with memory outputs
19242 ; These two don't make sense for PPro/PII -- we're expanding a 4-uop
19243 ; instruction into two 1-uop insns plus a 2-uop insn. That last has
19244 ; the same decoder scheduling characteristics as the original.
19247 [(match_scratch:SI 2 "r")
19248 (parallel [(set (match_operand:SI 0 "memory_operand" "")
19249 (match_operator:SI 3 "arith_or_logical_operator"
19251 (match_operand:SI 1 "nonmemory_operand" "")]))
19252 (clobber (reg:CC FLAGS_REG))])]
19253 "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
19254 [(set (match_dup 2) (match_dup 0))
19255 (parallel [(set (match_dup 2)
19256 (match_op_dup 3 [(match_dup 2) (match_dup 1)]))
19257 (clobber (reg:CC FLAGS_REG))])
19258 (set (match_dup 0) (match_dup 2))]
19262 [(match_scratch:SI 2 "r")
19263 (parallel [(set (match_operand:SI 0 "memory_operand" "")
19264 (match_operator:SI 3 "arith_or_logical_operator"
19265 [(match_operand:SI 1 "nonmemory_operand" "")
19267 (clobber (reg:CC FLAGS_REG))])]
19268 "! optimize_size && ! TARGET_READ_MODIFY_WRITE"
19269 [(set (match_dup 2) (match_dup 0))
19270 (parallel [(set (match_dup 2)
19271 (match_op_dup 3 [(match_dup 1) (match_dup 2)]))
19272 (clobber (reg:CC FLAGS_REG))])
19273 (set (match_dup 0) (match_dup 2))]
19276 ;; Attempt to always use XOR for zeroing registers.
19278 [(set (match_operand 0 "register_operand" "")
19279 (match_operand 1 "const0_operand" ""))]
19280 "GET_MODE_SIZE (GET_MODE (operands[0])) <= UNITS_PER_WORD
19281 && (! TARGET_USE_MOV0 || optimize_size)
19282 && GENERAL_REG_P (operands[0])
19283 && peep2_regno_dead_p (0, FLAGS_REG)"
19284 [(parallel [(set (match_dup 0) (const_int 0))
19285 (clobber (reg:CC FLAGS_REG))])]
19287 operands[0] = gen_lowpart (word_mode, operands[0]);
19291 [(set (strict_low_part (match_operand 0 "register_operand" ""))
19293 "(GET_MODE (operands[0]) == QImode
19294 || GET_MODE (operands[0]) == HImode)
19295 && (! TARGET_USE_MOV0 || optimize_size)
19296 && peep2_regno_dead_p (0, FLAGS_REG)"
19297 [(parallel [(set (strict_low_part (match_dup 0)) (const_int 0))
19298 (clobber (reg:CC FLAGS_REG))])])
19300 ;; For HI and SI modes, or $-1,reg is smaller than mov $-1,reg.
19302 [(set (match_operand 0 "register_operand" "")
19304 "(GET_MODE (operands[0]) == HImode
19305 || GET_MODE (operands[0]) == SImode
19306 || (GET_MODE (operands[0]) == DImode && TARGET_64BIT))
19307 && (optimize_size || TARGET_PENTIUM)
19308 && peep2_regno_dead_p (0, FLAGS_REG)"
19309 [(parallel [(set (match_dup 0) (const_int -1))
19310 (clobber (reg:CC FLAGS_REG))])]
19311 "operands[0] = gen_lowpart (GET_MODE (operands[0]) == DImode ? DImode : SImode,
19314 ;; Attempt to convert simple leas to adds. These can be created by
19317 [(set (match_operand:SI 0 "register_operand" "")
19318 (plus:SI (match_dup 0)
19319 (match_operand:SI 1 "nonmemory_operand" "")))]
19320 "peep2_regno_dead_p (0, FLAGS_REG)"
19321 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 1)))
19322 (clobber (reg:CC FLAGS_REG))])]
19326 [(set (match_operand:SI 0 "register_operand" "")
19327 (subreg:SI (plus:DI (match_operand:DI 1 "register_operand" "")
19328 (match_operand:DI 2 "nonmemory_operand" "")) 0))]
19329 "peep2_regno_dead_p (0, FLAGS_REG) && REGNO (operands[0]) == REGNO (operands[1])"
19330 [(parallel [(set (match_dup 0) (plus:SI (match_dup 0) (match_dup 2)))
19331 (clobber (reg:CC FLAGS_REG))])]
19332 "operands[2] = gen_lowpart (SImode, operands[2]);")
19335 [(set (match_operand:DI 0 "register_operand" "")
19336 (plus:DI (match_dup 0)
19337 (match_operand:DI 1 "x86_64_general_operand" "")))]
19338 "peep2_regno_dead_p (0, FLAGS_REG)"
19339 [(parallel [(set (match_dup 0) (plus:DI (match_dup 0) (match_dup 1)))
19340 (clobber (reg:CC FLAGS_REG))])]
19344 [(set (match_operand:SI 0 "register_operand" "")
19345 (mult:SI (match_dup 0)
19346 (match_operand:SI 1 "const_int_operand" "")))]
19347 "exact_log2 (INTVAL (operands[1])) >= 0
19348 && peep2_regno_dead_p (0, FLAGS_REG)"
19349 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
19350 (clobber (reg:CC FLAGS_REG))])]
19351 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
19354 [(set (match_operand:DI 0 "register_operand" "")
19355 (mult:DI (match_dup 0)
19356 (match_operand:DI 1 "const_int_operand" "")))]
19357 "exact_log2 (INTVAL (operands[1])) >= 0
19358 && peep2_regno_dead_p (0, FLAGS_REG)"
19359 [(parallel [(set (match_dup 0) (ashift:DI (match_dup 0) (match_dup 2)))
19360 (clobber (reg:CC FLAGS_REG))])]
19361 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[1])));")
19364 [(set (match_operand:SI 0 "register_operand" "")
19365 (subreg:SI (mult:DI (match_operand:DI 1 "register_operand" "")
19366 (match_operand:DI 2 "const_int_operand" "")) 0))]
19367 "exact_log2 (INTVAL (operands[2])) >= 0
19368 && REGNO (operands[0]) == REGNO (operands[1])
19369 && peep2_regno_dead_p (0, FLAGS_REG)"
19370 [(parallel [(set (match_dup 0) (ashift:SI (match_dup 0) (match_dup 2)))
19371 (clobber (reg:CC FLAGS_REG))])]
19372 "operands[2] = GEN_INT (exact_log2 (INTVAL (operands[2])));")
19374 ;; The ESP adjustments can be done by the push and pop instructions. Resulting
19375 ;; code is shorter, since push is only 1 byte, while add imm, %esp 3 bytes. On
19376 ;; many CPUs it is also faster, since special hardware to avoid esp
19377 ;; dependencies is present.
19379 ;; While some of these conversions may be done using splitters, we use peepholes
19380 ;; in order to allow combine_stack_adjustments pass to see nonobfuscated RTL.
19382 ;; Convert prologue esp subtractions to push.
19383 ;; We need register to push. In order to keep verify_flow_info happy we have
19385 ;; - use scratch and clobber it in order to avoid dependencies
19386 ;; - use already live register
19387 ;; We can't use the second way right now, since there is no reliable way how to
19388 ;; verify that given register is live. First choice will also most likely in
19389 ;; fewer dependencies. On the place of esp adjustments it is very likely that
19390 ;; call clobbered registers are dead. We may want to use base pointer as an
19391 ;; alternative when no register is available later.
19394 [(match_scratch:SI 0 "r")
19395 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
19396 (clobber (reg:CC FLAGS_REG))
19397 (clobber (mem:BLK (scratch)))])]
19398 "optimize_size || !TARGET_SUB_ESP_4"
19399 [(clobber (match_dup 0))
19400 (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
19401 (clobber (mem:BLK (scratch)))])])
19404 [(match_scratch:SI 0 "r")
19405 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
19406 (clobber (reg:CC FLAGS_REG))
19407 (clobber (mem:BLK (scratch)))])]
19408 "optimize_size || !TARGET_SUB_ESP_8"
19409 [(clobber (match_dup 0))
19410 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
19411 (parallel [(set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
19412 (clobber (mem:BLK (scratch)))])])
19414 ;; Convert esp subtractions to push.
19416 [(match_scratch:SI 0 "r")
19417 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -4)))
19418 (clobber (reg:CC FLAGS_REG))])]
19419 "optimize_size || !TARGET_SUB_ESP_4"
19420 [(clobber (match_dup 0))
19421 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
19424 [(match_scratch:SI 0 "r")
19425 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int -8)))
19426 (clobber (reg:CC FLAGS_REG))])]
19427 "optimize_size || !TARGET_SUB_ESP_8"
19428 [(clobber (match_dup 0))
19429 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))
19430 (set (mem:SI (pre_dec:SI (reg:SI SP_REG))) (match_dup 0))])
19432 ;; Convert epilogue deallocator to pop.
19434 [(match_scratch:SI 0 "r")
19435 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19436 (clobber (reg:CC FLAGS_REG))
19437 (clobber (mem:BLK (scratch)))])]
19438 "optimize_size || !TARGET_ADD_ESP_4"
19439 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19440 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19441 (clobber (mem:BLK (scratch)))])]
19444 ;; Two pops case is tricky, since pop causes dependency on destination register.
19445 ;; We use two registers if available.
19447 [(match_scratch:SI 0 "r")
19448 (match_scratch:SI 1 "r")
19449 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19450 (clobber (reg:CC FLAGS_REG))
19451 (clobber (mem:BLK (scratch)))])]
19452 "optimize_size || !TARGET_ADD_ESP_8"
19453 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19454 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19455 (clobber (mem:BLK (scratch)))])
19456 (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
19457 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19461 [(match_scratch:SI 0 "r")
19462 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19463 (clobber (reg:CC FLAGS_REG))
19464 (clobber (mem:BLK (scratch)))])]
19466 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19467 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19468 (clobber (mem:BLK (scratch)))])
19469 (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19470 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19473 ;; Convert esp additions to pop.
19475 [(match_scratch:SI 0 "r")
19476 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))
19477 (clobber (reg:CC FLAGS_REG))])]
19479 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19480 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19483 ;; Two pops case is tricky, since pop causes dependency on destination register.
19484 ;; We use two registers if available.
19486 [(match_scratch:SI 0 "r")
19487 (match_scratch:SI 1 "r")
19488 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19489 (clobber (reg:CC FLAGS_REG))])]
19491 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19492 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
19493 (parallel [(set (match_dup 1) (mem:SI (reg:SI SP_REG)))
19494 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19498 [(match_scratch:SI 0 "r")
19499 (parallel [(set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 8)))
19500 (clobber (reg:CC FLAGS_REG))])]
19502 [(parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19503 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])
19504 (parallel [(set (match_dup 0) (mem:SI (reg:SI SP_REG)))
19505 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG) (const_int 4)))])]
19508 ;; Convert compares with 1 to shorter inc/dec operations when CF is not
19509 ;; required and register dies. Similarly for 128 to plus -128.
19511 [(set (match_operand 0 "flags_reg_operand" "")
19512 (match_operator 1 "compare_operator"
19513 [(match_operand 2 "register_operand" "")
19514 (match_operand 3 "const_int_operand" "")]))]
19515 "(INTVAL (operands[3]) == -1
19516 || INTVAL (operands[3]) == 1
19517 || INTVAL (operands[3]) == 128)
19518 && ix86_match_ccmode (insn, CCGCmode)
19519 && peep2_reg_dead_p (1, operands[2])"
19520 [(parallel [(set (match_dup 0)
19521 (match_op_dup 1 [(match_dup 2) (match_dup 3)]))
19522 (clobber (match_dup 2))])]
19526 [(match_scratch:DI 0 "r")
19527 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
19528 (clobber (reg:CC FLAGS_REG))
19529 (clobber (mem:BLK (scratch)))])]
19530 "optimize_size || !TARGET_SUB_ESP_4"
19531 [(clobber (match_dup 0))
19532 (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19533 (clobber (mem:BLK (scratch)))])])
19536 [(match_scratch:DI 0 "r")
19537 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
19538 (clobber (reg:CC FLAGS_REG))
19539 (clobber (mem:BLK (scratch)))])]
19540 "optimize_size || !TARGET_SUB_ESP_8"
19541 [(clobber (match_dup 0))
19542 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19543 (parallel [(set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19544 (clobber (mem:BLK (scratch)))])])
19546 ;; Convert esp subtractions to push.
19548 [(match_scratch:DI 0 "r")
19549 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -8)))
19550 (clobber (reg:CC FLAGS_REG))])]
19551 "optimize_size || !TARGET_SUB_ESP_4"
19552 [(clobber (match_dup 0))
19553 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
19556 [(match_scratch:DI 0 "r")
19557 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int -16)))
19558 (clobber (reg:CC FLAGS_REG))])]
19559 "optimize_size || !TARGET_SUB_ESP_8"
19560 [(clobber (match_dup 0))
19561 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))
19562 (set (mem:DI (pre_dec:DI (reg:DI SP_REG))) (match_dup 0))])
19564 ;; Convert epilogue deallocator to pop.
19566 [(match_scratch:DI 0 "r")
19567 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19568 (clobber (reg:CC FLAGS_REG))
19569 (clobber (mem:BLK (scratch)))])]
19570 "optimize_size || !TARGET_ADD_ESP_4"
19571 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19572 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19573 (clobber (mem:BLK (scratch)))])]
19576 ;; Two pops case is tricky, since pop causes dependency on destination register.
19577 ;; We use two registers if available.
19579 [(match_scratch:DI 0 "r")
19580 (match_scratch:DI 1 "r")
19581 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19582 (clobber (reg:CC FLAGS_REG))
19583 (clobber (mem:BLK (scratch)))])]
19584 "optimize_size || !TARGET_ADD_ESP_8"
19585 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19586 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19587 (clobber (mem:BLK (scratch)))])
19588 (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
19589 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19593 [(match_scratch:DI 0 "r")
19594 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19595 (clobber (reg:CC FLAGS_REG))
19596 (clobber (mem:BLK (scratch)))])]
19598 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19599 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19600 (clobber (mem:BLK (scratch)))])
19601 (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19602 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19605 ;; Convert esp additions to pop.
19607 [(match_scratch:DI 0 "r")
19608 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))
19609 (clobber (reg:CC FLAGS_REG))])]
19611 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19612 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19615 ;; Two pops case is tricky, since pop causes dependency on destination register.
19616 ;; We use two registers if available.
19618 [(match_scratch:DI 0 "r")
19619 (match_scratch:DI 1 "r")
19620 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19621 (clobber (reg:CC FLAGS_REG))])]
19623 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19624 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
19625 (parallel [(set (match_dup 1) (mem:DI (reg:DI SP_REG)))
19626 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19630 [(match_scratch:DI 0 "r")
19631 (parallel [(set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 16)))
19632 (clobber (reg:CC FLAGS_REG))])]
19634 [(parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19635 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])
19636 (parallel [(set (match_dup 0) (mem:DI (reg:DI SP_REG)))
19637 (set (reg:DI SP_REG) (plus:DI (reg:DI SP_REG) (const_int 8)))])]
19640 ;; Convert imul by three, five and nine into lea
19643 [(set (match_operand:SI 0 "register_operand" "")
19644 (mult:SI (match_operand:SI 1 "register_operand" "")
19645 (match_operand:SI 2 "const_int_operand" "")))
19646 (clobber (reg:CC FLAGS_REG))])]
19647 "INTVAL (operands[2]) == 3
19648 || INTVAL (operands[2]) == 5
19649 || INTVAL (operands[2]) == 9"
19650 [(set (match_dup 0)
19651 (plus:SI (mult:SI (match_dup 1) (match_dup 2))
19653 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19657 [(set (match_operand:SI 0 "register_operand" "")
19658 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
19659 (match_operand:SI 2 "const_int_operand" "")))
19660 (clobber (reg:CC FLAGS_REG))])]
19662 && (INTVAL (operands[2]) == 3
19663 || INTVAL (operands[2]) == 5
19664 || INTVAL (operands[2]) == 9)"
19665 [(set (match_dup 0) (match_dup 1))
19667 (plus:SI (mult:SI (match_dup 0) (match_dup 2))
19669 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19673 [(set (match_operand:DI 0 "register_operand" "")
19674 (mult:DI (match_operand:DI 1 "register_operand" "")
19675 (match_operand:DI 2 "const_int_operand" "")))
19676 (clobber (reg:CC FLAGS_REG))])]
19678 && (INTVAL (operands[2]) == 3
19679 || INTVAL (operands[2]) == 5
19680 || INTVAL (operands[2]) == 9)"
19681 [(set (match_dup 0)
19682 (plus:DI (mult:DI (match_dup 1) (match_dup 2))
19684 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19688 [(set (match_operand:DI 0 "register_operand" "")
19689 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
19690 (match_operand:DI 2 "const_int_operand" "")))
19691 (clobber (reg:CC FLAGS_REG))])]
19694 && (INTVAL (operands[2]) == 3
19695 || INTVAL (operands[2]) == 5
19696 || INTVAL (operands[2]) == 9)"
19697 [(set (match_dup 0) (match_dup 1))
19699 (plus:DI (mult:DI (match_dup 0) (match_dup 2))
19701 { operands[2] = GEN_INT (INTVAL (operands[2]) - 1); })
19703 ;; Imul $32bit_imm, mem, reg is vector decoded, while
19704 ;; imul $32bit_imm, reg, reg is direct decoded.
19706 [(match_scratch:DI 3 "r")
19707 (parallel [(set (match_operand:DI 0 "register_operand" "")
19708 (mult:DI (match_operand:DI 1 "memory_operand" "")
19709 (match_operand:DI 2 "immediate_operand" "")))
19710 (clobber (reg:CC FLAGS_REG))])]
19711 "TARGET_K8 && !optimize_size
19712 && (GET_CODE (operands[2]) != CONST_INT
19713 || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19714 [(set (match_dup 3) (match_dup 1))
19715 (parallel [(set (match_dup 0) (mult:DI (match_dup 3) (match_dup 2)))
19716 (clobber (reg:CC FLAGS_REG))])]
19720 [(match_scratch:SI 3 "r")
19721 (parallel [(set (match_operand:SI 0 "register_operand" "")
19722 (mult:SI (match_operand:SI 1 "memory_operand" "")
19723 (match_operand:SI 2 "immediate_operand" "")))
19724 (clobber (reg:CC FLAGS_REG))])]
19725 "TARGET_K8 && !optimize_size
19726 && (GET_CODE (operands[2]) != CONST_INT
19727 || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19728 [(set (match_dup 3) (match_dup 1))
19729 (parallel [(set (match_dup 0) (mult:SI (match_dup 3) (match_dup 2)))
19730 (clobber (reg:CC FLAGS_REG))])]
19734 [(match_scratch:SI 3 "r")
19735 (parallel [(set (match_operand:DI 0 "register_operand" "")
19737 (mult:SI (match_operand:SI 1 "memory_operand" "")
19738 (match_operand:SI 2 "immediate_operand" ""))))
19739 (clobber (reg:CC FLAGS_REG))])]
19740 "TARGET_K8 && !optimize_size
19741 && (GET_CODE (operands[2]) != CONST_INT
19742 || !CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K'))"
19743 [(set (match_dup 3) (match_dup 1))
19744 (parallel [(set (match_dup 0) (zero_extend:DI (mult:SI (match_dup 3) (match_dup 2))))
19745 (clobber (reg:CC FLAGS_REG))])]
19748 ;; imul $8/16bit_imm, regmem, reg is vector decoded.
19749 ;; Convert it into imul reg, reg
19750 ;; It would be better to force assembler to encode instruction using long
19751 ;; immediate, but there is apparently no way to do so.
19753 [(parallel [(set (match_operand:DI 0 "register_operand" "")
19754 (mult:DI (match_operand:DI 1 "nonimmediate_operand" "")
19755 (match_operand:DI 2 "const_int_operand" "")))
19756 (clobber (reg:CC FLAGS_REG))])
19757 (match_scratch:DI 3 "r")]
19758 "TARGET_K8 && !optimize_size
19759 && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')"
19760 [(set (match_dup 3) (match_dup 2))
19761 (parallel [(set (match_dup 0) (mult:DI (match_dup 0) (match_dup 3)))
19762 (clobber (reg:CC FLAGS_REG))])]
19764 if (!rtx_equal_p (operands[0], operands[1]))
19765 emit_move_insn (operands[0], operands[1]);
19769 [(parallel [(set (match_operand:SI 0 "register_operand" "")
19770 (mult:SI (match_operand:SI 1 "nonimmediate_operand" "")
19771 (match_operand:SI 2 "const_int_operand" "")))
19772 (clobber (reg:CC FLAGS_REG))])
19773 (match_scratch:SI 3 "r")]
19774 "TARGET_K8 && !optimize_size
19775 && CONST_OK_FOR_LETTER_P (INTVAL (operands[2]), 'K')"
19776 [(set (match_dup 3) (match_dup 2))
19777 (parallel [(set (match_dup 0) (mult:SI (match_dup 0) (match_dup 3)))
19778 (clobber (reg:CC FLAGS_REG))])]
19780 if (!rtx_equal_p (operands[0], operands[1]))
19781 emit_move_insn (operands[0], operands[1]);
19785 [(parallel [(set (match_operand:HI 0 "register_operand" "")
19786 (mult:HI (match_operand:HI 1 "nonimmediate_operand" "")
19787 (match_operand:HI 2 "immediate_operand" "")))
19788 (clobber (reg:CC FLAGS_REG))])
19789 (match_scratch:HI 3 "r")]
19790 "TARGET_K8 && !optimize_size"
19791 [(set (match_dup 3) (match_dup 2))
19792 (parallel [(set (match_dup 0) (mult:HI (match_dup 0) (match_dup 3)))
19793 (clobber (reg:CC FLAGS_REG))])]
19795 if (!rtx_equal_p (operands[0], operands[1]))
19796 emit_move_insn (operands[0], operands[1]);
19799 ;; After splitting up read-modify operations, array accesses with memory
19800 ;; operands might end up in form:
19802 ;; movl 4(%esp), %edx
19804 ;; instead of pre-splitting:
19806 ;; addl 4(%esp), %eax
19808 ;; movl 4(%esp), %edx
19809 ;; leal (%edx,%eax,4), %eax
19812 [(parallel [(set (match_operand 0 "register_operand" "")
19813 (ashift (match_operand 1 "register_operand" "")
19814 (match_operand 2 "const_int_operand" "")))
19815 (clobber (reg:CC FLAGS_REG))])
19816 (set (match_operand 3 "register_operand")
19817 (match_operand 4 "x86_64_general_operand" ""))
19818 (parallel [(set (match_operand 5 "register_operand" "")
19819 (plus (match_operand 6 "register_operand" "")
19820 (match_operand 7 "register_operand" "")))
19821 (clobber (reg:CC FLAGS_REG))])]
19822 "INTVAL (operands[2]) >= 0 && INTVAL (operands[2]) <= 3
19823 /* Validate MODE for lea. */
19824 && ((!TARGET_PARTIAL_REG_STALL
19825 && (GET_MODE (operands[0]) == QImode
19826 || GET_MODE (operands[0]) == HImode))
19827 || GET_MODE (operands[0]) == SImode
19828 || (TARGET_64BIT && GET_MODE (operands[0]) == DImode))
19829 /* We reorder load and the shift. */
19830 && !rtx_equal_p (operands[1], operands[3])
19831 && !reg_overlap_mentioned_p (operands[0], operands[4])
19832 /* Last PLUS must consist of operand 0 and 3. */
19833 && !rtx_equal_p (operands[0], operands[3])
19834 && (rtx_equal_p (operands[3], operands[6])
19835 || rtx_equal_p (operands[3], operands[7]))
19836 && (rtx_equal_p (operands[0], operands[6])
19837 || rtx_equal_p (operands[0], operands[7]))
19838 /* The intermediate operand 0 must die or be same as output. */
19839 && (rtx_equal_p (operands[0], operands[5])
19840 || peep2_reg_dead_p (3, operands[0]))"
19841 [(set (match_dup 3) (match_dup 4))
19842 (set (match_dup 0) (match_dup 1))]
19844 enum machine_mode mode = GET_MODE (operands[5]) == DImode ? DImode : SImode;
19845 int scale = 1 << INTVAL (operands[2]);
19846 rtx index = gen_lowpart (Pmode, operands[1]);
19847 rtx base = gen_lowpart (Pmode, operands[3]);
19848 rtx dest = gen_lowpart (mode, operands[5]);
19850 operands[1] = gen_rtx_PLUS (Pmode, base,
19851 gen_rtx_MULT (Pmode, index, GEN_INT (scale)));
19853 operands[1] = gen_rtx_SUBREG (mode, operands[1], 0);
19854 operands[0] = dest;
19857 ;; Call-value patterns last so that the wildcard operand does not
19858 ;; disrupt insn-recog's switch tables.
19860 (define_insn "*call_value_pop_0"
19861 [(set (match_operand 0 "" "")
19862 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
19863 (match_operand:SI 2 "" "")))
19864 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
19865 (match_operand:SI 3 "immediate_operand" "")))]
19868 if (SIBLING_CALL_P (insn))
19871 return "call\t%P1";
19873 [(set_attr "type" "callv")])
19875 (define_insn "*call_value_pop_1"
19876 [(set (match_operand 0 "" "")
19877 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
19878 (match_operand:SI 2 "" "")))
19879 (set (reg:SI SP_REG) (plus:SI (reg:SI SP_REG)
19880 (match_operand:SI 3 "immediate_operand" "i")))]
19883 if (constant_call_address_operand (operands[1], Pmode))
19885 if (SIBLING_CALL_P (insn))
19888 return "call\t%P1";
19890 if (SIBLING_CALL_P (insn))
19893 return "call\t%A1";
19895 [(set_attr "type" "callv")])
19897 (define_insn "*call_value_0"
19898 [(set (match_operand 0 "" "")
19899 (call (mem:QI (match_operand:SI 1 "constant_call_address_operand" ""))
19900 (match_operand:SI 2 "" "")))]
19903 if (SIBLING_CALL_P (insn))
19906 return "call\t%P1";
19908 [(set_attr "type" "callv")])
19910 (define_insn "*call_value_0_rex64"
19911 [(set (match_operand 0 "" "")
19912 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
19913 (match_operand:DI 2 "const_int_operand" "")))]
19916 if (SIBLING_CALL_P (insn))
19919 return "call\t%P1";
19921 [(set_attr "type" "callv")])
19923 (define_insn "*call_value_1"
19924 [(set (match_operand 0 "" "")
19925 (call (mem:QI (match_operand:SI 1 "call_insn_operand" "rsm"))
19926 (match_operand:SI 2 "" "")))]
19927 "!SIBLING_CALL_P (insn) && !TARGET_64BIT"
19929 if (constant_call_address_operand (operands[1], Pmode))
19930 return "call\t%P1";
19931 return "call\t%A1";
19933 [(set_attr "type" "callv")])
19935 (define_insn "*sibcall_value_1"
19936 [(set (match_operand 0 "" "")
19937 (call (mem:QI (match_operand:SI 1 "sibcall_insn_operand" "s,c,d,a"))
19938 (match_operand:SI 2 "" "")))]
19939 "SIBLING_CALL_P (insn) && !TARGET_64BIT"
19941 if (constant_call_address_operand (operands[1], Pmode))
19945 [(set_attr "type" "callv")])
19947 (define_insn "*call_value_1_rex64"
19948 [(set (match_operand 0 "" "")
19949 (call (mem:QI (match_operand:DI 1 "call_insn_operand" "rsm"))
19950 (match_operand:DI 2 "" "")))]
19951 "!SIBLING_CALL_P (insn) && TARGET_64BIT"
19953 if (constant_call_address_operand (operands[1], Pmode))
19954 return "call\t%P1";
19955 return "call\t%A1";
19957 [(set_attr "type" "callv")])
19959 (define_insn "*sibcall_value_1_rex64"
19960 [(set (match_operand 0 "" "")
19961 (call (mem:QI (match_operand:DI 1 "constant_call_address_operand" ""))
19962 (match_operand:DI 2 "" "")))]
19963 "SIBLING_CALL_P (insn) && TARGET_64BIT"
19965 [(set_attr "type" "callv")])
19967 (define_insn "*sibcall_value_1_rex64_v"
19968 [(set (match_operand 0 "" "")
19969 (call (mem:QI (reg:DI 40))
19970 (match_operand:DI 1 "" "")))]
19971 "SIBLING_CALL_P (insn) && TARGET_64BIT"
19973 [(set_attr "type" "callv")])
19975 ;; We used to use "int $5", in honor of #BR which maps to interrupt vector 5.
19976 ;; That, however, is usually mapped by the OS to SIGSEGV, which is often
19977 ;; caught for use by garbage collectors and the like. Using an insn that
19978 ;; maps to SIGILL makes it more likely the program will rightfully die.
19979 ;; Keeping with tradition, "6" is in honor of #UD.
19980 (define_insn "trap"
19981 [(trap_if (const_int 1) (const_int 6))]
19983 { return ASM_SHORT "0x0b0f"; }
19984 [(set_attr "length" "2")])
19986 (define_expand "sse_prologue_save"
19987 [(parallel [(set (match_operand:BLK 0 "" "")
19988 (unspec:BLK [(reg:DI 21)
19995 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
19996 (use (match_operand:DI 1 "register_operand" ""))
19997 (use (match_operand:DI 2 "immediate_operand" ""))
19998 (use (label_ref:DI (match_operand 3 "" "")))])]
20002 (define_insn "*sse_prologue_save_insn"
20003 [(set (mem:BLK (plus:DI (match_operand:DI 0 "register_operand" "R")
20004 (match_operand:DI 4 "const_int_operand" "n")))
20005 (unspec:BLK [(reg:DI 21)
20012 (reg:DI 28)] UNSPEC_SSE_PROLOGUE_SAVE))
20013 (use (match_operand:DI 1 "register_operand" "r"))
20014 (use (match_operand:DI 2 "const_int_operand" "i"))
20015 (use (label_ref:DI (match_operand 3 "" "X")))]
20017 && INTVAL (operands[4]) + SSE_REGPARM_MAX * 16 - 16 < 128
20018 && INTVAL (operands[4]) + INTVAL (operands[2]) * 16 >= -128"
20022 operands[0] = gen_rtx_MEM (Pmode,
20023 gen_rtx_PLUS (Pmode, operands[0], operands[4]));
20024 output_asm_insn (\"jmp\\t%A1\", operands);
20025 for (i = SSE_REGPARM_MAX - 1; i >= INTVAL (operands[2]); i--)
20027 operands[4] = adjust_address (operands[0], DImode, i*16);
20028 operands[5] = gen_rtx_REG (TImode, SSE_REGNO (i));
20029 PUT_MODE (operands[4], TImode);
20030 if (GET_CODE (XEXP (operands[0], 0)) != PLUS)
20031 output_asm_insn (\"rex\", operands);
20032 output_asm_insn (\"movaps\\t{%5, %4|%4, %5}\", operands);
20034 (*targetm.asm_out.internal_label) (asm_out_file, \"L\",
20035 CODE_LABEL_NUMBER (operands[3]));
20039 [(set_attr "type" "other")
20040 (set_attr "length_immediate" "0")
20041 (set_attr "length_address" "0")
20042 (set_attr "length" "135")
20043 (set_attr "memory" "store")
20044 (set_attr "modrm" "0")
20045 (set_attr "mode" "DI")])
20047 (define_expand "prefetch"
20048 [(prefetch (match_operand 0 "address_operand" "")
20049 (match_operand:SI 1 "const_int_operand" "")
20050 (match_operand:SI 2 "const_int_operand" ""))]
20051 "TARGET_PREFETCH_SSE || TARGET_3DNOW"
20053 int rw = INTVAL (operands[1]);
20054 int locality = INTVAL (operands[2]);
20056 gcc_assert (rw == 0 || rw == 1);
20057 gcc_assert (locality >= 0 && locality <= 3);
20058 gcc_assert (GET_MODE (operands[0]) == Pmode
20059 || GET_MODE (operands[0]) == VOIDmode);
20061 /* Use 3dNOW prefetch in case we are asking for write prefetch not
20062 supported by SSE counterpart or the SSE prefetch is not available
20063 (K6 machines). Otherwise use SSE prefetch as it allows specifying
20065 if (TARGET_3DNOW && (!TARGET_PREFETCH_SSE || rw))
20066 operands[2] = GEN_INT (3);
20068 operands[1] = const0_rtx;
20071 (define_insn "*prefetch_sse"
20072 [(prefetch (match_operand:SI 0 "address_operand" "p")
20074 (match_operand:SI 1 "const_int_operand" ""))]
20075 "TARGET_PREFETCH_SSE && !TARGET_64BIT"
20077 static const char * const patterns[4] = {
20078 "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
20081 int locality = INTVAL (operands[1]);
20082 gcc_assert (locality >= 0 && locality <= 3);
20084 return patterns[locality];
20086 [(set_attr "type" "sse")
20087 (set_attr "memory" "none")])
20089 (define_insn "*prefetch_sse_rex"
20090 [(prefetch (match_operand:DI 0 "address_operand" "p")
20092 (match_operand:SI 1 "const_int_operand" ""))]
20093 "TARGET_PREFETCH_SSE && TARGET_64BIT"
20095 static const char * const patterns[4] = {
20096 "prefetchnta\t%a0", "prefetcht2\t%a0", "prefetcht1\t%a0", "prefetcht0\t%a0"
20099 int locality = INTVAL (operands[1]);
20100 gcc_assert (locality >= 0 && locality <= 3);
20102 return patterns[locality];
20104 [(set_attr "type" "sse")
20105 (set_attr "memory" "none")])
20107 (define_insn "*prefetch_3dnow"
20108 [(prefetch (match_operand:SI 0 "address_operand" "p")
20109 (match_operand:SI 1 "const_int_operand" "n")
20111 "TARGET_3DNOW && !TARGET_64BIT"
20113 if (INTVAL (operands[1]) == 0)
20114 return "prefetch\t%a0";
20116 return "prefetchw\t%a0";
20118 [(set_attr "type" "mmx")
20119 (set_attr "memory" "none")])
20121 (define_insn "*prefetch_3dnow_rex"
20122 [(prefetch (match_operand:DI 0 "address_operand" "p")
20123 (match_operand:SI 1 "const_int_operand" "n")
20125 "TARGET_3DNOW && TARGET_64BIT"
20127 if (INTVAL (operands[1]) == 0)
20128 return "prefetch\t%a0";
20130 return "prefetchw\t%a0";
20132 [(set_attr "type" "mmx")
20133 (set_attr "memory" "none")])
20135 (define_expand "stack_protect_set"
20136 [(match_operand 0 "memory_operand" "")
20137 (match_operand 1 "memory_operand" "")]
20140 #ifdef TARGET_THREAD_SSP_OFFSET
20142 emit_insn (gen_stack_tls_protect_set_di (operands[0],
20143 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
20145 emit_insn (gen_stack_tls_protect_set_si (operands[0],
20146 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
20149 emit_insn (gen_stack_protect_set_di (operands[0], operands[1]));
20151 emit_insn (gen_stack_protect_set_si (operands[0], operands[1]));
20156 (define_insn "stack_protect_set_si"
20157 [(set (match_operand:SI 0 "memory_operand" "=m")
20158 (unspec:SI [(match_operand:SI 1 "memory_operand" "m")] UNSPEC_SP_SET))
20159 (set (match_scratch:SI 2 "=&r") (const_int 0))
20160 (clobber (reg:CC FLAGS_REG))]
20162 "mov{l}\t{%1, %2|%2, %1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
20163 [(set_attr "type" "multi")])
20165 (define_insn "stack_protect_set_di"
20166 [(set (match_operand:DI 0 "memory_operand" "=m")
20167 (unspec:DI [(match_operand:DI 1 "memory_operand" "m")] UNSPEC_SP_SET))
20168 (set (match_scratch:DI 2 "=&r") (const_int 0))
20169 (clobber (reg:CC FLAGS_REG))]
20171 "mov{q}\t{%1, %2|%2, %1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
20172 [(set_attr "type" "multi")])
20174 (define_insn "stack_tls_protect_set_si"
20175 [(set (match_operand:SI 0 "memory_operand" "=m")
20176 (unspec:SI [(match_operand:SI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
20177 (set (match_scratch:SI 2 "=&r") (const_int 0))
20178 (clobber (reg:CC FLAGS_REG))]
20180 "mov{l}\t{%%gs:%P1, %2|%2, DWORD PTR %%gs:%P1}\;mov{l}\t{%2, %0|%0, %2}\;xor{l}\t%2, %2"
20181 [(set_attr "type" "multi")])
20183 (define_insn "stack_tls_protect_set_di"
20184 [(set (match_operand:DI 0 "memory_operand" "=m")
20185 (unspec:DI [(match_operand:DI 1 "const_int_operand" "i")] UNSPEC_SP_TLS_SET))
20186 (set (match_scratch:DI 2 "=&r") (const_int 0))
20187 (clobber (reg:CC FLAGS_REG))]
20189 "mov{q}\t{%%fs:%P1, %2|%2, QWORD PTR %%fs:%P1}\;mov{q}\t{%2, %0|%0, %2}\;xor{l}\t%k2, %k2"
20190 [(set_attr "type" "multi")])
20192 (define_expand "stack_protect_test"
20193 [(match_operand 0 "memory_operand" "")
20194 (match_operand 1 "memory_operand" "")
20195 (match_operand 2 "" "")]
20198 rtx flags = gen_rtx_REG (CCZmode, FLAGS_REG);
20199 ix86_compare_op0 = operands[0];
20200 ix86_compare_op1 = operands[1];
20201 ix86_compare_emitted = flags;
20203 #ifdef TARGET_THREAD_SSP_OFFSET
20205 emit_insn (gen_stack_tls_protect_test_di (flags, operands[0],
20206 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
20208 emit_insn (gen_stack_tls_protect_test_si (flags, operands[0],
20209 GEN_INT (TARGET_THREAD_SSP_OFFSET)));
20212 emit_insn (gen_stack_protect_test_di (flags, operands[0], operands[1]));
20214 emit_insn (gen_stack_protect_test_si (flags, operands[0], operands[1]));
20216 emit_jump_insn (gen_beq (operands[2]));
20220 (define_insn "stack_protect_test_si"
20221 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
20222 (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
20223 (match_operand:SI 2 "memory_operand" "m")]
20225 (clobber (match_scratch:SI 3 "=&r"))]
20227 "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%2, %3|%3, %2}"
20228 [(set_attr "type" "multi")])
20230 (define_insn "stack_protect_test_di"
20231 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
20232 (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
20233 (match_operand:DI 2 "memory_operand" "m")]
20235 (clobber (match_scratch:DI 3 "=&r"))]
20237 "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%2, %3|%3, %2}"
20238 [(set_attr "type" "multi")])
20240 (define_insn "stack_tls_protect_test_si"
20241 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
20242 (unspec:CCZ [(match_operand:SI 1 "memory_operand" "m")
20243 (match_operand:SI 2 "const_int_operand" "i")]
20244 UNSPEC_SP_TLS_TEST))
20245 (clobber (match_scratch:SI 3 "=r"))]
20247 "mov{l}\t{%1, %3|%3, %1}\;xor{l}\t{%%gs:%P2, %3|%3, DWORD PTR %%gs:%P2}"
20248 [(set_attr "type" "multi")])
20250 (define_insn "stack_tls_protect_test_di"
20251 [(set (match_operand:CCZ 0 "flags_reg_operand" "")
20252 (unspec:CCZ [(match_operand:DI 1 "memory_operand" "m")
20253 (match_operand:DI 2 "const_int_operand" "i")]
20254 UNSPEC_SP_TLS_TEST))
20255 (clobber (match_scratch:DI 3 "=r"))]
20257 "mov{q}\t{%1, %3|%3, %1}\;xor{q}\t{%%fs:%P2, %3|%3, QWORD PTR %%fs:%P2}"
20258 [(set_attr "type" "multi")])
20262 (include "sync.md")