X-Git-Url: http://git.sourceforge.jp/view?p=pf3gnuchains%2Fgcc-fork.git;a=blobdiff_plain;f=gcc%2Fconfig%2Frs6000%2Frs6000.md;h=d1b43dc78af0b8b004409159f153282783c12635;hp=dcbe3a0278d0f84a8acfe20ea139e200cc7463b8;hb=2a4fe7b7180247bddcaa874fc7473462db67a10f;hpb=d68c5ad45f63d530f95f27da97eaa077f4cc8ee0 diff --git a/gcc/config/rs6000/rs6000.md b/gcc/config/rs6000/rs6000.md index dcbe3a0278d..d1b43dc78af 100644 --- a/gcc/config/rs6000/rs6000.md +++ b/gcc/config/rs6000/rs6000.md @@ -1,13 +1,14 @@ ;; Machine description for IBM RISC System 6000 (POWER) for GNU C compiler ;; Copyright (C) 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, -;; 1999, 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc. +;; 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007 +;; Free Software Foundation, Inc. ;; Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu) ;; This file is part of GCC. ;; GCC is free software; you can redistribute it and/or modify it ;; under the terms of the GNU General Public License as published -;; by the Free Software Foundation; either version 2, or (at your +;; by the Free Software Foundation; either version 3, or (at your ;; option) any later version. ;; GCC is distributed in the hope that it will be useful, but WITHOUT @@ -16,13 +17,39 @@ ;; License for more details. ;; You should have received a copy of the GNU General Public License -;; along with GCC; see the file COPYING. If not, write to the -;; Free Software Foundation, 51 Franklin Street, Fifth Floor, Boston, -;; MA 02110-1301, USA. +;; along with GCC; see the file COPYING3. If not see +;; . ;;- See file "rtl.def" for documentation on define_insn, match_*, et. al. ;; +;; REGNOS +;; + +(define_constants + [(MQ_REGNO 64) + (LR_REGNO 65) + (CTR_REGNO 66) + (CR0_REGNO 68) + (CR1_REGNO 69) + (CR2_REGNO 70) + (CR3_REGNO 71) + (CR4_REGNO 72) + (CR5_REGNO 73) + (CR6_REGNO 74) + (CR7_REGNO 75) + (MAX_CR_REGNO 75) + (XER_REGNO 76) + (FIRST_ALTIVEC_REGNO 77) + (LAST_ALTIVEC_REGNO 108) + (VRSAVE_REGNO 109) + (VSCR_REGNO 110) + (SPE_ACC_REGNO 111) + (SPEFSCR_REGNO 112) + (SFP_REGNO 113) + ]) + +;; ;; UNSPEC usage ;; @@ -34,6 +61,10 @@ (UNSPEC_MOVSI_GOT 8) (UNSPEC_MV_CR_OV 9) ; move_from_CR_ov_bit (UNSPEC_FCTIWZ 10) + (UNSPEC_FRIM 11) + (UNSPEC_FRIN 12) + (UNSPEC_FRIP 13) + (UNSPEC_FRIZ 14) (UNSPEC_LD_MPIC 15) ; load_macho_picbase (UNSPEC_MPIC_CORRECT 16) ; macho_correct_pic (UNSPEC_TLSGD 17) @@ -50,7 +81,7 @@ (UNSPEC_TLSGOTTPREL 28) (UNSPEC_TLSTLS 29) (UNSPEC_FIX_TRUNC_TF 30) ; fadd, rounding towards zero - (UNSPEC_MV_CR_GT 31) ; move_from_CR_eq_bit + (UNSPEC_MV_CR_GT 31) ; move_from_CR_gt_bit (UNSPEC_STFIWX 32) (UNSPEC_POPCNTB 33) (UNSPEC_FRES 34) @@ -64,6 +95,10 @@ (UNSPEC_CMPXCHG 42) (UNSPEC_XCHG 43) (UNSPEC_AND 44) + (UNSPEC_DLMZB 45) + (UNSPEC_DLMZB_CR 46) + (UNSPEC_DLMZB_STRLEN 47) + (UNSPEC_RSQRT 48) ]) ;; @@ -79,7 +114,7 @@ ;; Define an insn type attribute. This is used in function unit delay ;; computations. -(define_attr "type" "integer,two,three,load,load_ext,load_ext_u,load_ext_ux,load_ux,load_u,store,store_ux,store_u,fpload,fpload_ux,fpload_u,fpstore,fpstore_ux,fpstore_u,vecload,vecstore,imul,imul2,imul3,lmul,idiv,ldiv,insert_word,branch,cmp,fast_compare,compare,delayed_compare,imul_compare,lmul_compare,fpcompare,cr_logical,delayed_cr,mfcr,mfcrf,mtcr,mfjmpr,mtjmpr,fp,fpsimple,dmul,sdiv,ddiv,ssqrt,dsqrt,jmpreg,brinc,vecsimple,veccomplex,vecdiv,veccmp,veccmpsimple,vecperm,vecfloat,vecfdiv,isync,sync,load_l,store_c" +(define_attr "type" "integer,two,three,load,load_ext,load_ext_u,load_ext_ux,load_ux,load_u,store,store_ux,store_u,fpload,fpload_ux,fpload_u,fpstore,fpstore_ux,fpstore_u,vecload,vecstore,imul,imul2,imul3,lmul,idiv,ldiv,insert_word,branch,cmp,fast_compare,compare,var_delayed_compare,delayed_compare,imul_compare,lmul_compare,fpcompare,cr_logical,delayed_cr,mfcr,mfcrf,mtcr,mfjmpr,mtjmpr,fp,fpsimple,dmul,sdiv,ddiv,ssqrt,dsqrt,jmpreg,brinc,vecsimple,veccomplex,vecdiv,veccmp,veccmpsimple,vecperm,vecfloat,vecfdiv,isync,sync,load_l,store_c,shift,trap,insert_dword,var_shift_rotate,cntlz,exts,mffgpr,mftgpr" (const_string "integer")) ;; Length (in bytes). @@ -98,9 +133,26 @@ ;; Processor type -- this attribute must exactly match the processor_type ;; enumeration in rs6000.h. -(define_attr "cpu" "rios1,rios2,rs64a,mpccore,ppc403,ppc405,ppc440,ppc601,ppc603,ppc604,ppc604e,ppc620,ppc630,ppc750,ppc7400,ppc7450,ppc8540,power4,power5" +(define_attr "cpu" "rios1,rios2,rs64a,mpccore,ppc403,ppc405,ppc440,ppc601,ppc603,ppc604,ppc604e,ppc620,ppc630,ppc750,ppc7400,ppc7450,ppc8540,power4,power5,power6,cell" (const (symbol_ref "rs6000_cpu_attr"))) + +;; If this instruction is microcoded on the CELL processor +; The default for load and stores is conditional +; The default for load extended and the recorded instructions is always microcoded +(define_attr "cell_micro" "not,conditional,always" + (if_then_else (ior (ior (eq_attr "type" "load") + (eq_attr "type" "store")) + (ior (eq_attr "type" "fpload") + (eq_attr "type" "fpstore"))) + (const_string "conditional") + (if_then_else (ior (eq_attr "type" "load_ext") + (ior (eq_attr "type" "compare") + (eq_attr "type" "delayed_compare"))) + (const_string "always") + (const_string "not")))) + + (automata_option "ndfa") (include "rios1.md") @@ -116,39 +168,46 @@ (include "8540.md") (include "power4.md") (include "power5.md") +(include "power6.md") +(include "cell.md") (include "predicates.md") +(include "constraints.md") (include "darwin.md") -;; Mode macros +;; Mode iterators -; This mode macro allows :GPR to be used to indicate the allowable size +; This mode iterator allows :GPR to be used to indicate the allowable size ; of whole values in GPRs. -(define_mode_macro GPR [SI (DI "TARGET_POWERPC64")]) +(define_mode_iterator GPR [SI (DI "TARGET_POWERPC64")]) ; Any supported integer mode. -(define_mode_macro INT [QI HI SI DI TI]) +(define_mode_iterator INT [QI HI SI DI TI]) ; Any supported integer mode that fits in one register. -(define_mode_macro INT1 [QI HI SI (DI "TARGET_POWERPC64")]) +(define_mode_iterator INT1 [QI HI SI (DI "TARGET_POWERPC64")]) ; extend modes for DImode -(define_mode_macro QHSI [QI HI SI]) +(define_mode_iterator QHSI [QI HI SI]) ; SImode or DImode, even if DImode doesn't fit in GPRs. -(define_mode_macro SDI [SI DI]) +(define_mode_iterator SDI [SI DI]) ; The size of a pointer. Also, the size of the value that a record-condition ; (one with a '.') will compare. -(define_mode_macro P [(SI "TARGET_32BIT") (DI "TARGET_64BIT")]) +(define_mode_iterator P [(SI "TARGET_32BIT") (DI "TARGET_64BIT")]) ; Any hardware-supported floating-point mode -(define_mode_macro FP [(SF "TARGET_HARD_FLOAT") +(define_mode_iterator FP [(SF "TARGET_HARD_FLOAT") (DF "TARGET_HARD_FLOAT && (TARGET_FPRS || TARGET_E500_DOUBLE)") - (TF "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) - && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128")]) + (TF "!TARGET_IEEEQUAD + && TARGET_HARD_FLOAT + && (TARGET_FPRS || TARGET_E500_DOUBLE) + && TARGET_LONG_DOUBLE_128") + (DD "TARGET_DFP") + (TD "TARGET_DFP")]) ; Various instructions that come in SI and DI forms. ; A generic w/d attribute, for things like cmpw/cmpd. @@ -232,7 +291,8 @@ [(set (match_operand:DI 0 "gpc_reg_operand" "=r") (sign_extend:DI (match_operand:QI 1 "gpc_reg_operand" "r")))] "TARGET_POWERPC64" - "extsb %0,%1") + "extsb %0,%1" + [(set_attr "type" "exts")]) (define_insn "" [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") @@ -299,7 +359,7 @@ "@ lha%U1%X1 %0,%1 extsh %0,%1" - [(set_attr "type" "load_ext,*")]) + [(set_attr "type" "load_ext,exts")]) (define_insn "" [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") @@ -366,7 +426,7 @@ "@ lwa%U1%X1 %0,%1 extsw %0,%1" - [(set_attr "type" "load_ext,*")]) + [(set_attr "type" "load_ext,exts")]) (define_insn "" [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") @@ -506,7 +566,8 @@ [(set (match_operand:SI 0 "gpc_reg_operand" "=r") (sign_extend:SI (match_operand:QI 1 "gpc_reg_operand" "r")))] "TARGET_POWERPC" - "extsb %0,%1") + "extsb %0,%1" + [(set_attr "type" "exts")]) (define_insn "" [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") @@ -672,7 +733,8 @@ [(set (match_operand:HI 0 "gpc_reg_operand" "=r") (sign_extend:HI (match_operand:QI 1 "gpc_reg_operand" "r")))] "TARGET_POWERPC" - "extsb %0,%1") + "extsb %0,%1" + [(set_attr "type" "exts")]) (define_insn "" [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") @@ -834,7 +896,7 @@ "@ lha%U1%X1 %0,%1 {exts|extsh} %0,%1" - [(set_attr "type" "load_ext,*")]) + [(set_attr "type" "load_ext,exts")]) (define_insn "" [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") @@ -874,6 +936,537 @@ [(set_attr "type" "compare") (set_attr "length" "4,8")]) +;; IBM 405 and 440 half-word multiplication operations. + +(define_insn "*macchwc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (plus:SI (mult:SI (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)) + (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "r"))) + (match_operand:SI 4 "gpc_reg_operand" "0")) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (ashiftrt:SI + (match_dup 2) + (const_int 16)) + (sign_extend:SI + (match_dup 1))) + (match_dup 4)))] + "TARGET_MULHW" + "macchw. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*macchw" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)) + (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "r"))) + (match_operand:SI 3 "gpc_reg_operand" "0")))] + "TARGET_MULHW" + "macchw %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*macchwuc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (plus:SI (mult:SI (lshiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)) + (zero_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "r"))) + (match_operand:SI 4 "gpc_reg_operand" "0")) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (lshiftrt:SI + (match_dup 2) + (const_int 16)) + (zero_extend:SI + (match_dup 1))) + (match_dup 4)))] + "TARGET_MULHW" + "macchwu. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*macchwu" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (lshiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)) + (zero_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "r"))) + (match_operand:SI 3 "gpc_reg_operand" "0")))] + "TARGET_MULHW" + "macchwu %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*machhwc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (plus:SI (mult:SI (ashiftrt:SI + (match_operand:SI 1 "gpc_reg_operand" "%r") + (const_int 16)) + (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16))) + (match_operand:SI 4 "gpc_reg_operand" "0")) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (ashiftrt:SI + (match_dup 1) + (const_int 16)) + (ashiftrt:SI + (match_dup 2) + (const_int 16))) + (match_dup 4)))] + "TARGET_MULHW" + "machhw. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*machhw" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (ashiftrt:SI + (match_operand:SI 1 "gpc_reg_operand" "%r") + (const_int 16)) + (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16))) + (match_operand:SI 3 "gpc_reg_operand" "0")))] + "TARGET_MULHW" + "machhw %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*machhwuc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (plus:SI (mult:SI (lshiftrt:SI + (match_operand:SI 1 "gpc_reg_operand" "%r") + (const_int 16)) + (lshiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16))) + (match_operand:SI 4 "gpc_reg_operand" "0")) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (lshiftrt:SI + (match_dup 1) + (const_int 16)) + (lshiftrt:SI + (match_dup 2) + (const_int 16))) + (match_dup 4)))] + "TARGET_MULHW" + "machhwu. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*machhwu" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (lshiftrt:SI + (match_operand:SI 1 "gpc_reg_operand" "%r") + (const_int 16)) + (lshiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16))) + (match_operand:SI 3 "gpc_reg_operand" "0")))] + "TARGET_MULHW" + "machhwu %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*maclhwc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (plus:SI (mult:SI (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "%r")) + (sign_extend:SI + (match_operand:HI 2 "gpc_reg_operand" "r"))) + (match_operand:SI 4 "gpc_reg_operand" "0")) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (sign_extend:SI + (match_dup 1)) + (sign_extend:SI + (match_dup 2))) + (match_dup 4)))] + "TARGET_MULHW" + "maclhw. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*maclhw" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "%r")) + (sign_extend:SI + (match_operand:HI 2 "gpc_reg_operand" "r"))) + (match_operand:SI 3 "gpc_reg_operand" "0")))] + "TARGET_MULHW" + "maclhw %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*maclhwuc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (plus:SI (mult:SI (zero_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "%r")) + (zero_extend:SI + (match_operand:HI 2 "gpc_reg_operand" "r"))) + (match_operand:SI 4 "gpc_reg_operand" "0")) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (zero_extend:SI + (match_dup 1)) + (zero_extend:SI + (match_dup 2))) + (match_dup 4)))] + "TARGET_MULHW" + "maclhwu. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*maclhwu" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (plus:SI (mult:SI (zero_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "%r")) + (zero_extend:SI + (match_operand:HI 2 "gpc_reg_operand" "r"))) + (match_operand:SI 3 "gpc_reg_operand" "0")))] + "TARGET_MULHW" + "maclhwu %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*nmacchwc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (minus:SI (match_operand:SI 4 "gpc_reg_operand" "0") + (mult:SI (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)) + (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "r")))) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (minus:SI (match_dup 4) + (mult:SI (ashiftrt:SI + (match_dup 2) + (const_int 16)) + (sign_extend:SI + (match_dup 1)))))] + "TARGET_MULHW" + "nmacchw. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*nmacchw" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (minus:SI (match_operand:SI 3 "gpc_reg_operand" "0") + (mult:SI (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)) + (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "r")))))] + "TARGET_MULHW" + "nmacchw %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*nmachhwc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (minus:SI (match_operand:SI 4 "gpc_reg_operand" "0") + (mult:SI (ashiftrt:SI + (match_operand:SI 1 "gpc_reg_operand" "%r") + (const_int 16)) + (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)))) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (minus:SI (match_dup 4) + (mult:SI (ashiftrt:SI + (match_dup 1) + (const_int 16)) + (ashiftrt:SI + (match_dup 2) + (const_int 16)))))] + "TARGET_MULHW" + "nmachhw. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*nmachhw" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (minus:SI (match_operand:SI 3 "gpc_reg_operand" "0") + (mult:SI (ashiftrt:SI + (match_operand:SI 1 "gpc_reg_operand" "%r") + (const_int 16)) + (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)))))] + "TARGET_MULHW" + "nmachhw %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*nmaclhwc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (minus:SI (match_operand:SI 4 "gpc_reg_operand" "0") + (mult:SI (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "%r")) + (sign_extend:SI + (match_operand:HI 2 "gpc_reg_operand" "r")))) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (minus:SI (match_dup 4) + (mult:SI (sign_extend:SI + (match_dup 1)) + (sign_extend:SI + (match_dup 2)))))] + "TARGET_MULHW" + "nmaclhw. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*nmaclhw" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (minus:SI (match_operand:SI 3 "gpc_reg_operand" "0") + (mult:SI (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "%r")) + (sign_extend:SI + (match_operand:HI 2 "gpc_reg_operand" "r")))))] + "TARGET_MULHW" + "nmaclhw %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mulchwc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (mult:SI (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)) + (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "r"))) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (ashiftrt:SI + (match_dup 2) + (const_int 16)) + (sign_extend:SI + (match_dup 1))))] + "TARGET_MULHW" + "mulchw. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mulchw" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)) + (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "r"))))] + "TARGET_MULHW" + "mulchw %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mulchwuc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (mult:SI (lshiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)) + (zero_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "r"))) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (lshiftrt:SI + (match_dup 2) + (const_int 16)) + (zero_extend:SI + (match_dup 1))))] + "TARGET_MULHW" + "mulchwu. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mulchwu" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (lshiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16)) + (zero_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "r"))))] + "TARGET_MULHW" + "mulchwu %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mulhhwc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (mult:SI (ashiftrt:SI + (match_operand:SI 1 "gpc_reg_operand" "%r") + (const_int 16)) + (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16))) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (ashiftrt:SI + (match_dup 1) + (const_int 16)) + (ashiftrt:SI + (match_dup 2) + (const_int 16))))] + "TARGET_MULHW" + "mulhhw. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mulhhw" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (ashiftrt:SI + (match_operand:SI 1 "gpc_reg_operand" "%r") + (const_int 16)) + (ashiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16))))] + "TARGET_MULHW" + "mulhhw %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mulhhwuc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (mult:SI (lshiftrt:SI + (match_operand:SI 1 "gpc_reg_operand" "%r") + (const_int 16)) + (lshiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16))) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (lshiftrt:SI + (match_dup 1) + (const_int 16)) + (lshiftrt:SI + (match_dup 2) + (const_int 16))))] + "TARGET_MULHW" + "mulhhwu. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mulhhwu" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (lshiftrt:SI + (match_operand:SI 1 "gpc_reg_operand" "%r") + (const_int 16)) + (lshiftrt:SI + (match_operand:SI 2 "gpc_reg_operand" "r") + (const_int 16))))] + "TARGET_MULHW" + "mulhhwu %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mullhwc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (mult:SI (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "%r")) + (sign_extend:SI + (match_operand:HI 2 "gpc_reg_operand" "r"))) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (sign_extend:SI + (match_dup 1)) + (sign_extend:SI + (match_dup 2))))] + "TARGET_MULHW" + "mullhw. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mullhw" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (sign_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "%r")) + (sign_extend:SI + (match_operand:HI 2 "gpc_reg_operand" "r"))))] + "TARGET_MULHW" + "mullhw %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mullhwuc" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (compare:CC (mult:SI (zero_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "%r")) + (zero_extend:SI + (match_operand:HI 2 "gpc_reg_operand" "r"))) + (const_int 0))) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (zero_extend:SI + (match_dup 1)) + (zero_extend:SI + (match_dup 2))))] + "TARGET_MULHW" + "mullhwu. %0, %1, %2" + [(set_attr "type" "imul3")]) + +(define_insn "*mullhwu" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (mult:SI (zero_extend:SI + (match_operand:HI 1 "gpc_reg_operand" "%r")) + (zero_extend:SI + (match_operand:HI 2 "gpc_reg_operand" "r"))))] + "TARGET_MULHW" + "mullhwu %0, %1, %2" + [(set_attr "type" "imul3")]) + +;; IBM 405 and 440 string-search dlmzb instruction support. +(define_insn "dlmzb" + [(set (match_operand:CC 3 "cc_reg_operand" "=x") + (unspec:CC [(match_operand:SI 1 "gpc_reg_operand" "r") + (match_operand:SI 2 "gpc_reg_operand" "r")] + UNSPEC_DLMZB_CR)) + (set (match_operand:SI 0 "gpc_reg_operand" "=r") + (unspec:SI [(match_dup 1) + (match_dup 2)] + UNSPEC_DLMZB))] + "TARGET_DLMZB" + "dlmzb. %0, %1, %2") + +(define_expand "strlensi" + [(set (match_operand:SI 0 "gpc_reg_operand" "") + (unspec:SI [(match_operand:BLK 1 "general_operand" "") + (match_operand:QI 2 "const_int_operand" "") + (match_operand 3 "const_int_operand" "")] + UNSPEC_DLMZB_STRLEN)) + (clobber (match_scratch:CC 4 "=x"))] + "TARGET_DLMZB && WORDS_BIG_ENDIAN && !optimize_size" +{ + rtx result = operands[0]; + rtx src = operands[1]; + rtx search_char = operands[2]; + rtx align = operands[3]; + rtx addr, scratch_string, word1, word2, scratch_dlmzb; + rtx loop_label, end_label, mem, cr0, cond; + if (search_char != const0_rtx + || GET_CODE (align) != CONST_INT + || INTVAL (align) < 8) + FAIL; + word1 = gen_reg_rtx (SImode); + word2 = gen_reg_rtx (SImode); + scratch_dlmzb = gen_reg_rtx (SImode); + scratch_string = gen_reg_rtx (Pmode); + loop_label = gen_label_rtx (); + end_label = gen_label_rtx (); + addr = force_reg (Pmode, XEXP (src, 0)); + emit_move_insn (scratch_string, addr); + emit_label (loop_label); + mem = change_address (src, SImode, scratch_string); + emit_move_insn (word1, mem); + emit_move_insn (word2, adjust_address (mem, SImode, 4)); + cr0 = gen_rtx_REG (CCmode, CR0_REGNO); + emit_insn (gen_dlmzb (scratch_dlmzb, word1, word2, cr0)); + cond = gen_rtx_NE (VOIDmode, cr0, const0_rtx); + emit_jump_insn (gen_rtx_SET (VOIDmode, + pc_rtx, + gen_rtx_IF_THEN_ELSE (VOIDmode, + cond, + gen_rtx_LABEL_REF + (VOIDmode, + end_label), + pc_rtx))); + emit_insn (gen_addsi3 (scratch_string, scratch_string, GEN_INT (8))); + emit_jump_insn (gen_rtx_SET (VOIDmode, + pc_rtx, + gen_rtx_LABEL_REF (VOIDmode, loop_label))); + emit_barrier (); + emit_label (end_label); + emit_insn (gen_addsi3 (scratch_string, scratch_string, scratch_dlmzb)); + emit_insn (gen_subsi3 (result, scratch_string, addr)); + emit_insn (gen_subsi3 (result, result, const1_rtx)); + DONE; +}) + (define_split [(set (match_operand:CC 2 "cc_reg_not_cr0_operand" "") (compare:CC (sign_extend:SI (match_operand:HI 1 "gpc_reg_operand" "")) @@ -895,7 +1488,6 @@ (plus:SDI (match_operand:SDI 1 "gpc_reg_operand" "") (match_operand:SDI 2 "reg_or_add_cint_operand" "")))] "" - " { if (mode == DImode && ! TARGET_POWERPC64) { @@ -905,14 +1497,15 @@ else if (GET_CODE (operands[2]) == CONST_INT && ! add_operand (operands[2], mode)) { - rtx tmp = ((no_new_pseudos || rtx_equal_p (operands[0], operands[1])) + rtx tmp = ((!can_create_pseudo_p () + || rtx_equal_p (operands[0], operands[1])) ? operands[0] : gen_reg_rtx (mode)); HOST_WIDE_INT val = INTVAL (operands[2]); HOST_WIDE_INT low = ((val & 0xffff) ^ 0x8000) - 0x8000; HOST_WIDE_INT rest = trunc_int_for_mode (val - low, mode); - if (mode == DImode && !CONST_OK_FOR_LETTER_P (rest, 'L')) + if (mode == DImode && !satisfies_constraint_L (GEN_INT (rest))) FAIL; /* The ordering here is important for the prolog expander. @@ -922,7 +1515,7 @@ emit_insn (gen_add3 (operands[0], tmp, GEN_INT (low))); DONE; } -}") +}) ;; Discourage ai/addic because of carry but provide it in an alternative ;; allowing register zero as source. @@ -930,7 +1523,7 @@ [(set (match_operand:GPR 0 "gpc_reg_operand" "=r,r,?r,r") (plus:GPR (match_operand:GPR 1 "gpc_reg_operand" "%r,b,r,b") (match_operand:GPR 2 "add_operand" "r,I,I,L")))] - "" + "!DECIMAL_FLOAT_MODE_P (GET_MODE (operands[0])) && !DECIMAL_FLOAT_MODE_P (GET_MODE (operands[1]))" "@ {cax|add} %0,%1,%2 {cal %0,%2(%1)|addi %0,%1,%2} @@ -1020,16 +1613,15 @@ "" [(set (match_dup 0) (plus:GPR (match_dup 1) (match_dup 3))) (set (match_dup 0) (plus:GPR (match_dup 0) (match_dup 4)))] -" { HOST_WIDE_INT val = INTVAL (operands[2]); HOST_WIDE_INT low = ((val & 0xffff) ^ 0x8000) - 0x8000; HOST_WIDE_INT rest = trunc_int_for_mode (val - low, mode); operands[4] = GEN_INT (low); - if (mode == SImode || CONST_OK_FOR_LETTER_P (rest, 'L')) + if (mode == SImode || satisfies_constraint_L (GEN_INT (rest))) operands[3] = GEN_INT (rest); - else if (! no_new_pseudos) + else if (can_create_pseudo_p ()) { operands[3] = gen_reg_rtx (DImode); emit_move_insn (operands[3], operands[2]); @@ -1038,7 +1630,7 @@ } else FAIL; -}") +}) (define_insn "one_cmpl2" [(set (match_operand:GPR 0 "gpc_reg_operand" "=r") @@ -1562,16 +2154,17 @@ [(set (match_operand:GPR 0 "gpc_reg_operand" "=r") (clz:GPR (match_operand:GPR 1 "gpc_reg_operand" "r")))] "" - "{cntlz|cntlz} %0,%1") + "{cntlz|cntlz} %0,%1" + [(set_attr "type" "cntlz")]) (define_expand "ctz2" [(set (match_dup 2) - (neg:GPR (match_operand:GPR 1 "gpc_reg_operand" "r"))) + (neg:GPR (match_operand:GPR 1 "gpc_reg_operand" ""))) (parallel [(set (match_dup 3) (and:GPR (match_dup 1) (match_dup 2))) (clobber (scratch:CC))]) (set (match_dup 4) (clz:GPR (match_dup 3))) - (set (match_operand:GPR 0 "gpc_reg_operand" "=r") + (set (match_operand:GPR 0 "gpc_reg_operand" "") (minus:GPR (match_dup 5) (match_dup 4)))] "" { @@ -1583,12 +2176,12 @@ (define_expand "ffs2" [(set (match_dup 2) - (neg:GPR (match_operand:GPR 1 "gpc_reg_operand" "r"))) + (neg:GPR (match_operand:GPR 1 "gpc_reg_operand" ""))) (parallel [(set (match_dup 3) (and:GPR (match_dup 1) (match_dup 2))) (clobber (scratch:CC))]) (set (match_dup 4) (clz:GPR (match_dup 3))) - (set (match_operand:GPR 0 "gpc_reg_operand" "=r") + (set (match_operand:GPR 0 "gpc_reg_operand" "") (minus:GPR (match_dup 5) (match_dup 4)))] "" { @@ -1598,26 +2191,6 @@ operands[5] = GEN_INT (GET_MODE_BITSIZE (mode)); }) -(define_expand "popcount2" - [(set (match_dup 2) - (unspec:GPR [(match_operand:GPR 1 "gpc_reg_operand" "r")] - UNSPEC_POPCNTB)) - (set (match_dup 3) - (mult:GPR (match_dup 2) (match_dup 4))) - (set (match_operand:GPR 0 "gpc_reg_operand" "=r") - (lshiftrt:GPR (match_dup 3) (match_dup 5)))] - "TARGET_POPCNTB" - { - operands[2] = gen_reg_rtx (mode); - operands[3] = gen_reg_rtx (mode); - operands[4] = force_reg (mode, - mode == SImode - ? GEN_INT (0x01010101) - : GEN_INT ((HOST_WIDE_INT) - 0x01010101 << 32 | 0x01010101)); - operands[5] = GEN_INT (GET_MODE_BITSIZE (mode) - 8); - }) - (define_insn "popcntb2" [(set (match_operand:GPR 0 "gpc_reg_operand" "=r") (unspec:GPR [(match_operand:GPR 1 "gpc_reg_operand" "r")] @@ -1625,6 +2198,51 @@ "TARGET_POPCNTB" "popcntb %0,%1") +(define_expand "popcount2" + [(set (match_operand:GPR 0 "gpc_reg_operand" "") + (popcount:GPR (match_operand:GPR 1 "gpc_reg_operand" "")))] + "TARGET_POPCNTB" + { + rs6000_emit_popcount (operands[0], operands[1]); + DONE; + }) + +(define_expand "parity2" + [(set (match_operand:GPR 0 "gpc_reg_operand" "") + (parity:GPR (match_operand:GPR 1 "gpc_reg_operand" "")))] + "TARGET_POPCNTB" + { + rs6000_emit_parity (operands[0], operands[1]); + DONE; + }) + +(define_insn "bswapsi2" + [(set (match_operand:SI 0 "reg_or_mem_operand" "=r,Z,&r") + (bswap:SI (match_operand:SI 1 "reg_or_mem_operand" "Z,r,r")))] + "" + "@ + {lbrx|lwbrx} %0,%y1 + {stbrx|stwbrx} %1,%y0 + #" + [(set_attr "length" "4,4,12")]) + +(define_split + [(set (match_operand:SI 0 "gpc_reg_operand" "") + (bswap:SI (match_operand:SI 1 "gpc_reg_operand" "")))] + "reload_completed" + [(set (match_dup 0) + (rotate:SI (match_dup 1) (const_int 8))) + (set (zero_extract:SI (match_dup 0) + (const_int 8) + (const_int 0)) + (match_dup 1)) + (set (zero_extract:SI (match_dup 0) + (const_int 8) + (const_int 16)) + (rotate:SI (match_dup 1) + (const_int 16)))] + "") + (define_expand "mulsi3" [(use (match_operand:SI 0 "gpc_reg_operand" "")) (use (match_operand:SI 1 "gpc_reg_operand" "")) @@ -1859,7 +2477,11 @@ (match_operand:GPR 2 "gpc_reg_operand" "r")))] "TARGET_POWERPC && ! TARGET_POWER" "divu %0,%1,%2" - [(set_attr "type" "idiv")]) + [(set (attr "type") + (cond [(match_operand:SI 0 "" "") + (const_string "idiv")] + (const_string "ldiv")))]) + ;; For powers of two we can do srai/aze for divide and then adjust for ;; modulus. If it isn't a power of two, FAIL on POWER so divmodsi4 will be @@ -1878,7 +2500,7 @@ ; else if (TARGET_POWERPC) { - operands[2] = force_reg (SImode, operands[2]); + operands[2] = force_reg (mode, operands[2]); if (TARGET_POWER) { emit_insn (gen_divsi3_mq (operands[0], operands[1], operands[2])); @@ -1912,7 +2534,10 @@ (match_operand:GPR 2 "gpc_reg_operand" "r")))] "TARGET_POWERPC && ! TARGET_POWER" "div %0,%1,%2" - [(set_attr "type" "idiv")]) + [(set (attr "type") + (cond [(match_operand:SI 0 "" "") + (const_string "idiv")] + (const_string "ldiv")))]) (define_expand "mod3" [(use (match_operand:GPR 0 "gpc_reg_operand" "")) @@ -2118,7 +2743,7 @@ (lshiftrt:DI (mult:DI (sign_extend:DI (reg:SI 3)) (sign_extend:DI (reg:SI 4))) (const_int 32)))) - (clobber (match_scratch:SI 0 "=l"))] + (clobber (reg:SI LR_REGNO))] "! TARGET_POWER && ! TARGET_POWERPC" "bla __mulh" [(set_attr "type" "imul")]) @@ -2127,7 +2752,7 @@ [(set (reg:DI 3) (mult:DI (sign_extend:DI (reg:SI 3)) (sign_extend:DI (reg:SI 4)))) - (clobber (match_scratch:SI 0 "=l")) + (clobber (reg:SI LR_REGNO)) (clobber (reg:SI 0))] "! TARGET_POWER && ! TARGET_POWERPC" "bla __mull" @@ -2138,7 +2763,7 @@ (div:SI (reg:SI 3) (reg:SI 4))) (set (reg:SI 4) (mod:SI (reg:SI 3) (reg:SI 4))) - (clobber (match_scratch:SI 0 "=l")) + (clobber (reg:SI LR_REGNO)) (clobber (reg:SI 0))] "! TARGET_POWER && ! TARGET_POWERPC" "bla __divss" @@ -2149,10 +2774,10 @@ (udiv:SI (reg:SI 3) (reg:SI 4))) (set (reg:SI 4) (umod:SI (reg:SI 3) (reg:SI 4))) - (clobber (match_scratch:SI 0 "=l")) + (clobber (reg:SI LR_REGNO)) (clobber (reg:SI 0)) - (clobber (match_scratch:CC 1 "=x")) - (clobber (reg:CC 69))] + (clobber (match_scratch:CC 0 "=x")) + (clobber (reg:CC CR1_REGNO))] "! TARGET_POWER && ! TARGET_POWERPC" "bla __divus" [(set_attr "type" "idiv")]) @@ -2160,7 +2785,7 @@ (define_insn "quoss_call" [(set (reg:SI 3) (div:SI (reg:SI 3) (reg:SI 4))) - (clobber (match_scratch:SI 0 "=l"))] + (clobber (reg:SI LR_REGNO))] "! TARGET_POWER && ! TARGET_POWERPC" "bla __quoss" [(set_attr "type" "idiv")]) @@ -2168,10 +2793,10 @@ (define_insn "quous_call" [(set (reg:SI 3) (udiv:SI (reg:SI 3) (reg:SI 4))) - (clobber (match_scratch:SI 0 "=l")) + (clobber (reg:SI LR_REGNO)) (clobber (reg:SI 0)) - (clobber (match_scratch:CC 1 "=x")) - (clobber (reg:CC 69))] + (clobber (match_scratch:CC 0 "=x")) + (clobber (reg:CC CR1_REGNO))] "! TARGET_POWER && ! TARGET_POWERPC" "bla __quous" [(set_attr "type" "idiv")]) @@ -2393,7 +3018,8 @@ && ! logical_operand (operands[2], SImode)) { HOST_WIDE_INT value = INTVAL (operands[2]); - rtx tmp = ((no_new_pseudos || rtx_equal_p (operands[0], operands[1])) + rtx tmp = ((!can_create_pseudo_p () + || rtx_equal_p (operands[0], operands[1])) ? operands[0] : gen_reg_rtx (SImode)); emit_insn (gen_iorsi3 (tmp, operands[1], @@ -2414,7 +3040,8 @@ && ! logical_operand (operands[2], SImode)) { HOST_WIDE_INT value = INTVAL (operands[2]); - rtx tmp = ((no_new_pseudos || rtx_equal_p (operands[0], operands[1])) + rtx tmp = ((!can_create_pseudo_p () + || rtx_equal_p (operands[0], operands[1])) ? operands[0] : gen_reg_rtx (SImode)); emit_insn (gen_xorsi3 (tmp, operands[1], @@ -2851,9 +3478,12 @@ { /* Do not handle 16/8 bit structures that fit in HI/QI modes directly, since the (SUBREG:SI (REG:HI xxx)) that is otherwise generated can confuse the - compiler if the address of the structure is taken later. */ + compiler if the address of the structure is taken later. Likewise, do + not handle invalid E500 subregs. */ if (GET_CODE (operands[0]) == SUBREG - && (GET_MODE_SIZE (GET_MODE (SUBREG_REG (operands[0]))) < UNITS_PER_WORD)) + && (GET_MODE_SIZE (GET_MODE (SUBREG_REG (operands[0]))) < UNITS_PER_WORD + || ((TARGET_E500_DOUBLE || TARGET_SPE) + && invalid_e500_subreg (operands[0], GET_MODE (operands[0]))))) FAIL; if (TARGET_POWERPC64 && GET_MODE (operands[0]) == DImode) @@ -3011,7 +3641,8 @@ operands[1] = GEN_INT (64 - start - size); return \"rldimi %0,%3,%H1,%H2\"; -}") +}" + [(set_attr "type" "insert_dword")]) (define_insn "*insvdi_internal2" [(set (zero_extract:DI (match_operand:DI 0 "gpc_reg_operand" "+r") @@ -3132,7 +3763,7 @@ operands[3] = GEN_INT (start + size); return \"{rlinm.|rlwinm.} %4,%1,%3,%s2,31\"; }" - [(set_attr "type" "compare") + [(set_attr "type" "delayed_compare") (set_attr "length" "4,8")]) (define_split @@ -3183,7 +3814,7 @@ operands[3] = GEN_INT (start + size); return \"{rlinm.|rlwinm.} %0,%1,%3,%s2,31\"; }" - [(set_attr "type" "compare") + [(set_attr "type" "delayed_compare") (set_attr "length" "4,8")]) (define_split @@ -3267,24 +3898,29 @@ [(set_attr "type" "compare")]) (define_insn "rotlsi3" - [(set (match_operand:SI 0 "gpc_reg_operand" "=r") - (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r") - (match_operand:SI 2 "reg_or_cint_operand" "ri")))] + [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r") + (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i")))] "" - "{rl%I2nm|rlw%I2nm} %0,%1,%h2,0xffffffff") + "@ + {rlnm|rlwnm} %0,%1,%2,0xffffffff + {rlinm|rlwinm} %0,%1,%h2,0xffffffff" + [(set_attr "type" "var_shift_rotate,integer")]) (define_insn "*rotlsi3_internal2" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") - (compare:CC (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (clobber (match_scratch:SI 3 "=r,r"))] + (clobber (match_scratch:SI 3 "=r,r,r,r"))] "" "@ - {rl%I2nm.|rlw%I2nm.} %3,%1,%h2,0xffffffff + {rlnm.|rlwnm.} %3,%1,%2,0xffffffff + {rlinm.|rlwinm.} %3,%1,%h2,0xffffffff + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -3301,18 +3937,20 @@ "") (define_insn "*rotlsi3_internal3" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") - (compare:CC (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (set (match_operand:SI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r") (rotate:SI (match_dup 1) (match_dup 2)))] "" "@ - {rl%I2nm.|rlw%I2nm.} %0,%1,%h2,0xffffffff + {rlnm.|rlwnm.} %0,%1,%2,0xffffffff + {rlinm.|rlwinm.} %0,%1,%h2,0xffffffff + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -3330,27 +3968,32 @@ "") (define_insn "*rotlsi3_internal4" - [(set (match_operand:SI 0 "gpc_reg_operand" "=r") - (and:SI (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r") - (match_operand:SI 2 "reg_or_cint_operand" "ri")) - (match_operand:SI 3 "mask_operand" "n")))] + [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r") + (and:SI (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i")) + (match_operand:SI 3 "mask_operand" "n,n")))] "" - "{rl%I2nm|rlw%I2nm} %0,%1,%h2,%m3,%M3") + "@ + {rlnm|rlwnm} %0,%1,%2,%m3,%M3 + {rlinm|rlwinm} %0,%1,%h2,%m3,%M3" + [(set_attr "type" "var_shift_rotate,integer")]) (define_insn "*rotlsi3_internal5" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (and:SI - (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) - (match_operand:SI 3 "mask_operand" "n,n")) + (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) + (match_operand:SI 3 "mask_operand" "n,n,n,n")) (const_int 0))) - (clobber (match_scratch:SI 4 "=r,r"))] + (clobber (match_scratch:SI 4 "=r,r,r,r"))] "" "@ - {rl%I2nm.|rlw%I2nm.} %4,%1,%h2,%m3,%M3 + {rlnm.|rlwnm.} %4,%1,%2,%m3,%M3 + {rlinm.|rlwinm.} %4,%1,%h2,%m3,%M3 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -3371,20 +4014,22 @@ "") (define_insn "*rotlsi3_internal6" - [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 4 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (and:SI - (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) - (match_operand:SI 3 "mask_operand" "n,n")) + (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) + (match_operand:SI 3 "mask_operand" "n,n,n,n")) (const_int 0))) - (set (match_operand:SI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r") (and:SI (rotate:SI (match_dup 1) (match_dup 2)) (match_dup 3)))] "" "@ - {rl%I2nm.|rlw%I2nm.} %0,%1,%h2,%m3,%M3 + {rlnm.|rlwnm.} %0,%1,%2,%m3,%M3 + {rlinm.|rlwinm.} %0,%1,%h2,%m3,%M3 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 4 "cc_reg_not_cr0_operand" "") @@ -3413,19 +4058,21 @@ "{rl%I2nm|rlw%I2nm} %0,%1,%h2,0xff") (define_insn "*rotlsi3_internal8" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (zero_extend:SI (subreg:QI - (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) 0)) + (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) 0)) (const_int 0))) - (clobber (match_scratch:SI 3 "=r,r"))] + (clobber (match_scratch:SI 3 "=r,r,r,r"))] "" "@ - {rl%I2nm.|rlw%I2nm.} %3,%1,%h2,0xff + {rlnm.|rlwnm.} %3,%1,%2,0xff + {rlinm.|rlwinm.} %3,%1,%h2,0xff + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -3446,20 +4093,22 @@ "") (define_insn "*rotlsi3_internal9" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (zero_extend:SI (subreg:QI - (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) 0)) + (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) 0)) (const_int 0))) - (set (match_operand:SI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r") (zero_extend:SI (subreg:QI (rotate:SI (match_dup 1) (match_dup 2)) 0)))] "" "@ - {rl%I2nm.|rlw%I2nm.} %0,%1,%h2,0xff + {rlnm.|rlwnm.} %0,%1,%2,0xff + {rlinm.|rlwinm.} %0,%1,%h2,0xff + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -3479,28 +4128,34 @@ "") (define_insn "*rotlsi3_internal10" - [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r") (zero_extend:SI (subreg:HI - (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r") - (match_operand:SI 2 "reg_or_cint_operand" "ri")) 0)))] + (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i")) 0)))] "" - "{rl%I2nm|rlw%I2nm} %0,%1,%h2,0xffff") + "@ + {rlnm|rlwnm} %0,%1,%2,0xffff + {rlinm|rlwinm} %0,%1,%h2,0xffff" + [(set_attr "type" "var_shift_rotate,integer")]) + (define_insn "*rotlsi3_internal11" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (zero_extend:SI (subreg:HI - (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) 0)) + (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) 0)) (const_int 0))) - (clobber (match_scratch:SI 3 "=r,r"))] + (clobber (match_scratch:SI 3 "=r,r,r,r"))] "" "@ - {rl%I2nm.|rlw%I2nm.} %3,%1,%h2,0xffff + {rlnm.|rlwnm.} %3,%1,%2,0xffff + {rlinm.|rlwinm.} %3,%1,%h2,0xffff + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -3521,20 +4176,22 @@ "") (define_insn "*rotlsi3_internal12" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (zero_extend:SI (subreg:HI - (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) 0)) + (rotate:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) 0)) (const_int 0))) - (set (match_operand:SI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r") (zero_extend:SI (subreg:HI (rotate:SI (match_dup 1) (match_dup 2)) 0)))] "" "@ - {rl%I2nm.|rlw%I2nm.} %0,%1,%h2,0xffff + {rlnm.|rlwnm.} %0,%1,%2,0xffff + {rlinm.|rlwinm.} %0,%1,%h2,0xffff + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -3581,11 +4238,14 @@ {sli|slwi} %0,%1,%h2") (define_insn "ashlsi3_no_power" - [(set (match_operand:SI 0 "gpc_reg_operand" "=r") - (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r") - (match_operand:SI 2 "reg_or_cint_operand" "ri")))] + [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r") + (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i")))] "! TARGET_POWER" - "{sl|slw}%I2 %0,%1,%h2") + "@ + {sl|slw} %0,%1,%2 + {sli|slwi} %0,%1,%h2" + [(set_attr "type" "var_shift_rotate,shift")]) (define_insn "" [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") @@ -3620,17 +4280,19 @@ "") (define_insn "" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") - (compare:CC (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (clobber (match_scratch:SI 3 "=r,r"))] + (clobber (match_scratch:SI 3 "=r,r,r,r"))] "! TARGET_POWER && TARGET_32BIT" "@ - {sl|slw}%I2. %3,%1,%h2 + {sl.|slw.} %3,%1,%2 + {sli.|slwi.} %3,%1,%h2 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -3681,18 +4343,20 @@ "") (define_insn "" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") - (compare:CC (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (ashift:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (set (match_operand:SI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r") (ashift:SI (match_dup 1) (match_dup 2)))] "! TARGET_POWER && TARGET_32BIT" "@ - {sl|slw}%I2. %0,%1,%h2 + {sl.|slw.} %0,%1,%2 + {sli.|slwi.} %0,%1,%h2 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -3810,13 +4474,15 @@ {s%A2i|s%A2wi} %0,%1,%h2") (define_insn "lshrsi3_no_power" - [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r") - (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "O,ri")))] + [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r") + (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "O,r,i")))] "! TARGET_POWER" "@ mr %0,%1 - {sr|srw}%I2 %0,%1,%h2") + {sr|srw} %0,%1,%2 + {sri|srwi} %0,%1,%h2" + [(set_attr "type" "integer,var_shift_rotate,shift")]) (define_insn "" [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,x,?y,?y,?y") @@ -3853,19 +4519,21 @@ "") (define_insn "" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") - (compare:CC (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") - (match_operand:SI 2 "reg_or_cint_operand" "O,ri,O,ri")) + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,x,?y,?y,?y") + (compare:CC (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "O,r,i,O,r,i")) (const_int 0))) - (clobber (match_scratch:SI 3 "=X,r,X,r"))] + (clobber (match_scratch:SI 3 "=X,r,r,X,r,r"))] "! TARGET_POWER && TARGET_32BIT" "@ mr. %1,%1 - {sr|srw}%I2. %3,%1,%h2 + {sr.|srw.} %3,%1,%2 + {sri.|srwi.} %3,%1,%h2 + # # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,4,8,8")]) + [(set_attr "type" "delayed_compare,var_delayed_compare,delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,4,8,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -3918,20 +4586,22 @@ "") (define_insn "" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") - (compare:CC (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") - (match_operand:SI 2 "reg_or_cint_operand" "O,ri,O,ri")) + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,x,?y,?y,?y") + (compare:CC (lshiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "O,r,i,O,r,i")) (const_int 0))) - (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r") + (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r,r,r") (lshiftrt:SI (match_dup 1) (match_dup 2)))] "! TARGET_POWER && TARGET_32BIT" "@ mr. %0,%1 - {sr|srw}%I2. %0,%1,%h2 + {sr.|srw.} %0,%1,%2 + {sri.|srwi.} %0,%1,%h2 + # # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,4,8,8")]) + [(set_attr "type" "delayed_compare,var_delayed_compare,delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,4,8,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -4229,14 +4899,18 @@ "TARGET_POWER" "@ srea %0,%1,%2 - {srai|srawi} %0,%1,%h2") + {srai|srawi} %0,%1,%h2" + [(set_attr "type" "shift")]) (define_insn "ashrsi3_no_power" - [(set (match_operand:SI 0 "gpc_reg_operand" "=r") - (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r") - (match_operand:SI 2 "reg_or_cint_operand" "ri")))] + [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r") + (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i")))] "! TARGET_POWER" - "{sra|sraw}%I2 %0,%1,%h2") + "@ + {sra|sraw} %0,%1,%2 + {srai|srawi} %0,%1,%h2" + [(set_attr "type" "var_shift_rotate,shift")]) (define_insn "" [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") @@ -4271,17 +4945,19 @@ "") (define_insn "" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") - (compare:CC (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (clobber (match_scratch:SI 3 "=r,r"))] + (clobber (match_scratch:SI 3 "=r,r,r,r"))] "! TARGET_POWER" "@ - {sra|sraw}%I2. %3,%1,%h2 + {sra.|sraw.} %3,%1,%2 + {srai.|srawi.} %3,%1,%h2 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -4332,18 +5008,20 @@ "") (define_insn "" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") - (compare:CC (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (ashiftrt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (set (match_operand:SI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r") (ashiftrt:SI (match_dup 1) (match_dup 2)))] "! TARGET_POWER" "@ - {sra|sraw}%I2. %0,%1,%h2 + {sra.|sraw.} %0,%1,%2 + {srai.|srawi.} %0,%1,%h2 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -4520,26 +5198,12 @@ "{fm|fmul} %0,%1,%2" [(set_attr "type" "dmul")]) -(define_insn "fres" - [(set (match_operand:SF 0 "gpc_reg_operand" "=f") - (unspec:SF [(match_operand:SF 1 "gpc_reg_operand" "f")] UNSPEC_FRES))] - "TARGET_PPC_GFXOPT && flag_finite_math_only" - "fres %0,%1" - [(set_attr "type" "fp")]) - (define_expand "divsf3" [(set (match_operand:SF 0 "gpc_reg_operand" "") (div:SF (match_operand:SF 1 "gpc_reg_operand" "") (match_operand:SF 2 "gpc_reg_operand" "")))] "TARGET_HARD_FLOAT" -{ - if (swdiv && !optimize_size && TARGET_PPC_GFXOPT - && flag_finite_math_only && !flag_trapping_math) - { - rs6000_emit_swdivsf (operands[0], operands[1], operands[2]); - DONE; - } -}) + "") (define_insn "" [(set (match_operand:SF 0 "gpc_reg_operand" "=f") @@ -4557,6 +5221,25 @@ "{fd|fdiv} %0,%1,%2" [(set_attr "type" "ddiv")]) +(define_expand "recipsf3" + [(set (match_operand:SF 0 "gpc_reg_operand" "=f") + (unspec:SF [(match_operand:SF 1 "gpc_reg_operand" "f") + (match_operand:SF 2 "gpc_reg_operand" "f")] + UNSPEC_FRES))] + "TARGET_RECIP && TARGET_HARD_FLOAT && TARGET_PPC_GFXOPT && !optimize_size + && flag_finite_math_only && !flag_trapping_math" +{ + rs6000_emit_swdivsf (operands[0], operands[1], operands[2]); + DONE; +}) + +(define_insn "fres" + [(set (match_operand:SF 0 "gpc_reg_operand" "=f") + (unspec:SF [(match_operand:SF 1 "gpc_reg_operand" "f")] UNSPEC_FRES))] + "TARGET_PPC_GFXOPT && flag_finite_math_only" + "fres %0,%1" + [(set_attr "type" "fp")]) + (define_insn "" [(set (match_operand:SF 0 "gpc_reg_operand" "=f") (plus:SF (mult:SF (match_operand:SF 1 "gpc_reg_operand" "%f") @@ -4669,7 +5352,7 @@ "! TARGET_POWERPC && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_FUSED_MADD && ! HONOR_SIGNED_ZEROS (SFmode)" "{fnms|fnmsub} %0,%1,%2,%3" - [(set_attr "type" "fp")]) + [(set_attr "type" "dmul")]) (define_expand "sqrtsf2" [(set (match_operand:SF 0 "gpc_reg_operand" "") @@ -4691,6 +5374,25 @@ "fsqrt %0,%1" [(set_attr "type" "dsqrt")]) +(define_expand "rsqrtsf2" + [(set (match_operand:SF 0 "gpc_reg_operand" "=f") + (unspec:SF [(match_operand:SF 1 "gpc_reg_operand" "f")] + UNSPEC_RSQRT))] + "TARGET_RECIP && TARGET_HARD_FLOAT && TARGET_PPC_GFXOPT && !optimize_size + && flag_finite_math_only && !flag_trapping_math" +{ + rs6000_emit_swrsqrtsf (operands[0], operands[1]); + DONE; +}) + +(define_insn "*rsqrt_internal1" + [(set (match_operand:SF 0 "gpc_reg_operand" "=f") + (unspec:SF [(match_operand:SF 1 "gpc_reg_operand" "f")] + UNSPEC_RSQRT))] + "TARGET_HARD_FLOAT && TARGET_PPC_GFXOPT" + "frsqrte %0,%1" + [(set_attr "type" "fp")]) + (define_expand "copysignsf3" [(set (match_dup 3) (abs:SF (match_operand:SF 1 "gpc_reg_operand" ""))) @@ -4922,26 +5624,12 @@ "{fm|fmul} %0,%1,%2" [(set_attr "type" "dmul")]) -(define_insn "fred" - [(set (match_operand:DF 0 "gpc_reg_operand" "=f") - (unspec:DF [(match_operand:DF 1 "gpc_reg_operand" "f")] UNSPEC_FRES))] - "TARGET_POPCNTB && flag_finite_math_only" - "fre %0,%1" - [(set_attr "type" "fp")]) - (define_expand "divdf3" [(set (match_operand:DF 0 "gpc_reg_operand" "") (div:DF (match_operand:DF 1 "gpc_reg_operand" "") (match_operand:DF 2 "gpc_reg_operand" "")))] "TARGET_HARD_FLOAT && (TARGET_FPRS || TARGET_E500_DOUBLE)" -{ - if (swdiv && !optimize_size && TARGET_POPCNTB - && flag_finite_math_only && !flag_trapping_math) - { - rs6000_emit_swdivdf (operands[0], operands[1], operands[2]); - DONE; - } -}) + "") (define_insn "*divdf3_fpr" [(set (match_operand:DF 0 "gpc_reg_operand" "=f") @@ -4951,6 +5639,25 @@ "{fd|fdiv} %0,%1,%2" [(set_attr "type" "ddiv")]) +(define_expand "recipdf3" + [(set (match_operand:DF 0 "gpc_reg_operand" "=f") + (unspec:DF [(match_operand:DF 1 "gpc_reg_operand" "f") + (match_operand:DF 2 "gpc_reg_operand" "f")] + UNSPEC_FRES))] + "TARGET_RECIP && TARGET_HARD_FLOAT && TARGET_POPCNTB && !optimize_size + && flag_finite_math_only && !flag_trapping_math" +{ + rs6000_emit_swdivdf (operands[0], operands[1], operands[2]); + DONE; +}) + +(define_insn "fred" + [(set (match_operand:DF 0 "gpc_reg_operand" "=f") + (unspec:DF [(match_operand:DF 1 "gpc_reg_operand" "f")] UNSPEC_FRES))] + "TARGET_POPCNTB && flag_finite_math_only" + "fre %0,%1" + [(set_attr "type" "fp")]) + (define_insn "" [(set (match_operand:DF 0 "gpc_reg_operand" "=f") (plus:DF (mult:DF (match_operand:DF 1 "gpc_reg_operand" "%f") @@ -5111,7 +5818,7 @@ (clobber (match_dup 4)) (clobber (match_dup 5)) (clobber (match_dup 6))])] - "TARGET_HARD_FLOAT && TARGET_FPRS" + "TARGET_HARD_FLOAT && (TARGET_FPRS || TARGET_E500_DOUBLE)" " { if (TARGET_E500_DOUBLE) @@ -5119,6 +5826,12 @@ emit_insn (gen_spe_floatsidf2 (operands[0], operands[1])); DONE; } + if (TARGET_POWERPC64 && TARGET_MFPGPR && TARGET_HARD_FLOAT && TARGET_FPRS) + { + rtx t1 = gen_reg_rtx (DImode); + emit_insn (gen_floatsidf_ppc64_mfpgpr (operands[0], operands[1], t1)); + DONE; + } if (TARGET_POWERPC64) { rtx mem = assign_stack_temp (DImode, GET_MODE_SIZE (DImode), 0); @@ -5140,12 +5853,12 @@ (float:DF (match_operand:SI 1 "gpc_reg_operand" "r"))) (use (match_operand:SI 2 "gpc_reg_operand" "r")) (use (match_operand:DF 3 "gpc_reg_operand" "f")) - (clobber (match_operand:DF 4 "memory_operand" "=o")) + (clobber (match_operand:DF 4 "offsettable_mem_operand" "=o")) (clobber (match_operand:DF 5 "gpc_reg_operand" "=&f")) (clobber (match_operand:SI 6 "gpc_reg_operand" "=&r"))] "! TARGET_POWERPC64 && TARGET_HARD_FLOAT && TARGET_FPRS" "#" - "&& (!no_new_pseudos || offsettable_nonstrict_memref_p (operands[4]))" + "&& (can_create_pseudo_p () || offsettable_nonstrict_memref_p (operands[4]))" [(pc)] " { @@ -5211,11 +5924,11 @@ (unsigned_float:DF (match_operand:SI 1 "gpc_reg_operand" "r"))) (use (match_operand:SI 2 "gpc_reg_operand" "r")) (use (match_operand:DF 3 "gpc_reg_operand" "f")) - (clobber (match_operand:DF 4 "memory_operand" "=o")) + (clobber (match_operand:DF 4 "offsettable_mem_operand" "=o")) (clobber (match_operand:DF 5 "gpc_reg_operand" "=&f"))] "! TARGET_POWERPC64 && TARGET_HARD_FLOAT && TARGET_FPRS" "#" - "&& (!no_new_pseudos || offsettable_nonstrict_memref_p (operands[4]))" + "&& (can_create_pseudo_p () || offsettable_nonstrict_memref_p (operands[4]))" [(pc)] " { @@ -5252,6 +5965,14 @@ DONE; } operands[2] = gen_reg_rtx (DImode); + if (TARGET_POWERPC64 && TARGET_MFPGPR && TARGET_HARD_FLOAT && TARGET_FPRS + && gpc_reg_operand(operands[0], GET_MODE (operands[0]))) + { + operands[3] = gen_reg_rtx (DImode); + emit_insn (gen_fix_truncdfsi2_mfpgpr (operands[0], operands[1], + operands[2], operands[3])); + DONE; + } if (TARGET_PPC_GFXOPT) { rtx orig_dest = operands[0]; @@ -5270,10 +5991,10 @@ [(set (match_operand:SI 0 "gpc_reg_operand" "=r") (fix:SI (match_operand:DF 1 "gpc_reg_operand" "f"))) (clobber (match_operand:DI 2 "gpc_reg_operand" "=f")) - (clobber (match_operand:DI 3 "memory_operand" "=o"))] + (clobber (match_operand:DI 3 "offsettable_mem_operand" "=o"))] "(TARGET_POWER2 || TARGET_POWERPC) && TARGET_HARD_FLOAT && TARGET_FPRS" "#" - "&& (!no_new_pseudos || offsettable_nonstrict_memref_p (operands[3]))" + "&& (can_create_pseudo_p () || offsettable_nonstrict_memref_p (operands[3]))" [(pc)] " { @@ -5305,6 +6026,20 @@ }" [(set_attr "length" "16")]) +(define_insn_and_split "fix_truncdfsi2_mfpgpr" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r") + (fix:SI (match_operand:DF 1 "gpc_reg_operand" "f"))) + (clobber (match_operand:DI 2 "gpc_reg_operand" "=f")) + (clobber (match_operand:DI 3 "gpc_reg_operand" "=r"))] + "TARGET_POWERPC64 && TARGET_MFPGPR && TARGET_HARD_FLOAT && TARGET_FPRS" + "#" + "&& 1" + [(set (match_dup 2) (unspec:DI [(fix:SI (match_dup 1))] UNSPEC_FCTIWZ)) + (set (match_dup 3) (match_dup 2)) + (set (match_dup 0) (subreg:SI (match_dup 3) 4))] + "" + [(set_attr "length" "12")]) + ; Here, we use (set (reg) (unspec:DI [(fix:SI ...)] UNSPEC_FCTIWZ)) ; rather than (set (subreg:SI (reg)) (fix:SI ...)) ; because the first makes it clear that operand 0 is not live @@ -5317,6 +6052,62 @@ "{fcirz|fctiwz} %0,%1" [(set_attr "type" "fp")]) +(define_insn "btruncdf2" + [(set (match_operand:DF 0 "gpc_reg_operand" "=f") + (unspec:DF [(match_operand:DF 1 "gpc_reg_operand" "f")] UNSPEC_FRIZ))] + "TARGET_FPRND && TARGET_HARD_FLOAT && TARGET_FPRS" + "friz %0,%1" + [(set_attr "type" "fp")]) + +(define_insn "btruncsf2" + [(set (match_operand:SF 0 "gpc_reg_operand" "=f") + (unspec:SF [(match_operand:SF 1 "gpc_reg_operand" "f")] UNSPEC_FRIZ))] + "TARGET_FPRND && TARGET_HARD_FLOAT && TARGET_FPRS" + "friz %0,%1" + [(set_attr "type" "fp")]) + +(define_insn "ceildf2" + [(set (match_operand:DF 0 "gpc_reg_operand" "=f") + (unspec:DF [(match_operand:DF 1 "gpc_reg_operand" "f")] UNSPEC_FRIP))] + "TARGET_FPRND && TARGET_HARD_FLOAT && TARGET_FPRS" + "frip %0,%1" + [(set_attr "type" "fp")]) + +(define_insn "ceilsf2" + [(set (match_operand:SF 0 "gpc_reg_operand" "=f") + (unspec:SF [(match_operand:SF 1 "gpc_reg_operand" "f")] UNSPEC_FRIP))] + "TARGET_FPRND && TARGET_HARD_FLOAT && TARGET_FPRS" + "frip %0,%1" + [(set_attr "type" "fp")]) + +(define_insn "floordf2" + [(set (match_operand:DF 0 "gpc_reg_operand" "=f") + (unspec:DF [(match_operand:DF 1 "gpc_reg_operand" "f")] UNSPEC_FRIM))] + "TARGET_FPRND && TARGET_HARD_FLOAT && TARGET_FPRS" + "frim %0,%1" + [(set_attr "type" "fp")]) + +(define_insn "floorsf2" + [(set (match_operand:SF 0 "gpc_reg_operand" "=f") + (unspec:SF [(match_operand:SF 1 "gpc_reg_operand" "f")] UNSPEC_FRIM))] + "TARGET_FPRND && TARGET_HARD_FLOAT && TARGET_FPRS" + "frim %0,%1" + [(set_attr "type" "fp")]) + +(define_insn "rounddf2" + [(set (match_operand:DF 0 "gpc_reg_operand" "=f") + (unspec:DF [(match_operand:DF 1 "gpc_reg_operand" "f")] UNSPEC_FRIN))] + "TARGET_FPRND && TARGET_HARD_FLOAT && TARGET_FPRS" + "frin %0,%1" + [(set_attr "type" "fp")]) + +(define_insn "roundsf2" + [(set (match_operand:SF 0 "gpc_reg_operand" "=f") + (unspec:SF [(match_operand:SF 1 "gpc_reg_operand" "f")] UNSPEC_FRIN))] + "TARGET_FPRND && TARGET_HARD_FLOAT && TARGET_FPRS" + "frin %0,%1" + [(set_attr "type" "fp")]) + ; An UNSPEC is used so we don't have to support SImode in FP registers. (define_insn "stfiwx" [(set (match_operand:SI 0 "memory_operand" "=Z") @@ -5339,13 +6130,24 @@ "fcfid %0,%1" [(set_attr "type" "fp")]) +(define_insn_and_split "floatsidf_ppc64_mfpgpr" + [(set (match_operand:DF 0 "gpc_reg_operand" "=f") + (float:DF (match_operand:SI 1 "gpc_reg_operand" "r"))) + (clobber (match_operand:DI 2 "gpc_reg_operand" "=r"))] + "TARGET_POWERPC64 && TARGET_MFPGPR && TARGET_HARD_FLOAT && TARGET_FPRS" + "#" + "&& 1" + [(set (match_dup 2) (sign_extend:DI (match_dup 1))) + (set (match_dup 0) (float:DF (match_dup 2)))] + "") + (define_insn_and_split "floatsidf_ppc64" [(set (match_operand:DF 0 "gpc_reg_operand" "=f") (float:DF (match_operand:SI 1 "gpc_reg_operand" "r"))) - (clobber (match_operand:DI 2 "memory_operand" "=o")) + (clobber (match_operand:DI 2 "offsettable_mem_operand" "=o")) (clobber (match_operand:DI 3 "gpc_reg_operand" "=r")) (clobber (match_operand:DI 4 "gpc_reg_operand" "=f"))] - "TARGET_POWERPC64 && TARGET_HARD_FLOAT && TARGET_FPRS" + "TARGET_POWERPC64 && !TARGET_MFPGPR && TARGET_HARD_FLOAT && TARGET_FPRS" "#" "&& 1" [(set (match_dup 3) (sign_extend:DI (match_dup 1))) @@ -5357,7 +6159,7 @@ (define_insn_and_split "floatunssidf_ppc64" [(set (match_operand:DF 0 "gpc_reg_operand" "=f") (unsigned_float:DF (match_operand:SI 1 "gpc_reg_operand" "r"))) - (clobber (match_operand:DI 2 "memory_operand" "=o")) + (clobber (match_operand:DI 2 "offsettable_mem_operand" "=o")) (clobber (match_operand:DI 3 "gpc_reg_operand" "=r")) (clobber (match_operand:DI 4 "gpc_reg_operand" "=f"))] "TARGET_POWERPC64 && TARGET_HARD_FLOAT && TARGET_FPRS" @@ -5425,7 +6227,7 @@ (set (match_dup 0) (plus:DI (match_dup 0) (const_int 2047))) (set (match_dup 4) (compare:CCUNS (match_dup 3) - (const_int 3))) + (const_int 2))) (set (match_dup 0) (ior:DI (match_dup 0) (match_dup 1))) (parallel [(set (match_dup 0) (and:DI (match_dup 0) @@ -5640,9 +6442,9 @@ [(set (match_operand:SI 0 "gpc_reg_operand" "") (truncate:SI (lshiftrt:DI (mult:DI (sign_extend:DI - (match_operand:SI 1 "gpc_reg_operand" "%r")) + (match_operand:SI 1 "gpc_reg_operand" "")) (sign_extend:DI - (match_operand:SI 2 "gpc_reg_operand" "r"))) + (match_operand:SI 2 "gpc_reg_operand" ""))) (const_int 32))))] "" " @@ -5770,7 +6572,8 @@ "@ {srai|srawi} %0,%1,31\;{srai|srawi} %L0,%1,%h2 sraiq %0,%1,%h2\;srliq %L0,%L1,%h2" - [(set_attr "length" "8")]) + [(set_attr "type" "shift") + (set_attr "length" "8")]) (define_insn "ashrdi3_no_power" [(set (match_operand:DI 0 "gpc_reg_operand" "=&r,&r") @@ -5825,12 +6628,19 @@ "") (define_insn "muldi3" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") - (mult:DI (match_operand:DI 1 "gpc_reg_operand" "%r") - (match_operand:DI 2 "gpc_reg_operand" "r")))] + [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (mult:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r") + (match_operand:DI 2 "reg_or_short_operand" "r,I")))] "TARGET_POWERPC64" - "mulld %0,%1,%2" - [(set_attr "type" "lmul")]) + "@ + mulld %0,%1,%2 + mulli %0,%1,%2" + [(set (attr "type") + (cond [(match_operand:SI 2 "s8bit_cint_operand" "") + (const_string "imul3") + (match_operand:SI 2 "short_cint_operand" "") + (const_string "imul2")] + (const_string "lmul")))]) (define_insn "*muldi3_internal1" [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") @@ -5913,24 +6723,29 @@ [(set_attr "type" "lmul")]) (define_insn "rotldi3" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r") - (match_operand:DI 2 "reg_or_cint_operand" "ri")))] + [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i")))] "TARGET_POWERPC64" - "rld%I2cl %0,%1,%H2,0") + "@ + rldcl %0,%1,%2,0 + rldicl %0,%1,%H2,0" + [(set_attr "type" "var_shift_rotate,integer")]) (define_insn "*rotldi3_internal2" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") - (compare:CC (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:DI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (clobber (match_scratch:DI 3 "=r,r"))] + (clobber (match_scratch:DI 3 "=r,r,r,r"))] "TARGET_64BIT" "@ - rld%I2cl. %3,%1,%H2,0 + rldcl. %3,%1,%2,0 + rldicl. %3,%1,%H2,0 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -5947,18 +6762,20 @@ "") (define_insn "*rotldi3_internal3" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") - (compare:CC (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:DI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,r") (rotate:DI (match_dup 1) (match_dup 2)))] "TARGET_64BIT" "@ - rld%I2cl. %0,%1,%H2,0 + rldcl. %0,%1,%2,0 + rldicl. %0,%1,%H2,0 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -5976,34 +6793,39 @@ "") (define_insn "*rotldi3_internal4" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") - (and:DI (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r") - (match_operand:DI 2 "reg_or_cint_operand" "ri")) - (match_operand:DI 3 "mask_operand" "n")))] + [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (and:DI (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i")) + (match_operand:DI 3 "mask64_operand" "n,n")))] "TARGET_POWERPC64" - "rld%I2c%B3 %0,%1,%H2,%S3") + "@ + rldc%B3 %0,%1,%2,%S3 + rldic%B3 %0,%1,%H2,%S3" + [(set_attr "type" "var_shift_rotate,integer")]) (define_insn "*rotldi3_internal5" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (and:DI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:DI 2 "reg_or_cint_operand" "ri,ri")) - (match_operand:DI 3 "mask_operand" "n,n")) + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i,r,i")) + (match_operand:DI 3 "mask64_operand" "n,n,n,n")) (const_int 0))) - (clobber (match_scratch:DI 4 "=r,r"))] + (clobber (match_scratch:DI 4 "=r,r,r,r"))] "TARGET_64BIT" "@ - rld%I2c%B3. %4,%1,%H2,%S3 + rldc%B3. %4,%1,%2,%S3 + rldic%B3. %4,%1,%H2,%S3 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") (compare:CC (and:DI (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "") (match_operand:DI 2 "reg_or_cint_operand" "")) - (match_operand:DI 3 "mask_operand" "")) + (match_operand:DI 3 "mask64_operand" "")) (const_int 0))) (clobber (match_scratch:DI 4 ""))] "TARGET_POWERPC64 && reload_completed" @@ -6017,27 +6839,29 @@ "") (define_insn "*rotldi3_internal6" - [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 4 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (and:DI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:DI 2 "reg_or_cint_operand" "ri,ri")) - (match_operand:DI 3 "mask_operand" "n,n")) + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i,r,i")) + (match_operand:DI 3 "mask64_operand" "n,n,n,n")) (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,r") (and:DI (rotate:DI (match_dup 1) (match_dup 2)) (match_dup 3)))] "TARGET_64BIT" "@ - rld%I2c%B3. %0,%1,%H2,%S3 + rldc%B3. %0,%1,%2,%S3 + rldic%B3. %0,%1,%H2,%S3 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 4 "cc_reg_not_cr0_operand" "") (compare:CC (and:DI (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "") (match_operand:DI 2 "reg_or_cint_operand" "")) - (match_operand:DI 3 "mask_operand" "")) + (match_operand:DI 3 "mask64_operand" "")) (const_int 0))) (set (match_operand:DI 0 "gpc_reg_operand" "") (and:DI (rotate:DI (match_dup 1) (match_dup 2)) (match_dup 3)))] @@ -6050,28 +6874,33 @@ "") (define_insn "*rotldi3_internal7" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") + [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r") (zero_extend:DI (subreg:QI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r") - (match_operand:DI 2 "reg_or_cint_operand" "ri")) 0)))] + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i")) 0)))] "TARGET_POWERPC64" - "rld%I2cl %0,%1,%H2,56") + "@ + rldcl %0,%1,%2,56 + rldicl %0,%1,%H2,56" + [(set_attr "type" "var_shift_rotate,integer")]) (define_insn "*rotldi3_internal8" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (zero_extend:DI (subreg:QI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:DI 2 "reg_or_cint_operand" "ri,ri")) 0)) + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i,r,i")) 0)) (const_int 0))) - (clobber (match_scratch:DI 3 "=r,r"))] + (clobber (match_scratch:DI 3 "=r,r,r,r"))] "TARGET_64BIT" "@ - rld%I2cl. %3,%1,%H2,56 + rldcl. %3,%1,%2,56 + rldicl. %3,%1,%H2,56 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -6092,20 +6921,22 @@ "") (define_insn "*rotldi3_internal9" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (zero_extend:DI (subreg:QI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:DI 2 "reg_or_cint_operand" "ri,ri")) 0)) + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i,r,i")) 0)) (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,r") (zero_extend:DI (subreg:QI (rotate:DI (match_dup 1) (match_dup 2)) 0)))] "TARGET_64BIT" "@ - rld%I2cl. %0,%1,%H2,56 + rldcl. %0,%1,%2,56 + rldicl. %0,%1,%H2,56 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -6125,28 +6956,33 @@ "") (define_insn "*rotldi3_internal10" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") + [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r") (zero_extend:DI (subreg:HI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r") - (match_operand:DI 2 "reg_or_cint_operand" "ri")) 0)))] + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i")) 0)))] "TARGET_POWERPC64" - "rld%I2cl %0,%1,%H2,48") + "@ + rldcl %0,%1,%2,48 + rldicl %0,%1,%H2,48" + [(set_attr "type" "var_shift_rotate,integer")]) (define_insn "*rotldi3_internal11" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (zero_extend:DI (subreg:HI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:DI 2 "reg_or_cint_operand" "ri,ri")) 0)) + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i,r,i")) 0)) (const_int 0))) - (clobber (match_scratch:DI 3 "=r,r"))] + (clobber (match_scratch:DI 3 "=r,r,r,r"))] "TARGET_64BIT" "@ - rld%I2cl. %3,%1,%H2,48 + rldcl. %3,%1,%2,48 + rldicl. %3,%1,%H2,48 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -6167,20 +7003,22 @@ "") (define_insn "*rotldi3_internal12" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (zero_extend:DI (subreg:HI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:DI 2 "reg_or_cint_operand" "ri,ri")) 0)) + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i,r,i")) 0)) (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,r") (zero_extend:DI (subreg:HI (rotate:DI (match_dup 1) (match_dup 2)) 0)))] "TARGET_64BIT" "@ - rld%I2cl. %0,%1,%H2,48 + rldcl. %0,%1,%2,48 + rldicl. %0,%1,%H2,48 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -6200,28 +7038,33 @@ "") (define_insn "*rotldi3_internal13" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") + [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r") (zero_extend:DI (subreg:SI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r") - (match_operand:DI 2 "reg_or_cint_operand" "ri")) 0)))] + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i")) 0)))] "TARGET_POWERPC64" - "rld%I2cl %0,%1,%H2,32") + "@ + rldcl %0,%1,%2,32 + rldicl %0,%1,%H2,32" + [(set_attr "type" "var_shift_rotate,integer")]) (define_insn "*rotldi3_internal14" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (zero_extend:DI (subreg:SI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:DI 2 "reg_or_cint_operand" "ri,ri")) 0)) + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i,r,i")) 0)) (const_int 0))) - (clobber (match_scratch:DI 3 "=r,r"))] + (clobber (match_scratch:DI 3 "=r,r,r,r"))] "TARGET_64BIT" "@ - rld%I2cl. %3,%1,%H2,32 + rldcl. %3,%1,%2,32 + rldicl. %3,%1,%H2,32 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -6242,20 +7085,22 @@ "") (define_insn "*rotldi3_internal15" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") (compare:CC (zero_extend:DI (subreg:SI - (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:DI 2 "reg_or_cint_operand" "ri,ri")) 0)) + (rotate:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:DI 2 "reg_or_cint_operand" "r,i,r,i")) 0)) (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,r") (zero_extend:DI (subreg:SI (rotate:DI (match_dup 1) (match_dup 2)) 0)))] "TARGET_64BIT" "@ - rld%I2cl. %0,%1,%H2,32 + rldcl. %0,%1,%2,32 + rldicl. %0,%1,%H2,32 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -6293,24 +7138,29 @@ }") (define_insn "*ashldi3_internal1" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") - (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r") - (match_operand:SI 2 "reg_or_cint_operand" "ri")))] + [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i")))] "TARGET_POWERPC64" - "sld%I2 %0,%1,%H2") + "@ + sld %0,%1,%2 + sldi %0,%1,%H2" + [(set_attr "type" "var_shift_rotate,shift")]) (define_insn "*ashldi3_internal2" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") - (compare:CC (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (clobber (match_scratch:DI 3 "=r,r"))] + (clobber (match_scratch:DI 3 "=r,r,r,r"))] "TARGET_64BIT" "@ - sld%I2. %3,%1,%H2 + sld. %3,%1,%2 + sldi. %3,%1,%H2 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -6327,18 +7177,20 @@ "") (define_insn "*ashldi3_internal3" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") - (compare:CC (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,r") (ashift:DI (match_dup 1) (match_dup 2)))] "TARGET_64BIT" "@ - sld%I2. %0,%1,%H2 + sld. %0,%1,%2 + sldi. %0,%1,%H2 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -6375,7 +7227,7 @@ "@ rldic. %4,%1,%H2,%W3 #" - [(set_attr "type" "delayed_compare") + [(set_attr "type" "compare") (set_attr "length" "4,8")]) (define_split @@ -6409,7 +7261,7 @@ "@ rldic. %0,%1,%H2,%W3 #" - [(set_attr "type" "delayed_compare") + [(set_attr "type" "compare") (set_attr "length" "4,8")]) (define_split @@ -6435,7 +7287,7 @@ [(set (match_operand:DI 0 "gpc_reg_operand" "=r") (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r") (match_operand:SI 2 "const_int_operand" "i")) - (match_operand:DI 3 "mask_operand" "n")))] + (match_operand:DI 3 "mask64_operand" "n")))] "TARGET_POWERPC64 && includes_rldicr_lshift_p (operands[2], operands[3])" "rldicr %0,%1,%H2,%S3") @@ -6444,14 +7296,14 @@ (compare:CC (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") (match_operand:SI 2 "const_int_operand" "i,i")) - (match_operand:DI 3 "mask_operand" "n,n")) + (match_operand:DI 3 "mask64_operand" "n,n")) (const_int 0))) (clobber (match_scratch:DI 4 "=r,r"))] "TARGET_64BIT && includes_rldicr_lshift_p (operands[2], operands[3])" "@ rldicr. %4,%1,%H2,%S3 #" - [(set_attr "type" "delayed_compare") + [(set_attr "type" "compare") (set_attr "length" "4,8")]) (define_split @@ -6459,7 +7311,7 @@ (compare:CC (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "") (match_operand:SI 2 "const_int_operand" "")) - (match_operand:DI 3 "mask_operand" "")) + (match_operand:DI 3 "mask64_operand" "")) (const_int 0))) (clobber (match_scratch:DI 4 ""))] "TARGET_POWERPC64 && reload_completed @@ -6477,7 +7329,7 @@ (compare:CC (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") (match_operand:SI 2 "const_int_operand" "i,i")) - (match_operand:DI 3 "mask_operand" "n,n")) + (match_operand:DI 3 "mask64_operand" "n,n")) (const_int 0))) (set (match_operand:DI 0 "gpc_reg_operand" "=r,r") (and:DI (ashift:DI (match_dup 1) (match_dup 2)) (match_dup 3)))] @@ -6485,7 +7337,7 @@ "@ rldicr. %0,%1,%H2,%S3 #" - [(set_attr "type" "delayed_compare") + [(set_attr "type" "compare") (set_attr "length" "4,8")]) (define_split @@ -6493,7 +7345,7 @@ (compare:CC (and:DI (ashift:DI (match_operand:DI 1 "gpc_reg_operand" "") (match_operand:SI 2 "const_int_operand" "")) - (match_operand:DI 3 "mask_operand" "")) + (match_operand:DI 3 "mask64_operand" "")) (const_int 0))) (set (match_operand:DI 0 "gpc_reg_operand" "") (and:DI (ashift:DI (match_dup 1) (match_dup 2)) (match_dup 3)))] @@ -6526,24 +7378,29 @@ }") (define_insn "*lshrdi3_internal1" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") - (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r") - (match_operand:SI 2 "reg_or_cint_operand" "ri")))] + [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i")))] "TARGET_POWERPC64" - "srd%I2 %0,%1,%H2") + "@ + srd %0,%1,%2 + srdi %0,%1,%H2" + [(set_attr "type" "var_shift_rotate,shift")]) (define_insn "*lshrdi3_internal2" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") - (compare:CC (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (clobber (match_scratch:DI 3 "=r,r"))] + (clobber (match_scratch:DI 3 "=r,r,r,r"))] "TARGET_64BIT " "@ - srd%I2. %3,%1,%H2 + srd. %3,%1,%2 + srdi. %3,%1,%H2 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -6560,18 +7417,20 @@ "") (define_insn "*lshrdi3_internal3" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") - (compare:CC (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (lshiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,r") (lshiftrt:DI (match_dup 1) (match_dup 2)))] "TARGET_64BIT" "@ - srd%I2. %0,%1,%H2 + srd. %0,%1,%2 + srdi. %0,%1,%H2 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -6613,24 +7472,29 @@ }") (define_insn "*ashrdi3_internal1" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") - (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r") - (match_operand:SI 2 "reg_or_cint_operand" "ri")))] + [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i")))] "TARGET_POWERPC64" - "srad%I2 %0,%1,%H2") + "@ + srad %0,%1,%2 + sradi %0,%1,%H2" + [(set_attr "type" "var_shift_rotate,shift")]) (define_insn "*ashrdi3_internal2" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") - (compare:CC (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (clobber (match_scratch:DI 3 "=r,r"))] + (clobber (match_scratch:DI 3 "=r,r,r,r"))] "TARGET_64BIT" "@ - srad%I2. %3,%1,%H2 + srad. %3,%1,%2 + sradi. %3,%1,%H2 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 0 "cc_reg_not_cr0_operand" "") @@ -6647,18 +7511,20 @@ "") (define_insn "*ashrdi3_internal3" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,?y") - (compare:CC (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (match_operand:SI 2 "reg_or_cint_operand" "ri,ri")) + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,?y,?y") + (compare:CC (ashiftrt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,i,r,i")) (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "=r,r") + (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,r") (ashiftrt:DI (match_dup 1) (match_dup 2)))] "TARGET_64BIT" "@ - srad%I2. %0,%1,%H2 + srad. %0,%1,%2 + sradi. %0,%1,%H2 + # #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "4,8")]) + [(set_attr "type" "var_delayed_compare,delayed_compare,var_delayed_compare,delayed_compare") + (set_attr "length" "4,4,8,8")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") @@ -6698,7 +7564,8 @@ (clobber (match_scratch:CC 3 ""))] "TARGET_POWERPC64 && (fixed_regs[CR0_REGNO] || !logical_operand (operands[2], DImode)) - && !mask_operand (operands[2], DImode)" + && !mask_operand (operands[2], DImode) + && !mask64_operand (operands[2], DImode)" [(set (match_dup 0) (and:DI (rotate:DI (match_dup 1) (match_dup 4)) @@ -6712,16 +7579,17 @@ }) (define_insn "*anddi3_internal2" - [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,x,x,x,?y,?y,??y,??y,?y") - (compare:CC (and:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r,r,r,r,r,r,r,r,r") - (match_operand:DI 2 "and64_2_operand" "r,S,K,J,t,r,S,K,J,t")) + [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,x,x,x,x,?y,?y,?y,??y,??y,?y") + (compare:CC (and:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r,r,r,r,r,r,r,r,r,r,r") + (match_operand:DI 2 "and64_2_operand" "r,S,T,K,J,t,r,S,T,K,J,t")) (const_int 0))) - (clobber (match_scratch:DI 3 "=r,r,r,r,r,r,r,r,r,r")) - (clobber (match_scratch:CC 4 "=X,X,X,X,X,X,X,x,x,X"))] + (clobber (match_scratch:DI 3 "=r,r,r,r,r,r,r,r,r,r,r,r")) + (clobber (match_scratch:CC 4 "=X,X,X,X,X,X,X,X,X,x,x,X"))] "TARGET_64BIT" "@ and. %3,%1,%2 rldic%B2. %3,%1,0,%S2 + rlwinm. %3,%1,0,%m2,%M2 andi. %3,%1,%b2 andis. %3,%1,%u2 # @@ -6729,9 +7597,10 @@ # # # + # #" - [(set_attr "type" "compare,delayed_compare,compare,compare,delayed_compare,compare,compare,compare,compare,compare") - (set_attr "length" "4,4,4,4,8,8,8,8,8,12")]) + [(set_attr "type" "compare,compare,delayed_compare,compare,compare,compare,compare,compare,compare,compare,compare,compare") + (set_attr "length" "4,4,4,4,4,8,8,8,8,8,8,12")]) (define_split [(set (match_operand:CC 0 "cc_reg_operand" "") @@ -6740,9 +7609,10 @@ (const_int 0))) (clobber (match_scratch:DI 3 "")) (clobber (match_scratch:CC 4 ""))] - "TARGET_POWERPC64 && reload_completed + "TARGET_64BIT && reload_completed && (fixed_regs[CR0_REGNO] || !logical_operand (operands[2], DImode)) - && !mask_operand (operands[2], DImode)" + && !mask_operand (operands[2], DImode) + && !mask64_operand (operands[2], DImode)" [(set (match_dup 3) (and:DI (rotate:DI (match_dup 1) (match_dup 5)) @@ -6759,17 +7629,18 @@ }") (define_insn "*anddi3_internal3" - [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,x,x,x,?y,?y,??y,??y,?y") - (compare:CC (and:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r,r,r,r,r,r,r,r,r") - (match_operand:DI 2 "and64_2_operand" "r,S,K,J,t,r,S,K,J,t")) + [(set (match_operand:CC 3 "cc_reg_operand" "=x,x,x,x,x,x,?y,?y,?y,??y,??y,?y") + (compare:CC (and:DI (match_operand:DI 1 "gpc_reg_operand" "%r,r,r,r,r,r,r,r,r,r,r,r") + (match_operand:DI 2 "and64_2_operand" "r,S,T,K,J,t,r,S,T,K,J,t")) (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,r,r,r,r,r,r,r") + (set (match_operand:DI 0 "gpc_reg_operand" "=r,r,r,r,r,r,r,r,r,r,r,r") (and:DI (match_dup 1) (match_dup 2))) - (clobber (match_scratch:CC 4 "=X,X,X,X,X,X,X,x,x,X"))] + (clobber (match_scratch:CC 4 "=X,X,X,X,X,X,X,X,X,x,x,X"))] "TARGET_64BIT" "@ and. %0,%1,%2 rldic%B2. %0,%1,0,%S2 + rlwinm. %0,%1,0,%m2,%M2 andi. %0,%1,%b2 andis. %0,%1,%u2 # @@ -6777,19 +7648,20 @@ # # # + # #" - [(set_attr "type" "compare,delayed_compare,compare,compare,delayed_compare,compare,compare,compare,compare,compare") - (set_attr "length" "4,4,4,4,8,8,8,8,8,12")]) + [(set_attr "type" "compare,compare,delayed_compare,compare,compare,compare,compare,compare,compare,compare,compare,compare") + (set_attr "length" "4,4,4,4,4,8,8,8,8,8,8,12")]) (define_split [(set (match_operand:CC 3 "cc_reg_not_cr0_operand" "") (compare:CC (and:DI (match_operand:DI 1 "gpc_reg_operand" "") - (match_operand:DI 2 "and_operand" "")) + (match_operand:DI 2 "and64_2_operand" "")) (const_int 0))) (set (match_operand:DI 0 "gpc_reg_operand" "") (and:DI (match_dup 1) (match_dup 2))) (clobber (match_scratch:CC 4 ""))] - "TARGET_POWERPC64 && reload_completed" + "TARGET_64BIT && reload_completed" [(parallel [(set (match_dup 0) (and:DI (match_dup 1) (match_dup 2))) (clobber (match_dup 4))]) @@ -6806,9 +7678,10 @@ (set (match_operand:DI 0 "gpc_reg_operand" "") (and:DI (match_dup 1) (match_dup 2))) (clobber (match_scratch:CC 4 ""))] - "TARGET_POWERPC64 && reload_completed + "TARGET_64BIT && reload_completed && (fixed_regs[CR0_REGNO] || !logical_operand (operands[2], DImode)) - && !mask_operand (operands[2], DImode)" + && !mask_operand (operands[2], DImode) + && !mask64_operand (operands[2], DImode)" [(set (match_dup 0) (and:DI (rotate:DI (match_dup 1) (match_dup 5)) @@ -6837,7 +7710,8 @@ if (non_logical_cint_operand (operands[2], DImode)) { HOST_WIDE_INT value; - rtx tmp = ((no_new_pseudos || rtx_equal_p (operands[0], operands[1])) + rtx tmp = ((!can_create_pseudo_p () + || rtx_equal_p (operands[0], operands[1])) ? operands[0] : gen_reg_rtx (DImode)); if (GET_CODE (operands[2]) == CONST_INT) @@ -6870,7 +7744,8 @@ if (non_logical_cint_operand (operands[2], DImode)) { HOST_WIDE_INT value; - rtx tmp = ((no_new_pseudos || rtx_equal_p (operands[0], operands[1])) + rtx tmp = ((!can_create_pseudo_p () + || rtx_equal_p (operands[0], operands[1])) ? operands[0] : gen_reg_rtx (DImode)); if (GET_CODE (operands[2]) == CONST_INT) @@ -7148,7 +8023,9 @@ value = INTVAL (offset); if (value != 0) { - rtx tmp = (no_new_pseudos ? operands[0] : gen_reg_rtx (Pmode)); + rtx tmp = (!can_create_pseudo_p () + ? operands[0] + : gen_reg_rtx (Pmode)); emit_insn (gen_movsi_got (tmp, operands[1])); emit_insn (gen_addsi3 (operands[0], tmp, offset)); DONE; @@ -7312,42 +8189,44 @@ "") (define_insn "*movcc_internal1" - [(set (match_operand:CC 0 "nonimmediate_operand" "=y,x,?y,r,r,r,r,q,cl,r,m") - (match_operand:CC 1 "nonimmediate_operand" "y,r,r,x,y,r,h,r,r,m,r"))] + [(set (match_operand:CC 0 "nonimmediate_operand" "=y,x,?y,y,r,r,r,r,r,q,cl,r,m") + (match_operand:CC 1 "general_operand" "y,r,r,O,x,y,r,I,h,r,r,m,r"))] "register_operand (operands[0], CCmode) || register_operand (operands[1], CCmode)" "@ mcrf %0,%1 mtcrf 128,%1 {rlinm|rlwinm} %1,%1,%F0,0xffffffff\;mtcrf %R0,%1\;{rlinm|rlwinm} %1,%1,%f0,0xffffffff + crxor %0,%0,%0 mfcr %0%Q1 mfcr %0%Q1\;{rlinm|rlwinm} %0,%0,%f1,0xf0000000 mr %0,%1 + {lil|li} %0,%1 mf%1 %0 mt%0 %1 mt%0 %1 {l%U1%X1|lwz%U1%X1} %0,%1 {st%U0%U1|stw%U0%U1} %1,%0" [(set (attr "type") - (cond [(eq_attr "alternative" "0") + (cond [(eq_attr "alternative" "0,3") (const_string "cr_logical") (eq_attr "alternative" "1,2") (const_string "mtcr") - (eq_attr "alternative" "5,7") + (eq_attr "alternative" "6,7,9") (const_string "integer") - (eq_attr "alternative" "6") - (const_string "mfjmpr") (eq_attr "alternative" "8") + (const_string "mfjmpr") + (eq_attr "alternative" "10") (const_string "mtjmpr") - (eq_attr "alternative" "9") + (eq_attr "alternative" "11") (const_string "load") - (eq_attr "alternative" "10") + (eq_attr "alternative" "12") (const_string "store") (ne (symbol_ref "TARGET_MFCRF") (const_int 0)) (const_string "mfcrf") ] (const_string "mfcr"))) - (set_attr "length" "4,4,12,4,8,4,4,4,4,4,4")]) + (set_attr "length" "4,4,12,4,4,8,4,4,4,4,4,4,4")]) ;; For floating-point, we normally deal with the floating-point registers ;; unless -msoft-float is used. The sole exception is that parameter passing @@ -7386,7 +8265,7 @@ }") (define_insn "*movsf_hardfloat" - [(set (match_operand:SF 0 "nonimmediate_operand" "=!r,!r,m,f,f,m,!cl,!q,!r,!h,!r,!r") + [(set (match_operand:SF 0 "nonimmediate_operand" "=!r,!r,m,f,f,m,*c*l,*q,!r,*h,!r,!r") (match_operand:SF 1 "input_operand" "r,m,r,f,m,f,r,r,h,0,G,Fn"))] "(gpc_reg_operand (operands[0], SFmode) || gpc_reg_operand (operands[1], SFmode)) @@ -7404,7 +8283,7 @@ {cror 0,0,0|nop} # #" - [(set_attr "type" "*,load,store,fp,fpload,fpstore,*,mtjmpr,*,*,*,*") + [(set_attr "type" "*,load,store,fp,fpload,fpstore,mtjmpr,*,mfjmpr,*,*,*") (set_attr "length" "4,4,4,4,4,4,4,4,4,4,4,8")]) (define_insn "*movsf_softfloat" @@ -7426,7 +8305,7 @@ # # {cror 0,0,0|nop}" - [(set_attr "type" "*,mtjmpr,*,*,load,store,*,*,*,*,*,*") + [(set_attr "type" "*,mtjmpr,*,mfjmpr,load,store,*,*,*,*,*,*") (set_attr "length" "4,4,4,4,4,4,4,4,4,4,8,4")]) @@ -7488,7 +8367,7 @@ (define_split [(set (match_operand:DF 0 "gpc_reg_operand" "") - (match_operand:DF 1 "easy_fp_constant" ""))] + (match_operand:DF 1 "const_double_operand" ""))] "TARGET_POWERPC64 && reload_completed && ((GET_CODE (operands[0]) == REG && REGNO (operands[0]) <= 31) || (GET_CODE (operands[0]) == SUBREG @@ -7546,13 +8425,12 @@ else return \"mr %0,%1\;mr %L0,%L1\"; case 1: - if (GET_CODE (operands[1]) == MEM - && (rs6000_legitimate_offset_address_p (DFmode, XEXP (operands[1], 0), - reload_completed || reload_in_progress) - || GET_CODE (XEXP (operands[1], 0)) == REG - || GET_CODE (XEXP (operands[1], 0)) == LO_SUM + if (rs6000_offsettable_memref_p (operands[1]) + || (GET_CODE (operands[1]) == MEM + && (GET_CODE (XEXP (operands[1], 0)) == LO_SUM || GET_CODE (XEXP (operands[1], 0)) == PRE_INC - || GET_CODE (XEXP (operands[1], 0)) == PRE_DEC)) + || GET_CODE (XEXP (operands[1], 0)) == PRE_DEC + || GET_CODE (XEXP (operands[1], 0)) == PRE_MODIFY))) { /* If the low-address word is used in the address, we must load it last. Otherwise, load it first. Note that we cannot have @@ -7562,7 +8440,7 @@ operands[1], 0)) return \"{l|lwz} %L0,%L1\;{l|lwz} %0,%1\"; else - return \"{l%U1|lwz%U1} %0,%1\;{l|lwz} %L0,%L1\"; + return \"{l%U1%X1|lwz%U1%X1} %0,%1\;{l|lwz} %L0,%L1\"; } else { @@ -7574,36 +8452,35 @@ operands[1], 0)) { output_asm_insn (\"{cal|la} %0,4(%0)\", &addreg); - output_asm_insn (\"{lx|lwzx} %L0,%1\", operands); + output_asm_insn (\"{l%X1|lwz%X1} %L0,%1\", operands); output_asm_insn (\"{cal|la} %0,-4(%0)\", &addreg); - return \"{lx|lwzx} %0,%1\"; + return \"{l%X1|lwz%X1} %0,%1\"; } else { - output_asm_insn (\"{lx|lwzx} %0,%1\", operands); + output_asm_insn (\"{l%X1|lwz%X1} %0,%1\", operands); output_asm_insn (\"{cal|la} %0,4(%0)\", &addreg); - output_asm_insn (\"{lx|lwzx} %L0,%1\", operands); + output_asm_insn (\"{l%X1|lwz%X1} %L0,%1\", operands); output_asm_insn (\"{cal|la} %0,-4(%0)\", &addreg); return \"\"; } } case 2: - if (GET_CODE (operands[0]) == MEM - && (rs6000_legitimate_offset_address_p (DFmode, XEXP (operands[0], 0), - reload_completed || reload_in_progress) - || GET_CODE (XEXP (operands[0], 0)) == REG - || GET_CODE (XEXP (operands[0], 0)) == LO_SUM + if (rs6000_offsettable_memref_p (operands[0]) + || (GET_CODE (operands[0]) == MEM + && (GET_CODE (XEXP (operands[0], 0)) == LO_SUM || GET_CODE (XEXP (operands[0], 0)) == PRE_INC - || GET_CODE (XEXP (operands[0], 0)) == PRE_DEC)) - return \"{st%U0|stw%U0} %1,%0\;{st|stw} %L1,%L0\"; + || GET_CODE (XEXP (operands[0], 0)) == PRE_DEC + || GET_CODE (XEXP (operands[0], 0)) == PRE_MODIFY))) + return \"{st%U0%X0|stw%U0%X0} %1,%0\;{st|stw} %L1,%L0\"; else { rtx addreg; addreg = find_addr_reg (XEXP (operands[0], 0)); - output_asm_insn (\"{stx|stwx} %1,%0\", operands); + output_asm_insn (\"{st%X0|stw%X0} %1,%0\", operands); output_asm_insn (\"{cal|la} %0,4(%0)\", &addreg); - output_asm_insn (\"{stx|stwx} %L1,%0\", operands); + output_asm_insn (\"{st%X0|stw%X0} %L1,%0\", operands); output_asm_insn (\"{cal|la} %0,-4(%0)\", &addreg); return \"\"; } @@ -7651,9 +8528,9 @@ operands[1], 0)) return \"{l|lwz} %L0,%L1\;{l|lwz} %0,%1\"; else - return \"{l%U1|lwz%U1} %0,%1\;{l|lwz} %L0,%L1\"; + return \"{l%U1%X1|lwz%U1%X1} %0,%1\;{l|lwz} %L0,%L1\"; case 2: - return \"{st%U0|stw%U0} %1,%0\;{st|stw} %L1,%L0\"; + return \"{st%U0%X0|stw%U0%X0} %1,%0\;{st|stw} %L1,%L0\"; case 3: case 4: case 5: @@ -7665,10 +8542,36 @@ ; ld/std require word-aligned displacements -> 'Y' constraint. ; List Y->r and r->Y before r->r for reload. +(define_insn "*movdf_hardfloat64_mfpgpr" + [(set (match_operand:DF 0 "nonimmediate_operand" "=Y,r,!r,f,f,m,*c*l,!r,*h,!r,!r,!r,r,f") + (match_operand:DF 1 "input_operand" "r,Y,r,f,m,f,r,h,0,G,H,F,f,r"))] + "TARGET_POWERPC64 && TARGET_MFPGPR && TARGET_HARD_FLOAT && TARGET_FPRS + && (gpc_reg_operand (operands[0], DFmode) + || gpc_reg_operand (operands[1], DFmode))" + "@ + std%U0%X0 %1,%0 + ld%U1%X1 %0,%1 + mr %0,%1 + fmr %0,%1 + lfd%U1%X1 %0,%1 + stfd%U0%X0 %1,%0 + mt%0 %1 + mf%1 %0 + {cror 0,0,0|nop} + # + # + # + mftgpr %0,%1 + mffgpr %0,%1" + [(set_attr "type" "store,load,*,fp,fpload,fpstore,mtjmpr,mfjmpr,*,*,*,*,mftgpr,mffgpr") + (set_attr "length" "4,4,4,4,4,4,4,4,4,8,12,16,4,4")]) + +; ld/std require word-aligned displacements -> 'Y' constraint. +; List Y->r and r->Y before r->r for reload. (define_insn "*movdf_hardfloat64" - [(set (match_operand:DF 0 "nonimmediate_operand" "=Y,r,!r,f,f,m,!cl,!r,!h,!r,!r,!r") + [(set (match_operand:DF 0 "nonimmediate_operand" "=Y,r,!r,f,f,m,*c*l,!r,*h,!r,!r,!r") (match_operand:DF 1 "input_operand" "r,Y,r,f,m,f,r,h,0,G,H,F"))] - "TARGET_POWERPC64 && TARGET_HARD_FLOAT && TARGET_FPRS + "TARGET_POWERPC64 && !TARGET_MFPGPR && TARGET_HARD_FLOAT && TARGET_FPRS && (gpc_reg_operand (operands[0], DFmode) || gpc_reg_operand (operands[1], DFmode))" "@ @@ -7684,7 +8587,7 @@ # # #" - [(set_attr "type" "*,load,store,fp,fpload,fpstore,mtjmpr,*,*,*,*,*") + [(set_attr "type" "store,load,*,fp,fpload,fpstore,mtjmpr,mfjmpr,*,*,*,*") (set_attr "length" "4,4,4,4,4,4,4,4,4,8,12,16")]) (define_insn "*movdf_softfloat64" @@ -7703,14 +8606,13 @@ # # {cror 0,0,0|nop}" - [(set_attr "type" "load,store,*,*,*,*,*,*,*") + [(set_attr "type" "load,store,*,mtjmpr,mfjmpr,*,*,*,*") (set_attr "length" "4,4,4,4,4,8,12,16,4")]) (define_expand "movtf" [(set (match_operand:TF 0 "general_operand" "") (match_operand:TF 1 "any_operand" ""))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) - && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" + "!TARGET_IEEEQUAD && TARGET_LONG_DOUBLE_128" "{ rs6000_emit_move (operands[0], operands[1], TFmode); DONE; }") ; It's important to list the o->f and f->o moves before f->f because @@ -7719,7 +8621,7 @@ (define_insn_and_split "*movtf_internal" [(set (match_operand:TF 0 "nonimmediate_operand" "=o,f,f,r,Y,r") (match_operand:TF 1 "input_operand" "f,o,f,YGHF,r,r"))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) + "!TARGET_IEEEQUAD && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128 && (gpc_reg_operand (operands[0], TFmode) || gpc_reg_operand (operands[1], TFmode))" @@ -7729,21 +8631,52 @@ { rs6000_split_multireg_move (operands[0], operands[1]); DONE; } [(set_attr "length" "8,8,8,20,20,16")]) +(define_insn_and_split "*movtf_softfloat" + [(set (match_operand:TF 0 "rs6000_nonimmediate_operand" "=r,Y,r") + (match_operand:TF 1 "input_operand" "YGHF,r,r"))] + "!TARGET_IEEEQUAD + && (TARGET_SOFT_FLOAT || !TARGET_FPRS) && TARGET_LONG_DOUBLE_128 + && (gpc_reg_operand (operands[0], TFmode) + || gpc_reg_operand (operands[1], TFmode))" + "#" + "&& reload_completed" + [(pc)] +{ rs6000_split_multireg_move (operands[0], operands[1]); DONE; } + [(set_attr "length" "20,20,16")]) + (define_expand "extenddftf2" + [(set (match_operand:TF 0 "nonimmediate_operand" "") + (float_extend:TF (match_operand:DF 1 "input_operand" "")))] + "!TARGET_IEEEQUAD + && TARGET_HARD_FLOAT + && (TARGET_FPRS || TARGET_E500_DOUBLE) + && TARGET_LONG_DOUBLE_128" +{ + if (TARGET_E500_DOUBLE) + emit_insn (gen_spe_extenddftf2 (operands[0], operands[1])); + else + emit_insn (gen_extenddftf2_fprs (operands[0], operands[1])); + DONE; +}) + +(define_expand "extenddftf2_fprs" [(parallel [(set (match_operand:TF 0 "nonimmediate_operand" "") (float_extend:TF (match_operand:DF 1 "input_operand" ""))) (use (match_dup 2))])] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) + "!TARGET_IEEEQUAD && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" { operands[2] = CONST0_RTX (DFmode); + /* Generate GOT reference early for SVR4 PIC. */ + if (DEFAULT_ABI == ABI_V4 && flag_pic) + operands[2] = validize_mem (force_const_mem (DFmode, operands[2])); }) (define_insn_and_split "*extenddftf2_internal" [(set (match_operand:TF 0 "nonimmediate_operand" "=o,f,&f,r") (float_extend:TF (match_operand:DF 1 "input_operand" "fr,mf,mf,rmGHF"))) (use (match_operand:DF 2 "zero_reg_mem_operand" "rf,m,f,n"))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) + "!TARGET_IEEEQUAD && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" "#" "&& reload_completed" @@ -7761,8 +8694,10 @@ (define_expand "extendsftf2" [(set (match_operand:TF 0 "nonimmediate_operand" "") (float_extend:TF (match_operand:SF 1 "gpc_reg_operand" "")))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) - && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" + "!TARGET_IEEEQUAD + && TARGET_HARD_FLOAT + && (TARGET_FPRS || TARGET_E500_DOUBLE) + && TARGET_LONG_DOUBLE_128" { rtx tmp = gen_reg_rtx (DFmode); emit_insn (gen_extendsfdf2 (tmp, operands[1])); @@ -7773,14 +8708,16 @@ (define_expand "trunctfdf2" [(set (match_operand:DF 0 "gpc_reg_operand" "") (float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "")))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) - && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" + "!TARGET_IEEEQUAD + && TARGET_HARD_FLOAT + && (TARGET_FPRS || TARGET_E500_DOUBLE) + && TARGET_LONG_DOUBLE_128" "") (define_insn_and_split "trunctfdf2_internal1" [(set (match_operand:DF 0 "gpc_reg_operand" "=f,?f") (float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "0,f")))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) && !TARGET_XL_COMPAT + "!TARGET_IEEEQUAD && !TARGET_XL_COMPAT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" "@ # @@ -7796,16 +8733,31 @@ (define_insn "trunctfdf2_internal2" [(set (match_operand:DF 0 "gpc_reg_operand" "=f") (float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "f")))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) && TARGET_XL_COMPAT + "!TARGET_IEEEQUAD && TARGET_XL_COMPAT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" "fadd %0,%1,%L1" [(set_attr "type" "fp")]) -(define_insn_and_split "trunctfsf2" +(define_expand "trunctfsf2" + [(set (match_operand:SF 0 "gpc_reg_operand" "") + (float_truncate:SF (match_operand:TF 1 "gpc_reg_operand" "")))] + "!TARGET_IEEEQUAD + && TARGET_HARD_FLOAT + && (TARGET_FPRS || TARGET_E500_DOUBLE) + && TARGET_LONG_DOUBLE_128" +{ + if (TARGET_E500_DOUBLE) + emit_insn (gen_spe_trunctfsf2 (operands[0], operands[1])); + else + emit_insn (gen_trunctfsf2_fprs (operands[0], operands[1])); + DONE; +}) + +(define_insn_and_split "trunctfsf2_fprs" [(set (match_operand:SF 0 "gpc_reg_operand" "=f") (float_truncate:SF (match_operand:TF 1 "gpc_reg_operand" "f"))) (clobber (match_scratch:DF 2 "=f"))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) + "!TARGET_IEEEQUAD && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" "#" "&& reload_completed" @@ -7816,10 +8768,12 @@ "") (define_expand "floatsitf2" - [(set (match_operand:TF 0 "gpc_reg_operand" "=f") - (float:TF (match_operand:SI 1 "gpc_reg_operand" "r")))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) - && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" + [(set (match_operand:TF 0 "gpc_reg_operand" "") + (float:TF (match_operand:SI 1 "gpc_reg_operand" "")))] + "!TARGET_IEEEQUAD + && TARGET_HARD_FLOAT + && (TARGET_FPRS || TARGET_E500_DOUBLE) + && TARGET_LONG_DOUBLE_128" { rtx tmp = gen_reg_rtx (DFmode); expand_float (tmp, operands[1], false); @@ -7840,13 +8794,29 @@ (set_attr "length" "20")]) (define_expand "fix_trunctfsi2" + [(set (match_operand:SI 0 "gpc_reg_operand" "") + (fix:SI (match_operand:TF 1 "gpc_reg_operand" "")))] + "!TARGET_IEEEQUAD + && (TARGET_POWER2 || TARGET_POWERPC) + && TARGET_HARD_FLOAT + && (TARGET_FPRS || TARGET_E500_DOUBLE) + && TARGET_LONG_DOUBLE_128" +{ + if (TARGET_E500_DOUBLE) + emit_insn (gen_spe_fix_trunctfsi2 (operands[0], operands[1])); + else + emit_insn (gen_fix_trunctfsi2_fprs (operands[0], operands[1])); + DONE; +}) + +(define_expand "fix_trunctfsi2_fprs" [(parallel [(set (match_operand:SI 0 "gpc_reg_operand" "") (fix:SI (match_operand:TF 1 "gpc_reg_operand" ""))) (clobber (match_dup 2)) (clobber (match_dup 3)) (clobber (match_dup 4)) (clobber (match_dup 5))])] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) + "!TARGET_IEEEQUAD && (TARGET_POWER2 || TARGET_POWERPC) && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" { @@ -7862,11 +8832,11 @@ (clobber (match_operand:DF 2 "gpc_reg_operand" "=f")) (clobber (match_operand:DF 3 "gpc_reg_operand" "=&f")) (clobber (match_operand:DI 4 "gpc_reg_operand" "=f")) - (clobber (match_operand:DI 5 "memory_operand" "=o"))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) + (clobber (match_operand:DI 5 "offsettable_mem_operand" "=o"))] + "!TARGET_IEEEQUAD && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" "#" - "&& (!no_new_pseudos || offsettable_nonstrict_memref_p (operands[5]))" + "&& (can_create_pseudo_p () || offsettable_nonstrict_memref_p (operands[5]))" [(pc)] { rtx lowword; @@ -7881,10 +8851,19 @@ DONE; }) -(define_insn "negtf2" +(define_expand "negtf2" + [(set (match_operand:TF 0 "gpc_reg_operand" "") + (neg:TF (match_operand:TF 1 "gpc_reg_operand" "")))] + "!TARGET_IEEEQUAD + && TARGET_HARD_FLOAT + && (TARGET_FPRS || TARGET_E500_DOUBLE) + && TARGET_LONG_DOUBLE_128" + "") + +(define_insn "negtf2_internal" [(set (match_operand:TF 0 "gpc_reg_operand" "=f") (neg:TF (match_operand:TF 1 "gpc_reg_operand" "f")))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) + "!TARGET_IEEEQUAD && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" "* { @@ -7897,21 +8876,31 @@ (set_attr "length" "8")]) (define_expand "abstf2" - [(set (match_operand:TF 0 "gpc_reg_operand" "=f") - (abs:TF (match_operand:TF 1 "gpc_reg_operand" "f")))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) - && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" + [(set (match_operand:TF 0 "gpc_reg_operand" "") + (abs:TF (match_operand:TF 1 "gpc_reg_operand" "")))] + "!TARGET_IEEEQUAD + && TARGET_HARD_FLOAT + && (TARGET_FPRS || TARGET_E500_DOUBLE) + && TARGET_LONG_DOUBLE_128" " { rtx label = gen_label_rtx (); - emit_insn (gen_abstf2_internal (operands[0], operands[1], label)); + if (TARGET_E500_DOUBLE) + { + if (flag_unsafe_math_optimizations) + emit_insn (gen_spe_abstf2_tst (operands[0], operands[1], label)); + else + emit_insn (gen_spe_abstf2_cmp (operands[0], operands[1], label)); + } + else + emit_insn (gen_abstf2_internal (operands[0], operands[1], label)); emit_label (label); DONE; }") (define_expand "abstf2_internal" - [(set (match_operand:TF 0 "gpc_reg_operand" "=f") - (match_operand:TF 1 "gpc_reg_operand" "f")) + [(set (match_operand:TF 0 "gpc_reg_operand" "") + (match_operand:TF 1 "gpc_reg_operand" "")) (set (match_dup 3) (match_dup 5)) (set (match_dup 5) (abs:DF (match_dup 5))) (set (match_dup 4) (compare:CCFP (match_dup 3) (match_dup 5))) @@ -7919,7 +8908,7 @@ (label_ref (match_operand 2 "" "")) (pc))) (set (match_dup 6) (neg:DF (match_dup 6)))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) + "!TARGET_IEEEQUAD && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" " { @@ -7937,7 +8926,7 @@ ; List r->r after r->"o<>", otherwise reload will try to reload a ; non-offsettable address by using r->r which won't make progress. (define_insn "*movdi_internal32" - [(set (match_operand:DI 0 "nonimmediate_operand" "=o<>,r,r,*f,*f,m,r") + [(set (match_operand:DI 0 "rs6000_nonimmediate_operand" "=o<>,r,r,*f,*f,m,r") (match_operand:DI 1 "input_operand" "r,r,m,f,m,f,IJKnGHF"))] "! TARGET_POWERPC64 && (gpc_reg_operand (operands[0], DImode) @@ -7974,17 +8963,42 @@ }") (define_split - [(set (match_operand:DI 0 "nonimmediate_operand" "") + [(set (match_operand:DI 0 "rs6000_nonimmediate_operand" "") (match_operand:DI 1 "input_operand" ""))] "reload_completed && !TARGET_POWERPC64 && gpr_or_gpr_p (operands[0], operands[1])" [(pc)] { rs6000_split_multireg_move (operands[0], operands[1]); DONE; }) +(define_insn "*movdi_mfpgpr" + [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,m,r,r,r,r,*f,*f,m,r,*h,*h,r,*f") + (match_operand:DI 1 "input_operand" "r,m,r,I,L,nF,R,f,m,f,*h,r,0,*f,r"))] + "TARGET_POWERPC64 && TARGET_MFPGPR && TARGET_HARD_FLOAT && TARGET_FPRS + && (gpc_reg_operand (operands[0], DImode) + || gpc_reg_operand (operands[1], DImode))" + "@ + mr %0,%1 + ld%U1%X1 %0,%1 + std%U0%X0 %1,%0 + li %0,%1 + lis %0,%v1 + # + {cal|la} %0,%a1 + fmr %0,%1 + lfd%U1%X1 %0,%1 + stfd%U0%X0 %1,%0 + mf%1 %0 + mt%0 %1 + {cror 0,0,0|nop} + mftgpr %0,%1 + mffgpr %0,%1" + [(set_attr "type" "*,load,store,*,*,*,*,fp,fpload,fpstore,mfjmpr,mtjmpr,*,mftgpr,mffgpr") + (set_attr "length" "4,4,4,4,4,20,4,4,4,4,4,4,4,4,4")]) + (define_insn "*movdi_internal64" [(set (match_operand:DI 0 "nonimmediate_operand" "=r,r,m,r,r,r,r,*f,*f,m,r,*h,*h") (match_operand:DI 1 "input_operand" "r,m,r,I,L,nF,R,f,m,f,*h,r,0"))] - "TARGET_POWERPC64 + "TARGET_POWERPC64 && (!TARGET_MFPGPR || !TARGET_HARD_FLOAT || !TARGET_FPRS) && (gpc_reg_operand (operands[0], DImode) || gpc_reg_operand (operands[1], DImode))" "@ @@ -8022,7 +9036,7 @@ ;; Use (and:DI (rotate:DI ...)) to avoid anddi3 unnecessary clobber. (define_split [(set (match_operand:DI 0 "gpc_reg_operand" "") - (match_operand:DI 1 "mask_operand" ""))] + (match_operand:DI 1 "mask64_operand" ""))] "TARGET_POWERPC64 && num_insns_constant (operands[1], DImode) > 1" [(set (match_dup 0) (const_int -1)) (set (match_dup 0) @@ -8137,7 +9151,7 @@ return \"#\"; } }" - [(set_attr "type" "store,store,*,load,load,*")]) + [(set_attr "type" "store_ux,store_ux,*,load_ux,load_ux,*")]) (define_insn "*movti_ppc64" [(set (match_operand:TI 0 "nonimmediate_operand" "=r,o<>,r") @@ -8238,7 +9252,7 @@ "TARGET_STRING && XVECLEN (operands[0], 0) == 8" "* { return rs6000_output_load_multiple (operands); }" - [(set_attr "type" "load") + [(set_attr "type" "load_ux") (set_attr "length" "32")]) (define_insn "*ldmsi7" @@ -8260,7 +9274,7 @@ "TARGET_STRING && XVECLEN (operands[0], 0) == 7" "* { return rs6000_output_load_multiple (operands); }" - [(set_attr "type" "load") + [(set_attr "type" "load_ux") (set_attr "length" "32")]) (define_insn "*ldmsi6" @@ -8280,7 +9294,7 @@ "TARGET_STRING && XVECLEN (operands[0], 0) == 6" "* { return rs6000_output_load_multiple (operands); }" - [(set_attr "type" "load") + [(set_attr "type" "load_ux") (set_attr "length" "32")]) (define_insn "*ldmsi5" @@ -8298,7 +9312,7 @@ "TARGET_STRING && XVECLEN (operands[0], 0) == 5" "* { return rs6000_output_load_multiple (operands); }" - [(set_attr "type" "load") + [(set_attr "type" "load_ux") (set_attr "length" "32")]) (define_insn "*ldmsi4" @@ -8314,7 +9328,7 @@ "TARGET_STRING && XVECLEN (operands[0], 0) == 4" "* { return rs6000_output_load_multiple (operands); }" - [(set_attr "type" "load") + [(set_attr "type" "load_ux") (set_attr "length" "32")]) (define_insn "*ldmsi3" @@ -8328,7 +9342,7 @@ "TARGET_STRING && XVECLEN (operands[0], 0) == 3" "* { return rs6000_output_load_multiple (operands); }" - [(set_attr "type" "load") + [(set_attr "type" "load_ux") (set_attr "length" "32")]) (define_expand "store_multiple" @@ -8363,32 +9377,131 @@ to = force_reg (SImode, XEXP (operands[0], 0)); op0 = replace_equiv_address (operands[0], to); - XVECEXP (operands[3], 0, 0) - = gen_rtx_SET (VOIDmode, adjust_address_nv (op0, SImode, 0), operands[1]); - XVECEXP (operands[3], 0, 1) = gen_rtx_CLOBBER (VOIDmode, - gen_rtx_SCRATCH (SImode)); + XVECEXP (operands[3], 0, 0) + = gen_rtx_SET (VOIDmode, adjust_address_nv (op0, SImode, 0), operands[1]); + XVECEXP (operands[3], 0, 1) = gen_rtx_CLOBBER (VOIDmode, + gen_rtx_SCRATCH (SImode)); + + for (i = 1; i < count; i++) + XVECEXP (operands[3], 0, i + 1) + = gen_rtx_SET (VOIDmode, + adjust_address_nv (op0, SImode, i * 4), + gen_rtx_REG (SImode, regno + i)); +}") + +(define_insn "*stmsi8" + [(match_parallel 0 "store_multiple_operation" + [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) + (match_operand:SI 2 "gpc_reg_operand" "r")) + (clobber (match_scratch:SI 3 "=X")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) + (match_operand:SI 4 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) + (match_operand:SI 5 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 12))) + (match_operand:SI 6 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 16))) + (match_operand:SI 7 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 20))) + (match_operand:SI 8 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 24))) + (match_operand:SI 9 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 28))) + (match_operand:SI 10 "gpc_reg_operand" "r"))])] + "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 9" + "{stsi|stswi} %2,%1,%O0" + [(set_attr "type" "store_ux")]) + +(define_insn "*stmsi7" + [(match_parallel 0 "store_multiple_operation" + [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) + (match_operand:SI 2 "gpc_reg_operand" "r")) + (clobber (match_scratch:SI 3 "=X")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) + (match_operand:SI 4 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) + (match_operand:SI 5 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 12))) + (match_operand:SI 6 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 16))) + (match_operand:SI 7 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 20))) + (match_operand:SI 8 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 24))) + (match_operand:SI 9 "gpc_reg_operand" "r"))])] + "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 8" + "{stsi|stswi} %2,%1,%O0" + [(set_attr "type" "store_ux")]) + +(define_insn "*stmsi6" + [(match_parallel 0 "store_multiple_operation" + [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) + (match_operand:SI 2 "gpc_reg_operand" "r")) + (clobber (match_scratch:SI 3 "=X")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) + (match_operand:SI 4 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) + (match_operand:SI 5 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 12))) + (match_operand:SI 6 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 16))) + (match_operand:SI 7 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 20))) + (match_operand:SI 8 "gpc_reg_operand" "r"))])] + "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 7" + "{stsi|stswi} %2,%1,%O0" + [(set_attr "type" "store_ux")]) + +(define_insn "*stmsi5" + [(match_parallel 0 "store_multiple_operation" + [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) + (match_operand:SI 2 "gpc_reg_operand" "r")) + (clobber (match_scratch:SI 3 "=X")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) + (match_operand:SI 4 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) + (match_operand:SI 5 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 12))) + (match_operand:SI 6 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 16))) + (match_operand:SI 7 "gpc_reg_operand" "r"))])] + "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 6" + "{stsi|stswi} %2,%1,%O0" + [(set_attr "type" "store_ux")]) - for (i = 1; i < count; i++) - XVECEXP (operands[3], 0, i + 1) - = gen_rtx_SET (VOIDmode, - adjust_address_nv (op0, SImode, i * 4), - gen_rtx_REG (SImode, regno + i)); -}") +(define_insn "*stmsi4" + [(match_parallel 0 "store_multiple_operation" + [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) + (match_operand:SI 2 "gpc_reg_operand" "r")) + (clobber (match_scratch:SI 3 "=X")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) + (match_operand:SI 4 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) + (match_operand:SI 5 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 12))) + (match_operand:SI 6 "gpc_reg_operand" "r"))])] + "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 5" + "{stsi|stswi} %2,%1,%O0" + [(set_attr "type" "store_ux")]) -(define_insn "*store_multiple_power" +(define_insn "*stmsi3" [(match_parallel 0 "store_multiple_operation" - [(set (match_operand:SI 1 "indirect_operand" "=Q") - (match_operand:SI 2 "gpc_reg_operand" "r")) - (clobber (match_scratch:SI 3 "=q"))])] - "TARGET_STRING && TARGET_POWER" - "{stsi|stswi} %2,%P1,%O0" - [(set_attr "type" "store")]) + [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) + (match_operand:SI 2 "gpc_reg_operand" "r")) + (clobber (match_scratch:SI 3 "=X")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) + (match_operand:SI 4 "gpc_reg_operand" "r")) + (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) + (match_operand:SI 5 "gpc_reg_operand" "r"))])] + "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 4" + "{stsi|stswi} %2,%1,%O0" + [(set_attr "type" "store_ux")]) -(define_insn "*stmsi8" +(define_insn "*stmsi8_power" [(match_parallel 0 "store_multiple_operation" [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) (match_operand:SI 2 "gpc_reg_operand" "r")) - (clobber (match_scratch:SI 3 "X")) + (clobber (match_scratch:SI 3 "=q")) (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) (match_operand:SI 4 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) @@ -8403,15 +9516,15 @@ (match_operand:SI 9 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 28))) (match_operand:SI 10 "gpc_reg_operand" "r"))])] - "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 9" + "TARGET_STRING && TARGET_POWER && XVECLEN (operands[0], 0) == 9" "{stsi|stswi} %2,%1,%O0" - [(set_attr "type" "store")]) + [(set_attr "type" "store_ux")]) -(define_insn "*stmsi7" +(define_insn "*stmsi7_power" [(match_parallel 0 "store_multiple_operation" [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) (match_operand:SI 2 "gpc_reg_operand" "r")) - (clobber (match_scratch:SI 3 "X")) + (clobber (match_scratch:SI 3 "=q")) (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) (match_operand:SI 4 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) @@ -8424,15 +9537,15 @@ (match_operand:SI 8 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 24))) (match_operand:SI 9 "gpc_reg_operand" "r"))])] - "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 8" + "TARGET_STRING && TARGET_POWER && XVECLEN (operands[0], 0) == 8" "{stsi|stswi} %2,%1,%O0" - [(set_attr "type" "store")]) + [(set_attr "type" "store_ux")]) -(define_insn "*stmsi6" +(define_insn "*stmsi6_power" [(match_parallel 0 "store_multiple_operation" [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) (match_operand:SI 2 "gpc_reg_operand" "r")) - (clobber (match_scratch:SI 3 "X")) + (clobber (match_scratch:SI 3 "=q")) (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) (match_operand:SI 4 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) @@ -8443,15 +9556,15 @@ (match_operand:SI 7 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 20))) (match_operand:SI 8 "gpc_reg_operand" "r"))])] - "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 7" + "TARGET_STRING && TARGET_POWER && XVECLEN (operands[0], 0) == 7" "{stsi|stswi} %2,%1,%O0" - [(set_attr "type" "store")]) + [(set_attr "type" "store_ux")]) -(define_insn "*stmsi5" +(define_insn "*stmsi5_power" [(match_parallel 0 "store_multiple_operation" [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) (match_operand:SI 2 "gpc_reg_operand" "r")) - (clobber (match_scratch:SI 3 "X")) + (clobber (match_scratch:SI 3 "=q")) (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) (match_operand:SI 4 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) @@ -8460,37 +9573,37 @@ (match_operand:SI 6 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 16))) (match_operand:SI 7 "gpc_reg_operand" "r"))])] - "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 6" + "TARGET_STRING && TARGET_POWER && XVECLEN (operands[0], 0) == 6" "{stsi|stswi} %2,%1,%O0" - [(set_attr "type" "store")]) + [(set_attr "type" "store_ux")]) -(define_insn "*stmsi4" +(define_insn "*stmsi4_power" [(match_parallel 0 "store_multiple_operation" [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) (match_operand:SI 2 "gpc_reg_operand" "r")) - (clobber (match_scratch:SI 3 "X")) + (clobber (match_scratch:SI 3 "=q")) (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) (match_operand:SI 4 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) (match_operand:SI 5 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 12))) (match_operand:SI 6 "gpc_reg_operand" "r"))])] - "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 5" + "TARGET_STRING && TARGET_POWER && XVECLEN (operands[0], 0) == 5" "{stsi|stswi} %2,%1,%O0" - [(set_attr "type" "store")]) + [(set_attr "type" "store_ux")]) -(define_insn "*stmsi3" +(define_insn "*stmsi3_power" [(match_parallel 0 "store_multiple_operation" [(set (mem:SI (match_operand:SI 1 "gpc_reg_operand" "b")) (match_operand:SI 2 "gpc_reg_operand" "r")) - (clobber (match_scratch:SI 3 "X")) + (clobber (match_scratch:SI 3 "=q")) (set (mem:SI (plus:SI (match_dup 1) (const_int 4))) (match_operand:SI 4 "gpc_reg_operand" "r")) (set (mem:SI (plus:SI (match_dup 1) (const_int 8))) (match_operand:SI 5 "gpc_reg_operand" "r"))])] - "TARGET_STRING && !TARGET_POWER && XVECLEN (operands[0], 0) == 4" + "TARGET_STRING && TARGET_POWER && XVECLEN (operands[0], 0) == 4" "{stsi|stswi} %2,%1,%O0" - [(set_attr "type" "store")]) + [(set_attr "type" "store_ux")]) (define_expand "setmemsi" [(parallel [(set (match_operand:BLK 0 "" "") @@ -8571,7 +9684,7 @@ && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 12) && REGNO (operands[4]) == 5" "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2" - [(set_attr "type" "load") + [(set_attr "type" "store_ux") (set_attr "length" "8")]) (define_insn "" @@ -8587,7 +9700,7 @@ (clobber (reg:SI 10)) (clobber (reg:SI 11)) (clobber (reg:SI 12)) - (clobber (match_scratch:SI 5 "X"))] + (clobber (match_scratch:SI 5 "=X"))] "TARGET_STRING && ! TARGET_POWER && ((INTVAL (operands[2]) > 24 && INTVAL (operands[2]) < 32) || INTVAL (operands[2]) == 0) @@ -8595,7 +9708,7 @@ && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 12) && REGNO (operands[4]) == 5" "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2" - [(set_attr "type" "load") + [(set_attr "type" "store_ux") (set_attr "length" "8")]) ;; Move up to 24 bytes at a time. The fixed registers are needed because the @@ -8634,7 +9747,7 @@ && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 10) && REGNO (operands[4]) == 5" "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2" - [(set_attr "type" "load") + [(set_attr "type" "store_ux") (set_attr "length" "8")]) (define_insn "" @@ -8648,14 +9761,14 @@ (clobber (reg:SI 8)) (clobber (reg:SI 9)) (clobber (reg:SI 10)) - (clobber (match_scratch:SI 5 "X"))] + (clobber (match_scratch:SI 5 "=X"))] "TARGET_STRING && ! TARGET_POWER && INTVAL (operands[2]) > 16 && INTVAL (operands[2]) <= 32 && (REGNO (operands[0]) < 5 || REGNO (operands[0]) > 10) && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 10) && REGNO (operands[4]) == 5" "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2" - [(set_attr "type" "load") + [(set_attr "type" "store_ux") (set_attr "length" "8")]) ;; Move up to 16 bytes at a time, using 4 fixed registers to avoid spill @@ -8690,7 +9803,7 @@ && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 8) && REGNO (operands[4]) == 5" "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2" - [(set_attr "type" "load") + [(set_attr "type" "store_ux") (set_attr "length" "8")]) (define_insn "" @@ -8702,14 +9815,14 @@ (clobber (reg:SI 6)) (clobber (reg:SI 7)) (clobber (reg:SI 8)) - (clobber (match_scratch:SI 5 "X"))] + (clobber (match_scratch:SI 5 "=X"))] "TARGET_STRING && ! TARGET_POWER && INTVAL (operands[2]) > 8 && INTVAL (operands[2]) <= 16 && (REGNO (operands[0]) < 5 || REGNO (operands[0]) > 8) && (REGNO (operands[1]) < 5 || REGNO (operands[1]) > 8) && REGNO (operands[4]) == 5" "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2" - [(set_attr "type" "load") + [(set_attr "type" "store_ux") (set_attr "length" "8")]) ;; Move up to 8 bytes at a time. @@ -8733,7 +9846,7 @@ "TARGET_STRING && TARGET_POWER && ! TARGET_POWERPC64 && INTVAL (operands[2]) > 4 && INTVAL (operands[2]) <= 8" "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2" - [(set_attr "type" "load") + [(set_attr "type" "store_ux") (set_attr "length" "8")]) (define_insn "" @@ -8742,11 +9855,11 @@ (use (match_operand:SI 2 "immediate_operand" "i")) (use (match_operand:SI 3 "immediate_operand" "i")) (clobber (match_scratch:DI 4 "=&r")) - (clobber (match_scratch:SI 5 "X"))] + (clobber (match_scratch:SI 5 "=X"))] "TARGET_STRING && ! TARGET_POWER && ! TARGET_POWERPC64 && INTVAL (operands[2]) > 4 && INTVAL (operands[2]) <= 8" "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2" - [(set_attr "type" "load") + [(set_attr "type" "store_ux") (set_attr "length" "8")]) ;; Move up to 4 bytes at a time. @@ -8770,7 +9883,7 @@ "TARGET_STRING && TARGET_POWER && INTVAL (operands[2]) > 0 && INTVAL (operands[2]) <= 4" "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2" - [(set_attr "type" "load") + [(set_attr "type" "store_ux") (set_attr "length" "8")]) (define_insn "" @@ -8779,11 +9892,11 @@ (use (match_operand:SI 2 "immediate_operand" "i")) (use (match_operand:SI 3 "immediate_operand" "i")) (clobber (match_scratch:SI 4 "=&r")) - (clobber (match_scratch:SI 5 "X"))] + (clobber (match_scratch:SI 5 "=X"))] "TARGET_STRING && ! TARGET_POWER && INTVAL (operands[2]) > 0 && INTVAL (operands[2]) <= 4" "{lsi|lswi} %4,%1,%2\;{stsi|stswi} %4,%0,%2" - [(set_attr "type" "load") + [(set_attr "type" "store_ux") (set_attr "length" "8")]) ;; Define insns that do load or store with update. Some of these we can @@ -9058,18 +10171,20 @@ "operands[0] = widen_memory_access (operands[0], V2DFmode, 0); operands[1] = gen_rtx_REG (V2DFmode, REGNO (operands[1]));") -;; after inserting conditional returns we can sometimes have +;; After inserting conditional returns we can sometimes have ;; unnecessary register moves. Unfortunately we cannot have a ;; modeless peephole here, because some single SImode sets have early ;; clobber outputs. Although those sets expand to multi-ppc-insn ;; sequences, using get_attr_length here will smash the operands ;; array. Neither is there an early_cobbler_p predicate. +;; Disallow subregs for E500 so we don't munge frob_di_df_2. (define_peephole2 [(set (match_operand:DF 0 "gpc_reg_operand" "") (match_operand:DF 1 "any_operand" "")) (set (match_operand:DF 2 "gpc_reg_operand" "") (match_dup 0))] - "peep2_reg_dead_p (2, operands[0])" + "!(TARGET_E500_DOUBLE && GET_CODE (operands[2]) == SUBREG) + && peep2_reg_dead_p (2, operands[0])" [(set (match_dup 2) (match_dup 1))]) (define_peephole2 @@ -9267,7 +10382,7 @@ ;; We move the back-chain and decrement the stack pointer. (define_expand "allocate_stack" - [(set (match_operand 0 "gpc_reg_operand" "=r") + [(set (match_operand 0 "gpc_reg_operand" "") (minus (reg 1) (match_operand 1 "reg_or_short_operand" ""))) (set (reg 1) (minus (reg 1) (match_dup 1)))] @@ -9338,51 +10453,59 @@ "" "DONE;") +;; Adjust stack pointer (op0) to a new value (op1). +;; First copy old stack backchain to new location, and ensure that the +;; scheduler won't reorder the sp assignment before the backchain write. (define_expand "restore_stack_block" - [(use (match_operand 0 "register_operand" "")) - (set (match_dup 2) (match_dup 3)) - (set (match_dup 0) (match_operand 1 "register_operand" "")) - (set (match_dup 3) (match_dup 2))] + [(set (match_dup 2) (match_dup 3)) + (set (match_dup 4) (match_dup 2)) + (set (match_dup 5) (unspec:BLK [(match_dup 5)] UNSPEC_TIE)) + (set (match_operand 0 "register_operand" "") + (match_operand 1 "register_operand" ""))] "" " { + operands[1] = force_reg (Pmode, operands[1]); operands[2] = gen_reg_rtx (Pmode); - operands[3] = gen_rtx_MEM (Pmode, operands[0]); + operands[3] = gen_frame_mem (Pmode, operands[0]); + operands[4] = gen_frame_mem (Pmode, operands[1]); + operands[5] = gen_frame_mem (BLKmode, operands[0]); }") (define_expand "save_stack_nonlocal" - [(match_operand 0 "memory_operand" "") - (match_operand 1 "register_operand" "")] + [(set (match_dup 3) (match_dup 4)) + (set (match_operand 0 "memory_operand" "") (match_dup 3)) + (set (match_dup 2) (match_operand 1 "register_operand" ""))] "" " { - rtx temp = gen_reg_rtx (Pmode); int units_per_word = (TARGET_32BIT) ? 4 : 8; /* Copy the backchain to the first word, sp to the second. */ - emit_move_insn (temp, gen_rtx_MEM (Pmode, operands[1])); - emit_move_insn (adjust_address_nv (operands[0], Pmode, 0), temp); - emit_move_insn (adjust_address_nv (operands[0], Pmode, units_per_word), - operands[1]); - DONE; + operands[0] = adjust_address_nv (operands[0], Pmode, 0); + operands[2] = adjust_address_nv (operands[0], Pmode, units_per_word); + operands[3] = gen_reg_rtx (Pmode); + operands[4] = gen_frame_mem (Pmode, operands[1]); }") (define_expand "restore_stack_nonlocal" - [(match_operand 0 "register_operand" "") - (match_operand 1 "memory_operand" "")] + [(set (match_dup 2) (match_operand 1 "memory_operand" "")) + (set (match_dup 3) (match_dup 4)) + (set (match_dup 5) (match_dup 2)) + (set (match_dup 6) (unspec:BLK [(match_dup 6)] UNSPEC_TIE)) + (set (match_operand 0 "register_operand" "") (match_dup 3))] "" " { - rtx temp = gen_reg_rtx (Pmode); int units_per_word = (TARGET_32BIT) ? 4 : 8; /* Restore the backchain from the first word, sp from the second. */ - emit_move_insn (temp, - adjust_address_nv (operands[1], Pmode, 0)); - emit_move_insn (operands[0], - adjust_address_nv (operands[1], Pmode, units_per_word)); - emit_move_insn (gen_rtx_MEM (Pmode, operands[0]), temp); - DONE; + operands[2] = gen_reg_rtx (Pmode); + operands[3] = gen_reg_rtx (Pmode); + operands[1] = adjust_address_nv (operands[1], Pmode, 0); + operands[4] = adjust_address_nv (operands[1], Pmode, units_per_word); + operands[5] = gen_frame_mem (Pmode, operands[3]); + operands[6] = gen_frame_mem (BLKmode, operands[0]); }") ;; TOC register handling. @@ -9427,7 +10550,7 @@ [(set_attr "type" "load")]) (define_insn "load_toc_v4_pic_si" - [(set (match_operand:SI 0 "register_operand" "=l") + [(set (reg:SI LR_REGNO) (unspec:SI [(const_int 0)] UNSPEC_TOC))] "DEFAULT_ABI == ABI_V4 && flag_pic == 1 && TARGET_32BIT" "bl _GLOBAL_OFFSET_TABLE_@local-4" @@ -9435,21 +10558,21 @@ (set_attr "length" "4")]) (define_insn "load_toc_v4_PIC_1" - [(set (match_operand:SI 0 "register_operand" "=l") - (match_operand:SI 1 "immediate_operand" "s")) - (use (unspec [(match_dup 1)] UNSPEC_TOC))] + [(set (reg:SI LR_REGNO) + (match_operand:SI 0 "immediate_operand" "s")) + (use (unspec [(match_dup 0)] UNSPEC_TOC))] "TARGET_ELF && DEFAULT_ABI != ABI_AIX && (flag_pic == 2 || (flag_pic && TARGET_SECURE_PLT))" - "bcl 20,31,%1\\n%1:" + "bcl 20,31,%0\\n%0:" [(set_attr "type" "branch") (set_attr "length" "4")]) (define_insn "load_toc_v4_PIC_1b" - [(set (match_operand:SI 0 "register_operand" "=l") - (unspec:SI [(match_operand:SI 1 "immediate_operand" "s")] + [(set (reg:SI LR_REGNO) + (unspec:SI [(match_operand:SI 0 "immediate_operand" "s")] UNSPEC_TOCPTR))] "TARGET_ELF && DEFAULT_ABI != ABI_AIX && flag_pic == 2" - "bcl 20,31,$+8\\n\\t.long %1-$" + "bcl 20,31,$+8\\n\\t.long %0-$" [(set_attr "type" "branch") (set_attr "length" "8")]) @@ -9504,7 +10627,8 @@ CODE_LABEL_NUMBER (operands[0])); tmplabrtx = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (tmplab)); - emit_insn (gen_load_macho_picbase (picreg, tmplabrtx)); + emit_insn (gen_load_macho_picbase (tmplabrtx)); + emit_move_insn (picreg, gen_rtx_REG (Pmode, LR_REGNO)); emit_insn (gen_macho_correct_pic (picreg, picreg, picrtx, tmplabrtx)); } else @@ -9555,7 +10679,7 @@ (use (reg:SI 11)) (set (reg:SI 2) (mem:SI (plus:SI (reg:SI 1) (const_int 20)))) - (clobber (scratch:SI))])] + (clobber (reg:SI LR_REGNO))])] "TARGET_32BIT" " { operands[2] = gen_reg_rtx (SImode); }") @@ -9577,7 +10701,7 @@ (use (reg:DI 11)) (set (reg:DI 2) (mem:DI (plus:DI (reg:DI 1) (const_int 40)))) - (clobber (scratch:SI))])] + (clobber (reg:SI LR_REGNO))])] "TARGET_64BIT" " { operands[2] = gen_reg_rtx (DImode); }") @@ -9600,7 +10724,7 @@ (use (reg:SI 11)) (set (reg:SI 2) (mem:SI (plus:SI (reg:SI 1) (const_int 20)))) - (clobber (scratch:SI))])] + (clobber (reg:SI LR_REGNO))])] "TARGET_32BIT" " { operands[3] = gen_reg_rtx (SImode); }") @@ -9623,7 +10747,7 @@ (use (reg:DI 11)) (set (reg:DI 2) (mem:DI (plus:DI (reg:DI 1) (const_int 40)))) - (clobber (scratch:SI))])] + (clobber (reg:SI LR_REGNO))])] "TARGET_64BIT" " { operands[3] = gen_reg_rtx (DImode); }") @@ -9633,7 +10757,7 @@ [(parallel [(call (mem:SI (match_operand 0 "address_operand" "")) (match_operand 1 "" "")) (use (match_operand 2 "" "")) - (clobber (scratch:SI))])] + (clobber (reg:SI LR_REGNO))])] "" " { @@ -9660,7 +10784,8 @@ gen_rtx_MEM (SImode, operands[0]), operands[1]), gen_rtx_USE (VOIDmode, operands[2]), - gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (SImode))); + gen_rtx_CLOBBER (VOIDmode, + gen_rtx_REG (Pmode, LR_REGNO))); call = emit_call_insn (gen_rtx_PARALLEL (VOIDmode, tmp)); use_reg (&CALL_INSN_FUNCTION_USAGE (call), pic_offset_table_rtx); DONE; @@ -9703,7 +10828,7 @@ (call (mem:SI (match_operand 1 "address_operand" "")) (match_operand 2 "" ""))) (use (match_operand 3 "" "")) - (clobber (scratch:SI))])] + (clobber (reg:SI LR_REGNO))])] "" " { @@ -9733,7 +10858,8 @@ operands[1]), operands[2])), gen_rtx_USE (VOIDmode, operands[3]), - gen_rtx_CLOBBER (VOIDmode, gen_rtx_SCRATCH (SImode))); + gen_rtx_CLOBBER (VOIDmode, + gen_rtx_REG (Pmode, LR_REGNO))); call = emit_call_insn (gen_rtx_PARALLEL (VOIDmode, tmp)); use_reg (&CALL_INSN_FUNCTION_USAGE (call), pic_offset_table_rtx); DONE; @@ -9783,7 +10909,7 @@ [(call (mem:SI (match_operand:SI 0 "current_file_function_operand" "s,s")) (match_operand 1 "" "g,g")) (use (match_operand:SI 2 "immediate_operand" "O,n")) - (clobber (match_scratch:SI 3 "=l,l"))] + (clobber (reg:SI LR_REGNO))] "(INTVAL (operands[2]) & CALL_LONG) == 0" "* { @@ -9802,7 +10928,7 @@ [(call (mem:SI (match_operand:DI 0 "current_file_function_operand" "s,s")) (match_operand 1 "" "g,g")) (use (match_operand:SI 2 "immediate_operand" "O,n")) - (clobber (match_scratch:SI 3 "=l,l"))] + (clobber (reg:SI LR_REGNO))] "TARGET_64BIT && (INTVAL (operands[2]) & CALL_LONG) == 0" "* { @@ -9822,7 +10948,7 @@ (call (mem:SI (match_operand:SI 1 "current_file_function_operand" "s,s")) (match_operand 2 "" "g,g"))) (use (match_operand:SI 3 "immediate_operand" "O,n")) - (clobber (match_scratch:SI 4 "=l,l"))] + (clobber (reg:SI LR_REGNO))] "(INTVAL (operands[3]) & CALL_LONG) == 0" "* { @@ -9843,7 +10969,7 @@ (call (mem:SI (match_operand:DI 1 "current_file_function_operand" "s,s")) (match_operand 2 "" "g,g"))) (use (match_operand:SI 3 "immediate_operand" "O,n")) - (clobber (match_scratch:SI 4 "=l,l"))] + (clobber (reg:SI LR_REGNO))] "TARGET_64BIT && (INTVAL (operands[3]) & CALL_LONG) == 0" "* { @@ -9872,7 +10998,7 @@ (use (reg:SI 11)) (set (reg:SI 2) (mem:SI (plus:SI (reg:SI 1) (const_int 20)))) - (clobber (match_scratch:SI 2 "=l,l"))] + (clobber (reg:SI LR_REGNO))] "TARGET_32BIT && DEFAULT_ABI == ABI_AIX" "b%T0l\;{l|lwz} 2,20(1)" [(set_attr "type" "jmpreg") @@ -9882,7 +11008,7 @@ [(call (mem:SI (match_operand:SI 0 "symbol_ref_operand" "s")) (match_operand 1 "" "g")) (use (match_operand:SI 2 "immediate_operand" "O")) - (clobber (match_scratch:SI 3 "=l"))] + (clobber (reg:SI LR_REGNO))] "TARGET_32BIT && DEFAULT_ABI == ABI_AIX && (INTVAL (operands[2]) & CALL_LONG) == 0" @@ -9897,7 +11023,7 @@ (use (reg:DI 11)) (set (reg:DI 2) (mem:DI (plus:DI (reg:DI 1) (const_int 40)))) - (clobber (match_scratch:SI 2 "=l,l"))] + (clobber (reg:SI LR_REGNO))] "TARGET_64BIT && DEFAULT_ABI == ABI_AIX" "b%T0l\;ld 2,40(1)" [(set_attr "type" "jmpreg") @@ -9907,7 +11033,7 @@ [(call (mem:SI (match_operand:DI 0 "symbol_ref_operand" "s")) (match_operand 1 "" "g")) (use (match_operand:SI 2 "immediate_operand" "O")) - (clobber (match_scratch:SI 3 "=l"))] + (clobber (reg:SI LR_REGNO))] "TARGET_64BIT && DEFAULT_ABI == ABI_AIX && (INTVAL (operands[2]) & CALL_LONG) == 0" @@ -9923,7 +11049,7 @@ (use (reg:SI 11)) (set (reg:SI 2) (mem:SI (plus:SI (reg:SI 1) (const_int 20)))) - (clobber (match_scratch:SI 3 "=l,l"))] + (clobber (reg:SI LR_REGNO))] "TARGET_32BIT && DEFAULT_ABI == ABI_AIX" "b%T1l\;{l|lwz} 2,20(1)" [(set_attr "type" "jmpreg") @@ -9934,7 +11060,7 @@ (call (mem:SI (match_operand:SI 1 "symbol_ref_operand" "s")) (match_operand 2 "" "g"))) (use (match_operand:SI 3 "immediate_operand" "O")) - (clobber (match_scratch:SI 4 "=l"))] + (clobber (reg:SI LR_REGNO))] "TARGET_32BIT && DEFAULT_ABI == ABI_AIX && (INTVAL (operands[3]) & CALL_LONG) == 0" @@ -9950,7 +11076,7 @@ (use (reg:DI 11)) (set (reg:DI 2) (mem:DI (plus:DI (reg:DI 1) (const_int 40)))) - (clobber (match_scratch:SI 3 "=l,l"))] + (clobber (reg:SI LR_REGNO))] "TARGET_64BIT && DEFAULT_ABI == ABI_AIX" "b%T1l\;ld 2,40(1)" [(set_attr "type" "jmpreg") @@ -9961,7 +11087,7 @@ (call (mem:SI (match_operand:DI 1 "symbol_ref_operand" "s")) (match_operand 2 "" "g"))) (use (match_operand:SI 3 "immediate_operand" "O")) - (clobber (match_scratch:SI 4 "=l"))] + (clobber (reg:SI LR_REGNO))] "TARGET_64BIT && DEFAULT_ABI == ABI_AIX && (INTVAL (operands[3]) & CALL_LONG) == 0" @@ -9975,11 +11101,11 @@ ;; operands[2] is the value FUNCTION_ARG returns for the VOID argument ;; which indicates how to set cr1 -(define_insn "*call_indirect_nonlocal_sysv" - [(call (mem:SI (match_operand:SI 0 "register_operand" "c,*l,c,*l")) +(define_insn "*call_indirect_nonlocal_sysv" + [(call (mem:SI (match_operand:P 0 "register_operand" "c,*l,c,*l")) (match_operand 1 "" "g,g,g,g")) (use (match_operand:SI 2 "immediate_operand" "O,O,n,n")) - (clobber (match_scratch:SI 3 "=l,l,l,l"))] + (clobber (reg:SI LR_REGNO))] "DEFAULT_ABI == ABI_V4 || DEFAULT_ABI == ABI_DARWIN" { @@ -9994,11 +11120,11 @@ [(set_attr "type" "jmpreg,jmpreg,jmpreg,jmpreg") (set_attr "length" "4,4,8,8")]) -(define_insn "*call_nonlocal_sysv" - [(call (mem:SI (match_operand:SI 0 "symbol_ref_operand" "s,s")) +(define_insn "*call_nonlocal_sysv" + [(call (mem:SI (match_operand:P 0 "symbol_ref_operand" "s,s")) (match_operand 1 "" "g,g")) (use (match_operand:SI 2 "immediate_operand" "O,n")) - (clobber (match_scratch:SI 3 "=l,l"))] + (clobber (reg:SI LR_REGNO))] "(DEFAULT_ABI == ABI_DARWIN || (DEFAULT_ABI == ABI_V4 && (INTVAL (operands[2]) & CALL_LONG) == 0))" @@ -10029,12 +11155,12 @@ [(set_attr "type" "branch,branch") (set_attr "length" "4,8")]) -(define_insn "*call_value_indirect_nonlocal_sysv" +(define_insn "*call_value_indirect_nonlocal_sysv" [(set (match_operand 0 "" "") - (call (mem:SI (match_operand:SI 1 "register_operand" "c,*l,c,*l")) + (call (mem:SI (match_operand:P 1 "register_operand" "c,*l,c,*l")) (match_operand 2 "" "g,g,g,g"))) (use (match_operand:SI 3 "immediate_operand" "O,O,n,n")) - (clobber (match_scratch:SI 4 "=l,l,l,l"))] + (clobber (reg:SI LR_REGNO))] "DEFAULT_ABI == ABI_V4 || DEFAULT_ABI == ABI_DARWIN" { @@ -10049,12 +11175,12 @@ [(set_attr "type" "jmpreg,jmpreg,jmpreg,jmpreg") (set_attr "length" "4,4,8,8")]) -(define_insn "*call_value_nonlocal_sysv" +(define_insn "*call_value_nonlocal_sysv" [(set (match_operand 0 "" "") - (call (mem:SI (match_operand:SI 1 "symbol_ref_operand" "s,s")) + (call (mem:SI (match_operand:P 1 "symbol_ref_operand" "s,s")) (match_operand 2 "" "g,g"))) (use (match_operand:SI 3 "immediate_operand" "O,n")) - (clobber (match_scratch:SI 4 "=l,l"))] + (clobber (reg:SI LR_REGNO))] "(DEFAULT_ABI == ABI_DARWIN || (DEFAULT_ABI == ABI_V4 && (INTVAL (operands[3]) & CALL_LONG) == 0))" @@ -10115,7 +11241,7 @@ [(parallel [(call (mem:SI (match_operand 0 "address_operand" "")) (match_operand 1 "" "")) (use (match_operand 2 "" "")) - (use (match_operand 3 "" "")) + (use (reg:SI LR_REGNO)) (return)])] "" " @@ -10129,8 +11255,6 @@ gcc_assert (GET_CODE (operands[1]) == CONST_INT); operands[0] = XEXP (operands[0], 0); - operands[3] = gen_reg_rtx (SImode); - }") ;; this and similar patterns must be marked as using LR, otherwise @@ -10141,7 +11265,7 @@ [(call (mem:SI (match_operand:SI 0 "current_file_function_operand" "s,s")) (match_operand 1 "" "g,g")) (use (match_operand:SI 2 "immediate_operand" "O,n")) - (use (match_operand:SI 3 "register_operand" "l,l")) + (use (reg:SI LR_REGNO)) (return)] "(INTVAL (operands[2]) & CALL_LONG) == 0" "* @@ -10161,7 +11285,7 @@ [(call (mem:SI (match_operand:DI 0 "current_file_function_operand" "s,s")) (match_operand 1 "" "g,g")) (use (match_operand:SI 2 "immediate_operand" "O,n")) - (use (match_operand:SI 3 "register_operand" "l,l")) + (use (reg:SI LR_REGNO)) (return)] "TARGET_64BIT && (INTVAL (operands[2]) & CALL_LONG) == 0" "* @@ -10182,7 +11306,7 @@ (call (mem:SI (match_operand:SI 1 "current_file_function_operand" "s,s")) (match_operand 2 "" "g,g"))) (use (match_operand:SI 3 "immediate_operand" "O,n")) - (use (match_operand:SI 4 "register_operand" "l,l")) + (use (reg:SI LR_REGNO)) (return)] "(INTVAL (operands[3]) & CALL_LONG) == 0" "* @@ -10204,7 +11328,7 @@ (call (mem:SI (match_operand:DI 1 "current_file_function_operand" "s,s")) (match_operand 2 "" "g,g"))) (use (match_operand:SI 3 "immediate_operand" "O,n")) - (use (match_operand:SI 4 "register_operand" "l,l")) + (use (reg:SI LR_REGNO)) (return)] "TARGET_64BIT && (INTVAL (operands[3]) & CALL_LONG) == 0" "* @@ -10224,7 +11348,7 @@ [(call (mem:SI (match_operand:SI 0 "symbol_ref_operand" "s")) (match_operand 1 "" "g")) (use (match_operand:SI 2 "immediate_operand" "O")) - (use (match_operand:SI 3 "register_operand" "l")) + (use (reg:SI LR_REGNO)) (return)] "TARGET_32BIT && DEFAULT_ABI == ABI_AIX @@ -10237,7 +11361,7 @@ [(call (mem:SI (match_operand:DI 0 "symbol_ref_operand" "s")) (match_operand 1 "" "g")) (use (match_operand:SI 2 "immediate_operand" "O")) - (use (match_operand:SI 3 "register_operand" "l")) + (use (reg:SI LR_REGNO)) (return)] "TARGET_64BIT && DEFAULT_ABI == ABI_AIX @@ -10251,7 +11375,7 @@ (call (mem:SI (match_operand:SI 1 "symbol_ref_operand" "s")) (match_operand 2 "" "g"))) (use (match_operand:SI 3 "immediate_operand" "O")) - (use (match_operand:SI 4 "register_operand" "l")) + (use (reg:SI LR_REGNO)) (return)] "TARGET_32BIT && DEFAULT_ABI == ABI_AIX @@ -10265,7 +11389,7 @@ (call (mem:SI (match_operand:DI 1 "symbol_ref_operand" "s")) (match_operand 2 "" "g"))) (use (match_operand:SI 3 "immediate_operand" "O")) - (use (match_operand:SI 4 "register_operand" "l")) + (use (reg:SI LR_REGNO)) (return)] "TARGET_64BIT && DEFAULT_ABI == ABI_AIX @@ -10274,11 +11398,11 @@ [(set_attr "type" "branch") (set_attr "length" "4")]) -(define_insn "*sibcall_nonlocal_sysv" - [(call (mem:SI (match_operand:SI 0 "symbol_ref_operand" "s,s")) +(define_insn "*sibcall_nonlocal_sysv" + [(call (mem:SI (match_operand:P 0 "symbol_ref_operand" "s,s")) (match_operand 1 "" "")) (use (match_operand 2 "immediate_operand" "O,n")) - (use (match_operand:SI 3 "register_operand" "l,l")) + (use (reg:SI LR_REGNO)) (return)] "(DEFAULT_ABI == ABI_DARWIN || DEFAULT_ABI == ABI_V4) @@ -10309,7 +11433,7 @@ (call (mem:SI (match_operand 1 "address_operand" "")) (match_operand 2 "" ""))) (use (match_operand 3 "" "")) - (use (match_operand 4 "" "")) + (use (reg:SI LR_REGNO)) (return)])] "" " @@ -10323,16 +11447,14 @@ gcc_assert (GET_CODE (operands[2]) == CONST_INT); operands[1] = XEXP (operands[1], 0); - operands[4] = gen_reg_rtx (SImode); - }") -(define_insn "*sibcall_value_nonlocal_sysv" +(define_insn "*sibcall_value_nonlocal_sysv" [(set (match_operand 0 "" "") - (call (mem:SI (match_operand:SI 1 "symbol_ref_operand" "s,s")) + (call (mem:SI (match_operand:P 1 "symbol_ref_operand" "s,s")) (match_operand 2 "" ""))) (use (match_operand:SI 3 "immediate_operand" "O,n")) - (use (match_operand:SI 4 "register_operand" "l,l")) + (use (reg:SI LR_REGNO)) (return)] "(DEFAULT_ABI == ABI_DARWIN || DEFAULT_ABI == ABI_V4) @@ -10464,37 +11586,37 @@ (define_expand "bunordered" [(use (match_operand 0 "" ""))] - "! (TARGET_HARD_FLOAT && TARGET_E500 && !TARGET_FPRS)" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_cbranch (UNORDERED, operands[0]); DONE; }") (define_expand "bordered" [(use (match_operand 0 "" ""))] - "! (TARGET_HARD_FLOAT && TARGET_E500 && !TARGET_FPRS)" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_cbranch (ORDERED, operands[0]); DONE; }") (define_expand "buneq" [(use (match_operand 0 "" ""))] - "" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_cbranch (UNEQ, operands[0]); DONE; }") (define_expand "bunge" [(use (match_operand 0 "" ""))] - "" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_cbranch (UNGE, operands[0]); DONE; }") (define_expand "bungt" [(use (match_operand 0 "" ""))] - "" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_cbranch (UNGT, operands[0]); DONE; }") (define_expand "bunle" [(use (match_operand 0 "" ""))] - "" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_cbranch (UNLE, operands[0]); DONE; }") (define_expand "bunlt" [(use (match_operand 0 "" ""))] - "" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_cbranch (UNLT, operands[0]); DONE; }") (define_expand "bltgt" @@ -10598,37 +11720,37 @@ (define_expand "sunordered" [(clobber (match_operand:SI 0 "gpc_reg_operand" ""))] - "! (TARGET_HARD_FLOAT && TARGET_E500 && !TARGET_FPRS)" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_sCOND (UNORDERED, operands[0]); DONE; }") (define_expand "sordered" [(clobber (match_operand:SI 0 "gpc_reg_operand" ""))] - "! (TARGET_HARD_FLOAT && TARGET_E500 && !TARGET_FPRS)" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_sCOND (ORDERED, operands[0]); DONE; }") (define_expand "suneq" [(clobber (match_operand:SI 0 "gpc_reg_operand" ""))] - "" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_sCOND (UNEQ, operands[0]); DONE; }") (define_expand "sunge" [(clobber (match_operand:SI 0 "gpc_reg_operand" ""))] - "" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_sCOND (UNGE, operands[0]); DONE; }") (define_expand "sungt" [(clobber (match_operand:SI 0 "gpc_reg_operand" ""))] - "" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_sCOND (UNGT, operands[0]); DONE; }") (define_expand "sunle" [(clobber (match_operand:SI 0 "gpc_reg_operand" ""))] - "" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_sCOND (UNLE, operands[0]); DONE; }") (define_expand "sunlt" [(clobber (match_operand:SI 0 "gpc_reg_operand" ""))] - "" + "! (TARGET_HARD_FLOAT && !TARGET_FPRS)" "{ rs6000_emit_sCOND (UNLT, operands[0]); DONE; }") (define_expand "sltgt" @@ -10727,32 +11849,47 @@ [(set_attr "type" "cmp")]) ;; If we are comparing a register for equality with a large constant, -;; we can do this with an XOR followed by a compare. But we need a scratch -;; register for the result of the XOR. - -(define_split - [(set (match_operand:CC 0 "cc_reg_operand" "") - (compare:CC (match_operand:SI 1 "gpc_reg_operand" "") - (match_operand:SI 2 "non_short_cint_operand" ""))) - (clobber (match_operand:SI 3 "gpc_reg_operand" ""))] - "find_single_use (operands[0], insn, 0) - && (GET_CODE (*find_single_use (operands[0], insn, 0)) == EQ - || GET_CODE (*find_single_use (operands[0], insn, 0)) == NE)" - [(set (match_dup 3) (xor:SI (match_dup 1) (match_dup 4))) - (set (match_dup 0) (compare:CC (match_dup 3) (match_dup 5)))] - " -{ - /* Get the constant we are comparing against, C, and see what it looks like - sign-extended to 16 bits. Then see what constant could be XOR'ed - with C to get the sign-extended value. */ +;; we can do this with an XOR followed by a compare. But this is profitable +;; only if the large constant is only used for the comparison (and in this +;; case we already have a register to reuse as scratch). +;; +;; For 64-bit registers, we could only do so if the constant's bit 15 is clear: +;; otherwise we'd need to XOR with FFFFFFFF????0000 which is not available. - HOST_WIDE_INT c = INTVAL (operands[2]); +(define_peephole2 + [(set (match_operand:SI 0 "register_operand") + (match_operand:SI 1 "logical_const_operand" "")) + (set (match_dup 0) (match_operator:SI 3 "boolean_or_operator" + [(match_dup 0) + (match_operand:SI 2 "logical_const_operand" "")])) + (set (match_operand:CC 4 "cc_reg_operand" "") + (compare:CC (match_operand:SI 5 "gpc_reg_operand" "") + (match_dup 0))) + (set (pc) + (if_then_else (match_operator 6 "equality_operator" + [(match_dup 4) (const_int 0)]) + (match_operand 7 "" "") + (match_operand 8 "" "")))] + "peep2_reg_dead_p (3, operands[0]) + && peep2_reg_dead_p (4, operands[4])" + [(set (match_dup 0) (xor:SI (match_dup 5) (match_dup 9))) + (set (match_dup 4) (compare:CC (match_dup 0) (match_dup 10))) + (set (pc) (if_then_else (match_dup 6) (match_dup 7) (match_dup 8)))] + +{ + /* Get the constant we are comparing against, and see what it looks like + when sign-extended from 16 to 32 bits. Then see what constant we could + XOR with SEXTC to get the sign-extended value. */ + rtx cnst = simplify_const_binary_operation (GET_CODE (operands[3]), + SImode, + operands[1], operands[2]); + HOST_WIDE_INT c = INTVAL (cnst); HOST_WIDE_INT sextc = ((c & 0xffff) ^ 0x8000) - 0x8000; HOST_WIDE_INT xorv = c ^ sextc; - operands[4] = GEN_INT (xorv); - operands[5] = GEN_INT (sextc); -}") + operands[9] = GEN_INT (xorv); + operands[10] = GEN_INT (sextc); +}) (define_insn "*cmpsi_internal2" [(set (match_operand:CCUNS 0 "cc_reg_operand" "=y") @@ -10836,7 +11973,7 @@ [(set (match_operand:CCFP 0 "cc_reg_operand" "=y") (compare:CCFP (match_operand:TF 1 "gpc_reg_operand" "f") (match_operand:TF 2 "gpc_reg_operand" "f")))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) && !TARGET_XL_COMPAT + "!TARGET_IEEEQUAD && !TARGET_XL_COMPAT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" "fcmpu %0,%1,%2\;bne %0,$+8\;fcmpu %0,%L1,%L2" [(set_attr "type" "fpcompare") @@ -10854,7 +11991,7 @@ (clobber (match_scratch:DF 8 "=f")) (clobber (match_scratch:DF 9 "=f")) (clobber (match_scratch:DF 10 "=f"))] - "(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) && TARGET_XL_COMPAT + "!TARGET_IEEEQUAD && TARGET_XL_COMPAT && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128" "#" "&& reload_completed" @@ -11121,58 +12258,60 @@ (define_insn_and_split "*eq" [(set (match_operand:GPR 0 "gpc_reg_operand" "=r") (eq:GPR (match_operand:GPR 1 "gpc_reg_operand" "r") - (match_operand:GPR 2 "scc_eq_operand" ""))) - (clobber (match_scratch:GPR 3 "=r")) - (clobber (match_scratch:GPR 4 "=r"))] - "" + (match_operand:GPR 2 "scc_eq_operand" "")))] + "!TARGET_POWER" "#" - "reload_completed" - [(set (match_dup 3) - (clz:GPR (match_dup 4))) + "!TARGET_POWER" + [(set (match_dup 0) + (clz:GPR (match_dup 3))) (set (match_dup 0) - (lshiftrt:GPR (match_dup 3) (match_dup 5)))] + (lshiftrt:GPR (match_dup 0) (match_dup 4)))] { if (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0) { + /* Use output operand as intermediate. */ + operands[3] = operands[0]; + if (logical_operand (operands[2], mode)) - emit_insn (gen_rtx_SET (VOIDmode, operands[4], + emit_insn (gen_rtx_SET (VOIDmode, operands[3], gen_rtx_XOR (mode, operands[1], operands[2]))); else - emit_insn (gen_rtx_SET (VOIDmode, operands[4], + emit_insn (gen_rtx_SET (VOIDmode, operands[3], gen_rtx_PLUS (mode, operands[1], negate_rtx (mode, operands[2])))); } else - operands[4] = operands[1]; + operands[3] = operands[1]; - operands[5] = GEN_INT (exact_log2 (GET_MODE_BITSIZE (mode))); + operands[4] = GEN_INT (exact_log2 (GET_MODE_BITSIZE (mode))); }) (define_insn_and_split "*eq_compare" - [(set (match_operand:CC 5 "cc_reg_operand" "=y") + [(set (match_operand:CC 3 "cc_reg_operand" "=y") (compare:CC (eq:P (match_operand:P 1 "gpc_reg_operand" "=r") (match_operand:P 2 "scc_eq_operand" "")) (const_int 0))) (set (match_operand:P 0 "gpc_reg_operand" "=r") - (eq:P (match_dup 1) (match_dup 2))) - (clobber (match_scratch:P 3 "=r")) - (clobber (match_scratch:P 4 "=r"))] - "" + (eq:P (match_dup 1) (match_dup 2)))] + "!TARGET_POWER && optimize_size" "#" - "reload_completed" - [(set (match_dup 3) + "!TARGET_POWER && optimize_size" + [(set (match_dup 0) (clz:P (match_dup 4))) - (parallel [(set (match_dup 5) - (compare:CC (lshiftrt:P (match_dup 3) (match_dup 6)) + (parallel [(set (match_dup 3) + (compare:CC (lshiftrt:P (match_dup 0) (match_dup 5)) (const_int 0))) (set (match_dup 0) - (lshiftrt:P (match_dup 3) (match_dup 6)))])] + (lshiftrt:P (match_dup 0) (match_dup 5)))])] { if (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0) { + /* Use output operand as intermediate. */ + operands[4] = operands[0]; + if (logical_operand (operands[2], mode)) emit_insn (gen_rtx_SET (VOIDmode, operands[4], gen_rtx_XOR (mode, @@ -11186,9 +12325,24 @@ else operands[4] = operands[1]; - operands[6] = GEN_INT (exact_log2 (GET_MODE_BITSIZE (mode))); + operands[5] = GEN_INT (exact_log2 (GET_MODE_BITSIZE (mode))); }) +(define_insn "*eqsi_power" + [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r,r") + (eq:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r,r") + (match_operand:SI 2 "reg_or_cint_operand" "r,O,K,L,I"))) + (clobber (match_scratch:SI 3 "=r,&r,r,r,r"))] + "TARGET_POWER" + "@ + xor %0,%1,%2\;{sfi|subfic} %3,%0,0\;{ae|adde} %0,%3,%0 + {sfi|subfic} %3,%1,0\;{ae|adde} %0,%3,%1 + {xoril|xori} %0,%1,%b2\;{sfi|subfic} %3,%0,0\;{ae|adde} %0,%3,%0 + {xoriu|xoris} %0,%1,%u2\;{sfi|subfic} %3,%0,0\;{ae|adde} %0,%3,%0 + {sfi|subfic} %0,%1,%2\;{sfi|subfic} %3,%0,0\;{ae|adde} %0,%3,%0" + [(set_attr "type" "three,two,three,three,three") + (set_attr "length" "12,8,12,12,12")]) + ;; We have insns of the form shown by the first define_insn below. If ;; there is something inside the comparison operation, we must split it. (define_split @@ -11204,7 +12358,7 @@ (set (match_dup 2) (plus:SI (match_op_dup 1 [(match_dup 2) (match_dup 3)]) (match_dup 4)))]) -(define_insn "" +(define_insn "*plus_eqsi" [(set (match_operand:SI 0 "gpc_reg_operand" "=&r,&r,&r,&r,&r") (plus:SI (eq:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r,r") (match_operand:SI 2 "scc_eq_operand" "r,O,K,L,I")) @@ -11219,7 +12373,7 @@ [(set_attr "type" "three,two,three,three,three") (set_attr "length" "12,8,12,12,12")]) -(define_insn "" +(define_insn "*compare_plus_eqsi" [(set (match_operand:CC 0 "cc_reg_operand" "=x,x,x,x,x,?y,?y,?y,?y,?y") (compare:CC (plus:SI @@ -11228,7 +12382,7 @@ (match_operand:SI 3 "gpc_reg_operand" "r,r,r,r,r,r,r,r,r,r")) (const_int 0))) (clobber (match_scratch:SI 4 "=&r,&r,&r,&r,&r,&r,&r,&r,&r,&r"))] - "TARGET_32BIT" + "TARGET_32BIT && optimize_size" "@ xor %4,%1,%2\;{sfi|subfic} %4,%4,0\;{aze.|addze.} %4,%3 {sfi|subfic} %4,%1,0\;{aze.|addze.} %4,%3 @@ -11252,7 +12406,7 @@ (match_operand:SI 3 "gpc_reg_operand" "")) (const_int 0))) (clobber (match_scratch:SI 4 ""))] - "TARGET_32BIT && reload_completed" + "TARGET_32BIT && optimize_size && reload_completed" [(set (match_dup 4) (plus:SI (eq:SI (match_dup 1) (match_dup 2)) @@ -11262,7 +12416,7 @@ (const_int 0)))] "") -(define_insn "" +(define_insn "*plus_eqsi_compare" [(set (match_operand:CC 4 "cc_reg_operand" "=x,x,x,x,x,?y,?y,?y,?y,?y") (compare:CC (plus:SI @@ -11272,7 +12426,7 @@ (const_int 0))) (set (match_operand:SI 0 "gpc_reg_operand" "=&r,&r,&r,&r,&r,&r,&r,&r,&r,&r") (plus:SI (eq:SI (match_dup 1) (match_dup 2)) (match_dup 3)))] - "TARGET_32BIT" + "TARGET_32BIT && optimize_size" "@ xor %0,%1,%2\;{sfi|subfic} %0,%0,0\;{aze.|addze.} %0,%3 {sfi|subfic} %0,%1,0\;{aze.|addze.} %0,%3 @@ -11297,7 +12451,7 @@ (const_int 0))) (set (match_operand:SI 0 "gpc_reg_operand" "") (plus:SI (eq:SI (match_dup 1) (match_dup 2)) (match_dup 3)))] - "TARGET_32BIT && reload_completed" + "TARGET_32BIT && optimize_size && reload_completed" [(set (match_dup 0) (plus:SI (eq:SI (match_dup 1) (match_dup 2)) (match_dup 3))) (set (match_dup 4) @@ -11305,19 +12459,42 @@ (const_int 0)))] "") -(define_insn "" - [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r,r,r,r") - (neg:SI (eq:SI (match_operand:SI 1 "gpc_reg_operand" "%r,r,r,r,r") - (match_operand:SI 2 "scc_eq_operand" "r,O,K,L,I"))))] - "TARGET_32BIT" - "@ - xor %0,%1,%2\;{ai|addic} %0,%0,-1\;{sfe|subfe} %0,%0,%0 - {ai|addic} %0,%1,-1\;{sfe|subfe} %0,%0,%0 - {xoril|xori} %0,%1,%b2\;{ai|addic} %0,%0,-1\;{sfe|subfe} %0,%0,%0 - {xoriu|xoris} %0,%1,%u2\;{ai|addic} %0,%0,-1\;{sfe|subfe} %0,%0,%0 - {sfi|subfic} %0,%1,%2\;{ai|addic} %0,%0,-1\;{sfe|subfe} %0,%0,%0" - [(set_attr "type" "three,two,three,three,three") - (set_attr "length" "12,8,12,12,12")]) +(define_insn "*neg_eq0" + [(set (match_operand:P 0 "gpc_reg_operand" "=r") + (neg:P (eq:P (match_operand:P 1 "gpc_reg_operand" "r") + (const_int 0))))] + "" + "{ai|addic} %0,%1,-1\;{sfe|subfe} %0,%0,%0" + [(set_attr "type" "two") + (set_attr "length" "8")]) + +(define_insn_and_split "*neg_eq" + [(set (match_operand:P 0 "gpc_reg_operand" "=r") + (neg:P (eq:P (match_operand:P 1 "gpc_reg_operand" "%r") + (match_operand:P 2 "scc_eq_operand" ""))))] + "" + "#" + "" + [(set (match_dup 0) (neg:P (eq:P (match_dup 3) (const_int 0))))] + { + if (GET_CODE (operands[2]) != CONST_INT || INTVAL (operands[2]) != 0) + { + /* Use output operand as intermediate. */ + operands[3] = operands[0]; + + if (logical_operand (operands[2], mode)) + emit_insn (gen_rtx_SET (VOIDmode, operands[3], + gen_rtx_XOR (mode, + operands[1], operands[2]))); + else + emit_insn (gen_rtx_SET (VOIDmode, operands[3], + gen_rtx_PLUS (mode, operands[1], + negate_rtx (mode, + operands[2])))); + } + else + operands[3] = operands[1]; + }) ;; Simplify (ne X (const_int 0)) on the PowerPC. No need to on the Power, ;; since it nabs/sr is just as fast. @@ -11342,7 +12519,7 @@ (set_attr "length" "8")]) ;; This is what (plus (ne X (const_int 0)) Y) looks like. -(define_insn "" +(define_insn "*plus_ne0si" [(set (match_operand:SI 0 "gpc_reg_operand" "=r") (plus:SI (lshiftrt:SI (neg:SI (abs:SI (match_operand:SI 1 "gpc_reg_operand" "r"))) @@ -11354,7 +12531,7 @@ [(set_attr "type" "two") (set_attr "length" "8")]) -(define_insn "" +(define_insn "*plus_ne0di" [(set (match_operand:DI 0 "gpc_reg_operand" "=r") (plus:DI (lshiftrt:DI (neg:DI (abs:DI (match_operand:DI 1 "gpc_reg_operand" "r"))) @@ -11366,7 +12543,7 @@ [(set_attr "type" "two") (set_attr "length" "8")]) -(define_insn "" +(define_insn "*compare_plus_ne0si" [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") (compare:CC (plus:SI (lshiftrt:SI @@ -11404,7 +12581,7 @@ (const_int 0)))] "") -(define_insn "" +(define_insn "*compare_plus_ne0di" [(set (match_operand:CC 0 "cc_reg_operand" "=x,?y") (compare:CC (plus:DI (lshiftrt:DI @@ -11439,7 +12616,7 @@ (const_int 0)))] "") -(define_insn "" +(define_insn "*plus_ne0si_compare" [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y") (compare:CC (plus:SI (lshiftrt:SI @@ -11480,7 +12657,7 @@ (const_int 0)))] "") -(define_insn "" +(define_insn "*plus_ne0di_compare" [(set (match_operand:CC 4 "cc_reg_operand" "=x,?y") (compare:CC (plus:DI (lshiftrt:DI @@ -12401,86 +13578,6 @@ (const_int 0)))] "") -(define_insn "*gt0si" - [(set (match_operand:SI 0 "gpc_reg_operand" "=r") - (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r") - (const_int 0)))] - "TARGET_32BIT" - "{sfi|subfic} %0,%1,0\;{ame|addme} %0,%0\;{sri|srwi} %0,%0,31" - [(set_attr "type" "three") - (set_attr "length" "12")]) - -(define_insn "*gt0di" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") - (gt:DI (match_operand:DI 1 "gpc_reg_operand" "r") - (const_int 0)))] - "TARGET_64BIT" - "subfic %0,%1,0\;addme %0,%0\;srdi %0,%0,63" - [(set_attr "type" "three") - (set_attr "length" "12")]) - -(define_insn "" - [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y") - (compare:CC - (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r,r") - (const_int 0)) - (const_int 0))) - (set (match_operand:SI 0 "gpc_reg_operand" "=r,r") - (gt:SI (match_dup 1) (const_int 0)))] - "TARGET_32BIT" - "@ - {sfi|subfic} %0,%1,0\;{ame|addme} %0,%0\;{sri.|srwi.} %0,%0,31 - #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "12,16")]) - -(define_split - [(set (match_operand:CC 2 "cc_reg_not_cr0_operand" "") - (compare:CC - (gt:SI (match_operand:SI 1 "gpc_reg_operand" "") - (const_int 0)) - (const_int 0))) - (set (match_operand:SI 0 "gpc_reg_operand" "") - (gt:SI (match_dup 1) (const_int 0)))] - "TARGET_32BIT && reload_completed" - [(set (match_dup 0) - (gt:SI (match_dup 1) (const_int 0))) - (set (match_dup 2) - (compare:CC (match_dup 0) - (const_int 0)))] - "") - -(define_insn "" - [(set (match_operand:CC 2 "cc_reg_operand" "=x,?y") - (compare:CC - (gt:DI (match_operand:DI 1 "gpc_reg_operand" "r,r") - (const_int 0)) - (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "=r,r") - (gt:DI (match_dup 1) (const_int 0)))] - "TARGET_64BIT" - "@ - subfic %0,%1,0\;addme %0,%0\;srdi. %0,%0,63 - #" - [(set_attr "type" "delayed_compare") - (set_attr "length" "12,16")]) - -(define_split - [(set (match_operand:CC 2 "cc_reg_not_cr0_operand" "") - (compare:CC - (gt:DI (match_operand:DI 1 "gpc_reg_operand" "") - (const_int 0)) - (const_int 0))) - (set (match_operand:DI 0 "gpc_reg_operand" "") - (gt:DI (match_dup 1) (const_int 0)))] - "TARGET_64BIT && reload_completed" - [(set (match_dup 0) - (gt:DI (match_dup 1) (const_int 0))) - (set (match_dup 2) - (compare:CC (match_dup 0) - (const_int 0)))] - "") - (define_insn "" [(set (match_operand:SI 0 "gpc_reg_operand" "=r") (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r") @@ -12520,7 +13617,7 @@ (const_int 0)))] "") -(define_insn "*plus_gt" +(define_insn "*plus_gt0" [(set (match_operand:P 0 "gpc_reg_operand" "=&r") (plus:P (gt:P (match_operand:P 1 "gpc_reg_operand" "r") (const_int 0)) @@ -12733,24 +13830,6 @@ (const_int 0)))] "") -(define_insn "*neg_gt0si" - [(set (match_operand:SI 0 "gpc_reg_operand" "=r") - (neg:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r") - (const_int 0))))] - "TARGET_32BIT" - "{sfi|subfic} %0,%1,0\;{ame|addme} %0,%0\;{srai|srawi} %0,%0,31" - [(set_attr "type" "three") - (set_attr "length" "12")]) - -(define_insn "neg_gt0di" - [(set (match_operand:DI 0 "gpc_reg_operand" "=r") - (neg:DI (gt:DI (match_operand:DI 1 "gpc_reg_operand" "r") - (const_int 0))))] - "TARGET_64BIT" - "subfic %0,%1,0\;addme %0,%0\;sradi %0,%0,63" - [(set_attr "type" "three") - (set_attr "length" "12")]) - (define_insn "" [(set (match_operand:SI 0 "gpc_reg_operand" "=r") (neg:SI (gt:SI (match_operand:SI 1 "gpc_reg_operand" "r") @@ -12860,7 +13939,7 @@ { return output_cbranch (operands[0], NULL, 0, insn); }" - [(set_attr "type" "branch") + [(set_attr "type" "jmpreg") (set_attr "length" "4")]) (define_insn "" @@ -12891,7 +13970,7 @@ { return output_cbranch (operands[0], NULL, 1, insn); }" - [(set_attr "type" "branch") + [(set_attr "type" "jmpreg") (set_attr "length" "4")]) ;; Logic on condition register values. @@ -13062,7 +14141,7 @@ (define_expand "tablejumpdi" [(set (match_dup 4) - (sign_extend:DI (match_operand:SI 0 "lwa_operand" "rm"))) + (sign_extend:DI (match_operand:SI 0 "lwa_operand" ""))) (set (match_dup 3) (plus:DI (match_dup 4) (match_dup 2))) @@ -13297,7 +14376,8 @@ (define_insn "trap" [(trap_if (const_int 1) (const_int 0))] "" - "{t 31,0,0|trap}") + "{t 31,0,0|trap}" + [(set_attr "type" "trap")]) (define_expand "conditional_trap" [(trap_if (match_operator 0 "trap_comparison_operator" @@ -13314,7 +14394,8 @@ (match_operand:GPR 2 "reg_or_short_operand" "rI")]) (const_int 0))] "" - "{t|t}%V0%I2 %1,%2") + "{t|t}%V0%I2 %1,%2" + [(set_attr "type" "trap")]) ;; Insns related to generating the function prologue and epilogue. @@ -13350,8 +14431,10 @@ (define_insn "movesi_from_cr" [(set (match_operand:SI 0 "gpc_reg_operand" "=r") - (unspec:SI [(reg:CC 68) (reg:CC 69) (reg:CC 70) (reg:CC 71) - (reg:CC 72) (reg:CC 73) (reg:CC 74) (reg:CC 75)] + (unspec:SI [(reg:CC CR0_REGNO) (reg:CC CR1_REGNO) + (reg:CC CR2_REGNO) (reg:CC CR3_REGNO) + (reg:CC CR4_REGNO) (reg:CC CR5_REGNO) + (reg:CC CR6_REGNO) (reg:CC CR7_REGNO)] UNSPEC_MOVESI_FROM_CR))] "" "mfcr %0" @@ -13362,16 +14445,17 @@ [(set (match_operand:SI 1 "memory_operand" "=m") (match_operand:SI 2 "gpc_reg_operand" "r"))])] "TARGET_MULTIPLE" - "{stm|stmw} %2,%1") + "{stm|stmw} %2,%1" + [(set_attr "type" "store_ux")]) (define_insn "*save_fpregs_" [(match_parallel 0 "any_parallel_operand" - [(clobber (match_operand:P 1 "register_operand" "=l")) - (use (match_operand:P 2 "call_operand" "s")) - (set (match_operand:DF 3 "memory_operand" "=m") - (match_operand:DF 4 "gpc_reg_operand" "f"))])] + [(clobber (reg:P 65)) + (use (match_operand:P 1 "call_operand" "s")) + (set (match_operand:DF 2 "memory_operand" "=m") + (match_operand:DF 3 "gpc_reg_operand" "f"))])] "" - "bl %z2" + "bl %z1" [(set_attr "type" "branch") (set_attr "length" "4")]) @@ -13399,8 +14483,8 @@ ; faster; for instance, on the 601 and 750. (define_expand "movsi_to_cr_one" - [(set (match_operand:CC 0 "cc_reg_operand" "=y") - (unspec:CC [(match_operand:SI 1 "gpc_reg_operand" "r") + [(set (match_operand:CC 0 "cc_reg_operand" "") + (unspec:CC [(match_operand:SI 1 "gpc_reg_operand" "") (match_dup 2)] UNSPEC_MOVESI_TO_CR))] "" "operands[2] = GEN_INT (1 << (75 - REGNO (operands[0])));") @@ -13437,14 +14521,15 @@ ; The load-multiple instructions have similar properties. ; Note that "load_multiple" is a name known to the machine-independent -; code that actually corresponds to the powerpc load-string. +; code that actually corresponds to the PowerPC load-string. (define_insn "*lmw" [(match_parallel 0 "lmw_operation" [(set (match_operand:SI 1 "gpc_reg_operand" "=r") (match_operand:SI 2 "memory_operand" "m"))])] "TARGET_MULTIPLE" - "{lm|lmw} %1,%2") + "{lm|lmw} %1,%2" + [(set_attr "type" "load_ux")]) (define_insn "*return_internal_" [(return) @@ -13459,12 +14544,12 @@ (define_insn "*return_and_restore_fpregs_" [(match_parallel 0 "any_parallel_operand" [(return) - (use (match_operand:P 1 "register_operand" "l")) - (use (match_operand:P 2 "call_operand" "s")) - (set (match_operand:DF 3 "gpc_reg_operand" "=f") - (match_operand:DF 4 "memory_operand" "m"))])] + (use (reg:P 65)) + (use (match_operand:P 1 "call_operand" "s")) + (set (match_operand:DF 2 "gpc_reg_operand" "=f") + (match_operand:DF 3 "memory_operand" "m"))])] "" - "b %z2") + "b %z1") ; This is used in compiling the unwind routines. (define_expand "eh_return" @@ -13515,3 +14600,5 @@ (include "sync.md") (include "altivec.md") (include "spe.md") +(include "dfp.md") +(include "paired.md")