1 ;; Machine description for IBM RISC System 6000 (POWER) for GNU C compiler
2 ;; Copyright (C) 1990-2015 Free Software Foundation, Inc.
3 ;; Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu)
5 ;; This file is part of GCC.
7 ;; GCC is free software; you can redistribute it and/or modify it
8 ;; under the terms of the GNU General Public License as published
9 ;; by the Free Software Foundation; either version 3, or (at your
10 ;; option) any later version.
12 ;; GCC is distributed in the hope that it will be useful, but WITHOUT
13 ;; ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
14 ;; or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
15 ;; License for more details.
17 ;; You should have received a copy of the GNU General Public License
18 ;; along with GCC; see the file COPYING3. If not see
19 ;; <http://www.gnu.org/licenses/>.
21 ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al.
29 (STACK_POINTER_REGNUM 1)
31 (STATIC_CHAIN_REGNUM 11)
32 (HARD_FRAME_POINTER_REGNUM 31)
38 (ARG_POINTER_REGNUM 67)
49 (FIRST_ALTIVEC_REGNO 77)
50 (LAST_ALTIVEC_REGNO 108)
55 (FRAME_POINTER_REGNUM 113)
59 (FIRST_SPE_HIGH_REGNO 117)
60 (LAST_SPE_HIGH_REGNO 148)
67 (define_c_enum "unspec"
68 [UNSPEC_FRSP ; frsp for POWER machines
69 UNSPEC_PROBE_STACK ; probe stack memory reference
70 UNSPEC_TOCPTR ; address of a word pointing to the TOC
71 UNSPEC_TOC ; address of the TOC (more-or-less)
72 UNSPEC_TOCSLOT ; offset from r1 of toc pointer save slot
74 UNSPEC_MV_CR_OV ; move_from_CR_ov_bit
80 UNSPEC_LD_MPIC ; load_macho_picbase
81 UNSPEC_RELD_MPIC ; re-load_macho_picbase
82 UNSPEC_MPIC_CORRECT ; macho_correct_pic
96 UNSPEC_FIX_TRUNC_TF ; fadd, rounding towards zero
97 UNSPEC_MV_CR_GT ; move_from_CR_gt_bit
115 UNSPEC_MACHOPIC_OFFSET
128 UNSPEC_P8V_RELOAD_FROM_GPR
131 UNSPEC_P8V_RELOAD_FROM_VSX
146 ;; UNSPEC_VOLATILE usage
149 (define_c_enum "unspecv"
151 UNSPECV_LL ; load-locked
152 UNSPECV_SC ; store-conditional
153 UNSPECV_PROBE_STACK_RANGE ; probe range of stack addresses
154 UNSPECV_EH_RR ; eh_reg_restore
155 UNSPECV_ISYNC ; isync instruction
156 UNSPECV_MFTB ; move from time base
157 UNSPECV_NLGR ; non-local goto receiver
158 UNSPECV_MFFS ; Move from FPSCR
159 UNSPECV_MTFSF ; Move to FPSCR Fields
163 ;; Define an insn type attribute. This is used in function unit delay
167 add,logical,shift,insert,
169 exts,cntlz,popcnt,isel,
170 load,store,fpload,fpstore,vecload,vecstore,
172 branch,jmpreg,mfjmpr,mtjmpr,trap,isync,sync,load_l,store_c,
173 cr_logical,delayed_cr,mfcr,mfcrf,mtcr,
174 fpcompare,fp,fpsimple,dmul,sdiv,ddiv,ssqrt,dsqrt,
176 vecsimple,veccomplex,vecdiv,veccmp,veccmpsimple,vecperm,
177 vecfloat,vecfdiv,vecdouble,mffgpr,mftgpr,crypto,
179 (const_string "integer"))
181 ;; What data size does this instruction work on?
182 ;; This is used for insert, mul.
183 (define_attr "size" "8,16,32,64" (const_string "32"))
185 ;; Is this instruction record form ("dot", signed compare to 0, writing CR0)?
186 ;; This is used for add, logical, shift, exts, mul.
187 (define_attr "dot" "no,yes" (const_string "no"))
189 ;; Does this instruction sign-extend its result?
190 ;; This is used for load insns.
191 (define_attr "sign_extend" "no,yes" (const_string "no"))
193 ;; Does this instruction use indexed (that is, reg+reg) addressing?
194 ;; This is used for load and store insns. If operand 0 or 1 is a MEM
195 ;; it is automatically set based on that. If a load or store instruction
196 ;; has fewer than two operands it needs to set this attribute manually
197 ;; or the compiler will crash.
198 (define_attr "indexed" "no,yes"
199 (if_then_else (ior (match_operand 0 "indexed_address_mem")
200 (match_operand 1 "indexed_address_mem"))
202 (const_string "no")))
204 ;; Does this instruction use update addressing?
205 ;; This is used for load and store insns. See the comments for "indexed".
206 (define_attr "update" "no,yes"
207 (if_then_else (ior (match_operand 0 "update_address_mem")
208 (match_operand 1 "update_address_mem"))
210 (const_string "no")))
212 ;; Is this instruction using operands[2] as shift amount, and can that be a
214 ;; This is used for shift insns.
215 (define_attr "maybe_var_shift" "no,yes" (const_string "no"))
217 ;; Is this instruction using a shift amount from a register?
218 ;; This is used for shift insns.
219 (define_attr "var_shift" "no,yes"
220 (if_then_else (and (eq_attr "type" "shift")
221 (eq_attr "maybe_var_shift" "yes"))
222 (if_then_else (match_operand 2 "gpc_reg_operand")
225 (const_string "no")))
227 ;; Define floating point instruction sub-types for use with Xfpu.md
228 (define_attr "fp_type" "fp_default,fp_addsub_s,fp_addsub_d,fp_mul_s,fp_mul_d,fp_div_s,fp_div_d,fp_maddsub_s,fp_maddsub_d,fp_sqrt_s,fp_sqrt_d" (const_string "fp_default"))
230 ;; Length (in bytes).
231 ; '(pc)' in the following doesn't include the instruction itself; it is
232 ; calculated as if the instruction had zero size.
233 (define_attr "length" ""
234 (if_then_else (eq_attr "type" "branch")
235 (if_then_else (and (ge (minus (match_dup 0) (pc))
237 (lt (minus (match_dup 0) (pc))
243 ;; Processor type -- this attribute must exactly match the processor_type
244 ;; enumeration in rs6000-opts.h.
246 "ppc601,ppc603,ppc604,ppc604e,ppc620,ppc630,
247 ppc750,ppc7400,ppc7450,
248 ppc403,ppc405,ppc440,ppc476,
249 ppc8540,ppc8548,ppce300c2,ppce300c3,ppce500mc,ppce500mc64,ppce5500,ppce6500,
250 power4,power5,power6,power7,power8,
251 rs64a,mpccore,cell,ppca2,titan"
252 (const (symbol_ref "rs6000_cpu_attr")))
255 ;; If this instruction is microcoded on the CELL processor
256 ; The default for load extended, the recorded instructions and rotate/shifts by a variable is always microcoded
257 (define_attr "cell_micro" "not,conditional,always"
258 (if_then_else (ior (and (eq_attr "type" "shift,exts,mul")
259 (eq_attr "dot" "yes"))
260 (and (eq_attr "type" "load")
261 (eq_attr "sign_extend" "yes"))
262 (and (eq_attr "type" "shift")
263 (eq_attr "var_shift" "yes")))
264 (const_string "always")
265 (const_string "not")))
267 (automata_option "ndfa")
280 (include "e300c2c3.md")
281 (include "e500mc.md")
282 (include "e500mc64.md")
285 (include "power4.md")
286 (include "power5.md")
287 (include "power6.md")
288 (include "power7.md")
289 (include "power8.md")
295 (include "predicates.md")
296 (include "constraints.md")
298 (include "darwin.md")
303 ; This mode iterator allows :GPR to be used to indicate the allowable size
304 ; of whole values in GPRs.
305 (define_mode_iterator GPR [SI (DI "TARGET_POWERPC64")])
307 ; Any supported integer mode.
308 (define_mode_iterator INT [QI HI SI DI TI PTI])
310 ; Any supported integer mode that fits in one register.
311 (define_mode_iterator INT1 [QI HI SI (DI "TARGET_POWERPC64")])
313 ; Everything we can extend QImode to.
314 (define_mode_iterator EXTQI [HI SI (DI "TARGET_POWERPC64")])
316 ; Everything we can extend HImode to.
317 (define_mode_iterator EXTHI [SI (DI "TARGET_POWERPC64")])
319 ; Everything we can extend SImode to.
320 (define_mode_iterator EXTSI [(DI "TARGET_POWERPC64")])
322 ; QImode or HImode for small atomic ops
323 (define_mode_iterator QHI [QI HI])
325 ; HImode or SImode for sign extended fusion ops
326 (define_mode_iterator HSI [HI SI])
328 ; SImode or DImode, even if DImode doesn't fit in GPRs.
329 (define_mode_iterator SDI [SI DI])
331 ; The size of a pointer. Also, the size of the value that a record-condition
332 ; (one with a '.') will compare; and the size used for arithmetic carries.
333 (define_mode_iterator P [(SI "TARGET_32BIT") (DI "TARGET_64BIT")])
335 ; Iterator to add PTImode along with TImode (TImode can go in VSX registers,
336 ; PTImode is GPR only)
337 (define_mode_iterator TI2 [TI PTI])
339 ; Any hardware-supported floating-point mode
340 (define_mode_iterator FP [
341 (SF "TARGET_HARD_FLOAT
342 && ((TARGET_FPRS && TARGET_SINGLE_FLOAT) || TARGET_E500_SINGLE)")
343 (DF "TARGET_HARD_FLOAT
344 && ((TARGET_FPRS && TARGET_DOUBLE_FLOAT) || TARGET_E500_DOUBLE)")
345 (TF "!TARGET_IEEEQUAD
347 && (TARGET_FPRS || TARGET_E500_DOUBLE)
348 && TARGET_LONG_DOUBLE_128")
352 ; Any fma capable floating-point mode.
353 (define_mode_iterator FMA_F [
354 (SF "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT")
355 (DF "(TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT)
356 || VECTOR_UNIT_VSX_P (DFmode)")
357 (V2SF "TARGET_PAIRED_FLOAT")
358 (V4SF "VECTOR_UNIT_ALTIVEC_OR_VSX_P (V4SFmode)")
359 (V2DF "VECTOR_UNIT_ALTIVEC_OR_VSX_P (V2DFmode)")
362 ; Floating point move iterators to combine binary and decimal moves
363 (define_mode_iterator FMOVE32 [SF SD])
364 (define_mode_iterator FMOVE64 [DF DD])
365 (define_mode_iterator FMOVE64X [DI DF DD])
366 (define_mode_iterator FMOVE128 [(TF "!TARGET_IEEEQUAD && TARGET_LONG_DOUBLE_128")
367 (TD "TARGET_HARD_FLOAT && TARGET_FPRS")])
369 ; Iterators for 128 bit types for direct move
370 (define_mode_iterator FMOVE128_GPR [(TI "TARGET_VSX_TIMODE")
379 ; Whether a floating point move is ok, don't allow SD without hardware FP
380 (define_mode_attr fmove_ok [(SF "")
382 (SD "TARGET_HARD_FLOAT && TARGET_FPRS")
385 ; Convert REAL_VALUE to the appropriate bits
386 (define_mode_attr real_value_to_target [(SF "REAL_VALUE_TO_TARGET_SINGLE")
387 (DF "REAL_VALUE_TO_TARGET_DOUBLE")
388 (SD "REAL_VALUE_TO_TARGET_DECIMAL32")
389 (DD "REAL_VALUE_TO_TARGET_DECIMAL64")])
391 ; Definitions for load to 32-bit fpr register
392 (define_mode_attr f32_lr [(SF "f") (SD "wz")])
393 (define_mode_attr f32_lm [(SF "m") (SD "Z")])
394 (define_mode_attr f32_li [(SF "lfs%U1%X1 %0,%1") (SD "lfiwzx %0,%y1")])
395 (define_mode_attr f32_lv [(SF "lxsspx %x0,%y1") (SD "lxsiwzx %x0,%y1")])
397 ; Definitions for store from 32-bit fpr register
398 (define_mode_attr f32_sr [(SF "f") (SD "wx")])
399 (define_mode_attr f32_sm [(SF "m") (SD "Z")])
400 (define_mode_attr f32_si [(SF "stfs%U0%X0 %1,%0") (SD "stfiwx %1,%y0")])
401 (define_mode_attr f32_sv [(SF "stxsspx %x1,%y0") (SD "stxsiwzx %x1,%y0")])
403 ; Definitions for 32-bit fpr direct move
404 ; At present, the decimal modes are not allowed in the traditional altivec
405 ; registers, so restrict the constraints to just the traditional FPRs.
406 (define_mode_attr f32_dm [(SF "wn") (SD "wh")])
408 ; Definitions for 32-bit VSX
409 (define_mode_attr f32_vsx [(SF "ww") (SD "wn")])
411 ; Definitions for 32-bit use of altivec registers
412 (define_mode_attr f32_av [(SF "wu") (SD "wn")])
414 ; Definitions for 64-bit VSX
415 (define_mode_attr f64_vsx [(DF "ws") (DD "wn")])
417 ; Definitions for 64-bit direct move
418 (define_mode_attr f64_dm [(DF "wk") (DD "wh")])
420 ; Definitions for 64-bit use of altivec registers
421 (define_mode_attr f64_av [(DF "wv") (DD "wn")])
423 ; These modes do not fit in integer registers in 32-bit mode.
424 ; but on e500v2, the gpr are 64 bit registers
425 (define_mode_iterator DIFD [DI (DF "!TARGET_E500_DOUBLE") DD])
427 ; Iterator for reciprocal estimate instructions
428 (define_mode_iterator RECIPF [SF DF V4SF V2DF])
430 ; Iterator for just SF/DF
431 (define_mode_iterator SFDF [SF DF])
433 ; SF/DF suffix for traditional floating instructions
434 (define_mode_attr Ftrad [(SF "s") (DF "")])
436 ; SF/DF suffix for VSX instructions
437 (define_mode_attr Fvsx [(SF "sp") (DF "dp")])
439 ; SF/DF constraint for arithmetic on traditional floating point registers
440 (define_mode_attr Ff [(SF "f") (DF "d")])
442 ; SF/DF constraint for arithmetic on VSX registers
443 (define_mode_attr Fv [(SF "wy") (DF "ws")])
445 ; SF/DF constraint for arithmetic on altivec registers
446 (define_mode_attr Fa [(SF "wu") (DF "wv")])
448 ; s/d suffix for things like fp_addsub_s/fp_addsub_d
449 (define_mode_attr Fs [(SF "s") (DF "d")])
452 (define_mode_attr Ffre [(SF "fres") (DF "fre")])
453 (define_mode_attr FFRE [(SF "FRES") (DF "FRE")])
455 ; Conditional returns.
456 (define_code_iterator any_return [return simple_return])
457 (define_code_attr return_pred [(return "direct_return ()")
458 (simple_return "1")])
459 (define_code_attr return_str [(return "") (simple_return "simple_")])
462 (define_code_iterator iorxor [ior xor])
464 ; Signed/unsigned variants of ops.
465 (define_code_iterator any_extend [sign_extend zero_extend])
466 (define_code_attr u [(sign_extend "") (zero_extend "u")])
467 (define_code_attr su [(sign_extend "s") (zero_extend "u")])
469 ; Various instructions that come in SI and DI forms.
470 ; A generic w/d attribute, for things like cmpw/cmpd.
471 (define_mode_attr wd [(QI "b")
480 ;; How many bits in this mode?
481 (define_mode_attr bits [(QI "8") (HI "16") (SI "32") (DI "64")])
484 (define_mode_attr dbits [(QI "56") (HI "48") (SI "32")])
486 ;; ISEL/ISEL64 target selection
487 (define_mode_attr sel [(SI "") (DI "64")])
489 ;; Bitmask for shift instructions
490 (define_mode_attr hH [(SI "h") (DI "H")])
492 ;; A mode twice the size of the given mode
493 (define_mode_attr dmode [(SI "di") (DI "ti")])
494 (define_mode_attr DMODE [(SI "DI") (DI "TI")])
496 ;; Suffix for reload patterns
497 (define_mode_attr ptrsize [(SI "32bit")
500 (define_mode_attr tptrsize [(SI "TARGET_32BIT")
501 (DI "TARGET_64BIT")])
503 (define_mode_attr mptrsize [(SI "si")
506 (define_mode_attr ptrload [(SI "lwz")
509 (define_mode_attr ptrm [(SI "m")
512 (define_mode_attr rreg [(SF "f")
519 (define_mode_attr rreg2 [(SF "f")
522 (define_mode_attr SI_CONVERT_FP [(SF "TARGET_FCFIDS")
523 (DF "TARGET_FCFID")])
525 (define_mode_attr E500_CONVERT [(SF "!TARGET_FPRS")
526 (DF "TARGET_E500_DOUBLE")])
528 (define_mode_attr TARGET_FLOAT [(SF "TARGET_SINGLE_FLOAT")
529 (DF "TARGET_DOUBLE_FLOAT")])
531 ;; Mode iterator for logical operations on 128-bit types
532 (define_mode_iterator BOOL_128 [TI
534 (V16QI "TARGET_ALTIVEC")
535 (V8HI "TARGET_ALTIVEC")
536 (V4SI "TARGET_ALTIVEC")
537 (V4SF "TARGET_ALTIVEC")
538 (V2DI "TARGET_ALTIVEC")
539 (V2DF "TARGET_ALTIVEC")
540 (V1TI "TARGET_ALTIVEC")])
542 ;; For the GPRs we use 3 constraints for register outputs, two that are the
543 ;; same as the output register, and a third where the output register is an
544 ;; early clobber, so we don't have to deal with register overlaps. For the
545 ;; vector types, we prefer to use the vector registers. For TI mode, allow
548 ;; Mode attribute for boolean operation register constraints for output
549 (define_mode_attr BOOL_REGS_OUTPUT [(TI "&r,r,r,wt,v")
551 (V16QI "wa,v,&?r,?r,?r")
552 (V8HI "wa,v,&?r,?r,?r")
553 (V4SI "wa,v,&?r,?r,?r")
554 (V4SF "wa,v,&?r,?r,?r")
555 (V2DI "wa,v,&?r,?r,?r")
556 (V2DF "wa,v,&?r,?r,?r")
557 (V1TI "wa,v,&?r,?r,?r")])
559 ;; Mode attribute for boolean operation register constraints for operand1
560 (define_mode_attr BOOL_REGS_OP1 [(TI "r,0,r,wt,v")
568 (V1TI "wa,v,r,0,r")])
570 ;; Mode attribute for boolean operation register constraints for operand2
571 (define_mode_attr BOOL_REGS_OP2 [(TI "r,r,0,wt,v")
579 (V1TI "wa,v,r,r,0")])
581 ;; Mode attribute for boolean operation register constraints for operand1
582 ;; for one_cmpl. To simplify things, we repeat the constraint where 0
583 ;; is used for operand1 or operand2
584 (define_mode_attr BOOL_REGS_UNARY [(TI "r,0,0,wt,v")
592 (V1TI "wa,v,r,0,0")])
594 ;; Reload iterator for creating the function to allocate a base register to
595 ;; supplement addressing modes.
596 (define_mode_iterator RELOAD [V16QI V8HI V4SI V2DI V4SF V2DF V1TI
597 SF SD SI DF DD DI TI PTI])
600 ;; Start with fixed-point load and store insns. Here we put only the more
601 ;; complex forms. Basic data transfer is done later.
603 (define_insn "zero_extendqi<mode>2"
604 [(set (match_operand:EXTQI 0 "gpc_reg_operand" "=r,r")
605 (zero_extend:EXTQI (match_operand:QI 1 "reg_or_mem_operand" "m,r")))]
610 [(set_attr "type" "load,shift")])
612 (define_insn_and_split "*zero_extendqi<mode>2_dot"
613 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
614 (compare:CC (zero_extend:EXTQI (match_operand:QI 1 "gpc_reg_operand" "r,r"))
616 (clobber (match_scratch:EXTQI 0 "=r,r"))]
617 "rs6000_gen_cell_microcode"
621 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
623 (zero_extend:EXTQI (match_dup 1)))
625 (compare:CC (match_dup 0)
628 [(set_attr "type" "logical")
629 (set_attr "dot" "yes")
630 (set_attr "length" "4,8")])
632 (define_insn_and_split "*zero_extendqi<mode>2_dot2"
633 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
634 (compare:CC (zero_extend:EXTQI (match_operand:QI 1 "gpc_reg_operand" "r,r"))
636 (set (match_operand:EXTQI 0 "gpc_reg_operand" "=r,r")
637 (zero_extend:EXTQI (match_dup 1)))]
638 "rs6000_gen_cell_microcode"
642 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
644 (zero_extend:EXTQI (match_dup 1)))
646 (compare:CC (match_dup 0)
649 [(set_attr "type" "logical")
650 (set_attr "dot" "yes")
651 (set_attr "length" "4,8")])
654 (define_insn "zero_extendhi<mode>2"
655 [(set (match_operand:EXTHI 0 "gpc_reg_operand" "=r,r")
656 (zero_extend:EXTHI (match_operand:HI 1 "reg_or_mem_operand" "m,r")))]
660 rlwinm %0,%1,0,0xffff"
661 [(set_attr "type" "load,shift")])
663 (define_insn_and_split "*zero_extendhi<mode>2_dot"
664 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
665 (compare:CC (zero_extend:EXTHI (match_operand:HI 1 "gpc_reg_operand" "r,r"))
667 (clobber (match_scratch:EXTHI 0 "=r,r"))]
668 "rs6000_gen_cell_microcode"
672 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
674 (zero_extend:EXTHI (match_dup 1)))
676 (compare:CC (match_dup 0)
679 [(set_attr "type" "logical")
680 (set_attr "dot" "yes")
681 (set_attr "length" "4,8")])
683 (define_insn_and_split "*zero_extendhi<mode>2_dot2"
684 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
685 (compare:CC (zero_extend:EXTHI (match_operand:HI 1 "gpc_reg_operand" "r,r"))
687 (set (match_operand:EXTHI 0 "gpc_reg_operand" "=r,r")
688 (zero_extend:EXTHI (match_dup 1)))]
689 "rs6000_gen_cell_microcode"
693 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
695 (zero_extend:EXTHI (match_dup 1)))
697 (compare:CC (match_dup 0)
700 [(set_attr "type" "logical")
701 (set_attr "dot" "yes")
702 (set_attr "length" "4,8")])
705 (define_insn "zero_extendsi<mode>2"
706 [(set (match_operand:EXTSI 0 "gpc_reg_operand" "=r,r,??wj,!wz,!wu")
707 (zero_extend:EXTSI (match_operand:SI 1 "reg_or_mem_operand" "m,r,r,Z,Z")))]
715 [(set_attr "type" "load,shift,mffgpr,fpload,fpload")])
717 (define_insn_and_split "*zero_extendsi<mode>2_dot"
718 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
719 (compare:CC (zero_extend:EXTSI (match_operand:SI 1 "gpc_reg_operand" "r,r"))
721 (clobber (match_scratch:EXTSI 0 "=r,r"))]
722 "rs6000_gen_cell_microcode"
726 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
728 (zero_extend:DI (match_dup 1)))
730 (compare:CC (match_dup 0)
733 [(set_attr "type" "shift")
734 (set_attr "dot" "yes")
735 (set_attr "length" "4,8")])
737 (define_insn_and_split "*zero_extendsi<mode>2_dot2"
738 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
739 (compare:CC (zero_extend:EXTSI (match_operand:SI 1 "gpc_reg_operand" "r,r"))
741 (set (match_operand:EXTSI 0 "gpc_reg_operand" "=r,r")
742 (zero_extend:EXTSI (match_dup 1)))]
743 "rs6000_gen_cell_microcode"
747 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
749 (zero_extend:EXTSI (match_dup 1)))
751 (compare:CC (match_dup 0)
754 [(set_attr "type" "shift")
755 (set_attr "dot" "yes")
756 (set_attr "length" "4,8")])
759 (define_insn "extendqi<mode>2"
760 [(set (match_operand:EXTQI 0 "gpc_reg_operand" "=r")
761 (sign_extend:EXTQI (match_operand:QI 1 "gpc_reg_operand" "r")))]
764 [(set_attr "type" "exts")])
766 (define_insn_and_split "*extendqi<mode>2_dot"
767 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
768 (compare:CC (sign_extend:EXTQI (match_operand:QI 1 "gpc_reg_operand" "r,r"))
770 (clobber (match_scratch:EXTQI 0 "=r,r"))]
771 "rs6000_gen_cell_microcode"
775 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
777 (sign_extend:EXTQI (match_dup 1)))
779 (compare:CC (match_dup 0)
782 [(set_attr "type" "exts")
783 (set_attr "dot" "yes")
784 (set_attr "length" "4,8")])
786 (define_insn_and_split "*extendqi<mode>2_dot2"
787 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
788 (compare:CC (sign_extend:EXTQI (match_operand:QI 1 "gpc_reg_operand" "r,r"))
790 (set (match_operand:EXTQI 0 "gpc_reg_operand" "=r,r")
791 (sign_extend:EXTQI (match_dup 1)))]
792 "rs6000_gen_cell_microcode"
796 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
798 (sign_extend:EXTQI (match_dup 1)))
800 (compare:CC (match_dup 0)
803 [(set_attr "type" "exts")
804 (set_attr "dot" "yes")
805 (set_attr "length" "4,8")])
808 (define_expand "extendhi<mode>2"
809 [(set (match_operand:EXTHI 0 "gpc_reg_operand" "")
810 (sign_extend:EXTHI (match_operand:HI 1 "gpc_reg_operand" "")))]
814 (define_insn "*extendhi<mode>2"
815 [(set (match_operand:EXTHI 0 "gpc_reg_operand" "=r,r")
816 (sign_extend:EXTHI (match_operand:HI 1 "reg_or_mem_operand" "m,r")))]
817 "rs6000_gen_cell_microcode"
821 [(set_attr "type" "load,exts")
822 (set_attr "sign_extend" "yes")])
824 (define_insn "*extendhi<mode>2_noload"
825 [(set (match_operand:EXTHI 0 "gpc_reg_operand" "=r")
826 (sign_extend:EXTHI (match_operand:HI 1 "gpc_reg_operand" "r")))]
827 "!rs6000_gen_cell_microcode"
829 [(set_attr "type" "exts")])
831 (define_insn_and_split "*extendhi<mode>2_dot"
832 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
833 (compare:CC (sign_extend:EXTHI (match_operand:HI 1 "gpc_reg_operand" "r,r"))
835 (clobber (match_scratch:EXTHI 0 "=r,r"))]
836 "rs6000_gen_cell_microcode"
840 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
842 (sign_extend:EXTHI (match_dup 1)))
844 (compare:CC (match_dup 0)
847 [(set_attr "type" "exts")
848 (set_attr "dot" "yes")
849 (set_attr "length" "4,8")])
851 (define_insn_and_split "*extendhi<mode>2_dot2"
852 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
853 (compare:CC (sign_extend:EXTHI (match_operand:HI 1 "gpc_reg_operand" "r,r"))
855 (set (match_operand:EXTHI 0 "gpc_reg_operand" "=r,r")
856 (sign_extend:EXTHI (match_dup 1)))]
857 "rs6000_gen_cell_microcode"
861 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
863 (sign_extend:EXTHI (match_dup 1)))
865 (compare:CC (match_dup 0)
868 [(set_attr "type" "exts")
869 (set_attr "dot" "yes")
870 (set_attr "length" "4,8")])
873 (define_insn "extendsi<mode>2"
874 [(set (match_operand:EXTSI 0 "gpc_reg_operand" "=r,r,??wj,!wl,!wu")
875 (sign_extend:EXTSI (match_operand:SI 1 "lwa_operand" "Y,r,r,Z,Z")))]
883 [(set_attr "type" "load,exts,mffgpr,fpload,fpload")
884 (set_attr "sign_extend" "yes")])
886 (define_insn_and_split "*extendsi<mode>2_dot"
887 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
888 (compare:CC (sign_extend:EXTSI (match_operand:SI 1 "gpc_reg_operand" "r,r"))
890 (clobber (match_scratch:EXTSI 0 "=r,r"))]
891 "rs6000_gen_cell_microcode"
895 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
897 (sign_extend:EXTSI (match_dup 1)))
899 (compare:CC (match_dup 0)
902 [(set_attr "type" "exts")
903 (set_attr "dot" "yes")
904 (set_attr "length" "4,8")])
906 (define_insn_and_split "*extendsi<mode>2_dot2"
907 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
908 (compare:CC (sign_extend:EXTSI (match_operand:SI 1 "gpc_reg_operand" "r,r"))
910 (set (match_operand:EXTSI 0 "gpc_reg_operand" "=r,r")
911 (sign_extend:EXTSI (match_dup 1)))]
912 "rs6000_gen_cell_microcode"
916 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
918 (sign_extend:EXTSI (match_dup 1)))
920 (compare:CC (match_dup 0)
923 [(set_attr "type" "exts")
924 (set_attr "dot" "yes")
925 (set_attr "length" "4,8")])
927 ;; IBM 405, 440, 464 and 476 half-word multiplication operations.
929 (define_insn "*macchwc"
930 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
931 (compare:CC (plus:SI (mult:SI (ashiftrt:SI
932 (match_operand:SI 2 "gpc_reg_operand" "r")
935 (match_operand:HI 1 "gpc_reg_operand" "r")))
936 (match_operand:SI 4 "gpc_reg_operand" "0"))
938 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
939 (plus:SI (mult:SI (ashiftrt:SI
947 [(set_attr "type" "halfmul")])
949 (define_insn "*macchw"
950 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
951 (plus:SI (mult:SI (ashiftrt:SI
952 (match_operand:SI 2 "gpc_reg_operand" "r")
955 (match_operand:HI 1 "gpc_reg_operand" "r")))
956 (match_operand:SI 3 "gpc_reg_operand" "0")))]
959 [(set_attr "type" "halfmul")])
961 (define_insn "*macchwuc"
962 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
963 (compare:CC (plus:SI (mult:SI (lshiftrt:SI
964 (match_operand:SI 2 "gpc_reg_operand" "r")
967 (match_operand:HI 1 "gpc_reg_operand" "r")))
968 (match_operand:SI 4 "gpc_reg_operand" "0"))
970 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
971 (plus:SI (mult:SI (lshiftrt:SI
979 [(set_attr "type" "halfmul")])
981 (define_insn "*macchwu"
982 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
983 (plus:SI (mult:SI (lshiftrt:SI
984 (match_operand:SI 2 "gpc_reg_operand" "r")
987 (match_operand:HI 1 "gpc_reg_operand" "r")))
988 (match_operand:SI 3 "gpc_reg_operand" "0")))]
991 [(set_attr "type" "halfmul")])
993 (define_insn "*machhwc"
994 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
995 (compare:CC (plus:SI (mult:SI (ashiftrt:SI
996 (match_operand:SI 1 "gpc_reg_operand" "%r")
999 (match_operand:SI 2 "gpc_reg_operand" "r")
1001 (match_operand:SI 4 "gpc_reg_operand" "0"))
1003 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1004 (plus:SI (mult:SI (ashiftrt:SI
1013 [(set_attr "type" "halfmul")])
1015 (define_insn "*machhw"
1016 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1017 (plus:SI (mult:SI (ashiftrt:SI
1018 (match_operand:SI 1 "gpc_reg_operand" "%r")
1021 (match_operand:SI 2 "gpc_reg_operand" "r")
1023 (match_operand:SI 3 "gpc_reg_operand" "0")))]
1026 [(set_attr "type" "halfmul")])
1028 (define_insn "*machhwuc"
1029 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1030 (compare:CC (plus:SI (mult:SI (lshiftrt:SI
1031 (match_operand:SI 1 "gpc_reg_operand" "%r")
1034 (match_operand:SI 2 "gpc_reg_operand" "r")
1036 (match_operand:SI 4 "gpc_reg_operand" "0"))
1038 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1039 (plus:SI (mult:SI (lshiftrt:SI
1048 [(set_attr "type" "halfmul")])
1050 (define_insn "*machhwu"
1051 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1052 (plus:SI (mult:SI (lshiftrt:SI
1053 (match_operand:SI 1 "gpc_reg_operand" "%r")
1056 (match_operand:SI 2 "gpc_reg_operand" "r")
1058 (match_operand:SI 3 "gpc_reg_operand" "0")))]
1061 [(set_attr "type" "halfmul")])
1063 (define_insn "*maclhwc"
1064 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1065 (compare:CC (plus:SI (mult:SI (sign_extend:SI
1066 (match_operand:HI 1 "gpc_reg_operand" "%r"))
1068 (match_operand:HI 2 "gpc_reg_operand" "r")))
1069 (match_operand:SI 4 "gpc_reg_operand" "0"))
1071 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1072 (plus:SI (mult:SI (sign_extend:SI
1079 [(set_attr "type" "halfmul")])
1081 (define_insn "*maclhw"
1082 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1083 (plus:SI (mult:SI (sign_extend:SI
1084 (match_operand:HI 1 "gpc_reg_operand" "%r"))
1086 (match_operand:HI 2 "gpc_reg_operand" "r")))
1087 (match_operand:SI 3 "gpc_reg_operand" "0")))]
1090 [(set_attr "type" "halfmul")])
1092 (define_insn "*maclhwuc"
1093 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1094 (compare:CC (plus:SI (mult:SI (zero_extend:SI
1095 (match_operand:HI 1 "gpc_reg_operand" "%r"))
1097 (match_operand:HI 2 "gpc_reg_operand" "r")))
1098 (match_operand:SI 4 "gpc_reg_operand" "0"))
1100 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1101 (plus:SI (mult:SI (zero_extend:SI
1108 [(set_attr "type" "halfmul")])
1110 (define_insn "*maclhwu"
1111 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1112 (plus:SI (mult:SI (zero_extend:SI
1113 (match_operand:HI 1 "gpc_reg_operand" "%r"))
1115 (match_operand:HI 2 "gpc_reg_operand" "r")))
1116 (match_operand:SI 3 "gpc_reg_operand" "0")))]
1119 [(set_attr "type" "halfmul")])
1121 (define_insn "*nmacchwc"
1122 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1123 (compare:CC (minus:SI (match_operand:SI 4 "gpc_reg_operand" "0")
1124 (mult:SI (ashiftrt:SI
1125 (match_operand:SI 2 "gpc_reg_operand" "r")
1128 (match_operand:HI 1 "gpc_reg_operand" "r"))))
1130 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1131 (minus:SI (match_dup 4)
1132 (mult:SI (ashiftrt:SI
1139 [(set_attr "type" "halfmul")])
1141 (define_insn "*nmacchw"
1142 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1143 (minus:SI (match_operand:SI 3 "gpc_reg_operand" "0")
1144 (mult:SI (ashiftrt:SI
1145 (match_operand:SI 2 "gpc_reg_operand" "r")
1148 (match_operand:HI 1 "gpc_reg_operand" "r")))))]
1151 [(set_attr "type" "halfmul")])
1153 (define_insn "*nmachhwc"
1154 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1155 (compare:CC (minus:SI (match_operand:SI 4 "gpc_reg_operand" "0")
1156 (mult:SI (ashiftrt:SI
1157 (match_operand:SI 1 "gpc_reg_operand" "%r")
1160 (match_operand:SI 2 "gpc_reg_operand" "r")
1163 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1164 (minus:SI (match_dup 4)
1165 (mult:SI (ashiftrt:SI
1173 [(set_attr "type" "halfmul")])
1175 (define_insn "*nmachhw"
1176 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1177 (minus:SI (match_operand:SI 3 "gpc_reg_operand" "0")
1178 (mult:SI (ashiftrt:SI
1179 (match_operand:SI 1 "gpc_reg_operand" "%r")
1182 (match_operand:SI 2 "gpc_reg_operand" "r")
1186 [(set_attr "type" "halfmul")])
1188 (define_insn "*nmaclhwc"
1189 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1190 (compare:CC (minus:SI (match_operand:SI 4 "gpc_reg_operand" "0")
1191 (mult:SI (sign_extend:SI
1192 (match_operand:HI 1 "gpc_reg_operand" "%r"))
1194 (match_operand:HI 2 "gpc_reg_operand" "r"))))
1196 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1197 (minus:SI (match_dup 4)
1198 (mult:SI (sign_extend:SI
1204 [(set_attr "type" "halfmul")])
1206 (define_insn "*nmaclhw"
1207 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1208 (minus:SI (match_operand:SI 3 "gpc_reg_operand" "0")
1209 (mult:SI (sign_extend:SI
1210 (match_operand:HI 1 "gpc_reg_operand" "%r"))
1212 (match_operand:HI 2 "gpc_reg_operand" "r")))))]
1215 [(set_attr "type" "halfmul")])
1217 (define_insn "*mulchwc"
1218 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1219 (compare:CC (mult:SI (ashiftrt:SI
1220 (match_operand:SI 2 "gpc_reg_operand" "r")
1223 (match_operand:HI 1 "gpc_reg_operand" "r")))
1225 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1226 (mult:SI (ashiftrt:SI
1233 [(set_attr "type" "halfmul")])
1235 (define_insn "*mulchw"
1236 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1237 (mult:SI (ashiftrt:SI
1238 (match_operand:SI 2 "gpc_reg_operand" "r")
1241 (match_operand:HI 1 "gpc_reg_operand" "r"))))]
1244 [(set_attr "type" "halfmul")])
1246 (define_insn "*mulchwuc"
1247 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1248 (compare:CC (mult:SI (lshiftrt:SI
1249 (match_operand:SI 2 "gpc_reg_operand" "r")
1252 (match_operand:HI 1 "gpc_reg_operand" "r")))
1254 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1255 (mult:SI (lshiftrt:SI
1262 [(set_attr "type" "halfmul")])
1264 (define_insn "*mulchwu"
1265 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1266 (mult:SI (lshiftrt:SI
1267 (match_operand:SI 2 "gpc_reg_operand" "r")
1270 (match_operand:HI 1 "gpc_reg_operand" "r"))))]
1273 [(set_attr "type" "halfmul")])
1275 (define_insn "*mulhhwc"
1276 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1277 (compare:CC (mult:SI (ashiftrt:SI
1278 (match_operand:SI 1 "gpc_reg_operand" "%r")
1281 (match_operand:SI 2 "gpc_reg_operand" "r")
1284 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1285 (mult:SI (ashiftrt:SI
1293 [(set_attr "type" "halfmul")])
1295 (define_insn "*mulhhw"
1296 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1297 (mult:SI (ashiftrt:SI
1298 (match_operand:SI 1 "gpc_reg_operand" "%r")
1301 (match_operand:SI 2 "gpc_reg_operand" "r")
1305 [(set_attr "type" "halfmul")])
1307 (define_insn "*mulhhwuc"
1308 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1309 (compare:CC (mult:SI (lshiftrt:SI
1310 (match_operand:SI 1 "gpc_reg_operand" "%r")
1313 (match_operand:SI 2 "gpc_reg_operand" "r")
1316 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1317 (mult:SI (lshiftrt:SI
1325 [(set_attr "type" "halfmul")])
1327 (define_insn "*mulhhwu"
1328 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1329 (mult:SI (lshiftrt:SI
1330 (match_operand:SI 1 "gpc_reg_operand" "%r")
1333 (match_operand:SI 2 "gpc_reg_operand" "r")
1337 [(set_attr "type" "halfmul")])
1339 (define_insn "*mullhwc"
1340 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1341 (compare:CC (mult:SI (sign_extend:SI
1342 (match_operand:HI 1 "gpc_reg_operand" "%r"))
1344 (match_operand:HI 2 "gpc_reg_operand" "r")))
1346 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1347 (mult:SI (sign_extend:SI
1353 [(set_attr "type" "halfmul")])
1355 (define_insn "*mullhw"
1356 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1357 (mult:SI (sign_extend:SI
1358 (match_operand:HI 1 "gpc_reg_operand" "%r"))
1360 (match_operand:HI 2 "gpc_reg_operand" "r"))))]
1363 [(set_attr "type" "halfmul")])
1365 (define_insn "*mullhwuc"
1366 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1367 (compare:CC (mult:SI (zero_extend:SI
1368 (match_operand:HI 1 "gpc_reg_operand" "%r"))
1370 (match_operand:HI 2 "gpc_reg_operand" "r")))
1372 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1373 (mult:SI (zero_extend:SI
1379 [(set_attr "type" "halfmul")])
1381 (define_insn "*mullhwu"
1382 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
1383 (mult:SI (zero_extend:SI
1384 (match_operand:HI 1 "gpc_reg_operand" "%r"))
1386 (match_operand:HI 2 "gpc_reg_operand" "r"))))]
1389 [(set_attr "type" "halfmul")])
1391 ;; IBM 405, 440, 464 and 476 string-search dlmzb instruction support.
1392 (define_insn "dlmzb"
1393 [(set (match_operand:CC 3 "cc_reg_operand" "=x")
1394 (unspec:CC [(match_operand:SI 1 "gpc_reg_operand" "r")
1395 (match_operand:SI 2 "gpc_reg_operand" "r")]
1397 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
1398 (unspec:SI [(match_dup 1)
1404 (define_expand "strlensi"
1405 [(set (match_operand:SI 0 "gpc_reg_operand" "")
1406 (unspec:SI [(match_operand:BLK 1 "general_operand" "")
1407 (match_operand:QI 2 "const_int_operand" "")
1408 (match_operand 3 "const_int_operand" "")]
1409 UNSPEC_DLMZB_STRLEN))
1410 (clobber (match_scratch:CC 4 "=x"))]
1411 "TARGET_DLMZB && WORDS_BIG_ENDIAN && !optimize_size"
1413 rtx result = operands[0];
1414 rtx src = operands[1];
1415 rtx search_char = operands[2];
1416 rtx align = operands[3];
1417 rtx addr, scratch_string, word1, word2, scratch_dlmzb;
1418 rtx loop_label, end_label, mem, cr0, cond;
1419 if (search_char != const0_rtx
1420 || GET_CODE (align) != CONST_INT
1421 || INTVAL (align) < 8)
1423 word1 = gen_reg_rtx (SImode);
1424 word2 = gen_reg_rtx (SImode);
1425 scratch_dlmzb = gen_reg_rtx (SImode);
1426 scratch_string = gen_reg_rtx (Pmode);
1427 loop_label = gen_label_rtx ();
1428 end_label = gen_label_rtx ();
1429 addr = force_reg (Pmode, XEXP (src, 0));
1430 emit_move_insn (scratch_string, addr);
1431 emit_label (loop_label);
1432 mem = change_address (src, SImode, scratch_string);
1433 emit_move_insn (word1, mem);
1434 emit_move_insn (word2, adjust_address (mem, SImode, 4));
1435 cr0 = gen_rtx_REG (CCmode, CR0_REGNO);
1436 emit_insn (gen_dlmzb (scratch_dlmzb, word1, word2, cr0));
1437 cond = gen_rtx_NE (VOIDmode, cr0, const0_rtx);
1438 emit_jump_insn (gen_rtx_SET (pc_rtx,
1439 gen_rtx_IF_THEN_ELSE (VOIDmode,
1445 emit_insn (gen_addsi3 (scratch_string, scratch_string, GEN_INT (8)));
1446 emit_jump_insn (gen_rtx_SET (pc_rtx,
1447 gen_rtx_LABEL_REF (VOIDmode, loop_label)));
1449 emit_label (end_label);
1450 emit_insn (gen_addsi3 (scratch_string, scratch_string, scratch_dlmzb));
1451 emit_insn (gen_subsi3 (result, scratch_string, addr));
1452 emit_insn (gen_addsi3 (result, result, constm1_rtx));
1456 ;; Fixed-point arithmetic insns.
1458 (define_expand "add<mode>3"
1459 [(set (match_operand:SDI 0 "gpc_reg_operand" "")
1460 (plus:SDI (match_operand:SDI 1 "gpc_reg_operand" "")
1461 (match_operand:SDI 2 "reg_or_add_cint_operand" "")))]
1464 if (<MODE>mode == DImode && !TARGET_POWERPC64)
1466 rtx lo0 = gen_lowpart (SImode, operands[0]);
1467 rtx lo1 = gen_lowpart (SImode, operands[1]);
1468 rtx lo2 = gen_lowpart (SImode, operands[2]);
1469 rtx hi0 = gen_highpart (SImode, operands[0]);
1470 rtx hi1 = gen_highpart (SImode, operands[1]);
1471 rtx hi2 = gen_highpart_mode (SImode, DImode, operands[2]);
1473 if (!reg_or_short_operand (lo2, SImode))
1474 lo2 = force_reg (SImode, lo2);
1475 if (!adde_operand (hi2, SImode))
1476 hi2 = force_reg (SImode, hi2);
1478 emit_insn (gen_addsi3_carry (lo0, lo1, lo2));
1479 emit_insn (gen_addsi3_carry_in (hi0, hi1, hi2));
1483 if (CONST_INT_P (operands[2]) && !add_operand (operands[2], <MODE>mode))
1485 rtx tmp = ((!can_create_pseudo_p ()
1486 || rtx_equal_p (operands[0], operands[1]))
1487 ? operands[0] : gen_reg_rtx (<MODE>mode));
1489 HOST_WIDE_INT val = INTVAL (operands[2]);
1490 HOST_WIDE_INT low = ((val & 0xffff) ^ 0x8000) - 0x8000;
1491 HOST_WIDE_INT rest = trunc_int_for_mode (val - low, <MODE>mode);
1493 if (<MODE>mode == DImode && !satisfies_constraint_L (GEN_INT (rest)))
1496 /* The ordering here is important for the prolog expander.
1497 When space is allocated from the stack, adding 'low' first may
1498 produce a temporary deallocation (which would be bad). */
1499 emit_insn (gen_add<mode>3 (tmp, operands[1], GEN_INT (rest)));
1500 emit_insn (gen_add<mode>3 (operands[0], tmp, GEN_INT (low)));
1505 (define_insn "*add<mode>3"
1506 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r,r,r")
1507 (plus:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,b,b")
1508 (match_operand:GPR 2 "add_operand" "r,I,L")))]
1514 [(set_attr "type" "add")])
1516 (define_insn "addsi3_high"
1517 [(set (match_operand:SI 0 "gpc_reg_operand" "=b")
1518 (plus:SI (match_operand:SI 1 "gpc_reg_operand" "b")
1519 (high:SI (match_operand 2 "" ""))))]
1520 "TARGET_MACHO && !TARGET_64BIT"
1521 "addis %0,%1,ha16(%2)"
1522 [(set_attr "type" "add")])
1524 (define_insn_and_split "*add<mode>3_dot"
1525 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
1526 (compare:CC (plus:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
1527 (match_operand:GPR 2 "gpc_reg_operand" "r,r"))
1529 (clobber (match_scratch:GPR 0 "=r,r"))]
1530 "<MODE>mode == Pmode"
1534 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
1536 (plus:GPR (match_dup 1)
1539 (compare:CC (match_dup 0)
1542 [(set_attr "type" "add")
1543 (set_attr "dot" "yes")
1544 (set_attr "length" "4,8")])
1546 (define_insn_and_split "*add<mode>3_dot2"
1547 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
1548 (compare:CC (plus:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
1549 (match_operand:GPR 2 "gpc_reg_operand" "r,r"))
1551 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
1552 (plus:GPR (match_dup 1)
1554 "<MODE>mode == Pmode"
1558 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
1560 (plus:GPR (match_dup 1)
1563 (compare:CC (match_dup 0)
1566 [(set_attr "type" "add")
1567 (set_attr "dot" "yes")
1568 (set_attr "length" "4,8")])
1570 (define_insn_and_split "*add<mode>3_imm_dot"
1571 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
1572 (compare:CC (plus:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,b")
1573 (match_operand:GPR 2 "short_cint_operand" "I,I"))
1575 (clobber (match_scratch:GPR 0 "=r,r"))
1576 (clobber (reg:GPR CA_REGNO))]
1577 "<MODE>mode == Pmode"
1581 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
1583 (plus:GPR (match_dup 1)
1586 (compare:CC (match_dup 0)
1589 [(set_attr "type" "add")
1590 (set_attr "dot" "yes")
1591 (set_attr "length" "4,8")])
1593 (define_insn_and_split "*add<mode>3_imm_dot2"
1594 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
1595 (compare:CC (plus:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,b")
1596 (match_operand:GPR 2 "short_cint_operand" "I,I"))
1598 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
1599 (plus:GPR (match_dup 1)
1601 (clobber (reg:GPR CA_REGNO))]
1602 "<MODE>mode == Pmode"
1606 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
1608 (plus:GPR (match_dup 1)
1611 (compare:CC (match_dup 0)
1614 [(set_attr "type" "add")
1615 (set_attr "dot" "yes")
1616 (set_attr "length" "4,8")])
1618 ;; Split an add that we can't do in one insn into two insns, each of which
1619 ;; does one 16-bit part. This is used by combine. Note that the low-order
1620 ;; add should be last in case the result gets used in an address.
1623 [(set (match_operand:GPR 0 "gpc_reg_operand" "")
1624 (plus:GPR (match_operand:GPR 1 "gpc_reg_operand" "")
1625 (match_operand:GPR 2 "non_add_cint_operand" "")))]
1627 [(set (match_dup 0) (plus:GPR (match_dup 1) (match_dup 3)))
1628 (set (match_dup 0) (plus:GPR (match_dup 0) (match_dup 4)))]
1630 HOST_WIDE_INT val = INTVAL (operands[2]);
1631 HOST_WIDE_INT low = ((val & 0xffff) ^ 0x8000) - 0x8000;
1632 HOST_WIDE_INT rest = trunc_int_for_mode (val - low, <MODE>mode);
1634 operands[4] = GEN_INT (low);
1635 if (<MODE>mode == SImode || satisfies_constraint_L (GEN_INT (rest)))
1636 operands[3] = GEN_INT (rest);
1637 else if (can_create_pseudo_p ())
1639 operands[3] = gen_reg_rtx (DImode);
1640 emit_move_insn (operands[3], operands[2]);
1641 emit_insn (gen_adddi3 (operands[0], operands[1], operands[3]));
1649 (define_insn "add<mode>3_carry"
1650 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
1651 (plus:P (match_operand:P 1 "gpc_reg_operand" "r")
1652 (match_operand:P 2 "reg_or_short_operand" "rI")))
1653 (set (reg:P CA_REGNO)
1654 (ltu:P (plus:P (match_dup 1)
1659 [(set_attr "type" "add")])
1661 (define_insn "*add<mode>3_imm_carry_pos"
1662 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
1663 (plus:P (match_operand:P 1 "gpc_reg_operand" "r")
1664 (match_operand:P 2 "short_cint_operand" "n")))
1665 (set (reg:P CA_REGNO)
1666 (geu:P (match_dup 1)
1667 (match_operand:P 3 "const_int_operand" "n")))]
1668 "INTVAL (operands[2]) > 0
1669 && INTVAL (operands[2]) + INTVAL (operands[3]) == 0"
1671 [(set_attr "type" "add")])
1673 (define_insn "*add<mode>3_imm_carry_0"
1674 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
1675 (match_operand:P 1 "gpc_reg_operand" "r"))
1676 (set (reg:P CA_REGNO)
1680 [(set_attr "type" "add")])
1682 (define_insn "*add<mode>3_imm_carry_m1"
1683 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
1684 (plus:P (match_operand:P 1 "gpc_reg_operand" "r")
1686 (set (reg:P CA_REGNO)
1691 [(set_attr "type" "add")])
1693 (define_insn "*add<mode>3_imm_carry_neg"
1694 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
1695 (plus:P (match_operand:P 1 "gpc_reg_operand" "r")
1696 (match_operand:P 2 "short_cint_operand" "n")))
1697 (set (reg:P CA_REGNO)
1698 (gtu:P (match_dup 1)
1699 (match_operand:P 3 "const_int_operand" "n")))]
1700 "INTVAL (operands[2]) < 0
1701 && INTVAL (operands[2]) + INTVAL (operands[3]) == -1"
1703 [(set_attr "type" "add")])
1706 (define_expand "add<mode>3_carry_in"
1708 (set (match_operand:GPR 0 "gpc_reg_operand")
1709 (plus:GPR (plus:GPR (match_operand:GPR 1 "gpc_reg_operand")
1710 (match_operand:GPR 2 "adde_operand"))
1711 (reg:GPR CA_REGNO)))
1712 (clobber (reg:GPR CA_REGNO))])]
1715 if (operands[2] == const0_rtx)
1717 emit_insn (gen_add<mode>3_carry_in_0 (operands[0], operands[1]));
1720 if (operands[2] == constm1_rtx)
1722 emit_insn (gen_add<mode>3_carry_in_m1 (operands[0], operands[1]));
1727 (define_insn "*add<mode>3_carry_in_internal"
1728 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
1729 (plus:GPR (plus:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
1730 (match_operand:GPR 2 "gpc_reg_operand" "r"))
1731 (reg:GPR CA_REGNO)))
1732 (clobber (reg:GPR CA_REGNO))]
1735 [(set_attr "type" "add")])
1737 (define_insn "add<mode>3_carry_in_0"
1738 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
1739 (plus:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
1740 (reg:GPR CA_REGNO)))
1741 (clobber (reg:GPR CA_REGNO))]
1744 [(set_attr "type" "add")])
1746 (define_insn "add<mode>3_carry_in_m1"
1747 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
1748 (plus:GPR (plus:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
1751 (clobber (reg:GPR CA_REGNO))]
1754 [(set_attr "type" "add")])
1757 (define_expand "one_cmpl<mode>2"
1758 [(set (match_operand:SDI 0 "gpc_reg_operand" "")
1759 (not:SDI (match_operand:SDI 1 "gpc_reg_operand" "")))]
1762 if (<MODE>mode == DImode && !TARGET_POWERPC64)
1764 rs6000_split_logical (operands, NOT, false, false, false);
1769 (define_insn "*one_cmpl<mode>2"
1770 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
1771 (not:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")))]
1775 (define_insn_and_split "*one_cmpl<mode>2_dot"
1776 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
1777 (compare:CC (not:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r"))
1779 (clobber (match_scratch:GPR 0 "=r,r"))]
1780 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
1784 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
1786 (not:GPR (match_dup 1)))
1788 (compare:CC (match_dup 0)
1791 [(set_attr "type" "logical")
1792 (set_attr "dot" "yes")
1793 (set_attr "length" "4,8")])
1795 (define_insn_and_split "*one_cmpl<mode>2_dot2"
1796 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
1797 (compare:CC (not:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r"))
1799 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
1800 (not:GPR (match_dup 1)))]
1801 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
1805 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
1807 (not:GPR (match_dup 1)))
1809 (compare:CC (match_dup 0)
1812 [(set_attr "type" "logical")
1813 (set_attr "dot" "yes")
1814 (set_attr "length" "4,8")])
1817 (define_expand "sub<mode>3"
1818 [(set (match_operand:SDI 0 "gpc_reg_operand" "")
1819 (minus:SDI (match_operand:SDI 1 "reg_or_short_operand" "")
1820 (match_operand:SDI 2 "gpc_reg_operand" "")))]
1823 if (<MODE>mode == DImode && !TARGET_POWERPC64)
1825 rtx lo0 = gen_lowpart (SImode, operands[0]);
1826 rtx lo1 = gen_lowpart (SImode, operands[1]);
1827 rtx lo2 = gen_lowpart (SImode, operands[2]);
1828 rtx hi0 = gen_highpart (SImode, operands[0]);
1829 rtx hi1 = gen_highpart_mode (SImode, DImode, operands[1]);
1830 rtx hi2 = gen_highpart (SImode, operands[2]);
1832 if (!reg_or_short_operand (lo1, SImode))
1833 lo1 = force_reg (SImode, lo1);
1834 if (!adde_operand (hi1, SImode))
1835 hi1 = force_reg (SImode, hi1);
1837 emit_insn (gen_subfsi3_carry (lo0, lo2, lo1));
1838 emit_insn (gen_subfsi3_carry_in (hi0, hi2, hi1));
1842 if (short_cint_operand (operands[1], <MODE>mode))
1844 emit_insn (gen_subf<mode>3_imm (operands[0], operands[2], operands[1]));
1849 (define_insn "*subf<mode>3"
1850 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
1851 (minus:GPR (match_operand:GPR 2 "gpc_reg_operand" "r")
1852 (match_operand:GPR 1 "gpc_reg_operand" "r")))]
1855 [(set_attr "type" "add")])
1857 (define_insn_and_split "*subf<mode>3_dot"
1858 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
1859 (compare:CC (minus:GPR (match_operand:GPR 2 "gpc_reg_operand" "r,r")
1860 (match_operand:GPR 1 "gpc_reg_operand" "r,r"))
1862 (clobber (match_scratch:GPR 0 "=r,r"))]
1863 "<MODE>mode == Pmode"
1867 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
1869 (minus:GPR (match_dup 2)
1872 (compare:CC (match_dup 0)
1875 [(set_attr "type" "add")
1876 (set_attr "dot" "yes")
1877 (set_attr "length" "4,8")])
1879 (define_insn_and_split "*subf<mode>3_dot2"
1880 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
1881 (compare:CC (minus:GPR (match_operand:GPR 2 "gpc_reg_operand" "r,r")
1882 (match_operand:GPR 1 "gpc_reg_operand" "r,r"))
1884 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
1885 (minus:GPR (match_dup 2)
1887 "<MODE>mode == Pmode"
1891 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
1893 (minus:GPR (match_dup 2)
1896 (compare:CC (match_dup 0)
1899 [(set_attr "type" "add")
1900 (set_attr "dot" "yes")
1901 (set_attr "length" "4,8")])
1903 (define_insn "subf<mode>3_imm"
1904 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
1905 (minus:GPR (match_operand:GPR 2 "short_cint_operand" "I")
1906 (match_operand:GPR 1 "gpc_reg_operand" "r")))
1907 (clobber (reg:GPR CA_REGNO))]
1910 [(set_attr "type" "add")])
1913 (define_insn "subf<mode>3_carry"
1914 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
1915 (minus:P (match_operand:P 2 "reg_or_short_operand" "rI")
1916 (match_operand:P 1 "gpc_reg_operand" "r")))
1917 (set (reg:P CA_REGNO)
1918 (leu:P (match_dup 1)
1922 [(set_attr "type" "add")])
1924 (define_insn "*subf<mode>3_imm_carry_0"
1925 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
1926 (neg:P (match_operand:P 1 "gpc_reg_operand" "r")))
1927 (set (reg:P CA_REGNO)
1932 [(set_attr "type" "add")])
1934 (define_insn "*subf<mode>3_imm_carry_m1"
1935 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
1936 (not:P (match_operand:P 1 "gpc_reg_operand" "r")))
1937 (set (reg:P CA_REGNO)
1941 [(set_attr "type" "add")])
1944 (define_expand "subf<mode>3_carry_in"
1946 (set (match_operand:GPR 0 "gpc_reg_operand")
1947 (plus:GPR (plus:GPR (not:GPR (match_operand:GPR 1 "gpc_reg_operand"))
1949 (match_operand:GPR 2 "adde_operand")))
1950 (clobber (reg:GPR CA_REGNO))])]
1953 if (operands[2] == const0_rtx)
1955 emit_insn (gen_subf<mode>3_carry_in_0 (operands[0], operands[1]));
1958 if (operands[2] == constm1_rtx)
1960 emit_insn (gen_subf<mode>3_carry_in_m1 (operands[0], operands[1]));
1965 (define_insn "*subf<mode>3_carry_in_internal"
1966 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
1967 (plus:GPR (plus:GPR (not:GPR (match_operand:GPR 1 "gpc_reg_operand" "r"))
1969 (match_operand:GPR 2 "gpc_reg_operand" "r")))
1970 (clobber (reg:GPR CA_REGNO))]
1973 [(set_attr "type" "add")])
1975 (define_insn "subf<mode>3_carry_in_0"
1976 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
1977 (plus:GPR (not:GPR (match_operand:GPR 1 "gpc_reg_operand" "r"))
1978 (reg:GPR CA_REGNO)))
1979 (clobber (reg:GPR CA_REGNO))]
1982 [(set_attr "type" "add")])
1984 (define_insn "subf<mode>3_carry_in_m1"
1985 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
1986 (plus:GPR (minus:GPR (reg:GPR CA_REGNO)
1987 (match_operand:GPR 1 "gpc_reg_operand" "r"))
1989 (clobber (reg:GPR CA_REGNO))]
1992 [(set_attr "type" "add")])
1994 (define_insn "subf<mode>3_carry_in_xx"
1995 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
1996 (plus:GPR (reg:GPR CA_REGNO)
1998 (clobber (reg:GPR CA_REGNO))]
2001 [(set_attr "type" "add")])
2004 (define_insn "neg<mode>2"
2005 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
2006 (neg:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")))]
2009 [(set_attr "type" "add")])
2011 (define_insn_and_split "*neg<mode>2_dot"
2012 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
2013 (compare:CC (neg:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r"))
2015 (clobber (match_scratch:GPR 0 "=r,r"))]
2016 "<MODE>mode == Pmode"
2020 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
2022 (neg:GPR (match_dup 1)))
2024 (compare:CC (match_dup 0)
2027 [(set_attr "type" "add")
2028 (set_attr "dot" "yes")
2029 (set_attr "length" "4,8")])
2031 (define_insn_and_split "*neg<mode>2_dot2"
2032 [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
2033 (compare:CC (neg:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r"))
2035 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
2036 (neg:GPR (match_dup 1)))]
2037 "<MODE>mode == Pmode"
2041 "&& reload_completed && cc_reg_not_cr0_operand (operands[2], CCmode)"
2043 (neg:GPR (match_dup 1)))
2045 (compare:CC (match_dup 0)
2048 [(set_attr "type" "add")
2049 (set_attr "dot" "yes")
2050 (set_attr "length" "4,8")])
2053 (define_insn "clz<mode>2"
2054 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
2055 (clz:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")))]
2058 [(set_attr "type" "cntlz")])
2060 (define_expand "ctz<mode>2"
2062 (neg:GPR (match_operand:GPR 1 "gpc_reg_operand" "")))
2064 (and:GPR (match_dup 1)
2067 (clz:GPR (match_dup 3)))
2068 (parallel [(set (match_operand:GPR 0 "gpc_reg_operand" "")
2069 (minus:GPR (match_dup 5)
2071 (clobber (reg:GPR CA_REGNO))])]
2074 operands[2] = gen_reg_rtx (<MODE>mode);
2075 operands[3] = gen_reg_rtx (<MODE>mode);
2076 operands[4] = gen_reg_rtx (<MODE>mode);
2077 operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode) - 1);
2080 (define_expand "ffs<mode>2"
2082 (neg:GPR (match_operand:GPR 1 "gpc_reg_operand" "")))
2084 (and:GPR (match_dup 1)
2087 (clz:GPR (match_dup 3)))
2088 (parallel [(set (match_operand:GPR 0 "gpc_reg_operand" "")
2089 (minus:GPR (match_dup 5)
2091 (clobber (reg:GPR CA_REGNO))])]
2094 operands[2] = gen_reg_rtx (<MODE>mode);
2095 operands[3] = gen_reg_rtx (<MODE>mode);
2096 operands[4] = gen_reg_rtx (<MODE>mode);
2097 operands[5] = GEN_INT (GET_MODE_BITSIZE (<MODE>mode));
2101 (define_expand "popcount<mode>2"
2102 [(set (match_operand:GPR 0 "gpc_reg_operand" "")
2103 (popcount:GPR (match_operand:GPR 1 "gpc_reg_operand" "")))]
2104 "TARGET_POPCNTB || TARGET_POPCNTD"
2106 rs6000_emit_popcount (operands[0], operands[1]);
2110 (define_insn "popcntb<mode>2"
2111 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
2112 (unspec:GPR [(match_operand:GPR 1 "gpc_reg_operand" "r")]
2116 [(set_attr "type" "popcnt")])
2118 (define_insn "popcntd<mode>2"
2119 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
2120 (popcount:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")))]
2123 [(set_attr "type" "popcnt")])
2126 (define_expand "parity<mode>2"
2127 [(set (match_operand:GPR 0 "gpc_reg_operand" "")
2128 (parity:GPR (match_operand:GPR 1 "gpc_reg_operand" "")))]
2131 rs6000_emit_parity (operands[0], operands[1]);
2135 (define_insn "parity<mode>2_cmpb"
2136 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
2137 (unspec:GPR [(match_operand:GPR 1 "gpc_reg_operand" "r")] UNSPEC_PARITY))]
2138 "TARGET_CMPB && TARGET_POPCNTB"
2140 [(set_attr "type" "popcnt")])
2143 ;; Since the hardware zeros the upper part of the register, save generating the
2144 ;; AND immediate if we are converting to unsigned
2145 (define_insn "*bswaphi2_extenddi"
2146 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
2148 (bswap:HI (match_operand:HI 1 "memory_operand" "Z"))))]
2151 [(set_attr "length" "4")
2152 (set_attr "type" "load")])
2154 (define_insn "*bswaphi2_extendsi"
2155 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2157 (bswap:HI (match_operand:HI 1 "memory_operand" "Z"))))]
2160 [(set_attr "length" "4")
2161 (set_attr "type" "load")])
2163 (define_expand "bswaphi2"
2164 [(parallel [(set (match_operand:HI 0 "reg_or_mem_operand" "")
2166 (match_operand:HI 1 "reg_or_mem_operand" "")))
2167 (clobber (match_scratch:SI 2 ""))])]
2170 if (!REG_P (operands[0]) && !REG_P (operands[1]))
2171 operands[1] = force_reg (HImode, operands[1]);
2174 (define_insn "bswaphi2_internal"
2175 [(set (match_operand:HI 0 "reg_or_mem_operand" "=r,Z,&r")
2177 (match_operand:HI 1 "reg_or_mem_operand" "Z,r,r")))
2178 (clobber (match_scratch:SI 2 "=X,X,&r"))]
2184 [(set_attr "length" "4,4,12")
2185 (set_attr "type" "load,store,*")])
2187 ;; We are always BITS_BIG_ENDIAN, so the (const_int 16) below is
2188 ;; correct for -mlittle as well as -mbig.
2190 [(set (match_operand:HI 0 "gpc_reg_operand" "")
2191 (bswap:HI (match_operand:HI 1 "gpc_reg_operand" "")))
2192 (clobber (match_operand:SI 2 "gpc_reg_operand" ""))]
2195 (zero_extract:SI (match_dup 4)
2199 (and:SI (ashift:SI (match_dup 4)
2201 (const_int 65280))) ;; 0xff00
2203 (ior:SI (match_dup 3)
2207 operands[3] = simplify_gen_subreg (SImode, operands[0], HImode, 0);
2208 operands[4] = simplify_gen_subreg (SImode, operands[1], HImode, 0);
2211 (define_insn "*bswapsi2_extenddi"
2212 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
2214 (bswap:SI (match_operand:SI 1 "memory_operand" "Z"))))]
2217 [(set_attr "length" "4")
2218 (set_attr "type" "load")])
2220 (define_expand "bswapsi2"
2221 [(set (match_operand:SI 0 "reg_or_mem_operand" "")
2223 (match_operand:SI 1 "reg_or_mem_operand" "")))]
2226 if (!REG_P (operands[0]) && !REG_P (operands[1]))
2227 operands[1] = force_reg (SImode, operands[1]);
2230 (define_insn "*bswapsi2_internal"
2231 [(set (match_operand:SI 0 "reg_or_mem_operand" "=r,Z,&r")
2233 (match_operand:SI 1 "reg_or_mem_operand" "Z,r,r")))]
2239 [(set_attr "length" "4,4,12")
2240 (set_attr "type" "load,store,*")])
2242 ;; We are always BITS_BIG_ENDIAN, so the bit positions below in
2243 ;; zero_extract insns do not change for -mlittle.
2245 [(set (match_operand:SI 0 "gpc_reg_operand" "")
2246 (bswap:SI (match_operand:SI 1 "gpc_reg_operand" "")))]
2249 (rotate:SI (match_dup 1) (const_int 8)))
2250 (set (zero_extract:SI (match_dup 0)
2254 (set (zero_extract:SI (match_dup 0)
2257 (rotate:SI (match_dup 1)
2261 (define_expand "bswapdi2"
2262 [(parallel [(set (match_operand:DI 0 "reg_or_mem_operand" "")
2264 (match_operand:DI 1 "reg_or_mem_operand" "")))
2265 (clobber (match_scratch:DI 2 ""))
2266 (clobber (match_scratch:DI 3 ""))])]
2269 if (!REG_P (operands[0]) && !REG_P (operands[1]))
2270 operands[1] = force_reg (DImode, operands[1]);
2272 if (!TARGET_POWERPC64)
2274 /* 32-bit mode needs fewer scratch registers, but 32-bit addressing mode
2275 that uses 64-bit registers needs the same scratch registers as 64-bit
2277 emit_insn (gen_bswapdi2_32bit (operands[0], operands[1]));
2282 ;; Power7/cell has ldbrx/stdbrx, so use it directly
2283 (define_insn "*bswapdi2_ldbrx"
2284 [(set (match_operand:DI 0 "reg_or_mem_operand" "=r,Z,&r")
2285 (bswap:DI (match_operand:DI 1 "reg_or_mem_operand" "Z,r,r")))
2286 (clobber (match_scratch:DI 2 "=X,X,&r"))
2287 (clobber (match_scratch:DI 3 "=X,X,&r"))]
2288 "TARGET_POWERPC64 && TARGET_LDBRX
2289 && (REG_P (operands[0]) || REG_P (operands[1]))"
2294 [(set_attr "length" "4,4,36")
2295 (set_attr "type" "load,store,*")])
2297 ;; Non-power7/cell, fall back to use lwbrx/stwbrx
2298 (define_insn "*bswapdi2_64bit"
2299 [(set (match_operand:DI 0 "reg_or_mem_operand" "=r,Z,&r")
2300 (bswap:DI (match_operand:DI 1 "reg_or_mem_operand" "Z,r,r")))
2301 (clobber (match_scratch:DI 2 "=&b,&b,&r"))
2302 (clobber (match_scratch:DI 3 "=&r,&r,&r"))]
2303 "TARGET_POWERPC64 && !TARGET_LDBRX
2304 && (REG_P (operands[0]) || REG_P (operands[1]))
2305 && !(MEM_P (operands[0]) && MEM_VOLATILE_P (operands[0]))
2306 && !(MEM_P (operands[1]) && MEM_VOLATILE_P (operands[1]))"
2308 [(set_attr "length" "16,12,36")])
2311 [(set (match_operand:DI 0 "gpc_reg_operand" "")
2312 (bswap:DI (match_operand:DI 1 "indexed_or_indirect_operand" "")))
2313 (clobber (match_operand:DI 2 "gpc_reg_operand" ""))
2314 (clobber (match_operand:DI 3 "gpc_reg_operand" ""))]
2315 "TARGET_POWERPC64 && !TARGET_LDBRX && reload_completed"
2319 rtx dest = operands[0];
2320 rtx src = operands[1];
2321 rtx op2 = operands[2];
2322 rtx op3 = operands[3];
2323 rtx op3_32 = simplify_gen_subreg (SImode, op3, DImode,
2324 BYTES_BIG_ENDIAN ? 4 : 0);
2325 rtx dest_32 = simplify_gen_subreg (SImode, dest, DImode,
2326 BYTES_BIG_ENDIAN ? 4 : 0);
2332 addr1 = XEXP (src, 0);
2333 if (GET_CODE (addr1) == PLUS)
2335 emit_insn (gen_add3_insn (op2, XEXP (addr1, 0), GEN_INT (4)));
2336 if (TARGET_AVOID_XFORM)
2338 emit_insn (gen_add3_insn (op2, XEXP (addr1, 1), op2));
2342 addr2 = gen_rtx_PLUS (Pmode, op2, XEXP (addr1, 1));
2344 else if (TARGET_AVOID_XFORM)
2346 emit_insn (gen_add3_insn (op2, addr1, GEN_INT (4)));
2351 emit_move_insn (op2, GEN_INT (4));
2352 addr2 = gen_rtx_PLUS (Pmode, op2, addr1);
2355 word1 = change_address (src, SImode, addr1);
2356 word2 = change_address (src, SImode, addr2);
2358 if (BYTES_BIG_ENDIAN)
2360 emit_insn (gen_bswapsi2 (op3_32, word2));
2361 emit_insn (gen_bswapsi2 (dest_32, word1));
2365 emit_insn (gen_bswapsi2 (op3_32, word1));
2366 emit_insn (gen_bswapsi2 (dest_32, word2));
2369 emit_insn (gen_ashldi3 (op3, op3, GEN_INT (32)));
2370 emit_insn (gen_iordi3 (dest, dest, op3));
2375 [(set (match_operand:DI 0 "indexed_or_indirect_operand" "")
2376 (bswap:DI (match_operand:DI 1 "gpc_reg_operand" "")))
2377 (clobber (match_operand:DI 2 "gpc_reg_operand" ""))
2378 (clobber (match_operand:DI 3 "gpc_reg_operand" ""))]
2379 "TARGET_POWERPC64 && !TARGET_LDBRX && reload_completed"
2383 rtx dest = operands[0];
2384 rtx src = operands[1];
2385 rtx op2 = operands[2];
2386 rtx op3 = operands[3];
2387 rtx src_si = simplify_gen_subreg (SImode, src, DImode,
2388 BYTES_BIG_ENDIAN ? 4 : 0);
2389 rtx op3_si = simplify_gen_subreg (SImode, op3, DImode,
2390 BYTES_BIG_ENDIAN ? 4 : 0);
2396 addr1 = XEXP (dest, 0);
2397 if (GET_CODE (addr1) == PLUS)
2399 emit_insn (gen_add3_insn (op2, XEXP (addr1, 0), GEN_INT (4)));
2400 if (TARGET_AVOID_XFORM)
2402 emit_insn (gen_add3_insn (op2, XEXP (addr1, 1), op2));
2406 addr2 = gen_rtx_PLUS (Pmode, op2, XEXP (addr1, 1));
2408 else if (TARGET_AVOID_XFORM)
2410 emit_insn (gen_add3_insn (op2, addr1, GEN_INT (4)));
2415 emit_move_insn (op2, GEN_INT (4));
2416 addr2 = gen_rtx_PLUS (Pmode, op2, addr1);
2419 word1 = change_address (dest, SImode, addr1);
2420 word2 = change_address (dest, SImode, addr2);
2422 emit_insn (gen_lshrdi3 (op3, src, GEN_INT (32)));
2424 if (BYTES_BIG_ENDIAN)
2426 emit_insn (gen_bswapsi2 (word1, src_si));
2427 emit_insn (gen_bswapsi2 (word2, op3_si));
2431 emit_insn (gen_bswapsi2 (word2, src_si));
2432 emit_insn (gen_bswapsi2 (word1, op3_si));
2438 [(set (match_operand:DI 0 "gpc_reg_operand" "")
2439 (bswap:DI (match_operand:DI 1 "gpc_reg_operand" "")))
2440 (clobber (match_operand:DI 2 "gpc_reg_operand" ""))
2441 (clobber (match_operand:DI 3 "gpc_reg_operand" ""))]
2442 "TARGET_POWERPC64 && reload_completed"
2446 rtx dest = operands[0];
2447 rtx src = operands[1];
2448 rtx op2 = operands[2];
2449 rtx op3 = operands[3];
2450 int lo_off = BYTES_BIG_ENDIAN ? 4 : 0;
2451 rtx dest_si = simplify_gen_subreg (SImode, dest, DImode, lo_off);
2452 rtx src_si = simplify_gen_subreg (SImode, src, DImode, lo_off);
2453 rtx op2_si = simplify_gen_subreg (SImode, op2, DImode, lo_off);
2454 rtx op3_si = simplify_gen_subreg (SImode, op3, DImode, lo_off);
2456 emit_insn (gen_lshrdi3 (op2, src, GEN_INT (32)));
2457 emit_insn (gen_bswapsi2 (dest_si, src_si));
2458 emit_insn (gen_bswapsi2 (op3_si, op2_si));
2459 emit_insn (gen_ashldi3 (dest, dest, GEN_INT (32)));
2460 emit_insn (gen_iordi3 (dest, dest, op3));
2464 (define_insn "bswapdi2_32bit"
2465 [(set (match_operand:DI 0 "reg_or_mem_operand" "=r,Z,?&r")
2466 (bswap:DI (match_operand:DI 1 "reg_or_mem_operand" "Z,r,r")))
2467 (clobber (match_scratch:SI 2 "=&b,&b,X"))]
2468 "!TARGET_POWERPC64 && (REG_P (operands[0]) || REG_P (operands[1]))"
2470 [(set_attr "length" "16,12,36")])
2473 [(set (match_operand:DI 0 "gpc_reg_operand" "")
2474 (bswap:DI (match_operand:DI 1 "indexed_or_indirect_operand" "")))
2475 (clobber (match_operand:SI 2 "gpc_reg_operand" ""))]
2476 "!TARGET_POWERPC64 && reload_completed"
2480 rtx dest = operands[0];
2481 rtx src = operands[1];
2482 rtx op2 = operands[2];
2483 rtx dest1 = simplify_gen_subreg (SImode, dest, DImode, 0);
2484 rtx dest2 = simplify_gen_subreg (SImode, dest, DImode, 4);
2490 addr1 = XEXP (src, 0);
2491 if (GET_CODE (addr1) == PLUS)
2493 emit_insn (gen_add3_insn (op2, XEXP (addr1, 0), GEN_INT (4)));
2494 if (TARGET_AVOID_XFORM
2495 || REGNO (XEXP (addr1, 1)) == REGNO (dest2))
2497 emit_insn (gen_add3_insn (op2, XEXP (addr1, 1), op2));
2501 addr2 = gen_rtx_PLUS (SImode, op2, XEXP (addr1, 1));
2503 else if (TARGET_AVOID_XFORM
2504 || REGNO (addr1) == REGNO (dest2))
2506 emit_insn (gen_add3_insn (op2, addr1, GEN_INT (4)));
2511 emit_move_insn (op2, GEN_INT (4));
2512 addr2 = gen_rtx_PLUS (SImode, op2, addr1);
2515 word1 = change_address (src, SImode, addr1);
2516 word2 = change_address (src, SImode, addr2);
2518 emit_insn (gen_bswapsi2 (dest2, word1));
2519 /* The REGNO (dest2) tests above ensure that addr2 has not been trashed,
2520 thus allowing us to omit an early clobber on the output. */
2521 emit_insn (gen_bswapsi2 (dest1, word2));
2526 [(set (match_operand:DI 0 "indexed_or_indirect_operand" "")
2527 (bswap:DI (match_operand:DI 1 "gpc_reg_operand" "")))
2528 (clobber (match_operand:SI 2 "gpc_reg_operand" ""))]
2529 "!TARGET_POWERPC64 && reload_completed"
2533 rtx dest = operands[0];
2534 rtx src = operands[1];
2535 rtx op2 = operands[2];
2536 rtx src1 = simplify_gen_subreg (SImode, src, DImode, 0);
2537 rtx src2 = simplify_gen_subreg (SImode, src, DImode, 4);
2543 addr1 = XEXP (dest, 0);
2544 if (GET_CODE (addr1) == PLUS)
2546 emit_insn (gen_add3_insn (op2, XEXP (addr1, 0), GEN_INT (4)));
2547 if (TARGET_AVOID_XFORM)
2549 emit_insn (gen_add3_insn (op2, XEXP (addr1, 1), op2));
2553 addr2 = gen_rtx_PLUS (SImode, op2, XEXP (addr1, 1));
2555 else if (TARGET_AVOID_XFORM)
2557 emit_insn (gen_add3_insn (op2, addr1, GEN_INT (4)));
2562 emit_move_insn (op2, GEN_INT (4));
2563 addr2 = gen_rtx_PLUS (SImode, op2, addr1);
2566 word1 = change_address (dest, SImode, addr1);
2567 word2 = change_address (dest, SImode, addr2);
2569 emit_insn (gen_bswapsi2 (word2, src1));
2570 emit_insn (gen_bswapsi2 (word1, src2));
2575 [(set (match_operand:DI 0 "gpc_reg_operand" "")
2576 (bswap:DI (match_operand:DI 1 "gpc_reg_operand" "")))
2577 (clobber (match_operand:SI 2 "" ""))]
2578 "!TARGET_POWERPC64 && reload_completed"
2582 rtx dest = operands[0];
2583 rtx src = operands[1];
2584 rtx src1 = simplify_gen_subreg (SImode, src, DImode, 0);
2585 rtx src2 = simplify_gen_subreg (SImode, src, DImode, 4);
2586 rtx dest1 = simplify_gen_subreg (SImode, dest, DImode, 0);
2587 rtx dest2 = simplify_gen_subreg (SImode, dest, DImode, 4);
2589 emit_insn (gen_bswapsi2 (dest1, src2));
2590 emit_insn (gen_bswapsi2 (dest2, src1));
2595 (define_insn "mul<mode>3"
2596 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
2597 (mult:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,r")
2598 (match_operand:GPR 2 "reg_or_short_operand" "r,I")))]
2603 [(set_attr "type" "mul")
2605 (cond [(match_operand:GPR 2 "s8bit_cint_operand" "")
2607 (match_operand:GPR 2 "short_cint_operand" "")
2608 (const_string "16")]
2609 (const_string "<bits>")))])
2611 (define_insn_and_split "*mul<mode>3_dot"
2612 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
2613 (compare:CC (mult:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
2614 (match_operand:GPR 2 "gpc_reg_operand" "r,r"))
2616 (clobber (match_scratch:GPR 0 "=r,r"))]
2617 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
2621 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
2623 (mult:GPR (match_dup 1)
2626 (compare:CC (match_dup 0)
2629 [(set_attr "type" "mul")
2630 (set_attr "size" "<bits>")
2631 (set_attr "dot" "yes")
2632 (set_attr "length" "4,8")])
2634 (define_insn_and_split "*mul<mode>3_dot2"
2635 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
2636 (compare:CC (mult:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
2637 (match_operand:GPR 2 "gpc_reg_operand" "r,r"))
2639 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
2640 (mult:GPR (match_dup 1)
2642 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
2646 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
2648 (mult:GPR (match_dup 1)
2651 (compare:CC (match_dup 0)
2654 [(set_attr "type" "mul")
2655 (set_attr "size" "<bits>")
2656 (set_attr "dot" "yes")
2657 (set_attr "length" "4,8")])
2660 (define_expand "<su>mul<mode>3_highpart"
2661 [(set (match_operand:GPR 0 "gpc_reg_operand")
2663 (mult:<DMODE> (any_extend:<DMODE>
2664 (match_operand:GPR 1 "gpc_reg_operand"))
2666 (match_operand:GPR 2 "gpc_reg_operand")))
2670 if (<MODE>mode == SImode && TARGET_POWERPC64)
2672 emit_insn (gen_<su>mulsi3_highpart_64 (operands[0], operands[1],
2677 if (!WORDS_BIG_ENDIAN)
2679 emit_insn (gen_<su>mul<mode>3_highpart_le (operands[0], operands[1],
2685 (define_insn "*<su>mul<mode>3_highpart"
2686 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
2688 (mult:<DMODE> (any_extend:<DMODE>
2689 (match_operand:GPR 1 "gpc_reg_operand" "r"))
2691 (match_operand:GPR 2 "gpc_reg_operand" "r")))
2693 "WORDS_BIG_ENDIAN && !(<MODE>mode == SImode && TARGET_POWERPC64)"
2694 "mulh<wd><u> %0,%1,%2"
2695 [(set_attr "type" "mul")
2696 (set_attr "size" "<bits>")])
2698 (define_insn "<su>mulsi3_highpart_le"
2699 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2701 (mult:DI (any_extend:DI
2702 (match_operand:SI 1 "gpc_reg_operand" "r"))
2704 (match_operand:SI 2 "gpc_reg_operand" "r")))
2706 "!WORDS_BIG_ENDIAN && !TARGET_POWERPC64"
2708 [(set_attr "type" "mul")])
2710 (define_insn "<su>muldi3_highpart_le"
2711 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
2713 (mult:TI (any_extend:TI
2714 (match_operand:DI 1 "gpc_reg_operand" "r"))
2716 (match_operand:DI 2 "gpc_reg_operand" "r")))
2718 "!WORDS_BIG_ENDIAN && TARGET_POWERPC64"
2720 [(set_attr "type" "mul")
2721 (set_attr "size" "64")])
2723 (define_insn "<su>mulsi3_highpart_64"
2724 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
2727 (mult:DI (any_extend:DI
2728 (match_operand:SI 1 "gpc_reg_operand" "r"))
2730 (match_operand:SI 2 "gpc_reg_operand" "r")))
2734 [(set_attr "type" "mul")])
2736 (define_expand "<u>mul<mode><dmode>3"
2737 [(set (match_operand:<DMODE> 0 "gpc_reg_operand")
2738 (mult:<DMODE> (any_extend:<DMODE>
2739 (match_operand:GPR 1 "gpc_reg_operand"))
2741 (match_operand:GPR 2 "gpc_reg_operand"))))]
2742 "!(<MODE>mode == SImode && TARGET_POWERPC64)"
2744 rtx l = gen_reg_rtx (<MODE>mode);
2745 rtx h = gen_reg_rtx (<MODE>mode);
2746 emit_insn (gen_mul<mode>3 (l, operands[1], operands[2]));
2747 emit_insn (gen_<su>mul<mode>3_highpart (h, operands[1], operands[2]));
2748 emit_move_insn (gen_lowpart (<MODE>mode, operands[0]), l);
2749 emit_move_insn (gen_highpart (<MODE>mode, operands[0]), h);
2754 (define_insn "udiv<mode>3"
2755 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
2756 (udiv:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
2757 (match_operand:GPR 2 "gpc_reg_operand" "r")))]
2760 [(set_attr "type" "div")
2761 (set_attr "size" "<bits>")])
2764 ;; For powers of two we can do sra[wd]i/addze for divide and then adjust for
2765 ;; modulus. If it isn't a power of two, force operands into register and do
2767 (define_expand "div<mode>3"
2768 [(set (match_operand:GPR 0 "gpc_reg_operand" "")
2769 (div:GPR (match_operand:GPR 1 "gpc_reg_operand" "")
2770 (match_operand:GPR 2 "reg_or_cint_operand" "")))]
2773 if (CONST_INT_P (operands[2])
2774 && INTVAL (operands[2]) > 0
2775 && exact_log2 (INTVAL (operands[2])) >= 0)
2777 emit_insn (gen_div<mode>3_sra (operands[0], operands[1], operands[2]));
2781 operands[2] = force_reg (<MODE>mode, operands[2]);
2784 (define_insn "*div<mode>3"
2785 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
2786 (div:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
2787 (match_operand:GPR 2 "gpc_reg_operand" "r")))]
2790 [(set_attr "type" "div")
2791 (set_attr "size" "<bits>")])
2793 (define_insn "div<mode>3_sra"
2794 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
2795 (div:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
2796 (match_operand:GPR 2 "exact_log2_cint_operand" "N")))
2797 (clobber (reg:GPR CA_REGNO))]
2799 "sra<wd>i %0,%1,%p2\;addze %0,%0"
2800 [(set_attr "type" "two")
2801 (set_attr "length" "8")])
2803 (define_insn_and_split "*div<mode>3_sra_dot"
2804 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
2805 (compare:CC (div:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
2806 (match_operand:GPR 2 "exact_log2_cint_operand" "N,N"))
2808 (clobber (match_scratch:GPR 0 "=r,r"))
2809 (clobber (reg:GPR CA_REGNO))]
2810 "<MODE>mode == Pmode"
2812 sra<wd>i %0,%1,%p2\;addze. %0,%0
2814 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
2815 [(parallel [(set (match_dup 0)
2816 (div:GPR (match_dup 1)
2818 (clobber (reg:GPR CA_REGNO))])
2820 (compare:CC (match_dup 0)
2823 [(set_attr "type" "two")
2824 (set_attr "length" "8,12")
2825 (set_attr "cell_micro" "not")])
2827 (define_insn_and_split "*div<mode>3_sra_dot2"
2828 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
2829 (compare:CC (div:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
2830 (match_operand:GPR 2 "exact_log2_cint_operand" "N,N"))
2832 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
2833 (div:GPR (match_dup 1)
2835 (clobber (reg:GPR CA_REGNO))]
2836 "<MODE>mode == Pmode"
2838 sra<wd>i %0,%1,%p2\;addze. %0,%0
2840 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
2841 [(parallel [(set (match_dup 0)
2842 (div:GPR (match_dup 1)
2844 (clobber (reg:GPR CA_REGNO))])
2846 (compare:CC (match_dup 0)
2849 [(set_attr "type" "two")
2850 (set_attr "length" "8,12")
2851 (set_attr "cell_micro" "not")])
2853 (define_expand "mod<mode>3"
2854 [(use (match_operand:GPR 0 "gpc_reg_operand" ""))
2855 (use (match_operand:GPR 1 "gpc_reg_operand" ""))
2856 (use (match_operand:GPR 2 "reg_or_cint_operand" ""))]
2863 if (GET_CODE (operands[2]) != CONST_INT
2864 || INTVAL (operands[2]) <= 0
2865 || (i = exact_log2 (INTVAL (operands[2]))) < 0)
2868 temp1 = gen_reg_rtx (<MODE>mode);
2869 temp2 = gen_reg_rtx (<MODE>mode);
2871 emit_insn (gen_div<mode>3 (temp1, operands[1], operands[2]));
2872 emit_insn (gen_ashl<mode>3 (temp2, temp1, GEN_INT (i)));
2873 emit_insn (gen_sub<mode>3 (operands[0], operands[1], temp2));
2877 ;; Logical instructions
2878 ;; The logical instructions are mostly combined by using match_operator,
2879 ;; but the plain AND insns are somewhat different because there is no
2880 ;; plain 'andi' (only 'andi.'), no plain 'andis', and there are all
2881 ;; those rotate-and-mask operations. Thus, the AND insns come first.
2883 (define_expand "and<mode>3"
2884 [(set (match_operand:SDI 0 "gpc_reg_operand" "")
2885 (and:SDI (match_operand:SDI 1 "gpc_reg_operand" "")
2886 (match_operand:SDI 2 "reg_or_cint_operand" "")))]
2889 if (<MODE>mode == DImode && !TARGET_POWERPC64)
2891 rs6000_split_logical (operands, AND, false, false, false);
2895 if (logical_const_operand (operands[2], <MODE>mode)
2896 && !any_mask_operand (operands[2], <MODE>mode))
2898 if (rs6000_gen_cell_microcode)
2900 emit_insn (gen_and<mode>3_imm (operands[0], operands[1], operands[2]));
2904 operands[2] = force_reg (<MODE>mode, operands[2]);
2907 if ((<MODE>mode == DImode && !and64_2_operand (operands[2], <MODE>mode))
2908 || (<MODE>mode != DImode && !and_operand (operands[2], <MODE>mode)))
2909 operands[2] = force_reg (<MODE>mode, operands[2]);
2913 (define_insn "and<mode>3_imm"
2914 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
2915 (and:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r")
2916 (match_operand:GPR 2 "logical_const_operand" "n")))
2917 (clobber (match_scratch:CC 3 "=x"))]
2918 "rs6000_gen_cell_microcode
2919 && !any_mask_operand (operands[2], <MODE>mode)"
2920 "andi%e2. %0,%1,%u2"
2921 [(set_attr "type" "logical")
2922 (set_attr "dot" "yes")])
2924 (define_insn_and_split "*and<mode>3_imm_dot"
2925 [(set (match_operand:CC 3 "cc_reg_operand" "=x,??y")
2926 (compare:CC (and:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,r")
2927 (match_operand:GPR 2 "logical_const_operand" "n,n"))
2929 (clobber (match_scratch:GPR 0 "=r,r"))
2930 (clobber (match_scratch:CC 4 "=X,x"))]
2931 "(<MODE>mode == Pmode || UINTVAL (operands[2]) <= 0x7fffffff)
2932 && rs6000_gen_cell_microcode
2933 && !any_mask_operand (operands[2], <MODE>mode)"
2937 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
2938 [(parallel [(set (match_dup 0)
2939 (and:GPR (match_dup 1)
2941 (clobber (match_dup 4))])
2943 (compare:CC (match_dup 0)
2946 [(set_attr "type" "logical")
2947 (set_attr "dot" "yes")
2948 (set_attr "length" "4,8")])
2950 (define_insn_and_split "*and<mode>3_imm_dot2"
2951 [(set (match_operand:CC 3 "cc_reg_operand" "=x,??y")
2952 (compare:CC (and:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,r")
2953 (match_operand:GPR 2 "logical_const_operand" "n,n"))
2955 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
2956 (and:GPR (match_dup 1)
2958 (clobber (match_scratch:CC 4 "=X,x"))]
2959 "(<MODE>mode == Pmode || UINTVAL (operands[2]) <= 0x7fffffff)
2960 && rs6000_gen_cell_microcode
2961 && !any_mask_operand (operands[2], <MODE>mode)"
2965 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
2966 [(parallel [(set (match_dup 0)
2967 (and:GPR (match_dup 1)
2969 (clobber (match_dup 4))])
2971 (compare:CC (match_dup 0)
2974 [(set_attr "type" "logical")
2975 (set_attr "dot" "yes")
2976 (set_attr "length" "4,8")])
2978 (define_insn_and_split "*and<mode>3_imm_mask_dot"
2979 [(set (match_operand:CC 3 "cc_reg_operand" "=x,??y")
2980 (compare:CC (and:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,r")
2981 (match_operand:GPR 2 "logical_const_operand" "n,n"))
2983 (clobber (match_scratch:GPR 0 "=r,r"))]
2984 "(<MODE>mode == Pmode || UINTVAL (operands[2]) <= 0x7fffffff)
2985 && rs6000_gen_cell_microcode
2986 && any_mask_operand (operands[2], <MODE>mode)"
2990 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
2992 (and:GPR (match_dup 1)
2995 (compare:CC (match_dup 0)
2998 [(set_attr "type" "logical")
2999 (set_attr "dot" "yes")
3000 (set_attr "length" "4,8")])
3002 (define_insn_and_split "*and<mode>3_imm_mask_dot2"
3003 [(set (match_operand:CC 3 "cc_reg_operand" "=x,??y")
3004 (compare:CC (and:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,r")
3005 (match_operand:GPR 2 "logical_const_operand" "n,n"))
3007 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
3008 (and:GPR (match_dup 1)
3010 "(<MODE>mode == Pmode || UINTVAL (operands[2]) <= 0x7fffffff)
3011 && rs6000_gen_cell_microcode
3012 && any_mask_operand (operands[2], <MODE>mode)"
3016 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
3018 (and:GPR (match_dup 1)
3021 (compare:CC (match_dup 0)
3024 [(set_attr "type" "logical")
3025 (set_attr "dot" "yes")
3026 (set_attr "length" "4,8")])
3029 (define_insn "*and<mode>3_mask"
3030 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
3031 (and:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,r")
3032 (match_operand:GPR 2 "any_mask_operand" "S,T")))]
3035 rldic%B2 %0,%1,0,%S2
3036 rlwinm %0,%1,0,%m2,%M2"
3037 [(set_attr "type" "shift")])
3039 (define_insn_and_split "*and<mode>3_mask_dot"
3040 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y")
3041 (compare:CC (and:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,r,r,r")
3042 (match_operand:GPR 2 "any_mask_operand" "S,T,S,T"))
3044 (clobber (match_scratch:GPR 0 "=r,r,r,r"))]
3045 "(<MODE>mode == Pmode || UINTVAL (operands[2]) <= 0x7fffffff)
3046 && rs6000_gen_cell_microcode
3047 && !logical_const_operand (operands[2], <MODE>mode)"
3049 rldic%B2. %0,%1,0,%S2
3050 rlwinm. %0,%1,0,%m2,%M2
3053 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
3055 (and:GPR (match_dup 1)
3058 (compare:CC (match_dup 0)
3061 [(set_attr "type" "shift")
3062 (set_attr "dot" "yes")
3063 (set_attr "length" "4,4,8,8")])
3065 (define_insn_and_split "*and<mode>3_mask_dot2"
3066 [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y")
3067 (compare:CC (and:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,r,r,r")
3068 (match_operand:GPR 2 "any_mask_operand" "S,T,S,T"))
3070 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r,r,r")
3071 (and:GPR (match_dup 1)
3073 "(<MODE>mode == Pmode || UINTVAL (operands[2]) <= 0x7fffffff)
3074 && rs6000_gen_cell_microcode
3075 && !logical_const_operand (operands[2], <MODE>mode)"
3077 rldic%B2. %0,%1,0,%S2
3078 rlwinm. %0,%1,0,%m2,%M2
3081 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
3083 (and:GPR (match_dup 1)
3086 (compare:CC (match_dup 0)
3089 [(set_attr "type" "shift")
3090 (set_attr "dot" "yes")
3091 (set_attr "length" "4,4,8,8")])
3095 (define_insn "andsi3_internal0_nomc"
3096 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
3097 (and:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r")
3098 (match_operand:SI 2 "and_operand" "?r,T")))]
3099 "!rs6000_gen_cell_microcode"
3102 rlwinm %0,%1,0,%m2,%M2"
3103 [(set_attr "type" "logical,shift")])
3106 ;; Handle the PowerPC64 rlwinm corner case
3108 (define_insn_and_split "*andsi3_internal6"
3109 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
3110 (and:SI (match_operand:SI 1 "gpc_reg_operand" "r")
3111 (match_operand:SI 2 "mask_operand_wrap" "i")))]
3116 (and:SI (rotate:SI (match_dup 1) (match_dup 3))
3119 (rotate:SI (match_dup 0) (match_dup 5)))]
3122 int mb = extract_MB (operands[2]);
3123 int me = extract_ME (operands[2]);
3124 operands[3] = GEN_INT (me + 1);
3125 operands[5] = GEN_INT (32 - (me + 1));
3126 operands[4] = GEN_INT (~((HOST_WIDE_INT) -1 << (33 + me - mb)));
3128 [(set_attr "length" "8")])
3131 (define_expand "<code><mode>3"
3132 [(set (match_operand:SDI 0 "gpc_reg_operand" "")
3133 (iorxor:SDI (match_operand:SDI 1 "gpc_reg_operand" "")
3134 (match_operand:SDI 2 "reg_or_cint_operand" "")))]
3137 if (<MODE>mode == DImode && !TARGET_POWERPC64)
3139 rs6000_split_logical (operands, <CODE>, false, false, false);
3143 if (non_logical_cint_operand (operands[2], <MODE>mode))
3145 rtx tmp = ((!can_create_pseudo_p ()
3146 || rtx_equal_p (operands[0], operands[1]))
3147 ? operands[0] : gen_reg_rtx (<MODE>mode));
3149 HOST_WIDE_INT value = INTVAL (operands[2]);
3150 HOST_WIDE_INT lo = value & 0xffff;
3151 HOST_WIDE_INT hi = value - lo;
3153 emit_insn (gen_<code><mode>3 (tmp, operands[1], GEN_INT (hi)));
3154 emit_insn (gen_<code><mode>3 (operands[0], tmp, GEN_INT (lo)));
3158 if (!reg_or_logical_cint_operand (operands[2], <MODE>mode))
3159 operands[2] = force_reg (<MODE>mode, operands[2]);
3163 [(set (match_operand:GPR 0 "gpc_reg_operand" "")
3164 (iorxor:GPR (match_operand:GPR 1 "gpc_reg_operand" "")
3165 (match_operand:GPR 2 "non_logical_cint_operand" "")))]
3168 (iorxor:GPR (match_dup 1)
3171 (iorxor:GPR (match_dup 3)
3174 operands[3] = ((!can_create_pseudo_p ()
3175 || rtx_equal_p (operands[0], operands[1]))
3176 ? operands[0] : gen_reg_rtx (<MODE>mode));
3178 HOST_WIDE_INT value = INTVAL (operands[2]);
3179 HOST_WIDE_INT lo = value & 0xffff;
3180 HOST_WIDE_INT hi = value - lo;
3182 operands[4] = GEN_INT (hi);
3183 operands[5] = GEN_INT (lo);
3186 (define_insn "*bool<mode>3_imm"
3187 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
3188 (match_operator:GPR 3 "boolean_or_operator"
3189 [(match_operand:GPR 1 "gpc_reg_operand" "%r")
3190 (match_operand:GPR 2 "logical_const_operand" "n")]))]
3193 [(set_attr "type" "logical")])
3195 (define_insn "*bool<mode>3"
3196 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
3197 (match_operator:GPR 3 "boolean_operator"
3198 [(match_operand:GPR 1 "gpc_reg_operand" "r")
3199 (match_operand:GPR 2 "gpc_reg_operand" "r")]))]
3202 [(set_attr "type" "logical")])
3204 (define_insn_and_split "*bool<mode>3_dot"
3205 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
3206 (compare:CC (match_operator:GPR 3 "boolean_operator"
3207 [(match_operand:GPR 1 "gpc_reg_operand" "r,r")
3208 (match_operand:GPR 2 "gpc_reg_operand" "r,r")])
3210 (clobber (match_scratch:GPR 0 "=r,r"))]
3211 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
3215 "&& reload_completed && cc_reg_not_cr0_operand (operands[4], CCmode)"
3219 (compare:CC (match_dup 0)
3222 [(set_attr "type" "logical")
3223 (set_attr "dot" "yes")
3224 (set_attr "length" "4,8")])
3226 (define_insn_and_split "*bool<mode>3_dot2"
3227 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
3228 (compare:CC (match_operator:GPR 3 "boolean_operator"
3229 [(match_operand:GPR 1 "gpc_reg_operand" "r,r")
3230 (match_operand:GPR 2 "gpc_reg_operand" "r,r")])
3232 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
3234 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
3238 "&& reload_completed && cc_reg_not_cr0_operand (operands[4], CCmode)"
3242 (compare:CC (match_dup 0)
3245 [(set_attr "type" "logical")
3246 (set_attr "dot" "yes")
3247 (set_attr "length" "4,8")])
3250 (define_insn "*boolc<mode>3"
3251 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
3252 (match_operator:GPR 3 "boolean_operator"
3253 [(not:GPR (match_operand:GPR 2 "gpc_reg_operand" "r"))
3254 (match_operand:GPR 1 "gpc_reg_operand" "r")]))]
3257 [(set_attr "type" "logical")])
3259 (define_insn_and_split "*boolc<mode>3_dot"
3260 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
3261 (compare:CC (match_operator:GPR 3 "boolean_operator"
3262 [(not:GPR (match_operand:GPR 2 "gpc_reg_operand" "r,r"))
3263 (match_operand:GPR 1 "gpc_reg_operand" "r,r")])
3265 (clobber (match_scratch:GPR 0 "=r,r"))]
3266 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
3270 "&& reload_completed && cc_reg_not_cr0_operand (operands[4], CCmode)"
3274 (compare:CC (match_dup 0)
3277 [(set_attr "type" "logical")
3278 (set_attr "dot" "yes")
3279 (set_attr "length" "4,8")])
3281 (define_insn_and_split "*boolc<mode>3_dot2"
3282 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
3283 (compare:CC (match_operator:GPR 3 "boolean_operator"
3284 [(not:GPR (match_operand:GPR 2 "gpc_reg_operand" "r,r"))
3285 (match_operand:GPR 1 "gpc_reg_operand" "r,r")])
3287 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
3289 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
3293 "&& reload_completed && cc_reg_not_cr0_operand (operands[4], CCmode)"
3297 (compare:CC (match_dup 0)
3300 [(set_attr "type" "logical")
3301 (set_attr "dot" "yes")
3302 (set_attr "length" "4,8")])
3305 (define_insn "*boolcc<mode>3"
3306 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
3307 (match_operator:GPR 3 "boolean_operator"
3308 [(not:GPR (match_operand:GPR 1 "gpc_reg_operand" "r"))
3309 (not:GPR (match_operand:GPR 2 "gpc_reg_operand" "r"))]))]
3312 [(set_attr "type" "logical")])
3314 (define_insn_and_split "*boolcc<mode>3_dot"
3315 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
3316 (compare:CC (match_operator:GPR 3 "boolean_operator"
3317 [(not:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r"))
3318 (not:GPR (match_operand:GPR 2 "gpc_reg_operand" "r,r"))])
3320 (clobber (match_scratch:GPR 0 "=r,r"))]
3321 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
3325 "&& reload_completed && cc_reg_not_cr0_operand (operands[4], CCmode)"
3329 (compare:CC (match_dup 0)
3332 [(set_attr "type" "logical")
3333 (set_attr "dot" "yes")
3334 (set_attr "length" "4,8")])
3336 (define_insn_and_split "*boolcc<mode>3_dot2"
3337 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
3338 (compare:CC (match_operator:GPR 3 "boolean_operator"
3339 [(not:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r"))
3340 (not:GPR (match_operand:GPR 2 "gpc_reg_operand" "r,r"))])
3342 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
3344 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
3348 "&& reload_completed && cc_reg_not_cr0_operand (operands[4], CCmode)"
3352 (compare:CC (match_dup 0)
3355 [(set_attr "type" "logical")
3356 (set_attr "dot" "yes")
3357 (set_attr "length" "4,8")])
3360 ;; TODO: Should have dots of this as well.
3361 (define_insn "*eqv<mode>3"
3362 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
3363 (not:GPR (xor:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
3364 (match_operand:GPR 2 "gpc_reg_operand" "r"))))]
3367 [(set_attr "type" "logical")])
3369 ;; Rotate and shift insns, in all their variants. These support shifts,
3370 ;; field inserts and extracts, and various combinations thereof.
3371 (define_expand "insv"
3372 [(set (zero_extract (match_operand 0 "gpc_reg_operand" "")
3373 (match_operand:SI 1 "const_int_operand" "")
3374 (match_operand:SI 2 "const_int_operand" ""))
3375 (match_operand 3 "gpc_reg_operand" ""))]
3379 /* Do not handle 16/8 bit structures that fit in HI/QI modes directly, since
3380 the (SUBREG:SI (REG:HI xxx)) that is otherwise generated can confuse the
3381 compiler if the address of the structure is taken later. Likewise, do
3382 not handle invalid E500 subregs. */
3383 if (GET_CODE (operands[0]) == SUBREG
3384 && (GET_MODE_SIZE (GET_MODE (SUBREG_REG (operands[0]))) < UNITS_PER_WORD
3385 || ((TARGET_E500_DOUBLE || TARGET_SPE)
3386 && invalid_e500_subreg (operands[0], GET_MODE (operands[0])))))
3389 if (TARGET_POWERPC64 && GET_MODE (operands[0]) == DImode)
3390 emit_insn (gen_insvdi_internal (operands[0], operands[1], operands[2],
3393 emit_insn (gen_insvsi_internal (operands[0], operands[1], operands[2],
3398 (define_insn "insvsi_internal"
3399 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
3400 (match_operand:SI 1 "const_int_operand" "i")
3401 (match_operand:SI 2 "const_int_operand" "i"))
3402 (match_operand:SI 3 "gpc_reg_operand" "r"))]
3406 int start = INTVAL (operands[2]) & 31;
3407 int size = INTVAL (operands[1]) & 31;
3409 operands[4] = GEN_INT (32 - start - size);
3410 operands[1] = GEN_INT (start + size - 1);
3411 return \"rlwimi %0,%3,%h4,%h2,%h1\";
3413 [(set_attr "type" "insert")])
3415 (define_insn "*insvsi_internal1"
3416 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
3417 (match_operand:SI 1 "const_int_operand" "i")
3418 (match_operand:SI 2 "const_int_operand" "i"))
3419 (rotate:SI (match_operand:SI 3 "gpc_reg_operand" "r")
3420 (match_operand:SI 4 "const_int_operand" "i")))]
3421 "(32 - (INTVAL (operands[4]) & 31)) >= INTVAL (operands[1])"
3424 int shift = INTVAL (operands[4]) & 31;
3425 int start = INTVAL (operands[2]) & 31;
3426 int size = INTVAL (operands[1]) & 31;
3428 operands[4] = GEN_INT (shift - start - size);
3429 operands[1] = GEN_INT (start + size - 1);
3430 return \"rlwimi %0,%3,%h4,%h2,%h1\";
3432 [(set_attr "type" "insert")])
3434 (define_insn "*insvsi_internal2"
3435 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
3436 (match_operand:SI 1 "const_int_operand" "i")
3437 (match_operand:SI 2 "const_int_operand" "i"))
3438 (ashiftrt:SI (match_operand:SI 3 "gpc_reg_operand" "r")
3439 (match_operand:SI 4 "const_int_operand" "i")))]
3440 "(32 - (INTVAL (operands[4]) & 31)) >= INTVAL (operands[1])"
3443 int shift = INTVAL (operands[4]) & 31;
3444 int start = INTVAL (operands[2]) & 31;
3445 int size = INTVAL (operands[1]) & 31;
3447 operands[4] = GEN_INT (32 - shift - start - size);
3448 operands[1] = GEN_INT (start + size - 1);
3449 return \"rlwimi %0,%3,%h4,%h2,%h1\";
3451 [(set_attr "type" "insert")])
3453 (define_insn "*insvsi_internal3"
3454 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
3455 (match_operand:SI 1 "const_int_operand" "i")
3456 (match_operand:SI 2 "const_int_operand" "i"))
3457 (lshiftrt:SI (match_operand:SI 3 "gpc_reg_operand" "r")
3458 (match_operand:SI 4 "const_int_operand" "i")))]
3459 "(32 - (INTVAL (operands[4]) & 31)) >= INTVAL (operands[1])"
3462 int shift = INTVAL (operands[4]) & 31;
3463 int start = INTVAL (operands[2]) & 31;
3464 int size = INTVAL (operands[1]) & 31;
3466 operands[4] = GEN_INT (32 - shift - start - size);
3467 operands[1] = GEN_INT (start + size - 1);
3468 return \"rlwimi %0,%3,%h4,%h2,%h1\";
3470 [(set_attr "type" "insert")])
3472 (define_insn "*insvsi_internal4"
3473 [(set (zero_extract:SI (match_operand:SI 0 "gpc_reg_operand" "+r")
3474 (match_operand:SI 1 "const_int_operand" "i")
3475 (match_operand:SI 2 "const_int_operand" "i"))
3476 (zero_extract:SI (match_operand:SI 3 "gpc_reg_operand" "r")
3477 (match_operand:SI 4 "const_int_operand" "i")
3478 (match_operand:SI 5 "const_int_operand" "i")))]
3479 "INTVAL (operands[4]) >= INTVAL (operands[1])"
3482 int extract_start = INTVAL (operands[5]) & 31;
3483 int extract_size = INTVAL (operands[4]) & 31;
3484 int insert_start = INTVAL (operands[2]) & 31;
3485 int insert_size = INTVAL (operands[1]) & 31;
3487 /* Align extract field with insert field */
3488 operands[5] = GEN_INT (extract_start + extract_size - insert_start - insert_size);
3489 operands[1] = GEN_INT (insert_start + insert_size - 1);
3490 return \"rlwimi %0,%3,%h5,%h2,%h1\";
3492 [(set_attr "type" "insert")])
3494 ;; combine patterns for rlwimi
3495 (define_insn "*insvsi_internal5"
3496 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
3497 (ior:SI (and:SI (match_operand:SI 4 "gpc_reg_operand" "0")
3498 (match_operand:SI 1 "mask_operand" "i"))
3499 (and:SI (lshiftrt:SI (match_operand:SI 3 "gpc_reg_operand" "r")
3500 (match_operand:SI 2 "const_int_operand" "i"))
3501 (match_operand:SI 5 "mask_operand" "i"))))]
3502 "INTVAL(operands[1]) == ~INTVAL(operands[5])"
3505 int me = extract_ME(operands[5]);
3506 int mb = extract_MB(operands[5]);
3507 operands[4] = GEN_INT(32 - INTVAL(operands[2]));
3508 operands[2] = GEN_INT(mb);
3509 operands[1] = GEN_INT(me);
3510 return \"rlwimi %0,%3,%h4,%h2,%h1\";
3512 [(set_attr "type" "insert")])
3514 (define_insn "*insvsi_internal6"
3515 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
3516 (ior:SI (and:SI (lshiftrt:SI (match_operand:SI 3 "gpc_reg_operand" "r")
3517 (match_operand:SI 2 "const_int_operand" "i"))
3518 (match_operand:SI 5 "mask_operand" "i"))
3519 (and:SI (match_operand:SI 4 "gpc_reg_operand" "0")
3520 (match_operand:SI 1 "mask_operand" "i"))))]
3521 "INTVAL(operands[1]) == ~INTVAL(operands[5])"
3524 int me = extract_ME(operands[5]);
3525 int mb = extract_MB(operands[5]);
3526 operands[4] = GEN_INT(32 - INTVAL(operands[2]));
3527 operands[2] = GEN_INT(mb);
3528 operands[1] = GEN_INT(me);
3529 return \"rlwimi %0,%3,%h4,%h2,%h1\";
3531 [(set_attr "type" "insert")])
3533 (define_insn "insvdi_internal"
3534 [(set (zero_extract:DI (match_operand:DI 0 "gpc_reg_operand" "+r")
3535 (match_operand:SI 1 "const_int_operand" "i")
3536 (match_operand:SI 2 "const_int_operand" "i"))
3537 (match_operand:DI 3 "gpc_reg_operand" "r"))]
3541 int start = INTVAL (operands[2]) & 63;
3542 int size = INTVAL (operands[1]) & 63;
3544 operands[1] = GEN_INT (64 - start - size);
3545 return \"rldimi %0,%3,%H1,%H2\";
3547 [(set_attr "type" "insert")
3548 (set_attr "size" "64")])
3550 (define_insn "*insvdi_internal2"
3551 [(set (zero_extract:DI (match_operand:DI 0 "gpc_reg_operand" "+r")
3552 (match_operand:SI 1 "const_int_operand" "i")
3553 (match_operand:SI 2 "const_int_operand" "i"))
3554 (ashiftrt:DI (match_operand:DI 3 "gpc_reg_operand" "r")
3555 (match_operand:SI 4 "const_int_operand" "i")))]
3557 && insvdi_rshift_rlwimi_p (operands[1], operands[2], operands[4])"
3560 int shift = INTVAL (operands[4]) & 63;
3561 int start = (INTVAL (operands[2]) & 63) - 32;
3562 int size = INTVAL (operands[1]) & 63;
3564 operands[4] = GEN_INT (64 - shift - start - size);
3565 operands[2] = GEN_INT (start);
3566 operands[1] = GEN_INT (start + size - 1);
3567 return \"rlwimi %0,%3,%h4,%h2,%h1\";
3570 (define_insn "*insvdi_internal3"
3571 [(set (zero_extract:DI (match_operand:DI 0 "gpc_reg_operand" "+r")
3572 (match_operand:SI 1 "const_int_operand" "i")
3573 (match_operand:SI 2 "const_int_operand" "i"))
3574 (lshiftrt:DI (match_operand:DI 3 "gpc_reg_operand" "r")
3575 (match_operand:SI 4 "const_int_operand" "i")))]
3577 && insvdi_rshift_rlwimi_p (operands[1], operands[2], operands[4])"
3580 int shift = INTVAL (operands[4]) & 63;
3581 int start = (INTVAL (operands[2]) & 63) - 32;
3582 int size = INTVAL (operands[1]) & 63;
3584 operands[4] = GEN_INT (64 - shift - start - size);
3585 operands[2] = GEN_INT (start);
3586 operands[1] = GEN_INT (start + size - 1);
3587 return \"rlwimi %0,%3,%h4,%h2,%h1\";
3590 (define_expand "extzv"
3591 [(set (match_operand 0 "gpc_reg_operand" "")
3592 (zero_extract (match_operand 1 "gpc_reg_operand" "")
3593 (match_operand:SI 2 "const_int_operand" "")
3594 (match_operand:SI 3 "const_int_operand" "")))]
3598 /* Do not handle 16/8 bit structures that fit in HI/QI modes directly, since
3599 the (SUBREG:SI (REG:HI xxx)) that is otherwise generated can confuse the
3600 compiler if the address of the structure is taken later. */
3601 if (GET_CODE (operands[0]) == SUBREG
3602 && (GET_MODE_SIZE (GET_MODE (SUBREG_REG (operands[0]))) < UNITS_PER_WORD))
3605 if (TARGET_POWERPC64 && GET_MODE (operands[1]) == DImode)
3606 emit_insn (gen_extzvdi_internal (operands[0], operands[1], operands[2],
3609 emit_insn (gen_extzvsi_internal (operands[0], operands[1], operands[2],
3614 (define_insn "extzvsi_internal"
3615 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
3616 (zero_extract:SI (match_operand:SI 1 "gpc_reg_operand" "r")
3617 (match_operand:SI 2 "const_int_operand" "i")
3618 (match_operand:SI 3 "const_int_operand" "i")))]
3622 int start = INTVAL (operands[3]) & 31;
3623 int size = INTVAL (operands[2]) & 31;
3625 if (start + size >= 32)
3626 operands[3] = const0_rtx;
3628 operands[3] = GEN_INT (start + size);
3629 return \"rlwinm %0,%1,%3,%s2,31\";
3631 [(set_attr "type" "shift")])
3633 (define_insn "*extzvsi_internal1"
3634 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
3635 (compare:CC (zero_extract:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
3636 (match_operand:SI 2 "const_int_operand" "i,i")
3637 (match_operand:SI 3 "const_int_operand" "i,i"))
3639 (clobber (match_scratch:SI 4 "=r,r"))]
3643 int start = INTVAL (operands[3]) & 31;
3644 int size = INTVAL (operands[2]) & 31;
3646 /* Force split for non-cc0 compare. */
3647 if (which_alternative == 1)
3650 /* If the bit-field being tested fits in the upper or lower half of a
3651 word, it is possible to use andiu. or andil. to test it. This is
3652 useful because the condition register set-use delay is smaller for
3653 andi[ul]. than for rlinm. This doesn't work when the starting bit
3654 position is 0 because the LT and GT bits may be set wrong. */
3656 if ((start > 0 && start + size <= 16) || start >= 16)
3658 operands[3] = GEN_INT (((1 << (16 - (start & 15)))
3659 - (1 << (16 - (start & 15) - size))));
3661 return \"andis. %4,%1,%3\";
3663 return \"andi. %4,%1,%3\";
3666 if (start + size >= 32)
3667 operands[3] = const0_rtx;
3669 operands[3] = GEN_INT (start + size);
3670 return \"rlwinm. %4,%1,%3,%s2,31\";
3672 [(set_attr "type" "shift")
3673 (set_attr "dot" "yes")
3674 (set_attr "length" "4,8")])
3677 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
3678 (compare:CC (zero_extract:SI (match_operand:SI 1 "gpc_reg_operand" "")
3679 (match_operand:SI 2 "const_int_operand" "")
3680 (match_operand:SI 3 "const_int_operand" ""))
3682 (clobber (match_scratch:SI 4 ""))]
3685 (zero_extract:SI (match_dup 1) (match_dup 2)
3688 (compare:CC (match_dup 4)
3692 (define_insn "*extzvsi_internal2"
3693 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
3694 (compare:CC (zero_extract:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
3695 (match_operand:SI 2 "const_int_operand" "i,i")
3696 (match_operand:SI 3 "const_int_operand" "i,i"))
3698 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
3699 (zero_extract:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
3703 int start = INTVAL (operands[3]) & 31;
3704 int size = INTVAL (operands[2]) & 31;
3706 /* Force split for non-cc0 compare. */
3707 if (which_alternative == 1)
3710 /* Since we are using the output value, we can't ignore any need for
3711 a shift. The bit-field must end at the LSB. */
3712 if (start >= 16 && start + size == 32)
3714 operands[3] = GEN_INT ((1 << size) - 1);
3715 return \"andi. %0,%1,%3\";
3718 if (start + size >= 32)
3719 operands[3] = const0_rtx;
3721 operands[3] = GEN_INT (start + size);
3722 return \"rlwinm. %0,%1,%3,%s2,31\";
3724 [(set_attr "type" "shift")
3725 (set_attr "dot" "yes")
3726 (set_attr "length" "4,8")])
3729 [(set (match_operand:CC 4 "cc_reg_not_micro_cr0_operand" "")
3730 (compare:CC (zero_extract:SI (match_operand:SI 1 "gpc_reg_operand" "")
3731 (match_operand:SI 2 "const_int_operand" "")
3732 (match_operand:SI 3 "const_int_operand" ""))
3734 (set (match_operand:SI 0 "gpc_reg_operand" "")
3735 (zero_extract:SI (match_dup 1) (match_dup 2) (match_dup 3)))]
3738 (zero_extract:SI (match_dup 1) (match_dup 2) (match_dup 3)))
3740 (compare:CC (match_dup 0)
3744 (define_insn "extzvdi_internal"
3745 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
3746 (zero_extract:DI (match_operand:DI 1 "gpc_reg_operand" "r")
3747 (match_operand:SI 2 "const_int_operand" "i")
3748 (match_operand:SI 3 "const_int_operand" "i")))]
3752 int start = INTVAL (operands[3]) & 63;
3753 int size = INTVAL (operands[2]) & 63;
3755 if (start + size >= 64)
3756 operands[3] = const0_rtx;
3758 operands[3] = GEN_INT (start + size);
3759 operands[2] = GEN_INT (64 - size);
3760 return \"rldicl %0,%1,%3,%2\";
3762 [(set_attr "type" "shift")])
3764 (define_insn "*extzvdi_internal1"
3765 [(set (match_operand:CC 0 "gpc_reg_operand" "=x")
3766 (compare:CC (zero_extract:DI (match_operand:DI 1 "gpc_reg_operand" "r")
3767 (match_operand:SI 2 "const_int_operand" "i")
3768 (match_operand:SI 3 "const_int_operand" "i"))
3770 (clobber (match_scratch:DI 4 "=r"))]
3771 "TARGET_64BIT && rs6000_gen_cell_microcode"
3774 int start = INTVAL (operands[3]) & 63;
3775 int size = INTVAL (operands[2]) & 63;
3777 if (start + size >= 64)
3778 operands[3] = const0_rtx;
3780 operands[3] = GEN_INT (start + size);
3781 operands[2] = GEN_INT (64 - size);
3782 return \"rldicl. %4,%1,%3,%2\";
3784 [(set_attr "type" "shift")
3785 (set_attr "dot" "yes")])
3787 (define_insn "*extzvdi_internal2"
3788 [(set (match_operand:CC 4 "gpc_reg_operand" "=x")
3789 (compare:CC (zero_extract:DI (match_operand:DI 1 "gpc_reg_operand" "r")
3790 (match_operand:SI 2 "const_int_operand" "i")
3791 (match_operand:SI 3 "const_int_operand" "i"))
3793 (set (match_operand:DI 0 "gpc_reg_operand" "=r")
3794 (zero_extract:DI (match_dup 1) (match_dup 2) (match_dup 3)))]
3795 "TARGET_64BIT && rs6000_gen_cell_microcode"
3798 int start = INTVAL (operands[3]) & 63;
3799 int size = INTVAL (operands[2]) & 63;
3801 if (start + size >= 64)
3802 operands[3] = const0_rtx;
3804 operands[3] = GEN_INT (start + size);
3805 operands[2] = GEN_INT (64 - size);
3806 return \"rldicl. %0,%1,%3,%2\";
3808 [(set_attr "type" "shift")
3809 (set_attr "dot" "yes")])
3812 (define_insn "rotl<mode>3"
3813 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
3814 (rotate:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
3815 (match_operand:SI 2 "reg_or_cint_operand" "rn")))]
3817 "rotl<wd>%I2 %0,%1,%<hH>2"
3818 [(set_attr "type" "shift")
3819 (set_attr "maybe_var_shift" "yes")])
3821 (define_insn "*rotlsi3_64"
3822 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
3824 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
3825 (match_operand:SI 2 "reg_or_cint_operand" "rn"))))]
3827 "rotlw%I2 %0,%1,%h2"
3828 [(set_attr "type" "shift")
3829 (set_attr "maybe_var_shift" "yes")])
3831 (define_insn_and_split "*rotl<mode>3_dot"
3832 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
3833 (compare:CC (rotate:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
3834 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn"))
3836 (clobber (match_scratch:GPR 0 "=r,r"))]
3837 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
3839 rotl<wd>%I2. %0,%1,%<hH>2
3841 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
3843 (rotate:GPR (match_dup 1)
3846 (compare:CC (match_dup 0)
3849 [(set_attr "type" "shift")
3850 (set_attr "maybe_var_shift" "yes")
3851 (set_attr "dot" "yes")
3852 (set_attr "length" "4,8")])
3854 (define_insn_and_split "*rotl<mode>3_dot2"
3855 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
3856 (compare:CC (rotate:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
3857 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn"))
3859 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
3860 (rotate:GPR (match_dup 1)
3862 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
3864 rotl<wd>%I2. %0,%1,%<hH>2
3866 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
3868 (rotate:GPR (match_dup 1)
3871 (compare:CC (match_dup 0)
3874 [(set_attr "type" "shift")
3875 (set_attr "maybe_var_shift" "yes")
3876 (set_attr "dot" "yes")
3877 (set_attr "length" "4,8")])
3880 (define_insn "*rotlsi3_internal4"
3881 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
3882 (and:SI (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
3883 (match_operand:SI 2 "reg_or_cint_operand" "rn"))
3884 (match_operand:SI 3 "mask_operand" "n")))]
3886 "rlw%I2nm %0,%1,%h2,%m3,%M3"
3887 [(set_attr "type" "shift")
3888 (set_attr "maybe_var_shift" "yes")])
3890 (define_insn "*rotlsi3_internal5"
3891 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
3893 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
3894 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn"))
3895 (match_operand:SI 3 "mask_operand" "n,n"))
3897 (clobber (match_scratch:SI 4 "=r,r"))]
3900 rlw%I2nm. %4,%1,%h2,%m3,%M3
3902 [(set_attr "type" "shift")
3903 (set_attr "maybe_var_shift" "yes")
3904 (set_attr "dot" "yes")
3905 (set_attr "length" "4,8")])
3908 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
3910 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "")
3911 (match_operand:SI 2 "reg_or_cint_operand" ""))
3912 (match_operand:SI 3 "mask_operand" ""))
3914 (clobber (match_scratch:SI 4 ""))]
3917 (and:SI (rotate:SI (match_dup 1)
3921 (compare:CC (match_dup 4)
3925 (define_insn "*rotlsi3_internal6"
3926 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
3928 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
3929 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn"))
3930 (match_operand:SI 3 "mask_operand" "n,n"))
3932 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
3933 (and:SI (rotate:SI (match_dup 1) (match_dup 2)) (match_dup 3)))]
3936 rlw%I2nm. %0,%1,%h2,%m3,%M3
3938 [(set_attr "type" "shift")
3939 (set_attr "maybe_var_shift" "yes")
3940 (set_attr "dot" "yes")
3941 (set_attr "length" "4,8")])
3944 [(set (match_operand:CC 4 "cc_reg_not_micro_cr0_operand" "")
3946 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "")
3947 (match_operand:SI 2 "reg_or_cint_operand" ""))
3948 (match_operand:SI 3 "mask_operand" ""))
3950 (set (match_operand:SI 0 "gpc_reg_operand" "")
3951 (and:SI (rotate:SI (match_dup 1) (match_dup 2)) (match_dup 3)))]
3954 (and:SI (rotate:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
3956 (compare:CC (match_dup 0)
3960 (define_insn "*rotlsi3_internal7le"
3961 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
3964 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
3965 (match_operand:SI 2 "reg_or_cint_operand" "ri")) 0)))]
3967 "rlw%I2nm %0,%1,%h2,0xff"
3968 [(set (attr "cell_micro")
3969 (if_then_else (match_operand:SI 2 "const_int_operand" "")
3970 (const_string "not")
3971 (const_string "always")))
3972 (set_attr "type" "shift")])
3974 (define_insn "*rotlsi3_internal7be"
3975 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
3978 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
3979 (match_operand:SI 2 "reg_or_cint_operand" "ri")) 3)))]
3981 "rlw%I2nm %0,%1,%h2,0xff"
3982 [(set (attr "cell_micro")
3983 (if_then_else (match_operand:SI 2 "const_int_operand" "")
3984 (const_string "not")
3985 (const_string "always")))
3986 (set_attr "type" "shift")])
3988 (define_insn "*rotlsi3_internal8le"
3989 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
3990 (compare:CC (zero_extend:SI
3992 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
3993 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn")) 0))
3995 (clobber (match_scratch:SI 3 "=r,r"))]
3998 rlw%I2nm. %3,%1,%h2,0xff
4000 [(set_attr "type" "shift")
4001 (set_attr "maybe_var_shift" "yes")
4002 (set_attr "dot" "yes")
4003 (set_attr "length" "4,8")])
4005 (define_insn "*rotlsi3_internal8be"
4006 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
4007 (compare:CC (zero_extend:SI
4009 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4010 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn")) 3))
4012 (clobber (match_scratch:SI 3 "=r,r"))]
4015 rlw%I2nm. %3,%1,%h2,0xff
4017 [(set_attr "type" "shift")
4018 (set_attr "maybe_var_shift" "yes")
4019 (set_attr "dot" "yes")
4020 (set_attr "length" "4,8")])
4023 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
4024 (compare:CC (zero_extend:SI
4026 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "")
4027 (match_operand:SI 2 "reg_or_cint_operand" "")) 0))
4029 (clobber (match_scratch:SI 3 ""))]
4030 "!BYTES_BIG_ENDIAN && reload_completed"
4032 (zero_extend:SI (subreg:QI
4033 (rotate:SI (match_dup 1)
4036 (compare:CC (match_dup 3)
4041 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
4042 (compare:CC (zero_extend:SI
4044 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "")
4045 (match_operand:SI 2 "reg_or_cint_operand" "")) 3))
4047 (clobber (match_scratch:SI 3 ""))]
4048 "BYTES_BIG_ENDIAN && reload_completed"
4050 (zero_extend:SI (subreg:QI
4051 (rotate:SI (match_dup 1)
4054 (compare:CC (match_dup 3)
4058 (define_insn "*rotlsi3_internal9le"
4059 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4060 (compare:CC (zero_extend:SI
4062 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4063 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn")) 0))
4065 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
4066 (zero_extend:SI (subreg:QI (rotate:SI (match_dup 1) (match_dup 2)) 0)))]
4069 rlw%I2nm. %0,%1,%h2,0xff
4071 [(set_attr "type" "shift")
4072 (set_attr "maybe_var_shift" "yes")
4073 (set_attr "dot" "yes")
4074 (set_attr "length" "4,8")])
4076 (define_insn "*rotlsi3_internal9be"
4077 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4078 (compare:CC (zero_extend:SI
4080 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4081 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn")) 3))
4083 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
4084 (zero_extend:SI (subreg:QI (rotate:SI (match_dup 1) (match_dup 2)) 3)))]
4087 rlw%I2nm. %0,%1,%h2,0xff
4089 [(set_attr "type" "shift")
4090 (set_attr "maybe_var_shift" "yes")
4091 (set_attr "dot" "yes")
4092 (set_attr "length" "4,8")])
4095 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
4096 (compare:CC (zero_extend:SI
4098 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "")
4099 (match_operand:SI 2 "reg_or_cint_operand" "")) 0))
4101 (set (match_operand:SI 0 "gpc_reg_operand" "")
4102 (zero_extend:SI (subreg:QI (rotate:SI (match_dup 1) (match_dup 2)) 0)))]
4103 "!BYTES_BIG_ENDIAN && reload_completed"
4105 (zero_extend:SI (subreg:QI (rotate:SI (match_dup 1) (match_dup 2)) 0)))
4107 (compare:CC (match_dup 0)
4112 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
4113 (compare:CC (zero_extend:SI
4115 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "")
4116 (match_operand:SI 2 "reg_or_cint_operand" "")) 3))
4118 (set (match_operand:SI 0 "gpc_reg_operand" "")
4119 (zero_extend:SI (subreg:QI (rotate:SI (match_dup 1) (match_dup 2)) 3)))]
4120 "BYTES_BIG_ENDIAN && reload_completed"
4122 (zero_extend:SI (subreg:QI (rotate:SI (match_dup 1) (match_dup 2)) 3)))
4124 (compare:CC (match_dup 0)
4128 (define_insn "*rotlsi3_internal10le"
4129 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
4132 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4133 (match_operand:SI 2 "reg_or_cint_operand" "rn")) 0)))]
4135 "rlw%I2nm %0,%1,%h2,0xffff"
4136 [(set_attr "type" "shift")
4137 (set_attr "maybe_var_shift" "yes")])
4139 (define_insn "*rotlsi3_internal10be"
4140 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
4143 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4144 (match_operand:SI 2 "reg_or_cint_operand" "rn")) 2)))]
4146 "rlw%I2nm %0,%1,%h2,0xffff"
4147 [(set_attr "type" "shift")
4148 (set_attr "maybe_var_shift" "yes")])
4150 (define_insn "*rotlsi3_internal11le"
4151 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
4152 (compare:CC (zero_extend:SI
4154 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4155 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn")) 0))
4157 (clobber (match_scratch:SI 3 "=r,r"))]
4160 rlw%I2nm. %3,%1,%h2,0xffff
4162 [(set_attr "type" "shift")
4163 (set_attr "maybe_var_shift" "yes")
4164 (set_attr "dot" "yes")
4165 (set_attr "length" "4,8")])
4167 (define_insn "*rotlsi3_internal11be"
4168 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
4169 (compare:CC (zero_extend:SI
4171 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4172 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn")) 2))
4174 (clobber (match_scratch:SI 3 "=r,r"))]
4177 rlw%I2nm. %3,%1,%h2,0xffff
4179 [(set_attr "type" "shift")
4180 (set_attr "maybe_var_shift" "yes")
4181 (set_attr "dot" "yes")
4182 (set_attr "length" "4,8")])
4185 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
4186 (compare:CC (zero_extend:SI
4188 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "")
4189 (match_operand:SI 2 "reg_or_cint_operand" "")) 0))
4191 (clobber (match_scratch:SI 3 ""))]
4192 "!BYTES_BIG_ENDIAN && reload_completed"
4194 (zero_extend:SI (subreg:HI
4195 (rotate:SI (match_dup 1)
4198 (compare:CC (match_dup 3)
4203 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
4204 (compare:CC (zero_extend:SI
4206 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "")
4207 (match_operand:SI 2 "reg_or_cint_operand" "")) 2))
4209 (clobber (match_scratch:SI 3 ""))]
4210 "BYTES_BIG_ENDIAN && reload_completed"
4212 (zero_extend:SI (subreg:HI
4213 (rotate:SI (match_dup 1)
4216 (compare:CC (match_dup 3)
4220 (define_insn "*rotlsi3_internal12le"
4221 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4222 (compare:CC (zero_extend:SI
4224 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4225 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn")) 0))
4227 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
4228 (zero_extend:SI (subreg:HI (rotate:SI (match_dup 1) (match_dup 2)) 0)))]
4231 rlw%I2nm. %0,%1,%h2,0xffff
4233 [(set_attr "type" "shift")
4234 (set_attr "maybe_var_shift" "yes")
4235 (set_attr "dot" "yes")
4236 (set_attr "length" "4,8")])
4238 (define_insn "*rotlsi3_internal12be"
4239 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4240 (compare:CC (zero_extend:SI
4242 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4243 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn")) 2))
4245 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
4246 (zero_extend:SI (subreg:HI (rotate:SI (match_dup 1) (match_dup 2)) 2)))]
4249 rlw%I2nm. %0,%1,%h2,0xffff
4251 [(set_attr "type" "shift")
4252 (set_attr "maybe_var_shift" "yes")
4253 (set_attr "dot" "yes")
4254 (set_attr "length" "4,8")])
4257 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
4258 (compare:CC (zero_extend:SI
4260 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "")
4261 (match_operand:SI 2 "reg_or_cint_operand" "")) 0))
4263 (set (match_operand:SI 0 "gpc_reg_operand" "")
4264 (zero_extend:SI (subreg:HI (rotate:SI (match_dup 1) (match_dup 2)) 0)))]
4265 "!BYTES_BIG_ENDIAN && reload_completed"
4267 (zero_extend:SI (subreg:HI (rotate:SI (match_dup 1) (match_dup 2)) 0)))
4269 (compare:CC (match_dup 0)
4274 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
4275 (compare:CC (zero_extend:SI
4277 (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "")
4278 (match_operand:SI 2 "reg_or_cint_operand" "")) 2))
4280 (set (match_operand:SI 0 "gpc_reg_operand" "")
4281 (zero_extend:SI (subreg:HI (rotate:SI (match_dup 1) (match_dup 2)) 2)))]
4282 "BYTES_BIG_ENDIAN && reload_completed"
4284 (zero_extend:SI (subreg:HI (rotate:SI (match_dup 1) (match_dup 2)) 2)))
4286 (compare:CC (match_dup 0)
4291 (define_insn "ashl<mode>3"
4292 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
4293 (ashift:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
4294 (match_operand:SI 2 "reg_or_cint_operand" "rn")))]
4296 "sl<wd>%I2 %0,%1,%<hH>2"
4297 [(set_attr "type" "shift")
4298 (set_attr "maybe_var_shift" "yes")])
4300 (define_insn "*ashlsi3_64"
4301 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4303 (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4304 (match_operand:SI 2 "reg_or_cint_operand" "rn"))))]
4307 [(set_attr "type" "shift")
4308 (set_attr "maybe_var_shift" "yes")])
4310 (define_insn_and_split "*ashl<mode>3_dot"
4311 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4312 (compare:CC (ashift:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
4313 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn"))
4315 (clobber (match_scratch:GPR 0 "=r,r"))]
4316 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
4318 sl<wd>%I2. %0,%1,%<hH>2
4320 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
4322 (ashift:GPR (match_dup 1)
4325 (compare:CC (match_dup 0)
4328 [(set_attr "type" "shift")
4329 (set_attr "maybe_var_shift" "yes")
4330 (set_attr "dot" "yes")
4331 (set_attr "length" "4,8")])
4333 (define_insn_and_split "*ashl<mode>3_dot2"
4334 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4335 (compare:CC (ashift:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
4336 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn"))
4338 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
4339 (ashift:GPR (match_dup 1)
4341 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
4343 sl<wd>%I2. %0,%1,%<hH>2
4345 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
4347 (ashift:GPR (match_dup 1)
4350 (compare:CC (match_dup 0)
4353 [(set_attr "type" "shift")
4354 (set_attr "maybe_var_shift" "yes")
4355 (set_attr "dot" "yes")
4356 (set_attr "length" "4,8")])
4359 (define_insn "rlwinm"
4360 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
4361 (and:SI (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4362 (match_operand:SI 2 "const_int_operand" "i"))
4363 (match_operand:SI 3 "mask_operand" "n")))]
4364 "includes_lshift_p (operands[2], operands[3])"
4365 "rlwinm %0,%1,%h2,%m3,%M3"
4366 [(set_attr "type" "shift")])
4369 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
4371 (and:SI (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4372 (match_operand:SI 2 "const_int_operand" "i,i"))
4373 (match_operand:SI 3 "mask_operand" "n,n"))
4375 (clobber (match_scratch:SI 4 "=r,r"))]
4376 "includes_lshift_p (operands[2], operands[3])"
4378 rlwinm. %4,%1,%h2,%m3,%M3
4380 [(set_attr "type" "shift")
4381 (set_attr "dot" "yes")
4382 (set_attr "length" "4,8")])
4385 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
4387 (and:SI (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "")
4388 (match_operand:SI 2 "const_int_operand" ""))
4389 (match_operand:SI 3 "mask_operand" ""))
4391 (clobber (match_scratch:SI 4 ""))]
4392 "includes_lshift_p (operands[2], operands[3]) && reload_completed"
4394 (and:SI (ashift:SI (match_dup 1) (match_dup 2))
4397 (compare:CC (match_dup 4)
4402 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
4404 (and:SI (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4405 (match_operand:SI 2 "const_int_operand" "i,i"))
4406 (match_operand:SI 3 "mask_operand" "n,n"))
4408 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
4409 (and:SI (ashift:SI (match_dup 1) (match_dup 2)) (match_dup 3)))]
4410 "includes_lshift_p (operands[2], operands[3])"
4412 rlwinm. %0,%1,%h2,%m3,%M3
4414 [(set_attr "type" "shift")
4415 (set_attr "dot" "yes")
4416 (set_attr "length" "4,8")])
4419 [(set (match_operand:CC 4 "cc_reg_not_micro_cr0_operand" "")
4421 (and:SI (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "")
4422 (match_operand:SI 2 "const_int_operand" ""))
4423 (match_operand:SI 3 "mask_operand" ""))
4425 (set (match_operand:SI 0 "gpc_reg_operand" "")
4426 (and:SI (ashift:SI (match_dup 1) (match_dup 2)) (match_dup 3)))]
4427 "includes_lshift_p (operands[2], operands[3]) && reload_completed"
4429 (and:SI (ashift:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
4431 (compare:CC (match_dup 0)
4436 (define_insn "lshr<mode>3"
4437 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
4438 (lshiftrt:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
4439 (match_operand:SI 2 "reg_or_cint_operand" "rn")))]
4441 "sr<wd>%I2 %0,%1,%<hH>2"
4442 [(set_attr "type" "shift")
4443 (set_attr "maybe_var_shift" "yes")])
4445 (define_insn "*lshrsi3_64"
4446 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4448 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4449 (match_operand:SI 2 "reg_or_cint_operand" "rn"))))]
4452 [(set_attr "type" "shift")
4453 (set_attr "maybe_var_shift" "yes")])
4455 (define_insn_and_split "*lshr<mode>3_dot"
4456 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4457 (compare:CC (lshiftrt:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
4458 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn"))
4460 (clobber (match_scratch:GPR 0 "=r,r"))]
4461 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
4463 sr<wd>%I2. %0,%1,%<hH>2
4465 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
4467 (lshiftrt:GPR (match_dup 1)
4470 (compare:CC (match_dup 0)
4473 [(set_attr "type" "shift")
4474 (set_attr "maybe_var_shift" "yes")
4475 (set_attr "dot" "yes")
4476 (set_attr "length" "4,8")])
4478 (define_insn_and_split "*lshr<mode>3_dot2"
4479 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4480 (compare:CC (lshiftrt:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
4481 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn"))
4483 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
4484 (lshiftrt:GPR (match_dup 1)
4486 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
4488 sr<wd>%I2. %0,%1,%<hH>2
4490 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
4492 (lshiftrt:GPR (match_dup 1)
4495 (compare:CC (match_dup 0)
4498 [(set_attr "type" "shift")
4499 (set_attr "maybe_var_shift" "yes")
4500 (set_attr "dot" "yes")
4501 (set_attr "length" "4,8")])
4505 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
4506 (and:SI (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4507 (match_operand:SI 2 "const_int_operand" "i"))
4508 (match_operand:SI 3 "mask_operand" "n")))]
4509 "includes_rshift_p (operands[2], operands[3])"
4510 "rlwinm %0,%1,%s2,%m3,%M3"
4511 [(set_attr "type" "shift")])
4514 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
4516 (and:SI (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4517 (match_operand:SI 2 "const_int_operand" "i,i"))
4518 (match_operand:SI 3 "mask_operand" "n,n"))
4520 (clobber (match_scratch:SI 4 "=r,r"))]
4521 "includes_rshift_p (operands[2], operands[3])"
4523 rlwinm. %4,%1,%s2,%m3,%M3
4525 [(set_attr "type" "shift")
4526 (set_attr "dot" "yes")
4527 (set_attr "length" "4,8")])
4530 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
4532 (and:SI (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
4533 (match_operand:SI 2 "const_int_operand" ""))
4534 (match_operand:SI 3 "mask_operand" ""))
4536 (clobber (match_scratch:SI 4 ""))]
4537 "includes_rshift_p (operands[2], operands[3]) && reload_completed"
4539 (and:SI (lshiftrt:SI (match_dup 1) (match_dup 2))
4542 (compare:CC (match_dup 4)
4547 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
4549 (and:SI (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4550 (match_operand:SI 2 "const_int_operand" "i,i"))
4551 (match_operand:SI 3 "mask_operand" "n,n"))
4553 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
4554 (and:SI (lshiftrt:SI (match_dup 1) (match_dup 2)) (match_dup 3)))]
4555 "includes_rshift_p (operands[2], operands[3])"
4557 rlwinm. %0,%1,%s2,%m3,%M3
4559 [(set_attr "type" "shift")
4560 (set_attr "dot" "yes")
4561 (set_attr "length" "4,8")])
4564 [(set (match_operand:CC 4 "cc_reg_not_micro_cr0_operand" "")
4566 (and:SI (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
4567 (match_operand:SI 2 "const_int_operand" ""))
4568 (match_operand:SI 3 "mask_operand" ""))
4570 (set (match_operand:SI 0 "gpc_reg_operand" "")
4571 (and:SI (lshiftrt:SI (match_dup 1) (match_dup 2)) (match_dup 3)))]
4572 "includes_rshift_p (operands[2], operands[3]) && reload_completed"
4574 (and:SI (lshiftrt:SI (match_dup 1) (match_dup 2)) (match_dup 3)))
4576 (compare:CC (match_dup 0)
4580 (define_insn "*lshiftrt_internal1le"
4581 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
4584 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4585 (match_operand:SI 2 "const_int_operand" "i")) 0)))]
4586 "!BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (255))"
4587 "rlwinm %0,%1,%s2,0xff"
4588 [(set_attr "type" "shift")])
4590 (define_insn "*lshiftrt_internal1be"
4591 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
4594 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4595 (match_operand:SI 2 "const_int_operand" "i")) 3)))]
4596 "BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (255))"
4597 "rlwinm %0,%1,%s2,0xff"
4598 [(set_attr "type" "shift")])
4600 (define_insn "*lshiftrt_internal2le"
4601 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
4605 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4606 (match_operand:SI 2 "const_int_operand" "i,i")) 0))
4608 (clobber (match_scratch:SI 3 "=r,r"))]
4609 "!BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (255))"
4611 rlwinm. %3,%1,%s2,0xff
4613 [(set_attr "type" "shift")
4614 (set_attr "dot" "yes")
4615 (set_attr "length" "4,8")])
4617 (define_insn "*lshiftrt_internal2be"
4618 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
4622 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4623 (match_operand:SI 2 "const_int_operand" "i,i")) 3))
4625 (clobber (match_scratch:SI 3 "=r,r"))]
4626 "BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (255))"
4628 rlwinm. %3,%1,%s2,0xff
4630 [(set_attr "type" "shift")
4631 (set_attr "dot" "yes")
4632 (set_attr "length" "4,8")])
4635 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
4639 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
4640 (match_operand:SI 2 "const_int_operand" "")) 0))
4642 (clobber (match_scratch:SI 3 ""))]
4643 "!BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (255)) && reload_completed"
4645 (zero_extend:SI (subreg:QI
4646 (lshiftrt:SI (match_dup 1)
4649 (compare:CC (match_dup 3)
4654 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
4658 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
4659 (match_operand:SI 2 "const_int_operand" "")) 3))
4661 (clobber (match_scratch:SI 3 ""))]
4662 "BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (255)) && reload_completed"
4664 (zero_extend:SI (subreg:QI
4665 (lshiftrt:SI (match_dup 1)
4668 (compare:CC (match_dup 3)
4672 (define_insn "*lshiftrt_internal3le"
4673 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4677 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4678 (match_operand:SI 2 "const_int_operand" "i,i")) 0))
4680 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
4681 (zero_extend:SI (subreg:QI (lshiftrt:SI (match_dup 1) (match_dup 2)) 0)))]
4682 "!BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (255))"
4684 rlwinm. %0,%1,%s2,0xff
4686 [(set_attr "type" "shift")
4687 (set_attr "dot" "yes")
4688 (set_attr "length" "4,8")])
4690 (define_insn "*lshiftrt_internal3be"
4691 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4695 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4696 (match_operand:SI 2 "const_int_operand" "i,i")) 3))
4698 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
4699 (zero_extend:SI (subreg:QI (lshiftrt:SI (match_dup 1) (match_dup 2)) 3)))]
4700 "BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (255))"
4702 rlwinm. %0,%1,%s2,0xff
4704 [(set_attr "type" "shift")
4705 (set_attr "dot" "yes")
4706 (set_attr "length" "4,8")])
4709 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
4713 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
4714 (match_operand:SI 2 "const_int_operand" "")) 0))
4716 (set (match_operand:SI 0 "gpc_reg_operand" "")
4717 (zero_extend:SI (subreg:QI (lshiftrt:SI (match_dup 1) (match_dup 2)) 0)))]
4718 "!BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (255)) && reload_completed"
4720 (zero_extend:SI (subreg:QI (lshiftrt:SI (match_dup 1) (match_dup 2)) 0)))
4722 (compare:CC (match_dup 0)
4727 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
4731 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
4732 (match_operand:SI 2 "const_int_operand" "")) 3))
4734 (set (match_operand:SI 0 "gpc_reg_operand" "")
4735 (zero_extend:SI (subreg:QI (lshiftrt:SI (match_dup 1) (match_dup 2)) 3)))]
4736 "BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (255)) && reload_completed"
4738 (zero_extend:SI (subreg:QI (lshiftrt:SI (match_dup 1) (match_dup 2)) 3)))
4740 (compare:CC (match_dup 0)
4744 (define_insn "*lshiftrt_internal4le"
4745 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
4748 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4749 (match_operand:SI 2 "const_int_operand" "i")) 0)))]
4750 "!BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (65535))"
4751 "rlwinm %0,%1,%s2,0xffff"
4752 [(set_attr "type" "shift")])
4754 (define_insn "*lshiftrt_internal4be"
4755 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
4758 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4759 (match_operand:SI 2 "const_int_operand" "i")) 2)))]
4760 "BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (65535))"
4761 "rlwinm %0,%1,%s2,0xffff"
4762 [(set_attr "type" "shift")])
4764 (define_insn "*lshiftrt_internal5le"
4765 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
4769 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4770 (match_operand:SI 2 "const_int_operand" "i,i")) 0))
4772 (clobber (match_scratch:SI 3 "=r,r"))]
4773 "!BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (65535))"
4775 rlwinm. %3,%1,%s2,0xffff
4777 [(set_attr "type" "shift")
4778 (set_attr "dot" "yes")
4779 (set_attr "length" "4,8")])
4781 (define_insn "*lshiftrt_internal5be"
4782 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
4786 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4787 (match_operand:SI 2 "const_int_operand" "i,i")) 2))
4789 (clobber (match_scratch:SI 3 "=r,r"))]
4790 "BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (65535))"
4792 rlwinm. %3,%1,%s2,0xffff
4794 [(set_attr "type" "shift")
4795 (set_attr "dot" "yes")
4796 (set_attr "length" "4,8")])
4799 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
4803 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
4804 (match_operand:SI 2 "const_int_operand" "")) 0))
4806 (clobber (match_scratch:SI 3 ""))]
4807 "!BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (65535)) && reload_completed"
4809 (zero_extend:SI (subreg:HI
4810 (lshiftrt:SI (match_dup 1)
4813 (compare:CC (match_dup 3)
4818 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
4822 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
4823 (match_operand:SI 2 "const_int_operand" "")) 2))
4825 (clobber (match_scratch:SI 3 ""))]
4826 "BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (65535)) && reload_completed"
4828 (zero_extend:SI (subreg:HI
4829 (lshiftrt:SI (match_dup 1)
4832 (compare:CC (match_dup 3)
4836 (define_insn "*lshiftrt_internal5le"
4837 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4841 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4842 (match_operand:SI 2 "const_int_operand" "i,i")) 0))
4844 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
4845 (zero_extend:SI (subreg:HI (lshiftrt:SI (match_dup 1) (match_dup 2)) 0)))]
4846 "!BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (65535))"
4848 rlwinm. %0,%1,%s2,0xffff
4850 [(set_attr "type" "shift")
4851 (set_attr "dot" "yes")
4852 (set_attr "length" "4,8")])
4854 (define_insn "*lshiftrt_internal5be"
4855 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4859 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
4860 (match_operand:SI 2 "const_int_operand" "i,i")) 2))
4862 (set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
4863 (zero_extend:SI (subreg:HI (lshiftrt:SI (match_dup 1) (match_dup 2)) 2)))]
4864 "BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (65535))"
4866 rlwinm. %0,%1,%s2,0xffff
4868 [(set_attr "type" "shift")
4869 (set_attr "dot" "yes")
4870 (set_attr "length" "4,8")])
4873 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
4877 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
4878 (match_operand:SI 2 "const_int_operand" "")) 0))
4880 (set (match_operand:SI 0 "gpc_reg_operand" "")
4881 (zero_extend:SI (subreg:HI (lshiftrt:SI (match_dup 1) (match_dup 2)) 0)))]
4882 "!BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (65535)) && reload_completed"
4884 (zero_extend:SI (subreg:HI (lshiftrt:SI (match_dup 1) (match_dup 2)) 0)))
4886 (compare:CC (match_dup 0)
4891 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
4895 (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "")
4896 (match_operand:SI 2 "const_int_operand" "")) 2))
4898 (set (match_operand:SI 0 "gpc_reg_operand" "")
4899 (zero_extend:SI (subreg:HI (lshiftrt:SI (match_dup 1) (match_dup 2)) 2)))]
4900 "BYTES_BIG_ENDIAN && includes_rshift_p (operands[2], GEN_INT (65535)) && reload_completed"
4902 (zero_extend:SI (subreg:HI (lshiftrt:SI (match_dup 1) (match_dup 2)) 2)))
4904 (compare:CC (match_dup 0)
4909 (define_expand "ashr<mode>3"
4910 [(parallel [(set (match_operand:GPR 0 "gpc_reg_operand" "")
4911 (ashiftrt:GPR (match_operand:GPR 1 "gpc_reg_operand" "")
4912 (match_operand:SI 2 "reg_or_cint_operand" "")))
4913 (clobber (reg:GPR CA_REGNO))])]
4916 /* The generic code does not generate optimal code for the low word
4917 (it should be a rlwimi and a rot). Until we have target code to
4918 solve this generically, keep this expander. */
4920 if (<MODE>mode == DImode && !TARGET_POWERPC64)
4922 if (CONST_INT_P (operands[2]))
4924 emit_insn (gen_ashrdi3_no_power (operands[0], operands[1], operands[2]));
4932 (define_insn "*ashr<mode>3"
4933 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
4934 (ashiftrt:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
4935 (match_operand:SI 2 "reg_or_cint_operand" "rn")))
4936 (clobber (reg:GPR CA_REGNO))]
4938 "sra<wd>%I2 %0,%1,%<hH>2"
4939 [(set_attr "type" "shift")
4940 (set_attr "maybe_var_shift" "yes")])
4942 (define_insn "*ashrsi3_64"
4943 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
4945 (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r")
4946 (match_operand:SI 2 "reg_or_cint_operand" "rn"))))
4947 (clobber (reg:SI CA_REGNO))]
4950 [(set_attr "type" "shift")
4951 (set_attr "maybe_var_shift" "yes")])
4953 (define_insn_and_split "*ashr<mode>3_dot"
4954 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4955 (compare:CC (ashiftrt:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
4956 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn"))
4958 (clobber (match_scratch:GPR 0 "=r,r"))
4959 (clobber (reg:GPR CA_REGNO))]
4960 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
4962 sra<wd>%I2. %0,%1,%<hH>2
4964 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
4965 [(parallel [(set (match_dup 0)
4966 (ashiftrt:GPR (match_dup 1)
4968 (clobber (reg:GPR CA_REGNO))])
4970 (compare:CC (match_dup 0)
4973 [(set_attr "type" "shift")
4974 (set_attr "maybe_var_shift" "yes")
4975 (set_attr "dot" "yes")
4976 (set_attr "length" "4,8")])
4978 (define_insn_and_split "*ashr<mode>3_dot2"
4979 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
4980 (compare:CC (ashiftrt:GPR (match_operand:GPR 1 "gpc_reg_operand" "r,r")
4981 (match_operand:SI 2 "reg_or_cint_operand" "rn,rn"))
4983 (set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
4984 (ashiftrt:GPR (match_dup 1)
4986 (clobber (reg:GPR CA_REGNO))]
4987 "<MODE>mode == Pmode && rs6000_gen_cell_microcode"
4989 sra<wd>%I2. %0,%1,%<hH>2
4991 "&& reload_completed && cc_reg_not_cr0_operand (operands[3], CCmode)"
4992 [(parallel [(set (match_dup 0)
4993 (ashiftrt:GPR (match_dup 1)
4995 (clobber (reg:GPR CA_REGNO))])
4997 (compare:CC (match_dup 0)
5000 [(set_attr "type" "shift")
5001 (set_attr "maybe_var_shift" "yes")
5002 (set_attr "dot" "yes")
5003 (set_attr "length" "4,8")])
5005 ;; Builtins to replace a division to generate FRE reciprocal estimate
5006 ;; instructions and the necessary fixup instructions
5007 (define_expand "recip<mode>3"
5008 [(match_operand:RECIPF 0 "gpc_reg_operand" "")
5009 (match_operand:RECIPF 1 "gpc_reg_operand" "")
5010 (match_operand:RECIPF 2 "gpc_reg_operand" "")]
5011 "RS6000_RECIP_HAVE_RE_P (<MODE>mode)"
5013 rs6000_emit_swdiv (operands[0], operands[1], operands[2], false);
5017 ;; Split to create division from FRE/FRES/etc. and fixup instead of the normal
5018 ;; hardware division. This is only done before register allocation and with
5019 ;; -ffast-math. This must appear before the divsf3/divdf3 insns.
5021 [(set (match_operand:RECIPF 0 "gpc_reg_operand" "")
5022 (div:RECIPF (match_operand 1 "gpc_reg_operand" "")
5023 (match_operand 2 "gpc_reg_operand" "")))]
5024 "RS6000_RECIP_AUTO_RE_P (<MODE>mode)
5025 && can_create_pseudo_p () && optimize_insn_for_speed_p ()
5026 && flag_finite_math_only && !flag_trapping_math && flag_reciprocal_math"
5029 rs6000_emit_swdiv (operands[0], operands[1], operands[2], true);
5033 ;; Builtins to replace 1/sqrt(x) with instructions using RSQRTE and the
5034 ;; appropriate fixup.
5035 (define_expand "rsqrt<mode>2"
5036 [(match_operand:RECIPF 0 "gpc_reg_operand" "")
5037 (match_operand:RECIPF 1 "gpc_reg_operand" "")]
5038 "RS6000_RECIP_HAVE_RSQRTE_P (<MODE>mode)"
5040 rs6000_emit_swrsqrt (operands[0], operands[1]);
5044 ;; Floating-point insns, excluding normal data motion. We combine the SF/DF
5045 ;; modes here, and also add in conditional vsx/power8-vector support to access
5046 ;; values in the traditional Altivec registers if the appropriate
5047 ;; -mupper-regs-{df,sf} option is enabled.
5049 (define_expand "abs<mode>2"
5050 [(set (match_operand:SFDF 0 "gpc_reg_operand" "")
5051 (abs:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "")))]
5052 "TARGET_<MODE>_INSN"
5055 (define_insn "*abs<mode>2_fpr"
5056 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5057 (abs:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")))]
5062 [(set_attr "type" "fp")
5063 (set_attr "fp_type" "fp_addsub_<Fs>")])
5065 (define_insn "*nabs<mode>2_fpr"
5066 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5069 (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>"))))]
5074 [(set_attr "type" "fp")
5075 (set_attr "fp_type" "fp_addsub_<Fs>")])
5077 (define_expand "neg<mode>2"
5078 [(set (match_operand:SFDF 0 "gpc_reg_operand" "")
5079 (neg:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "")))]
5080 "TARGET_<MODE>_INSN"
5083 (define_insn "*neg<mode>2_fpr"
5084 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5085 (neg:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")))]
5090 [(set_attr "type" "fp")
5091 (set_attr "fp_type" "fp_addsub_<Fs>")])
5093 (define_expand "add<mode>3"
5094 [(set (match_operand:SFDF 0 "gpc_reg_operand" "")
5095 (plus:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "")
5096 (match_operand:SFDF 2 "gpc_reg_operand" "")))]
5097 "TARGET_<MODE>_INSN"
5100 (define_insn "*add<mode>3_fpr"
5101 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5102 (plus:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv>")
5103 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
5106 fadd<Ftrad> %0,%1,%2
5107 xsadd<Fvsx> %x0,%x1,%x2"
5108 [(set_attr "type" "fp")
5109 (set_attr "fp_type" "fp_addsub_<Fs>")])
5111 (define_expand "sub<mode>3"
5112 [(set (match_operand:SFDF 0 "gpc_reg_operand" "")
5113 (minus:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "")
5114 (match_operand:SFDF 2 "gpc_reg_operand" "")))]
5115 "TARGET_<MODE>_INSN"
5118 (define_insn "*sub<mode>3_fpr"
5119 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5120 (minus:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")
5121 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
5124 fsub<Ftrad> %0,%1,%2
5125 xssub<Fvsx> %x0,%x1,%x2"
5126 [(set_attr "type" "fp")
5127 (set_attr "fp_type" "fp_addsub_<Fs>")])
5129 (define_expand "mul<mode>3"
5130 [(set (match_operand:SFDF 0 "gpc_reg_operand" "")
5131 (mult:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "")
5132 (match_operand:SFDF 2 "gpc_reg_operand" "")))]
5133 "TARGET_<MODE>_INSN"
5136 (define_insn "*mul<mode>3_fpr"
5137 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5138 (mult:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv>")
5139 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
5142 fmul<Ftrad> %0,%1,%2
5143 xsmul<Fvsx> %x0,%x1,%x2"
5144 [(set_attr "type" "dmul")
5145 (set_attr "fp_type" "fp_mul_<Fs>")])
5147 (define_expand "div<mode>3"
5148 [(set (match_operand:SFDF 0 "gpc_reg_operand" "")
5149 (div:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "")
5150 (match_operand:SFDF 2 "gpc_reg_operand" "")))]
5151 "TARGET_<MODE>_INSN && !TARGET_SIMPLE_FPU"
5154 (define_insn "*div<mode>3_fpr"
5155 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5156 (div:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")
5157 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
5158 "TARGET_<MODE>_FPR && !TARGET_SIMPLE_FPU"
5160 fdiv<Ftrad> %0,%1,%2
5161 xsdiv<Fvsx> %x0,%x1,%x2"
5162 [(set_attr "type" "<Fs>div")
5163 (set_attr "fp_type" "fp_div_<Fs>")])
5165 (define_insn "sqrt<mode>2"
5166 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5167 (sqrt:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")))]
5168 "TARGET_<MODE>_FPR && !TARGET_SIMPLE_FPU
5169 && (TARGET_PPC_GPOPT || (<MODE>mode == SFmode && TARGET_XILINX_FPU))"
5172 xssqrt<Fvsx> %x0,%x1"
5173 [(set_attr "type" "<Fs>sqrt")
5174 (set_attr "fp_type" "fp_sqrt_<Fs>")])
5176 ;; Floating point reciprocal approximation
5177 (define_insn "fre<Fs>"
5178 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5179 (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")]
5185 [(set_attr "type" "fp")])
5187 (define_insn "*rsqrt<mode>2"
5188 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5189 (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")]
5191 "RS6000_RECIP_HAVE_RSQRTE_P (<MODE>mode)"
5193 frsqrte<Ftrad> %0,%1
5194 xsrsqrte<Fvsx> %x0,%x1"
5195 [(set_attr "type" "fp")])
5197 ;; Floating point comparisons
5198 (define_insn "*cmp<mode>_fpr"
5199 [(set (match_operand:CCFP 0 "cc_reg_operand" "=y,y")
5200 (compare:CCFP (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")
5201 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
5205 xscmpudp %0,%x1,%x2"
5206 [(set_attr "type" "fpcompare")])
5208 ;; Floating point conversions
5209 (define_expand "extendsfdf2"
5210 [(set (match_operand:DF 0 "gpc_reg_operand" "")
5211 (float_extend:DF (match_operand:SF 1 "reg_or_none500mem_operand" "")))]
5212 "TARGET_HARD_FLOAT && ((TARGET_FPRS && TARGET_DOUBLE_FLOAT) || TARGET_E500_DOUBLE)"
5215 (define_insn_and_split "*extendsfdf2_fpr"
5216 [(set (match_operand:DF 0 "gpc_reg_operand" "=d,?d,d,ws,?ws,wu")
5217 (float_extend:DF (match_operand:SF 1 "reg_or_mem_operand" "0,f,m,0,wy,Z")))]
5218 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT"
5224 xscpsgndp %x0,%x1,%x1
5226 "&& reload_completed && REG_P (operands[1]) && REGNO (operands[0]) == REGNO (operands[1])"
5229 emit_note (NOTE_INSN_DELETED);
5232 [(set_attr "type" "fp,fp,fpload,fp,fp,fpload")])
5234 (define_expand "truncdfsf2"
5235 [(set (match_operand:SF 0 "gpc_reg_operand" "")
5236 (float_truncate:SF (match_operand:DF 1 "gpc_reg_operand" "")))]
5237 "TARGET_HARD_FLOAT && ((TARGET_FPRS && TARGET_DOUBLE_FLOAT) || TARGET_E500_DOUBLE)"
5240 (define_insn "*truncdfsf2_fpr"
5241 [(set (match_operand:SF 0 "gpc_reg_operand" "=f,wy")
5242 (float_truncate:SF (match_operand:DF 1 "gpc_reg_operand" "d,ws")))]
5243 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT"
5247 [(set_attr "type" "fp")])
5249 ;; This expander is here to avoid FLOAT_WORDS_BIGENDIAN tests in
5250 ;; builtins.c and optabs.c that are not correct for IBM long double
5251 ;; when little-endian.
5252 (define_expand "signbittf2"
5254 (float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "")))
5256 (subreg:DI (match_dup 2) 0))
5259 (set (match_operand:SI 0 "gpc_reg_operand" "")
5262 && TARGET_HARD_FLOAT
5263 && (TARGET_FPRS || TARGET_E500_DOUBLE)
5264 && TARGET_LONG_DOUBLE_128"
5266 operands[2] = gen_reg_rtx (DFmode);
5267 operands[3] = gen_reg_rtx (DImode);
5268 if (TARGET_POWERPC64)
5270 operands[4] = gen_reg_rtx (DImode);
5271 operands[5] = gen_rtx_LSHIFTRT (DImode, operands[3], GEN_INT (63));
5272 operands[6] = gen_rtx_SUBREG (SImode, operands[4],
5273 WORDS_BIG_ENDIAN ? 4 : 0);
5277 operands[4] = gen_reg_rtx (SImode);
5278 operands[5] = gen_rtx_SUBREG (SImode, operands[3],
5279 WORDS_BIG_ENDIAN ? 0 : 4);
5280 operands[6] = gen_rtx_LSHIFTRT (SImode, operands[4], GEN_INT (31));
5284 (define_expand "copysign<mode>3"
5286 (abs:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "")))
5288 (neg:SFDF (abs:SFDF (match_dup 1))))
5289 (set (match_operand:SFDF 0 "gpc_reg_operand" "")
5290 (if_then_else:SFDF (ge (match_operand:SFDF 2 "gpc_reg_operand" "")
5294 "TARGET_HARD_FLOAT && TARGET_FPRS && <TARGET_FLOAT>
5295 && ((TARGET_PPC_GFXOPT
5296 && !HONOR_NANS (<MODE>mode)
5297 && !HONOR_SIGNED_ZEROS (<MODE>mode))
5299 || VECTOR_UNIT_VSX_P (<MODE>mode))"
5301 if (TARGET_CMPB || VECTOR_UNIT_VSX_P (<MODE>mode))
5303 emit_insn (gen_copysign<mode>3_fcpsgn (operands[0], operands[1],
5308 operands[3] = gen_reg_rtx (<MODE>mode);
5309 operands[4] = gen_reg_rtx (<MODE>mode);
5310 operands[5] = CONST0_RTX (<MODE>mode);
5313 ;; Use an unspec rather providing an if-then-else in RTL, to prevent the
5314 ;; compiler from optimizing -0.0
5315 (define_insn "copysign<mode>3_fcpsgn"
5316 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5317 (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")
5318 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")]
5320 "TARGET_<MODE>_FPR && TARGET_CMPB"
5323 xscpsgndp %x0,%x2,%x1"
5324 [(set_attr "type" "fp")])
5326 ;; For MIN, MAX, and conditional move, we use DEFINE_EXPAND's that involve a
5327 ;; fsel instruction and some auxiliary computations. Then we just have a
5328 ;; single DEFINE_INSN for fsel and the define_splits to make them if made by
5330 ;; For MIN, MAX on non-VSX machines, and conditional move all of the time, we
5331 ;; use DEFINE_EXPAND's that involve a fsel instruction and some auxiliary
5332 ;; computations. Then we just have a single DEFINE_INSN for fsel and the
5333 ;; define_splits to make them if made by combine. On VSX machines we have the
5334 ;; min/max instructions.
5336 ;; On VSX, we only check for TARGET_VSX instead of checking for a vsx/p8 vector
5337 ;; to allow either DF/SF to use only traditional registers.
5339 (define_expand "smax<mode>3"
5340 [(set (match_operand:SFDF 0 "gpc_reg_operand" "")
5341 (if_then_else:SFDF (ge (match_operand:SFDF 1 "gpc_reg_operand" "")
5342 (match_operand:SFDF 2 "gpc_reg_operand" ""))
5345 "TARGET_<MODE>_FPR && TARGET_PPC_GFXOPT && !flag_trapping_math"
5347 rs6000_emit_minmax (operands[0], SMAX, operands[1], operands[2]);
5351 (define_insn "*smax<mode>3_vsx"
5352 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5353 (smax:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv>")
5354 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
5355 "TARGET_<MODE>_FPR && TARGET_VSX"
5356 "xsmaxdp %x0,%x1,%x2"
5357 [(set_attr "type" "fp")])
5359 (define_expand "smin<mode>3"
5360 [(set (match_operand:SFDF 0 "gpc_reg_operand" "")
5361 (if_then_else:SFDF (ge (match_operand:SFDF 1 "gpc_reg_operand" "")
5362 (match_operand:SFDF 2 "gpc_reg_operand" ""))
5365 "TARGET_<MODE>_FPR && TARGET_PPC_GFXOPT && !flag_trapping_math"
5367 rs6000_emit_minmax (operands[0], SMIN, operands[1], operands[2]);
5371 (define_insn "*smin<mode>3_vsx"
5372 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
5373 (smin:SFDF (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv>")
5374 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>")))]
5375 "TARGET_<MODE>_FPR && TARGET_VSX"
5376 "xsmindp %x0,%x1,%x2"
5377 [(set_attr "type" "fp")])
5380 [(set (match_operand:SFDF 0 "gpc_reg_operand" "")
5381 (match_operator:SFDF 3 "min_max_operator"
5382 [(match_operand:SFDF 1 "gpc_reg_operand" "")
5383 (match_operand:SFDF 2 "gpc_reg_operand" "")]))]
5384 "TARGET_<MODE>_FPR && TARGET_PPC_GFXOPT && !flag_trapping_math
5388 rs6000_emit_minmax (operands[0], GET_CODE (operands[3]), operands[1],
5394 [(set (match_operand:SF 0 "gpc_reg_operand" "")
5395 (match_operator:SF 3 "min_max_operator"
5396 [(match_operand:SF 1 "gpc_reg_operand" "")
5397 (match_operand:SF 2 "gpc_reg_operand" "")]))]
5398 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT && TARGET_FPRS
5399 && TARGET_SINGLE_FLOAT && !flag_trapping_math"
5402 { rs6000_emit_minmax (operands[0], GET_CODE (operands[3]),
5403 operands[1], operands[2]);
5407 (define_expand "mov<mode>cc"
5408 [(set (match_operand:GPR 0 "gpc_reg_operand" "")
5409 (if_then_else:GPR (match_operand 1 "comparison_operator" "")
5410 (match_operand:GPR 2 "gpc_reg_operand" "")
5411 (match_operand:GPR 3 "gpc_reg_operand" "")))]
5415 if (rs6000_emit_cmove (operands[0], operands[1], operands[2], operands[3]))
5421 ;; We use the BASE_REGS for the isel input operands because, if rA is
5422 ;; 0, the value of 0 is placed in rD upon truth. Similarly for rB
5423 ;; because we may switch the operands and rB may end up being rA.
5425 ;; We need 2 patterns: an unsigned and a signed pattern. We could
5426 ;; leave out the mode in operand 4 and use one pattern, but reload can
5427 ;; change the mode underneath our feet and then gets confused trying
5428 ;; to reload the value.
5429 (define_insn "isel_signed_<mode>"
5430 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
5432 (match_operator 1 "scc_comparison_operator"
5433 [(match_operand:CC 4 "cc_reg_operand" "y,y")
5435 (match_operand:GPR 2 "reg_or_cint_operand" "O,b")
5436 (match_operand:GPR 3 "gpc_reg_operand" "r,r")))]
5439 { return output_isel (operands); }"
5440 [(set_attr "type" "isel")
5441 (set_attr "length" "4")])
5443 (define_insn "isel_unsigned_<mode>"
5444 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r,r")
5446 (match_operator 1 "scc_comparison_operator"
5447 [(match_operand:CCUNS 4 "cc_reg_operand" "y,y")
5449 (match_operand:GPR 2 "reg_or_cint_operand" "O,b")
5450 (match_operand:GPR 3 "gpc_reg_operand" "r,r")))]
5453 { return output_isel (operands); }"
5454 [(set_attr "type" "isel")
5455 (set_attr "length" "4")])
5457 ;; These patterns can be useful for combine; they let combine know that
5458 ;; isel can handle reversed comparisons so long as the operands are
5461 (define_insn "*isel_reversed_signed_<mode>"
5462 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
5464 (match_operator 1 "scc_rev_comparison_operator"
5465 [(match_operand:CC 4 "cc_reg_operand" "y")
5467 (match_operand:GPR 2 "gpc_reg_operand" "b")
5468 (match_operand:GPR 3 "gpc_reg_operand" "b")))]
5471 { return output_isel (operands); }"
5472 [(set_attr "type" "isel")
5473 (set_attr "length" "4")])
5475 (define_insn "*isel_reversed_unsigned_<mode>"
5476 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
5478 (match_operator 1 "scc_rev_comparison_operator"
5479 [(match_operand:CCUNS 4 "cc_reg_operand" "y")
5481 (match_operand:GPR 2 "gpc_reg_operand" "b")
5482 (match_operand:GPR 3 "gpc_reg_operand" "b")))]
5485 { return output_isel (operands); }"
5486 [(set_attr "type" "isel")
5487 (set_attr "length" "4")])
5489 (define_expand "movsfcc"
5490 [(set (match_operand:SF 0 "gpc_reg_operand" "")
5491 (if_then_else:SF (match_operand 1 "comparison_operator" "")
5492 (match_operand:SF 2 "gpc_reg_operand" "")
5493 (match_operand:SF 3 "gpc_reg_operand" "")))]
5494 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT"
5497 if (rs6000_emit_cmove (operands[0], operands[1], operands[2], operands[3]))
5503 (define_insn "*fselsfsf4"
5504 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
5505 (if_then_else:SF (ge (match_operand:SF 1 "gpc_reg_operand" "f")
5506 (match_operand:SF 4 "zero_fp_constant" "F"))
5507 (match_operand:SF 2 "gpc_reg_operand" "f")
5508 (match_operand:SF 3 "gpc_reg_operand" "f")))]
5509 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT"
5511 [(set_attr "type" "fp")])
5513 (define_insn "*fseldfsf4"
5514 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
5515 (if_then_else:SF (ge (match_operand:DF 1 "gpc_reg_operand" "d")
5516 (match_operand:DF 4 "zero_fp_constant" "F"))
5517 (match_operand:SF 2 "gpc_reg_operand" "f")
5518 (match_operand:SF 3 "gpc_reg_operand" "f")))]
5519 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_SINGLE_FLOAT"
5521 [(set_attr "type" "fp")])
5523 ;; The conditional move instructions allow us to perform max and min
5524 ;; operations even when
5527 [(set (match_operand:DF 0 "gpc_reg_operand" "")
5528 (match_operator:DF 3 "min_max_operator"
5529 [(match_operand:DF 1 "gpc_reg_operand" "")
5530 (match_operand:DF 2 "gpc_reg_operand" "")]))]
5531 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
5532 && !flag_trapping_math"
5535 { rs6000_emit_minmax (operands[0], GET_CODE (operands[3]),
5536 operands[1], operands[2]);
5540 (define_expand "movdfcc"
5541 [(set (match_operand:DF 0 "gpc_reg_operand" "")
5542 (if_then_else:DF (match_operand 1 "comparison_operator" "")
5543 (match_operand:DF 2 "gpc_reg_operand" "")
5544 (match_operand:DF 3 "gpc_reg_operand" "")))]
5545 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT"
5548 if (rs6000_emit_cmove (operands[0], operands[1], operands[2], operands[3]))
5554 (define_insn "*fseldfdf4"
5555 [(set (match_operand:DF 0 "gpc_reg_operand" "=d")
5556 (if_then_else:DF (ge (match_operand:DF 1 "gpc_reg_operand" "d")
5557 (match_operand:DF 4 "zero_fp_constant" "F"))
5558 (match_operand:DF 2 "gpc_reg_operand" "d")
5559 (match_operand:DF 3 "gpc_reg_operand" "d")))]
5560 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT"
5562 [(set_attr "type" "fp")])
5564 (define_insn "*fselsfdf4"
5565 [(set (match_operand:DF 0 "gpc_reg_operand" "=d")
5566 (if_then_else:DF (ge (match_operand:SF 1 "gpc_reg_operand" "f")
5567 (match_operand:SF 4 "zero_fp_constant" "F"))
5568 (match_operand:DF 2 "gpc_reg_operand" "d")
5569 (match_operand:DF 3 "gpc_reg_operand" "d")))]
5570 "TARGET_PPC_GFXOPT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_SINGLE_FLOAT"
5572 [(set_attr "type" "fp")])
5574 ;; Conversions to and from floating-point.
5576 ; We don't define lfiwax/lfiwzx with the normal definition, because we
5577 ; don't want to support putting SImode in FPR registers.
5578 (define_insn "lfiwax"
5579 [(set (match_operand:DI 0 "gpc_reg_operand" "=d,wj,!wj")
5580 (unspec:DI [(match_operand:SI 1 "reg_or_indexed_operand" "Z,Z,r")]
5582 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_LFIWAX"
5587 [(set_attr "type" "fpload,fpload,mffgpr")])
5589 ; This split must be run before register allocation because it allocates the
5590 ; memory slot that is needed to move values to/from the FPR. We don't allocate
5591 ; it earlier to allow for the combiner to merge insns together where it might
5592 ; not be needed and also in case the insns are deleted as dead code.
5594 (define_insn_and_split "floatsi<mode>2_lfiwax"
5595 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Fv>")
5596 (float:SFDF (match_operand:SI 1 "nonimmediate_operand" "r")))
5597 (clobber (match_scratch:DI 2 "=wj"))]
5598 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_LFIWAX
5599 && <SI_CONVERT_FP> && can_create_pseudo_p ()"
5605 rtx dest = operands[0];
5606 rtx src = operands[1];
5609 if (!MEM_P (src) && TARGET_POWERPC64
5610 && (TARGET_MFPGPR || TARGET_DIRECT_MOVE))
5611 tmp = convert_to_mode (DImode, src, false);
5615 if (GET_CODE (tmp) == SCRATCH)
5616 tmp = gen_reg_rtx (DImode);
5619 src = rs6000_address_for_fpconvert (src);
5620 emit_insn (gen_lfiwax (tmp, src));
5624 rtx stack = rs6000_allocate_stack_temp (SImode, false, true);
5625 emit_move_insn (stack, src);
5626 emit_insn (gen_lfiwax (tmp, stack));
5629 emit_insn (gen_floatdi<mode>2 (dest, tmp));
5632 [(set_attr "length" "12")
5633 (set_attr "type" "fpload")])
5635 (define_insn_and_split "floatsi<mode>2_lfiwax_mem"
5636 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fa>")
5639 (match_operand:SI 1 "indexed_or_indirect_operand" "Z,Z"))))
5640 (clobber (match_scratch:DI 2 "=0,d"))]
5641 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_LFIWAX
5648 operands[1] = rs6000_address_for_fpconvert (operands[1]);
5649 if (GET_CODE (operands[2]) == SCRATCH)
5650 operands[2] = gen_reg_rtx (DImode);
5651 emit_insn (gen_lfiwax (operands[2], operands[1]));
5652 emit_insn (gen_floatdi<mode>2 (operands[0], operands[2]));
5655 [(set_attr "length" "8")
5656 (set_attr "type" "fpload")])
5658 (define_insn "lfiwzx"
5659 [(set (match_operand:DI 0 "gpc_reg_operand" "=d,wj,!wj")
5660 (unspec:DI [(match_operand:SI 1 "reg_or_indexed_operand" "Z,Z,r")]
5662 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_LFIWZX"
5667 [(set_attr "type" "fpload,fpload,mftgpr")])
5669 (define_insn_and_split "floatunssi<mode>2_lfiwzx"
5670 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Fv>")
5671 (unsigned_float:SFDF (match_operand:SI 1 "nonimmediate_operand" "r")))
5672 (clobber (match_scratch:DI 2 "=wj"))]
5673 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_LFIWZX
5680 rtx dest = operands[0];
5681 rtx src = operands[1];
5684 if (!MEM_P (src) && TARGET_POWERPC64
5685 && (TARGET_MFPGPR || TARGET_DIRECT_MOVE))
5686 tmp = convert_to_mode (DImode, src, true);
5690 if (GET_CODE (tmp) == SCRATCH)
5691 tmp = gen_reg_rtx (DImode);
5694 src = rs6000_address_for_fpconvert (src);
5695 emit_insn (gen_lfiwzx (tmp, src));
5699 rtx stack = rs6000_allocate_stack_temp (SImode, false, true);
5700 emit_move_insn (stack, src);
5701 emit_insn (gen_lfiwzx (tmp, stack));
5704 emit_insn (gen_floatdi<mode>2 (dest, tmp));
5707 [(set_attr "length" "12")
5708 (set_attr "type" "fpload")])
5710 (define_insn_and_split "floatunssi<mode>2_lfiwzx_mem"
5711 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fa>")
5712 (unsigned_float:SFDF
5714 (match_operand:SI 1 "indexed_or_indirect_operand" "Z,Z"))))
5715 (clobber (match_scratch:DI 2 "=0,d"))]
5716 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_LFIWZX
5723 operands[1] = rs6000_address_for_fpconvert (operands[1]);
5724 if (GET_CODE (operands[2]) == SCRATCH)
5725 operands[2] = gen_reg_rtx (DImode);
5726 emit_insn (gen_lfiwzx (operands[2], operands[1]));
5727 emit_insn (gen_floatdi<mode>2 (operands[0], operands[2]));
5730 [(set_attr "length" "8")
5731 (set_attr "type" "fpload")])
5733 ; For each of these conversions, there is a define_expand, a define_insn
5734 ; with a '#' template, and a define_split (with C code). The idea is
5735 ; to allow constant folding with the template of the define_insn,
5736 ; then to have the insns split later (between sched1 and final).
5738 (define_expand "floatsidf2"
5739 [(parallel [(set (match_operand:DF 0 "gpc_reg_operand" "")
5740 (float:DF (match_operand:SI 1 "nonimmediate_operand" "")))
5743 (clobber (match_dup 4))
5744 (clobber (match_dup 5))
5745 (clobber (match_dup 6))])]
5747 && ((TARGET_FPRS && TARGET_DOUBLE_FLOAT) || TARGET_E500_DOUBLE)"
5750 if (TARGET_E500_DOUBLE)
5752 if (!REG_P (operands[1]))
5753 operands[1] = force_reg (SImode, operands[1]);
5754 emit_insn (gen_spe_floatsidf2 (operands[0], operands[1]));
5757 else if (TARGET_LFIWAX && TARGET_FCFID)
5759 emit_insn (gen_floatsidf2_lfiwax (operands[0], operands[1]));
5762 else if (TARGET_FCFID)
5764 rtx dreg = operands[1];
5766 dreg = force_reg (SImode, dreg);
5767 dreg = convert_to_mode (DImode, dreg, false);
5768 emit_insn (gen_floatdidf2 (operands[0], dreg));
5772 if (!REG_P (operands[1]))
5773 operands[1] = force_reg (SImode, operands[1]);
5774 operands[2] = force_reg (SImode, GEN_INT (0x43300000));
5775 operands[3] = force_reg (DFmode, CONST_DOUBLE_ATOF (\"4503601774854144\", DFmode));
5776 operands[4] = rs6000_allocate_stack_temp (DFmode, true, false);
5777 operands[5] = gen_reg_rtx (DFmode);
5778 operands[6] = gen_reg_rtx (SImode);
5781 (define_insn_and_split "*floatsidf2_internal"
5782 [(set (match_operand:DF 0 "gpc_reg_operand" "=&d")
5783 (float:DF (match_operand:SI 1 "gpc_reg_operand" "r")))
5784 (use (match_operand:SI 2 "gpc_reg_operand" "r"))
5785 (use (match_operand:DF 3 "gpc_reg_operand" "d"))
5786 (clobber (match_operand:DF 4 "offsettable_mem_operand" "=o"))
5787 (clobber (match_operand:DF 5 "gpc_reg_operand" "=&d"))
5788 (clobber (match_operand:SI 6 "gpc_reg_operand" "=&r"))]
5789 "! TARGET_FCFID && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT"
5795 rtx lowword, highword;
5796 gcc_assert (MEM_P (operands[4]));
5797 highword = adjust_address (operands[4], SImode, 0);
5798 lowword = adjust_address (operands[4], SImode, 4);
5799 if (! WORDS_BIG_ENDIAN)
5800 std::swap (lowword, highword);
5802 emit_insn (gen_xorsi3 (operands[6], operands[1],
5803 GEN_INT (~ (HOST_WIDE_INT) 0x7fffffff)));
5804 emit_move_insn (lowword, operands[6]);
5805 emit_move_insn (highword, operands[2]);
5806 emit_move_insn (operands[5], operands[4]);
5807 emit_insn (gen_subdf3 (operands[0], operands[5], operands[3]));
5810 [(set_attr "length" "24")
5811 (set_attr "type" "fp")])
5813 ;; If we don't have a direct conversion to single precision, don't enable this
5814 ;; conversion for 32-bit without fast math, because we don't have the insn to
5815 ;; generate the fixup swizzle to avoid double rounding problems.
5816 (define_expand "floatunssisf2"
5817 [(set (match_operand:SF 0 "gpc_reg_operand" "")
5818 (unsigned_float:SF (match_operand:SI 1 "nonimmediate_operand" "")))]
5819 "TARGET_HARD_FLOAT && TARGET_SINGLE_FLOAT
5822 && ((TARGET_FCFIDUS && TARGET_LFIWZX)
5823 || (TARGET_DOUBLE_FLOAT && TARGET_FCFID
5824 && (TARGET_POWERPC64 || flag_unsafe_math_optimizations)))))"
5829 if (!REG_P (operands[1]))
5830 operands[1] = force_reg (SImode, operands[1]);
5832 else if (TARGET_LFIWZX && TARGET_FCFIDUS)
5834 emit_insn (gen_floatunssisf2_lfiwzx (operands[0], operands[1]));
5839 rtx dreg = operands[1];
5841 dreg = force_reg (SImode, dreg);
5842 dreg = convert_to_mode (DImode, dreg, true);
5843 emit_insn (gen_floatdisf2 (operands[0], dreg));
5848 (define_expand "floatunssidf2"
5849 [(parallel [(set (match_operand:DF 0 "gpc_reg_operand" "")
5850 (unsigned_float:DF (match_operand:SI 1 "nonimmediate_operand" "")))
5853 (clobber (match_dup 4))
5854 (clobber (match_dup 5))])]
5856 && ((TARGET_FPRS && TARGET_DOUBLE_FLOAT) || TARGET_E500_DOUBLE)"
5859 if (TARGET_E500_DOUBLE)
5861 if (!REG_P (operands[1]))
5862 operands[1] = force_reg (SImode, operands[1]);
5863 emit_insn (gen_spe_floatunssidf2 (operands[0], operands[1]));
5866 else if (TARGET_LFIWZX && TARGET_FCFID)
5868 emit_insn (gen_floatunssidf2_lfiwzx (operands[0], operands[1]));
5871 else if (TARGET_FCFID)
5873 rtx dreg = operands[1];
5875 dreg = force_reg (SImode, dreg);
5876 dreg = convert_to_mode (DImode, dreg, true);
5877 emit_insn (gen_floatdidf2 (operands[0], dreg));
5881 if (!REG_P (operands[1]))
5882 operands[1] = force_reg (SImode, operands[1]);
5883 operands[2] = force_reg (SImode, GEN_INT (0x43300000));
5884 operands[3] = force_reg (DFmode, CONST_DOUBLE_ATOF (\"4503599627370496\", DFmode));
5885 operands[4] = rs6000_allocate_stack_temp (DFmode, true, false);
5886 operands[5] = gen_reg_rtx (DFmode);
5889 (define_insn_and_split "*floatunssidf2_internal"
5890 [(set (match_operand:DF 0 "gpc_reg_operand" "=&d")
5891 (unsigned_float:DF (match_operand:SI 1 "gpc_reg_operand" "r")))
5892 (use (match_operand:SI 2 "gpc_reg_operand" "r"))
5893 (use (match_operand:DF 3 "gpc_reg_operand" "d"))
5894 (clobber (match_operand:DF 4 "offsettable_mem_operand" "=o"))
5895 (clobber (match_operand:DF 5 "gpc_reg_operand" "=&d"))]
5896 "! TARGET_FCFIDU && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
5897 && !(TARGET_FCFID && TARGET_POWERPC64)"
5903 rtx lowword, highword;
5904 gcc_assert (MEM_P (operands[4]));
5905 highword = adjust_address (operands[4], SImode, 0);
5906 lowword = adjust_address (operands[4], SImode, 4);
5907 if (! WORDS_BIG_ENDIAN)
5908 std::swap (lowword, highword);
5910 emit_move_insn (lowword, operands[1]);
5911 emit_move_insn (highword, operands[2]);
5912 emit_move_insn (operands[5], operands[4]);
5913 emit_insn (gen_subdf3 (operands[0], operands[5], operands[3]));
5916 [(set_attr "length" "20")
5917 (set_attr "type" "fp")])
5919 (define_expand "fix_trunc<mode>si2"
5920 [(set (match_operand:SI 0 "gpc_reg_operand" "")
5921 (fix:SI (match_operand:SFDF 1 "gpc_reg_operand" "")))]
5922 "TARGET_HARD_FLOAT && ((TARGET_FPRS && <TARGET_FLOAT>) || <E500_CONVERT>)"
5925 if (!<E500_CONVERT>)
5930 emit_insn (gen_fix_trunc<mode>si2_stfiwx (operands[0], operands[1]));
5933 tmp = gen_reg_rtx (DImode);
5934 stack = rs6000_allocate_stack_temp (DImode, true, false);
5935 emit_insn (gen_fix_trunc<mode>si2_internal (operands[0], operands[1],
5942 ; Like the convert to float patterns, this insn must be split before
5943 ; register allocation so that it can allocate the memory slot if it
5945 (define_insn_and_split "fix_trunc<mode>si2_stfiwx"
5946 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
5947 (fix:SI (match_operand:SFDF 1 "gpc_reg_operand" "d")))
5948 (clobber (match_scratch:DI 2 "=d"))]
5949 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
5950 && (<MODE>mode != SFmode || TARGET_SINGLE_FLOAT)
5951 && TARGET_STFIWX && can_create_pseudo_p ()"
5956 rtx dest = operands[0];
5957 rtx src = operands[1];
5958 rtx tmp = operands[2];
5960 if (GET_CODE (tmp) == SCRATCH)
5961 tmp = gen_reg_rtx (DImode);
5963 emit_insn (gen_fctiwz_<mode> (tmp, src));
5966 dest = rs6000_address_for_fpconvert (dest);
5967 emit_insn (gen_stfiwx (dest, tmp));
5970 else if (TARGET_POWERPC64 && (TARGET_MFPGPR || TARGET_DIRECT_MOVE))
5972 dest = gen_lowpart (DImode, dest);
5973 emit_move_insn (dest, tmp);
5978 rtx stack = rs6000_allocate_stack_temp (SImode, false, true);
5979 emit_insn (gen_stfiwx (stack, tmp));
5980 emit_move_insn (dest, stack);
5984 [(set_attr "length" "12")
5985 (set_attr "type" "fp")])
5987 (define_insn_and_split "fix_trunc<mode>si2_internal"
5988 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,?r")
5989 (fix:SI (match_operand:SFDF 1 "gpc_reg_operand" "d,<rreg>")))
5990 (clobber (match_operand:DI 2 "gpc_reg_operand" "=1,d"))
5991 (clobber (match_operand:DI 3 "offsettable_mem_operand" "=o,o"))]
5992 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT"
5999 gcc_assert (MEM_P (operands[3]));
6000 lowword = adjust_address (operands[3], SImode, WORDS_BIG_ENDIAN ? 4 : 0);
6002 emit_insn (gen_fctiwz_<mode> (operands[2], operands[1]));
6003 emit_move_insn (operands[3], operands[2]);
6004 emit_move_insn (operands[0], lowword);
6007 [(set_attr "length" "16")
6008 (set_attr "type" "fp")])
6010 (define_expand "fix_trunc<mode>di2"
6011 [(set (match_operand:DI 0 "gpc_reg_operand" "")
6012 (fix:DI (match_operand:SFDF 1 "gpc_reg_operand" "")))]
6013 "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_FPRS
6017 (define_insn "*fix_trunc<mode>di2_fctidz"
6018 [(set (match_operand:DI 0 "gpc_reg_operand" "=d,wi")
6019 (fix:DI (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fa>")))]
6020 "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_FPRS
6025 [(set_attr "type" "fp")])
6027 (define_expand "fixuns_trunc<mode>si2"
6028 [(set (match_operand:SI 0 "gpc_reg_operand" "")
6029 (unsigned_fix:SI (match_operand:SFDF 1 "gpc_reg_operand" "")))]
6031 && ((TARGET_FPRS && <TARGET_FLOAT> && TARGET_FCTIWUZ && TARGET_STFIWX)
6035 if (!<E500_CONVERT>)
6037 emit_insn (gen_fixuns_trunc<mode>si2_stfiwx (operands[0], operands[1]));
6042 (define_insn_and_split "fixuns_trunc<mode>si2_stfiwx"
6043 [(set (match_operand:SI 0 "nonimmediate_operand" "=rm")
6044 (unsigned_fix:SI (match_operand:SFDF 1 "gpc_reg_operand" "d")))
6045 (clobber (match_scratch:DI 2 "=d"))]
6046 "TARGET_HARD_FLOAT && TARGET_FPRS && <TARGET_FLOAT> && TARGET_FCTIWUZ
6047 && TARGET_STFIWX && can_create_pseudo_p ()"
6052 rtx dest = operands[0];
6053 rtx src = operands[1];
6054 rtx tmp = operands[2];
6056 if (GET_CODE (tmp) == SCRATCH)
6057 tmp = gen_reg_rtx (DImode);
6059 emit_insn (gen_fctiwuz_<mode> (tmp, src));
6062 dest = rs6000_address_for_fpconvert (dest);
6063 emit_insn (gen_stfiwx (dest, tmp));
6066 else if (TARGET_POWERPC64 && (TARGET_MFPGPR || TARGET_DIRECT_MOVE))
6068 dest = gen_lowpart (DImode, dest);
6069 emit_move_insn (dest, tmp);
6074 rtx stack = rs6000_allocate_stack_temp (SImode, false, true);
6075 emit_insn (gen_stfiwx (stack, tmp));
6076 emit_move_insn (dest, stack);
6080 [(set_attr "length" "12")
6081 (set_attr "type" "fp")])
6083 (define_expand "fixuns_trunc<mode>di2"
6084 [(set (match_operand:DI 0 "register_operand" "")
6085 (unsigned_fix:DI (match_operand:SFDF 1 "register_operand" "")))]
6086 "TARGET_HARD_FLOAT && (TARGET_FCTIDUZ || VECTOR_UNIT_VSX_P (<MODE>mode))"
6089 (define_insn "*fixuns_trunc<mode>di2_fctiduz"
6090 [(set (match_operand:DI 0 "gpc_reg_operand" "=d,wi")
6091 (unsigned_fix:DI (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fa>")))]
6092 "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_FPRS
6097 [(set_attr "type" "fp")])
6099 ; Here, we use (set (reg) (unspec:DI [(fix:SI ...)] UNSPEC_FCTIWZ))
6100 ; rather than (set (subreg:SI (reg)) (fix:SI ...))
6101 ; because the first makes it clear that operand 0 is not live
6102 ; before the instruction.
6103 (define_insn "fctiwz_<mode>"
6104 [(set (match_operand:DI 0 "gpc_reg_operand" "=d,wi")
6105 (unspec:DI [(fix:SI (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>"))]
6107 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT"
6111 [(set_attr "type" "fp")])
6113 (define_insn "fctiwuz_<mode>"
6114 [(set (match_operand:DI 0 "gpc_reg_operand" "=d,wi")
6115 (unspec:DI [(unsigned_fix:SI
6116 (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>"))]
6118 "TARGET_HARD_FLOAT && TARGET_FPRS && <TARGET_FLOAT> && TARGET_FCTIWUZ"
6122 [(set_attr "type" "fp")])
6124 ;; Only optimize (float (fix x)) -> frz if we are in fast-math mode, since
6125 ;; since the friz instruction does not truncate the value if the floating
6126 ;; point value is < LONG_MIN or > LONG_MAX.
6127 (define_insn "*friz"
6128 [(set (match_operand:DF 0 "gpc_reg_operand" "=d,ws")
6129 (float:DF (fix:DI (match_operand:DF 1 "gpc_reg_operand" "d,ws"))))]
6130 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_FPRND
6131 && flag_unsafe_math_optimizations && !flag_trapping_math && TARGET_FRIZ"
6135 [(set_attr "type" "fp")])
6137 ;; Since FCTIWZ doesn't sign extend the upper bits, we have to do a store and a
6138 ;; load to properly sign extend the value, but at least doing a store, load
6139 ;; into a GPR to sign extend, a store from the GPR and a load back into the FPR
6140 ;; if we have 32-bit memory ops
6141 (define_insn_and_split "*round32<mode>2_fprs"
6142 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=d")
6144 (fix:SI (match_operand:SFDF 1 "gpc_reg_operand" "d"))))
6145 (clobber (match_scratch:DI 2 "=d"))
6146 (clobber (match_scratch:DI 3 "=d"))]
6147 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
6148 && <SI_CONVERT_FP> && TARGET_LFIWAX && TARGET_STFIWX && TARGET_FCFID
6149 && can_create_pseudo_p ()"
6154 rtx dest = operands[0];
6155 rtx src = operands[1];
6156 rtx tmp1 = operands[2];
6157 rtx tmp2 = operands[3];
6158 rtx stack = rs6000_allocate_stack_temp (SImode, false, true);
6160 if (GET_CODE (tmp1) == SCRATCH)
6161 tmp1 = gen_reg_rtx (DImode);
6162 if (GET_CODE (tmp2) == SCRATCH)
6163 tmp2 = gen_reg_rtx (DImode);
6165 emit_insn (gen_fctiwz_<mode> (tmp1, src));
6166 emit_insn (gen_stfiwx (stack, tmp1));
6167 emit_insn (gen_lfiwax (tmp2, stack));
6168 emit_insn (gen_floatdi<mode>2 (dest, tmp2));
6171 [(set_attr "type" "fpload")
6172 (set_attr "length" "16")])
6174 (define_insn_and_split "*roundu32<mode>2_fprs"
6175 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=d")
6176 (unsigned_float:SFDF
6177 (unsigned_fix:SI (match_operand:SFDF 1 "gpc_reg_operand" "d"))))
6178 (clobber (match_scratch:DI 2 "=d"))
6179 (clobber (match_scratch:DI 3 "=d"))]
6180 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
6181 && TARGET_LFIWZX && TARGET_STFIWX && TARGET_FCFIDU
6182 && can_create_pseudo_p ()"
6187 rtx dest = operands[0];
6188 rtx src = operands[1];
6189 rtx tmp1 = operands[2];
6190 rtx tmp2 = operands[3];
6191 rtx stack = rs6000_allocate_stack_temp (SImode, false, true);
6193 if (GET_CODE (tmp1) == SCRATCH)
6194 tmp1 = gen_reg_rtx (DImode);
6195 if (GET_CODE (tmp2) == SCRATCH)
6196 tmp2 = gen_reg_rtx (DImode);
6198 emit_insn (gen_fctiwuz_<mode> (tmp1, src));
6199 emit_insn (gen_stfiwx (stack, tmp1));
6200 emit_insn (gen_lfiwzx (tmp2, stack));
6201 emit_insn (gen_floatdi<mode>2 (dest, tmp2));
6204 [(set_attr "type" "fpload")
6205 (set_attr "length" "16")])
6207 ;; No VSX equivalent to fctid
6208 (define_insn "lrint<mode>di2"
6209 [(set (match_operand:DI 0 "gpc_reg_operand" "=d")
6210 (unspec:DI [(match_operand:SFDF 1 "gpc_reg_operand" "<rreg2>")]
6212 "TARGET_<MODE>_FPR && TARGET_FPRND"
6214 [(set_attr "type" "fp")])
6216 (define_insn "btrunc<mode>2"
6217 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
6218 (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")]
6220 "TARGET_<MODE>_FPR && TARGET_FPRND"
6224 [(set_attr "type" "fp")
6225 (set_attr "fp_type" "fp_addsub_<Fs>")])
6227 (define_insn "ceil<mode>2"
6228 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
6229 (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")]
6231 "TARGET_<MODE>_FPR && TARGET_FPRND"
6235 [(set_attr "type" "fp")
6236 (set_attr "fp_type" "fp_addsub_<Fs>")])
6238 (define_insn "floor<mode>2"
6239 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>")
6240 (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>")]
6242 "TARGET_<MODE>_FPR && TARGET_FPRND"
6246 [(set_attr "type" "fp")
6247 (set_attr "fp_type" "fp_addsub_<Fs>")])
6249 ;; No VSX equivalent to frin
6250 (define_insn "round<mode>2"
6251 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<rreg2>")
6252 (unspec:SFDF [(match_operand:SFDF 1 "gpc_reg_operand" "<rreg2>")]
6254 "TARGET_<MODE>_FPR && TARGET_FPRND"
6256 [(set_attr "type" "fp")
6257 (set_attr "fp_type" "fp_addsub_<Fs>")])
6259 ; An UNSPEC is used so we don't have to support SImode in FP registers.
6260 (define_insn "stfiwx"
6261 [(set (match_operand:SI 0 "memory_operand" "=Z")
6262 (unspec:SI [(match_operand:DI 1 "gpc_reg_operand" "d")]
6266 [(set_attr "type" "fpstore")])
6268 ;; If we don't have a direct conversion to single precision, don't enable this
6269 ;; conversion for 32-bit without fast math, because we don't have the insn to
6270 ;; generate the fixup swizzle to avoid double rounding problems.
6271 (define_expand "floatsisf2"
6272 [(set (match_operand:SF 0 "gpc_reg_operand" "")
6273 (float:SF (match_operand:SI 1 "nonimmediate_operand" "")))]
6274 "TARGET_HARD_FLOAT && TARGET_SINGLE_FLOAT
6277 && ((TARGET_FCFIDS && TARGET_LFIWAX)
6278 || (TARGET_DOUBLE_FLOAT && TARGET_FCFID
6279 && (TARGET_POWERPC64 || flag_unsafe_math_optimizations)))))"
6284 if (!REG_P (operands[1]))
6285 operands[1] = force_reg (SImode, operands[1]);
6287 else if (TARGET_FCFIDS && TARGET_LFIWAX)
6289 emit_insn (gen_floatsisf2_lfiwax (operands[0], operands[1]));
6292 else if (TARGET_FCFID && TARGET_LFIWAX)
6294 rtx dfreg = gen_reg_rtx (DFmode);
6295 emit_insn (gen_floatsidf2_lfiwax (dfreg, operands[1]));
6296 emit_insn (gen_truncdfsf2 (operands[0], dfreg));
6301 rtx dreg = operands[1];
6303 dreg = force_reg (SImode, dreg);
6304 dreg = convert_to_mode (DImode, dreg, false);
6305 emit_insn (gen_floatdisf2 (operands[0], dreg));
6310 (define_expand "floatdidf2"
6311 [(set (match_operand:DF 0 "gpc_reg_operand" "")
6312 (float:DF (match_operand:DI 1 "gpc_reg_operand" "")))]
6313 "TARGET_FCFID && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_FPRS"
6316 (define_insn "*floatdidf2_fpr"
6317 [(set (match_operand:DF 0 "gpc_reg_operand" "=d,ws")
6318 (float:DF (match_operand:DI 1 "gpc_reg_operand" "d,wi")))]
6319 "TARGET_FCFID && TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_FPRS"
6323 [(set_attr "type" "fp")])
6325 ; Allow the combiner to merge source memory operands to the conversion so that
6326 ; the optimizer/register allocator doesn't try to load the value too early in a
6327 ; GPR and then use store/load to move it to a FPR and suffer from a store-load
6328 ; hit. We will split after reload to avoid the trip through the GPRs
6330 (define_insn_and_split "*floatdidf2_mem"
6331 [(set (match_operand:DF 0 "gpc_reg_operand" "=d,ws")
6332 (float:DF (match_operand:DI 1 "memory_operand" "m,Z")))
6333 (clobber (match_scratch:DI 2 "=d,wi"))]
6334 "TARGET_HARD_FLOAT && TARGET_DOUBLE_FLOAT && TARGET_FPRS && TARGET_FCFID"
6336 "&& reload_completed"
6337 [(set (match_dup 2) (match_dup 1))
6338 (set (match_dup 0) (float:DF (match_dup 2)))]
6340 [(set_attr "length" "8")
6341 (set_attr "type" "fpload")])
6343 (define_expand "floatunsdidf2"
6344 [(set (match_operand:DF 0 "gpc_reg_operand" "")
6346 (match_operand:DI 1 "gpc_reg_operand" "")))]
6347 "TARGET_HARD_FLOAT && TARGET_FCFIDU"
6350 (define_insn "*floatunsdidf2_fcfidu"
6351 [(set (match_operand:DF 0 "gpc_reg_operand" "=d,ws")
6352 (unsigned_float:DF (match_operand:DI 1 "gpc_reg_operand" "d,wi")))]
6353 "TARGET_HARD_FLOAT && TARGET_FCFIDU"
6357 [(set_attr "type" "fp")
6358 (set_attr "length" "4")])
6360 (define_insn_and_split "*floatunsdidf2_mem"
6361 [(set (match_operand:DF 0 "gpc_reg_operand" "=d,ws")
6362 (unsigned_float:DF (match_operand:DI 1 "memory_operand" "m,Z")))
6363 (clobber (match_scratch:DI 2 "=d,wi"))]
6364 "TARGET_HARD_FLOAT && (TARGET_FCFIDU || VECTOR_UNIT_VSX_P (DFmode))"
6366 "&& reload_completed"
6367 [(set (match_dup 2) (match_dup 1))
6368 (set (match_dup 0) (unsigned_float:DF (match_dup 2)))]
6370 [(set_attr "length" "8")
6371 (set_attr "type" "fpload")])
6373 (define_expand "floatdisf2"
6374 [(set (match_operand:SF 0 "gpc_reg_operand" "")
6375 (float:SF (match_operand:DI 1 "gpc_reg_operand" "")))]
6376 "TARGET_FCFID && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT
6377 && (TARGET_FCFIDS || TARGET_POWERPC64 || flag_unsafe_math_optimizations)"
6382 rtx val = operands[1];
6383 if (!flag_unsafe_math_optimizations)
6385 rtx label = gen_label_rtx ();
6386 val = gen_reg_rtx (DImode);
6387 emit_insn (gen_floatdisf2_internal2 (val, operands[1], label));
6390 emit_insn (gen_floatdisf2_internal1 (operands[0], val));
6395 (define_insn "floatdisf2_fcfids"
6396 [(set (match_operand:SF 0 "gpc_reg_operand" "=f,wy")
6397 (float:SF (match_operand:DI 1 "gpc_reg_operand" "d,wi")))]
6398 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT
6399 && TARGET_DOUBLE_FLOAT && TARGET_FCFIDS"
6403 [(set_attr "type" "fp")])
6405 (define_insn_and_split "*floatdisf2_mem"
6406 [(set (match_operand:SF 0 "gpc_reg_operand" "=f,wy,wy")
6407 (float:SF (match_operand:DI 1 "memory_operand" "m,m,Z")))
6408 (clobber (match_scratch:DI 2 "=d,d,wi"))]
6409 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT
6410 && TARGET_DOUBLE_FLOAT && TARGET_FCFIDS"
6412 "&& reload_completed"
6416 emit_move_insn (operands[2], operands[1]);
6417 emit_insn (gen_floatdisf2_fcfids (operands[0], operands[2]));
6420 [(set_attr "length" "8")])
6422 ;; This is not IEEE compliant if rounding mode is "round to nearest".
6423 ;; If the DI->DF conversion is inexact, then it's possible to suffer
6424 ;; from double rounding.
6425 ;; Instead of creating a new cpu type for two FP operations, just use fp
6426 (define_insn_and_split "floatdisf2_internal1"
6427 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
6428 (float:SF (match_operand:DI 1 "gpc_reg_operand" "d")))
6429 (clobber (match_scratch:DF 2 "=d"))]
6430 "TARGET_FCFID && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT
6433 "&& reload_completed"
6435 (float:DF (match_dup 1)))
6437 (float_truncate:SF (match_dup 2)))]
6439 [(set_attr "length" "8")
6440 (set_attr "type" "fp")])
6442 ;; Twiddles bits to avoid double rounding.
6443 ;; Bits that might be truncated when converting to DFmode are replaced
6444 ;; by a bit that won't be lost at that stage, but is below the SFmode
6445 ;; rounding position.
6446 (define_expand "floatdisf2_internal2"
6447 [(parallel [(set (match_dup 3) (ashiftrt:DI (match_operand:DI 1 "" "")
6449 (clobber (reg:DI CA_REGNO))])
6450 (set (match_operand:DI 0 "" "") (and:DI (match_dup 1)
6452 (set (match_dup 3) (plus:DI (match_dup 3)
6454 (set (match_dup 0) (plus:DI (match_dup 0)
6456 (set (match_dup 4) (compare:CCUNS (match_dup 3)
6458 (set (match_dup 0) (ior:DI (match_dup 0)
6460 (set (match_dup 0) (and:DI (match_dup 0)
6462 (set (pc) (if_then_else (geu (match_dup 4) (const_int 0))
6463 (label_ref (match_operand:DI 2 "" ""))
6465 (set (match_dup 0) (match_dup 1))]
6466 "TARGET_POWERPC64 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT
6470 operands[3] = gen_reg_rtx (DImode);
6471 operands[4] = gen_reg_rtx (CCUNSmode);
6474 (define_expand "floatunsdisf2"
6475 [(set (match_operand:SF 0 "gpc_reg_operand" "")
6476 (unsigned_float:SF (match_operand:DI 1 "gpc_reg_operand" "")))]
6477 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT
6478 && TARGET_DOUBLE_FLOAT && TARGET_FCFIDUS"
6481 (define_insn "floatunsdisf2_fcfidus"
6482 [(set (match_operand:SF 0 "gpc_reg_operand" "=f,wu")
6483 (unsigned_float:SF (match_operand:DI 1 "gpc_reg_operand" "d,wi")))]
6484 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT
6485 && TARGET_DOUBLE_FLOAT && TARGET_FCFIDUS"
6489 [(set_attr "type" "fp")])
6491 (define_insn_and_split "*floatunsdisf2_mem"
6492 [(set (match_operand:SF 0 "gpc_reg_operand" "=f,wy,wy")
6493 (unsigned_float:SF (match_operand:DI 1 "memory_operand" "m,m,Z")))
6494 (clobber (match_scratch:DI 2 "=d,d,wi"))]
6495 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT
6496 && TARGET_DOUBLE_FLOAT && TARGET_FCFIDUS"
6498 "&& reload_completed"
6502 emit_move_insn (operands[2], operands[1]);
6503 emit_insn (gen_floatunsdisf2_fcfidus (operands[0], operands[2]));
6506 [(set_attr "length" "8")
6507 (set_attr "type" "fpload")])
6509 ;; Define the TImode operations that can be done in a small number
6510 ;; of instructions. The & constraints are to prevent the register
6511 ;; allocator from allocating registers that overlap with the inputs
6512 ;; (for example, having an input in 7,8 and an output in 6,7). We
6513 ;; also allow for the output being the same as one of the inputs.
6515 (define_expand "addti3"
6516 [(set (match_operand:TI 0 "gpc_reg_operand" "")
6517 (plus:TI (match_operand:TI 1 "gpc_reg_operand" "")
6518 (match_operand:TI 2 "reg_or_short_operand" "")))]
6521 rtx lo0 = gen_lowpart (DImode, operands[0]);
6522 rtx lo1 = gen_lowpart (DImode, operands[1]);
6523 rtx lo2 = gen_lowpart (DImode, operands[2]);
6524 rtx hi0 = gen_highpart (DImode, operands[0]);
6525 rtx hi1 = gen_highpart (DImode, operands[1]);
6526 rtx hi2 = gen_highpart_mode (DImode, TImode, operands[2]);
6528 if (!reg_or_short_operand (lo2, DImode))
6529 lo2 = force_reg (DImode, lo2);
6530 if (!adde_operand (hi2, DImode))
6531 hi2 = force_reg (DImode, hi2);
6533 emit_insn (gen_adddi3_carry (lo0, lo1, lo2));
6534 emit_insn (gen_adddi3_carry_in (hi0, hi1, hi2));
6538 (define_expand "subti3"
6539 [(set (match_operand:TI 0 "gpc_reg_operand" "")
6540 (minus:TI (match_operand:TI 1 "reg_or_short_operand" "")
6541 (match_operand:TI 2 "gpc_reg_operand" "")))]
6544 rtx lo0 = gen_lowpart (DImode, operands[0]);
6545 rtx lo1 = gen_lowpart (DImode, operands[1]);
6546 rtx lo2 = gen_lowpart (DImode, operands[2]);
6547 rtx hi0 = gen_highpart (DImode, operands[0]);
6548 rtx hi1 = gen_highpart_mode (DImode, TImode, operands[1]);
6549 rtx hi2 = gen_highpart (DImode, operands[2]);
6551 if (!reg_or_short_operand (lo1, DImode))
6552 lo1 = force_reg (DImode, lo1);
6553 if (!adde_operand (hi1, DImode))
6554 hi1 = force_reg (DImode, hi1);
6556 emit_insn (gen_subfdi3_carry (lo0, lo2, lo1));
6557 emit_insn (gen_subfdi3_carry_in (hi0, hi2, hi1));
6562 ;; Shift by a variable amount is too complex to be worth open-coding. We
6563 ;; just handle shifts by constants.
6564 (define_insn "ashrdi3_no_power"
6565 [(set (match_operand:DI 0 "gpc_reg_operand" "=&r,&r")
6566 (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6567 (match_operand:SI 2 "const_int_operand" "M,i")))
6568 (clobber (reg:SI CA_REGNO))]
6571 switch (which_alternative)
6576 if (WORDS_BIG_ENDIAN)
6577 return \"srawi %0,%1,31\;srawi %L0,%1,%h2\";
6579 return \"srawi %L0,%L1,31\;srawi %0,%L1,%h2\";
6581 if (WORDS_BIG_ENDIAN)
6582 return \"srwi %L0,%L1,%h2\;insrwi %L0,%1,%h2,0\;srawi %0,%1,%h2\";
6584 return \"srwi %0,%1,%h2\;insrwi %0,%L1,%h2,0\;srawi %L0,%L1,%h2\";
6587 [(set_attr "type" "two,three")
6588 (set_attr "length" "8,12")])
6590 (define_insn "*ashrdisi3_noppc64be"
6591 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
6592 (subreg:SI (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r")
6593 (const_int 32)) 4))]
6594 "TARGET_32BIT && !TARGET_POWERPC64 && WORDS_BIG_ENDIAN"
6597 if (REGNO (operands[0]) == REGNO (operands[1]))
6600 return \"mr %0,%1\";
6602 [(set_attr "length" "4")])
6605 ;; PowerPC64 DImode operations.
6607 (define_insn "*rotldi3_internal4"
6608 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
6609 (and:DI (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r")
6610 (match_operand:DI 2 "reg_or_cint_operand" "rn"))
6611 (match_operand:DI 3 "mask64_operand" "n")))]
6613 "rld%I2c%B3 %0,%1,%H2,%S3"
6614 [(set_attr "type" "shift")
6615 (set_attr "maybe_var_shift" "yes")])
6617 (define_insn "*rotldi3_internal5"
6618 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
6620 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6621 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn"))
6622 (match_operand:DI 3 "mask64_operand" "n,n"))
6624 (clobber (match_scratch:DI 4 "=r,r"))]
6627 rld%I2c%B3. %4,%1,%H2,%S3
6629 [(set_attr "type" "shift")
6630 (set_attr "maybe_var_shift" "yes")
6631 (set_attr "dot" "yes")
6632 (set_attr "length" "4,8")])
6635 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
6637 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
6638 (match_operand:DI 2 "reg_or_cint_operand" ""))
6639 (match_operand:DI 3 "mask64_operand" ""))
6641 (clobber (match_scratch:DI 4 ""))]
6642 "TARGET_POWERPC64 && reload_completed"
6644 (and:DI (rotate:DI (match_dup 1)
6648 (compare:CC (match_dup 4)
6652 (define_insn "*rotldi3_internal6"
6653 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
6655 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6656 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn"))
6657 (match_operand:DI 3 "mask64_operand" "n,n"))
6659 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
6660 (and:DI (rotate:DI (match_dup 1) (match_dup 2)) (match_dup 3)))]
6663 rld%I2c%B3. %0,%1,%H2,%S3
6665 [(set_attr "type" "shift")
6666 (set_attr "maybe_var_shift" "yes")
6667 (set_attr "dot" "yes")
6668 (set_attr "length" "4,8")])
6671 [(set (match_operand:CC 4 "cc_reg_not_micro_cr0_operand" "")
6673 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
6674 (match_operand:DI 2 "reg_or_cint_operand" ""))
6675 (match_operand:DI 3 "mask64_operand" ""))
6677 (set (match_operand:DI 0 "gpc_reg_operand" "")
6678 (and:DI (rotate:DI (match_dup 1) (match_dup 2)) (match_dup 3)))]
6679 "TARGET_POWERPC64 && reload_completed"
6681 (and:DI (rotate:DI (match_dup 1) (match_dup 2)) (match_dup 3)))
6683 (compare:CC (match_dup 0)
6687 (define_insn "*rotldi3_internal7le"
6688 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
6691 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r")
6692 (match_operand:DI 2 "reg_or_cint_operand" "rn")) 0)))]
6693 "TARGET_POWERPC64 && !BYTES_BIG_ENDIAN"
6694 "rld%I2cl %0,%1,%H2,56"
6695 [(set_attr "type" "shift")
6696 (set_attr "maybe_var_shift" "yes")])
6698 (define_insn "*rotldi3_internal7be"
6699 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
6702 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r")
6703 (match_operand:DI 2 "reg_or_cint_operand" "rn")) 7)))]
6704 "TARGET_POWERPC64 && BYTES_BIG_ENDIAN"
6705 "rld%I2cl %0,%1,%H2,56"
6706 [(set_attr "type" "shift")
6707 (set_attr "maybe_var_shift" "yes")])
6709 (define_insn "*rotldi3_internal8le"
6710 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
6711 (compare:CC (zero_extend:DI
6713 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6714 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 0))
6716 (clobber (match_scratch:DI 3 "=r,r"))]
6717 "TARGET_64BIT && !BYTES_BIG_ENDIAN"
6719 rld%I2cl. %3,%1,%H2,56
6721 [(set_attr "type" "shift")
6722 (set_attr "maybe_var_shift" "yes")
6723 (set_attr "dot" "yes")
6724 (set_attr "length" "4,8")])
6726 (define_insn "*rotldi3_internal8be"
6727 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
6728 (compare:CC (zero_extend:DI
6730 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6731 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 7))
6733 (clobber (match_scratch:DI 3 "=r,r"))]
6734 "TARGET_64BIT && BYTES_BIG_ENDIAN"
6736 rld%I2cl. %3,%1,%H2,56
6738 [(set_attr "type" "shift")
6739 (set_attr "maybe_var_shift" "yes")
6740 (set_attr "dot" "yes")
6741 (set_attr "length" "4,8")])
6744 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
6745 (compare:CC (zero_extend:DI
6747 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
6748 (match_operand:DI 2 "reg_or_cint_operand" "")) 0))
6750 (clobber (match_scratch:DI 3 ""))]
6751 "TARGET_POWERPC64 && !BYTES_BIG_ENDIAN && reload_completed"
6753 (zero_extend:DI (subreg:QI
6754 (rotate:DI (match_dup 1)
6757 (compare:CC (match_dup 3)
6762 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
6763 (compare:CC (zero_extend:DI
6765 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
6766 (match_operand:DI 2 "reg_or_cint_operand" "")) 7))
6768 (clobber (match_scratch:DI 3 ""))]
6769 "TARGET_POWERPC64 && BYTES_BIG_ENDIAN && reload_completed"
6771 (zero_extend:DI (subreg:QI
6772 (rotate:DI (match_dup 1)
6775 (compare:CC (match_dup 3)
6779 (define_insn "*rotldi3_internal9le"
6780 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
6781 (compare:CC (zero_extend:DI
6783 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6784 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 0))
6786 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
6787 (zero_extend:DI (subreg:QI (rotate:DI (match_dup 1) (match_dup 2)) 0)))]
6788 "TARGET_64BIT && !BYTES_BIG_ENDIAN"
6790 rld%I2cl. %0,%1,%H2,56
6792 [(set_attr "type" "shift")
6793 (set_attr "maybe_var_shift" "yes")
6794 (set_attr "dot" "yes")
6795 (set_attr "length" "4,8")])
6797 (define_insn "*rotldi3_internal9be"
6798 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
6799 (compare:CC (zero_extend:DI
6801 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6802 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 7))
6804 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
6805 (zero_extend:DI (subreg:QI (rotate:DI (match_dup 1) (match_dup 2)) 7)))]
6806 "TARGET_64BIT && BYTES_BIG_ENDIAN"
6808 rld%I2cl. %0,%1,%H2,56
6810 [(set_attr "type" "shift")
6811 (set_attr "maybe_var_shift" "yes")
6812 (set_attr "dot" "yes")
6813 (set_attr "length" "4,8")])
6816 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
6817 (compare:CC (zero_extend:DI
6819 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
6820 (match_operand:DI 2 "reg_or_cint_operand" "")) 0))
6822 (set (match_operand:DI 0 "gpc_reg_operand" "")
6823 (zero_extend:DI (subreg:QI (rotate:DI (match_dup 1) (match_dup 2)) 0)))]
6824 "TARGET_POWERPC64 && !BYTES_BIG_ENDIAN && reload_completed"
6826 (zero_extend:DI (subreg:QI (rotate:DI (match_dup 1) (match_dup 2)) 0)))
6828 (compare:CC (match_dup 0)
6833 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
6834 (compare:CC (zero_extend:DI
6836 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
6837 (match_operand:DI 2 "reg_or_cint_operand" "")) 7))
6839 (set (match_operand:DI 0 "gpc_reg_operand" "")
6840 (zero_extend:DI (subreg:QI (rotate:DI (match_dup 1) (match_dup 2)) 7)))]
6841 "TARGET_POWERPC64 && BYTES_BIG_ENDIAN && reload_completed"
6843 (zero_extend:DI (subreg:QI (rotate:DI (match_dup 1) (match_dup 2)) 7)))
6845 (compare:CC (match_dup 0)
6849 (define_insn "*rotldi3_internal10le"
6850 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
6853 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r")
6854 (match_operand:DI 2 "reg_or_cint_operand" "rn")) 0)))]
6855 "TARGET_POWERPC64 && !BYTES_BIG_ENDIAN"
6856 "rld%I2cl %0,%1,%H2,48"
6857 [(set_attr "type" "shift")
6858 (set_attr "maybe_var_shift" "yes")])
6860 (define_insn "*rotldi3_internal10be"
6861 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
6864 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r")
6865 (match_operand:DI 2 "reg_or_cint_operand" "rn")) 6)))]
6866 "TARGET_POWERPC64 && BYTES_BIG_ENDIAN"
6867 "rld%I2cl %0,%1,%H2,48"
6868 [(set_attr "type" "shift")
6869 (set_attr "maybe_var_shift" "yes")])
6871 (define_insn "*rotldi3_internal11le"
6872 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
6873 (compare:CC (zero_extend:DI
6875 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6876 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 0))
6878 (clobber (match_scratch:DI 3 "=r,r"))]
6879 "TARGET_64BIT && !BYTES_BIG_ENDIAN"
6881 rld%I2cl. %3,%1,%H2,48
6883 [(set_attr "type" "shift")
6884 (set_attr "maybe_var_shift" "yes")
6885 (set_attr "dot" "yes")
6886 (set_attr "length" "4,8")])
6888 (define_insn "*rotldi3_internal11be"
6889 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
6890 (compare:CC (zero_extend:DI
6892 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6893 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 6))
6895 (clobber (match_scratch:DI 3 "=r,r"))]
6896 "TARGET_64BIT && BYTES_BIG_ENDIAN"
6898 rld%I2cl. %3,%1,%H2,48
6900 [(set_attr "type" "shift")
6901 (set_attr "maybe_var_shift" "yes")
6902 (set_attr "dot" "yes")
6903 (set_attr "length" "4,8")])
6906 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
6907 (compare:CC (zero_extend:DI
6909 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
6910 (match_operand:DI 2 "reg_or_cint_operand" "")) 0))
6912 (clobber (match_scratch:DI 3 ""))]
6913 "TARGET_POWERPC64 && !BYTES_BIG_ENDIAN && reload_completed"
6915 (zero_extend:DI (subreg:HI
6916 (rotate:DI (match_dup 1)
6919 (compare:CC (match_dup 3)
6924 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
6925 (compare:CC (zero_extend:DI
6927 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
6928 (match_operand:DI 2 "reg_or_cint_operand" "")) 6))
6930 (clobber (match_scratch:DI 3 ""))]
6931 "TARGET_POWERPC64 && BYTES_BIG_ENDIAN && reload_completed"
6933 (zero_extend:DI (subreg:HI
6934 (rotate:DI (match_dup 1)
6937 (compare:CC (match_dup 3)
6941 (define_insn "*rotldi3_internal12le"
6942 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
6943 (compare:CC (zero_extend:DI
6945 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6946 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 0))
6948 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
6949 (zero_extend:DI (subreg:HI (rotate:DI (match_dup 1) (match_dup 2)) 0)))]
6950 "TARGET_64BIT && !BYTES_BIG_ENDIAN"
6952 rld%I2cl. %0,%1,%H2,48
6954 [(set_attr "type" "shift")
6955 (set_attr "maybe_var_shift" "yes")
6956 (set_attr "dot" "yes")
6957 (set_attr "length" "4,8")])
6959 (define_insn "*rotldi3_internal12be"
6960 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
6961 (compare:CC (zero_extend:DI
6963 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
6964 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 6))
6966 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
6967 (zero_extend:DI (subreg:HI (rotate:DI (match_dup 1) (match_dup 2)) 6)))]
6968 "TARGET_64BIT && BYTES_BIG_ENDIAN"
6970 rld%I2cl. %0,%1,%H2,48
6972 [(set_attr "type" "shift")
6973 (set_attr "maybe_var_shift" "yes")
6974 (set_attr "dot" "yes")
6975 (set_attr "length" "4,8")])
6978 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
6979 (compare:CC (zero_extend:DI
6981 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
6982 (match_operand:DI 2 "reg_or_cint_operand" "")) 0))
6984 (set (match_operand:DI 0 "gpc_reg_operand" "")
6985 (zero_extend:DI (subreg:HI (rotate:DI (match_dup 1) (match_dup 2)) 0)))]
6986 "TARGET_POWERPC64 && !BYTES_BIG_ENDIAN && reload_completed"
6988 (zero_extend:DI (subreg:HI (rotate:DI (match_dup 1) (match_dup 2)) 0)))
6990 (compare:CC (match_dup 0)
6995 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
6996 (compare:CC (zero_extend:DI
6998 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
6999 (match_operand:DI 2 "reg_or_cint_operand" "")) 6))
7001 (set (match_operand:DI 0 "gpc_reg_operand" "")
7002 (zero_extend:DI (subreg:HI (rotate:DI (match_dup 1) (match_dup 2)) 6)))]
7003 "TARGET_POWERPC64 && BYTES_BIG_ENDIAN && reload_completed"
7005 (zero_extend:DI (subreg:HI (rotate:DI (match_dup 1) (match_dup 2)) 6)))
7007 (compare:CC (match_dup 0)
7011 (define_insn "*rotldi3_internal13le"
7012 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
7015 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r")
7016 (match_operand:DI 2 "reg_or_cint_operand" "rn")) 0)))]
7017 "TARGET_POWERPC64 && !BYTES_BIG_ENDIAN"
7018 "rld%I2cl %0,%1,%H2,32"
7019 [(set_attr "type" "shift")
7020 (set_attr "maybe_var_shift" "yes")])
7022 (define_insn "*rotldi3_internal13be"
7023 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
7026 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r")
7027 (match_operand:DI 2 "reg_or_cint_operand" "rn")) 4)))]
7028 "TARGET_POWERPC64 && BYTES_BIG_ENDIAN"
7029 "rld%I2cl %0,%1,%H2,32"
7030 [(set_attr "type" "shift")
7031 (set_attr "maybe_var_shift" "yes")])
7033 (define_insn "*rotldi3_internal14le"
7034 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
7035 (compare:CC (zero_extend:DI
7037 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
7038 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 0))
7040 (clobber (match_scratch:DI 3 "=r,r"))]
7041 "TARGET_64BIT && !BYTES_BIG_ENDIAN"
7043 rld%I2cl. %3,%1,%H2,32
7045 [(set_attr "type" "shift")
7046 (set_attr "maybe_var_shift" "yes")
7047 (set_attr "dot" "yes")
7048 (set_attr "length" "4,8")])
7050 (define_insn "*rotldi3_internal14be"
7051 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
7052 (compare:CC (zero_extend:DI
7054 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
7055 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 4))
7057 (clobber (match_scratch:DI 3 "=r,r"))]
7058 "TARGET_64BIT && BYTES_BIG_ENDIAN"
7060 rld%I2cl. %3,%1,%H2,32
7062 [(set_attr "type" "shift")
7063 (set_attr "maybe_var_shift" "yes")
7064 (set_attr "dot" "yes")
7065 (set_attr "length" "4,8")])
7068 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
7069 (compare:CC (zero_extend:DI
7071 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
7072 (match_operand:DI 2 "reg_or_cint_operand" "")) 0))
7074 (clobber (match_scratch:DI 3 ""))]
7075 "TARGET_POWERPC64 && !BYTES_BIG_ENDIAN && reload_completed"
7077 (zero_extend:DI (subreg:SI
7078 (rotate:DI (match_dup 1)
7081 (compare:CC (match_dup 3)
7086 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
7087 (compare:CC (zero_extend:DI
7089 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
7090 (match_operand:DI 2 "reg_or_cint_operand" "")) 4))
7092 (clobber (match_scratch:DI 3 ""))]
7093 "TARGET_POWERPC64 && BYTES_BIG_ENDIAN && reload_completed"
7095 (zero_extend:DI (subreg:SI
7096 (rotate:DI (match_dup 1)
7099 (compare:CC (match_dup 3)
7103 (define_insn "*rotldi3_internal15le"
7104 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
7105 (compare:CC (zero_extend:DI
7107 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
7108 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 0))
7110 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
7111 (zero_extend:DI (subreg:SI (rotate:DI (match_dup 1) (match_dup 2)) 0)))]
7112 "TARGET_64BIT && !BYTES_BIG_ENDIAN"
7114 rld%I2cl. %0,%1,%H2,32
7116 [(set_attr "type" "shift")
7117 (set_attr "maybe_var_shift" "yes")
7118 (set_attr "dot" "yes")
7119 (set_attr "length" "4,8")])
7121 (define_insn "*rotldi3_internal15be"
7122 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
7123 (compare:CC (zero_extend:DI
7125 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
7126 (match_operand:DI 2 "reg_or_cint_operand" "rn,rn")) 4))
7128 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
7129 (zero_extend:DI (subreg:SI (rotate:DI (match_dup 1) (match_dup 2)) 4)))]
7130 "TARGET_64BIT && BYTES_BIG_ENDIAN"
7132 rld%I2cl. %0,%1,%H2,32
7134 [(set_attr "type" "shift")
7135 (set_attr "maybe_var_shift" "yes")
7136 (set_attr "dot" "yes")
7137 (set_attr "length" "4,8")])
7140 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
7141 (compare:CC (zero_extend:DI
7143 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
7144 (match_operand:DI 2 "reg_or_cint_operand" "")) 0))
7146 (set (match_operand:DI 0 "gpc_reg_operand" "")
7147 (zero_extend:DI (subreg:SI (rotate:DI (match_dup 1) (match_dup 2)) 0)))]
7148 "TARGET_POWERPC64 && !BYTES_BIG_ENDIAN && reload_completed"
7150 (zero_extend:DI (subreg:SI (rotate:DI (match_dup 1) (match_dup 2)) 0)))
7152 (compare:CC (match_dup 0)
7157 [(set (match_operand:CC 3 "cc_reg_not_micro_cr0_operand" "")
7158 (compare:CC (zero_extend:DI
7160 (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "")
7161 (match_operand:DI 2 "reg_or_cint_operand" "")) 4))
7163 (set (match_operand:DI 0 "gpc_reg_operand" "")
7164 (zero_extend:DI (subreg:SI (rotate:DI (match_dup 1) (match_dup 2)) 4)))]
7165 "TARGET_POWERPC64 && BYTES_BIG_ENDIAN && reload_completed"
7167 (zero_extend:DI (subreg:SI (rotate:DI (match_dup 1) (match_dup 2)) 4)))
7169 (compare:CC (match_dup 0)
7173 (define_insn "*ashldi3_internal4"
7174 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
7175 (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r")
7176 (match_operand:SI 2 "const_int_operand" "i"))
7177 (match_operand:DI 3 "const_int_operand" "n")))]
7178 "TARGET_POWERPC64 && includes_rldic_lshift_p (operands[2], operands[3])"
7179 "rldic %0,%1,%H2,%W3"
7180 [(set_attr "type" "shift")])
7182 (define_insn "ashldi3_internal5"
7183 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
7185 (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
7186 (match_operand:SI 2 "const_int_operand" "i,i"))
7187 (match_operand:DI 3 "const_int_operand" "n,n"))
7189 (clobber (match_scratch:DI 4 "=r,r"))]
7190 "TARGET_64BIT && includes_rldic_lshift_p (operands[2], operands[3])"
7192 rldic. %4,%1,%H2,%W3
7194 [(set_attr "type" "shift")
7195 (set_attr "dot" "yes")
7196 (set_attr "length" "4,8")])
7199 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
7201 (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "")
7202 (match_operand:SI 2 "const_int_operand" ""))
7203 (match_operand:DI 3 "const_int_operand" ""))
7205 (clobber (match_scratch:DI 4 ""))]
7206 "TARGET_POWERPC64 && reload_completed
7207 && includes_rldic_lshift_p (operands[2], operands[3])"
7209 (and:DI (ashift:DI (match_dup 1) (match_dup 2))
7212 (compare:CC (match_dup 4)
7216 (define_insn "*ashldi3_internal6"
7217 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
7219 (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
7220 (match_operand:SI 2 "const_int_operand" "i,i"))
7221 (match_operand:DI 3 "const_int_operand" "n,n"))
7223 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
7224 (and:DI (ashift:DI (match_dup 1) (match_dup 2)) (match_dup 3)))]
7225 "TARGET_64BIT && includes_rldic_lshift_p (operands[2], operands[3])"
7227 rldic. %0,%1,%H2,%W3
7229 [(set_attr "type" "shift")
7230 (set_attr "dot" "yes")
7231 (set_attr "length" "4,8")])
7234 [(set (match_operand:CC 4 "cc_reg_not_micro_cr0_operand" "")
7236 (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "")
7237 (match_operand:SI 2 "const_int_operand" ""))
7238 (match_operand:DI 3 "const_int_operand" ""))
7240 (set (match_operand:DI 0 "gpc_reg_operand" "")
7241 (and:DI (ashift:DI (match_dup 1) (match_dup 2)) (match_dup 3)))]
7242 "TARGET_POWERPC64 && reload_completed
7243 && includes_rldic_lshift_p (operands[2], operands[3])"
7245 (and:DI (ashift:DI (match_dup 1) (match_dup 2))
7248 (compare:CC (match_dup 0)
7252 (define_insn "*ashldi3_internal7"
7253 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
7254 (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r")
7255 (match_operand:SI 2 "const_int_operand" "i"))
7256 (match_operand:DI 3 "mask64_operand" "n")))]
7257 "TARGET_POWERPC64 && includes_rldicr_lshift_p (operands[2], operands[3])"
7258 "rldicr %0,%1,%H2,%S3"
7259 [(set_attr "type" "shift")])
7261 (define_insn "ashldi3_internal8"
7262 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
7264 (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
7265 (match_operand:SI 2 "const_int_operand" "i,i"))
7266 (match_operand:DI 3 "mask64_operand" "n,n"))
7268 (clobber (match_scratch:DI 4 "=r,r"))]
7269 "TARGET_64BIT && includes_rldicr_lshift_p (operands[2], operands[3])"
7271 rldicr. %4,%1,%H2,%S3
7273 [(set_attr "type" "shift")
7274 (set_attr "dot" "yes")
7275 (set_attr "length" "4,8")])
7278 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
7280 (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "")
7281 (match_operand:SI 2 "const_int_operand" ""))
7282 (match_operand:DI 3 "mask64_operand" ""))
7284 (clobber (match_scratch:DI 4 ""))]
7285 "TARGET_POWERPC64 && reload_completed
7286 && includes_rldicr_lshift_p (operands[2], operands[3])"
7288 (and:DI (ashift:DI (match_dup 1) (match_dup 2))
7291 (compare:CC (match_dup 4)
7295 (define_insn "*ashldi3_internal9"
7296 [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y")
7298 (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r")
7299 (match_operand:SI 2 "const_int_operand" "i,i"))
7300 (match_operand:DI 3 "mask64_operand" "n,n"))
7302 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
7303 (and:DI (ashift:DI (match_dup 1) (match_dup 2)) (match_dup 3)))]
7304 "TARGET_64BIT && includes_rldicr_lshift_p (operands[2], operands[3])"
7306 rldicr. %0,%1,%H2,%S3
7308 [(set_attr "type" "shift")
7309 (set_attr "dot" "yes")
7310 (set_attr "length" "4,8")])
7313 [(set (match_operand:CC 4 "cc_reg_not_micro_cr0_operand" "")
7315 (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "")
7316 (match_operand:SI 2 "const_int_operand" ""))
7317 (match_operand:DI 3 "mask64_operand" ""))
7319 (set (match_operand:DI 0 "gpc_reg_operand" "")
7320 (and:DI (ashift:DI (match_dup 1) (match_dup 2)) (match_dup 3)))]
7321 "TARGET_POWERPC64 && reload_completed
7322 && includes_rldicr_lshift_p (operands[2], operands[3])"
7324 (and:DI (ashift:DI (match_dup 1) (match_dup 2))
7327 (compare:CC (match_dup 0)
7332 (define_insn_and_split "*anddi3_2rld"
7333 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
7334 (and:DI (match_operand:DI 1 "gpc_reg_operand" "%r")
7335 (match_operand:DI 2 "and_2rld_operand" "n")))]
7340 (and:DI (rotate:DI (match_dup 1)
7344 (and:DI (rotate:DI (match_dup 0)
7348 build_mask64_2_operands (operands[2], &operands[4]);
7350 [(set_attr "length" "8")])
7352 (define_insn_and_split "*anddi3_2rld_dot"
7353 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
7354 (compare:CC (and:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r")
7355 (match_operand:DI 2 "and_2rld_operand" "n,n"))
7357 (clobber (match_scratch:DI 0 "=r,r"))]
7358 "TARGET_64BIT && rs6000_gen_cell_microcode"
7362 "&& reload_completed"
7364 (and:DI (rotate:DI (match_dup 1)
7367 (parallel [(set (match_dup 3)
7368 (compare:CC (and:DI (rotate:DI (match_dup 0)
7372 (clobber (match_dup 0))])]
7374 build_mask64_2_operands (operands[2], &operands[4]);
7376 [(set_attr "type" "two")
7377 (set_attr "dot" "yes")
7378 (set_attr "length" "8,12")])
7380 (define_insn_and_split "*anddi3_2rld_dot2"
7381 [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y")
7382 (compare:CC (and:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r")
7383 (match_operand:DI 2 "and_2rld_operand" "n,n"))
7385 (set (match_operand:DI 0 "gpc_reg_operand" "=r,r")
7386 (and:DI (match_dup 1)
7388 "TARGET_64BIT && rs6000_gen_cell_microcode"
7392 "&& reload_completed"
7394 (and:DI (rotate:DI (match_dup 1)
7397 (parallel [(set (match_dup 3)
7398 (compare:CC (and:DI (rotate:DI (match_dup 0)
7403 (and:DI (rotate:DI (match_dup 0)
7407 build_mask64_2_operands (operands[2], &operands[4]);
7409 [(set_attr "type" "two")
7410 (set_attr "dot" "yes")
7411 (set_attr "length" "8,12")])
7413 ;; 128-bit logical operations expanders
7415 (define_expand "and<mode>3"
7416 [(set (match_operand:BOOL_128 0 "vlogical_operand" "")
7417 (and:BOOL_128 (match_operand:BOOL_128 1 "vlogical_operand" "")
7418 (match_operand:BOOL_128 2 "vlogical_operand" "")))]
7422 (define_expand "ior<mode>3"
7423 [(set (match_operand:BOOL_128 0 "vlogical_operand" "")
7424 (ior:BOOL_128 (match_operand:BOOL_128 1 "vlogical_operand" "")
7425 (match_operand:BOOL_128 2 "vlogical_operand" "")))]
7429 (define_expand "xor<mode>3"
7430 [(set (match_operand:BOOL_128 0 "vlogical_operand" "")
7431 (xor:BOOL_128 (match_operand:BOOL_128 1 "vlogical_operand" "")
7432 (match_operand:BOOL_128 2 "vlogical_operand" "")))]
7436 (define_expand "one_cmpl<mode>2"
7437 [(set (match_operand:BOOL_128 0 "vlogical_operand" "")
7438 (not:BOOL_128 (match_operand:BOOL_128 1 "vlogical_operand" "")))]
7442 (define_expand "nor<mode>3"
7443 [(set (match_operand:BOOL_128 0 "vlogical_operand" "")
7445 (not:BOOL_128 (match_operand:BOOL_128 1 "vlogical_operand" ""))
7446 (not:BOOL_128 (match_operand:BOOL_128 2 "vlogical_operand" ""))))]
7450 (define_expand "andc<mode>3"
7451 [(set (match_operand:BOOL_128 0 "vlogical_operand" "")
7453 (not:BOOL_128 (match_operand:BOOL_128 2 "vlogical_operand" ""))
7454 (match_operand:BOOL_128 1 "vlogical_operand" "")))]
7458 ;; Power8 vector logical instructions.
7459 (define_expand "eqv<mode>3"
7460 [(set (match_operand:BOOL_128 0 "vlogical_operand" "")
7462 (xor:BOOL_128 (match_operand:BOOL_128 1 "vlogical_operand" "")
7463 (match_operand:BOOL_128 2 "vlogical_operand" ""))))]
7464 "<MODE>mode == TImode || <MODE>mode == PTImode || TARGET_P8_VECTOR"
7467 ;; Rewrite nand into canonical form
7468 (define_expand "nand<mode>3"
7469 [(set (match_operand:BOOL_128 0 "vlogical_operand" "")
7471 (not:BOOL_128 (match_operand:BOOL_128 1 "vlogical_operand" ""))
7472 (not:BOOL_128 (match_operand:BOOL_128 2 "vlogical_operand" ""))))]
7473 "<MODE>mode == TImode || <MODE>mode == PTImode || TARGET_P8_VECTOR"
7476 ;; The canonical form is to have the negated element first, so we need to
7477 ;; reverse arguments.
7478 (define_expand "orc<mode>3"
7479 [(set (match_operand:BOOL_128 0 "vlogical_operand" "")
7481 (not:BOOL_128 (match_operand:BOOL_128 2 "vlogical_operand" ""))
7482 (match_operand:BOOL_128 1 "vlogical_operand" "")))]
7483 "<MODE>mode == TImode || <MODE>mode == PTImode || TARGET_P8_VECTOR"
7486 ;; 128-bit logical operations insns and split operations
7487 (define_insn_and_split "*and<mode>3_internal"
7488 [(set (match_operand:BOOL_128 0 "vlogical_operand" "=<BOOL_REGS_OUTPUT>")
7490 (match_operand:BOOL_128 1 "vlogical_operand" "%<BOOL_REGS_OP1>")
7491 (match_operand:BOOL_128 2 "vlogical_operand" "<BOOL_REGS_OP2>")))]
7494 if (TARGET_VSX && vsx_register_operand (operands[0], <MODE>mode))
7495 return "xxland %x0,%x1,%x2";
7497 if (TARGET_ALTIVEC && altivec_register_operand (operands[0], <MODE>mode))
7498 return "vand %0,%1,%2";
7502 "reload_completed && int_reg_operand (operands[0], <MODE>mode)"
7505 rs6000_split_logical (operands, AND, false, false, false);
7510 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7511 (const_string "vecsimple")
7512 (const_string "integer")))
7513 (set (attr "length")
7515 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7518 (match_test "TARGET_POWERPC64")
7520 (const_string "16"))))])
7523 (define_insn_and_split "*bool<mode>3_internal"
7524 [(set (match_operand:BOOL_128 0 "vlogical_operand" "=<BOOL_REGS_OUTPUT>")
7525 (match_operator:BOOL_128 3 "boolean_or_operator"
7526 [(match_operand:BOOL_128 1 "vlogical_operand" "%<BOOL_REGS_OP1>")
7527 (match_operand:BOOL_128 2 "vlogical_operand" "<BOOL_REGS_OP2>")]))]
7530 if (TARGET_VSX && vsx_register_operand (operands[0], <MODE>mode))
7531 return "xxl%q3 %x0,%x1,%x2";
7533 if (TARGET_ALTIVEC && altivec_register_operand (operands[0], <MODE>mode))
7534 return "v%q3 %0,%1,%2";
7538 "reload_completed && int_reg_operand (operands[0], <MODE>mode)"
7541 rs6000_split_logical (operands, GET_CODE (operands[3]), false, false, false);
7546 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7547 (const_string "vecsimple")
7548 (const_string "integer")))
7549 (set (attr "length")
7551 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7554 (match_test "TARGET_POWERPC64")
7556 (const_string "16"))))])
7559 (define_insn_and_split "*boolc<mode>3_internal1"
7560 [(set (match_operand:BOOL_128 0 "vlogical_operand" "=<BOOL_REGS_OUTPUT>")
7561 (match_operator:BOOL_128 3 "boolean_operator"
7563 (match_operand:BOOL_128 2 "vlogical_operand" "<BOOL_REGS_OP2>"))
7564 (match_operand:BOOL_128 1 "vlogical_operand" "<BOOL_REGS_OP1>")]))]
7565 "TARGET_P8_VECTOR || (GET_CODE (operands[3]) == AND)"
7567 if (TARGET_VSX && vsx_register_operand (operands[0], <MODE>mode))
7568 return "xxl%q3 %x0,%x1,%x2";
7570 if (TARGET_ALTIVEC && altivec_register_operand (operands[0], <MODE>mode))
7571 return "v%q3 %0,%1,%2";
7575 "(TARGET_P8_VECTOR || (GET_CODE (operands[3]) == AND))
7576 && reload_completed && int_reg_operand (operands[0], <MODE>mode)"
7579 rs6000_split_logical (operands, GET_CODE (operands[3]), false, false, true);
7584 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7585 (const_string "vecsimple")
7586 (const_string "integer")))
7587 (set (attr "length")
7589 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7592 (match_test "TARGET_POWERPC64")
7594 (const_string "16"))))])
7596 (define_insn_and_split "*boolc<mode>3_internal2"
7597 [(set (match_operand:TI2 0 "int_reg_operand" "=&r,r,r")
7598 (match_operator:TI2 3 "boolean_operator"
7600 (match_operand:TI2 2 "int_reg_operand" "r,0,r"))
7601 (match_operand:TI2 1 "int_reg_operand" "r,r,0")]))]
7602 "!TARGET_P8_VECTOR && (GET_CODE (operands[3]) != AND)"
7604 "reload_completed && !TARGET_P8_VECTOR && (GET_CODE (operands[3]) != AND)"
7607 rs6000_split_logical (operands, GET_CODE (operands[3]), false, false, true);
7610 [(set_attr "type" "integer")
7611 (set (attr "length")
7613 (match_test "TARGET_POWERPC64")
7615 (const_string "16")))])
7618 (define_insn_and_split "*boolcc<mode>3_internal1"
7619 [(set (match_operand:BOOL_128 0 "vlogical_operand" "=<BOOL_REGS_OUTPUT>")
7620 (match_operator:BOOL_128 3 "boolean_operator"
7622 (match_operand:BOOL_128 1 "vlogical_operand" "<BOOL_REGS_OP1>"))
7624 (match_operand:BOOL_128 2 "vlogical_operand" "<BOOL_REGS_OP2>"))]))]
7625 "TARGET_P8_VECTOR || (GET_CODE (operands[3]) == AND)"
7627 if (TARGET_VSX && vsx_register_operand (operands[0], <MODE>mode))
7628 return "xxl%q3 %x0,%x1,%x2";
7630 if (TARGET_ALTIVEC && altivec_register_operand (operands[0], <MODE>mode))
7631 return "v%q3 %0,%1,%2";
7635 "(TARGET_P8_VECTOR || (GET_CODE (operands[3]) == AND))
7636 && reload_completed && int_reg_operand (operands[0], <MODE>mode)"
7639 rs6000_split_logical (operands, GET_CODE (operands[3]), false, true, true);
7644 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7645 (const_string "vecsimple")
7646 (const_string "integer")))
7647 (set (attr "length")
7649 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7652 (match_test "TARGET_POWERPC64")
7654 (const_string "16"))))])
7656 (define_insn_and_split "*boolcc<mode>3_internal2"
7657 [(set (match_operand:TI2 0 "int_reg_operand" "=&r,r,r")
7658 (match_operator:TI2 3 "boolean_operator"
7660 (match_operand:TI2 1 "int_reg_operand" "r,0,r"))
7662 (match_operand:TI2 2 "int_reg_operand" "r,r,0"))]))]
7663 "!TARGET_P8_VECTOR && (GET_CODE (operands[3]) != AND)"
7665 "reload_completed && !TARGET_P8_VECTOR && (GET_CODE (operands[3]) != AND)"
7668 rs6000_split_logical (operands, GET_CODE (operands[3]), false, true, true);
7671 [(set_attr "type" "integer")
7672 (set (attr "length")
7674 (match_test "TARGET_POWERPC64")
7676 (const_string "16")))])
7680 (define_insn_and_split "*eqv<mode>3_internal1"
7681 [(set (match_operand:BOOL_128 0 "vlogical_operand" "=<BOOL_REGS_OUTPUT>")
7684 (match_operand:BOOL_128 1 "vlogical_operand" "<BOOL_REGS_OP1>")
7685 (match_operand:BOOL_128 2 "vlogical_operand" "<BOOL_REGS_OP2>"))))]
7688 if (vsx_register_operand (operands[0], <MODE>mode))
7689 return "xxleqv %x0,%x1,%x2";
7693 "TARGET_P8_VECTOR && reload_completed
7694 && int_reg_operand (operands[0], <MODE>mode)"
7697 rs6000_split_logical (operands, XOR, true, false, false);
7702 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7703 (const_string "vecsimple")
7704 (const_string "integer")))
7705 (set (attr "length")
7707 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7710 (match_test "TARGET_POWERPC64")
7712 (const_string "16"))))])
7714 (define_insn_and_split "*eqv<mode>3_internal2"
7715 [(set (match_operand:TI2 0 "int_reg_operand" "=&r,r,r")
7718 (match_operand:TI2 1 "int_reg_operand" "r,0,r")
7719 (match_operand:TI2 2 "int_reg_operand" "r,r,0"))))]
7722 "reload_completed && !TARGET_P8_VECTOR"
7725 rs6000_split_logical (operands, XOR, true, false, false);
7728 [(set_attr "type" "integer")
7729 (set (attr "length")
7731 (match_test "TARGET_POWERPC64")
7733 (const_string "16")))])
7735 ;; 128-bit one's complement
7736 (define_insn_and_split "*one_cmpl<mode>3_internal"
7737 [(set (match_operand:BOOL_128 0 "vlogical_operand" "=<BOOL_REGS_OUTPUT>")
7739 (match_operand:BOOL_128 1 "vlogical_operand" "<BOOL_REGS_UNARY>")))]
7742 if (TARGET_VSX && vsx_register_operand (operands[0], <MODE>mode))
7743 return "xxlnor %x0,%x1,%x1";
7745 if (TARGET_ALTIVEC && altivec_register_operand (operands[0], <MODE>mode))
7746 return "vnor %0,%1,%1";
7750 "reload_completed && int_reg_operand (operands[0], <MODE>mode)"
7753 rs6000_split_logical (operands, NOT, false, false, false);
7758 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7759 (const_string "vecsimple")
7760 (const_string "integer")))
7761 (set (attr "length")
7763 (match_test "vsx_register_operand (operands[0], <MODE>mode)")
7766 (match_test "TARGET_POWERPC64")
7768 (const_string "16"))))])
7771 ;; Now define ways of moving data around.
7773 ;; Set up a register with a value from the GOT table
7775 (define_expand "movsi_got"
7776 [(set (match_operand:SI 0 "gpc_reg_operand" "")
7777 (unspec:SI [(match_operand:SI 1 "got_operand" "")
7778 (match_dup 2)] UNSPEC_MOVSI_GOT))]
7779 "DEFAULT_ABI == ABI_V4 && flag_pic == 1"
7782 if (GET_CODE (operands[1]) == CONST)
7784 rtx offset = const0_rtx;
7785 HOST_WIDE_INT value;
7787 operands[1] = eliminate_constant_term (XEXP (operands[1], 0), &offset);
7788 value = INTVAL (offset);
7791 rtx tmp = (!can_create_pseudo_p ()
7793 : gen_reg_rtx (Pmode));
7794 emit_insn (gen_movsi_got (tmp, operands[1]));
7795 emit_insn (gen_addsi3 (operands[0], tmp, offset));
7800 operands[2] = rs6000_got_register (operands[1]);
7803 (define_insn "*movsi_got_internal"
7804 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7805 (unspec:SI [(match_operand:SI 1 "got_no_const_operand" "")
7806 (match_operand:SI 2 "gpc_reg_operand" "b")]
7808 "DEFAULT_ABI == ABI_V4 && flag_pic == 1"
7809 "lwz %0,%a1@got(%2)"
7810 [(set_attr "type" "load")])
7812 ;; Used by sched, shorten_branches and final when the GOT pseudo reg
7813 ;; didn't get allocated to a hard register.
7815 [(set (match_operand:SI 0 "gpc_reg_operand" "")
7816 (unspec:SI [(match_operand:SI 1 "got_no_const_operand" "")
7817 (match_operand:SI 2 "memory_operand" "")]
7819 "DEFAULT_ABI == ABI_V4
7821 && (reload_in_progress || reload_completed)"
7822 [(set (match_dup 0) (match_dup 2))
7823 (set (match_dup 0) (unspec:SI [(match_dup 1)(match_dup 0)]
7827 ;; For SI, we special-case integers that can't be loaded in one insn. We
7828 ;; do the load 16-bits at a time. We could do this by loading from memory,
7829 ;; and this is even supposed to be faster, but it is simpler not to get
7830 ;; integers in the TOC.
7831 (define_insn "movsi_low"
7832 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
7833 (mem:SI (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b")
7834 (match_operand 2 "" ""))))]
7835 "TARGET_MACHO && ! TARGET_64BIT"
7836 "lwz %0,lo16(%2)(%1)"
7837 [(set_attr "type" "load")
7838 (set_attr "length" "4")])
7840 (define_insn "*movsi_internal1"
7841 [(set (match_operand:SI 0 "rs6000_nonimmediate_operand" "=r,r,r,m,r,r,r,r,*c*l,*h,*h")
7842 (match_operand:SI 1 "input_operand" "r,U,m,r,I,L,n,*h,r,r,0"))]
7843 "!TARGET_SINGLE_FPU &&
7844 (gpc_reg_operand (operands[0], SImode) || gpc_reg_operand (operands[1], SImode))"
7857 [(set_attr "type" "*,*,load,store,*,*,*,mfjmpr,mtjmpr,*,*")
7858 (set_attr "length" "4,4,4,4,4,4,8,4,4,4,4")])
7860 (define_insn "*movsi_internal1_single"
7861 [(set (match_operand:SI 0 "rs6000_nonimmediate_operand" "=r,r,r,m,r,r,r,r,*c*l,*h,*h,m,*f")
7862 (match_operand:SI 1 "input_operand" "r,U,m,r,I,L,n,*h,r,r,0,f,m"))]
7863 "TARGET_SINGLE_FPU &&
7864 (gpc_reg_operand (operands[0], SImode) || gpc_reg_operand (operands[1], SImode))"
7879 [(set_attr "type" "*,*,load,store,*,*,*,mfjmpr,mtjmpr,*,*,fpstore,fpload")
7880 (set_attr "length" "4,4,4,4,4,4,8,4,4,4,4,4,4")])
7882 ;; Split a load of a large constant into the appropriate two-insn
7886 [(set (match_operand:SI 0 "gpc_reg_operand" "")
7887 (match_operand:SI 1 "const_int_operand" ""))]
7888 "(unsigned HOST_WIDE_INT) (INTVAL (operands[1]) + 0x8000) >= 0x10000
7889 && (INTVAL (operands[1]) & 0xffff) != 0"
7893 (ior:SI (match_dup 0)
7897 if (rs6000_emit_set_const (operands[0], operands[1]))
7903 (define_insn "*mov<mode>_internal2"
7904 [(set (match_operand:CC 2 "cc_reg_operand" "=y,x,?y")
7905 (compare:CC (match_operand:P 1 "gpc_reg_operand" "0,r,r")
7907 (set (match_operand:P 0 "gpc_reg_operand" "=r,r,r") (match_dup 1))]
7913 [(set_attr "type" "cmp,logical,cmp")
7914 (set_attr "dot" "yes")
7915 (set_attr "length" "4,4,8")])
7918 [(set (match_operand:CC 2 "cc_reg_not_micro_cr0_operand" "")
7919 (compare:CC (match_operand:P 1 "gpc_reg_operand" "")
7921 (set (match_operand:P 0 "gpc_reg_operand" "") (match_dup 1))]
7923 [(set (match_dup 0) (match_dup 1))
7925 (compare:CC (match_dup 0)
7929 (define_insn "*movhi_internal"
7930 [(set (match_operand:HI 0 "nonimmediate_operand" "=r,r,m,r,r,*c*l,*h")
7931 (match_operand:HI 1 "input_operand" "r,m,r,i,*h,r,0"))]
7932 "gpc_reg_operand (operands[0], HImode)
7933 || gpc_reg_operand (operands[1], HImode)"
7942 [(set_attr "type" "*,load,store,*,mfjmpr,mtjmpr,*")])
7944 (define_expand "mov<mode>"
7945 [(set (match_operand:INT 0 "general_operand" "")
7946 (match_operand:INT 1 "any_operand" ""))]
7948 "{ rs6000_emit_move (operands[0], operands[1], <MODE>mode); DONE; }")
7950 (define_insn "*movqi_internal"
7951 [(set (match_operand:QI 0 "nonimmediate_operand" "=r,r,m,r,r,*c*l,*h")
7952 (match_operand:QI 1 "input_operand" "r,m,r,i,*h,r,0"))]
7953 "gpc_reg_operand (operands[0], QImode)
7954 || gpc_reg_operand (operands[1], QImode)"
7963 [(set_attr "type" "*,load,store,*,mfjmpr,mtjmpr,*")])
7965 ;; Here is how to move condition codes around. When we store CC data in
7966 ;; an integer register or memory, we store just the high-order 4 bits.
7967 ;; This lets us not shift in the most common case of CR0.
7968 (define_expand "movcc"
7969 [(set (match_operand:CC 0 "nonimmediate_operand" "")
7970 (match_operand:CC 1 "nonimmediate_operand" ""))]
7974 (define_insn "*movcc_internal1"
7975 [(set (match_operand:CC 0 "nonimmediate_operand" "=y,x,?y,y,r,r,r,r,r,cl,r,m")
7976 (match_operand:CC 1 "general_operand" "y,r,r,O,x,y,r,I,h,r,m,r"))]
7977 "register_operand (operands[0], CCmode)
7978 || register_operand (operands[1], CCmode)"
7982 rlwinm %1,%1,%F0,0xffffffff\;mtcrf %R0,%1\;rlwinm %1,%1,%f0,0xffffffff
7985 mfcr %0%Q1\;rlwinm %0,%0,%f1,0xf0000000
7993 (cond [(eq_attr "alternative" "0,3")
7994 (const_string "cr_logical")
7995 (eq_attr "alternative" "1,2")
7996 (const_string "mtcr")
7997 (eq_attr "alternative" "6,7")
7998 (const_string "integer")
7999 (eq_attr "alternative" "8")
8000 (const_string "mfjmpr")
8001 (eq_attr "alternative" "9")
8002 (const_string "mtjmpr")
8003 (eq_attr "alternative" "10")
8004 (const_string "load")
8005 (eq_attr "alternative" "11")
8006 (const_string "store")
8007 (match_test "TARGET_MFCRF")
8008 (const_string "mfcrf")
8010 (const_string "mfcr")))
8011 (set_attr "length" "4,4,12,4,4,8,4,4,4,4,4,4")])
8013 ;; For floating-point, we normally deal with the floating-point registers
8014 ;; unless -msoft-float is used. The sole exception is that parameter passing
8015 ;; can produce floating-point values in fixed-point registers. Unless the
8016 ;; value is a simple constant or already in memory, we deal with this by
8017 ;; allocating memory and copying the value explicitly via that memory location.
8019 ;; Move 32-bit binary/decimal floating point
8020 (define_expand "mov<mode>"
8021 [(set (match_operand:FMOVE32 0 "nonimmediate_operand" "")
8022 (match_operand:FMOVE32 1 "any_operand" ""))]
8024 "{ rs6000_emit_move (operands[0], operands[1], <MODE>mode); DONE; }")
8027 [(set (match_operand:FMOVE32 0 "gpc_reg_operand" "")
8028 (match_operand:FMOVE32 1 "const_double_operand" ""))]
8030 && ((GET_CODE (operands[0]) == REG && REGNO (operands[0]) <= 31)
8031 || (GET_CODE (operands[0]) == SUBREG
8032 && GET_CODE (SUBREG_REG (operands[0])) == REG
8033 && REGNO (SUBREG_REG (operands[0])) <= 31))"
8034 [(set (match_dup 2) (match_dup 3))]
8040 REAL_VALUE_FROM_CONST_DOUBLE (rv, operands[1]);
8041 <real_value_to_target> (rv, l);
8043 if (! TARGET_POWERPC64)
8044 operands[2] = operand_subword (operands[0], 0, 0, <MODE>mode);
8046 operands[2] = gen_lowpart (SImode, operands[0]);
8048 operands[3] = gen_int_mode (l, SImode);
8051 (define_insn "mov<mode>_hardfloat"
8052 [(set (match_operand:FMOVE32 0 "nonimmediate_operand" "=!r,!r,m,f,<f32_vsx>,<f32_vsx>,!r,<f32_lr>,<f32_sm>,<f32_av>,Z,?<f32_dm>,?r,*c*l,!r,*h")
8053 (match_operand:FMOVE32 1 "input_operand" "r,m,r,f,<f32_vsx>,j,j,<f32_lm>,<f32_sr>,Z,<f32_av>,r,<f32_dm>,r,h,0"))]
8054 "(gpc_reg_operand (operands[0], <MODE>mode)
8055 || gpc_reg_operand (operands[1], <MODE>mode))
8056 && (TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT)"
8062 xscpsgndp %x0,%x1,%x1
8074 [(set_attr "type" "*,load,store,fp,fp,vecsimple,integer,fpload,fpstore,fpload,fpstore,mftgpr,mffgpr,mtjmpr,mfjmpr,*")
8075 (set_attr "length" "4")])
8077 (define_insn "*mov<mode>_softfloat"
8078 [(set (match_operand:FMOVE32 0 "nonimmediate_operand" "=r,cl,r,r,m,r,r,r,r,*h")
8079 (match_operand:FMOVE32 1 "input_operand" "r,r,h,m,r,I,L,G,Fn,0"))]
8080 "(gpc_reg_operand (operands[0], <MODE>mode)
8081 || gpc_reg_operand (operands[1], <MODE>mode))
8082 && (TARGET_SOFT_FLOAT || !TARGET_FPRS)"
8094 [(set_attr "type" "*,mtjmpr,mfjmpr,load,store,*,*,*,*,*")
8095 (set_attr "length" "4,4,4,4,4,4,4,4,8,4")])
8098 ;; Move 64-bit binary/decimal floating point
8099 (define_expand "mov<mode>"
8100 [(set (match_operand:FMOVE64 0 "nonimmediate_operand" "")
8101 (match_operand:FMOVE64 1 "any_operand" ""))]
8103 "{ rs6000_emit_move (operands[0], operands[1], <MODE>mode); DONE; }")
8106 [(set (match_operand:FMOVE64 0 "gpc_reg_operand" "")
8107 (match_operand:FMOVE64 1 "const_int_operand" ""))]
8108 "! TARGET_POWERPC64 && reload_completed
8109 && ((GET_CODE (operands[0]) == REG && REGNO (operands[0]) <= 31)
8110 || (GET_CODE (operands[0]) == SUBREG
8111 && GET_CODE (SUBREG_REG (operands[0])) == REG
8112 && REGNO (SUBREG_REG (operands[0])) <= 31))"
8113 [(set (match_dup 2) (match_dup 4))
8114 (set (match_dup 3) (match_dup 1))]
8117 int endian = (WORDS_BIG_ENDIAN == 0);
8118 HOST_WIDE_INT value = INTVAL (operands[1]);
8120 operands[2] = operand_subword (operands[0], endian, 0, <MODE>mode);
8121 operands[3] = operand_subword (operands[0], 1 - endian, 0, <MODE>mode);
8122 operands[4] = GEN_INT (value >> 32);
8123 operands[1] = GEN_INT (((value & 0xffffffff) ^ 0x80000000) - 0x80000000);
8127 [(set (match_operand:FMOVE64 0 "gpc_reg_operand" "")
8128 (match_operand:FMOVE64 1 "const_double_operand" ""))]
8129 "! TARGET_POWERPC64 && reload_completed
8130 && ((GET_CODE (operands[0]) == REG && REGNO (operands[0]) <= 31)
8131 || (GET_CODE (operands[0]) == SUBREG
8132 && GET_CODE (SUBREG_REG (operands[0])) == REG
8133 && REGNO (SUBREG_REG (operands[0])) <= 31))"
8134 [(set (match_dup 2) (match_dup 4))
8135 (set (match_dup 3) (match_dup 5))]
8138 int endian = (WORDS_BIG_ENDIAN == 0);
8142 REAL_VALUE_FROM_CONST_DOUBLE (rv, operands[1]);
8143 <real_value_to_target> (rv, l);
8145 operands[2] = operand_subword (operands[0], endian, 0, <MODE>mode);
8146 operands[3] = operand_subword (operands[0], 1 - endian, 0, <MODE>mode);
8147 operands[4] = gen_int_mode (l[endian], SImode);
8148 operands[5] = gen_int_mode (l[1 - endian], SImode);
8152 [(set (match_operand:FMOVE64 0 "gpc_reg_operand" "")
8153 (match_operand:FMOVE64 1 "const_double_operand" ""))]
8154 "TARGET_POWERPC64 && reload_completed
8155 && ((GET_CODE (operands[0]) == REG && REGNO (operands[0]) <= 31)
8156 || (GET_CODE (operands[0]) == SUBREG
8157 && GET_CODE (SUBREG_REG (operands[0])) == REG
8158 && REGNO (SUBREG_REG (operands[0])) <= 31))"
8159 [(set (match_dup 2) (match_dup 3))]
8162 int endian = (WORDS_BIG_ENDIAN == 0);
8167 REAL_VALUE_FROM_CONST_DOUBLE (rv, operands[1]);
8168 <real_value_to_target> (rv, l);
8170 operands[2] = gen_lowpart (DImode, operands[0]);
8171 /* HIGHPART is lower memory address when WORDS_BIG_ENDIAN. */
8172 val = ((HOST_WIDE_INT)(unsigned long)l[endian] << 32
8173 | ((HOST_WIDE_INT)(unsigned long)l[1 - endian]));
8175 operands[3] = gen_int_mode (val, DImode);
8178 ;; Don't have reload use general registers to load a constant. It is
8179 ;; less efficient than loading the constant into an FP register, since
8180 ;; it will probably be used there.
8182 ;; The move constraints are ordered to prefer floating point registers before
8183 ;; general purpose registers to avoid doing a store and a load to get the value
8184 ;; into a floating point register when it is needed for a floating point
8185 ;; operation. Prefer traditional floating point registers over VSX registers,
8186 ;; since the D-form version of the memory instructions does not need a GPR for
8189 ;; If we have FPR registers, rs6000_emit_move has moved all constants to memory,
8190 ;; except for 0.0 which can be created on VSX with an xor instruction.
8192 (define_insn "*mov<mode>_hardfloat32"
8193 [(set (match_operand:FMOVE64 0 "nonimmediate_operand" "=m,d,d,<f64_av>,Z,<f64_vsx>,<f64_vsx>,!r,Y,r,!r")
8194 (match_operand:FMOVE64 1 "input_operand" "d,m,d,Z,<f64_av>,<f64_vsx>,j,j,r,Y,r"))]
8195 "! TARGET_POWERPC64 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
8196 && (gpc_reg_operand (operands[0], <MODE>mode)
8197 || gpc_reg_operand (operands[1], <MODE>mode))"
8210 [(set_attr "type" "fpstore,fpload,fp,fpload,fpstore,vecsimple,vecsimple,two,store,load,two")
8211 (set_attr "length" "4,4,4,4,4,4,4,8,8,8,8")])
8213 (define_insn "*mov<mode>_softfloat32"
8214 [(set (match_operand:FMOVE64 0 "nonimmediate_operand" "=Y,r,r,r,r,r")
8215 (match_operand:FMOVE64 1 "input_operand" "r,Y,r,G,H,F"))]
8217 && ((TARGET_FPRS && TARGET_SINGLE_FLOAT)
8218 || TARGET_SOFT_FLOAT || TARGET_E500_SINGLE
8219 || (<MODE>mode == DDmode && TARGET_E500_DOUBLE))
8220 && (gpc_reg_operand (operands[0], <MODE>mode)
8221 || gpc_reg_operand (operands[1], <MODE>mode))"
8223 [(set_attr "type" "store,load,two,*,*,*")
8224 (set_attr "length" "8,8,8,8,12,16")])
8226 ; ld/std require word-aligned displacements -> 'Y' constraint.
8227 ; List Y->r and r->Y before r->r for reload.
8228 (define_insn "*mov<mode>_hardfloat64"
8229 [(set (match_operand:FMOVE64 0 "nonimmediate_operand" "=m,d,d,<f64_av>,Z,<f64_vsx>,<f64_vsx>,!r,Y,r,!r,*c*l,!r,*h,r,wg,r,<f64_dm>")
8230 (match_operand:FMOVE64 1 "input_operand" "d,m,d,Z,<f64_av>,<f64_vsx>,j,j,r,Y,r,r,h,0,wg,r,<f64_dm>,r"))]
8231 "TARGET_POWERPC64 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
8232 && (gpc_reg_operand (operands[0], <MODE>mode)
8233 || gpc_reg_operand (operands[1], <MODE>mode))"
8253 [(set_attr "type" "fpstore,fpload,fp,fpload,fpstore,vecsimple,vecsimple,integer,store,load,*,mtjmpr,mfjmpr,*,mftgpr,mffgpr,mftgpr,mffgpr")
8254 (set_attr "length" "4")])
8256 (define_insn "*mov<mode>_softfloat64"
8257 [(set (match_operand:FMOVE64 0 "nonimmediate_operand" "=Y,r,r,cl,r,r,r,r,*h")
8258 (match_operand:FMOVE64 1 "input_operand" "r,Y,r,r,h,G,H,F,0"))]
8259 "TARGET_POWERPC64 && (TARGET_SOFT_FLOAT || !TARGET_FPRS)
8260 && (gpc_reg_operand (operands[0], <MODE>mode)
8261 || gpc_reg_operand (operands[1], <MODE>mode))"
8272 [(set_attr "type" "store,load,*,mtjmpr,mfjmpr,*,*,*,*")
8273 (set_attr "length" "4,4,4,4,4,8,12,16,4")])
8275 (define_expand "mov<mode>"
8276 [(set (match_operand:FMOVE128 0 "general_operand" "")
8277 (match_operand:FMOVE128 1 "any_operand" ""))]
8279 "{ rs6000_emit_move (operands[0], operands[1], <MODE>mode); DONE; }")
8281 ;; It's important to list Y->r and r->Y before r->r because otherwise
8282 ;; reload, given m->r, will try to pick r->r and reload it, which
8283 ;; doesn't make progress.
8285 ;; We can't split little endian direct moves of TDmode, because the words are
8286 ;; not swapped like they are for TImode or TFmode. Subregs therefore are
8287 ;; problematical. Don't allow direct move for this case.
8289 (define_insn_and_split "*mov<mode>_64bit_dm"
8290 [(set (match_operand:FMOVE128 0 "nonimmediate_operand" "=m,d,d,ws,Y,r,r,r,wm")
8291 (match_operand:FMOVE128 1 "input_operand" "d,m,d,j,r,jY,r,wm,r"))]
8292 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_POWERPC64
8293 && (<MODE>mode != TDmode || WORDS_BIG_ENDIAN)
8294 && (gpc_reg_operand (operands[0], <MODE>mode)
8295 || gpc_reg_operand (operands[1], <MODE>mode))"
8297 "&& reload_completed"
8299 { rs6000_split_multireg_move (operands[0], operands[1]); DONE; }
8300 [(set_attr "length" "8,8,8,8,12,12,8,8,8")])
8302 (define_insn_and_split "*movtd_64bit_nodm"
8303 [(set (match_operand:TD 0 "nonimmediate_operand" "=m,d,d,ws,Y,r,r")
8304 (match_operand:TD 1 "input_operand" "d,m,d,j,r,jY,r"))]
8305 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_POWERPC64 && !WORDS_BIG_ENDIAN
8306 && (gpc_reg_operand (operands[0], TDmode)
8307 || gpc_reg_operand (operands[1], TDmode))"
8309 "&& reload_completed"
8311 { rs6000_split_multireg_move (operands[0], operands[1]); DONE; }
8312 [(set_attr "length" "8,8,8,8,12,12,8")])
8314 (define_insn_and_split "*mov<mode>_32bit"
8315 [(set (match_operand:FMOVE128 0 "nonimmediate_operand" "=m,d,d,ws,Y,r,r")
8316 (match_operand:FMOVE128 1 "input_operand" "d,m,d,j,r,jY,r"))]
8317 "TARGET_HARD_FLOAT && TARGET_FPRS && !TARGET_POWERPC64
8318 && (gpc_reg_operand (operands[0], <MODE>mode)
8319 || gpc_reg_operand (operands[1], <MODE>mode))"
8321 "&& reload_completed"
8323 { rs6000_split_multireg_move (operands[0], operands[1]); DONE; }
8324 [(set_attr "length" "8,8,8,8,20,20,16")])
8326 (define_insn_and_split "*mov<mode>_softfloat"
8327 [(set (match_operand:FMOVE128 0 "rs6000_nonimmediate_operand" "=Y,r,r")
8328 (match_operand:FMOVE128 1 "input_operand" "r,YGHF,r"))]
8329 "(TARGET_SOFT_FLOAT || !TARGET_FPRS)
8330 && (gpc_reg_operand (operands[0], <MODE>mode)
8331 || gpc_reg_operand (operands[1], <MODE>mode))"
8333 "&& reload_completed"
8335 { rs6000_split_multireg_move (operands[0], operands[1]); DONE; }
8336 [(set_attr "length" "20,20,16")])
8338 (define_expand "extenddftf2"
8339 [(set (match_operand:TF 0 "nonimmediate_operand" "")
8340 (float_extend:TF (match_operand:DF 1 "input_operand" "")))]
8342 && TARGET_HARD_FLOAT
8343 && (TARGET_FPRS || TARGET_E500_DOUBLE)
8344 && TARGET_LONG_DOUBLE_128"
8346 if (TARGET_E500_DOUBLE)
8347 emit_insn (gen_spe_extenddftf2 (operands[0], operands[1]));
8349 emit_insn (gen_extenddftf2_fprs (operands[0], operands[1]));
8353 (define_expand "extenddftf2_fprs"
8354 [(parallel [(set (match_operand:TF 0 "nonimmediate_operand" "")
8355 (float_extend:TF (match_operand:DF 1 "input_operand" "")))
8356 (use (match_dup 2))])]
8358 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
8359 && TARGET_LONG_DOUBLE_128"
8361 /* VSX can create 0.0 directly, otherwise let rs6000_emit_move create
8362 the proper constant. */
8364 operands[2] = CONST0_RTX (DFmode);
8367 operands[2] = gen_reg_rtx (DFmode);
8368 rs6000_emit_move (operands[2], CONST0_RTX (DFmode), DFmode);
8372 (define_insn_and_split "*extenddftf2_internal"
8373 [(set (match_operand:TF 0 "nonimmediate_operand" "=m,Y,ws,d,&d")
8374 (float_extend:TF (match_operand:DF 1 "input_operand" "d,r,md,md,md")))
8375 (use (match_operand:DF 2 "zero_reg_mem_operand" "d,r,j,m,d"))]
8377 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
8378 && TARGET_LONG_DOUBLE_128"
8380 "&& reload_completed"
8383 const int lo_word = LONG_DOUBLE_LARGE_FIRST ? GET_MODE_SIZE (DFmode) : 0;
8384 const int hi_word = LONG_DOUBLE_LARGE_FIRST ? 0 : GET_MODE_SIZE (DFmode);
8385 emit_move_insn (simplify_gen_subreg (DFmode, operands[0], TFmode, hi_word),
8387 emit_move_insn (simplify_gen_subreg (DFmode, operands[0], TFmode, lo_word),
8392 (define_expand "extendsftf2"
8393 [(set (match_operand:TF 0 "nonimmediate_operand" "")
8394 (float_extend:TF (match_operand:SF 1 "gpc_reg_operand" "")))]
8396 && TARGET_HARD_FLOAT
8397 && (TARGET_FPRS || TARGET_E500_DOUBLE)
8398 && TARGET_LONG_DOUBLE_128"
8400 rtx tmp = gen_reg_rtx (DFmode);
8401 emit_insn (gen_extendsfdf2 (tmp, operands[1]));
8402 emit_insn (gen_extenddftf2 (operands[0], tmp));
8406 (define_expand "trunctfdf2"
8407 [(set (match_operand:DF 0 "gpc_reg_operand" "")
8408 (float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "")))]
8410 && TARGET_HARD_FLOAT
8411 && (TARGET_FPRS || TARGET_E500_DOUBLE)
8412 && TARGET_LONG_DOUBLE_128"
8415 (define_insn_and_split "trunctfdf2_internal1"
8416 [(set (match_operand:DF 0 "gpc_reg_operand" "=d,?d")
8417 (float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "0,d")))]
8418 "!TARGET_IEEEQUAD && !TARGET_XL_COMPAT
8419 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128"
8423 "&& reload_completed && REGNO (operands[0]) == REGNO (operands[1])"
8426 emit_note (NOTE_INSN_DELETED);
8429 [(set_attr "type" "fp")])
8431 (define_insn "trunctfdf2_internal2"
8432 [(set (match_operand:DF 0 "gpc_reg_operand" "=d")
8433 (float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "d")))]
8434 "!TARGET_IEEEQUAD && TARGET_XL_COMPAT
8435 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
8436 && TARGET_LONG_DOUBLE_128"
8438 [(set_attr "type" "fp")
8439 (set_attr "fp_type" "fp_addsub_d")])
8441 (define_expand "trunctfsf2"
8442 [(set (match_operand:SF 0 "gpc_reg_operand" "")
8443 (float_truncate:SF (match_operand:TF 1 "gpc_reg_operand" "")))]
8445 && TARGET_HARD_FLOAT
8446 && (TARGET_FPRS || TARGET_E500_DOUBLE)
8447 && TARGET_LONG_DOUBLE_128"
8449 if (TARGET_E500_DOUBLE)
8450 emit_insn (gen_spe_trunctfsf2 (operands[0], operands[1]));
8452 emit_insn (gen_trunctfsf2_fprs (operands[0], operands[1]));
8456 (define_insn_and_split "trunctfsf2_fprs"
8457 [(set (match_operand:SF 0 "gpc_reg_operand" "=f")
8458 (float_truncate:SF (match_operand:TF 1 "gpc_reg_operand" "d")))
8459 (clobber (match_scratch:DF 2 "=d"))]
8461 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT
8462 && TARGET_LONG_DOUBLE_128"
8464 "&& reload_completed"
8466 (float_truncate:DF (match_dup 1)))
8468 (float_truncate:SF (match_dup 2)))]
8471 (define_expand "floatsitf2"
8472 [(set (match_operand:TF 0 "gpc_reg_operand" "")
8473 (float:TF (match_operand:SI 1 "gpc_reg_operand" "")))]
8475 && TARGET_HARD_FLOAT
8476 && (TARGET_FPRS || TARGET_E500_DOUBLE)
8477 && TARGET_LONG_DOUBLE_128"
8479 rtx tmp = gen_reg_rtx (DFmode);
8480 expand_float (tmp, operands[1], false);
8481 emit_insn (gen_extenddftf2 (operands[0], tmp));
8485 ; fadd, but rounding towards zero.
8486 ; This is probably not the optimal code sequence.
8487 (define_insn "fix_trunc_helper"
8488 [(set (match_operand:DF 0 "gpc_reg_operand" "=d")
8489 (unspec:DF [(match_operand:TF 1 "gpc_reg_operand" "d")]
8490 UNSPEC_FIX_TRUNC_TF))
8491 (clobber (match_operand:DF 2 "gpc_reg_operand" "=&d"))]
8492 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT"
8493 "mffs %2\n\tmtfsb1 31\n\tmtfsb0 30\n\tfadd %0,%1,%L1\n\tmtfsf 1,%2"
8494 [(set_attr "type" "fp")
8495 (set_attr "length" "20")])
8497 (define_expand "fix_trunctfsi2"
8498 [(set (match_operand:SI 0 "gpc_reg_operand" "")
8499 (fix:SI (match_operand:TF 1 "gpc_reg_operand" "")))]
8500 "!TARGET_IEEEQUAD && TARGET_HARD_FLOAT
8501 && (TARGET_FPRS || TARGET_E500_DOUBLE) && TARGET_LONG_DOUBLE_128"
8503 if (TARGET_E500_DOUBLE)
8504 emit_insn (gen_spe_fix_trunctfsi2 (operands[0], operands[1]));
8506 emit_insn (gen_fix_trunctfsi2_fprs (operands[0], operands[1]));
8510 (define_expand "fix_trunctfsi2_fprs"
8511 [(parallel [(set (match_operand:SI 0 "gpc_reg_operand" "")
8512 (fix:SI (match_operand:TF 1 "gpc_reg_operand" "")))
8513 (clobber (match_dup 2))
8514 (clobber (match_dup 3))
8515 (clobber (match_dup 4))
8516 (clobber (match_dup 5))])]
8518 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128"
8520 operands[2] = gen_reg_rtx (DFmode);
8521 operands[3] = gen_reg_rtx (DFmode);
8522 operands[4] = gen_reg_rtx (DImode);
8523 operands[5] = assign_stack_temp (DImode, GET_MODE_SIZE (DImode));
8526 (define_insn_and_split "*fix_trunctfsi2_internal"
8527 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
8528 (fix:SI (match_operand:TF 1 "gpc_reg_operand" "d")))
8529 (clobber (match_operand:DF 2 "gpc_reg_operand" "=d"))
8530 (clobber (match_operand:DF 3 "gpc_reg_operand" "=&d"))
8531 (clobber (match_operand:DI 4 "gpc_reg_operand" "=d"))
8532 (clobber (match_operand:DI 5 "offsettable_mem_operand" "=o"))]
8534 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128"
8540 emit_insn (gen_fix_trunc_helper (operands[2], operands[1], operands[3]));
8542 gcc_assert (MEM_P (operands[5]));
8543 lowword = adjust_address (operands[5], SImode, WORDS_BIG_ENDIAN ? 4 : 0);
8545 emit_insn (gen_fctiwz_df (operands[4], operands[2]));
8546 emit_move_insn (operands[5], operands[4]);
8547 emit_move_insn (operands[0], lowword);
8551 (define_expand "negtf2"
8552 [(set (match_operand:TF 0 "gpc_reg_operand" "")
8553 (neg:TF (match_operand:TF 1 "gpc_reg_operand" "")))]
8555 && TARGET_HARD_FLOAT
8556 && (TARGET_FPRS || TARGET_E500_DOUBLE)
8557 && TARGET_LONG_DOUBLE_128"
8560 (define_insn "negtf2_internal"
8561 [(set (match_operand:TF 0 "gpc_reg_operand" "=d")
8562 (neg:TF (match_operand:TF 1 "gpc_reg_operand" "d")))]
8564 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128"
8567 if (REGNO (operands[0]) == REGNO (operands[1]) + 1)
8568 return \"fneg %L0,%L1\;fneg %0,%1\";
8570 return \"fneg %0,%1\;fneg %L0,%L1\";
8572 [(set_attr "type" "fp")
8573 (set_attr "length" "8")])
8575 (define_expand "abstf2"
8576 [(set (match_operand:TF 0 "gpc_reg_operand" "")
8577 (abs:TF (match_operand:TF 1 "gpc_reg_operand" "")))]
8579 && TARGET_HARD_FLOAT
8580 && (TARGET_FPRS || TARGET_E500_DOUBLE)
8581 && TARGET_LONG_DOUBLE_128"
8584 rtx label = gen_label_rtx ();
8585 if (TARGET_E500_DOUBLE)
8587 if (flag_finite_math_only && !flag_trapping_math)
8588 emit_insn (gen_spe_abstf2_tst (operands[0], operands[1], label));
8590 emit_insn (gen_spe_abstf2_cmp (operands[0], operands[1], label));
8593 emit_insn (gen_abstf2_internal (operands[0], operands[1], label));
8598 (define_expand "abstf2_internal"
8599 [(set (match_operand:TF 0 "gpc_reg_operand" "")
8600 (match_operand:TF 1 "gpc_reg_operand" ""))
8601 (set (match_dup 3) (match_dup 5))
8602 (set (match_dup 5) (abs:DF (match_dup 5)))
8603 (set (match_dup 4) (compare:CCFP (match_dup 3) (match_dup 5)))
8604 (set (pc) (if_then_else (eq (match_dup 4) (const_int 0))
8605 (label_ref (match_operand 2 "" ""))
8607 (set (match_dup 6) (neg:DF (match_dup 6)))]
8609 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT
8610 && TARGET_LONG_DOUBLE_128"
8613 const int hi_word = LONG_DOUBLE_LARGE_FIRST ? 0 : GET_MODE_SIZE (DFmode);
8614 const int lo_word = LONG_DOUBLE_LARGE_FIRST ? GET_MODE_SIZE (DFmode) : 0;
8615 operands[3] = gen_reg_rtx (DFmode);
8616 operands[4] = gen_reg_rtx (CCFPmode);
8617 operands[5] = simplify_gen_subreg (DFmode, operands[0], TFmode, hi_word);
8618 operands[6] = simplify_gen_subreg (DFmode, operands[0], TFmode, lo_word);
8621 ;; Reload helper functions used by rs6000_secondary_reload. The patterns all
8622 ;; must have 3 arguments, and scratch register constraint must be a single
8625 ;; Reload patterns to support gpr load/store with misaligned mem.
8626 ;; and multiple gpr load/store at offset >= 0xfffc
8627 (define_expand "reload_<mode>_store"
8628 [(parallel [(match_operand 0 "memory_operand" "=m")
8629 (match_operand 1 "gpc_reg_operand" "r")
8630 (match_operand:GPR 2 "register_operand" "=&b")])]
8633 rs6000_secondary_reload_gpr (operands[1], operands[0], operands[2], true);
8637 (define_expand "reload_<mode>_load"
8638 [(parallel [(match_operand 0 "gpc_reg_operand" "=r")
8639 (match_operand 1 "memory_operand" "m")
8640 (match_operand:GPR 2 "register_operand" "=b")])]
8643 rs6000_secondary_reload_gpr (operands[0], operands[1], operands[2], false);
8648 ;; Reload patterns for various types using the vector registers. We may need
8649 ;; an additional base register to convert the reg+offset addressing to reg+reg
8650 ;; for vector registers and reg+reg or (reg+reg)&(-16) addressing to just an
8651 ;; index register for gpr registers.
8652 (define_expand "reload_<RELOAD:mode>_<P:mptrsize>_store"
8653 [(parallel [(match_operand:RELOAD 0 "memory_operand" "m")
8654 (match_operand:RELOAD 1 "gpc_reg_operand" "wa")
8655 (match_operand:P 2 "register_operand" "=b")])]
8658 rs6000_secondary_reload_inner (operands[1], operands[0], operands[2], true);
8662 (define_expand "reload_<RELOAD:mode>_<P:mptrsize>_load"
8663 [(parallel [(match_operand:RELOAD 0 "gpc_reg_operand" "wa")
8664 (match_operand:RELOAD 1 "memory_operand" "m")
8665 (match_operand:P 2 "register_operand" "=b")])]
8668 rs6000_secondary_reload_inner (operands[0], operands[1], operands[2], false);
8673 ;; Reload sometimes tries to move the address to a GPR, and can generate
8674 ;; invalid RTL for addresses involving AND -16. Allow addresses involving
8675 ;; reg+reg, reg+small constant, or just reg, all wrapped in an AND -16.
8677 (define_insn_and_split "*vec_reload_and_plus_<mptrsize>"
8678 [(set (match_operand:P 0 "gpc_reg_operand" "=b")
8679 (and:P (plus:P (match_operand:P 1 "gpc_reg_operand" "r")
8680 (match_operand:P 2 "reg_or_cint_operand" "rI"))
8682 "TARGET_ALTIVEC && (reload_in_progress || reload_completed)"
8684 "&& reload_completed"
8686 (plus:P (match_dup 1)
8689 (and:P (match_dup 0)
8692 ;; Power8 merge instructions to allow direct move to/from floating point
8693 ;; registers in 32-bit mode. We use TF mode to get two registers to move the
8694 ;; individual 32-bit parts across. Subreg doesn't work too well on the TF
8695 ;; value, since it is allocated in reload and not all of the flow information
8696 ;; is setup for it. We have two patterns to do the two moves between gprs and
8697 ;; fprs. There isn't a dependancy between the two, but we could potentially
8698 ;; schedule other instructions between the two instructions. TFmode is
8699 ;; currently limited to traditional FPR registers. If/when this is changed, we
8700 ;; will need to revist %L to make sure it works with VSX registers, or add an
8701 ;; %x version of %L.
8703 (define_insn "p8_fmrgow_<mode>"
8704 [(set (match_operand:FMOVE64X 0 "register_operand" "=d")
8705 (unspec:FMOVE64X [(match_operand:TF 1 "register_operand" "d")]
8706 UNSPEC_P8V_FMRGOW))]
8707 "!TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8709 [(set_attr "type" "vecperm")])
8711 (define_insn "p8_mtvsrwz_1"
8712 [(set (match_operand:TF 0 "register_operand" "=d")
8713 (unspec:TF [(match_operand:SI 1 "register_operand" "r")]
8714 UNSPEC_P8V_MTVSRWZ))]
8715 "!TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8717 [(set_attr "type" "mftgpr")])
8719 (define_insn "p8_mtvsrwz_2"
8720 [(set (match_operand:TF 0 "register_operand" "+d")
8721 (unspec:TF [(match_dup 0)
8722 (match_operand:SI 1 "register_operand" "r")]
8723 UNSPEC_P8V_MTVSRWZ))]
8724 "!TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8726 [(set_attr "type" "mftgpr")])
8728 (define_insn_and_split "reload_fpr_from_gpr<mode>"
8729 [(set (match_operand:FMOVE64X 0 "register_operand" "=ws")
8730 (unspec:FMOVE64X [(match_operand:FMOVE64X 1 "register_operand" "r")]
8731 UNSPEC_P8V_RELOAD_FROM_GPR))
8732 (clobber (match_operand:TF 2 "register_operand" "=d"))]
8733 "!TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8735 "&& reload_completed"
8738 rtx dest = operands[0];
8739 rtx src = operands[1];
8740 rtx tmp = operands[2];
8741 rtx gpr_hi_reg = gen_highpart (SImode, src);
8742 rtx gpr_lo_reg = gen_lowpart (SImode, src);
8744 emit_insn (gen_p8_mtvsrwz_1 (tmp, gpr_hi_reg));
8745 emit_insn (gen_p8_mtvsrwz_2 (tmp, gpr_lo_reg));
8746 emit_insn (gen_p8_fmrgow_<mode> (dest, tmp));
8749 [(set_attr "length" "12")
8750 (set_attr "type" "three")])
8752 ;; Move 128 bit values from GPRs to VSX registers in 64-bit mode
8753 (define_insn "p8_mtvsrd_1"
8754 [(set (match_operand:TF 0 "register_operand" "=ws")
8755 (unspec:TF [(match_operand:DI 1 "register_operand" "r")]
8756 UNSPEC_P8V_MTVSRD))]
8757 "TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8759 [(set_attr "type" "mftgpr")])
8761 (define_insn "p8_mtvsrd_2"
8762 [(set (match_operand:TF 0 "register_operand" "+ws")
8763 (unspec:TF [(match_dup 0)
8764 (match_operand:DI 1 "register_operand" "r")]
8765 UNSPEC_P8V_MTVSRD))]
8766 "TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8768 [(set_attr "type" "mftgpr")])
8770 (define_insn "p8_xxpermdi_<mode>"
8771 [(set (match_operand:FMOVE128_GPR 0 "register_operand" "=wa")
8772 (unspec:FMOVE128_GPR [(match_operand:TF 1 "register_operand" "ws")]
8773 UNSPEC_P8V_XXPERMDI))]
8774 "TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8775 "xxpermdi %x0,%1,%L1,0"
8776 [(set_attr "type" "vecperm")])
8778 (define_insn_and_split "reload_vsx_from_gpr<mode>"
8779 [(set (match_operand:FMOVE128_GPR 0 "register_operand" "=wa")
8780 (unspec:FMOVE128_GPR
8781 [(match_operand:FMOVE128_GPR 1 "register_operand" "r")]
8782 UNSPEC_P8V_RELOAD_FROM_GPR))
8783 (clobber (match_operand:TF 2 "register_operand" "=ws"))]
8784 "TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8786 "&& reload_completed"
8789 rtx dest = operands[0];
8790 rtx src = operands[1];
8791 rtx tmp = operands[2];
8792 rtx gpr_hi_reg = gen_highpart (DImode, src);
8793 rtx gpr_lo_reg = gen_lowpart (DImode, src);
8795 emit_insn (gen_p8_mtvsrd_1 (tmp, gpr_hi_reg));
8796 emit_insn (gen_p8_mtvsrd_2 (tmp, gpr_lo_reg));
8797 emit_insn (gen_p8_xxpermdi_<mode> (dest, tmp));
8800 [(set_attr "length" "12")
8801 (set_attr "type" "three")])
8804 [(set (match_operand:FMOVE128_GPR 0 "nonimmediate_operand" "")
8805 (match_operand:FMOVE128_GPR 1 "input_operand" ""))]
8807 && (int_reg_operand (operands[0], <MODE>mode)
8808 || int_reg_operand (operands[1], <MODE>mode))"
8810 { rs6000_split_multireg_move (operands[0], operands[1]); DONE; })
8812 ;; Move SFmode to a VSX from a GPR register. Because scalar floating point
8813 ;; type is stored internally as double precision in the VSX registers, we have
8814 ;; to convert it from the vector format.
8816 (define_insn_and_split "reload_vsx_from_gprsf"
8817 [(set (match_operand:SF 0 "register_operand" "=wa")
8818 (unspec:SF [(match_operand:SF 1 "register_operand" "r")]
8819 UNSPEC_P8V_RELOAD_FROM_GPR))
8820 (clobber (match_operand:DI 2 "register_operand" "=r"))]
8821 "TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8823 "&& reload_completed"
8826 rtx op0 = operands[0];
8827 rtx op1 = operands[1];
8828 rtx op2 = operands[2];
8829 /* Also use the destination register to hold the unconverted DImode value.
8830 This is conceptually a separate value from OP0, so we use gen_rtx_REG
8831 rather than simplify_gen_subreg. */
8832 rtx op0_di = gen_rtx_REG (DImode, REGNO (op0));
8833 rtx op1_di = simplify_gen_subreg (DImode, op1, SFmode, 0);
8835 /* Move SF value to upper 32-bits for xscvspdpn. */
8836 emit_insn (gen_ashldi3 (op2, op1_di, GEN_INT (32)));
8837 emit_move_insn (op0_di, op2);
8838 emit_insn (gen_vsx_xscvspdpn_directmove (op0, op0_di));
8841 [(set_attr "length" "8")
8842 (set_attr "type" "two")])
8844 ;; Move 128 bit values from VSX registers to GPRs in 64-bit mode by doing a
8845 ;; normal 64-bit move, followed by an xxpermdi to get the bottom 64-bit value,
8846 ;; and then doing a move of that.
8847 (define_insn "p8_mfvsrd_3_<mode>"
8848 [(set (match_operand:DF 0 "register_operand" "=r")
8849 (unspec:DF [(match_operand:FMOVE128_GPR 1 "register_operand" "wa")]
8850 UNSPEC_P8V_RELOAD_FROM_VSX))]
8851 "TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8853 [(set_attr "type" "mftgpr")])
8855 (define_insn_and_split "reload_gpr_from_vsx<mode>"
8856 [(set (match_operand:FMOVE128_GPR 0 "register_operand" "=r")
8857 (unspec:FMOVE128_GPR
8858 [(match_operand:FMOVE128_GPR 1 "register_operand" "wa")]
8859 UNSPEC_P8V_RELOAD_FROM_VSX))
8860 (clobber (match_operand:FMOVE128_GPR 2 "register_operand" "=wa"))]
8861 "TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8863 "&& reload_completed"
8866 rtx dest = operands[0];
8867 rtx src = operands[1];
8868 rtx tmp = operands[2];
8869 rtx gpr_hi_reg = gen_highpart (DFmode, dest);
8870 rtx gpr_lo_reg = gen_lowpart (DFmode, dest);
8872 emit_insn (gen_p8_mfvsrd_3_<mode> (gpr_hi_reg, src));
8873 emit_insn (gen_vsx_xxpermdi_<mode> (tmp, src, src, GEN_INT (3)));
8874 emit_insn (gen_p8_mfvsrd_3_<mode> (gpr_lo_reg, tmp));
8877 [(set_attr "length" "12")
8878 (set_attr "type" "three")])
8880 ;; Move SFmode to a GPR from a VSX register. Because scalar floating point
8881 ;; type is stored internally as double precision, we have to convert it to the
8884 (define_insn_and_split "reload_gpr_from_vsxsf"
8885 [(set (match_operand:SF 0 "register_operand" "=r")
8886 (unspec:SF [(match_operand:SF 1 "register_operand" "wa")]
8887 UNSPEC_P8V_RELOAD_FROM_VSX))
8888 (clobber (match_operand:V4SF 2 "register_operand" "=wa"))]
8889 "TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8891 "&& reload_completed"
8894 rtx op0 = operands[0];
8895 rtx op1 = operands[1];
8896 rtx op2 = operands[2];
8897 rtx diop0 = simplify_gen_subreg (DImode, op0, SFmode, 0);
8899 emit_insn (gen_vsx_xscvdpspn_scalar (op2, op1));
8900 emit_insn (gen_p8_mfvsrd_4_disf (diop0, op2));
8901 emit_insn (gen_lshrdi3 (diop0, diop0, GEN_INT (32)));
8904 [(set_attr "length" "12")
8905 (set_attr "type" "three")])
8907 (define_insn "p8_mfvsrd_4_disf"
8908 [(set (match_operand:DI 0 "register_operand" "=r")
8909 (unspec:DI [(match_operand:V4SF 1 "register_operand" "wa")]
8910 UNSPEC_P8V_RELOAD_FROM_VSX))]
8911 "TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
8913 [(set_attr "type" "mftgpr")])
8916 ;; Next come the multi-word integer load and store and the load and store
8919 ;; List r->r after r->Y, otherwise reload will try to reload a
8920 ;; non-offsettable address by using r->r which won't make progress.
8921 ;; Use of fprs is disparaged slightly otherwise reload prefers to reload
8922 ;; a gpr into a fpr instead of reloading an invalid 'Y' address
8923 (define_insn "*movdi_internal32"
8924 [(set (match_operand:DI 0 "rs6000_nonimmediate_operand" "=Y,r,r,?m,?*d,?*d,r")
8925 (match_operand:DI 1 "input_operand" "r,Y,r,d,m,d,IJKnGHF"))]
8927 && (gpc_reg_operand (operands[0], DImode)
8928 || gpc_reg_operand (operands[1], DImode))"
8937 [(set_attr "type" "store,load,*,fpstore,fpload,fp,*")])
8940 [(set (match_operand:DI 0 "gpc_reg_operand" "")
8941 (match_operand:DI 1 "const_int_operand" ""))]
8942 "! TARGET_POWERPC64 && reload_completed
8943 && gpr_or_gpr_p (operands[0], operands[1])
8944 && !direct_move_p (operands[0], operands[1])"
8945 [(set (match_dup 2) (match_dup 4))
8946 (set (match_dup 3) (match_dup 1))]
8949 HOST_WIDE_INT value = INTVAL (operands[1]);
8950 operands[2] = operand_subword_force (operands[0], WORDS_BIG_ENDIAN == 0,
8952 operands[3] = operand_subword_force (operands[0], WORDS_BIG_ENDIAN != 0,
8954 operands[4] = GEN_INT (value >> 32);
8955 operands[1] = GEN_INT (((value & 0xffffffff) ^ 0x80000000) - 0x80000000);
8959 [(set (match_operand:DIFD 0 "rs6000_nonimmediate_operand" "")
8960 (match_operand:DIFD 1 "input_operand" ""))]
8961 "reload_completed && !TARGET_POWERPC64
8962 && gpr_or_gpr_p (operands[0], operands[1])
8963 && !direct_move_p (operands[0], operands[1])"
8965 { rs6000_split_multireg_move (operands[0], operands[1]); DONE; })
8967 (define_insn "*movdi_internal64"
8968 [(set (match_operand:DI 0 "nonimmediate_operand" "=Y,r,r,r,r,r,?m,?*d,?*d,r,*h,*h,r,?*wg,r,?*wj,?*wi")
8969 (match_operand:DI 1 "input_operand" "r,Y,r,I,L,nF,d,m,d,*h,r,0,*wg,r,*wj,r,O"))]
8971 && (gpc_reg_operand (operands[0], DImode)
8972 || gpc_reg_operand (operands[1], DImode))"
8991 [(set_attr "type" "store,load,*,*,*,*,fpstore,fpload,fp,mfjmpr,mtjmpr,*,mftgpr,mffgpr,mftgpr,mffgpr,vecsimple")
8992 (set_attr "length" "4,4,4,4,4,20,4,4,4,4,4,4,4,4,4,4,4")])
8994 ;; Generate all one-bits and clear left or right.
8995 ;; Use (and:DI (rotate:DI ...)) to avoid anddi3 unnecessary clobber.
8997 [(set (match_operand:DI 0 "gpc_reg_operand" "")
8998 (match_operand:DI 1 "mask64_operand" ""))]
8999 "TARGET_POWERPC64 && num_insns_constant (operands[1], DImode) > 1"
9000 [(set (match_dup 0) (const_int -1))
9002 (and:DI (rotate:DI (match_dup 0)
9007 ;; Split a load of a large constant into the appropriate five-instruction
9008 ;; sequence. Handle anything in a constant number of insns.
9009 ;; When non-easy constants can go in the TOC, this should use
9010 ;; easy_fp_constant predicate.
9012 [(set (match_operand:DI 0 "gpc_reg_operand" "")
9013 (match_operand:DI 1 "const_int_operand" ""))]
9014 "TARGET_POWERPC64 && num_insns_constant (operands[1], DImode) > 1"
9015 [(set (match_dup 0) (match_dup 2))
9016 (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 3)))]
9019 if (rs6000_emit_set_const (operands[0], operands[1]))
9026 [(set (match_operand:DI 0 "gpc_reg_operand" "")
9027 (match_operand:DI 1 "const_scalar_int_operand" ""))]
9028 "TARGET_POWERPC64 && num_insns_constant (operands[1], DImode) > 1"
9029 [(set (match_dup 0) (match_dup 2))
9030 (set (match_dup 0) (plus:DI (match_dup 0) (match_dup 3)))]
9033 if (rs6000_emit_set_const (operands[0], operands[1]))
9039 ;; TImode/PTImode is similar, except that we usually want to compute the
9040 ;; address into a register and use lsi/stsi (the exception is during reload).
9042 (define_insn "*mov<mode>_string"
9043 [(set (match_operand:TI2 0 "reg_or_mem_operand" "=Q,Y,????r,????r,????r,r")
9044 (match_operand:TI2 1 "input_operand" "r,r,Q,Y,r,n"))]
9046 && (<MODE>mode != TImode || VECTOR_MEM_NONE_P (TImode))
9047 && (gpc_reg_operand (operands[0], <MODE>mode)
9048 || gpc_reg_operand (operands[1], <MODE>mode))"
9051 switch (which_alternative)
9057 return \"stswi %1,%P0,16\";
9061 /* If the address is not used in the output, we can use lsi. Otherwise,
9062 fall through to generating four loads. */
9064 && ! reg_overlap_mentioned_p (operands[0], operands[1]))
9065 return \"lswi %0,%P1,16\";
9066 /* ... fall through ... */
9073 [(set_attr "type" "store,store,load,load,*,*")
9074 (set_attr "update" "yes")
9075 (set_attr "indexed" "yes")
9076 (set (attr "cell_micro") (if_then_else (match_test "TARGET_STRING")
9077 (const_string "always")
9078 (const_string "conditional")))])
9080 (define_insn "*mov<mode>_ppc64"
9081 [(set (match_operand:TI2 0 "nonimmediate_operand" "=wQ,Y,r,r,r,r")
9082 (match_operand:TI2 1 "input_operand" "r,r,wQ,Y,r,n"))]
9083 "(TARGET_POWERPC64 && VECTOR_MEM_NONE_P (<MODE>mode)
9084 && (gpc_reg_operand (operands[0], <MODE>mode)
9085 || gpc_reg_operand (operands[1], <MODE>mode)))"
9087 return rs6000_output_move_128bit (operands);
9089 [(set_attr "type" "store,store,load,load,*,*")
9090 (set_attr "length" "8")])
9093 [(set (match_operand:TI2 0 "int_reg_operand" "")
9094 (match_operand:TI2 1 "const_scalar_int_operand" ""))]
9096 && (VECTOR_MEM_NONE_P (<MODE>mode)
9097 || (reload_completed && INT_REGNO_P (REGNO (operands[0]))))"
9098 [(set (match_dup 2) (match_dup 4))
9099 (set (match_dup 3) (match_dup 5))]
9102 operands[2] = operand_subword_force (operands[0], WORDS_BIG_ENDIAN == 0,
9104 operands[3] = operand_subword_force (operands[0], WORDS_BIG_ENDIAN != 0,
9106 if (CONST_WIDE_INT_P (operands[1]))
9108 operands[4] = GEN_INT (CONST_WIDE_INT_ELT (operands[1], 1));
9109 operands[5] = GEN_INT (CONST_WIDE_INT_ELT (operands[1], 0));
9111 else if (CONST_INT_P (operands[1]))
9113 operands[4] = GEN_INT (- (INTVAL (operands[1]) < 0));
9114 operands[5] = operands[1];
9121 [(set (match_operand:TI2 0 "nonimmediate_operand" "")
9122 (match_operand:TI2 1 "input_operand" ""))]
9124 && gpr_or_gpr_p (operands[0], operands[1])
9125 && !direct_move_p (operands[0], operands[1])
9126 && !quad_load_store_p (operands[0], operands[1])"
9128 { rs6000_split_multireg_move (operands[0], operands[1]); DONE; })
9130 (define_expand "load_multiple"
9131 [(match_par_dup 3 [(set (match_operand:SI 0 "" "")
9132 (match_operand:SI 1 "" ""))
9133 (use (match_operand:SI 2 "" ""))])]
9134 "TARGET_STRING && !TARGET_POWERPC64"
9142 /* Support only loading a constant number of fixed-point registers from
9143 memory and only bother with this if more than two; the machine
9144 doesn't support more than eight. */
9145 if (GET_CODE (operands[2]) != CONST_INT
9146 || INTVAL (operands[2]) <= 2
9147 || INTVAL (operands[2]) > 8
9148 || GET_CODE (operands[1]) != MEM
9149 || GET_CODE (operands[0]) != REG
9150 || REGNO (operands[0]) >= 32)
9153 count = INTVAL (operands[2]);
9154 regno = REGNO (operands[0]);
9156 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count));
9157 op1 = replace_equiv_address (operands[1],
9158 force_reg (SImode, XEXP (operands[1], 0)));
9160 for (i = 0; i < count; i++)
9161 XVECEXP (operands[3], 0, i)
9162 = gen_rtx_SET (gen_rtx_REG (SImode, regno + i),
9163 adjust_address_nv (op1, SImode, i * 4));
9166 (define_insn "*ldmsi8"
9167 [(match_parallel 0 "load_multiple_operation"
9168 [(set (match_operand:SI 2 "gpc_reg_operand" "")
9169 (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")))
9170 (set (match_operand:SI 3 "gpc_reg_operand" "")
9171 (mem:SI (plus:SI (match_dup 1) (const_int 4))))
9172 (set (match_operand:SI 4 "gpc_reg_operand" "")
9173 (mem:SI (plus:SI (match_dup 1) (const_int 8))))
9174 (set (match_operand:SI 5 "gpc_reg_operand" "")
9175 (mem:SI (plus:SI (match_dup 1) (const_int 12))))
9176 (set (match_operand:SI 6 "gpc_reg_operand" "")
9177 (mem:SI (plus:SI (match_dup 1) (const_int 16))))
9178 (set (match_operand:SI 7 "gpc_reg_operand" "")
9179 (mem:SI (plus:SI (match_dup 1) (const_int 20))))
9180 (set (match_operand:SI 8 "gpc_reg_operand" "")
9181 (mem:SI (plus:SI (match_dup 1) (const_int 24))))
9182 (set (match_operand:SI 9 "gpc_reg_operand" "")
9183 (mem:SI (plus:SI (match_dup 1) (const_int 28))))])]
9184 "TARGET_STRING && XVECLEN (operands[0], 0) == 8"
9186 { return rs6000_output_load_multiple (operands); }"
9187 [(set_attr "type" "load")
9188 (set_attr "update" "yes")
9189 (set_attr "indexed" "yes")
9190 (set_attr "length" "32")])
9192 (define_insn "*ldmsi7"
9193 [(match_parallel 0 "load_multiple_operation"
9194 [(set (match_operand:SI 2 "gpc_reg_operand" "")
9195 (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")))
9196 (set (match_operand:SI 3 "gpc_reg_operand" "")
9197 (mem:SI (plus:SI (match_dup 1) (const_int 4))))
9198 (set (match_operand:SI 4 "gpc_reg_operand" "")
9199 (mem:SI (plus:SI (match_dup 1) (const_int 8))))
9200 (set (match_operand:SI 5 "gpc_reg_operand" "")
9201 (mem:SI (plus:SI (match_dup 1) (const_int 12))))
9202 (set (match_operand:SI 6 "gpc_reg_operand" "")
9203 (mem:SI (plus:SI (match_dup 1) (const_int 16))))
9204 (set (match_operand:SI 7 "gpc_reg_operand" "")
9205 (mem:SI (plus:SI (match_dup 1) (const_int 20))))
9206 (set (match_operand:SI 8 "gpc_reg_operand" "")
9207 (mem:SI (plus:SI (match_dup 1) (const_int 24))))])]
9208 "TARGET_STRING && XVECLEN (operands[0], 0) == 7"
9210 { return rs6000_output_load_multiple (operands); }"
9211 [(set_attr "type" "load")
9212 (set_attr "update" "yes")
9213 (set_attr "indexed" "yes")
9214 (set_attr "length" "32")])
9216 (define_insn "*ldmsi6"
9217 [(match_parallel 0 "load_multiple_operation"
9218 [(set (match_operand:SI 2 "gpc_reg_operand" "")
9219 (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")))
9220 (set (match_operand:SI 3 "gpc_reg_operand" "")
9221 (mem:SI (plus:SI (match_dup 1) (const_int 4))))
9222 (set (match_operand:SI 4 "gpc_reg_operand" "")
9223 (mem:SI (plus:SI (match_dup 1) (const_int 8))))
9224 (set (match_operand:SI 5 "gpc_reg_operand" "")
9225 (mem:SI (plus:SI (match_dup 1) (const_int 12))))
9226 (set (match_operand:SI 6 "gpc_reg_operand" "")
9227 (mem:SI (plus:SI (match_dup 1) (const_int 16))))
9228 (set (match_operand:SI 7 "gpc_reg_operand" "")
9229 (mem:SI (plus:SI (match_dup 1) (const_int 20))))])]
9230 "TARGET_STRING && XVECLEN (operands[0], 0) == 6"
9232 { return rs6000_output_load_multiple (operands); }"
9233 [(set_attr "type" "load")
9234 (set_attr "update" "yes")
9235 (set_attr "indexed" "yes")
9236 (set_attr "length" "32")])
9238 (define_insn "*ldmsi5"
9239 [(match_parallel 0 "load_multiple_operation"
9240 [(set (match_operand:SI 2 "gpc_reg_operand" "")
9241 (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")))
9242 (set (match_operand:SI 3 "gpc_reg_operand" "")
9243 (mem:SI (plus:SI (match_dup 1) (const_int 4))))
9244 (set (match_operand:SI 4 "gpc_reg_operand" "")
9245 (mem:SI (plus:SI (match_dup 1) (const_int 8))))
9246 (set (match_operand:SI 5 "gpc_reg_operand" "")
9247 (mem:SI (plus:SI (match_dup 1) (const_int 12))))
9248 (set (match_operand:SI 6 "gpc_reg_operand" "")
9249 (mem:SI (plus:SI (match_dup 1) (const_int 16))))])]
9250 "TARGET_STRING && XVECLEN (operands[0], 0) == 5"
9252 { return rs6000_output_load_multiple (operands); }"
9253 [(set_attr "type" "load")
9254 (set_attr "update" "yes")
9255 (set_attr "indexed" "yes")
9256 (set_attr "length" "32")])
9258 (define_insn "*ldmsi4"
9259 [(match_parallel 0 "load_multiple_operation"
9260 [(set (match_operand:SI 2 "gpc_reg_operand" "")
9261 (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")))
9262 (set (match_operand:SI 3 "gpc_reg_operand" "")
9263 (mem:SI (plus:SI (match_dup 1) (const_int 4))))
9264 (set (match_operand:SI 4 "gpc_reg_operand" "")
9265 (mem:SI (plus:SI (match_dup 1) (const_int 8))))
9266 (set (match_operand:SI 5 "gpc_reg_operand" "")
9267 (mem:SI (plus:SI (match_dup 1) (const_int 12))))])]
9268 "TARGET_STRING && XVECLEN (operands[0], 0) == 4"
9270 { return rs6000_output_load_multiple (operands); }"
9271 [(set_attr "type" "load")
9272 (set_attr "update" "yes")
9273 (set_attr "indexed" "yes")
9274 (set_attr "length" "32")])
9276 (define_insn "*ldmsi3"
9277 [(match_parallel 0 "load_multiple_operation"
9278 [(set (match_operand:SI 2 "gpc_reg_operand" "")
9279 (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")))
9280 (set (match_operand:SI 3 "gpc_reg_operand" "")
9281 (mem:SI (plus:SI (match_dup 1) (const_int 4))))
9282 (set (match_operand:SI 4 "gpc_reg_operand" "")
9283 (mem:SI (plus:SI (match_dup 1) (const_int 8))))])]
9284 "TARGET_STRING && XVECLEN (operands[0], 0) == 3"
9286 { return rs6000_output_load_multiple (operands); }"
9287 [(set_attr "type" "load")
9288 (set_attr "update" "yes")
9289 (set_attr "indexed" "yes")
9290 (set_attr "length" "32")])
9292 (define_expand "store_multiple"
9293 [(match_par_dup 3 [(set (match_operand:SI 0 "" "")
9294 (match_operand:SI 1 "" ""))
9295 (clobber (scratch:SI))
9296 (use (match_operand:SI 2 "" ""))])]
9297 "TARGET_STRING && !TARGET_POWERPC64"
9306 /* Support only storing a constant number of fixed-point registers to
9307 memory and only bother with this if more than two; the machine
9308 doesn't support more than eight. */
9309 if (GET_CODE (operands[2]) != CONST_INT
9310 || INTVAL (operands[2]) <= 2
9311 || INTVAL (operands[2]) > 8
9312 || GET_CODE (operands[0]) != MEM
9313 || GET_CODE (operands[1]) != REG
9314 || REGNO (operands[1]) >= 32)
9317 count = INTVAL (operands[2]);
9318 regno = REGNO (operands[1]);
9320 operands[3] = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (count + 1));
9321 to = force_reg (SImode, XEXP (operands[0], 0));
9322 op0 = replace_equiv_address (operands[0], to);
9324 XVECEXP (operands[3], 0, 0)
9325 = gen_rtx_SET (adjust_address_nv (op0, SImode, 0), operands[1]);
9326 XVECEXP (operands[3], 0, 1) = gen_rtx_CLOBBER (VOIDmode,
9327 gen_rtx_SCRATCH (SImode));
9329 for (i = 1; i < count; i++)
9330 XVECEXP (operands[3], 0, i + 1)
9331 = gen_rtx_SET (adjust_address_nv (op0, SImode, i * 4),
9332 gen_rtx_REG (SImode, regno + i));
9335 (define_insn "*stmsi8"
9336 [(match_parallel 0 "store_multiple_operation"
9337 [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b"))
9338 (match_operand:SI 2 "gpc_reg_operand" "r"))
9339 (clobber (match_scratch:SI 3 "=X"))
9340 (set (mem:SI (plus:SI (match_dup 1) (const_int 4)))
9341 (match_operand:SI 4 "gpc_reg_operand" "r"))
9342 (set (mem:SI (plus:SI (match_dup 1) (const_int 8)))
9343 (match_operand:SI 5 "gpc_reg_operand" "r"))
9344 (set (mem:SI (plus:SI (match_dup 1) (const_int 12)))
9345 (match_operand:SI 6 "gpc_reg_operand" "r"))
9346 (set (mem:SI (plus:SI (match_dup 1) (const_int 16)))
9347 (match_operand:SI 7 "gpc_reg_operand" "r"))
9348 (set (mem:SI (plus:SI (match_dup 1) (const_int 20)))
9349 (match_operand:SI 8 "gpc_reg_operand" "r"))
9350 (set (mem:SI (plus:SI (match_dup 1) (const_int 24)))
9351 (match_operand:SI 9 "gpc_reg_operand" "r"))
9352 (set (mem:SI (plus:SI (match_dup 1) (const_int 28)))
9353 (match_operand:SI 10 "gpc_reg_operand" "r"))])]
9354 "TARGET_STRING && XVECLEN (operands[0], 0) == 9"
9356 [(set_attr "type" "store")
9357 (set_attr "update" "yes")
9358 (set_attr "indexed" "yes")
9359 (set_attr "cell_micro" "always")])
9361 (define_insn "*stmsi7"
9362 [(match_parallel 0 "store_multiple_operation"
9363 [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b"))
9364 (match_operand:SI 2 "gpc_reg_operand" "r"))
9365 (clobber (match_scratch:SI 3 "=X"))
9366 (set (mem:SI (plus:SI (match_dup 1) (const_int 4)))
9367 (match_operand:SI 4 "gpc_reg_operand" "r"))
9368 (set (mem:SI (plus:SI (match_dup 1) (const_int 8)))
9369 (match_operand:SI 5 "gpc_reg_operand" "r"))
9370 (set (mem:SI (plus:SI (match_dup 1) (const_int 12)))
9371 (match_operand:SI 6 "gpc_reg_operand" "r"))
9372 (set (mem:SI (plus:SI (match_dup 1) (const_int 16)))
9373 (match_operand:SI 7 "gpc_reg_operand" "r"))
9374 (set (mem:SI (plus:SI (match_dup 1) (const_int 20)))
9375 (match_operand:SI 8 "gpc_reg_operand" "r"))
9376 (set (mem:SI (plus:SI (match_dup 1) (const_int 24)))
9377 (match_operand:SI 9 "gpc_reg_operand" "r"))])]
9378 "TARGET_STRING && XVECLEN (operands[0], 0) == 8"
9380 [(set_attr "type" "store")
9381 (set_attr "update" "yes")
9382 (set_attr "indexed" "yes")
9383 (set_attr "cell_micro" "always")])
9385 (define_insn "*stmsi6"
9386 [(match_parallel 0 "store_multiple_operation"
9387 [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b"))
9388 (match_operand:SI 2 "gpc_reg_operand" "r"))
9389 (clobber (match_scratch:SI 3 "=X"))
9390 (set (mem:SI (plus:SI (match_dup 1) (const_int 4)))
9391 (match_operand:SI 4 "gpc_reg_operand" "r"))
9392 (set (mem:SI (plus:SI (match_dup 1) (const_int 8)))
9393 (match_operand:SI 5 "gpc_reg_operand" "r"))
9394 (set (mem:SI (plus:SI (match_dup 1) (const_int 12)))
9395 (match_operand:SI 6 "gpc_reg_operand" "r"))
9396 (set (mem:SI (plus:SI (match_dup 1) (const_int 16)))
9397 (match_operand:SI 7 "gpc_reg_operand" "r"))
9398 (set (mem:SI (plus:SI (match_dup 1) (const_int 20)))
9399 (match_operand:SI 8 "gpc_reg_operand" "r"))])]
9400 "TARGET_STRING && XVECLEN (operands[0], 0) == 7"
9402 [(set_attr "type" "store")
9403 (set_attr "update" "yes")
9404 (set_attr "indexed" "yes")
9405 (set_attr "cell_micro" "always")])
9407 (define_insn "*stmsi5"
9408 [(match_parallel 0 "store_multiple_operation"
9409 [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b"))
9410 (match_operand:SI 2 "gpc_reg_operand" "r"))
9411 (clobber (match_scratch:SI 3 "=X"))
9412 (set (mem:SI (plus:SI (match_dup 1) (const_int 4)))
9413 (match_operand:SI 4 "gpc_reg_operand" "r"))
9414 (set (mem:SI (plus:SI (match_dup 1) (const_int 8)))
9415 (match_operand:SI 5 "gpc_reg_operand" "r"))
9416 (set (mem:SI (plus:SI (match_dup 1) (const_int 12)))
9417 (match_operand:SI 6 "gpc_reg_operand" "r"))
9418 (set (mem:SI (plus:SI (match_dup 1) (const_int 16)))
9419 (match_operand:SI 7 "gpc_reg_operand" "r"))])]
9420 "TARGET_STRING && XVECLEN (operands[0], 0) == 6"
9422 [(set_attr "type" "store")
9423 (set_attr "update" "yes")
9424 (set_attr "indexed" "yes")
9425 (set_attr "cell_micro" "always")])
9427 (define_insn "*stmsi4"
9428 [(match_parallel 0 "store_multiple_operation"
9429 [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b"))
9430 (match_operand:SI 2 "gpc_reg_operand" "r"))
9431 (clobber (match_scratch:SI 3 "=X"))
9432 (set (mem:SI (plus:SI (match_dup 1) (const_int 4)))
9433 (match_operand:SI 4 "gpc_reg_operand" "r"))
9434 (set (mem:SI (plus:SI (match_dup 1) (const_int 8)))
9435 (match_operand:SI 5 "gpc_reg_operand" "r"))
9436 (set (mem:SI (plus:SI (match_dup 1) (const_int 12)))
9437 (match_operand:SI 6 "gpc_reg_operand" "r"))])]
9438 "TARGET_STRING && XVECLEN (operands[0], 0) == 5"
9440 [(set_attr "type" "store")
9441 (set_attr "update" "yes")
9442 (set_attr "indexed" "yes")
9443 (set_attr "cell_micro" "always")])
9445 (define_insn "*stmsi3"
9446 [(match_parallel 0 "store_multiple_operation"
9447 [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b"))
9448 (match_operand:SI 2 "gpc_reg_operand" "r"))
9449 (clobber (match_scratch:SI 3 "=X"))
9450 (set (mem:SI (plus:SI (match_dup 1) (const_int 4)))
9451 (match_operand:SI 4 "gpc_reg_operand" "r"))
9452 (set (mem:SI (plus:SI (match_dup 1) (const_int 8)))
9453 (match_operand:SI 5 "gpc_reg_operand" "r"))])]
9454 "TARGET_STRING && XVECLEN (operands[0], 0) == 4"
9456 [(set_attr "type" "store")
9457 (set_attr "update" "yes")
9458 (set_attr "indexed" "yes")
9459 (set_attr "cell_micro" "always")])
9461 (define_expand "setmemsi"
9462 [(parallel [(set (match_operand:BLK 0 "" "")
9463 (match_operand 2 "const_int_operand" ""))
9464 (use (match_operand:SI 1 "" ""))
9465 (use (match_operand:SI 3 "" ""))])]
9469 /* If value to set is not zero, use the library routine. */
9470 if (operands[2] != const0_rtx)
9473 if (expand_block_clear (operands))
9479 ;; String/block move insn.
9480 ;; Argument 0 is the destination
9481 ;; Argument 1 is the source
9482 ;; Argument 2 is the length
9483 ;; Argument 3 is the alignment
9485 (define_expand "movmemsi"
9486 [(parallel [(set (match_operand:BLK 0 "" "")
9487 (match_operand:BLK 1 "" ""))
9488 (use (match_operand:SI 2 "" ""))
9489 (use (match_operand:SI 3 "" ""))])]
9493 if (expand_block_move (operands))
9499 ;; Move up to 32 bytes at a time. The fixed registers are needed because the
9500 ;; register allocator doesn't have a clue about allocating 8 word registers.
9501 ;; rD/rS = r5 is preferred, efficient form.
9502 (define_expand "movmemsi_8reg"
9503 [(parallel [(set (match_operand 0 "" "")
9504 (match_operand 1 "" ""))
9505 (use (match_operand 2 "" ""))
9506 (use (match_operand 3 "" ""))
9507 (clobber (reg:SI 5))
9508 (clobber (reg:SI 6))
9509 (clobber (reg:SI 7))
9510 (clobber (reg:SI 8))
9511 (clobber (reg:SI 9))
9512 (clobber (reg:SI 10))
9513 (clobber (reg:SI 11))
9514 (clobber (reg:SI 12))
9515 (clobber (match_scratch:SI 4 ""))])]
9520 [(set (mem:BLK (match_operand:P 0 "gpc_reg_operand" "b"))
9521 (mem:BLK (match_operand:P 1 "gpc_reg_operand" "b")))
9522 (use (match_operand:SI 2 "immediate_operand" "i"))
9523 (use (match_operand:SI 3 "immediate_operand" "i"))
9524 (clobber (match_operand:SI 4 "gpc_reg_operand" "=&r"))
9525 (clobber (reg:SI 6))
9526 (clobber (reg:SI 7))
9527 (clobber (reg:SI 8))
9528 (clobber (reg:SI 9))
9529 (clobber (reg:SI 10))
9530 (clobber (reg:SI 11))
9531 (clobber (reg:SI 12))
9532 (clobber (match_scratch:SI 5 "=X"))]
9534 && ((INTVAL (operands[2]) > 24 && INTVAL (operands[2]) < 32)
9535 || INTVAL (operands[2]) == 0)
9536 && (REGNO (operands[0]) < 5 || REGNO (operands[0]) > 12)
9537 && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 12)
9538 && REGNO (operands[4]) == 5"
9539 "lswi %4,%1,%2\;stswi %4,%0,%2"
9540 [(set_attr "type" "store")
9541 (set_attr "update" "yes")
9542 (set_attr "indexed" "yes")
9543 (set_attr "cell_micro" "always")
9544 (set_attr "length" "8")])
9546 ;; Move up to 24 bytes at a time. The fixed registers are needed because the
9547 ;; register allocator doesn't have a clue about allocating 6 word registers.
9548 ;; rD/rS = r5 is preferred, efficient form.
9549 (define_expand "movmemsi_6reg"
9550 [(parallel [(set (match_operand 0 "" "")
9551 (match_operand 1 "" ""))
9552 (use (match_operand 2 "" ""))
9553 (use (match_operand 3 "" ""))
9554 (clobber (reg:SI 5))
9555 (clobber (reg:SI 6))
9556 (clobber (reg:SI 7))
9557 (clobber (reg:SI 8))
9558 (clobber (reg:SI 9))
9559 (clobber (reg:SI 10))
9560 (clobber (match_scratch:SI 4 ""))])]
9565 [(set (mem:BLK (match_operand:P 0 "gpc_reg_operand" "b"))
9566 (mem:BLK (match_operand:P 1 "gpc_reg_operand" "b")))
9567 (use (match_operand:SI 2 "immediate_operand" "i"))
9568 (use (match_operand:SI 3 "immediate_operand" "i"))
9569 (clobber (match_operand:SI 4 "gpc_reg_operand" "=&r"))
9570 (clobber (reg:SI 6))
9571 (clobber (reg:SI 7))
9572 (clobber (reg:SI 8))
9573 (clobber (reg:SI 9))
9574 (clobber (reg:SI 10))
9575 (clobber (match_scratch:SI 5 "=X"))]
9577 && INTVAL (operands[2]) > 16 && INTVAL (operands[2]) <= 32
9578 && (REGNO (operands[0]) < 5 || REGNO (operands[0]) > 10)
9579 && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 10)
9580 && REGNO (operands[4]) == 5"
9581 "lswi %4,%1,%2\;stswi %4,%0,%2"
9582 [(set_attr "type" "store")
9583 (set_attr "update" "yes")
9584 (set_attr "indexed" "yes")
9585 (set_attr "cell_micro" "always")
9586 (set_attr "length" "8")])
9588 ;; Move up to 16 bytes at a time, using 4 fixed registers to avoid spill
9589 ;; problems with TImode.
9590 ;; rD/rS = r5 is preferred, efficient form.
9591 (define_expand "movmemsi_4reg"
9592 [(parallel [(set (match_operand 0 "" "")
9593 (match_operand 1 "" ""))
9594 (use (match_operand 2 "" ""))
9595 (use (match_operand 3 "" ""))
9596 (clobber (reg:SI 5))
9597 (clobber (reg:SI 6))
9598 (clobber (reg:SI 7))
9599 (clobber (reg:SI 8))
9600 (clobber (match_scratch:SI 4 ""))])]
9605 [(set (mem:BLK (match_operand:P 0 "gpc_reg_operand" "b"))
9606 (mem:BLK (match_operand:P 1 "gpc_reg_operand" "b")))
9607 (use (match_operand:SI 2 "immediate_operand" "i"))
9608 (use (match_operand:SI 3 "immediate_operand" "i"))
9609 (clobber (match_operand:SI 4 "gpc_reg_operand" "=&r"))
9610 (clobber (reg:SI 6))
9611 (clobber (reg:SI 7))
9612 (clobber (reg:SI 8))
9613 (clobber (match_scratch:SI 5 "=X"))]
9615 && INTVAL (operands[2]) > 8 && INTVAL (operands[2]) <= 16
9616 && (REGNO (operands[0]) < 5 || REGNO (operands[0]) > 8)
9617 && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 8)
9618 && REGNO (operands[4]) == 5"
9619 "lswi %4,%1,%2\;stswi %4,%0,%2"
9620 [(set_attr "type" "store")
9621 (set_attr "update" "yes")
9622 (set_attr "indexed" "yes")
9623 (set_attr "cell_micro" "always")
9624 (set_attr "length" "8")])
9626 ;; Move up to 8 bytes at a time.
9627 (define_expand "movmemsi_2reg"
9628 [(parallel [(set (match_operand 0 "" "")
9629 (match_operand 1 "" ""))
9630 (use (match_operand 2 "" ""))
9631 (use (match_operand 3 "" ""))
9632 (clobber (match_scratch:DI 4 ""))
9633 (clobber (match_scratch:SI 5 ""))])]
9634 "TARGET_STRING && ! TARGET_POWERPC64"
9638 [(set (mem:BLK (match_operand:SI 0 "gpc_reg_operand" "b"))
9639 (mem:BLK (match_operand:SI 1 "gpc_reg_operand" "b")))
9640 (use (match_operand:SI 2 "immediate_operand" "i"))
9641 (use (match_operand:SI 3 "immediate_operand" "i"))
9642 (clobber (match_scratch:DI 4 "=&r"))
9643 (clobber (match_scratch:SI 5 "=X"))]
9644 "TARGET_STRING && ! TARGET_POWERPC64
9645 && INTVAL (operands[2]) > 4 && INTVAL (operands[2]) <= 8"
9646 "lswi %4,%1,%2\;stswi %4,%0,%2"
9647 [(set_attr "type" "store")
9648 (set_attr "update" "yes")
9649 (set_attr "indexed" "yes")
9650 (set_attr "cell_micro" "always")
9651 (set_attr "length" "8")])
9653 ;; Move up to 4 bytes at a time.
9654 (define_expand "movmemsi_1reg"
9655 [(parallel [(set (match_operand 0 "" "")
9656 (match_operand 1 "" ""))
9657 (use (match_operand 2 "" ""))
9658 (use (match_operand 3 "" ""))
9659 (clobber (match_scratch:SI 4 ""))
9660 (clobber (match_scratch:SI 5 ""))])]
9665 [(set (mem:BLK (match_operand:P 0 "gpc_reg_operand" "b"))
9666 (mem:BLK (match_operand:P 1 "gpc_reg_operand" "b")))
9667 (use (match_operand:SI 2 "immediate_operand" "i"))
9668 (use (match_operand:SI 3 "immediate_operand" "i"))
9669 (clobber (match_scratch:SI 4 "=&r"))
9670 (clobber (match_scratch:SI 5 "=X"))]
9671 "TARGET_STRING && INTVAL (operands[2]) > 0 && INTVAL (operands[2]) <= 4"
9672 "lswi %4,%1,%2\;stswi %4,%0,%2"
9673 [(set_attr "type" "store")
9674 (set_attr "update" "yes")
9675 (set_attr "indexed" "yes")
9676 (set_attr "cell_micro" "always")
9677 (set_attr "length" "8")])
9679 ;; Define insns that do load or store with update. Some of these we can
9680 ;; get by using pre-decrement or pre-increment, but the hardware can also
9681 ;; do cases where the increment is not the size of the object.
9683 ;; In all these cases, we use operands 0 and 1 for the register being
9684 ;; incremented because those are the operands that local-alloc will
9685 ;; tie and these are the pair most likely to be tieable (and the ones
9686 ;; that will benefit the most).
9688 (define_insn "*movdi_update1"
9689 [(set (match_operand:DI 3 "gpc_reg_operand" "=r,r")
9690 (mem:DI (plus:DI (match_operand:DI 1 "gpc_reg_operand" "0,0")
9691 (match_operand:DI 2 "reg_or_aligned_short_operand" "r,I"))))
9692 (set (match_operand:DI 0 "gpc_reg_operand" "=b,b")
9693 (plus:DI (match_dup 1) (match_dup 2)))]
9694 "TARGET_POWERPC64 && TARGET_UPDATE
9695 && (!avoiding_indexed_address_p (DImode)
9696 || !gpc_reg_operand (operands[2], DImode))"
9700 [(set_attr "type" "load")
9701 (set_attr "update" "yes")
9702 (set_attr "indexed" "yes,no")])
9704 (define_insn "movdi_<mode>_update"
9705 [(set (mem:DI (plus:P (match_operand:P 1 "gpc_reg_operand" "0,0")
9706 (match_operand:P 2 "reg_or_aligned_short_operand" "r,I")))
9707 (match_operand:DI 3 "gpc_reg_operand" "r,r"))
9708 (set (match_operand:P 0 "gpc_reg_operand" "=b,b")
9709 (plus:P (match_dup 1) (match_dup 2)))]
9710 "TARGET_POWERPC64 && TARGET_UPDATE
9711 && (!avoiding_indexed_address_p (Pmode)
9712 || !gpc_reg_operand (operands[2], Pmode)
9713 || (REG_P (operands[0])
9714 && REGNO (operands[0]) == STACK_POINTER_REGNUM))"
9718 [(set_attr "type" "store")
9719 (set_attr "update" "yes")
9720 (set_attr "indexed" "yes,no")])
9722 ;; This pattern is only conditional on TARGET_POWERPC64, as it is
9723 ;; needed for stack allocation, even if the user passes -mno-update.
9724 (define_insn "movdi_<mode>_update_stack"
9725 [(set (mem:DI (plus:P (match_operand:P 1 "gpc_reg_operand" "0,0")
9726 (match_operand:P 2 "reg_or_aligned_short_operand" "r,I")))
9727 (match_operand:DI 3 "gpc_reg_operand" "r,r"))
9728 (set (match_operand:P 0 "gpc_reg_operand" "=b,b")
9729 (plus:P (match_dup 1) (match_dup 2)))]
9734 [(set_attr "type" "store")
9735 (set_attr "update" "yes")
9736 (set_attr "indexed" "yes,no")])
9738 (define_insn "*movsi_update1"
9739 [(set (match_operand:SI 3 "gpc_reg_operand" "=r,r")
9740 (mem:SI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9741 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
9742 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9743 (plus:SI (match_dup 1) (match_dup 2)))]
9745 && (!avoiding_indexed_address_p (SImode)
9746 || !gpc_reg_operand (operands[2], SImode))"
9750 [(set_attr "type" "load")
9751 (set_attr "update" "yes")
9752 (set_attr "indexed" "yes,no")])
9754 (define_insn "*movsi_update2"
9755 [(set (match_operand:DI 3 "gpc_reg_operand" "=r")
9757 (mem:SI (plus:DI (match_operand:DI 1 "gpc_reg_operand" "0")
9758 (match_operand:DI 2 "gpc_reg_operand" "r")))))
9759 (set (match_operand:DI 0 "gpc_reg_operand" "=b")
9760 (plus:DI (match_dup 1) (match_dup 2)))]
9761 "TARGET_POWERPC64 && rs6000_gen_cell_microcode
9762 && !avoiding_indexed_address_p (DImode)"
9764 [(set_attr "type" "load")
9765 (set_attr "sign_extend" "yes")
9766 (set_attr "update" "yes")
9767 (set_attr "indexed" "yes")])
9769 (define_insn "movsi_update"
9770 [(set (mem:SI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9771 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
9772 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
9773 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9774 (plus:SI (match_dup 1) (match_dup 2)))]
9776 && (!avoiding_indexed_address_p (SImode)
9777 || !gpc_reg_operand (operands[2], SImode)
9778 || (REG_P (operands[0])
9779 && REGNO (operands[0]) == STACK_POINTER_REGNUM))"
9783 [(set_attr "type" "store")
9784 (set_attr "update" "yes")
9785 (set_attr "indexed" "yes,no")])
9787 ;; This is an unconditional pattern; needed for stack allocation, even
9788 ;; if the user passes -mno-update.
9789 (define_insn "movsi_update_stack"
9790 [(set (mem:SI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9791 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
9792 (match_operand:SI 3 "gpc_reg_operand" "r,r"))
9793 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9794 (plus:SI (match_dup 1) (match_dup 2)))]
9799 [(set_attr "type" "store")
9800 (set_attr "update" "yes")
9801 (set_attr "indexed" "yes,no")])
9803 (define_insn "*movhi_update1"
9804 [(set (match_operand:HI 3 "gpc_reg_operand" "=r,r")
9805 (mem:HI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9806 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
9807 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9808 (plus:SI (match_dup 1) (match_dup 2)))]
9810 && (!avoiding_indexed_address_p (SImode)
9811 || !gpc_reg_operand (operands[2], SImode))"
9815 [(set_attr "type" "load")
9816 (set_attr "update" "yes")
9817 (set_attr "indexed" "yes,no")])
9819 (define_insn "*movhi_update2"
9820 [(set (match_operand:SI 3 "gpc_reg_operand" "=r,r")
9822 (mem:HI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9823 (match_operand:SI 2 "reg_or_short_operand" "r,I")))))
9824 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9825 (plus:SI (match_dup 1) (match_dup 2)))]
9827 && (!avoiding_indexed_address_p (SImode)
9828 || !gpc_reg_operand (operands[2], SImode))"
9832 [(set_attr "type" "load")
9833 (set_attr "update" "yes")
9834 (set_attr "indexed" "yes,no")])
9836 (define_insn "*movhi_update3"
9837 [(set (match_operand:SI 3 "gpc_reg_operand" "=r,r")
9839 (mem:HI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9840 (match_operand:SI 2 "reg_or_short_operand" "r,I")))))
9841 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9842 (plus:SI (match_dup 1) (match_dup 2)))]
9843 "TARGET_UPDATE && rs6000_gen_cell_microcode
9844 && (!avoiding_indexed_address_p (SImode)
9845 || !gpc_reg_operand (operands[2], SImode))"
9849 [(set_attr "type" "load")
9850 (set_attr "sign_extend" "yes")
9851 (set_attr "update" "yes")
9852 (set_attr "indexed" "yes,no")])
9854 (define_insn "*movhi_update4"
9855 [(set (mem:HI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9856 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
9857 (match_operand:HI 3 "gpc_reg_operand" "r,r"))
9858 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9859 (plus:SI (match_dup 1) (match_dup 2)))]
9861 && (!avoiding_indexed_address_p (SImode)
9862 || !gpc_reg_operand (operands[2], SImode))"
9866 [(set_attr "type" "store")
9867 (set_attr "update" "yes")
9868 (set_attr "indexed" "yes,no")])
9870 (define_insn "*movqi_update1"
9871 [(set (match_operand:QI 3 "gpc_reg_operand" "=r,r")
9872 (mem:QI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9873 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
9874 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9875 (plus:SI (match_dup 1) (match_dup 2)))]
9877 && (!avoiding_indexed_address_p (SImode)
9878 || !gpc_reg_operand (operands[2], SImode))"
9882 [(set_attr "type" "load")
9883 (set_attr "update" "yes")
9884 (set_attr "indexed" "yes,no")])
9886 (define_insn "*movqi_update2"
9887 [(set (match_operand:SI 3 "gpc_reg_operand" "=r,r")
9889 (mem:QI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9890 (match_operand:SI 2 "reg_or_short_operand" "r,I")))))
9891 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9892 (plus:SI (match_dup 1) (match_dup 2)))]
9894 && (!avoiding_indexed_address_p (SImode)
9895 || !gpc_reg_operand (operands[2], SImode))"
9899 [(set_attr "type" "load")
9900 (set_attr "update" "yes")
9901 (set_attr "indexed" "yes,no")])
9903 (define_insn "*movqi_update3"
9904 [(set (mem:QI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9905 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
9906 (match_operand:QI 3 "gpc_reg_operand" "r,r"))
9907 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9908 (plus:SI (match_dup 1) (match_dup 2)))]
9910 && (!avoiding_indexed_address_p (SImode)
9911 || !gpc_reg_operand (operands[2], SImode))"
9915 [(set_attr "type" "store")
9916 (set_attr "update" "yes")
9917 (set_attr "indexed" "yes,no")])
9919 (define_insn "*movsf_update1"
9920 [(set (match_operand:SF 3 "gpc_reg_operand" "=f,f")
9921 (mem:SF (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9922 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
9923 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9924 (plus:SI (match_dup 1) (match_dup 2)))]
9925 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT && TARGET_UPDATE
9926 && (!avoiding_indexed_address_p (SImode)
9927 || !gpc_reg_operand (operands[2], SImode))"
9931 [(set_attr "type" "fpload")
9932 (set_attr "update" "yes")
9933 (set_attr "indexed" "yes,no")])
9935 (define_insn "*movsf_update2"
9936 [(set (mem:SF (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9937 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
9938 (match_operand:SF 3 "gpc_reg_operand" "f,f"))
9939 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9940 (plus:SI (match_dup 1) (match_dup 2)))]
9941 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_SINGLE_FLOAT && TARGET_UPDATE
9942 && (!avoiding_indexed_address_p (SImode)
9943 || !gpc_reg_operand (operands[2], SImode))"
9947 [(set_attr "type" "fpstore")
9948 (set_attr "update" "yes")
9949 (set_attr "indexed" "yes,no")])
9951 (define_insn "*movsf_update3"
9952 [(set (match_operand:SF 3 "gpc_reg_operand" "=r,r")
9953 (mem:SF (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9954 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
9955 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9956 (plus:SI (match_dup 1) (match_dup 2)))]
9957 "(TARGET_SOFT_FLOAT || !TARGET_FPRS) && TARGET_UPDATE
9958 && (!avoiding_indexed_address_p (SImode)
9959 || !gpc_reg_operand (operands[2], SImode))"
9963 [(set_attr "type" "load")
9964 (set_attr "update" "yes")
9965 (set_attr "indexed" "yes,no")])
9967 (define_insn "*movsf_update4"
9968 [(set (mem:SF (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9969 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
9970 (match_operand:SF 3 "gpc_reg_operand" "r,r"))
9971 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9972 (plus:SI (match_dup 1) (match_dup 2)))]
9973 "(TARGET_SOFT_FLOAT || !TARGET_FPRS) && TARGET_UPDATE
9974 && (!avoiding_indexed_address_p (SImode)
9975 || !gpc_reg_operand (operands[2], SImode))"
9979 [(set_attr "type" "store")
9980 (set_attr "update" "yes")
9981 (set_attr "indexed" "yes,no")])
9983 (define_insn "*movdf_update1"
9984 [(set (match_operand:DF 3 "gpc_reg_operand" "=d,d")
9985 (mem:DF (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
9986 (match_operand:SI 2 "reg_or_short_operand" "r,I"))))
9987 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
9988 (plus:SI (match_dup 1) (match_dup 2)))]
9989 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_UPDATE
9990 && (!avoiding_indexed_address_p (SImode)
9991 || !gpc_reg_operand (operands[2], SImode))"
9995 [(set_attr "type" "fpload")
9996 (set_attr "update" "yes")
9997 (set_attr "indexed" "yes,no")])
9999 (define_insn "*movdf_update2"
10000 [(set (mem:DF (plus:SI (match_operand:SI 1 "gpc_reg_operand" "0,0")
10001 (match_operand:SI 2 "reg_or_short_operand" "r,I")))
10002 (match_operand:DF 3 "gpc_reg_operand" "d,d"))
10003 (set (match_operand:SI 0 "gpc_reg_operand" "=b,b")
10004 (plus:SI (match_dup 1) (match_dup 2)))]
10005 "TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_UPDATE
10006 && (!avoiding_indexed_address_p (SImode)
10007 || !gpc_reg_operand (operands[2], SImode))"
10011 [(set_attr "type" "fpstore")
10012 (set_attr "update" "yes")
10013 (set_attr "indexed" "yes,no")])
10016 ;; After inserting conditional returns we can sometimes have
10017 ;; unnecessary register moves. Unfortunately we cannot have a
10018 ;; modeless peephole here, because some single SImode sets have early
10019 ;; clobber outputs. Although those sets expand to multi-ppc-insn
10020 ;; sequences, using get_attr_length here will smash the operands
10021 ;; array. Neither is there an early_cobbler_p predicate.
10022 ;; Disallow subregs for E500 so we don't munge frob_di_df_2.
10023 ;; Also this optimization interferes with scalars going into
10024 ;; altivec registers (the code does reloading through the FPRs).
10026 [(set (match_operand:DF 0 "gpc_reg_operand" "")
10027 (match_operand:DF 1 "any_operand" ""))
10028 (set (match_operand:DF 2 "gpc_reg_operand" "")
10030 "!(TARGET_E500_DOUBLE && GET_CODE (operands[2]) == SUBREG)
10031 && !TARGET_UPPER_REGS_DF
10032 && peep2_reg_dead_p (2, operands[0])"
10033 [(set (match_dup 2) (match_dup 1))])
10036 [(set (match_operand:SF 0 "gpc_reg_operand" "")
10037 (match_operand:SF 1 "any_operand" ""))
10038 (set (match_operand:SF 2 "gpc_reg_operand" "")
10040 "!TARGET_UPPER_REGS_SF
10041 && peep2_reg_dead_p (2, operands[0])"
10042 [(set (match_dup 2) (match_dup 1))])
10047 ;; Mode attributes for different ABIs.
10048 (define_mode_iterator TLSmode [(SI "! TARGET_64BIT") (DI "TARGET_64BIT")])
10049 (define_mode_attr tls_abi_suffix [(SI "32") (DI "64")])
10050 (define_mode_attr tls_sysv_suffix [(SI "si") (DI "di")])
10051 (define_mode_attr tls_insn_suffix [(SI "wz") (DI "d")])
10053 (define_insn_and_split "tls_gd_aix<TLSmode:tls_abi_suffix>"
10054 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10055 (call (mem:TLSmode (match_operand:TLSmode 3 "symbol_ref_operand" "s"))
10056 (match_operand 4 "" "g")))
10057 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10058 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10060 (clobber (reg:SI LR_REGNO))]
10061 "HAVE_AS_TLS && (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)"
10063 if (TARGET_CMODEL != CMODEL_SMALL)
10064 return "addis %0,%1,%2@got@tlsgd@ha\;addi %0,%0,%2@got@tlsgd@l\;"
10067 return "addi %0,%1,%2@got@tlsgd\;bl %z3\;nop";
10069 "&& TARGET_TLS_MARKERS"
10070 [(set (match_dup 0)
10071 (unspec:TLSmode [(match_dup 1)
10074 (parallel [(set (match_dup 0)
10075 (call (mem:TLSmode (match_dup 3))
10077 (unspec:TLSmode [(match_dup 2)] UNSPEC_TLSGD)
10078 (clobber (reg:SI LR_REGNO))])]
10080 [(set_attr "type" "two")
10081 (set (attr "length")
10082 (if_then_else (ne (symbol_ref "TARGET_CMODEL") (symbol_ref "CMODEL_SMALL"))
10086 (define_insn_and_split "tls_gd_sysv<TLSmode:tls_sysv_suffix>"
10087 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10088 (call (mem:TLSmode (match_operand:TLSmode 3 "symbol_ref_operand" "s"))
10089 (match_operand 4 "" "g")))
10090 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10091 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10093 (clobber (reg:SI LR_REGNO))]
10094 "HAVE_AS_TLS && DEFAULT_ABI == ABI_V4"
10098 if (TARGET_SECURE_PLT && flag_pic == 2)
10099 return "addi %0,%1,%2@got@tlsgd\;bl %z3+32768@plt";
10101 return "addi %0,%1,%2@got@tlsgd\;bl %z3@plt";
10104 return "addi %0,%1,%2@got@tlsgd\;bl %z3";
10106 "&& TARGET_TLS_MARKERS"
10107 [(set (match_dup 0)
10108 (unspec:TLSmode [(match_dup 1)
10111 (parallel [(set (match_dup 0)
10112 (call (mem:TLSmode (match_dup 3))
10114 (unspec:TLSmode [(match_dup 2)] UNSPEC_TLSGD)
10115 (clobber (reg:SI LR_REGNO))])]
10117 [(set_attr "type" "two")
10118 (set_attr "length" "8")])
10120 (define_insn_and_split "*tls_gd<TLSmode:tls_abi_suffix>"
10121 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10122 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10123 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10125 "HAVE_AS_TLS && TARGET_TLS_MARKERS"
10126 "addi %0,%1,%2@got@tlsgd"
10127 "&& TARGET_CMODEL != CMODEL_SMALL"
10128 [(set (match_dup 3)
10130 (unspec:TLSmode [(match_dup 1) (match_dup 2)] UNSPEC_TLSGD)))
10132 (lo_sum:TLSmode (match_dup 3)
10133 (unspec:TLSmode [(match_dup 1) (match_dup 2)] UNSPEC_TLSGD)))]
10136 operands[3] = gen_reg_rtx (TARGET_64BIT ? DImode : SImode);
10138 [(set (attr "length")
10139 (if_then_else (ne (symbol_ref "TARGET_CMODEL") (symbol_ref "CMODEL_SMALL"))
10143 (define_insn "*tls_gd_high<TLSmode:tls_abi_suffix>"
10144 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10146 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10147 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10149 "HAVE_AS_TLS && TARGET_TLS_MARKERS && TARGET_CMODEL != CMODEL_SMALL"
10150 "addis %0,%1,%2@got@tlsgd@ha"
10151 [(set_attr "length" "4")])
10153 (define_insn "*tls_gd_low<TLSmode:tls_abi_suffix>"
10154 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10155 (lo_sum:TLSmode (match_operand:TLSmode 1 "gpc_reg_operand" "b")
10156 (unspec:TLSmode [(match_operand:TLSmode 3 "gpc_reg_operand" "b")
10157 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10159 "HAVE_AS_TLS && TARGET_TLS_MARKERS && TARGET_CMODEL != CMODEL_SMALL"
10160 "addi %0,%1,%2@got@tlsgd@l"
10161 [(set_attr "length" "4")])
10163 (define_insn "*tls_gd_call_aix<TLSmode:tls_abi_suffix>"
10164 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10165 (call (mem:TLSmode (match_operand:TLSmode 1 "symbol_ref_operand" "s"))
10166 (match_operand 2 "" "g")))
10167 (unspec:TLSmode [(match_operand:TLSmode 3 "rs6000_tls_symbol_ref" "")]
10169 (clobber (reg:SI LR_REGNO))]
10170 "HAVE_AS_TLS && TARGET_TLS_MARKERS
10171 && (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)"
10172 "bl %z1(%3@tlsgd)\;nop"
10173 [(set_attr "type" "branch")
10174 (set_attr "length" "8")])
10176 (define_insn "*tls_gd_call_sysv<TLSmode:tls_abi_suffix>"
10177 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10178 (call (mem:TLSmode (match_operand:TLSmode 1 "symbol_ref_operand" "s"))
10179 (match_operand 2 "" "g")))
10180 (unspec:TLSmode [(match_operand:TLSmode 3 "rs6000_tls_symbol_ref" "")]
10182 (clobber (reg:SI LR_REGNO))]
10183 "HAVE_AS_TLS && DEFAULT_ABI == ABI_V4 && TARGET_TLS_MARKERS"
10187 if (TARGET_SECURE_PLT && flag_pic == 2)
10188 return "bl %z1+32768(%3@tlsgd)@plt";
10189 return "bl %z1(%3@tlsgd)@plt";
10191 return "bl %z1(%3@tlsgd)";
10193 [(set_attr "type" "branch")
10194 (set_attr "length" "4")])
10196 (define_insn_and_split "tls_ld_aix<TLSmode:tls_abi_suffix>"
10197 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10198 (call (mem:TLSmode (match_operand:TLSmode 2 "symbol_ref_operand" "s"))
10199 (match_operand 3 "" "g")))
10200 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")]
10202 (clobber (reg:SI LR_REGNO))]
10203 "HAVE_AS_TLS && (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)"
10205 if (TARGET_CMODEL != CMODEL_SMALL)
10206 return "addis %0,%1,%&@got@tlsld@ha\;addi %0,%0,%&@got@tlsld@l\;"
10209 return "addi %0,%1,%&@got@tlsld\;bl %z2\;nop";
10211 "&& TARGET_TLS_MARKERS"
10212 [(set (match_dup 0)
10213 (unspec:TLSmode [(match_dup 1)]
10215 (parallel [(set (match_dup 0)
10216 (call (mem:TLSmode (match_dup 2))
10218 (unspec:TLSmode [(const_int 0)] UNSPEC_TLSLD)
10219 (clobber (reg:SI LR_REGNO))])]
10221 [(set_attr "type" "two")
10222 (set (attr "length")
10223 (if_then_else (ne (symbol_ref "TARGET_CMODEL") (symbol_ref "CMODEL_SMALL"))
10227 (define_insn_and_split "tls_ld_sysv<TLSmode:tls_sysv_suffix>"
10228 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10229 (call (mem:TLSmode (match_operand:TLSmode 2 "symbol_ref_operand" "s"))
10230 (match_operand 3 "" "g")))
10231 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")]
10233 (clobber (reg:SI LR_REGNO))]
10234 "HAVE_AS_TLS && DEFAULT_ABI == ABI_V4"
10238 if (TARGET_SECURE_PLT && flag_pic == 2)
10239 return "addi %0,%1,%&@got@tlsld\;bl %z2+32768@plt";
10241 return "addi %0,%1,%&@got@tlsld\;bl %z2@plt";
10244 return "addi %0,%1,%&@got@tlsld\;bl %z2";
10246 "&& TARGET_TLS_MARKERS"
10247 [(set (match_dup 0)
10248 (unspec:TLSmode [(match_dup 1)]
10250 (parallel [(set (match_dup 0)
10251 (call (mem:TLSmode (match_dup 2))
10253 (unspec:TLSmode [(const_int 0)] UNSPEC_TLSLD)
10254 (clobber (reg:SI LR_REGNO))])]
10256 [(set_attr "length" "8")])
10258 (define_insn_and_split "*tls_ld<TLSmode:tls_abi_suffix>"
10259 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10260 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")]
10262 "HAVE_AS_TLS && TARGET_TLS_MARKERS"
10263 "addi %0,%1,%&@got@tlsld"
10264 "&& TARGET_CMODEL != CMODEL_SMALL"
10265 [(set (match_dup 2)
10267 (unspec:TLSmode [(const_int 0) (match_dup 1)] UNSPEC_TLSLD)))
10269 (lo_sum:TLSmode (match_dup 2)
10270 (unspec:TLSmode [(const_int 0) (match_dup 1)] UNSPEC_TLSLD)))]
10273 operands[2] = gen_reg_rtx (TARGET_64BIT ? DImode : SImode);
10275 [(set (attr "length")
10276 (if_then_else (ne (symbol_ref "TARGET_CMODEL") (symbol_ref "CMODEL_SMALL"))
10280 (define_insn "*tls_ld_high<TLSmode:tls_abi_suffix>"
10281 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10283 (unspec:TLSmode [(const_int 0)
10284 (match_operand:TLSmode 1 "gpc_reg_operand" "b")]
10286 "HAVE_AS_TLS && TARGET_TLS_MARKERS && TARGET_CMODEL != CMODEL_SMALL"
10287 "addis %0,%1,%&@got@tlsld@ha"
10288 [(set_attr "length" "4")])
10290 (define_insn "*tls_ld_low<TLSmode:tls_abi_suffix>"
10291 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10292 (lo_sum:TLSmode (match_operand:TLSmode 1 "gpc_reg_operand" "b")
10293 (unspec:TLSmode [(const_int 0)
10294 (match_operand:TLSmode 2 "gpc_reg_operand" "b")]
10296 "HAVE_AS_TLS && TARGET_TLS_MARKERS && TARGET_CMODEL != CMODEL_SMALL"
10297 "addi %0,%1,%&@got@tlsld@l"
10298 [(set_attr "length" "4")])
10300 (define_insn "*tls_ld_call_aix<TLSmode:tls_abi_suffix>"
10301 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10302 (call (mem:TLSmode (match_operand:TLSmode 1 "symbol_ref_operand" "s"))
10303 (match_operand 2 "" "g")))
10304 (unspec:TLSmode [(const_int 0)] UNSPEC_TLSLD)
10305 (clobber (reg:SI LR_REGNO))]
10306 "HAVE_AS_TLS && TARGET_TLS_MARKERS
10307 && (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)"
10308 "bl %z1(%&@tlsld)\;nop"
10309 [(set_attr "type" "branch")
10310 (set_attr "length" "8")])
10312 (define_insn "*tls_ld_call_sysv<TLSmode:tls_abi_suffix>"
10313 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10314 (call (mem:TLSmode (match_operand:TLSmode 1 "symbol_ref_operand" "s"))
10315 (match_operand 2 "" "g")))
10316 (unspec:TLSmode [(const_int 0)] UNSPEC_TLSLD)
10317 (clobber (reg:SI LR_REGNO))]
10318 "HAVE_AS_TLS && DEFAULT_ABI == ABI_V4 && TARGET_TLS_MARKERS"
10322 if (TARGET_SECURE_PLT && flag_pic == 2)
10323 return "bl %z1+32768(%&@tlsld)@plt";
10324 return "bl %z1(%&@tlsld)@plt";
10326 return "bl %z1(%&@tlsld)";
10328 [(set_attr "type" "branch")
10329 (set_attr "length" "4")])
10331 (define_insn "tls_dtprel_<TLSmode:tls_abi_suffix>"
10332 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=r")
10333 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10334 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10335 UNSPEC_TLSDTPREL))]
10337 "addi %0,%1,%2@dtprel")
10339 (define_insn "tls_dtprel_ha_<TLSmode:tls_abi_suffix>"
10340 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=r")
10341 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10342 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10343 UNSPEC_TLSDTPRELHA))]
10345 "addis %0,%1,%2@dtprel@ha")
10347 (define_insn "tls_dtprel_lo_<TLSmode:tls_abi_suffix>"
10348 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=r")
10349 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10350 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10351 UNSPEC_TLSDTPRELLO))]
10353 "addi %0,%1,%2@dtprel@l")
10355 (define_insn_and_split "tls_got_dtprel_<TLSmode:tls_abi_suffix>"
10356 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=r")
10357 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10358 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10359 UNSPEC_TLSGOTDTPREL))]
10361 "l<TLSmode:tls_insn_suffix> %0,%2@got@dtprel(%1)"
10362 "&& TARGET_CMODEL != CMODEL_SMALL"
10363 [(set (match_dup 3)
10365 (unspec:TLSmode [(match_dup 1) (match_dup 2)] UNSPEC_TLSGOTDTPREL)))
10367 (lo_sum:TLSmode (match_dup 3)
10368 (unspec:TLSmode [(match_dup 1) (match_dup 2)] UNSPEC_TLSGOTDTPREL)))]
10371 operands[3] = gen_reg_rtx (TARGET_64BIT ? DImode : SImode);
10373 [(set (attr "length")
10374 (if_then_else (ne (symbol_ref "TARGET_CMODEL") (symbol_ref "CMODEL_SMALL"))
10378 (define_insn "*tls_got_dtprel_high<TLSmode:tls_abi_suffix>"
10379 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10381 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10382 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10383 UNSPEC_TLSGOTDTPREL)))]
10384 "HAVE_AS_TLS && TARGET_CMODEL != CMODEL_SMALL"
10385 "addis %0,%1,%2@got@dtprel@ha"
10386 [(set_attr "length" "4")])
10388 (define_insn "*tls_got_dtprel_low<TLSmode:tls_abi_suffix>"
10389 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=r")
10390 (lo_sum:TLSmode (match_operand:TLSmode 1 "gpc_reg_operand" "b")
10391 (unspec:TLSmode [(match_operand:TLSmode 3 "gpc_reg_operand" "b")
10392 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10393 UNSPEC_TLSGOTDTPREL)))]
10394 "HAVE_AS_TLS && TARGET_CMODEL != CMODEL_SMALL"
10395 "l<TLSmode:tls_insn_suffix> %0,%2@got@dtprel@l(%1)"
10396 [(set_attr "length" "4")])
10398 (define_insn "tls_tprel_<TLSmode:tls_abi_suffix>"
10399 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=r")
10400 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10401 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10404 "addi %0,%1,%2@tprel")
10406 (define_insn "tls_tprel_ha_<TLSmode:tls_abi_suffix>"
10407 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=r")
10408 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10409 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10410 UNSPEC_TLSTPRELHA))]
10412 "addis %0,%1,%2@tprel@ha")
10414 (define_insn "tls_tprel_lo_<TLSmode:tls_abi_suffix>"
10415 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=r")
10416 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10417 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10418 UNSPEC_TLSTPRELLO))]
10420 "addi %0,%1,%2@tprel@l")
10422 ;; "b" output constraint here and on tls_tls input to support linker tls
10423 ;; optimization. The linker may edit the instructions emitted by a
10424 ;; tls_got_tprel/tls_tls pair to addis,addi.
10425 (define_insn_and_split "tls_got_tprel_<TLSmode:tls_abi_suffix>"
10426 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10427 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10428 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10429 UNSPEC_TLSGOTTPREL))]
10431 "l<TLSmode:tls_insn_suffix> %0,%2@got@tprel(%1)"
10432 "&& TARGET_CMODEL != CMODEL_SMALL"
10433 [(set (match_dup 3)
10435 (unspec:TLSmode [(match_dup 1) (match_dup 2)] UNSPEC_TLSGOTTPREL)))
10437 (lo_sum:TLSmode (match_dup 3)
10438 (unspec:TLSmode [(match_dup 1) (match_dup 2)] UNSPEC_TLSGOTTPREL)))]
10441 operands[3] = gen_reg_rtx (TARGET_64BIT ? DImode : SImode);
10443 [(set (attr "length")
10444 (if_then_else (ne (symbol_ref "TARGET_CMODEL") (symbol_ref "CMODEL_SMALL"))
10448 (define_insn "*tls_got_tprel_high<TLSmode:tls_abi_suffix>"
10449 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=b")
10451 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10452 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10453 UNSPEC_TLSGOTTPREL)))]
10454 "HAVE_AS_TLS && TARGET_CMODEL != CMODEL_SMALL"
10455 "addis %0,%1,%2@got@tprel@ha"
10456 [(set_attr "length" "4")])
10458 (define_insn "*tls_got_tprel_low<TLSmode:tls_abi_suffix>"
10459 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=r")
10460 (lo_sum:TLSmode (match_operand:TLSmode 1 "gpc_reg_operand" "b")
10461 (unspec:TLSmode [(match_operand:TLSmode 3 "gpc_reg_operand" "b")
10462 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10463 UNSPEC_TLSGOTTPREL)))]
10464 "HAVE_AS_TLS && TARGET_CMODEL != CMODEL_SMALL"
10465 "l<TLSmode:tls_insn_suffix> %0,%2@got@tprel@l(%1)"
10466 [(set_attr "length" "4")])
10468 (define_insn "tls_tls_<TLSmode:tls_abi_suffix>"
10469 [(set (match_operand:TLSmode 0 "gpc_reg_operand" "=r")
10470 (unspec:TLSmode [(match_operand:TLSmode 1 "gpc_reg_operand" "b")
10471 (match_operand:TLSmode 2 "rs6000_tls_symbol_ref" "")]
10473 "TARGET_ELF && HAVE_AS_TLS"
10474 "add %0,%1,%2@tls")
10476 (define_expand "tls_get_tpointer"
10477 [(set (match_operand:SI 0 "gpc_reg_operand" "")
10478 (unspec:SI [(const_int 0)] UNSPEC_TLSTLS))]
10479 "TARGET_XCOFF && HAVE_AS_TLS"
10482 emit_insn (gen_tls_get_tpointer_internal ());
10483 emit_move_insn (operands[0], gen_rtx_REG (SImode, 3));
10487 (define_insn "tls_get_tpointer_internal"
10489 (unspec:SI [(const_int 0)] UNSPEC_TLSTLS))
10490 (clobber (reg:SI LR_REGNO))]
10491 "TARGET_XCOFF && HAVE_AS_TLS"
10492 "bla __get_tpointer")
10494 (define_expand "tls_get_addr<mode>"
10495 [(set (match_operand:P 0 "gpc_reg_operand" "")
10496 (unspec:P [(match_operand:P 1 "gpc_reg_operand" "")
10497 (match_operand:P 2 "gpc_reg_operand" "")] UNSPEC_TLSTLS))]
10498 "TARGET_XCOFF && HAVE_AS_TLS"
10501 emit_move_insn (gen_rtx_REG (Pmode, 3), operands[1]);
10502 emit_move_insn (gen_rtx_REG (Pmode, 4), operands[2]);
10503 emit_insn (gen_tls_get_addr_internal<mode> ());
10504 emit_move_insn (operands[0], gen_rtx_REG (Pmode, 3));
10508 (define_insn "tls_get_addr_internal<mode>"
10510 (unspec:P [(reg:P 3) (reg:P 4)] UNSPEC_TLSTLS))
10511 (clobber (reg:P 0))
10512 (clobber (reg:P 4))
10513 (clobber (reg:P 5))
10514 (clobber (reg:P 11))
10515 (clobber (reg:CC CR0_REGNO))
10516 (clobber (reg:P LR_REGNO))]
10517 "TARGET_XCOFF && HAVE_AS_TLS"
10518 "bla __tls_get_addr")
10520 ;; Next come insns related to the calling sequence.
10522 ;; First, an insn to allocate new stack space for dynamic use (e.g., alloca).
10523 ;; We move the back-chain and decrement the stack pointer.
10525 (define_expand "allocate_stack"
10526 [(set (match_operand 0 "gpc_reg_operand" "")
10527 (minus (reg 1) (match_operand 1 "reg_or_short_operand" "")))
10529 (minus (reg 1) (match_dup 1)))]
10532 { rtx chain = gen_reg_rtx (Pmode);
10533 rtx stack_bot = gen_rtx_MEM (Pmode, stack_pointer_rtx);
10535 rtx insn, par, set, mem;
10537 emit_move_insn (chain, stack_bot);
10539 /* Check stack bounds if necessary. */
10540 if (crtl->limit_stack)
10543 available = expand_binop (Pmode, sub_optab,
10544 stack_pointer_rtx, stack_limit_rtx,
10545 NULL_RTX, 1, OPTAB_WIDEN);
10546 emit_insn (gen_cond_trap (LTU, available, operands[1], const0_rtx));
10549 if (GET_CODE (operands[1]) != CONST_INT
10550 || INTVAL (operands[1]) < -32767
10551 || INTVAL (operands[1]) > 32768)
10553 neg_op0 = gen_reg_rtx (Pmode);
10555 emit_insn (gen_negsi2 (neg_op0, operands[1]));
10557 emit_insn (gen_negdi2 (neg_op0, operands[1]));
10560 neg_op0 = GEN_INT (- INTVAL (operands[1]));
10562 insn = emit_insn ((* ((TARGET_32BIT) ? gen_movsi_update_stack
10563 : gen_movdi_di_update_stack))
10564 (stack_pointer_rtx, stack_pointer_rtx, neg_op0,
10566 /* Since we didn't use gen_frame_mem to generate the MEM, grab
10567 it now and set the alias set/attributes. The above gen_*_update
10568 calls will generate a PARALLEL with the MEM set being the first
10570 par = PATTERN (insn);
10571 gcc_assert (GET_CODE (par) == PARALLEL);
10572 set = XVECEXP (par, 0, 0);
10573 gcc_assert (GET_CODE (set) == SET);
10574 mem = SET_DEST (set);
10575 gcc_assert (MEM_P (mem));
10576 MEM_NOTRAP_P (mem) = 1;
10577 set_mem_alias_set (mem, get_frame_alias_set ());
10579 emit_move_insn (operands[0], virtual_stack_dynamic_rtx);
10583 ;; These patterns say how to save and restore the stack pointer. We need not
10584 ;; save the stack pointer at function level since we are careful to
10585 ;; preserve the backchain. At block level, we have to restore the backchain
10586 ;; when we restore the stack pointer.
10588 ;; For nonlocal gotos, we must save both the stack pointer and its
10589 ;; backchain and restore both. Note that in the nonlocal case, the
10590 ;; save area is a memory location.
10592 (define_expand "save_stack_function"
10593 [(match_operand 0 "any_operand" "")
10594 (match_operand 1 "any_operand" "")]
10598 (define_expand "restore_stack_function"
10599 [(match_operand 0 "any_operand" "")
10600 (match_operand 1 "any_operand" "")]
10604 ;; Adjust stack pointer (op0) to a new value (op1).
10605 ;; First copy old stack backchain to new location, and ensure that the
10606 ;; scheduler won't reorder the sp assignment before the backchain write.
10607 (define_expand "restore_stack_block"
10608 [(set (match_dup 2) (match_dup 3))
10609 (set (match_dup 4) (match_dup 2))
10611 (set (match_operand 0 "register_operand" "")
10612 (match_operand 1 "register_operand" ""))]
10618 operands[1] = force_reg (Pmode, operands[1]);
10619 operands[2] = gen_reg_rtx (Pmode);
10620 operands[3] = gen_frame_mem (Pmode, operands[0]);
10621 operands[4] = gen_frame_mem (Pmode, operands[1]);
10622 p = rtvec_alloc (1);
10623 RTVEC_ELT (p, 0) = gen_rtx_SET (gen_frame_mem (BLKmode, operands[0]),
10625 operands[5] = gen_rtx_PARALLEL (VOIDmode, p);
10628 (define_expand "save_stack_nonlocal"
10629 [(set (match_dup 3) (match_dup 4))
10630 (set (match_operand 0 "memory_operand" "") (match_dup 3))
10631 (set (match_dup 2) (match_operand 1 "register_operand" ""))]
10635 int units_per_word = (TARGET_32BIT) ? 4 : 8;
10637 /* Copy the backchain to the first word, sp to the second. */
10638 operands[0] = adjust_address_nv (operands[0], Pmode, 0);
10639 operands[2] = adjust_address_nv (operands[0], Pmode, units_per_word);
10640 operands[3] = gen_reg_rtx (Pmode);
10641 operands[4] = gen_frame_mem (Pmode, operands[1]);
10644 (define_expand "restore_stack_nonlocal"
10645 [(set (match_dup 2) (match_operand 1 "memory_operand" ""))
10646 (set (match_dup 3) (match_dup 4))
10647 (set (match_dup 5) (match_dup 2))
10649 (set (match_operand 0 "register_operand" "") (match_dup 3))]
10653 int units_per_word = (TARGET_32BIT) ? 4 : 8;
10656 /* Restore the backchain from the first word, sp from the second. */
10657 operands[2] = gen_reg_rtx (Pmode);
10658 operands[3] = gen_reg_rtx (Pmode);
10659 operands[1] = adjust_address_nv (operands[1], Pmode, 0);
10660 operands[4] = adjust_address_nv (operands[1], Pmode, units_per_word);
10661 operands[5] = gen_frame_mem (Pmode, operands[3]);
10662 p = rtvec_alloc (1);
10663 RTVEC_ELT (p, 0) = gen_rtx_SET (gen_frame_mem (BLKmode, operands[0]),
10665 operands[6] = gen_rtx_PARALLEL (VOIDmode, p);
10668 ;; TOC register handling.
10670 ;; Code to initialize the TOC register...
10672 (define_insn "load_toc_aix_si"
10673 [(parallel [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
10674 (unspec:SI [(const_int 0)] UNSPEC_TOC))
10675 (use (reg:SI 2))])]
10676 "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && TARGET_32BIT"
10680 ASM_GENERATE_INTERNAL_LABEL (buf, \"LCTOC\", 1);
10681 operands[1] = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (buf));
10682 operands[2] = gen_rtx_REG (Pmode, 2);
10683 return \"lwz %0,%1(%2)\";
10685 [(set_attr "type" "load")
10686 (set_attr "update" "no")
10687 (set_attr "indexed" "no")])
10689 (define_insn "load_toc_aix_di"
10690 [(parallel [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
10691 (unspec:DI [(const_int 0)] UNSPEC_TOC))
10692 (use (reg:DI 2))])]
10693 "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2) && TARGET_64BIT"
10697 #ifdef TARGET_RELOCATABLE
10698 ASM_GENERATE_INTERNAL_LABEL (buf, \"LCTOC\",
10699 !TARGET_MINIMAL_TOC || TARGET_RELOCATABLE);
10701 ASM_GENERATE_INTERNAL_LABEL (buf, \"LCTOC\", 1);
10704 strcat (buf, \"@toc\");
10705 operands[1] = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (buf));
10706 operands[2] = gen_rtx_REG (Pmode, 2);
10707 return \"ld %0,%1(%2)\";
10709 [(set_attr "type" "load")
10710 (set_attr "update" "no")
10711 (set_attr "indexed" "no")])
10713 (define_insn "load_toc_v4_pic_si"
10714 [(set (reg:SI LR_REGNO)
10715 (unspec:SI [(const_int 0)] UNSPEC_TOC))]
10716 "DEFAULT_ABI == ABI_V4 && flag_pic == 1 && TARGET_32BIT"
10717 "bl _GLOBAL_OFFSET_TABLE_@local-4"
10718 [(set_attr "type" "branch")
10719 (set_attr "length" "4")])
10721 (define_expand "load_toc_v4_PIC_1"
10722 [(parallel [(set (reg:SI LR_REGNO)
10723 (match_operand:SI 0 "immediate_operand" "s"))
10724 (use (unspec [(match_dup 0)] UNSPEC_TOC))])]
10725 "TARGET_ELF && DEFAULT_ABI == ABI_V4
10726 && (flag_pic == 2 || (flag_pic && TARGET_SECURE_PLT))"
10729 (define_insn "load_toc_v4_PIC_1_normal"
10730 [(set (reg:SI LR_REGNO)
10731 (match_operand:SI 0 "immediate_operand" "s"))
10732 (use (unspec [(match_dup 0)] UNSPEC_TOC))]
10733 "!TARGET_LINK_STACK && TARGET_ELF && DEFAULT_ABI == ABI_V4
10734 && (flag_pic == 2 || (flag_pic && TARGET_SECURE_PLT))"
10735 "bcl 20,31,%0\\n%0:"
10736 [(set_attr "type" "branch")
10737 (set_attr "length" "4")])
10739 (define_insn "load_toc_v4_PIC_1_476"
10740 [(set (reg:SI LR_REGNO)
10741 (match_operand:SI 0 "immediate_operand" "s"))
10742 (use (unspec [(match_dup 0)] UNSPEC_TOC))]
10743 "TARGET_LINK_STACK && TARGET_ELF && DEFAULT_ABI == ABI_V4
10744 && (flag_pic == 2 || (flag_pic && TARGET_SECURE_PLT))"
10748 static char templ[32];
10750 get_ppc476_thunk_name (name);
10751 sprintf (templ, \"bl %s\\n%%0:\", name);
10754 [(set_attr "type" "branch")
10755 (set_attr "length" "4")])
10757 (define_expand "load_toc_v4_PIC_1b"
10758 [(parallel [(set (reg:SI LR_REGNO)
10759 (unspec:SI [(match_operand:SI 0 "immediate_operand" "s")
10760 (label_ref (match_operand 1 "" ""))]
10763 "TARGET_ELF && DEFAULT_ABI == ABI_V4 && flag_pic == 2"
10766 (define_insn "load_toc_v4_PIC_1b_normal"
10767 [(set (reg:SI LR_REGNO)
10768 (unspec:SI [(match_operand:SI 0 "immediate_operand" "s")
10769 (label_ref (match_operand 1 "" ""))]
10772 "!TARGET_LINK_STACK && TARGET_ELF && DEFAULT_ABI == ABI_V4 && flag_pic == 2"
10773 "bcl 20,31,$+8\;.long %0-$"
10774 [(set_attr "type" "branch")
10775 (set_attr "length" "8")])
10777 (define_insn "load_toc_v4_PIC_1b_476"
10778 [(set (reg:SI LR_REGNO)
10779 (unspec:SI [(match_operand:SI 0 "immediate_operand" "s")
10780 (label_ref (match_operand 1 "" ""))]
10783 "TARGET_LINK_STACK && TARGET_ELF && DEFAULT_ABI == ABI_V4 && flag_pic == 2"
10787 static char templ[32];
10789 get_ppc476_thunk_name (name);
10790 sprintf (templ, \"bl %s\\n\\tb $+8\\n\\t.long %%0-$\", name);
10793 [(set_attr "type" "branch")
10794 (set_attr "length" "16")])
10796 (define_insn "load_toc_v4_PIC_2"
10797 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
10798 (mem:SI (plus:SI (match_operand:SI 1 "gpc_reg_operand" "b")
10799 (minus:SI (match_operand:SI 2 "immediate_operand" "s")
10800 (match_operand:SI 3 "immediate_operand" "s")))))]
10801 "TARGET_ELF && DEFAULT_ABI == ABI_V4 && flag_pic == 2"
10803 [(set_attr "type" "load")])
10805 (define_insn "load_toc_v4_PIC_3b"
10806 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
10807 (plus:SI (match_operand:SI 1 "gpc_reg_operand" "b")
10809 (minus:SI (match_operand:SI 2 "symbol_ref_operand" "s")
10810 (match_operand:SI 3 "symbol_ref_operand" "s")))))]
10811 "TARGET_ELF && TARGET_SECURE_PLT && DEFAULT_ABI == ABI_V4 && flag_pic"
10812 "addis %0,%1,%2-%3@ha")
10814 (define_insn "load_toc_v4_PIC_3c"
10815 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
10816 (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b")
10817 (minus:SI (match_operand:SI 2 "symbol_ref_operand" "s")
10818 (match_operand:SI 3 "symbol_ref_operand" "s"))))]
10819 "TARGET_ELF && TARGET_SECURE_PLT && DEFAULT_ABI == ABI_V4 && flag_pic"
10820 "addi %0,%1,%2-%3@l")
10822 ;; If the TOC is shared over a translation unit, as happens with all
10823 ;; the kinds of PIC that we support, we need to restore the TOC
10824 ;; pointer only when jumping over units of translation.
10825 ;; On Darwin, we need to reload the picbase.
10827 (define_expand "builtin_setjmp_receiver"
10828 [(use (label_ref (match_operand 0 "" "")))]
10829 "(DEFAULT_ABI == ABI_V4 && flag_pic == 1)
10830 || (TARGET_TOC && TARGET_MINIMAL_TOC)
10831 || (DEFAULT_ABI == ABI_DARWIN && flag_pic)"
10835 if (DEFAULT_ABI == ABI_DARWIN)
10837 rtx picrtx = gen_rtx_SYMBOL_REF (Pmode, MACHOPIC_FUNCTION_BASE_NAME);
10838 rtx picreg = gen_rtx_REG (Pmode, RS6000_PIC_OFFSET_TABLE_REGNUM);
10842 crtl->uses_pic_offset_table = 1;
10843 ASM_GENERATE_INTERNAL_LABEL(tmplab, \"LSJR\",
10844 CODE_LABEL_NUMBER (operands[0]));
10845 tmplabrtx = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (tmplab));
10847 emit_insn (gen_load_macho_picbase (tmplabrtx));
10848 emit_move_insn (picreg, gen_rtx_REG (Pmode, LR_REGNO));
10849 emit_insn (gen_macho_correct_pic (picreg, picreg, picrtx, tmplabrtx));
10853 rs6000_emit_load_toc_table (FALSE);
10857 ;; Largetoc support
10858 (define_insn "*largetoc_high"
10859 [(set (match_operand:DI 0 "gpc_reg_operand" "=b*r")
10861 (unspec [(match_operand:DI 1 "" "")
10862 (match_operand:DI 2 "gpc_reg_operand" "b")]
10864 "TARGET_ELF && TARGET_CMODEL != CMODEL_SMALL"
10865 "addis %0,%2,%1@toc@ha")
10867 (define_insn "*largetoc_high_aix<mode>"
10868 [(set (match_operand:P 0 "gpc_reg_operand" "=b*r")
10870 (unspec [(match_operand:P 1 "" "")
10871 (match_operand:P 2 "gpc_reg_operand" "b")]
10873 "TARGET_XCOFF && TARGET_CMODEL != CMODEL_SMALL"
10874 "addis %0,%1@u(%2)")
10876 (define_insn "*largetoc_high_plus"
10877 [(set (match_operand:DI 0 "gpc_reg_operand" "=b*r")
10880 (unspec [(match_operand:DI 1 "" "")
10881 (match_operand:DI 2 "gpc_reg_operand" "b")]
10883 (match_operand:DI 3 "add_cint_operand" "n"))))]
10884 "TARGET_ELF && TARGET_CMODEL != CMODEL_SMALL"
10885 "addis %0,%2,%1+%3@toc@ha")
10887 (define_insn "*largetoc_high_plus_aix<mode>"
10888 [(set (match_operand:P 0 "gpc_reg_operand" "=b*r")
10891 (unspec [(match_operand:P 1 "" "")
10892 (match_operand:P 2 "gpc_reg_operand" "b")]
10894 (match_operand:P 3 "add_cint_operand" "n"))))]
10895 "TARGET_XCOFF && TARGET_CMODEL != CMODEL_SMALL"
10896 "addis %0,%1+%3@u(%2)")
10898 (define_insn "*largetoc_low"
10899 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
10900 (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b")
10901 (match_operand:DI 2 "" "")))]
10902 "TARGET_ELF && TARGET_CMODEL != CMODEL_SMALL"
10905 (define_insn "*largetoc_low_aix<mode>"
10906 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
10907 (lo_sum:P (match_operand:P 1 "gpc_reg_operand" "b")
10908 (match_operand:P 2 "" "")))]
10909 "TARGET_XCOFF && TARGET_CMODEL != CMODEL_SMALL"
10912 (define_insn_and_split "*tocref<mode>"
10913 [(set (match_operand:P 0 "gpc_reg_operand" "=b")
10914 (match_operand:P 1 "small_toc_ref" "R"))]
10917 "&& TARGET_CMODEL != CMODEL_SMALL && reload_completed"
10918 [(set (match_dup 0) (high:P (match_dup 1)))
10919 (set (match_dup 0) (lo_sum:P (match_dup 0) (match_dup 1)))])
10921 ;; Elf specific ways of loading addresses for non-PIC code.
10922 ;; The output of this could be r0, but we make a very strong
10923 ;; preference for a base register because it will usually
10924 ;; be needed there.
10925 (define_insn "elf_high"
10926 [(set (match_operand:SI 0 "gpc_reg_operand" "=b*r")
10927 (high:SI (match_operand 1 "" "")))]
10928 "TARGET_ELF && ! TARGET_64BIT"
10931 (define_insn "elf_low"
10932 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
10933 (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b")
10934 (match_operand 2 "" "")))]
10935 "TARGET_ELF && ! TARGET_64BIT"
10938 ;; Call and call_value insns
10939 (define_expand "call"
10940 [(parallel [(call (mem:SI (match_operand 0 "address_operand" ""))
10941 (match_operand 1 "" ""))
10942 (use (match_operand 2 "" ""))
10943 (clobber (reg:SI LR_REGNO))])]
10948 if (MACHOPIC_INDIRECT)
10949 operands[0] = machopic_indirect_call_target (operands[0]);
10952 gcc_assert (GET_CODE (operands[0]) == MEM);
10953 gcc_assert (GET_CODE (operands[1]) == CONST_INT);
10955 operands[0] = XEXP (operands[0], 0);
10957 if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)
10959 rs6000_call_aix (NULL_RTX, operands[0], operands[1], operands[2]);
10963 if (GET_CODE (operands[0]) != SYMBOL_REF
10964 || (DEFAULT_ABI != ABI_DARWIN && (INTVAL (operands[2]) & CALL_LONG) != 0))
10966 if (INTVAL (operands[2]) & CALL_LONG)
10967 operands[0] = rs6000_longcall_ref (operands[0]);
10969 switch (DEFAULT_ABI)
10973 operands[0] = force_reg (Pmode, operands[0]);
10977 gcc_unreachable ();
10982 (define_expand "call_value"
10983 [(parallel [(set (match_operand 0 "" "")
10984 (call (mem:SI (match_operand 1 "address_operand" ""))
10985 (match_operand 2 "" "")))
10986 (use (match_operand 3 "" ""))
10987 (clobber (reg:SI LR_REGNO))])]
10992 if (MACHOPIC_INDIRECT)
10993 operands[1] = machopic_indirect_call_target (operands[1]);
10996 gcc_assert (GET_CODE (operands[1]) == MEM);
10997 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
10999 operands[1] = XEXP (operands[1], 0);
11001 if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)
11003 rs6000_call_aix (operands[0], operands[1], operands[2], operands[3]);
11007 if (GET_CODE (operands[1]) != SYMBOL_REF
11008 || (DEFAULT_ABI != ABI_DARWIN && (INTVAL (operands[3]) & CALL_LONG) != 0))
11010 if (INTVAL (operands[3]) & CALL_LONG)
11011 operands[1] = rs6000_longcall_ref (operands[1]);
11013 switch (DEFAULT_ABI)
11017 operands[1] = force_reg (Pmode, operands[1]);
11021 gcc_unreachable ();
11026 ;; Call to function in current module. No TOC pointer reload needed.
11027 ;; Operand2 is nonzero if we are using the V.4 calling sequence and
11028 ;; either the function was not prototyped, or it was prototyped as a
11029 ;; variable argument function. It is > 0 if FP registers were passed
11030 ;; and < 0 if they were not.
11032 (define_insn "*call_local32"
11033 [(call (mem:SI (match_operand:SI 0 "current_file_function_operand" "s,s"))
11034 (match_operand 1 "" "g,g"))
11035 (use (match_operand:SI 2 "immediate_operand" "O,n"))
11036 (clobber (reg:SI LR_REGNO))]
11037 "(INTVAL (operands[2]) & CALL_LONG) == 0"
11040 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
11041 output_asm_insn (\"crxor 6,6,6\", operands);
11043 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
11044 output_asm_insn (\"creqv 6,6,6\", operands);
11046 return (DEFAULT_ABI == ABI_V4 && flag_pic) ? \"bl %z0@local\" : \"bl %z0\";
11048 [(set_attr "type" "branch")
11049 (set_attr "length" "4,8")])
11051 (define_insn "*call_local64"
11052 [(call (mem:SI (match_operand:DI 0 "current_file_function_operand" "s,s"))
11053 (match_operand 1 "" "g,g"))
11054 (use (match_operand:SI 2 "immediate_operand" "O,n"))
11055 (clobber (reg:SI LR_REGNO))]
11056 "TARGET_64BIT && (INTVAL (operands[2]) & CALL_LONG) == 0"
11059 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
11060 output_asm_insn (\"crxor 6,6,6\", operands);
11062 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
11063 output_asm_insn (\"creqv 6,6,6\", operands);
11065 return (DEFAULT_ABI == ABI_V4 && flag_pic) ? \"bl %z0@local\" : \"bl %z0\";
11067 [(set_attr "type" "branch")
11068 (set_attr "length" "4,8")])
11070 (define_insn "*call_value_local32"
11071 [(set (match_operand 0 "" "")
11072 (call (mem:SI (match_operand:SI 1 "current_file_function_operand" "s,s"))
11073 (match_operand 2 "" "g,g")))
11074 (use (match_operand:SI 3 "immediate_operand" "O,n"))
11075 (clobber (reg:SI LR_REGNO))]
11076 "(INTVAL (operands[3]) & CALL_LONG) == 0"
11079 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
11080 output_asm_insn (\"crxor 6,6,6\", operands);
11082 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
11083 output_asm_insn (\"creqv 6,6,6\", operands);
11085 return (DEFAULT_ABI == ABI_V4 && flag_pic) ? \"bl %z1@local\" : \"bl %z1\";
11087 [(set_attr "type" "branch")
11088 (set_attr "length" "4,8")])
11091 (define_insn "*call_value_local64"
11092 [(set (match_operand 0 "" "")
11093 (call (mem:SI (match_operand:DI 1 "current_file_function_operand" "s,s"))
11094 (match_operand 2 "" "g,g")))
11095 (use (match_operand:SI 3 "immediate_operand" "O,n"))
11096 (clobber (reg:SI LR_REGNO))]
11097 "TARGET_64BIT && (INTVAL (operands[3]) & CALL_LONG) == 0"
11100 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
11101 output_asm_insn (\"crxor 6,6,6\", operands);
11103 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
11104 output_asm_insn (\"creqv 6,6,6\", operands);
11106 return (DEFAULT_ABI == ABI_V4 && flag_pic) ? \"bl %z1@local\" : \"bl %z1\";
11108 [(set_attr "type" "branch")
11109 (set_attr "length" "4,8")])
11112 ;; A function pointer under System V is just a normal pointer
11113 ;; operands[0] is the function pointer
11114 ;; operands[1] is the stack size to clean up
11115 ;; operands[2] is the value FUNCTION_ARG returns for the VOID argument
11116 ;; which indicates how to set cr1
11118 (define_insn "*call_indirect_nonlocal_sysv<mode>"
11119 [(call (mem:SI (match_operand:P 0 "register_operand" "c,*l,c,*l"))
11120 (match_operand 1 "" "g,g,g,g"))
11121 (use (match_operand:SI 2 "immediate_operand" "O,O,n,n"))
11122 (clobber (reg:SI LR_REGNO))]
11123 "DEFAULT_ABI == ABI_V4
11124 || DEFAULT_ABI == ABI_DARWIN"
11126 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
11127 output_asm_insn ("crxor 6,6,6", operands);
11129 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
11130 output_asm_insn ("creqv 6,6,6", operands);
11134 [(set_attr "type" "jmpreg,jmpreg,jmpreg,jmpreg")
11135 (set_attr "length" "4,4,8,8")])
11137 (define_insn_and_split "*call_nonlocal_sysv<mode>"
11138 [(call (mem:SI (match_operand:P 0 "symbol_ref_operand" "s,s"))
11139 (match_operand 1 "" "g,g"))
11140 (use (match_operand:SI 2 "immediate_operand" "O,n"))
11141 (clobber (reg:SI LR_REGNO))]
11142 "(DEFAULT_ABI == ABI_DARWIN
11143 || (DEFAULT_ABI == ABI_V4
11144 && (INTVAL (operands[2]) & CALL_LONG) == 0))"
11146 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
11147 output_asm_insn ("crxor 6,6,6", operands);
11149 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
11150 output_asm_insn ("creqv 6,6,6", operands);
11153 return output_call(insn, operands, 0, 2);
11155 if (DEFAULT_ABI == ABI_V4 && flag_pic)
11157 gcc_assert (!TARGET_SECURE_PLT);
11158 return "bl %z0@plt";
11164 "DEFAULT_ABI == ABI_V4
11165 && TARGET_SECURE_PLT && flag_pic && !SYMBOL_REF_LOCAL_P (operands[0])
11166 && (INTVAL (operands[2]) & CALL_LONG) == 0"
11167 [(parallel [(call (mem:SI (match_dup 0))
11169 (use (match_dup 2))
11170 (use (match_dup 3))
11171 (clobber (reg:SI LR_REGNO))])]
11173 operands[3] = pic_offset_table_rtx;
11175 [(set_attr "type" "branch,branch")
11176 (set_attr "length" "4,8")])
11178 (define_insn "*call_nonlocal_sysv_secure<mode>"
11179 [(call (mem:SI (match_operand:P 0 "symbol_ref_operand" "s,s"))
11180 (match_operand 1 "" "g,g"))
11181 (use (match_operand:SI 2 "immediate_operand" "O,n"))
11182 (use (match_operand:SI 3 "register_operand" "r,r"))
11183 (clobber (reg:SI LR_REGNO))]
11184 "(DEFAULT_ABI == ABI_V4
11185 && TARGET_SECURE_PLT && flag_pic && !SYMBOL_REF_LOCAL_P (operands[0])
11186 && (INTVAL (operands[2]) & CALL_LONG) == 0)"
11188 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
11189 output_asm_insn ("crxor 6,6,6", operands);
11191 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
11192 output_asm_insn ("creqv 6,6,6", operands);
11195 /* The magic 32768 offset here and in the other sysv call insns
11196 corresponds to the offset of r30 in .got2, as given by LCTOC1.
11197 See sysv4.h:toc_section. */
11198 return "bl %z0+32768@plt";
11200 return "bl %z0@plt";
11202 [(set_attr "type" "branch,branch")
11203 (set_attr "length" "4,8")])
11205 (define_insn "*call_value_indirect_nonlocal_sysv<mode>"
11206 [(set (match_operand 0 "" "")
11207 (call (mem:SI (match_operand:P 1 "register_operand" "c,*l,c,*l"))
11208 (match_operand 2 "" "g,g,g,g")))
11209 (use (match_operand:SI 3 "immediate_operand" "O,O,n,n"))
11210 (clobber (reg:SI LR_REGNO))]
11211 "DEFAULT_ABI == ABI_V4
11212 || DEFAULT_ABI == ABI_DARWIN"
11214 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
11215 output_asm_insn ("crxor 6,6,6", operands);
11217 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
11218 output_asm_insn ("creqv 6,6,6", operands);
11222 [(set_attr "type" "jmpreg,jmpreg,jmpreg,jmpreg")
11223 (set_attr "length" "4,4,8,8")])
11225 (define_insn_and_split "*call_value_nonlocal_sysv<mode>"
11226 [(set (match_operand 0 "" "")
11227 (call (mem:SI (match_operand:P 1 "symbol_ref_operand" "s,s"))
11228 (match_operand 2 "" "g,g")))
11229 (use (match_operand:SI 3 "immediate_operand" "O,n"))
11230 (clobber (reg:SI LR_REGNO))]
11231 "(DEFAULT_ABI == ABI_DARWIN
11232 || (DEFAULT_ABI == ABI_V4
11233 && (INTVAL (operands[3]) & CALL_LONG) == 0))"
11235 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
11236 output_asm_insn ("crxor 6,6,6", operands);
11238 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
11239 output_asm_insn ("creqv 6,6,6", operands);
11242 return output_call(insn, operands, 1, 3);
11244 if (DEFAULT_ABI == ABI_V4 && flag_pic)
11246 gcc_assert (!TARGET_SECURE_PLT);
11247 return "bl %z1@plt";
11253 "DEFAULT_ABI == ABI_V4
11254 && TARGET_SECURE_PLT && flag_pic && !SYMBOL_REF_LOCAL_P (operands[1])
11255 && (INTVAL (operands[3]) & CALL_LONG) == 0"
11256 [(parallel [(set (match_dup 0)
11257 (call (mem:SI (match_dup 1))
11259 (use (match_dup 3))
11260 (use (match_dup 4))
11261 (clobber (reg:SI LR_REGNO))])]
11263 operands[4] = pic_offset_table_rtx;
11265 [(set_attr "type" "branch,branch")
11266 (set_attr "length" "4,8")])
11268 (define_insn "*call_value_nonlocal_sysv_secure<mode>"
11269 [(set (match_operand 0 "" "")
11270 (call (mem:SI (match_operand:P 1 "symbol_ref_operand" "s,s"))
11271 (match_operand 2 "" "g,g")))
11272 (use (match_operand:SI 3 "immediate_operand" "O,n"))
11273 (use (match_operand:SI 4 "register_operand" "r,r"))
11274 (clobber (reg:SI LR_REGNO))]
11275 "(DEFAULT_ABI == ABI_V4
11276 && TARGET_SECURE_PLT && flag_pic && !SYMBOL_REF_LOCAL_P (operands[1])
11277 && (INTVAL (operands[3]) & CALL_LONG) == 0)"
11279 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
11280 output_asm_insn ("crxor 6,6,6", operands);
11282 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
11283 output_asm_insn ("creqv 6,6,6", operands);
11286 return "bl %z1+32768@plt";
11288 return "bl %z1@plt";
11290 [(set_attr "type" "branch,branch")
11291 (set_attr "length" "4,8")])
11294 ;; Call to AIX abi function in the same module.
11296 (define_insn "*call_local_aix<mode>"
11297 [(call (mem:SI (match_operand:P 0 "current_file_function_operand" "s"))
11298 (match_operand 1 "" "g"))
11299 (clobber (reg:P LR_REGNO))]
11300 "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2"
11302 [(set_attr "type" "branch")
11303 (set_attr "length" "4")])
11305 (define_insn "*call_value_local_aix<mode>"
11306 [(set (match_operand 0 "" "")
11307 (call (mem:SI (match_operand:P 1 "current_file_function_operand" "s"))
11308 (match_operand 2 "" "g")))
11309 (clobber (reg:P LR_REGNO))]
11310 "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2"
11312 [(set_attr "type" "branch")
11313 (set_attr "length" "4")])
11315 ;; Call to AIX abi function which may be in another module.
11316 ;; Restore the TOC pointer (r2) after the call.
11318 (define_insn "*call_nonlocal_aix<mode>"
11319 [(call (mem:SI (match_operand:P 0 "symbol_ref_operand" "s"))
11320 (match_operand 1 "" "g"))
11321 (clobber (reg:P LR_REGNO))]
11322 "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2"
11324 [(set_attr "type" "branch")
11325 (set_attr "length" "8")])
11327 (define_insn "*call_value_nonlocal_aix<mode>"
11328 [(set (match_operand 0 "" "")
11329 (call (mem:SI (match_operand:P 1 "symbol_ref_operand" "s"))
11330 (match_operand 2 "" "g")))
11331 (clobber (reg:P LR_REGNO))]
11332 "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2"
11334 [(set_attr "type" "branch")
11335 (set_attr "length" "8")])
11337 ;; Call to indirect functions with the AIX abi using a 3 word descriptor.
11338 ;; Operand0 is the addresss of the function to call
11339 ;; Operand2 is the location in the function descriptor to load r2 from
11340 ;; Operand3 is the offset of the stack location holding the current TOC pointer
11342 (define_insn "*call_indirect_aix<mode>"
11343 [(call (mem:SI (match_operand:P 0 "register_operand" "c,*l"))
11344 (match_operand 1 "" "g,g"))
11345 (use (match_operand:P 2 "memory_operand" "<ptrm>,<ptrm>"))
11346 (set (reg:P TOC_REGNUM) (unspec [(match_operand:P 3 "const_int_operand" "n,n")] UNSPEC_TOCSLOT))
11347 (clobber (reg:P LR_REGNO))]
11348 "DEFAULT_ABI == ABI_AIX"
11349 "<ptrload> 2,%2\;b%T0l\;<ptrload> 2,%3(1)"
11350 [(set_attr "type" "jmpreg")
11351 (set_attr "length" "12")])
11353 (define_insn "*call_value_indirect_aix<mode>"
11354 [(set (match_operand 0 "" "")
11355 (call (mem:SI (match_operand:P 1 "register_operand" "c,*l"))
11356 (match_operand 2 "" "g,g")))
11357 (use (match_operand:P 3 "memory_operand" "<ptrm>,<ptrm>"))
11358 (set (reg:P TOC_REGNUM) (unspec [(match_operand:P 4 "const_int_operand" "n,n")] UNSPEC_TOCSLOT))
11359 (clobber (reg:P LR_REGNO))]
11360 "DEFAULT_ABI == ABI_AIX"
11361 "<ptrload> 2,%3\;b%T1l\;<ptrload> 2,%4(1)"
11362 [(set_attr "type" "jmpreg")
11363 (set_attr "length" "12")])
11365 ;; Call to indirect functions with the ELFv2 ABI.
11366 ;; Operand0 is the addresss of the function to call
11367 ;; Operand2 is the offset of the stack location holding the current TOC pointer
11369 (define_insn "*call_indirect_elfv2<mode>"
11370 [(call (mem:SI (match_operand:P 0 "register_operand" "c,*l"))
11371 (match_operand 1 "" "g,g"))
11372 (set (reg:P TOC_REGNUM) (unspec [(match_operand:P 2 "const_int_operand" "n,n")] UNSPEC_TOCSLOT))
11373 (clobber (reg:P LR_REGNO))]
11374 "DEFAULT_ABI == ABI_ELFv2"
11375 "b%T0l\;<ptrload> 2,%2(1)"
11376 [(set_attr "type" "jmpreg")
11377 (set_attr "length" "8")])
11379 (define_insn "*call_value_indirect_elfv2<mode>"
11380 [(set (match_operand 0 "" "")
11381 (call (mem:SI (match_operand:P 1 "register_operand" "c,*l"))
11382 (match_operand 2 "" "g,g")))
11383 (set (reg:P TOC_REGNUM) (unspec [(match_operand:P 3 "const_int_operand" "n,n")] UNSPEC_TOCSLOT))
11384 (clobber (reg:P LR_REGNO))]
11385 "DEFAULT_ABI == ABI_ELFv2"
11386 "b%T1l\;<ptrload> 2,%3(1)"
11387 [(set_attr "type" "jmpreg")
11388 (set_attr "length" "8")])
11391 ;; Call subroutine returning any type.
11392 (define_expand "untyped_call"
11393 [(parallel [(call (match_operand 0 "" "")
11395 (match_operand 1 "" "")
11396 (match_operand 2 "" "")])]
11402 emit_call_insn (GEN_CALL (operands[0], const0_rtx, const0_rtx, const0_rtx));
11404 for (i = 0; i < XVECLEN (operands[2], 0); i++)
11406 rtx set = XVECEXP (operands[2], 0, i);
11407 emit_move_insn (SET_DEST (set), SET_SRC (set));
11410 /* The optimizer does not know that the call sets the function value
11411 registers we stored in the result block. We avoid problems by
11412 claiming that all hard registers are used and clobbered at this
11414 emit_insn (gen_blockage ());
11419 ;; sibling call patterns
11420 (define_expand "sibcall"
11421 [(parallel [(call (mem:SI (match_operand 0 "address_operand" ""))
11422 (match_operand 1 "" ""))
11423 (use (match_operand 2 "" ""))
11424 (use (reg:SI LR_REGNO))
11430 if (MACHOPIC_INDIRECT)
11431 operands[0] = machopic_indirect_call_target (operands[0]);
11434 gcc_assert (GET_CODE (operands[0]) == MEM);
11435 gcc_assert (GET_CODE (operands[1]) == CONST_INT);
11437 operands[0] = XEXP (operands[0], 0);
11439 if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)
11441 rs6000_sibcall_aix (NULL_RTX, operands[0], operands[1], operands[2]);
11446 (define_expand "sibcall_value"
11447 [(parallel [(set (match_operand 0 "register_operand" "")
11448 (call (mem:SI (match_operand 1 "address_operand" ""))
11449 (match_operand 2 "" "")))
11450 (use (match_operand 3 "" ""))
11451 (use (reg:SI LR_REGNO))
11457 if (MACHOPIC_INDIRECT)
11458 operands[1] = machopic_indirect_call_target (operands[1]);
11461 gcc_assert (GET_CODE (operands[1]) == MEM);
11462 gcc_assert (GET_CODE (operands[2]) == CONST_INT);
11464 operands[1] = XEXP (operands[1], 0);
11466 if (DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2)
11468 rs6000_sibcall_aix (operands[0], operands[1], operands[2], operands[3]);
11473 ;; this and similar patterns must be marked as using LR, otherwise
11474 ;; dataflow will try to delete the store into it. This is true
11475 ;; even when the actual reg to jump to is in CTR, when LR was
11476 ;; saved and restored around the PIC-setting BCL.
11477 (define_insn "*sibcall_local32"
11478 [(call (mem:SI (match_operand:SI 0 "current_file_function_operand" "s,s"))
11479 (match_operand 1 "" "g,g"))
11480 (use (match_operand:SI 2 "immediate_operand" "O,n"))
11481 (use (reg:SI LR_REGNO))
11483 "(INTVAL (operands[2]) & CALL_LONG) == 0"
11486 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
11487 output_asm_insn (\"crxor 6,6,6\", operands);
11489 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
11490 output_asm_insn (\"creqv 6,6,6\", operands);
11492 return (DEFAULT_ABI == ABI_V4 && flag_pic) ? \"b %z0@local\" : \"b %z0\";
11494 [(set_attr "type" "branch")
11495 (set_attr "length" "4,8")])
11497 (define_insn "*sibcall_local64"
11498 [(call (mem:SI (match_operand:DI 0 "current_file_function_operand" "s,s"))
11499 (match_operand 1 "" "g,g"))
11500 (use (match_operand:SI 2 "immediate_operand" "O,n"))
11501 (use (reg:SI LR_REGNO))
11503 "TARGET_64BIT && (INTVAL (operands[2]) & CALL_LONG) == 0"
11506 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
11507 output_asm_insn (\"crxor 6,6,6\", operands);
11509 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
11510 output_asm_insn (\"creqv 6,6,6\", operands);
11512 return (DEFAULT_ABI == ABI_V4 && flag_pic) ? \"b %z0@local\" : \"b %z0\";
11514 [(set_attr "type" "branch")
11515 (set_attr "length" "4,8")])
11517 (define_insn "*sibcall_value_local32"
11518 [(set (match_operand 0 "" "")
11519 (call (mem:SI (match_operand:SI 1 "current_file_function_operand" "s,s"))
11520 (match_operand 2 "" "g,g")))
11521 (use (match_operand:SI 3 "immediate_operand" "O,n"))
11522 (use (reg:SI LR_REGNO))
11524 "(INTVAL (operands[3]) & CALL_LONG) == 0"
11527 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
11528 output_asm_insn (\"crxor 6,6,6\", operands);
11530 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
11531 output_asm_insn (\"creqv 6,6,6\", operands);
11533 return (DEFAULT_ABI == ABI_V4 && flag_pic) ? \"b %z1@local\" : \"b %z1\";
11535 [(set_attr "type" "branch")
11536 (set_attr "length" "4,8")])
11538 (define_insn "*sibcall_value_local64"
11539 [(set (match_operand 0 "" "")
11540 (call (mem:SI (match_operand:DI 1 "current_file_function_operand" "s,s"))
11541 (match_operand 2 "" "g,g")))
11542 (use (match_operand:SI 3 "immediate_operand" "O,n"))
11543 (use (reg:SI LR_REGNO))
11545 "TARGET_64BIT && (INTVAL (operands[3]) & CALL_LONG) == 0"
11548 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
11549 output_asm_insn (\"crxor 6,6,6\", operands);
11551 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
11552 output_asm_insn (\"creqv 6,6,6\", operands);
11554 return (DEFAULT_ABI == ABI_V4 && flag_pic) ? \"b %z1@local\" : \"b %z1\";
11556 [(set_attr "type" "branch")
11557 (set_attr "length" "4,8")])
11559 (define_insn "*sibcall_nonlocal_sysv<mode>"
11560 [(call (mem:SI (match_operand:P 0 "call_operand" "s,s,c,c"))
11561 (match_operand 1 "" ""))
11562 (use (match_operand 2 "immediate_operand" "O,n,O,n"))
11563 (use (reg:SI LR_REGNO))
11565 "(DEFAULT_ABI == ABI_DARWIN
11566 || DEFAULT_ABI == ABI_V4)
11567 && (INTVAL (operands[2]) & CALL_LONG) == 0"
11570 if (INTVAL (operands[2]) & CALL_V4_SET_FP_ARGS)
11571 output_asm_insn (\"crxor 6,6,6\", operands);
11573 else if (INTVAL (operands[2]) & CALL_V4_CLEAR_FP_ARGS)
11574 output_asm_insn (\"creqv 6,6,6\", operands);
11576 if (which_alternative >= 2)
11578 else if (DEFAULT_ABI == ABI_V4 && flag_pic)
11580 gcc_assert (!TARGET_SECURE_PLT);
11581 return \"b %z0@plt\";
11586 [(set_attr "type" "branch")
11587 (set_attr "length" "4,8,4,8")])
11589 (define_insn "*sibcall_value_nonlocal_sysv<mode>"
11590 [(set (match_operand 0 "" "")
11591 (call (mem:SI (match_operand:P 1 "call_operand" "s,s,c,c"))
11592 (match_operand 2 "" "")))
11593 (use (match_operand:SI 3 "immediate_operand" "O,n,O,n"))
11594 (use (reg:SI LR_REGNO))
11596 "(DEFAULT_ABI == ABI_DARWIN
11597 || DEFAULT_ABI == ABI_V4)
11598 && (INTVAL (operands[3]) & CALL_LONG) == 0"
11601 if (INTVAL (operands[3]) & CALL_V4_SET_FP_ARGS)
11602 output_asm_insn (\"crxor 6,6,6\", operands);
11604 else if (INTVAL (operands[3]) & CALL_V4_CLEAR_FP_ARGS)
11605 output_asm_insn (\"creqv 6,6,6\", operands);
11607 if (which_alternative >= 2)
11609 else if (DEFAULT_ABI == ABI_V4 && flag_pic)
11611 gcc_assert (!TARGET_SECURE_PLT);
11612 return \"b %z1@plt\";
11617 [(set_attr "type" "branch")
11618 (set_attr "length" "4,8,4,8")])
11620 ;; AIX ABI sibling call patterns.
11622 (define_insn "*sibcall_aix<mode>"
11623 [(call (mem:SI (match_operand:P 0 "call_operand" "s,c"))
11624 (match_operand 1 "" "g,g"))
11626 "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2"
11630 [(set_attr "type" "branch")
11631 (set_attr "length" "4")])
11633 (define_insn "*sibcall_value_aix<mode>"
11634 [(set (match_operand 0 "" "")
11635 (call (mem:SI (match_operand:P 1 "call_operand" "s,c"))
11636 (match_operand 2 "" "g,g")))
11638 "DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_ELFv2"
11642 [(set_attr "type" "branch")
11643 (set_attr "length" "4")])
11645 (define_expand "sibcall_epilogue"
11646 [(use (const_int 0))]
11649 if (!TARGET_SCHED_PROLOG)
11650 emit_insn (gen_blockage ());
11651 rs6000_emit_epilogue (TRUE);
11655 ;; UNSPEC_VOLATILE is considered to use and clobber all hard registers and
11656 ;; all of memory. This blocks insns from being moved across this point.
11658 (define_insn "blockage"
11659 [(unspec_volatile [(const_int 0)] UNSPECV_BLOCK)]
11663 (define_expand "probe_stack_address"
11664 [(use (match_operand 0 "address_operand"))]
11667 operands[0] = gen_rtx_MEM (Pmode, operands[0]);
11668 MEM_VOLATILE_P (operands[0]) = 1;
11671 emit_insn (gen_probe_stack_di (operands[0]));
11673 emit_insn (gen_probe_stack_si (operands[0]));
11677 (define_insn "probe_stack_<mode>"
11678 [(set (match_operand:P 0 "memory_operand" "=m")
11679 (unspec:P [(const_int 0)] UNSPEC_PROBE_STACK))]
11682 operands[1] = gen_rtx_REG (Pmode, 0);
11683 return "st<wd>%U0%X0 %1,%0";
11685 [(set_attr "type" "store")
11686 (set (attr "update")
11687 (if_then_else (match_operand 0 "update_address_mem")
11688 (const_string "yes")
11689 (const_string "no")))
11690 (set (attr "indexed")
11691 (if_then_else (match_operand 0 "indexed_address_mem")
11692 (const_string "yes")
11693 (const_string "no")))
11694 (set_attr "length" "4")])
11696 (define_insn "probe_stack_range<P:mode>"
11697 [(set (match_operand:P 0 "register_operand" "=r")
11698 (unspec_volatile:P [(match_operand:P 1 "register_operand" "0")
11699 (match_operand:P 2 "register_operand" "r")]
11700 UNSPECV_PROBE_STACK_RANGE))]
11702 "* return output_probe_stack_range (operands[0], operands[2]);"
11703 [(set_attr "type" "three")])
11705 ;; Compare insns are next. Note that the RS/6000 has two types of compares,
11706 ;; signed & unsigned, and one type of branch.
11708 ;; Start with the DEFINE_EXPANDs to generate the rtl for compares, scc
11709 ;; insns, and branches.
11711 (define_expand "cbranch<mode>4"
11712 [(use (match_operator 0 "rs6000_cbranch_operator"
11713 [(match_operand:GPR 1 "gpc_reg_operand" "")
11714 (match_operand:GPR 2 "reg_or_short_operand" "")]))
11715 (use (match_operand 3 ""))]
11719 /* Take care of the possibility that operands[2] might be negative but
11720 this might be a logical operation. That insn doesn't exist. */
11721 if (GET_CODE (operands[2]) == CONST_INT
11722 && INTVAL (operands[2]) < 0)
11724 operands[2] = force_reg (<MODE>mode, operands[2]);
11725 operands[0] = gen_rtx_fmt_ee (GET_CODE (operands[0]),
11726 GET_MODE (operands[0]),
11727 operands[1], operands[2]);
11730 rs6000_emit_cbranch (<MODE>mode, operands);
11734 (define_expand "cbranch<mode>4"
11735 [(use (match_operator 0 "rs6000_cbranch_operator"
11736 [(match_operand:FP 1 "gpc_reg_operand" "")
11737 (match_operand:FP 2 "gpc_reg_operand" "")]))
11738 (use (match_operand 3 ""))]
11742 rs6000_emit_cbranch (<MODE>mode, operands);
11746 (define_expand "cstore<mode>4_unsigned"
11747 [(use (match_operator 1 "unsigned_comparison_operator"
11748 [(match_operand:P 2 "gpc_reg_operand" "")
11749 (match_operand:P 3 "reg_or_short_operand" "")]))
11750 (clobber (match_operand:P 0 "register_operand"))]
11753 enum rtx_code cond_code = GET_CODE (operands[1]);
11755 rtx op0 = operands[0];
11756 rtx op1 = operands[2];
11757 rtx op2 = operands[3];
11759 if (cond_code == GEU || cond_code == LTU)
11761 cond_code = swap_condition (cond_code);
11766 if (!gpc_reg_operand (op1, <MODE>mode))
11767 op1 = force_reg (<MODE>mode, op1);
11768 if (!reg_or_short_operand (op2, <MODE>mode))
11769 op2 = force_reg (<MODE>mode, op2);
11771 rtx tmp = gen_reg_rtx (<MODE>mode);
11772 rtx tmp2 = gen_reg_rtx (<MODE>mode);
11774 emit_insn (gen_subf<mode>3_carry (tmp, op1, op2));
11775 emit_insn (gen_subf<mode>3_carry_in_xx (tmp2));
11777 if (cond_code == LEU)
11778 emit_insn (gen_add<mode>3 (op0, tmp2, const1_rtx));
11780 emit_insn (gen_neg<mode>2 (op0, tmp2));
11785 (define_expand "cstore<mode>4_signed_imm"
11786 [(use (match_operator 1 "signed_comparison_operator"
11787 [(match_operand:GPR 2 "gpc_reg_operand")
11788 (match_operand:GPR 3 "immediate_operand")]))
11789 (clobber (match_operand:GPR 0 "register_operand"))]
11792 bool invert = false;
11794 enum rtx_code cond_code = GET_CODE (operands[1]);
11796 rtx op0 = operands[0];
11797 rtx op1 = operands[2];
11798 HOST_WIDE_INT val = INTVAL (operands[3]);
11800 if (cond_code == GE || cond_code == GT)
11802 cond_code = reverse_condition (cond_code);
11806 if (cond_code == LE)
11809 rtx tmp = gen_reg_rtx (<MODE>mode);
11810 emit_insn (gen_add<mode>3 (tmp, op1, GEN_INT (-val)));
11811 rtx x = gen_reg_rtx (<MODE>mode);
11813 emit_insn (gen_and<mode>3 (x, op1, tmp));
11815 emit_insn (gen_ior<mode>3 (x, op1, tmp));
11819 rtx tmp = gen_reg_rtx (<MODE>mode);
11820 emit_insn (gen_one_cmpl<mode>2 (tmp, x));
11824 int sh = GET_MODE_BITSIZE (<MODE>mode) - 1;
11825 emit_insn (gen_lshr<mode>3 (op0, x, GEN_INT (sh)));
11830 (define_expand "cstore<mode>4_unsigned_imm"
11831 [(use (match_operator 1 "unsigned_comparison_operator"
11832 [(match_operand:GPR 2 "gpc_reg_operand")
11833 (match_operand:GPR 3 "immediate_operand")]))
11834 (clobber (match_operand:GPR 0 "register_operand"))]
11837 bool invert = false;
11839 enum rtx_code cond_code = GET_CODE (operands[1]);
11841 rtx op0 = operands[0];
11842 rtx op1 = operands[2];
11843 HOST_WIDE_INT val = INTVAL (operands[3]);
11845 if (cond_code == GEU || cond_code == GTU)
11847 cond_code = reverse_condition (cond_code);
11851 if (cond_code == LEU)
11854 rtx tmp = gen_reg_rtx (<MODE>mode);
11855 rtx tmp2 = gen_reg_rtx (<MODE>mode);
11856 emit_insn (gen_add<mode>3 (tmp, op1, GEN_INT (-val)));
11857 emit_insn (gen_one_cmpl<mode>2 (tmp2, op1));
11858 rtx x = gen_reg_rtx (<MODE>mode);
11860 emit_insn (gen_ior<mode>3 (x, tmp, tmp2));
11862 emit_insn (gen_and<mode>3 (x, tmp, tmp2));
11866 rtx tmp = gen_reg_rtx (<MODE>mode);
11867 emit_insn (gen_one_cmpl<mode>2 (tmp, x));
11871 int sh = GET_MODE_BITSIZE (<MODE>mode) - 1;
11872 emit_insn (gen_lshr<mode>3 (op0, x, GEN_INT (sh)));
11877 (define_expand "cstore<mode>4"
11878 [(use (match_operator 1 "rs6000_cbranch_operator"
11879 [(match_operand:GPR 2 "gpc_reg_operand")
11880 (match_operand:GPR 3 "reg_or_short_operand")]))
11881 (clobber (match_operand:GPR 0 "register_operand"))]
11884 /* Use ISEL if the user asked for it. */
11886 rs6000_emit_sISEL (<MODE>mode, operands);
11888 /* Expanding EQ and NE directly to some machine instructions does not help
11889 but does hurt combine. So don't. */
11890 else if (GET_CODE (operands[1]) == EQ)
11891 emit_insn (gen_eq<mode>3 (operands[0], operands[2], operands[3]));
11892 else if (<MODE>mode == Pmode
11893 && GET_CODE (operands[1]) == NE)
11894 emit_insn (gen_ne<mode>3 (operands[0], operands[2], operands[3]));
11895 else if (GET_CODE (operands[1]) == NE)
11897 rtx tmp = gen_reg_rtx (<MODE>mode);
11898 emit_insn (gen_eq<mode>3 (tmp, operands[2], operands[3]));
11899 emit_insn (gen_xor<mode>3 (operands[0], tmp, const1_rtx));
11902 /* Expanding the unsigned comparisons however helps a lot: all the neg_ltu
11903 etc. combinations magically work out just right. */
11904 else if (<MODE>mode == Pmode
11905 && unsigned_comparison_operator (operands[1], VOIDmode))
11906 emit_insn (gen_cstore<mode>4_unsigned (operands[0], operands[1],
11907 operands[2], operands[3]));
11909 /* For signed comparisons against a constant, we can do some simple
11911 else if (signed_comparison_operator (operands[1], VOIDmode)
11912 && CONST_INT_P (operands[3]))
11913 emit_insn (gen_cstore<mode>4_signed_imm (operands[0], operands[1],
11914 operands[2], operands[3]));
11916 /* And similarly for unsigned comparisons. */
11917 else if (unsigned_comparison_operator (operands[1], VOIDmode)
11918 && CONST_INT_P (operands[3]))
11919 emit_insn (gen_cstore<mode>4_unsigned_imm (operands[0], operands[1],
11920 operands[2], operands[3]));
11922 /* Everything else, use the mfcr brute force. */
11924 rs6000_emit_sCOND (<MODE>mode, operands);
11929 (define_expand "cstore<mode>4"
11930 [(use (match_operator 1 "rs6000_cbranch_operator"
11931 [(match_operand:FP 2 "gpc_reg_operand" "")
11932 (match_operand:FP 3 "gpc_reg_operand" "")]))
11933 (clobber (match_operand:SI 0 "register_operand"))]
11936 rs6000_emit_sCOND (<MODE>mode, operands);
11941 (define_expand "stack_protect_set"
11942 [(match_operand 0 "memory_operand" "")
11943 (match_operand 1 "memory_operand" "")]
11946 #ifdef TARGET_THREAD_SSP_OFFSET
11947 rtx tlsreg = gen_rtx_REG (Pmode, TARGET_64BIT ? 13 : 2);
11948 rtx addr = gen_rtx_PLUS (Pmode, tlsreg, GEN_INT (TARGET_THREAD_SSP_OFFSET));
11949 operands[1] = gen_rtx_MEM (Pmode, addr);
11952 emit_insn (gen_stack_protect_setdi (operands[0], operands[1]));
11954 emit_insn (gen_stack_protect_setsi (operands[0], operands[1]));
11958 (define_insn "stack_protect_setsi"
11959 [(set (match_operand:SI 0 "memory_operand" "=m")
11960 (unspec:SI [(match_operand:SI 1 "memory_operand" "m")] UNSPEC_SP_SET))
11961 (set (match_scratch:SI 2 "=&r") (const_int 0))]
11963 "lwz%U1%X1 %2,%1\;stw%U0%X0 %2,%0\;li %2,0"
11964 [(set_attr "type" "three")
11965 (set_attr "length" "12")])
11967 (define_insn "stack_protect_setdi"
11968 [(set (match_operand:DI 0 "memory_operand" "=Y")
11969 (unspec:DI [(match_operand:DI 1 "memory_operand" "Y")] UNSPEC_SP_SET))
11970 (set (match_scratch:DI 2 "=&r") (const_int 0))]
11972 "ld%U1%X1 %2,%1\;std%U0%X0 %2,%0\;li %2,0"
11973 [(set_attr "type" "three")
11974 (set_attr "length" "12")])
11976 (define_expand "stack_protect_test"
11977 [(match_operand 0 "memory_operand" "")
11978 (match_operand 1 "memory_operand" "")
11979 (match_operand 2 "" "")]
11982 rtx test, op0, op1;
11983 #ifdef TARGET_THREAD_SSP_OFFSET
11984 rtx tlsreg = gen_rtx_REG (Pmode, TARGET_64BIT ? 13 : 2);
11985 rtx addr = gen_rtx_PLUS (Pmode, tlsreg, GEN_INT (TARGET_THREAD_SSP_OFFSET));
11986 operands[1] = gen_rtx_MEM (Pmode, addr);
11989 op1 = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, operands[1]), UNSPEC_SP_TEST);
11990 test = gen_rtx_EQ (VOIDmode, op0, op1);
11991 emit_jump_insn (gen_cbranchsi4 (test, op0, op1, operands[2]));
11995 (define_insn "stack_protect_testsi"
11996 [(set (match_operand:CCEQ 0 "cc_reg_operand" "=x,?y")
11997 (unspec:CCEQ [(match_operand:SI 1 "memory_operand" "m,m")
11998 (match_operand:SI 2 "memory_operand" "m,m")]
12000 (set (match_scratch:SI 4 "=r,r") (const_int 0))
12001 (clobber (match_scratch:SI 3 "=&r,&r"))]
12004 lwz%U1%X1 %3,%1\;lwz%U2%X2 %4,%2\;xor. %3,%3,%4\;li %4,0
12005 lwz%U1%X1 %3,%1\;lwz%U2%X2 %4,%2\;cmplw %0,%3,%4\;li %3,0\;li %4,0"
12006 [(set_attr "length" "16,20")])
12008 (define_insn "stack_protect_testdi"
12009 [(set (match_operand:CCEQ 0 "cc_reg_operand" "=x,?y")
12010 (unspec:CCEQ [(match_operand:DI 1 "memory_operand" "Y,Y")
12011 (match_operand:DI 2 "memory_operand" "Y,Y")]
12013 (set (match_scratch:DI 4 "=r,r") (const_int 0))
12014 (clobber (match_scratch:DI 3 "=&r,&r"))]
12017 ld%U1%X1 %3,%1\;ld%U2%X2 %4,%2\;xor. %3,%3,%4\;li %4,0
12018 ld%U1%X1 %3,%1\;ld%U2%X2 %4,%2\;cmpld %0,%3,%4\;li %3,0\;li %4,0"
12019 [(set_attr "length" "16,20")])
12022 ;; Here are the actual compare insns.
12023 (define_insn "*cmp<mode>_internal1"
12024 [(set (match_operand:CC 0 "cc_reg_operand" "=y")
12025 (compare:CC (match_operand:GPR 1 "gpc_reg_operand" "r")
12026 (match_operand:GPR 2 "reg_or_short_operand" "rI")))]
12028 "cmp<wd>%I2 %0,%1,%2"
12029 [(set_attr "type" "cmp")])
12031 ;; If we are comparing a register for equality with a large constant,
12032 ;; we can do this with an XOR followed by a compare. But this is profitable
12033 ;; only if the large constant is only used for the comparison (and in this
12034 ;; case we already have a register to reuse as scratch).
12036 ;; For 64-bit registers, we could only do so if the constant's bit 15 is clear:
12037 ;; otherwise we'd need to XOR with FFFFFFFF????0000 which is not available.
12040 [(set (match_operand:SI 0 "register_operand")
12041 (match_operand:SI 1 "logical_const_operand" ""))
12042 (set (match_dup 0) (match_operator:SI 3 "boolean_or_operator"
12044 (match_operand:SI 2 "logical_const_operand" "")]))
12045 (set (match_operand:CC 4 "cc_reg_operand" "")
12046 (compare:CC (match_operand:SI 5 "gpc_reg_operand" "")
12049 (if_then_else (match_operator 6 "equality_operator"
12050 [(match_dup 4) (const_int 0)])
12051 (match_operand 7 "" "")
12052 (match_operand 8 "" "")))]
12053 "peep2_reg_dead_p (3, operands[0])
12054 && peep2_reg_dead_p (4, operands[4])"
12055 [(set (match_dup 0) (xor:SI (match_dup 5) (match_dup 9)))
12056 (set (match_dup 4) (compare:CC (match_dup 0) (match_dup 10)))
12057 (set (pc) (if_then_else (match_dup 6) (match_dup 7) (match_dup 8)))]
12060 /* Get the constant we are comparing against, and see what it looks like
12061 when sign-extended from 16 to 32 bits. Then see what constant we could
12062 XOR with SEXTC to get the sign-extended value. */
12063 rtx cnst = simplify_const_binary_operation (GET_CODE (operands[3]),
12065 operands[1], operands[2]);
12066 HOST_WIDE_INT c = INTVAL (cnst);
12067 HOST_WIDE_INT sextc = ((c & 0xffff) ^ 0x8000) - 0x8000;
12068 HOST_WIDE_INT xorv = c ^ sextc;
12070 operands[9] = GEN_INT (xorv);
12071 operands[10] = GEN_INT (sextc);
12074 (define_insn "*cmpsi_internal2"
12075 [(set (match_operand:CCUNS 0 "cc_reg_operand" "=y")
12076 (compare:CCUNS (match_operand:SI 1 "gpc_reg_operand" "r")
12077 (match_operand:SI 2 "reg_or_u_short_operand" "rK")))]
12079 "cmplw%I2 %0,%1,%b2"
12080 [(set_attr "type" "cmp")])
12082 (define_insn "*cmpdi_internal2"
12083 [(set (match_operand:CCUNS 0 "cc_reg_operand" "=y")
12084 (compare:CCUNS (match_operand:DI 1 "gpc_reg_operand" "r")
12085 (match_operand:DI 2 "reg_or_u_short_operand" "rK")))]
12087 "cmpld%I2 %0,%1,%b2"
12088 [(set_attr "type" "cmp")])
12090 ;; The following two insns don't exist as single insns, but if we provide
12091 ;; them, we can swap an add and compare, which will enable us to overlap more
12092 ;; of the required delay between a compare and branch. We generate code for
12093 ;; them by splitting.
12096 [(set (match_operand:CC 3 "cc_reg_operand" "=y")
12097 (compare:CC (match_operand:SI 1 "gpc_reg_operand" "r")
12098 (match_operand:SI 2 "short_cint_operand" "i")))
12099 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
12100 (plus:SI (match_dup 1) (match_operand:SI 4 "short_cint_operand" "i")))]
12103 [(set_attr "length" "8")])
12106 [(set (match_operand:CCUNS 3 "cc_reg_operand" "=y")
12107 (compare:CCUNS (match_operand:SI 1 "gpc_reg_operand" "r")
12108 (match_operand:SI 2 "u_short_cint_operand" "i")))
12109 (set (match_operand:SI 0 "gpc_reg_operand" "=r")
12110 (plus:SI (match_dup 1) (match_operand:SI 4 "short_cint_operand" "i")))]
12113 [(set_attr "length" "8")])
12116 [(set (match_operand:CC 3 "cc_reg_operand" "")
12117 (compare:CC (match_operand:SI 1 "gpc_reg_operand" "")
12118 (match_operand:SI 2 "short_cint_operand" "")))
12119 (set (match_operand:SI 0 "gpc_reg_operand" "")
12120 (plus:SI (match_dup 1) (match_operand:SI 4 "short_cint_operand" "")))]
12122 [(set (match_dup 3) (compare:CC (match_dup 1) (match_dup 2)))
12123 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 4)))])
12126 [(set (match_operand:CCUNS 3 "cc_reg_operand" "")
12127 (compare:CCUNS (match_operand:SI 1 "gpc_reg_operand" "")
12128 (match_operand:SI 2 "u_short_cint_operand" "")))
12129 (set (match_operand:SI 0 "gpc_reg_operand" "")
12130 (plus:SI (match_dup 1) (match_operand:SI 4 "short_cint_operand" "")))]
12132 [(set (match_dup 3) (compare:CCUNS (match_dup 1) (match_dup 2)))
12133 (set (match_dup 0) (plus:SI (match_dup 1) (match_dup 4)))])
12135 ;; Only need to compare second words if first words equal
12136 (define_insn "*cmptf_internal1"
12137 [(set (match_operand:CCFP 0 "cc_reg_operand" "=y")
12138 (compare:CCFP (match_operand:TF 1 "gpc_reg_operand" "d")
12139 (match_operand:TF 2 "gpc_reg_operand" "d")))]
12140 "!TARGET_IEEEQUAD && !TARGET_XL_COMPAT
12141 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_LONG_DOUBLE_128"
12142 "fcmpu %0,%1,%2\;bne %0,$+8\;fcmpu %0,%L1,%L2"
12143 [(set_attr "type" "fpcompare")
12144 (set_attr "length" "12")])
12146 (define_insn_and_split "*cmptf_internal2"
12147 [(set (match_operand:CCFP 0 "cc_reg_operand" "=y")
12148 (compare:CCFP (match_operand:TF 1 "gpc_reg_operand" "d")
12149 (match_operand:TF 2 "gpc_reg_operand" "d")))
12150 (clobber (match_scratch:DF 3 "=d"))
12151 (clobber (match_scratch:DF 4 "=d"))
12152 (clobber (match_scratch:DF 5 "=d"))
12153 (clobber (match_scratch:DF 6 "=d"))
12154 (clobber (match_scratch:DF 7 "=d"))
12155 (clobber (match_scratch:DF 8 "=d"))
12156 (clobber (match_scratch:DF 9 "=d"))
12157 (clobber (match_scratch:DF 10 "=d"))
12158 (clobber (match_scratch:GPR 11 "=b"))]
12159 "!TARGET_IEEEQUAD && TARGET_XL_COMPAT
12160 && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_DOUBLE_FLOAT && TARGET_LONG_DOUBLE_128"
12162 "&& reload_completed"
12163 [(set (match_dup 3) (match_dup 14))
12164 (set (match_dup 4) (match_dup 15))
12165 (set (match_dup 9) (abs:DF (match_dup 5)))
12166 (set (match_dup 0) (compare:CCFP (match_dup 9) (match_dup 3)))
12167 (set (pc) (if_then_else (ne (match_dup 0) (const_int 0))
12168 (label_ref (match_dup 12))
12170 (set (match_dup 0) (compare:CCFP (match_dup 5) (match_dup 7)))
12171 (set (pc) (label_ref (match_dup 13)))
12173 (set (match_dup 10) (minus:DF (match_dup 5) (match_dup 7)))
12174 (set (match_dup 9) (minus:DF (match_dup 6) (match_dup 8)))
12175 (set (match_dup 9) (plus:DF (match_dup 10) (match_dup 9)))
12176 (set (match_dup 0) (compare:CCFP (match_dup 9) (match_dup 4)))
12179 REAL_VALUE_TYPE rv;
12180 const int lo_word = LONG_DOUBLE_LARGE_FIRST ? GET_MODE_SIZE (DFmode) : 0;
12181 const int hi_word = LONG_DOUBLE_LARGE_FIRST ? 0 : GET_MODE_SIZE (DFmode);
12183 operands[5] = simplify_gen_subreg (DFmode, operands[1], TFmode, hi_word);
12184 operands[6] = simplify_gen_subreg (DFmode, operands[1], TFmode, lo_word);
12185 operands[7] = simplify_gen_subreg (DFmode, operands[2], TFmode, hi_word);
12186 operands[8] = simplify_gen_subreg (DFmode, operands[2], TFmode, lo_word);
12187 operands[12] = gen_label_rtx ();
12188 operands[13] = gen_label_rtx ();
12190 operands[14] = force_const_mem (DFmode,
12191 CONST_DOUBLE_FROM_REAL_VALUE (rv, DFmode));
12192 operands[15] = force_const_mem (DFmode,
12193 CONST_DOUBLE_FROM_REAL_VALUE (dconst0,
12198 tocref = create_TOC_reference (XEXP (operands[14], 0), operands[11]);
12199 operands[14] = gen_const_mem (DFmode, tocref);
12200 tocref = create_TOC_reference (XEXP (operands[15], 0), operands[11]);
12201 operands[15] = gen_const_mem (DFmode, tocref);
12202 set_mem_alias_set (operands[14], get_TOC_alias_set ());
12203 set_mem_alias_set (operands[15], get_TOC_alias_set ());
12207 ;; Now we have the scc insns. We can do some combinations because of the
12208 ;; way the machine works.
12210 ;; Note that this is probably faster if we can put an insn between the
12211 ;; mfcr and rlinm, but this is tricky. Let's leave it for now. In most
12212 ;; cases the insns below which don't use an intermediate CR field will
12213 ;; be used instead.
12215 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
12216 (match_operator:SI 1 "scc_comparison_operator"
12217 [(match_operand 2 "cc_reg_operand" "y")
12220 "mfcr %0%Q2\;rlwinm %0,%0,%J1,1"
12221 [(set (attr "type")
12222 (cond [(match_test "TARGET_MFCRF")
12223 (const_string "mfcrf")
12225 (const_string "mfcr")))
12226 (set_attr "length" "8")])
12228 ;; Same as above, but get the GT bit.
12229 (define_insn "move_from_CR_gt_bit"
12230 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
12231 (unspec:SI [(match_operand 1 "cc_reg_operand" "y")] UNSPEC_MV_CR_GT))]
12232 "TARGET_HARD_FLOAT && !TARGET_FPRS"
12233 "mfcr %0\;rlwinm %0,%0,%D1,31,31"
12234 [(set_attr "type" "mfcr")
12235 (set_attr "length" "8")])
12237 ;; Same as above, but get the OV/ORDERED bit.
12238 (define_insn "move_from_CR_ov_bit"
12239 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
12240 (unspec:SI [(match_operand:CC 1 "cc_reg_operand" "y")]
12243 "mfcr %0\;rlwinm %0,%0,%t1,1"
12244 [(set_attr "type" "mfcr")
12245 (set_attr "length" "8")])
12248 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
12249 (match_operator:DI 1 "scc_comparison_operator"
12250 [(match_operand 2 "cc_reg_operand" "y")
12253 "mfcr %0%Q2\;rlwinm %0,%0,%J1,1"
12254 [(set (attr "type")
12255 (cond [(match_test "TARGET_MFCRF")
12256 (const_string "mfcrf")
12258 (const_string "mfcr")))
12259 (set_attr "length" "8")])
12262 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
12263 (compare:CC (match_operator:SI 1 "scc_comparison_operator"
12264 [(match_operand 2 "cc_reg_operand" "y,y")
12267 (set (match_operand:SI 3 "gpc_reg_operand" "=r,r")
12268 (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
12271 mfcr %3%Q2\;rlwinm. %3,%3,%J1,1
12273 [(set_attr "type" "shift")
12274 (set_attr "dot" "yes")
12275 (set_attr "length" "8,16")])
12278 [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "")
12279 (compare:CC (match_operator:SI 1 "scc_comparison_operator"
12280 [(match_operand 2 "cc_reg_operand" "")
12283 (set (match_operand:SI 3 "gpc_reg_operand" "")
12284 (match_op_dup 1 [(match_dup 2) (const_int 0)]))]
12285 "TARGET_32BIT && reload_completed"
12286 [(set (match_dup 3)
12287 (match_op_dup 1 [(match_dup 2) (const_int 0)]))
12289 (compare:CC (match_dup 3)
12294 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
12295 (ashift:SI (match_operator:SI 1 "scc_comparison_operator"
12296 [(match_operand 2 "cc_reg_operand" "y")
12298 (match_operand:SI 3 "const_int_operand" "n")))]
12302 int is_bit = ccr_bit (operands[1], 1);
12303 int put_bit = 31 - (INTVAL (operands[3]) & 31);
12306 if (is_bit >= put_bit)
12307 count = is_bit - put_bit;
12309 count = 32 - (put_bit - is_bit);
12311 operands[4] = GEN_INT (count);
12312 operands[5] = GEN_INT (put_bit);
12314 return \"mfcr %0%Q2\;rlwinm %0,%0,%4,%5,%5\";
12316 [(set (attr "type")
12317 (cond [(match_test "TARGET_MFCRF")
12318 (const_string "mfcrf")
12320 (const_string "mfcr")))
12321 (set_attr "length" "8")])
12324 [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y")
12326 (ashift:SI (match_operator:SI 1 "scc_comparison_operator"
12327 [(match_operand 2 "cc_reg_operand" "y,y")
12329 (match_operand:SI 3 "const_int_operand" "n,n"))
12331 (set (match_operand:SI 4 "gpc_reg_operand" "=r,r")
12332 (ashift:SI (match_op_dup 1 [(match_dup 2) (const_int 0)])
12337 int is_bit = ccr_bit (operands[1], 1);
12338 int put_bit = 31 - (INTVAL (operands[3]) & 31);
12341 /* Force split for non-cc0 compare. */
12342 if (which_alternative == 1)
12345 if (is_bit >= put_bit)
12346 count = is_bit - put_bit;
12348 count = 32 - (put_bit - is_bit);
12350 operands[5] = GEN_INT (count);
12351 operands[6] = GEN_INT (put_bit);
12353 return \"mfcr %4%Q2\;rlwinm. %4,%4,%5,%6,%6\";
12355 [(set_attr "type" "shift")
12356 (set_attr "dot" "yes")
12357 (set_attr "length" "8,16")])
12360 [(set (match_operand:CC 0 "cc_reg_not_micro_cr0_operand" "")
12362 (ashift:SI (match_operator:SI 1 "scc_comparison_operator"
12363 [(match_operand 2 "cc_reg_operand" "")
12365 (match_operand:SI 3 "const_int_operand" ""))
12367 (set (match_operand:SI 4 "gpc_reg_operand" "")
12368 (ashift:SI (match_op_dup 1 [(match_dup 2) (const_int 0)])
12371 [(set (match_dup 4)
12372 (ashift:SI (match_op_dup 1 [(match_dup 2) (const_int 0)])
12375 (compare:CC (match_dup 4)
12379 ;; There is a 3 cycle delay between consecutive mfcr instructions
12380 ;; so it is useful to combine 2 scc instructions to use only one mfcr.
12383 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
12384 (match_operator:SI 1 "scc_comparison_operator"
12385 [(match_operand 2 "cc_reg_operand" "y")
12387 (set (match_operand:SI 3 "gpc_reg_operand" "=r")
12388 (match_operator:SI 4 "scc_comparison_operator"
12389 [(match_operand 5 "cc_reg_operand" "y")
12391 "REGNO (operands[2]) != REGNO (operands[5])"
12392 "mfcr %3\;rlwinm %0,%3,%J1,1\;rlwinm %3,%3,%J4,1"
12393 [(set_attr "type" "mfcr")
12394 (set_attr "length" "12")])
12397 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
12398 (match_operator:DI 1 "scc_comparison_operator"
12399 [(match_operand 2 "cc_reg_operand" "y")
12401 (set (match_operand:DI 3 "gpc_reg_operand" "=r")
12402 (match_operator:DI 4 "scc_comparison_operator"
12403 [(match_operand 5 "cc_reg_operand" "y")
12405 "TARGET_POWERPC64 && REGNO (operands[2]) != REGNO (operands[5])"
12406 "mfcr %3\;rlwinm %0,%3,%J1,1\;rlwinm %3,%3,%J4,1"
12407 [(set_attr "type" "mfcr")
12408 (set_attr "length" "12")])
12411 (define_mode_attr scc_eq_op2 [(SI "rKLI")
12414 (define_insn_and_split "eq<mode>3"
12415 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
12416 (eq:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")
12417 (match_operand:GPR 2 "scc_eq_operand" "<scc_eq_op2>")))
12418 (clobber (match_scratch:GPR 3 "=r"))
12419 (clobber (match_scratch:GPR 4 "=r"))]
12423 [(set (match_dup 4)
12424 (clz:GPR (match_dup 3)))
12426 (lshiftrt:GPR (match_dup 4)
12429 operands[3] = rs6000_emit_eqne (<MODE>mode,
12430 operands[1], operands[2], operands[3]);
12432 if (GET_CODE (operands[4]) == SCRATCH)
12433 operands[4] = gen_reg_rtx (<MODE>mode);
12435 operands[5] = GEN_INT (exact_log2 (GET_MODE_BITSIZE (<MODE>mode)));
12437 [(set (attr "length")
12438 (if_then_else (match_test "operands[2] == const0_rtx")
12440 (const_string "12")))])
12442 (define_insn_and_split "ne<mode>3"
12443 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
12444 (ne:P (match_operand:P 1 "gpc_reg_operand" "r")
12445 (match_operand:P 2 "scc_eq_operand" "<scc_eq_op2>")))
12446 (clobber (match_scratch:P 3 "=r"))
12447 (clobber (match_scratch:P 4 "=r"))
12448 (clobber (reg:P CA_REGNO))]
12452 [(parallel [(set (match_dup 4)
12453 (plus:P (match_dup 3)
12455 (set (reg:P CA_REGNO)
12456 (ne:P (match_dup 3)
12458 (parallel [(set (match_dup 0)
12459 (plus:P (plus:P (not:P (match_dup 4))
12462 (clobber (reg:P CA_REGNO))])]
12464 operands[3] = rs6000_emit_eqne (<MODE>mode,
12465 operands[1], operands[2], operands[3]);
12467 if (GET_CODE (operands[4]) == SCRATCH)
12468 operands[4] = gen_reg_rtx (<MODE>mode);
12470 [(set (attr "length")
12471 (if_then_else (match_test "operands[2] == const0_rtx")
12473 (const_string "12")))])
12475 (define_insn_and_split "*neg_eq_<mode>"
12476 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
12477 (neg:P (eq:P (match_operand:P 1 "gpc_reg_operand" "r")
12478 (match_operand:P 2 "scc_eq_operand" "<scc_eq_op2>"))))
12479 (clobber (match_scratch:P 3 "=r"))
12480 (clobber (match_scratch:P 4 "=r"))
12481 (clobber (reg:P CA_REGNO))]
12485 [(parallel [(set (match_dup 4)
12486 (plus:P (match_dup 3)
12488 (set (reg:P CA_REGNO)
12489 (ne:P (match_dup 3)
12491 (parallel [(set (match_dup 0)
12492 (plus:P (reg:P CA_REGNO)
12494 (clobber (reg:P CA_REGNO))])]
12496 operands[3] = rs6000_emit_eqne (<MODE>mode,
12497 operands[1], operands[2], operands[3]);
12499 if (GET_CODE (operands[4]) == SCRATCH)
12500 operands[4] = gen_reg_rtx (<MODE>mode);
12502 [(set (attr "length")
12503 (if_then_else (match_test "operands[2] == const0_rtx")
12505 (const_string "12")))])
12507 (define_insn_and_split "*neg_ne_<mode>"
12508 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
12509 (neg:P (ne:P (match_operand:P 1 "gpc_reg_operand" "r")
12510 (match_operand:P 2 "scc_eq_operand" "<scc_eq_op2>"))))
12511 (clobber (match_scratch:P 3 "=r"))
12512 (clobber (match_scratch:P 4 "=r"))
12513 (clobber (reg:P CA_REGNO))]
12517 [(parallel [(set (match_dup 4)
12518 (neg:P (match_dup 3)))
12519 (set (reg:P CA_REGNO)
12520 (eq:P (match_dup 3)
12522 (parallel [(set (match_dup 0)
12523 (plus:P (reg:P CA_REGNO)
12525 (clobber (reg:P CA_REGNO))])]
12527 operands[3] = rs6000_emit_eqne (<MODE>mode,
12528 operands[1], operands[2], operands[3]);
12530 if (GET_CODE (operands[4]) == SCRATCH)
12531 operands[4] = gen_reg_rtx (<MODE>mode);
12533 [(set (attr "length")
12534 (if_then_else (match_test "operands[2] == const0_rtx")
12536 (const_string "12")))])
12538 (define_insn_and_split "*plus_eq_<mode>"
12539 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
12540 (plus:P (eq:P (match_operand:P 1 "gpc_reg_operand" "r")
12541 (match_operand:P 2 "scc_eq_operand" "<scc_eq_op2>"))
12542 (match_operand:P 3 "gpc_reg_operand" "r")))
12543 (clobber (match_scratch:P 4 "=r"))
12544 (clobber (match_scratch:P 5 "=r"))
12545 (clobber (reg:P CA_REGNO))]
12549 [(parallel [(set (match_dup 5)
12550 (neg:P (match_dup 4)))
12551 (set (reg:P CA_REGNO)
12552 (eq:P (match_dup 4)
12554 (parallel [(set (match_dup 0)
12555 (plus:P (match_dup 3)
12557 (clobber (reg:P CA_REGNO))])]
12559 operands[4] = rs6000_emit_eqne (<MODE>mode,
12560 operands[1], operands[2], operands[4]);
12562 if (GET_CODE (operands[5]) == SCRATCH)
12563 operands[5] = gen_reg_rtx (<MODE>mode);
12565 [(set (attr "length")
12566 (if_then_else (match_test "operands[2] == const0_rtx")
12568 (const_string "12")))])
12570 (define_insn_and_split "*plus_ne_<mode>"
12571 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
12572 (plus:P (ne:P (match_operand:P 1 "gpc_reg_operand" "r")
12573 (match_operand:P 2 "scc_eq_operand" "<scc_eq_op2>"))
12574 (match_operand:P 3 "gpc_reg_operand" "r")))
12575 (clobber (match_scratch:P 4 "=r"))
12576 (clobber (match_scratch:P 5 "=r"))
12577 (clobber (reg:P CA_REGNO))]
12581 [(parallel [(set (match_dup 5)
12582 (plus:P (match_dup 4)
12584 (set (reg:P CA_REGNO)
12585 (ne:P (match_dup 4)
12587 (parallel [(set (match_dup 0)
12588 (plus:P (match_dup 3)
12590 (clobber (reg:P CA_REGNO))])]
12592 operands[4] = rs6000_emit_eqne (<MODE>mode,
12593 operands[1], operands[2], operands[4]);
12595 if (GET_CODE (operands[5]) == SCRATCH)
12596 operands[5] = gen_reg_rtx (<MODE>mode);
12598 [(set (attr "length")
12599 (if_then_else (match_test "operands[2] == const0_rtx")
12601 (const_string "12")))])
12603 (define_insn_and_split "*minus_eq_<mode>"
12604 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
12605 (minus:P (match_operand:P 3 "gpc_reg_operand" "r")
12606 (eq:P (match_operand:P 1 "gpc_reg_operand" "r")
12607 (match_operand:P 2 "scc_eq_operand" "<scc_eq_op2>"))))
12608 (clobber (match_scratch:P 4 "=r"))
12609 (clobber (match_scratch:P 5 "=r"))
12610 (clobber (reg:P CA_REGNO))]
12614 [(parallel [(set (match_dup 5)
12615 (plus:P (match_dup 4)
12617 (set (reg:P CA_REGNO)
12618 (ne:P (match_dup 4)
12620 (parallel [(set (match_dup 0)
12621 (plus:P (plus:P (match_dup 3)
12624 (clobber (reg:P CA_REGNO))])]
12626 operands[4] = rs6000_emit_eqne (<MODE>mode,
12627 operands[1], operands[2], operands[4]);
12629 if (GET_CODE (operands[5]) == SCRATCH)
12630 operands[5] = gen_reg_rtx (<MODE>mode);
12632 [(set (attr "length")
12633 (if_then_else (match_test "operands[2] == const0_rtx")
12635 (const_string "12")))])
12637 (define_insn_and_split "*minus_ne_<mode>"
12638 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
12639 (minus:P (match_operand:P 3 "gpc_reg_operand" "r")
12640 (ne:P (match_operand:P 1 "gpc_reg_operand" "r")
12641 (match_operand:P 2 "scc_eq_operand" "<scc_eq_op2>"))))
12642 (clobber (match_scratch:P 4 "=r"))
12643 (clobber (match_scratch:P 5 "=r"))
12644 (clobber (reg:P CA_REGNO))]
12648 [(parallel [(set (match_dup 5)
12649 (neg:P (match_dup 4)))
12650 (set (reg:P CA_REGNO)
12651 (eq:P (match_dup 4)
12653 (parallel [(set (match_dup 0)
12654 (plus:P (plus:P (match_dup 3)
12657 (clobber (reg:P CA_REGNO))])]
12659 operands[4] = rs6000_emit_eqne (<MODE>mode,
12660 operands[1], operands[2], operands[4]);
12662 if (GET_CODE (operands[5]) == SCRATCH)
12663 operands[5] = gen_reg_rtx (<MODE>mode);
12665 [(set (attr "length")
12666 (if_then_else (match_test "operands[2] == const0_rtx")
12668 (const_string "12")))])
12670 (define_insn_and_split "*eqsi3_ext<mode>"
12671 [(set (match_operand:EXTSI 0 "gpc_reg_operand" "=r")
12672 (eq:EXTSI (match_operand:SI 1 "gpc_reg_operand" "r")
12673 (match_operand:SI 2 "scc_eq_operand" "rKLI")))
12674 (clobber (match_scratch:SI 3 "=r"))
12675 (clobber (match_scratch:SI 4 "=r"))]
12679 [(set (match_dup 4)
12680 (clz:SI (match_dup 3)))
12683 (lshiftrt:SI (match_dup 4)
12686 operands[3] = rs6000_emit_eqne (SImode,
12687 operands[1], operands[2], operands[3]);
12689 if (GET_CODE (operands[4]) == SCRATCH)
12690 operands[4] = gen_reg_rtx (SImode);
12692 [(set (attr "length")
12693 (if_then_else (match_test "operands[2] == const0_rtx")
12695 (const_string "12")))])
12697 (define_insn_and_split "*nesi3_ext<mode>"
12698 [(set (match_operand:EXTSI 0 "gpc_reg_operand" "=r")
12699 (ne:EXTSI (match_operand:SI 1 "gpc_reg_operand" "r")
12700 (match_operand:SI 2 "scc_eq_operand" "rKLI")))
12701 (clobber (match_scratch:SI 3 "=r"))
12702 (clobber (match_scratch:SI 4 "=r"))
12703 (clobber (match_scratch:EXTSI 5 "=r"))]
12707 [(set (match_dup 4)
12708 (clz:SI (match_dup 3)))
12711 (lshiftrt:SI (match_dup 4)
12714 (xor:EXTSI (match_dup 5)
12717 operands[3] = rs6000_emit_eqne (SImode,
12718 operands[1], operands[2], operands[3]);
12720 if (GET_CODE (operands[4]) == SCRATCH)
12721 operands[4] = gen_reg_rtx (SImode);
12722 if (GET_CODE (operands[5]) == SCRATCH)
12723 operands[5] = gen_reg_rtx (<MODE>mode);
12725 [(set (attr "length")
12726 (if_then_else (match_test "operands[2] == const0_rtx")
12727 (const_string "12")
12728 (const_string "16")))])
12730 ;; Define both directions of branch and return. If we need a reload
12731 ;; register, we'd rather use CR0 since it is much easier to copy a
12732 ;; register CC value to there.
12736 (if_then_else (match_operator 1 "branch_comparison_operator"
12738 "cc_reg_operand" "y")
12740 (label_ref (match_operand 0 "" ""))
12745 return output_cbranch (operands[1], \"%l0\", 0, insn);
12747 [(set_attr "type" "branch")])
12751 (if_then_else (match_operator 0 "branch_comparison_operator"
12753 "cc_reg_operand" "y")
12760 return output_cbranch (operands[0], NULL, 0, insn);
12762 [(set_attr "type" "jmpreg")
12763 (set_attr "length" "4")])
12767 (if_then_else (match_operator 1 "branch_comparison_operator"
12769 "cc_reg_operand" "y")
12772 (label_ref (match_operand 0 "" ""))))]
12776 return output_cbranch (operands[1], \"%l0\", 1, insn);
12778 [(set_attr "type" "branch")])
12782 (if_then_else (match_operator 0 "branch_comparison_operator"
12784 "cc_reg_operand" "y")
12791 return output_cbranch (operands[0], NULL, 1, insn);
12793 [(set_attr "type" "jmpreg")
12794 (set_attr "length" "4")])
12796 ;; Logic on condition register values.
12798 ; This pattern matches things like
12799 ; (set (reg:CCEQ 68) (compare:CCEQ (ior:SI (gt:SI (reg:CCFP 68) (const_int 0))
12800 ; (eq:SI (reg:CCFP 68) (const_int 0)))
12802 ; which are generated by the branch logic.
12803 ; Prefer destructive operations where BT = BB (for crXX BT,BA,BB)
12805 (define_insn "*cceq_ior_compare"
12806 [(set (match_operand:CCEQ 0 "cc_reg_operand" "=y,?y")
12807 (compare:CCEQ (match_operator:SI 1 "boolean_operator"
12808 [(match_operator:SI 2
12809 "branch_positive_comparison_operator"
12811 "cc_reg_operand" "y,y")
12813 (match_operator:SI 4
12814 "branch_positive_comparison_operator"
12816 "cc_reg_operand" "0,y")
12820 "cr%q1 %E0,%j2,%j4"
12821 [(set_attr "type" "cr_logical,delayed_cr")])
12823 ; Why is the constant -1 here, but 1 in the previous pattern?
12824 ; Because ~1 has all but the low bit set.
12826 [(set (match_operand:CCEQ 0 "cc_reg_operand" "=y,?y")
12827 (compare:CCEQ (match_operator:SI 1 "boolean_or_operator"
12828 [(not:SI (match_operator:SI 2
12829 "branch_positive_comparison_operator"
12831 "cc_reg_operand" "y,y")
12833 (match_operator:SI 4
12834 "branch_positive_comparison_operator"
12836 "cc_reg_operand" "0,y")
12840 "cr%q1 %E0,%j2,%j4"
12841 [(set_attr "type" "cr_logical,delayed_cr")])
12843 (define_insn "*cceq_rev_compare"
12844 [(set (match_operand:CCEQ 0 "cc_reg_operand" "=y,?y")
12845 (compare:CCEQ (match_operator:SI 1
12846 "branch_positive_comparison_operator"
12848 "cc_reg_operand" "0,y")
12853 [(set_attr "type" "cr_logical,delayed_cr")])
12855 ;; If we are comparing the result of two comparisons, this can be done
12856 ;; using creqv or crxor.
12858 (define_insn_and_split ""
12859 [(set (match_operand:CCEQ 0 "cc_reg_operand" "=y")
12860 (compare:CCEQ (match_operator 1 "branch_comparison_operator"
12861 [(match_operand 2 "cc_reg_operand" "y")
12863 (match_operator 3 "branch_comparison_operator"
12864 [(match_operand 4 "cc_reg_operand" "y")
12869 [(set (match_dup 0) (compare:CCEQ (xor:SI (match_dup 1) (match_dup 3))
12873 int positive_1, positive_2;
12875 positive_1 = branch_positive_comparison_operator (operands[1],
12876 GET_MODE (operands[1]));
12877 positive_2 = branch_positive_comparison_operator (operands[3],
12878 GET_MODE (operands[3]));
12881 operands[1] = gen_rtx_fmt_ee (rs6000_reverse_condition (GET_MODE (operands[2]),
12882 GET_CODE (operands[1])),
12884 operands[2], const0_rtx);
12885 else if (GET_MODE (operands[1]) != SImode)
12886 operands[1] = gen_rtx_fmt_ee (GET_CODE (operands[1]), SImode,
12887 operands[2], const0_rtx);
12890 operands[3] = gen_rtx_fmt_ee (rs6000_reverse_condition (GET_MODE (operands[4]),
12891 GET_CODE (operands[3])),
12893 operands[4], const0_rtx);
12894 else if (GET_MODE (operands[3]) != SImode)
12895 operands[3] = gen_rtx_fmt_ee (GET_CODE (operands[3]), SImode,
12896 operands[4], const0_rtx);
12898 if (positive_1 == positive_2)
12900 operands[1] = gen_rtx_NOT (SImode, operands[1]);
12901 operands[5] = constm1_rtx;
12905 operands[5] = const1_rtx;
12909 ;; Unconditional branch and return.
12911 (define_insn "jump"
12913 (label_ref (match_operand 0 "" "")))]
12916 [(set_attr "type" "branch")])
12918 (define_insn "<return_str>return"
12922 [(set_attr "type" "jmpreg")])
12924 (define_expand "indirect_jump"
12925 [(set (pc) (match_operand 0 "register_operand" ""))])
12927 (define_insn "*indirect_jump<mode>"
12928 [(set (pc) (match_operand:P 0 "register_operand" "c,*l"))]
12933 [(set_attr "type" "jmpreg")])
12935 ;; Table jump for switch statements:
12936 (define_expand "tablejump"
12937 [(use (match_operand 0 "" ""))
12938 (use (label_ref (match_operand 1 "" "")))]
12943 emit_jump_insn (gen_tablejumpsi (operands[0], operands[1]));
12945 emit_jump_insn (gen_tablejumpdi (operands[0], operands[1]));
12949 (define_expand "tablejumpsi"
12950 [(set (match_dup 3)
12951 (plus:SI (match_operand:SI 0 "" "")
12953 (parallel [(set (pc) (match_dup 3))
12954 (use (label_ref (match_operand 1 "" "")))])]
12957 { operands[0] = force_reg (SImode, operands[0]);
12958 operands[2] = force_reg (SImode, gen_rtx_LABEL_REF (SImode, operands[1]));
12959 operands[3] = gen_reg_rtx (SImode);
12962 (define_expand "tablejumpdi"
12963 [(set (match_dup 4)
12964 (sign_extend:DI (match_operand:SI 0 "lwa_operand" "")))
12966 (plus:DI (match_dup 4)
12968 (parallel [(set (pc) (match_dup 3))
12969 (use (label_ref (match_operand 1 "" "")))])]
12972 { operands[2] = force_reg (DImode, gen_rtx_LABEL_REF (DImode, operands[1]));
12973 operands[3] = gen_reg_rtx (DImode);
12974 operands[4] = gen_reg_rtx (DImode);
12977 (define_insn "*tablejump<mode>_internal1"
12979 (match_operand:P 0 "register_operand" "c,*l"))
12980 (use (label_ref (match_operand 1 "" "")))]
12985 [(set_attr "type" "jmpreg")])
12988 [(unspec [(const_int 0)] UNSPEC_NOP)]
12992 (define_insn "group_ending_nop"
12993 [(unspec [(const_int 0)] UNSPEC_GRP_END_NOP)]
12997 if (rs6000_cpu_attr == CPU_POWER6)
12998 return \"ori 1,1,0\";
12999 return \"ori 2,2,0\";
13002 ;; Define the subtract-one-and-jump insns, starting with the template
13003 ;; so loop.c knows what to generate.
13005 (define_expand "doloop_end"
13006 [(use (match_operand 0 "" "")) ; loop pseudo
13007 (use (match_operand 1 "" ""))] ; label
13013 if (GET_MODE (operands[0]) != DImode)
13015 emit_jump_insn (gen_ctrdi (operands[0], operands[1]));
13019 if (GET_MODE (operands[0]) != SImode)
13021 emit_jump_insn (gen_ctrsi (operands[0], operands[1]));
13026 (define_expand "ctr<mode>"
13027 [(parallel [(set (pc)
13028 (if_then_else (ne (match_operand:P 0 "register_operand" "")
13030 (label_ref (match_operand 1 "" ""))
13033 (plus:P (match_dup 0)
13035 (clobber (match_scratch:CC 2 ""))
13036 (clobber (match_scratch:P 3 ""))])]
13040 ;; We need to be able to do this for any operand, including MEM, or we
13041 ;; will cause reload to blow up since we don't allow output reloads on
13043 ;; For the length attribute to be calculated correctly, the
13044 ;; label MUST be operand 0.
13046 (define_insn "*ctr<mode>_internal1"
13048 (if_then_else (ne (match_operand:P 1 "register_operand" "c,*b,*b,*b")
13050 (label_ref (match_operand 0 "" ""))
13052 (set (match_operand:P 2 "nonimmediate_operand" "=1,*r,m,*c*l")
13053 (plus:P (match_dup 1)
13055 (clobber (match_scratch:CC 3 "=X,&x,&x,&x"))
13056 (clobber (match_scratch:P 4 "=X,X,&r,r"))]
13060 if (which_alternative != 0)
13062 else if (get_attr_length (insn) == 4)
13063 return \"bdnz %l0\";
13065 return \"bdz $+8\;b %l0\";
13067 [(set_attr "type" "branch")
13068 (set_attr "length" "*,16,20,20")])
13070 (define_insn "*ctr<mode>_internal2"
13072 (if_then_else (ne (match_operand:P 1 "register_operand" "c,*b,*b,*b")
13075 (label_ref (match_operand 0 "" ""))))
13076 (set (match_operand:P 2 "nonimmediate_operand" "=1,*r,m,*c*l")
13077 (plus:P (match_dup 1)
13079 (clobber (match_scratch:CC 3 "=X,&x,&x,&x"))
13080 (clobber (match_scratch:P 4 "=X,X,&r,r"))]
13084 if (which_alternative != 0)
13086 else if (get_attr_length (insn) == 4)
13087 return \"bdz %l0\";
13089 return \"bdnz $+8\;b %l0\";
13091 [(set_attr "type" "branch")
13092 (set_attr "length" "*,16,20,20")])
13094 ;; Similar but use EQ
13096 (define_insn "*ctr<mode>_internal5"
13098 (if_then_else (eq (match_operand:P 1 "register_operand" "c,*b,*b,*b")
13100 (label_ref (match_operand 0 "" ""))
13102 (set (match_operand:P 2 "nonimmediate_operand" "=1,*r,m,*c*l")
13103 (plus:P (match_dup 1)
13105 (clobber (match_scratch:CC 3 "=X,&x,&x,&x"))
13106 (clobber (match_scratch:P 4 "=X,X,&r,r"))]
13110 if (which_alternative != 0)
13112 else if (get_attr_length (insn) == 4)
13113 return \"bdz %l0\";
13115 return \"bdnz $+8\;b %l0\";
13117 [(set_attr "type" "branch")
13118 (set_attr "length" "*,16,20,20")])
13120 (define_insn "*ctr<mode>_internal6"
13122 (if_then_else (eq (match_operand:P 1 "register_operand" "c,*b,*b,*b")
13125 (label_ref (match_operand 0 "" ""))))
13126 (set (match_operand:P 2 "nonimmediate_operand" "=1,*r,m,*c*l")
13127 (plus:P (match_dup 1)
13129 (clobber (match_scratch:CC 3 "=X,&x,&x,&x"))
13130 (clobber (match_scratch:P 4 "=X,X,&r,r"))]
13134 if (which_alternative != 0)
13136 else if (get_attr_length (insn) == 4)
13137 return \"bdnz %l0\";
13139 return \"bdz $+8\;b %l0\";
13141 [(set_attr "type" "branch")
13142 (set_attr "length" "*,16,20,20")])
13144 ;; Now the splitters if we could not allocate the CTR register
13148 (if_then_else (match_operator 2 "comparison_operator"
13149 [(match_operand:P 1 "gpc_reg_operand" "")
13151 (match_operand 5 "" "")
13152 (match_operand 6 "" "")))
13153 (set (match_operand:P 0 "gpc_reg_operand" "")
13154 (plus:P (match_dup 1) (const_int -1)))
13155 (clobber (match_scratch:CC 3 ""))
13156 (clobber (match_scratch:P 4 ""))]
13158 [(set (match_dup 3)
13159 (compare:CC (match_dup 1)
13162 (plus:P (match_dup 1)
13164 (set (pc) (if_then_else (match_dup 7)
13168 { operands[7] = gen_rtx_fmt_ee (GET_CODE (operands[2]), VOIDmode,
13169 operands[3], const0_rtx); }")
13173 (if_then_else (match_operator 2 "comparison_operator"
13174 [(match_operand:P 1 "gpc_reg_operand" "")
13176 (match_operand 5 "" "")
13177 (match_operand 6 "" "")))
13178 (set (match_operand:P 0 "nonimmediate_operand" "")
13179 (plus:P (match_dup 1) (const_int -1)))
13180 (clobber (match_scratch:CC 3 ""))
13181 (clobber (match_scratch:P 4 ""))]
13182 "reload_completed && ! gpc_reg_operand (operands[0], SImode)"
13183 [(set (match_dup 3)
13184 (compare:CC (match_dup 1)
13187 (plus:P (match_dup 1)
13191 (set (pc) (if_then_else (match_dup 7)
13195 { operands[7] = gen_rtx_fmt_ee (GET_CODE (operands[2]), VOIDmode,
13196 operands[3], const0_rtx); }")
13198 (define_insn "trap"
13199 [(trap_if (const_int 1) (const_int 0))]
13202 [(set_attr "type" "trap")])
13204 (define_expand "ctrap<mode>4"
13205 [(trap_if (match_operator 0 "ordered_comparison_operator"
13206 [(match_operand:GPR 1 "register_operand")
13207 (match_operand:GPR 2 "reg_or_short_operand")])
13208 (match_operand 3 "zero_constant" ""))]
13213 [(trap_if (match_operator 0 "ordered_comparison_operator"
13214 [(match_operand:GPR 1 "register_operand" "r")
13215 (match_operand:GPR 2 "reg_or_short_operand" "rI")])
13218 "t<wd>%V0%I2 %1,%2"
13219 [(set_attr "type" "trap")])
13221 ;; Insns related to generating the function prologue and epilogue.
13223 (define_expand "prologue"
13224 [(use (const_int 0))]
13227 rs6000_emit_prologue ();
13228 if (!TARGET_SCHED_PROLOG)
13229 emit_insn (gen_blockage ());
13233 (define_insn "*movesi_from_cr_one"
13234 [(match_parallel 0 "mfcr_operation"
13235 [(set (match_operand:SI 1 "gpc_reg_operand" "=r")
13236 (unspec:SI [(match_operand:CC 2 "cc_reg_operand" "y")
13237 (match_operand 3 "immediate_operand" "n")]
13238 UNSPEC_MOVESI_FROM_CR))])]
13244 for (i = 0; i < XVECLEN (operands[0], 0); i++)
13246 mask = INTVAL (XVECEXP (SET_SRC (XVECEXP (operands[0], 0, i)), 0, 1));
13247 operands[4] = GEN_INT (mask);
13248 output_asm_insn (\"mfcr %1,%4\", operands);
13252 [(set_attr "type" "mfcrf")])
13254 (define_insn "movesi_from_cr"
13255 [(set (match_operand:SI 0 "gpc_reg_operand" "=r")
13256 (unspec:SI [(reg:CC CR0_REGNO) (reg:CC CR1_REGNO)
13257 (reg:CC CR2_REGNO) (reg:CC CR3_REGNO)
13258 (reg:CC CR4_REGNO) (reg:CC CR5_REGNO)
13259 (reg:CC CR6_REGNO) (reg:CC CR7_REGNO)]
13260 UNSPEC_MOVESI_FROM_CR))]
13263 [(set_attr "type" "mfcr")])
13265 (define_insn "*crsave"
13266 [(match_parallel 0 "crsave_operation"
13267 [(set (match_operand:SI 1 "memory_operand" "=m")
13268 (match_operand:SI 2 "gpc_reg_operand" "r"))])]
13271 [(set_attr "type" "store")])
13273 (define_insn "*stmw"
13274 [(match_parallel 0 "stmw_operation"
13275 [(set (match_operand:SI 1 "memory_operand" "=m")
13276 (match_operand:SI 2 "gpc_reg_operand" "r"))])]
13279 [(set_attr "type" "store")
13280 (set_attr "update" "yes")
13281 (set_attr "indexed" "yes")])
13283 ; The following comment applies to:
13287 ; return_and_restore_gpregs*
13288 ; return_and_restore_fpregs*
13289 ; return_and_restore_fpregs_aix*
13291 ; The out-of-line save / restore functions expects one input argument.
13292 ; Since those are not standard call_insn's, we must avoid using
13293 ; MATCH_OPERAND for that argument. That way the register rename
13294 ; optimization will not try to rename this register.
13295 ; Each pattern is repeated for each possible register number used in
13296 ; various ABIs (r11, r1, and for some functions r12)
13298 (define_insn "*save_gpregs_<mode>_r11"
13299 [(match_parallel 0 "any_parallel_operand"
13300 [(clobber (reg:P 65))
13301 (use (match_operand:P 1 "symbol_ref_operand" "s"))
13303 (set (match_operand:P 2 "memory_operand" "=m")
13304 (match_operand:P 3 "gpc_reg_operand" "r"))])]
13307 [(set_attr "type" "branch")
13308 (set_attr "length" "4")])
13310 (define_insn "*save_gpregs_<mode>_r12"
13311 [(match_parallel 0 "any_parallel_operand"
13312 [(clobber (reg:P 65))
13313 (use (match_operand:P 1 "symbol_ref_operand" "s"))
13315 (set (match_operand:P 2 "memory_operand" "=m")
13316 (match_operand:P 3 "gpc_reg_operand" "r"))])]
13319 [(set_attr "type" "branch")
13320 (set_attr "length" "4")])
13322 (define_insn "*save_gpregs_<mode>_r1"
13323 [(match_parallel 0 "any_parallel_operand"
13324 [(clobber (reg:P 65))
13325 (use (match_operand:P 1 "symbol_ref_operand" "s"))
13327 (set (match_operand:P 2 "memory_operand" "=m")
13328 (match_operand:P 3 "gpc_reg_operand" "r"))])]
13331 [(set_attr "type" "branch")
13332 (set_attr "length" "4")])
13334 (define_insn "*save_fpregs_<mode>_r11"
13335 [(match_parallel 0 "any_parallel_operand"
13336 [(clobber (reg:P 65))
13337 (use (match_operand:P 1 "symbol_ref_operand" "s"))
13339 (set (match_operand:DF 2 "memory_operand" "=m")
13340 (match_operand:DF 3 "gpc_reg_operand" "d"))])]
13343 [(set_attr "type" "branch")
13344 (set_attr "length" "4")])
13346 (define_insn "*save_fpregs_<mode>_r12"
13347 [(match_parallel 0 "any_parallel_operand"
13348 [(clobber (reg:P 65))
13349 (use (match_operand:P 1 "symbol_ref_operand" "s"))
13351 (set (match_operand:DF 2 "memory_operand" "=m")
13352 (match_operand:DF 3 "gpc_reg_operand" "d"))])]
13355 [(set_attr "type" "branch")
13356 (set_attr "length" "4")])
13358 (define_insn "*save_fpregs_<mode>_r1"
13359 [(match_parallel 0 "any_parallel_operand"
13360 [(clobber (reg:P 65))
13361 (use (match_operand:P 1 "symbol_ref_operand" "s"))
13363 (set (match_operand:DF 2 "memory_operand" "=m")
13364 (match_operand:DF 3 "gpc_reg_operand" "d"))])]
13367 [(set_attr "type" "branch")
13368 (set_attr "length" "4")])
13370 ; This is to explain that changes to the stack pointer should
13371 ; not be moved over loads from or stores to stack memory.
13372 (define_insn "stack_tie"
13373 [(match_parallel 0 "tie_operand"
13374 [(set (mem:BLK (reg 1)) (const_int 0))])]
13377 [(set_attr "length" "0")])
13379 (define_expand "epilogue"
13380 [(use (const_int 0))]
13383 if (!TARGET_SCHED_PROLOG)
13384 emit_insn (gen_blockage ());
13385 rs6000_emit_epilogue (FALSE);
13389 ; On some processors, doing the mtcrf one CC register at a time is
13390 ; faster (like on the 604e). On others, doing them all at once is
13391 ; faster; for instance, on the 601 and 750.
13393 (define_expand "movsi_to_cr_one"
13394 [(set (match_operand:CC 0 "cc_reg_operand" "")
13395 (unspec:CC [(match_operand:SI 1 "gpc_reg_operand" "")
13396 (match_dup 2)] UNSPEC_MOVESI_TO_CR))]
13398 "operands[2] = GEN_INT (1 << (75 - REGNO (operands[0])));")
13400 (define_insn "*movsi_to_cr"
13401 [(match_parallel 0 "mtcrf_operation"
13402 [(set (match_operand:CC 1 "cc_reg_operand" "=y")
13403 (unspec:CC [(match_operand:SI 2 "gpc_reg_operand" "r")
13404 (match_operand 3 "immediate_operand" "n")]
13405 UNSPEC_MOVESI_TO_CR))])]
13411 for (i = 0; i < XVECLEN (operands[0], 0); i++)
13412 mask |= INTVAL (XVECEXP (SET_SRC (XVECEXP (operands[0], 0, i)), 0, 1));
13413 operands[4] = GEN_INT (mask);
13414 return \"mtcrf %4,%2\";
13416 [(set_attr "type" "mtcr")])
13418 (define_insn "*mtcrfsi"
13419 [(set (match_operand:CC 0 "cc_reg_operand" "=y")
13420 (unspec:CC [(match_operand:SI 1 "gpc_reg_operand" "r")
13421 (match_operand 2 "immediate_operand" "n")]
13422 UNSPEC_MOVESI_TO_CR))]
13423 "GET_CODE (operands[0]) == REG
13424 && CR_REGNO_P (REGNO (operands[0]))
13425 && GET_CODE (operands[2]) == CONST_INT
13426 && INTVAL (operands[2]) == 1 << (75 - REGNO (operands[0]))"
13428 [(set_attr "type" "mtcr")])
13430 ; The load-multiple instructions have similar properties.
13431 ; Note that "load_multiple" is a name known to the machine-independent
13432 ; code that actually corresponds to the PowerPC load-string.
13434 (define_insn "*lmw"
13435 [(match_parallel 0 "lmw_operation"
13436 [(set (match_operand:SI 1 "gpc_reg_operand" "=r")
13437 (match_operand:SI 2 "memory_operand" "m"))])]
13440 [(set_attr "type" "load")
13441 (set_attr "update" "yes")
13442 (set_attr "indexed" "yes")
13443 (set_attr "cell_micro" "always")])
13445 (define_insn "*return_internal_<mode>"
13447 (use (match_operand:P 0 "register_operand" "lc"))]
13450 [(set_attr "type" "jmpreg")])
13452 ; FIXME: This would probably be somewhat simpler if the Cygnus sibcall
13453 ; stuff was in GCC. Oh, and "any_parallel_operand" is a bit flexible...
13455 ; The following comment applies to:
13459 ; return_and_restore_gpregs*
13460 ; return_and_restore_fpregs*
13461 ; return_and_restore_fpregs_aix*
13463 ; The out-of-line save / restore functions expects one input argument.
13464 ; Since those are not standard call_insn's, we must avoid using
13465 ; MATCH_OPERAND for that argument. That way the register rename
13466 ; optimization will not try to rename this register.
13467 ; Each pattern is repeated for each possible register number used in
13468 ; various ABIs (r11, r1, and for some functions r12)
13470 (define_insn "*restore_gpregs_<mode>_r11"
13471 [(match_parallel 0 "any_parallel_operand"
13472 [(clobber (match_operand:P 1 "register_operand" "=l"))
13473 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13475 (set (match_operand:P 3 "gpc_reg_operand" "=r")
13476 (match_operand:P 4 "memory_operand" "m"))])]
13479 [(set_attr "type" "branch")
13480 (set_attr "length" "4")])
13482 (define_insn "*restore_gpregs_<mode>_r12"
13483 [(match_parallel 0 "any_parallel_operand"
13484 [(clobber (match_operand:P 1 "register_operand" "=l"))
13485 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13487 (set (match_operand:P 3 "gpc_reg_operand" "=r")
13488 (match_operand:P 4 "memory_operand" "m"))])]
13491 [(set_attr "type" "branch")
13492 (set_attr "length" "4")])
13494 (define_insn "*restore_gpregs_<mode>_r1"
13495 [(match_parallel 0 "any_parallel_operand"
13496 [(clobber (match_operand:P 1 "register_operand" "=l"))
13497 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13499 (set (match_operand:P 3 "gpc_reg_operand" "=r")
13500 (match_operand:P 4 "memory_operand" "m"))])]
13503 [(set_attr "type" "branch")
13504 (set_attr "length" "4")])
13506 (define_insn "*return_and_restore_gpregs_<mode>_r11"
13507 [(match_parallel 0 "any_parallel_operand"
13509 (clobber (match_operand:P 1 "register_operand" "=l"))
13510 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13512 (set (match_operand:P 3 "gpc_reg_operand" "=r")
13513 (match_operand:P 4 "memory_operand" "m"))])]
13516 [(set_attr "type" "branch")
13517 (set_attr "length" "4")])
13519 (define_insn "*return_and_restore_gpregs_<mode>_r12"
13520 [(match_parallel 0 "any_parallel_operand"
13522 (clobber (match_operand:P 1 "register_operand" "=l"))
13523 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13525 (set (match_operand:P 3 "gpc_reg_operand" "=r")
13526 (match_operand:P 4 "memory_operand" "m"))])]
13529 [(set_attr "type" "branch")
13530 (set_attr "length" "4")])
13532 (define_insn "*return_and_restore_gpregs_<mode>_r1"
13533 [(match_parallel 0 "any_parallel_operand"
13535 (clobber (match_operand:P 1 "register_operand" "=l"))
13536 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13538 (set (match_operand:P 3 "gpc_reg_operand" "=r")
13539 (match_operand:P 4 "memory_operand" "m"))])]
13542 [(set_attr "type" "branch")
13543 (set_attr "length" "4")])
13545 (define_insn "*return_and_restore_fpregs_<mode>_r11"
13546 [(match_parallel 0 "any_parallel_operand"
13548 (clobber (match_operand:P 1 "register_operand" "=l"))
13549 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13551 (set (match_operand:DF 3 "gpc_reg_operand" "=d")
13552 (match_operand:DF 4 "memory_operand" "m"))])]
13555 [(set_attr "type" "branch")
13556 (set_attr "length" "4")])
13558 (define_insn "*return_and_restore_fpregs_<mode>_r12"
13559 [(match_parallel 0 "any_parallel_operand"
13561 (clobber (match_operand:P 1 "register_operand" "=l"))
13562 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13564 (set (match_operand:DF 3 "gpc_reg_operand" "=d")
13565 (match_operand:DF 4 "memory_operand" "m"))])]
13568 [(set_attr "type" "branch")
13569 (set_attr "length" "4")])
13571 (define_insn "*return_and_restore_fpregs_<mode>_r1"
13572 [(match_parallel 0 "any_parallel_operand"
13574 (clobber (match_operand:P 1 "register_operand" "=l"))
13575 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13577 (set (match_operand:DF 3 "gpc_reg_operand" "=d")
13578 (match_operand:DF 4 "memory_operand" "m"))])]
13581 [(set_attr "type" "branch")
13582 (set_attr "length" "4")])
13584 (define_insn "*return_and_restore_fpregs_aix_<mode>_r11"
13585 [(match_parallel 0 "any_parallel_operand"
13587 (use (match_operand:P 1 "register_operand" "l"))
13588 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13590 (set (match_operand:DF 3 "gpc_reg_operand" "=d")
13591 (match_operand:DF 4 "memory_operand" "m"))])]
13594 [(set_attr "type" "branch")
13595 (set_attr "length" "4")])
13597 (define_insn "*return_and_restore_fpregs_aix_<mode>_r1"
13598 [(match_parallel 0 "any_parallel_operand"
13600 (use (match_operand:P 1 "register_operand" "l"))
13601 (use (match_operand:P 2 "symbol_ref_operand" "s"))
13603 (set (match_operand:DF 3 "gpc_reg_operand" "=d")
13604 (match_operand:DF 4 "memory_operand" "m"))])]
13607 [(set_attr "type" "branch")
13608 (set_attr "length" "4")])
13610 ; This is used in compiling the unwind routines.
13611 (define_expand "eh_return"
13612 [(use (match_operand 0 "general_operand" ""))]
13617 emit_insn (gen_eh_set_lr_si (operands[0]));
13619 emit_insn (gen_eh_set_lr_di (operands[0]));
13623 ; We can't expand this before we know where the link register is stored.
13624 (define_insn "eh_set_lr_<mode>"
13625 [(unspec_volatile [(match_operand:P 0 "register_operand" "r")]
13627 (clobber (match_scratch:P 1 "=&b"))]
13632 [(unspec_volatile [(match_operand 0 "register_operand" "")] UNSPECV_EH_RR)
13633 (clobber (match_scratch 1 ""))]
13638 rs6000_emit_eh_reg_restore (operands[0], operands[1]);
13642 (define_insn "prefetch"
13643 [(prefetch (match_operand 0 "indexed_or_indirect_address" "a")
13644 (match_operand:SI 1 "const_int_operand" "n")
13645 (match_operand:SI 2 "const_int_operand" "n"))]
13649 if (GET_CODE (operands[0]) == REG)
13650 return INTVAL (operands[1]) ? \"dcbtst 0,%0\" : \"dcbt 0,%0\";
13651 return INTVAL (operands[1]) ? \"dcbtst %a0\" : \"dcbt %a0\";
13653 [(set_attr "type" "load")])
13655 (define_insn "bpermd_<mode>"
13656 [(set (match_operand:P 0 "gpc_reg_operand" "=r")
13657 (unspec:P [(match_operand:P 1 "gpc_reg_operand" "r")
13658 (match_operand:P 2 "gpc_reg_operand" "r")] UNSPEC_BPERM))]
13661 [(set_attr "type" "popcnt")])
13664 ;; Builtin fma support. Handle
13665 ;; Note that the conditions for expansion are in the FMA_F iterator.
13667 (define_expand "fma<mode>4"
13668 [(set (match_operand:FMA_F 0 "register_operand" "")
13670 (match_operand:FMA_F 1 "register_operand" "")
13671 (match_operand:FMA_F 2 "register_operand" "")
13672 (match_operand:FMA_F 3 "register_operand" "")))]
13676 (define_insn "*fma<mode>4_fpr"
13677 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>,<Fv>")
13679 (match_operand:SFDF 1 "gpc_reg_operand" "%<Ff>,<Fv>,<Fv>")
13680 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>,0")
13681 (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv>")))]
13682 "TARGET_<MODE>_FPR"
13684 fmadd<Ftrad> %0,%1,%2,%3
13685 xsmadda<Fvsx> %x0,%x1,%x2
13686 xsmaddm<Fvsx> %x0,%x1,%x3"
13687 [(set_attr "type" "fp")
13688 (set_attr "fp_type" "fp_maddsub_<Fs>")])
13690 ; Altivec only has fma and nfms.
13691 (define_expand "fms<mode>4"
13692 [(set (match_operand:FMA_F 0 "register_operand" "")
13694 (match_operand:FMA_F 1 "register_operand" "")
13695 (match_operand:FMA_F 2 "register_operand" "")
13696 (neg:FMA_F (match_operand:FMA_F 3 "register_operand" ""))))]
13697 "!VECTOR_UNIT_ALTIVEC_P (<MODE>mode)"
13700 (define_insn "*fms<mode>4_fpr"
13701 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>,<Fv>")
13703 (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>,<Fv>")
13704 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>,0")
13705 (neg:SFDF (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv>"))))]
13706 "TARGET_<MODE>_FPR"
13708 fmsub<Ftrad> %0,%1,%2,%3
13709 xsmsuba<Fvsx> %x0,%x1,%x2
13710 xsmsubm<Fvsx> %x0,%x1,%x3"
13711 [(set_attr "type" "fp")
13712 (set_attr "fp_type" "fp_maddsub_<Fs>")])
13714 ;; If signed zeros are ignored, -(a * b - c) = -a * b + c.
13715 (define_expand "fnma<mode>4"
13716 [(set (match_operand:FMA_F 0 "register_operand" "")
13719 (match_operand:FMA_F 1 "register_operand" "")
13720 (match_operand:FMA_F 2 "register_operand" "")
13721 (neg:FMA_F (match_operand:FMA_F 3 "register_operand" "")))))]
13722 "!HONOR_SIGNED_ZEROS (<MODE>mode)"
13725 ;; If signed zeros are ignored, -(a * b + c) = -a * b - c.
13726 (define_expand "fnms<mode>4"
13727 [(set (match_operand:FMA_F 0 "register_operand" "")
13730 (match_operand:FMA_F 1 "register_operand" "")
13731 (match_operand:FMA_F 2 "register_operand" "")
13732 (match_operand:FMA_F 3 "register_operand" ""))))]
13733 "!HONOR_SIGNED_ZEROS (<MODE>mode) && !VECTOR_UNIT_ALTIVEC_P (<MODE>mode)"
13736 ; Not an official optab name, but used from builtins.
13737 (define_expand "nfma<mode>4"
13738 [(set (match_operand:FMA_F 0 "register_operand" "")
13741 (match_operand:FMA_F 1 "register_operand" "")
13742 (match_operand:FMA_F 2 "register_operand" "")
13743 (match_operand:FMA_F 3 "register_operand" ""))))]
13744 "!VECTOR_UNIT_ALTIVEC_P (<MODE>mode)"
13747 (define_insn "*nfma<mode>4_fpr"
13748 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>,<Fv>")
13751 (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>,<Fv>")
13752 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>,0")
13753 (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv>"))))]
13754 "TARGET_<MODE>_FPR"
13756 fnmadd<Ftrad> %0,%1,%2,%3
13757 xsnmadda<Fvsx> %x0,%x1,%x2
13758 xsnmaddm<Fvsx> %x0,%x1,%x3"
13759 [(set_attr "type" "fp")
13760 (set_attr "fp_type" "fp_maddsub_<Fs>")])
13762 ; Not an official optab name, but used from builtins.
13763 (define_expand "nfms<mode>4"
13764 [(set (match_operand:FMA_F 0 "register_operand" "")
13767 (match_operand:FMA_F 1 "register_operand" "")
13768 (match_operand:FMA_F 2 "register_operand" "")
13769 (neg:FMA_F (match_operand:FMA_F 3 "register_operand" "")))))]
13773 (define_insn "*nfmssf4_fpr"
13774 [(set (match_operand:SFDF 0 "gpc_reg_operand" "=<Ff>,<Fv>,<Fv>")
13777 (match_operand:SFDF 1 "gpc_reg_operand" "<Ff>,<Fv>,<Fv>")
13778 (match_operand:SFDF 2 "gpc_reg_operand" "<Ff>,<Fv>,0")
13780 (match_operand:SFDF 3 "gpc_reg_operand" "<Ff>,0,<Fv>")))))]
13781 "TARGET_<MODE>_FPR"
13783 fnmsub<Ftrad> %0,%1,%2,%3
13784 xsnmsuba<Fvsx> %x0,%x1,%x2
13785 xsnmsubm<Fvsx> %x0,%x1,%x3"
13786 [(set_attr "type" "fp")
13787 (set_attr "fp_type" "fp_maddsub_<Fs>")])
13790 (define_expand "rs6000_get_timebase"
13791 [(use (match_operand:DI 0 "gpc_reg_operand" ""))]
13794 if (TARGET_POWERPC64)
13795 emit_insn (gen_rs6000_mftb_di (operands[0]));
13797 emit_insn (gen_rs6000_get_timebase_ppc32 (operands[0]));
13801 (define_insn "rs6000_get_timebase_ppc32"
13802 [(set (match_operand:DI 0 "gpc_reg_operand" "=r")
13803 (unspec_volatile:DI [(const_int 0)] UNSPECV_MFTB))
13804 (clobber (match_scratch:SI 1 "=r"))
13805 (clobber (match_scratch:CC 2 "=y"))]
13806 "!TARGET_POWERPC64"
13808 if (WORDS_BIG_ENDIAN)
13811 return "mfspr %0,269\;"
13819 return "mftbu %0\;"
13828 return "mfspr %L0,269\;"
13836 return "mftbu %L0\;"
13843 [(set_attr "length" "20")])
13845 (define_insn "rs6000_mftb_<mode>"
13846 [(set (match_operand:GPR 0 "gpc_reg_operand" "=r")
13847 (unspec_volatile:GPR [(const_int 0)] UNSPECV_MFTB))]
13851 return "mfspr %0,268";
13857 (define_insn "rs6000_mffs"
13858 [(set (match_operand:DF 0 "gpc_reg_operand" "=d")
13859 (unspec_volatile:DF [(const_int 0)] UNSPECV_MFFS))]
13860 "TARGET_HARD_FLOAT && TARGET_FPRS"
13863 (define_insn "rs6000_mtfsf"
13864 [(unspec_volatile [(match_operand:SI 0 "const_int_operand" "i")
13865 (match_operand:DF 1 "gpc_reg_operand" "d")]
13867 "TARGET_HARD_FLOAT && TARGET_FPRS"
13871 ;; Power8 fusion support for fusing an addis instruction with a D-form load of
13872 ;; a GPR. The addis instruction must be adjacent to the load, and use the same
13873 ;; register that is being loaded. The fused ops must be physically adjacent.
13875 ;; Find cases where the addis that feeds into a load instruction is either used
13876 ;; once or is the same as the target register, and replace it with the fusion
13880 [(set (match_operand:P 0 "base_reg_operand" "")
13881 (match_operand:P 1 "fusion_gpr_addis" ""))
13882 (set (match_operand:INT1 2 "base_reg_operand" "")
13883 (match_operand:INT1 3 "fusion_gpr_mem_load" ""))]
13885 && fusion_gpr_load_p (operands[0], operands[1], operands[2],
13889 expand_fusion_gpr_load (operands);
13893 ;; Fusion insn, created by the define_peephole2 above (and eventually by
13896 (define_insn "fusion_gpr_load_<mode>"
13897 [(set (match_operand:INT1 0 "base_reg_operand" "=&b")
13898 (unspec:INT1 [(match_operand:INT1 1 "fusion_gpr_mem_combo" "")]
13899 UNSPEC_FUSION_GPR))]
13902 return emit_fusion_gpr_load (operands[0], operands[1]);
13904 [(set_attr "type" "load")
13905 (set_attr "length" "8")])
13908 ;; Miscellaneous ISA 2.06 (power7) instructions
13909 (define_insn "addg6s"
13910 [(set (match_operand:SI 0 "register_operand" "=r")
13911 (unspec:SI [(match_operand:SI 1 "register_operand" "r")
13912 (match_operand:SI 2 "register_operand" "r")]
13916 [(set_attr "type" "integer")
13917 (set_attr "length" "4")])
13919 (define_insn "cdtbcd"
13920 [(set (match_operand:SI 0 "register_operand" "=r")
13921 (unspec:SI [(match_operand:SI 1 "register_operand" "r")]
13925 [(set_attr "type" "integer")
13926 (set_attr "length" "4")])
13928 (define_insn "cbcdtd"
13929 [(set (match_operand:SI 0 "register_operand" "=r")
13930 (unspec:SI [(match_operand:SI 1 "register_operand" "r")]
13934 [(set_attr "type" "integer")
13935 (set_attr "length" "4")])
13937 (define_int_iterator UNSPEC_DIV_EXTEND [UNSPEC_DIVE
13942 (define_int_attr div_extend [(UNSPEC_DIVE "e")
13943 (UNSPEC_DIVEO "eo")
13944 (UNSPEC_DIVEU "eu")
13945 (UNSPEC_DIVEUO "euo")])
13947 (define_insn "div<div_extend>_<mode>"
13948 [(set (match_operand:GPR 0 "register_operand" "=r")
13949 (unspec:GPR [(match_operand:GPR 1 "register_operand" "r")
13950 (match_operand:GPR 2 "register_operand" "r")]
13951 UNSPEC_DIV_EXTEND))]
13953 "div<wd><div_extend> %0,%1,%2"
13954 [(set_attr "type" "div")
13955 (set_attr "size" "<bits>")])
13958 ;; Pack/unpack 128-bit floating point types that take 2 scalar registers
13960 ; Type of the 64-bit part when packing/unpacking 128-bit floating point types
13961 (define_mode_attr FP128_64 [(TF "DF") (TD "DI")])
13963 (define_expand "unpack<mode>"
13964 [(set (match_operand:<FP128_64> 0 "nonimmediate_operand" "")
13966 [(match_operand:FMOVE128 1 "register_operand" "")
13967 (match_operand:QI 2 "const_0_to_1_operand" "")]
13968 UNSPEC_UNPACK_128BIT))]
13972 (define_insn_and_split "unpack<mode>_dm"
13973 [(set (match_operand:<FP128_64> 0 "nonimmediate_operand" "=d,m,d,r,m")
13975 [(match_operand:FMOVE128 1 "register_operand" "d,d,r,d,r")
13976 (match_operand:QI 2 "const_0_to_1_operand" "i,i,i,i,i")]
13977 UNSPEC_UNPACK_128BIT))]
13978 "TARGET_POWERPC64 && TARGET_DIRECT_MOVE"
13980 "&& reload_completed"
13981 [(set (match_dup 0) (match_dup 3))]
13983 unsigned fp_regno = REGNO (operands[1]) + UINTVAL (operands[2]);
13985 if (REG_P (operands[0]) && REGNO (operands[0]) == fp_regno)
13987 emit_note (NOTE_INSN_DELETED);
13991 operands[3] = gen_rtx_REG (<FP128_64>mode, fp_regno);
13993 [(set_attr "type" "fp,fpstore,mffgpr,mftgpr,store")
13994 (set_attr "length" "4")])
13996 (define_insn_and_split "unpack<mode>_nodm"
13997 [(set (match_operand:<FP128_64> 0 "nonimmediate_operand" "=d,m")
13999 [(match_operand:FMOVE128 1 "register_operand" "d,d")
14000 (match_operand:QI 2 "const_0_to_1_operand" "i,i")]
14001 UNSPEC_UNPACK_128BIT))]
14002 "!TARGET_POWERPC64 || !TARGET_DIRECT_MOVE"
14004 "&& reload_completed"
14005 [(set (match_dup 0) (match_dup 3))]
14007 unsigned fp_regno = REGNO (operands[1]) + UINTVAL (operands[2]);
14009 if (REG_P (operands[0]) && REGNO (operands[0]) == fp_regno)
14011 emit_note (NOTE_INSN_DELETED);
14015 operands[3] = gen_rtx_REG (<FP128_64>mode, fp_regno);
14017 [(set_attr "type" "fp,fpstore")
14018 (set_attr "length" "4")])
14020 (define_insn_and_split "pack<mode>"
14021 [(set (match_operand:FMOVE128 0 "register_operand" "=d,&d")
14023 [(match_operand:<FP128_64> 1 "register_operand" "0,d")
14024 (match_operand:<FP128_64> 2 "register_operand" "d,d")]
14025 UNSPEC_PACK_128BIT))]
14030 "&& reload_completed && REGNO (operands[0]) != REGNO (operands[1])"
14031 [(set (match_dup 3) (match_dup 1))
14032 (set (match_dup 4) (match_dup 2))]
14034 unsigned dest_hi = REGNO (operands[0]);
14035 unsigned dest_lo = dest_hi + 1;
14037 gcc_assert (!IN_RANGE (REGNO (operands[1]), dest_hi, dest_lo));
14038 gcc_assert (!IN_RANGE (REGNO (operands[2]), dest_hi, dest_lo));
14040 operands[3] = gen_rtx_REG (<FP128_64>mode, dest_hi);
14041 operands[4] = gen_rtx_REG (<FP128_64>mode, dest_lo);
14043 [(set_attr "type" "fp,fp")
14044 (set_attr "length" "4,8")])
14046 (define_insn "unpackv1ti"
14047 [(set (match_operand:DI 0 "register_operand" "=d,d")
14048 (unspec:DI [(match_operand:V1TI 1 "register_operand" "0,wa")
14049 (match_operand:QI 2 "const_0_to_1_operand" "O,i")]
14050 UNSPEC_UNPACK_128BIT))]
14053 if (REGNO (operands[0]) == REGNO (operands[1]) && INTVAL (operands[2]) == 0)
14054 return ASM_COMMENT_START " xxpermdi to same register";
14056 operands[3] = GEN_INT (INTVAL (operands[2]) == 0 ? 0 : 3);
14057 return "xxpermdi %x0,%x1,%x1,%3";
14059 [(set_attr "type" "vecperm")
14060 (set_attr "length" "4")])
14062 (define_insn "packv1ti"
14063 [(set (match_operand:V1TI 0 "register_operand" "=wa")
14065 [(match_operand:DI 1 "register_operand" "d")
14066 (match_operand:DI 2 "register_operand" "d")]
14067 UNSPEC_PACK_128BIT))]
14069 "xxpermdi %x0,%x1,%x2,0"
14070 [(set_attr "type" "vecperm")
14071 (set_attr "length" "4")])
14075 (include "sync.md")
14076 (include "vector.md")
14078 (include "altivec.md")
14081 (include "paired.md")
14082 (include "crypto.md")