diff options
Diffstat (limited to 'gcc')
47 files changed, 2153 insertions, 67 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 8dd8eb5c57e..10aab9ca08a 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,112 @@ +2008-10-02 David Edelsohn <edelsohn@gnu.org> + + * config/rs6000/rs6000.c (USE_FP_FOR_ARG_P): Revert + TARGET_DOUBLE_FLOAT, TARGET_SINGLE_FLOAT. + (function_arg_advance): Condition on TARGET_DOUBLE_FLOAT, + TARGET_SINGLE_FLOAT. + Revert SCALAR_FLOAT_MODE_P condition. + (function_arg): Condition on TARGET_DOUBLE_FLOAT, + TARGET_SINGLE_FLOAT. + (rs6000_function_value): Revert TARGET_DOUBLE_FLOAT, + TARGET_SINGLE_FLOAT. + +2008-10-02 Daniel Jacobowitz <dan@codesourcery.com> + + * builtins.c (fold_builtin_pow): Check for 0 ** NEGATIVE. + +2008-10-02 Richard Guenther <rguenther@suse.de> + + PR middle-end/37713 + * tree-ssa.c (useless_type_conversion_p_1): For COMPLEX_TYPE + and VECTOR_TYPE recurse with useless_type_conversion_p which + properly handles void pointer conversion. + +2008-10-02 Danny Smith <dannysmith@users.sourceforge.net> + + PR target/37528 + * config/i386/mingw32.h (LIBGCC_SPEC) : Replace with .. + (REAL_LIBGCC_SPEC): New. Always include -lgcc. + +2008-10-01 Andrew Pinski <andrew_pinski@playstation.sony.com> + + * config/rs6000/rs6000-c.c (altivec_resolve_overloaded_builtin): + Handle ALTIVEC_BUILTIN_VEC_SPLATS, ALTIVEC_BUILTIN_VEC_PROMOTE, + ALTIVEC_BUILTIN_VEC_EXTRACT, and ALTIVEC_BUILTIN_VEC_INSERT specially, + they translate to non builtins. + * config/rs6000/rs6000.c (altivec_init_builtins): Add new variable + opaque_ftype_opaque. Define builtins __builtin_vec_splats, + __builtin_vec_promote, __builtin_vec_extract, and + __builtin_vec_insert. + * config/rs6000/rs6000.h (enum rs6000_builtins): Add + ALTIVEC_BUILTIN_VEC_EXTRACT, ALTIVEC_BUILTIN_VEC_PROMOTE, + ALTIVEC_BUILTIN_VEC_INSERT, and ALTIVEC_BUILTIN_VEC_SPLATS. + * config/rs6000/altivec.h (vec_extract): Define + (vec_insert): Define. + (vec_splats): Define. + (vec_promote): Define. + +2008-10-01 Andrew Pinski <andrew_pinski@playstation.sony.com> + Yukishige Shibata <shibata@rd.scei.sony.co.jp> + Trevor Smigiel <Trevor_Smigiel@playstation.sony.com> + + * config/rs6000/rs6000-c.c (altivec_overloaded_builtins): Add Cell + Altivec intrinsics. + * config/rs6000/rs6000.c (altivec_expand_lv_builtin): Delete + prototype. Add new parameter, blk. + Use BLKmode for the MEM if blk is true. + (altivec_expand_builtin): Handle ALTIVEC_BUILTIN_STVLX, + ALTIVEC_BUILTIN_STVLXL, ALTIVEC_BUILTIN_STVRX, and + ALTIVEC_BUILTIN_STVRXL. + Update usage of altivec_expand_lv_builtin. + Handle ALTIVEC_BUILTIN_LVLX, ALTIVEC_BUILTIN_LVLXL, + ALTIVEC_BUILTIN_LVRX, and ALTIVEC_BUILTIN_LVRXL. + (altivec_init_builtins): If compiling for the Cell, also define the + cell VMX builtins. + * config/rs6000/rs6000.h (rs6000_builtins): Define + ALTIVEC_BUILTIN_LVLX, ALTIVEC_BUILTIN_LVLXL, ALTIVEC_BUILTIN_LVRX, + ALTIVEC_BUILTIN_LVRXL, ALTIVEC_BUILTIN_STVLX, ALTIVEC_BUILTIN_STVLXL, + ALTIVEC_BUILTIN_STVRX, ALTIVEC_BUILTIN_STVRXL, + ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_VEC_LVLXL, + ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_VEC_LVRXL, + ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_VEC_STVLXL, + ALTIVEC_BUILTIN_VEC_STVRX, and ALTIVEC_BUILTIN_VEC_STVRXL. + * config/rs6000/altivec.md (define_constants): Define UNSPEC_LVLX, + UNSPEC_LVLXL, UNSPEC_LVRX, UNSPEC_LVRXL, UNSPEC_STVLX, UNSPEC_STVLXL, + UNSPEC_STVRX, and UNSPEC_STVRXL. + (altivec_lvlx): New pattern. + (altivec_lvlxl): New pattern. + (altivec_lvrx): New pattern. + (altivec_lvrxl): New pattern. + (altivec_stvlx): New pattern. + (altivec_stvlxl): New pattern. + (altivec_stvrx): New pattern. + (altivec_stvrxl): New pattern. + * config/rs6000/altivec.h (vec_lvlx): Define if PPU is defined. + (vec_lvlxl): Likewise. + (vec_lvrx): Define if PPU is defined. + (vec_lvrxl): Likewise. + (vec_stvlx): Define if PPU is defined. + (vec_stvlxl): Likewise. + (vec_stvrx): Define if PPU is defined. + (vec_stvrxl): Likewise. + +2008-10-01 Geert Bosch <bosch@adacore.com> + + * tree.c (contains_placeholder_p): Return 0 for a SAVE_EXPR. + +2008-10-01 Richard Guenther <rguenther@suse.de> + + PR tree-optimization/37617 + * tree-ssa-pre.c (create_expression_by_pieces): During FRE + do not add to the NEW_SETS. + +2008-10-01 Richard Guenther <rguenther@suse.de> + + PR middle-end/37285 + * tree-vrp.c (execute_vrp): If we optimized away the default + case make sure to promote the label that got in place of it + to a default case label. + 2008-10-01 Richard Henderson <rth@redhat.com> PR tree-opt/35737 @@ -136,8 +245,8 @@ 2008-09-29 Tobias Grosser <grosser@fim.uni-passau.de> - * graphite.c (dot_all_scops_1): Remove unused checks. SCoPs always have - exit and entry. + * graphite.c (dot_all_scops_1): Remove unused checks. SCoPs always + have exit and entry. (new_scop): Take entry and exit edge to define new SCoP. (sd_region_p): New structure used during SCoP detection. (move_scops): Delete. @@ -177,7 +286,7 @@ for SHmedia. 2008-09-28 Andrew Pinski <andrew_pinski@playstation.sony.com> - Kaushal Kantawala <kaushal_kantawala@playstation.sony.com> + Kaushal Kantawala <kaushal_kantawala@playstation.sony.com> PR tree-opt/36891 * tree-ssa-loop-im.c (rewrite_reciprocal): Set DECL_GIMPLE_REG_P on @@ -203,7 +312,7 @@ 2008-09-26 Vladimir Makarov <vmakarov@redhat.com> Revert: - 2008-09-25 Vladimir Makarov <vmakarov@redhat.com> + 2008-09-25 Vladimir Makarov <vmakarov@redhat.com> * ira-lives.c:... * doc/rtl.texi:... @@ -230,7 +339,7 @@ CL_SAVE as first argument. 2008-09-26 Peter O'Gorman <pogma@thewrittenword.com> - Steve Ellcey <sje@cup.hp.com> + Steve Ellcey <sje@cup.hp.com> * configure: Regenerate for new libtool. * aclocal.m4: Ditto. @@ -729,11 +838,12 @@ (xtensa_legitimize_address): Handle TLS symbols. (xtensa_tls_referenced_p_1): New. (xtensa_tls_referenced_p): New. - (xtensa_output_addr_const_extra): Handle UNSPEC_TPOFF and UNSPEC_DTPOFF. + (xtensa_output_addr_const_extra): Handle UNSPEC_TPOFF and + UNSPEC_DTPOFF. (XTENSA_BUILTIN_THREAD_POINTER): New. (XTENSA_BUILTIN_SET_THREAD_POINTER): New. - (xtensa_init_builtins): Set NOTHROW and READONLY for umulsidi3 builtin. - Add declarations for __builtin_thread_pointer and + (xtensa_init_builtins): Set NOTHROW and READONLY for umulsidi3 + builtin. Add declarations for __builtin_thread_pointer and __builtin_set_thread_pointer. (xtensa_fold_builtin): Recognize new builtins. (xtensa_expand_builtin): Expand new builtins. @@ -784,10 +894,11 @@ (get_reference_vars_info): ... this one, use cgraph uids. (get_local_reference_vars_info, get_global_reference_vars_info): Use cgraph instead of decl. - (ipa_reference_get_read_local, ipa_reference_get_written_local): Remove. + (ipa_reference_get_read_local, ipa_reference_get_written_local): + Remove. (ipa_reference_get_read_global, ipa_reference_get_not_read_global - ipa_reference_get_written_global, ipa_reference_get_not_written_global): Use - cgraph argument. + ipa_reference_get_written_global, + ipa_reference_get_not_written_global): Use cgraph argument. (check_call): Simplify avail check. (scan_stmt_for_static_refs): Update. (propagate_bits): Update. @@ -807,8 +918,8 @@ (ipa_reference_get_read_local, ipa_reference_get_written_local): Remove. (ipa_reference_get_read_global, ipa_reference_get_written_global, - ipa_reference_get_not_read_global, ipa_reference_get_not_written_global): - Update prototype. + ipa_reference_get_not_read_global, + ipa_reference_get_not_written_global): Update prototype. * ipa-pure-const.c (funct_state_vec): Turn into VECtor. (init_state): Remove. (node_duplication_hook_holder, node_removal_hook_holder): New. @@ -817,14 +928,15 @@ (add_new_function): Likewise. (duplicate_node_data, remove_node_data): New. (generate_summary): Register hooks; do not care about clones. - (propafate): Do not care about clones; recursive functions are not looping. + (propafate): Do not care about clones; recursive functions are + not looping. * ipa-utils.c (searchc, ipa_utils_reduced_inorder): Do not skip clones. * ipa-prop.c (edge_removal_hook_holder, node_removal_hook_holder, * edge_duplication_hook_holder, node_duplication_hook_holder): Make static. * tree-flow.h (function_ann_d): Remove reference_vars_info. - * tree-ssa-opreands.c (add_call_clobber_ops, add_call_read_ops): Update call of - ipa-reference accesors. + * tree-ssa-opreands.c (add_call_clobber_ops, add_call_read_ops): + Update call of ipa-reference accesors. 2008-09-18 Simon Baldwin <simonb@google.com> @@ -1548,12 +1660,12 @@ 2008-09-10 Ira Rosen <irar@il.ibm.com> PR tree-optimization/37385 - * tree-vect-transform.c (vect_create_data_ref_ptr): Add a new argument, - and use it as a vector type if not NULL. + * tree-vect-transform.c (vect_create_data_ref_ptr): Add a new + argument, and use it as a vector type if not NULL. (vectorizable_store): Call vect_create_data_ref_ptr with the type of vectorized rhs. - (vect_setup_realignment): Call vect_create_data_ref_ptr with additional - argument. + (vect_setup_realignment): Call vect_create_data_ref_ptr with + additional argument. (vectorizable_load): Likewise. 2008-09-10 Jakub Jelinek <jakub@redhat.com> @@ -1602,8 +1714,8 @@ (update_call_notes_after_inlining): Likewise. Push new indirect edge to *new_edges instead of new_edges. Reread IPA_EDGE_REF after ipa_check_create_edge_args. - * ipa-inline.c (cgraph_decide_recursive_inlining): Change last argument - to pointer to vector pointer. + * ipa-inline.c (cgraph_decide_recursive_inlining): Change last + argument to pointer to vector pointer. (cgraph_decide_inlining_of_small_function): Adjust cgraph_decide_recursive_inlining and ipa_propagate_indirect_call_infos calls. diff --git a/gcc/DATESTAMP b/gcc/DATESTAMP index b1be787131c..98fc65eab46 100644 --- a/gcc/DATESTAMP +++ b/gcc/DATESTAMP @@ -1 +1 @@ -20081001 +20081003 diff --git a/gcc/builtins.c b/gcc/builtins.c index 81d0ab1dfa1..ea1a16d9bdd 100644 --- a/gcc/builtins.c +++ b/gcc/builtins.c @@ -8459,9 +8459,13 @@ fold_builtin_pow (tree fndecl, tree arg0, tree arg1, tree type) real_from_integer (&cint, VOIDmode, n, n < 0 ? -1 : 0, 0); if (real_identical (&c, &cint)) { - /* Attempt to evaluate pow at compile-time. */ + /* Attempt to evaluate pow at compile-time, unless this should + raise an exception. */ if (TREE_CODE (arg0) == REAL_CST - && !TREE_OVERFLOW (arg0)) + && !TREE_OVERFLOW (arg0) + && (n > 0 + || (!flag_trapping_math && !flag_errno_math) + || !REAL_VALUES_EQUAL (TREE_REAL_CST (arg0), dconst0))) { REAL_VALUE_TYPE x; bool inexact; diff --git a/gcc/config/i386/mingw32.h b/gcc/config/i386/mingw32.h index bb5fd7f7e6e..7a1ae9ebc6b 100644 --- a/gcc/config/i386/mingw32.h +++ b/gcc/config/i386/mingw32.h @@ -89,10 +89,12 @@ along with GCC; see the file COPYING3. If not see %(shared_libgcc_undefs)" /* Include in the mingw32 libraries with libgcc */ -#undef LIBGCC_SPEC -#define LIBGCC_SPEC \ +#undef REAL_LIBGCC_SPEC +#define REAL_LIBGCC_SPEC \ "-lmingw32 \ - %{shared-libgcc:-lgcc_s} -lgcc \ + %{shared-libgcc:-lgcc_s} \ + %{!shared-libgcc:-lgcc_eh} \ + -lgcc \ -lmoldname -lmingwex -lmsvcrt" #undef STARTFILE_SPEC diff --git a/gcc/config/i386/winnt.c b/gcc/config/i386/winnt.c index 8ef79058a7d..f4356c8bb94 100644 --- a/gcc/config/i386/winnt.c +++ b/gcc/config/i386/winnt.c @@ -352,8 +352,16 @@ i386_pe_strip_name_encoding_full (const char *str) /* Strip trailing "@n". */ p = strchr (name, '@'); if (p) - return ggc_alloc_string (name, p - name); - + { + /* We need to replace the suffix with a null terminator. + Do that before using ggc_alloc_string to allocate the + const char *. */ + size_t len = p - name; + char *newname = XALLOCAVEC (char, len + 1); + memcpy (newname, name, len); + newname [len] = 0; + return ggc_alloc_string (newname, len); + } return name; } diff --git a/gcc/config/rs6000/altivec.h b/gcc/config/rs6000/altivec.h index dc9cb83dd78..cfe384c27c6 100644 --- a/gcc/config/rs6000/altivec.h +++ b/gcc/config/rs6000/altivec.h @@ -205,6 +205,13 @@ #define vec_lvebx __builtin_vec_lvebx #define vec_lvehx __builtin_vec_lvehx #define vec_lvewx __builtin_vec_lvewx +/* Cell only intrinsics. */ +#ifdef __PPU__ +#define vec_lvlx __builtin_vec_lvlx +#define vec_lvlxl __builtin_vec_lvlxl +#define vec_lvrx __builtin_vec_lvrx +#define vec_lvrxl __builtin_vec_lvrxl +#endif #define vec_lvsl __builtin_vec_lvsl #define vec_lvsr __builtin_vec_lvsr #define vec_max __builtin_vec_max @@ -239,6 +246,13 @@ #define vec_stvebx __builtin_vec_stvebx #define vec_stvehx __builtin_vec_stvehx #define vec_stvewx __builtin_vec_stvewx +/* Cell only intrinsics. */ +#ifdef __PPU__ +#define vec_stvlx __builtin_vec_stvlx +#define vec_stvlxl __builtin_vec_stvlxl +#define vec_stvrx __builtin_vec_stvrx +#define vec_stvrxl __builtin_vec_stvrxl +#endif #define vec_sub __builtin_vec_sub #define vec_subs __builtin_vec_subs #define vec_sum __builtin_vec_sum @@ -290,6 +304,11 @@ #define vec_vsubuws __builtin_vec_vsubuws #define vec_xor __builtin_vec_xor +#define vec_extract __builtin_vec_extract +#define vec_insert __builtin_vec_insert +#define vec_splats __builtin_vec_splats +#define vec_promote __builtin_vec_promote + /* Predicates. For C++, we use templates in order to allow non-parenthesized arguments. For C, instead, we use macros since non-parenthesized arguments were diff --git a/gcc/config/rs6000/altivec.md b/gcc/config/rs6000/altivec.md index 5edd248b722..9c6245ae8ac 100644 --- a/gcc/config/rs6000/altivec.md +++ b/gcc/config/rs6000/altivec.md @@ -130,6 +130,14 @@ (UNSPEC_INTERLO_V8HI 233) (UNSPEC_INTERLO_V16QI 234) (UNSPEC_INTERLO_V4SF 235) + (UNSPEC_LVLX 236) + (UNSPEC_LVLXL 237) + (UNSPEC_LVRX 238) + (UNSPEC_LVRXL 239) + (UNSPEC_STVLX 240) + (UNSPEC_STVLXL 241) + (UNSPEC_STVRX 242) + (UNSPEC_STVRXL 243) (UNSPEC_VMULWHUB 308) (UNSPEC_VMULWLUB 309) (UNSPEC_VMULWHSB 310) @@ -2677,6 +2685,76 @@ DONE; }") +;; Vector SIMD PEM v2.06c defines LVLX, LVLXL, LVRX, LVRXL, +;; STVLX, STVLXL, STVVRX, STVRXL are available only on Cell. +(define_insn "altivec_lvlx" + [(set (match_operand:V16QI 0 "register_operand" "=v") + (unspec:V16QI [(match_operand 1 "memory_operand" "Z")] + UNSPEC_LVLX))] + "TARGET_ALTIVEC && rs6000_cpu == PROCESSOR_CELL" + "lvlx %0,%y1" + [(set_attr "type" "vecload")]) + +(define_insn "altivec_lvlxl" + [(set (match_operand:V16QI 0 "register_operand" "=v") + (unspec:V16QI [(match_operand 1 "memory_operand" "Z")] + UNSPEC_LVLXL))] + "TARGET_ALTIVEC && rs6000_cpu == PROCESSOR_CELL" + "lvlxl %0,%y1" + [(set_attr "type" "vecload")]) + +(define_insn "altivec_lvrx" + [(set (match_operand:V16QI 0 "register_operand" "=v") + (unspec:V16QI [(match_operand 1 "memory_operand" "Z")] + UNSPEC_LVRX))] + "TARGET_ALTIVEC && rs6000_cpu == PROCESSOR_CELL" + "lvrx %0,%y1" + [(set_attr "type" "vecload")]) + +(define_insn "altivec_lvrxl" + [(set (match_operand:V16QI 0 "register_operand" "=v") + (unspec:V16QI [(match_operand 1 "memory_operand" "Z")] + UNSPEC_LVRXL))] + "TARGET_ALTIVEC && rs6000_cpu == PROCESSOR_CELL" + "lvrxl %0,%y1" + [(set_attr "type" "vecload")]) + +(define_insn "altivec_stvlx" + [(parallel + [(set (match_operand:V4SI 0 "memory_operand" "=Z") + (match_operand:V4SI 1 "register_operand" "v")) + (unspec [(const_int 0)] UNSPEC_STVLX)])] + "TARGET_ALTIVEC && rs6000_cpu == PROCESSOR_CELL" + "stvlx %1,%y0" + [(set_attr "type" "vecstore")]) + +(define_insn "altivec_stvlxl" + [(parallel + [(set (match_operand:V4SI 0 "memory_operand" "=Z") + (match_operand:V4SI 1 "register_operand" "v")) + (unspec [(const_int 0)] UNSPEC_STVLXL)])] + "TARGET_ALTIVEC && rs6000_cpu == PROCESSOR_CELL" + "stvlxl %1,%y0" + [(set_attr "type" "vecstore")]) + +(define_insn "altivec_stvrx" + [(parallel + [(set (match_operand:V4SI 0 "memory_operand" "=Z") + (match_operand:V4SI 1 "register_operand" "v")) + (unspec [(const_int 0)] UNSPEC_STVRX)])] + "TARGET_ALTIVEC && rs6000_cpu == PROCESSOR_CELL" + "stvrx %1,%y0" + [(set_attr "type" "vecstore")]) + +(define_insn "altivec_stvrxl" + [(parallel + [(set (match_operand:V4SI 0 "memory_operand" "=Z") + (match_operand:V4SI 1 "register_operand" "v")) + (unspec [(const_int 0)] UNSPEC_STVRXL)])] + "TARGET_ALTIVEC && rs6000_cpu == PROCESSOR_CELL" + "stvrxl %1,%y0" + [(set_attr "type" "vecstore")]) + (define_expand "vec_extract_evenv4si" [(set (match_operand:V4SI 0 "register_operand" "") (unspec:V8HI [(match_operand:V4SI 1 "register_operand" "") diff --git a/gcc/config/rs6000/rs6000-c.c b/gcc/config/rs6000/rs6000-c.c index 10589bdc8e7..ed9b6c03683 100644 --- a/gcc/config/rs6000/rs6000-c.c +++ b/gcc/config/rs6000/rs6000-c.c @@ -996,6 +996,150 @@ const struct altivec_builtin_types altivec_overloaded_builtins[] = { RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_long, 0 }, { ALTIVEC_BUILTIN_VEC_LVSR, ALTIVEC_BUILTIN_LVSR, RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_float, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_V4SF, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_float, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_bool_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_INTSI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTSI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_bool_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_pixel_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_pixel_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_INTHI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTHI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_bool_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_INTQI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLX, ALTIVEC_BUILTIN_LVLX, + RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTQI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_V4SF, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_float, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_bool_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_INTSI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTSI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_bool_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_pixel_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_pixel_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_INTHI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTHI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_bool_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_INTQI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVLXL, ALTIVEC_BUILTIN_LVLXL, + RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTQI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_V4SF, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_float, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_bool_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_INTSI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTSI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_bool_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_pixel_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_pixel_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_INTHI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTHI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_bool_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_INTQI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRX, ALTIVEC_BUILTIN_LVRX, + RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTQI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_V4SF, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_float, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_bool_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_INTSI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V4SI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTSI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_bool_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_pixel_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_pixel_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_INTHI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V8HI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTHI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_bool_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_INTQI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V16QI, 0 }, + { ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_LVRXL, + RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTQI, 0 }, { ALTIVEC_BUILTIN_VEC_MAX, ALTIVEC_BUILTIN_VMAXUB, RS6000_BTI_unsigned_V16QI, RS6000_BTI_bool_V16QI, RS6000_BTI_unsigned_V16QI, 0 }, { ALTIVEC_BUILTIN_VEC_MAX, ALTIVEC_BUILTIN_VMAXUB, @@ -2432,6 +2576,150 @@ const struct altivec_builtin_types altivec_overloaded_builtins[] = { RS6000_BTI_void, RS6000_BTI_bool_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_INTQI }, { ALTIVEC_BUILTIN_VEC_STL, ALTIVEC_BUILTIN_STVXL, RS6000_BTI_void, RS6000_BTI_pixel_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_pixel_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_V4SF }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_float }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_bool_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_INTSI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTSI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_bool_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_pixel_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_pixel_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_INTHI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTHI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_bool_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_INTQI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVLX, ALTIVEC_BUILTIN_STVLX, + RS6000_BTI_void, RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTQI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_V4SF }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_float }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_bool_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_INTSI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTSI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_bool_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_pixel_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_pixel_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_INTHI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTHI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_bool_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_INTQI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVLXL, ALTIVEC_BUILTIN_STVLXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTQI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_V4SF }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_float }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_bool_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_INTSI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTSI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_bool_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_pixel_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_pixel_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_INTHI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTHI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_bool_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_INTQI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVRX, ALTIVEC_BUILTIN_STVRX, + RS6000_BTI_void, RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTQI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_V4SF }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_V4SF, RS6000_BTI_INTSI, ~RS6000_BTI_float }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_bool_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_INTSI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V4SI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V4SI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTSI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_bool_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_pixel_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_pixel_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_INTHI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V8HI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V8HI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTHI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_bool_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_bool_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_INTQI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_unsigned_V16QI }, + { ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_STVRXL, + RS6000_BTI_void, RS6000_BTI_unsigned_V16QI, RS6000_BTI_INTSI, ~RS6000_BTI_UINTQI }, /* Predicates. */ { ALTIVEC_BUILTIN_VCMPGT_P, ALTIVEC_BUILTIN_VCMPGTUB_P, @@ -2685,6 +2973,198 @@ altivec_resolve_overloaded_builtin (tree fndecl, tree arglist) || fcode > ALTIVEC_BUILTIN_OVERLOADED_LAST) return NULL_TREE; + /* For now treat vec_splats and vec_promote as the same. */ + if (fcode == ALTIVEC_BUILTIN_VEC_SPLATS + || fcode == ALTIVEC_BUILTIN_VEC_PROMOTE) + { + tree type, arg; + int size; + int i; + bool unsigned_p; + VEC(constructor_elt,gc) *vec; + const char *name = fcode == ALTIVEC_BUILTIN_VEC_SPLATS ? "vec_splats": "vec_promote"; + + if (!arglist) + { + error ("%s only accepts %d arguments", name, (fcode == ALTIVEC_BUILTIN_VEC_PROMOTE)+1 ); + return error_mark_node; + } + if (fcode == ALTIVEC_BUILTIN_VEC_SPLATS && TREE_CHAIN (arglist)) + { + error ("%s only accepts 1 argument", name); + return error_mark_node; + } + if (fcode == ALTIVEC_BUILTIN_VEC_PROMOTE && !TREE_CHAIN (arglist)) + { + error ("%s only accepts 2 arguments", name); + return error_mark_node; + } + /* Ignore promote's element argument. */ + if (fcode == ALTIVEC_BUILTIN_VEC_PROMOTE + && TREE_CHAIN (TREE_CHAIN (arglist))) + { + error ("%s only accepts 2 arguments", name); + return error_mark_node; + } + if (fcode == ALTIVEC_BUILTIN_VEC_PROMOTE + && !INTEGRAL_TYPE_P (TREE_TYPE (TREE_VALUE (TREE_CHAIN (arglist))))) + goto bad; + + arg = TREE_VALUE (arglist); + type = TREE_TYPE (arg); + if (!SCALAR_FLOAT_TYPE_P (type) + && !INTEGRAL_TYPE_P (type)) + goto bad; + unsigned_p = TYPE_UNSIGNED (type); + if (type == long_long_unsigned_type_node + || type == long_long_integer_type_node) + goto bad; + switch (TYPE_MODE (type)) + { + case SImode: + type = (unsigned_p ? unsigned_V4SI_type_node : V4SI_type_node); + size = 4; + break; + case HImode: + type = (unsigned_p ? unsigned_V8HI_type_node : V8HI_type_node); + size = 8; + break; + case QImode: + type = (unsigned_p ? unsigned_V16QI_type_node : V16QI_type_node); + size = 16; + break; + case SFmode: type = V4SF_type_node; size = 4; break; + default: + goto bad; + } + arg = save_expr (fold_convert (TREE_TYPE (type), arg)); + vec = VEC_alloc (constructor_elt, gc, size); + for(i = 0; i < size; i++) + { + constructor_elt *elt; + + elt = VEC_quick_push (constructor_elt, vec, NULL); + elt->index = NULL_TREE; + elt->value = arg; + } + return build_constructor (type, vec); + } + + /* For now use pointer tricks to do the extaction. */ + if (fcode == ALTIVEC_BUILTIN_VEC_EXTRACT) + { + tree arg1; + tree arg1_type; + tree arg2; + tree arg1_inner_type; + tree decl, stmt; + tree innerptrtype; + + /* No second argument. */ + if (!arglist || !TREE_CHAIN (arglist) + || TREE_CHAIN (TREE_CHAIN (arglist))) + { + error ("vec_extract only accepts 2 arguments"); + return error_mark_node; + } + + arg2 = TREE_VALUE (TREE_CHAIN (arglist)); + arg1 = TREE_VALUE (arglist); + arg1_type = TREE_TYPE (arg1); + + if (TREE_CODE (arg1_type) != VECTOR_TYPE) + goto bad; + if (!INTEGRAL_TYPE_P (TREE_TYPE (arg2))) + goto bad; + /* Build *(((arg1_inner_type*)&(vector type){arg1})+arg2). */ + arg1_inner_type = TREE_TYPE (arg1_type); + arg2 = build_binary_op (input_location, BIT_AND_EXPR, arg2, + build_int_cst (TREE_TYPE (arg2), + TYPE_VECTOR_SUBPARTS (arg1_type) + - 1), 0); + decl = build_decl (VAR_DECL, NULL_TREE, arg1_type); + DECL_EXTERNAL (decl) = 0; + TREE_PUBLIC (decl) = 0; + DECL_CONTEXT (decl) = current_function_decl; + TREE_USED (decl) = 1; + TREE_TYPE (decl) = arg1_type; + TREE_READONLY (decl) = TYPE_READONLY (arg1_type); + DECL_INITIAL (decl) = arg1; + stmt = build1 (DECL_EXPR, arg1_type, decl); + TREE_ADDRESSABLE (decl) = 1; + SET_EXPR_LOCATION (stmt, input_location); + stmt = build1 (COMPOUND_LITERAL_EXPR, arg1_type, stmt); + + innerptrtype = build_pointer_type (arg1_inner_type); + + stmt = build_unary_op (ADDR_EXPR, stmt, 0); + stmt = convert (innerptrtype, stmt); + stmt = build_binary_op (input_location, PLUS_EXPR, stmt, arg2, 1); + stmt = build_indirect_ref (stmt, NULL, input_location); + + return stmt; + } + + /* For now use pointer tricks to do the insertation. */ + if (fcode == ALTIVEC_BUILTIN_VEC_INSERT) + { + tree arg0; + tree arg1; + tree arg2; + tree arg1_type; + tree arg1_inner_type; + tree decl, stmt; + tree innerptrtype; + + /* No second or third arguments. */ + if (!arglist || !TREE_CHAIN (arglist) + || !TREE_CHAIN (TREE_CHAIN (arglist)) + || TREE_CHAIN (TREE_CHAIN (TREE_CHAIN (arglist)))) + { + error ("vec_insert only accepts 3 arguments"); + return error_mark_node; + } + + arg0 = TREE_VALUE (arglist); + arg1 = TREE_VALUE (TREE_CHAIN (arglist)); + arg1_type = TREE_TYPE (arg1); + arg2 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist))); + + if (TREE_CODE (arg1_type) != VECTOR_TYPE) + goto bad; + if (!INTEGRAL_TYPE_P (TREE_TYPE (arg2))) + goto bad; + /* Build *(((arg1_inner_type*)&(vector type){arg1})+arg2) = arg0. */ + arg1_inner_type = TREE_TYPE (arg1_type); + arg2 = build_binary_op (input_location, BIT_AND_EXPR, arg2, + build_int_cst (TREE_TYPE (arg2), + TYPE_VECTOR_SUBPARTS (arg1_type) + - 1), 0); + decl = build_decl (VAR_DECL, NULL_TREE, arg1_type); + DECL_EXTERNAL (decl) = 0; + TREE_PUBLIC (decl) = 0; + DECL_CONTEXT (decl) = current_function_decl; + TREE_USED (decl) = 1; + TREE_TYPE (decl) = arg1_type; + TREE_READONLY (decl) = TYPE_READONLY (arg1_type); + DECL_INITIAL (decl) = arg1; + stmt = build1 (DECL_EXPR, arg1_type, decl); + TREE_ADDRESSABLE (decl) = 1; + SET_EXPR_LOCATION (stmt, input_location); + stmt = build1 (COMPOUND_LITERAL_EXPR, arg1_type, stmt); + + innerptrtype = build_pointer_type (arg1_inner_type); + + stmt = build_unary_op (ADDR_EXPR, stmt, 0); + stmt = convert (innerptrtype, stmt); + stmt = build_binary_op (input_location, PLUS_EXPR, stmt, arg2, 1); + stmt = build_indirect_ref (stmt, NULL, input_location); + stmt = build2 (MODIFY_EXPR, TREE_TYPE (stmt), stmt, + convert (TREE_TYPE (stmt), arg0)); + stmt = build2 (COMPOUND_EXPR, arg1_type, stmt, decl); + return stmt; + } + for (n = 0; !VOID_TYPE_P (TREE_VALUE (fnargs)) && arglist; fnargs = TREE_CHAIN (fnargs), arglist = TREE_CHAIN (arglist), n++) diff --git a/gcc/config/rs6000/rs6000.c b/gcc/config/rs6000/rs6000.c index 67b64fd0f2b..e1e0d1c02f8 100644 --- a/gcc/config/rs6000/rs6000.c +++ b/gcc/config/rs6000/rs6000.c @@ -905,7 +905,6 @@ static rtx altivec_expand_dst_builtin (tree, rtx, bool *); static rtx altivec_expand_abs_builtin (enum insn_code, tree, rtx); static rtx altivec_expand_predicate_builtin (enum insn_code, const char *, tree, rtx); -static rtx altivec_expand_lv_builtin (enum insn_code, tree, rtx); static rtx altivec_expand_stv_builtin (enum insn_code, tree); static rtx altivec_expand_vec_init_builtin (tree, tree, rtx); static rtx altivec_expand_vec_set_builtin (tree); @@ -5250,9 +5249,7 @@ rs6000_emit_move (rtx dest, rtx source, enum machine_mode mode) #define USE_FP_FOR_ARG_P(CUM,MODE,TYPE) \ (SCALAR_FLOAT_MODE_P (MODE) \ && (CUM)->fregno <= FP_ARG_MAX_REG \ - && TARGET_HARD_FLOAT && TARGET_FPRS \ - && ((TARGET_DOUBLE_FLOAT && (MODE) == DFmode)\ - || (TARGET_SINGLE_FLOAT && (MODE) == SFmode))) + && TARGET_HARD_FLOAT && TARGET_FPRS) /* Nonzero if we can use an AltiVec register to pass this arg. */ #define USE_ALTIVEC_FOR_ARG_P(CUM,MODE,TYPE,NAMED) \ @@ -5729,9 +5726,10 @@ function_arg_advance (CUMULATIVE_ARGS *cum, enum machine_mode mode, else if (DEFAULT_ABI == ABI_V4) { if (TARGET_HARD_FLOAT && TARGET_FPRS - && (mode == SFmode || mode == DFmode - || mode == SDmode || mode == DDmode || mode == TDmode - || (mode == TFmode && !TARGET_IEEEQUAD))) + && ((TARGET_SINGLE_FLOAT && mode == SFmode) + || (TARGET_DOUBLE_FLOAT && mode == DFmode) + || (mode == TFmode && !TARGET_IEEEQUAD) + || mode == SDmode || mode == DDmode || mode == TDmode)) { /* _Decimal128 must use an even/odd register pair. This assumes that the register number is odd when fregno is odd. */ @@ -5797,9 +5795,7 @@ function_arg_advance (CUMULATIVE_ARGS *cum, enum machine_mode mode, cum->words = align_words + n_words; if (SCALAR_FLOAT_MODE_P (mode) - && TARGET_HARD_FLOAT && TARGET_FPRS - && ((TARGET_DOUBLE_FLOAT && mode == DFmode) - || (TARGET_SINGLE_FLOAT && mode == SFmode))) + && TARGET_HARD_FLOAT && TARGET_FPRS) { /* _Decimal128 must be passed in an even/odd float register pair. This assumes that the register number is odd when fregno is @@ -6293,7 +6289,8 @@ function_arg (CUMULATIVE_ARGS *cum, enum machine_mode mode, else if (abi == ABI_V4) { if (TARGET_HARD_FLOAT && TARGET_FPRS - && (mode == SFmode || mode == DFmode + && ((TARGET_SINGLE_FLOAT && mode == SFmode) + || (TARGET_DOUBLE_FLOAT && mode == DFmode) || (mode == TFmode && !TARGET_IEEEQUAD) || mode == SDmode || mode == DDmode || mode == TDmode)) { @@ -8065,7 +8062,7 @@ paired_expand_lv_builtin (enum insn_code icode, tree exp, rtx target) } static rtx -altivec_expand_lv_builtin (enum insn_code icode, tree exp, rtx target) +altivec_expand_lv_builtin (enum insn_code icode, tree exp, rtx target, bool blk) { rtx pat, addr; tree arg0 = CALL_EXPR_ARG (exp, 0); @@ -8093,12 +8090,12 @@ altivec_expand_lv_builtin (enum insn_code icode, tree exp, rtx target) if (op0 == const0_rtx) { - addr = gen_rtx_MEM (tmode, op1); + addr = gen_rtx_MEM (blk ? BLKmode : tmode, op1); } else { op0 = copy_to_mode_reg (mode0, op0); - addr = gen_rtx_MEM (tmode, gen_rtx_PLUS (Pmode, op0, op1)); + addr = gen_rtx_MEM (blk ? BLKmode : tmode, gen_rtx_PLUS (Pmode, op0, op1)); } pat = GEN_FCN (icode) (target, addr); @@ -8605,6 +8602,15 @@ altivec_expand_builtin (tree exp, rtx target, bool *expandedp) case ALTIVEC_BUILTIN_STVXL: return altivec_expand_stv_builtin (CODE_FOR_altivec_stvxl, exp); + case ALTIVEC_BUILTIN_STVLX: + return altivec_expand_stv_builtin (CODE_FOR_altivec_stvlx, exp); + case ALTIVEC_BUILTIN_STVLXL: + return altivec_expand_stv_builtin (CODE_FOR_altivec_stvlxl, exp); + case ALTIVEC_BUILTIN_STVRX: + return altivec_expand_stv_builtin (CODE_FOR_altivec_stvrx, exp); + case ALTIVEC_BUILTIN_STVRXL: + return altivec_expand_stv_builtin (CODE_FOR_altivec_stvrxl, exp); + case ALTIVEC_BUILTIN_MFVSCR: icode = CODE_FOR_altivec_mfvscr; tmode = insn_data[icode].operand[0].mode; @@ -8707,25 +8713,37 @@ altivec_expand_builtin (tree exp, rtx target, bool *expandedp) { case ALTIVEC_BUILTIN_LVSL: return altivec_expand_lv_builtin (CODE_FOR_altivec_lvsl, - exp, target); + exp, target, false); case ALTIVEC_BUILTIN_LVSR: return altivec_expand_lv_builtin (CODE_FOR_altivec_lvsr, - exp, target); + exp, target, false); case ALTIVEC_BUILTIN_LVEBX: return altivec_expand_lv_builtin (CODE_FOR_altivec_lvebx, - exp, target); + exp, target, false); case ALTIVEC_BUILTIN_LVEHX: return altivec_expand_lv_builtin (CODE_FOR_altivec_lvehx, - exp, target); + exp, target, false); case ALTIVEC_BUILTIN_LVEWX: return altivec_expand_lv_builtin (CODE_FOR_altivec_lvewx, - exp, target); + exp, target, false); case ALTIVEC_BUILTIN_LVXL: return altivec_expand_lv_builtin (CODE_FOR_altivec_lvxl, - exp, target); + exp, target, false); case ALTIVEC_BUILTIN_LVX: return altivec_expand_lv_builtin (CODE_FOR_altivec_lvx, - exp, target); + exp, target, false); + case ALTIVEC_BUILTIN_LVLX: + return altivec_expand_lv_builtin (CODE_FOR_altivec_lvlx, + exp, target, true); + case ALTIVEC_BUILTIN_LVLXL: + return altivec_expand_lv_builtin (CODE_FOR_altivec_lvlxl, + exp, target, true); + case ALTIVEC_BUILTIN_LVRX: + return altivec_expand_lv_builtin (CODE_FOR_altivec_lvrx, + exp, target, true); + case ALTIVEC_BUILTIN_LVRXL: + return altivec_expand_lv_builtin (CODE_FOR_altivec_lvrxl, + exp, target, true); default: break; /* Fall through. */ @@ -9764,7 +9782,9 @@ altivec_init_builtins (void) tree int_ftype_opaque = build_function_type_list (integer_type_node, opaque_V4SI_type_node, NULL_TREE); - + tree opaque_ftype_opaque + = build_function_type (integer_type_node, + NULL_TREE); tree opaque_ftype_opaque_int = build_function_type_list (opaque_V4SI_type_node, opaque_V4SI_type_node, integer_type_node, NULL_TREE); @@ -9910,10 +9930,36 @@ altivec_init_builtins (void) def_builtin (MASK_ALTIVEC, "__builtin_vec_stvebx", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STVEBX); def_builtin (MASK_ALTIVEC, "__builtin_vec_stvehx", void_ftype_opaque_long_pvoid, ALTIVEC_BUILTIN_VEC_STVEHX); + if (rs6000_cpu == PROCESSOR_CELL) + { + def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvlx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVLX); + def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvlxl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVLXL); + def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvrx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVRX); + def_builtin (MASK_ALTIVEC, "__builtin_altivec_lvrxl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_LVRXL); + + def_builtin (MASK_ALTIVEC, "__builtin_vec_lvlx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVLX); + def_builtin (MASK_ALTIVEC, "__builtin_vec_lvlxl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVLXL); + def_builtin (MASK_ALTIVEC, "__builtin_vec_lvrx", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVRX); + def_builtin (MASK_ALTIVEC, "__builtin_vec_lvrxl", v16qi_ftype_long_pcvoid, ALTIVEC_BUILTIN_VEC_LVRXL); + + def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvlx", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_STVLX); + def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvlxl", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_STVLXL); + def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvrx", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_STVRX); + def_builtin (MASK_ALTIVEC, "__builtin_altivec_stvrxl", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_STVRXL); + + def_builtin (MASK_ALTIVEC, "__builtin_vec_stvlx", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_VEC_STVLX); + def_builtin (MASK_ALTIVEC, "__builtin_vec_stvlxl", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_VEC_STVLXL); + def_builtin (MASK_ALTIVEC, "__builtin_vec_stvrx", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_VEC_STVRX); + def_builtin (MASK_ALTIVEC, "__builtin_vec_stvrxl", void_ftype_v16qi_long_pvoid, ALTIVEC_BUILTIN_VEC_STVRXL); + } def_builtin (MASK_ALTIVEC, "__builtin_vec_step", int_ftype_opaque, ALTIVEC_BUILTIN_VEC_STEP); + def_builtin (MASK_ALTIVEC, "__builtin_vec_splats", opaque_ftype_opaque, ALTIVEC_BUILTIN_VEC_SPLATS); + def_builtin (MASK_ALTIVEC, "__builtin_vec_promote", opaque_ftype_opaque, ALTIVEC_BUILTIN_VEC_PROMOTE); def_builtin (MASK_ALTIVEC, "__builtin_vec_sld", opaque_ftype_opaque_opaque_int, ALTIVEC_BUILTIN_VEC_SLD); def_builtin (MASK_ALTIVEC, "__builtin_vec_splat", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_SPLAT); + def_builtin (MASK_ALTIVEC, "__builtin_vec_extract", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_EXTRACT); + def_builtin (MASK_ALTIVEC, "__builtin_vec_insert", opaque_ftype_opaque_opaque_int, ALTIVEC_BUILTIN_VEC_INSERT); def_builtin (MASK_ALTIVEC, "__builtin_vec_vspltw", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VSPLTW); def_builtin (MASK_ALTIVEC, "__builtin_vec_vsplth", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VSPLTH); def_builtin (MASK_ALTIVEC, "__builtin_vec_vspltb", opaque_ftype_opaque_int, ALTIVEC_BUILTIN_VEC_VSPLTB); @@ -22474,10 +22520,7 @@ rs6000_function_value (const_tree valtype, const_tree func ATTRIBUTE_UNUSED) if (DECIMAL_FLOAT_MODE_P (mode) && TARGET_HARD_FLOAT && TARGET_FPRS) /* _Decimal128 must use an even/odd register pair. */ regno = (mode == TDmode) ? FP_ARG_RETURN + 1 : FP_ARG_RETURN; - else if (SCALAR_FLOAT_TYPE_P (valtype) && TARGET_FPRS - && (TARGET_HARD_FLOAT - && ((TARGET_SINGLE_FLOAT && mode == SFmode) - || TARGET_DOUBLE_FLOAT))) + else if (SCALAR_FLOAT_TYPE_P (valtype) && TARGET_HARD_FLOAT && TARGET_FPRS) regno = FP_ARG_RETURN; else if (TREE_CODE (valtype) == COMPLEX_TYPE && targetm.calls.split_complex_arg) diff --git a/gcc/config/rs6000/rs6000.h b/gcc/config/rs6000/rs6000.h index 627427a9739..e1023daa022 100644 --- a/gcc/config/rs6000/rs6000.h +++ b/gcc/config/rs6000/rs6000.h @@ -2543,10 +2543,18 @@ enum rs6000_builtins ALTIVEC_BUILTIN_LVXL, ALTIVEC_BUILTIN_LVX, ALTIVEC_BUILTIN_STVX, + ALTIVEC_BUILTIN_LVLX, + ALTIVEC_BUILTIN_LVLXL, + ALTIVEC_BUILTIN_LVRX, + ALTIVEC_BUILTIN_LVRXL, ALTIVEC_BUILTIN_STVEBX, ALTIVEC_BUILTIN_STVEHX, ALTIVEC_BUILTIN_STVEWX, ALTIVEC_BUILTIN_STVXL, + ALTIVEC_BUILTIN_STVLX, + ALTIVEC_BUILTIN_STVLXL, + ALTIVEC_BUILTIN_STVRX, + ALTIVEC_BUILTIN_STVRXL, ALTIVEC_BUILTIN_VCMPBFP_P, ALTIVEC_BUILTIN_VCMPEQFP_P, ALTIVEC_BUILTIN_VCMPEQUB_P, @@ -2595,6 +2603,7 @@ enum rs6000_builtins ALTIVEC_BUILTIN_VEC_AND, ALTIVEC_BUILTIN_VEC_ANDC, ALTIVEC_BUILTIN_VEC_AVG, + ALTIVEC_BUILTIN_VEC_EXTRACT, ALTIVEC_BUILTIN_VEC_CEIL, ALTIVEC_BUILTIN_VEC_CMPB, ALTIVEC_BUILTIN_VEC_CMPEQ, @@ -2621,6 +2630,10 @@ enum rs6000_builtins ALTIVEC_BUILTIN_VEC_LVEBX, ALTIVEC_BUILTIN_VEC_LVEHX, ALTIVEC_BUILTIN_VEC_LVEWX, + ALTIVEC_BUILTIN_VEC_LVLX, + ALTIVEC_BUILTIN_VEC_LVLXL, + ALTIVEC_BUILTIN_VEC_LVRX, + ALTIVEC_BUILTIN_VEC_LVRXL, ALTIVEC_BUILTIN_VEC_LVSL, ALTIVEC_BUILTIN_VEC_LVSR, ALTIVEC_BUILTIN_VEC_MADD, @@ -2680,6 +2693,10 @@ enum rs6000_builtins ALTIVEC_BUILTIN_VEC_STVEBX, ALTIVEC_BUILTIN_VEC_STVEHX, ALTIVEC_BUILTIN_VEC_STVEWX, + ALTIVEC_BUILTIN_VEC_STVLX, + ALTIVEC_BUILTIN_VEC_STVLXL, + ALTIVEC_BUILTIN_VEC_STVRX, + ALTIVEC_BUILTIN_VEC_STVRXL, ALTIVEC_BUILTIN_VEC_SUB, ALTIVEC_BUILTIN_VEC_SUBC, ALTIVEC_BUILTIN_VEC_SUBS, @@ -2796,7 +2813,10 @@ enum rs6000_builtins ALTIVEC_BUILTIN_VEC_VUPKLSH, ALTIVEC_BUILTIN_VEC_XOR, ALTIVEC_BUILTIN_VEC_STEP, - ALTIVEC_BUILTIN_OVERLOADED_LAST = ALTIVEC_BUILTIN_VEC_STEP, + ALTIVEC_BUILTIN_VEC_PROMOTE, + ALTIVEC_BUILTIN_VEC_INSERT, + ALTIVEC_BUILTIN_VEC_SPLATS, + ALTIVEC_BUILTIN_OVERLOADED_LAST = ALTIVEC_BUILTIN_VEC_SPLATS, /* SPE builtins. */ SPE_BUILTIN_EVADDW, diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 2438bd6941e..ea319f31aaa 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,7 @@ +2008-10-01 Andrew Pinski <andrew_pinski@playstation.sony.com> + + * tree.c (lvalue_p_1): COMPOUND_LITERAL_EXPR is also an lvalue. + 2008-09-30 H.J. Lu <hongjiu.lu@intel.com> PR c++/37683 diff --git a/gcc/cp/tree.c b/gcc/cp/tree.c index fb3e8fc956c..2ae65431c7b 100644 --- a/gcc/cp/tree.c +++ b/gcc/cp/tree.c @@ -129,6 +129,7 @@ lvalue_p_1 (const_tree ref, return op1_lvalue_kind; case STRING_CST: + case COMPOUND_LITERAL_EXPR: return clk_ordinary; case CONST_DECL: diff --git a/gcc/fortran/ChangeLog b/gcc/fortran/ChangeLog index 253caa2b8d1..869cd897b27 100644 --- a/gcc/fortran/ChangeLog +++ b/gcc/fortran/ChangeLog @@ -1,3 +1,19 @@ +2008-10-02 Steven Bosscher <steven@gcc.gnu.org> + + PR fortran/37635 + * intrinsic.c (add_functions): Add LEADZ and TRAILZ as generics. + * intrinsic.h (gfc_simplify_leadz, gfc_simplify_trailz): New protos. + * gfortran.h <enum gfc_isym_id>: (GFC_ISYM_LEADZ, GFC_ISYM_TRAILZ): New. + * f95-lang (gfc_init_builtin_functions): Add BUILT_IN_CLZ, + BUILT_IN_CLZL, BUILT_IN_CLZLL, BUILT_IN_CTZ, BUILT_IN_CTZL, and + BUILT_IN_CTZLL. + * trans-intrinsic.c (gfc_conv_intrinsic_leadz, + gfc_conv_intrinsic_trails): New code-generation functions for LEADZ + and TRAILZ intrinsics. + (gfc_conv_intrinsic_function): Use them + * intrinsic.texi: Add documentation for LEADZ and TRAILZ. + * simplify.c (gfc_simplify_leadz, gfc_simplify_trailz): New functions. + 2008-09-30 Janus Weil <janus@gcc.gnu.org> PR fortran/36592 diff --git a/gcc/fortran/f95-lang.c b/gcc/fortran/f95-lang.c index 30cc98e86d7..cf0dc2d48b7 100644 --- a/gcc/fortran/f95-lang.c +++ b/gcc/fortran/f95-lang.c @@ -1003,6 +1003,37 @@ gfc_init_builtin_functions (void) BUILT_IN_SINCOSF, "sincosf", false); } + /* For LEADZ / TRAILZ. */ + tmp = tree_cons (NULL_TREE, unsigned_type_node, void_list_node); + ftype = build_function_type (integer_type_node, tmp); + gfc_define_builtin ("__builtin_clz", ftype, BUILT_IN_CLZ, + "__builtin_clz", true); + + tmp = tree_cons (NULL_TREE, long_unsigned_type_node, void_list_node); + ftype = build_function_type (integer_type_node, tmp); + gfc_define_builtin ("__builtin_clzl", ftype, BUILT_IN_CLZL, + "__builtin_clzl", true); + + tmp = tree_cons (NULL_TREE, long_long_unsigned_type_node, void_list_node); + ftype = build_function_type (integer_type_node, tmp); + gfc_define_builtin ("__builtin_clzll", ftype, BUILT_IN_CLZLL, + "__builtin_clzll", true); + + tmp = tree_cons (NULL_TREE, unsigned_type_node, void_list_node); + ftype = build_function_type (integer_type_node, tmp); + gfc_define_builtin ("__builtin_ctz", ftype, BUILT_IN_CTZ, + "__builtin_ctz", true); + + tmp = tree_cons (NULL_TREE, long_unsigned_type_node, void_list_node); + ftype = build_function_type (integer_type_node, tmp); + gfc_define_builtin ("__builtin_ctzl", ftype, BUILT_IN_CTZL, + "__builtin_ctzl", true); + + tmp = tree_cons (NULL_TREE, long_long_unsigned_type_node, void_list_node); + ftype = build_function_type (integer_type_node, tmp); + gfc_define_builtin ("__builtin_ctzll", ftype, BUILT_IN_CTZLL, + "__builtin_ctzll", true); + /* Other builtin functions we use. */ tmp = tree_cons (NULL_TREE, long_integer_type_node, void_list_node); diff --git a/gcc/fortran/gfortran.h b/gcc/fortran/gfortran.h index 4e9959ea5bb..60d9baccf9b 100644 --- a/gcc/fortran/gfortran.h +++ b/gcc/fortran/gfortran.h @@ -417,6 +417,7 @@ enum gfc_isym_id GFC_ISYM_KILL, GFC_ISYM_KIND, GFC_ISYM_LBOUND, + GFC_ISYM_LEADZ, GFC_ISYM_LEN, GFC_ISYM_LEN_TRIM, GFC_ISYM_LGAMMA, @@ -503,6 +504,7 @@ enum gfc_isym_id GFC_ISYM_TIME, GFC_ISYM_TIME8, GFC_ISYM_TINY, + GFC_ISYM_TRAILZ, GFC_ISYM_TRANSFER, GFC_ISYM_TRANSPOSE, GFC_ISYM_TRIM, diff --git a/gcc/fortran/intrinsic.c b/gcc/fortran/intrinsic.c index 9b11db4bb64..035aef70d65 100644 --- a/gcc/fortran/intrinsic.c +++ b/gcc/fortran/intrinsic.c @@ -1781,6 +1781,13 @@ add_functions (void) make_generic ("lbound", GFC_ISYM_LBOUND, GFC_STD_F95); + add_sym_1 ("leadz", GFC_ISYM_LEADZ, CLASS_ELEMENTAL, ACTUAL_NO, + BT_INTEGER, di, GFC_STD_F2008, + gfc_check_i, gfc_simplify_leadz, NULL, + i, BT_INTEGER, di, REQUIRED); + + make_generic ("leadz", GFC_ISYM_LEADZ, GFC_STD_F2008); + add_sym_2 ("len", GFC_ISYM_LEN, CLASS_INQUIRY, ACTUAL_YES, BT_INTEGER, di, GFC_STD_F77, gfc_check_len_lentrim, gfc_simplify_len, gfc_resolve_len, @@ -2388,6 +2395,13 @@ add_functions (void) make_generic ("tiny", GFC_ISYM_TINY, GFC_STD_F95); + add_sym_1 ("trailz", GFC_ISYM_TRAILZ, CLASS_ELEMENTAL, ACTUAL_NO, + BT_INTEGER, di, GFC_STD_F2008, + gfc_check_i, gfc_simplify_trailz, NULL, + i, BT_INTEGER, di, REQUIRED); + + make_generic ("trailz", GFC_ISYM_TRAILZ, GFC_STD_F2008); + add_sym_3 ("transfer", GFC_ISYM_TRANSFER, CLASS_TRANSFORMATIONAL, ACTUAL_NO, BT_REAL, dr, GFC_STD_F95, gfc_check_transfer, gfc_simplify_transfer, gfc_resolve_transfer, src, BT_REAL, dr, REQUIRED, mo, BT_REAL, dr, REQUIRED, diff --git a/gcc/fortran/intrinsic.h b/gcc/fortran/intrinsic.h index 5994cf66a79..02eff464d0a 100644 --- a/gcc/fortran/intrinsic.h +++ b/gcc/fortran/intrinsic.h @@ -259,6 +259,7 @@ gfc_expr *gfc_simplify_ishft (gfc_expr *, gfc_expr *); gfc_expr *gfc_simplify_ishftc (gfc_expr *, gfc_expr *, gfc_expr *); gfc_expr *gfc_simplify_kind (gfc_expr *); gfc_expr *gfc_simplify_lbound (gfc_expr *, gfc_expr *, gfc_expr *); +gfc_expr *gfc_simplify_leadz (gfc_expr *); gfc_expr *gfc_simplify_len (gfc_expr *, gfc_expr *); gfc_expr *gfc_simplify_len_trim (gfc_expr *, gfc_expr *); gfc_expr *gfc_simplify_lgamma (gfc_expr *); @@ -310,6 +311,7 @@ gfc_expr *gfc_simplify_sqrt (gfc_expr *); gfc_expr *gfc_simplify_tan (gfc_expr *); gfc_expr *gfc_simplify_tanh (gfc_expr *); gfc_expr *gfc_simplify_tiny (gfc_expr *); +gfc_expr *gfc_simplify_trailz (gfc_expr *); gfc_expr *gfc_simplify_transfer (gfc_expr *, gfc_expr *, gfc_expr *); gfc_expr *gfc_simplify_trim (gfc_expr *); gfc_expr *gfc_simplify_ubound (gfc_expr *, gfc_expr *, gfc_expr *); diff --git a/gcc/fortran/intrinsic.texi b/gcc/fortran/intrinsic.texi index 8337f74c522..3418d05bdf3 100644 --- a/gcc/fortran/intrinsic.texi +++ b/gcc/fortran/intrinsic.texi @@ -164,6 +164,7 @@ Some basic guidelines for editing this document: * @code{KILL}: KILL, Send a signal to a process * @code{KIND}: KIND, Kind of an entity * @code{LBOUND}: LBOUND, Lower dimension bounds of an array +* @code{LEADZ}: LEADZ, Number of leading zero bits of an integer * @code{LEN}: LEN, Length of a character entity * @code{LEN_TRIM}: LEN_TRIM, Length of a character entity without trailing blank characters * @code{LOG_GAMMA}: LOG_GAMMA, Logarithm of the Gamma function @@ -252,6 +253,7 @@ Some basic guidelines for editing this document: * @code{TIME}: TIME, Time function * @code{TIME8}: TIME8, Time function (64-bit) * @code{TINY}: TINY, Smallest positive number of a real kind +* @code{TRAILZ}: TRAILZ, Number of trailing zero bits of an integer * @code{TRANSFER}: TRANSFER, Transfer bit patterns * @code{TRANSPOSE}: TRANSPOSE, Transpose an array of rank two * @code{TRIM}: TRIM, Remove trailing blank characters of a string @@ -6504,6 +6506,46 @@ dimension, the lower bound is taken to be 1. +@node LEADZ +@section @code{LEADZ} --- Number of leading zero bits of an integer +@fnindex LEADZ +@cindex zero bits + +@table @asis +@item @emph{Description}: +@code{LEADZ} returns the number of leading zero bits of an integer. + +@item @emph{Standard}: +Fortran 2008 and later + +@item @emph{Class}: +Elemental function + +@item @emph{Syntax}: +@code{RESULT = LEADZ(I)} + +@item @emph{Arguments}: +@multitable @columnfractions .15 .70 +@item @var{I} @tab Shall be of type @code{INTEGER}. +@end multitable + +@item @emph{Return value}: +The type of the return value is the default @code{INTEGER}. +If all the bits of @code{I} are zero, the result value is @code{BIT_SIZE(I)}. + +@item @emph{Example}: +@smallexample +PROGRAM test_leadz + WRITE (*,*) LEADZ(1) ! prints 8 if BITSIZE(I) has the value 32 +END PROGRAM +@end smallexample + +@item @emph{See also}: +@ref{BIT_SIZE}, @ref{TRAILZ} +@end table + + + @node LEN @section @code{LEN} --- Length of a character entity @fnindex LEN @@ -10642,6 +10684,46 @@ See @code{HUGE} for an example. +@node TRAILZ +@section @code{TRAILZ} --- Number of trailing zero bits of an integer +@fnindex TRAILZ +@cindex zero bits + +@table @asis +@item @emph{Description}: +@code{TRAILZ} returns the number of trailing zero bits of an integer. + +@item @emph{Standard}: +Fortran 2008 and later + +@item @emph{Class}: +Elemental function + +@item @emph{Syntax}: +@code{RESULT = TRAILZ(I)} + +@item @emph{Arguments}: +@multitable @columnfractions .15 .70 +@item @var{I} @tab Shall be of type @code{INTEGER}. +@end multitable + +@item @emph{Return value}: +The type of the return value is the default @code{INTEGER}. +If all the bits of @code{I} are zero, the result value is @code{BIT_SIZE(I)}. + +@item @emph{Example}: +@smallexample +PROGRAM test_trailz + WRITE (*,*) TRAILZ(8) ! prints 3 +END PROGRAM +@end smallexample + +@item @emph{See also}: +@ref{BIT_SIZE}, @ref{LEADZ} +@end table + + + @node TRANSFER @section @code{TRANSFER} --- Transfer bit patterns @fnindex TRANSFER diff --git a/gcc/fortran/simplify.c b/gcc/fortran/simplify.c index c0ac0262050..429c5151d2e 100644 --- a/gcc/fortran/simplify.c +++ b/gcc/fortran/simplify.c @@ -2400,6 +2400,30 @@ gfc_simplify_lbound (gfc_expr *array, gfc_expr *dim, gfc_expr *kind) gfc_expr * +gfc_simplify_leadz (gfc_expr *e) +{ + gfc_expr *result; + unsigned long lz, bs; + int i; + + if (e->expr_type != EXPR_CONSTANT) + return NULL; + + i = gfc_validate_kind (e->ts.type, e->ts.kind, false); + bs = gfc_integer_kinds[i].bit_size; + if (mpz_cmp_si (e->value.integer, 0) == 0) + lz = bs; + else + lz = bs - mpz_sizeinbase (e->value.integer, 2); + + result = gfc_constant_result (BT_INTEGER, gfc_default_integer_kind, &e->where); + mpz_set_ui (result->value.integer, lz); + + return result; +} + + +gfc_expr * gfc_simplify_len (gfc_expr *e, gfc_expr *kind) { gfc_expr *result; @@ -4338,6 +4362,27 @@ gfc_simplify_tiny (gfc_expr *e) gfc_expr * +gfc_simplify_trailz (gfc_expr *e) +{ + gfc_expr *result; + unsigned long tz, bs; + int i; + + if (e->expr_type != EXPR_CONSTANT) + return NULL; + + i = gfc_validate_kind (e->ts.type, e->ts.kind, false); + bs = gfc_integer_kinds[i].bit_size; + tz = mpz_scan1 (e->value.integer, 0); + + result = gfc_constant_result (BT_INTEGER, gfc_default_integer_kind, &e->where); + mpz_set_ui (result->value.integer, MIN (tz, bs)); + + return result; +} + + +gfc_expr * gfc_simplify_transfer (gfc_expr *source, gfc_expr *mold, gfc_expr *size) { gfc_expr *result; diff --git a/gcc/fortran/trans-intrinsic.c b/gcc/fortran/trans-intrinsic.c index f5f9922b68d..ffe1e5b913e 100644 --- a/gcc/fortran/trans-intrinsic.c +++ b/gcc/fortran/trans-intrinsic.c @@ -2653,6 +2653,141 @@ gfc_conv_intrinsic_ishftc (gfc_se * se, gfc_expr * expr) se->expr = fold_build3 (COND_EXPR, type, tmp, args[0], rrot); } +/* LEADZ (i) = (i == 0) ? BIT_SIZE (i) + : __builtin_clz(i) - (BIT_SIZE('int') - BIT_SIZE(i)) + + The conditional expression is necessary because the result of LEADZ(0) + is defined, but the result of __builtin_clz(0) is undefined for most + targets. + + For INTEGER kinds smaller than the C 'int' type, we have to subtract the + difference in bit size between the argument of LEADZ and the C int. */ + +static void +gfc_conv_intrinsic_leadz (gfc_se * se, gfc_expr * expr) +{ + tree arg; + tree arg_type; + tree cond; + tree result_type; + tree leadz; + tree bit_size; + tree tmp; + int arg_kind; + int i, n, s; + + gfc_conv_intrinsic_function_args (se, expr, &arg, 1); + + /* Which variant of __builtin_clz* should we call? */ + arg_kind = expr->value.function.actual->expr->ts.kind; + i = gfc_validate_kind (BT_INTEGER, arg_kind, false); + switch (arg_kind) + { + case 1: + case 2: + case 4: + arg_type = unsigned_type_node; + n = BUILT_IN_CLZ; + break; + + case 8: + arg_type = long_unsigned_type_node; + n = BUILT_IN_CLZL; + break; + + case 16: + arg_type = long_long_unsigned_type_node; + n = BUILT_IN_CLZLL; + break; + + default: + gcc_unreachable (); + } + + /* Convert the actual argument to the proper argument type for the built-in + function. But the return type is of the default INTEGER kind. */ + arg = fold_convert (arg_type, arg); + result_type = gfc_get_int_type (gfc_default_integer_kind); + + /* Compute LEADZ for the case i .ne. 0. */ + s = TYPE_PRECISION (arg_type) - gfc_integer_kinds[i].bit_size; + tmp = fold_convert (result_type, build_call_expr (built_in_decls[n], 1, arg)); + leadz = fold_build2 (MINUS_EXPR, result_type, + tmp, build_int_cst (result_type, s)); + + /* Build BIT_SIZE. */ + bit_size = build_int_cst (result_type, gfc_integer_kinds[i].bit_size); + + /* ??? For some combinations of targets and integer kinds, the condition + can be avoided if CLZ_DEFINED_VALUE_AT_ZERO is used. Later. */ + cond = fold_build2 (EQ_EXPR, boolean_type_node, + arg, build_int_cst (arg_type, 0)); + se->expr = fold_build3 (COND_EXPR, result_type, cond, bit_size, leadz); +} + +/* TRAILZ(i) = (i == 0) ? BIT_SIZE (i) : __builtin_ctz(i) + + The conditional expression is necessary because the result of TRAILZ(0) + is defined, but the result of __builtin_ctz(0) is undefined for most + targets. */ + +static void +gfc_conv_intrinsic_trailz (gfc_se * se, gfc_expr *expr) +{ + tree arg; + tree arg_type; + tree cond; + tree result_type; + tree trailz; + tree bit_size; + int arg_kind; + int i, n; + + gfc_conv_intrinsic_function_args (se, expr, &arg, 1); + + /* Which variant of __builtin_clz* should we call? */ + arg_kind = expr->value.function.actual->expr->ts.kind; + i = gfc_validate_kind (BT_INTEGER, arg_kind, false); + switch (expr->ts.kind) + { + case 1: + case 2: + case 4: + arg_type = unsigned_type_node; + n = BUILT_IN_CTZ; + break; + + case 8: + arg_type = long_unsigned_type_node; + n = BUILT_IN_CTZL; + break; + + case 16: + arg_type = long_long_unsigned_type_node; + n = BUILT_IN_CTZLL; + break; + + default: + gcc_unreachable (); + } + + /* Convert the actual argument to the proper argument type for the built-in + function. But the return type is of the default INTEGER kind. */ + arg = fold_convert (arg_type, arg); + result_type = gfc_get_int_type (gfc_default_integer_kind); + + /* Compute TRAILZ for the case i .ne. 0. */ + trailz = fold_convert (result_type, build_call_expr (built_in_decls[n], 1, arg)); + + /* Build BIT_SIZE. */ + bit_size = build_int_cst (result_type, gfc_integer_kinds[i].bit_size); + + /* ??? For some combinations of targets and integer kinds, the condition + can be avoided if CTZ_DEFINED_VALUE_AT_ZERO is used. Later. */ + cond = fold_build2 (EQ_EXPR, boolean_type_node, + arg, build_int_cst (arg_type, 0)); + se->expr = fold_build3 (COND_EXPR, result_type, cond, bit_size, trailz); +} /* Process an intrinsic with unspecified argument-types that has an optional argument (which could be of type character), e.g. EOSHIFT. For those, we @@ -4482,6 +4617,14 @@ gfc_conv_intrinsic_function (gfc_se * se, gfc_expr * expr) gfc_conv_intrinsic_ishftc (se, expr); break; + case GFC_ISYM_LEADZ: + gfc_conv_intrinsic_leadz (se, expr); + break; + + case GFC_ISYM_TRAILZ: + gfc_conv_intrinsic_trailz (se, expr); + break; + case GFC_ISYM_LBOUND: gfc_conv_intrinsic_bound (se, expr, 0); break; diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 755a9701033..7894386318c 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,52 @@ +2008-10-02 Steven Bosscher <steven@gcc.gnu.org> + + PR fortran/37635 + * gfortran.fortran-torture/execute/intrinsic_leadz.f90: New test. + * gfortran.fortran-torture/execute/intrinsic_trailz.f90: New test. + +2008-10-02 Janis Johnson <janis187@us.ibm.com> + + * gcc.dg/torture/pr36891.c: Ignore an irrelevant warning. + + * gcc.target/powerpc/ppc64-abi-3.c: Initialize variables to suppress + warning. + +2008-10-02 Richard Guenther <rguenther@suse.de> + + PR middle-end/37713 + * gcc.c-torture/compile/pr37713.c: New testcase. + +2008-10-01 Andrew Pinski <andrew_pinski@playstation.sony.com> + + * gcc.target/powerpc/altivec-cell-1.c: New test. + * gcc.target/powerpc/altivec-cell-2.c: New test. + * gcc.target/powerpc/altivec-cell-3.c: New test. + * gcc.target/powerpc/altivec-cell-4.c: New test. + * gcc.target/powerpc/altivec-cell-5.c: New test. + * g++.dg/ext/altivec-cell-1.C: New test. + * g++.dg/ext/altivec-cell-2.C: New test. + * g++.dg/ext/altivec-cell-3.C: New test. + * g++.dg/ext/altivec-cell-4.C: New test. + * g++.dg/ext/altivec-cell-5.C: New test. + +2008-10-01 Andrew Pinski <andrew_pinski@playstation.sony.com> + + * gcc.target/powerpc/altivec_check.h (altivec_cell_check): + New function. + * gcc.target/powerpc/altivec-cell-6.c: New test. + * gcc.target/powerpc/altivec-cell-7.c: New test. + * gcc.target/powerpc/altivec-cell-8.c: New test. + +2008-10-01 Richard Guenther <rguenther@suse.de> + + PR tree-optimization/37617 + * gcc.c-torture/compile/pr37617.c: New testcase. + +2008-10-01 Richard Guenther <rguenther@suse.de> + + PR middle-end/37285 + * gcc.c-torture/compile/pr37285.c: New testcase. + 2008-10-01 Kai Tietz <kai.tietz@onevision.com> * g++.dg/abi/offsetof.C (main): Use __SIZE_TYPE__ instead of @@ -52,7 +101,7 @@ addresses of non zero offset works. 2008-09-28 Andrew Pinski <andrew_pinski@playstation.sony.com> - Kaushal Kantawala <kaushal_kantawala@playstation.sony.com> + Kaushal Kantawala <kaushal_kantawala@playstation.sony.com> PR tree-opt/36891 * gcc.dg/torture/pr36891.c: New testcase. @@ -512,8 +561,8 @@ * g++.old-deja/g++.robertl/eb44.C: Ditto. * g++.old-deja/g++.robertl/eb4.C: Ditto. * g++.old-deja/g++.robertl/eb69.C: Ditto. - * g++.dg/parse/constructor1.C: Remove "error" from dg-error, preserving - column number. + * g++.dg/parse/constructor1.C: Remove "error" from dg-error, + preserving column number. * g++.dg/parse/error10.C: Ditto. * g++.dg/parse/error13.C: Ditto. * g++.dg/parse/error14.C: Ditto. diff --git a/gcc/testsuite/g++.dg/ext/altivec-cell-1.C b/gcc/testsuite/g++.dg/ext/altivec-cell-1.C new file mode 100644 index 00000000000..16d311c3bef --- /dev/null +++ b/gcc/testsuite/g++.dg/ext/altivec-cell-1.C @@ -0,0 +1,94 @@ +/* { dg-do compile { target powerpc*-*-* } } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec" } */ + +/* Basic test for the new VMX intrinsics. */ +#include <altivec.h> + +int f(vector int a, int b) +{ + return vec_extract (a, b); +} +short f1(vector short a, int b) +{ + return vec_extract (a, b); +} +vector short f2(vector short a, int b) +{ + return vec_insert (b, a, b); +} +vector float f3(vector float a, int b) +{ + return vec_insert (b, a, b); +} + +float g(void); + +vector float f4(float b, int t) +{ + return vec_promote (g(), t); +} +vector float f5(float b) +{ + return vec_splats (g()); +} + + + + +template <int> +int tf(vector int a, int b) +{ + return vec_extract (a, b); +} +template <int> +short tf1(vector short a, int b) +{ + return vec_extract (a, b); +} +template <int> +vector short tf2(vector short a, int b) +{ + return vec_insert (b, a, b); +} +template <int> +vector float tf3(vector float a, int b) +{ + return vec_insert (b, a, b); +} + +template <int> +vector float tf4(float b, int t) +{ + return vec_promote (g(), t); +} +template <int> +vector float tf5(float b) +{ + return vec_splats (g()); +} + +int t(vector int a, int b) +{ + return tf<1>(a, b); +} +short t1(vector short a, int b) +{ + return tf1<1>(a, b); +} +vector short t2(vector short a, int b) +{ + return tf2<1>(a, b); +} +vector float t3(vector float a, int b) +{ + return tf3<1>(a, b); +} +vector float t4(float b, int t) +{ + return tf4<1>(b, t); +} +vector float t5(float b) +{ + return tf5<1>(b); +} diff --git a/gcc/testsuite/g++.dg/ext/altivec-cell-2.C b/gcc/testsuite/g++.dg/ext/altivec-cell-2.C new file mode 100644 index 00000000000..969cc97aa8a --- /dev/null +++ b/gcc/testsuite/g++.dg/ext/altivec-cell-2.C @@ -0,0 +1,142 @@ +/* { dg-do run { target powerpc*-*-* } } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec" } */ +/* Test the vec_extract VMX intrinsics. */ +#include <altivec.h> +#include "altivec_check.h" + +extern "C" void abort (void); + +vector int a = {0, 1, 2, 3}; +vector short b = {0, 1, 2, 3, 4, 5, 6, 7}; + +int f(vector int a, int b) +{ + return vec_extract (a, b); +} + +int f0 (vector int a) +{ + return vec_extract (a, 0); +} +int f1 (vector int a) +{ + return vec_extract (a, 1); +} +int f2 (vector int a) +{ + return vec_extract (a, 2); +} +int f3 (vector int a) +{ + return vec_extract (a, 3); +} +int f4 (vector int a) +{ + return vec_extract (a, 4); +} + +int g(vector short a, int b) +{ + return vec_extract (a, b); +} + +int g0 (vector short a) +{ + return vec_extract (a, 0); +} +int g1 (vector short a) +{ + return vec_extract (a, 1); +} +int g2 (vector short a) +{ + return vec_extract (a, 2); +} +int g3 (vector short a) +{ + return vec_extract (a, 3); +} + +int g4 (vector short a) +{ + return vec_extract (a, 4); +} +int g5 (vector short a) +{ + return vec_extract (a, 5); +} +int g6 (vector short a) +{ + return vec_extract (a, 6); +} +int g7 (vector short a) +{ + return vec_extract (a, 7); +} +int g8 (vector short a) +{ + return vec_extract (a, 8); +} +int main1(void) __attribute__((noinline)); +int main1(void) +{ + int i; + /* Check vec_extract with a non constant element numbering */ + for(i=0;i<10;i++) + { + if (f(a, i) != (i&0x3)) + abort (); + } + + /* Check vec_extract with a constant element numbering */ + if (f0(a) != 0) + abort (); + if (f1(a) != 1) + abort (); + if (f2(a) != 2) + abort (); + if (f3(a) != 3) + abort (); + /* Check that vec_extract works with a constant element higher than + the number of elements. */ + if (f4(a) != 0) + abort (); + + /* Check vec_extract with a non constant element numbering */ + for(i=0;i<10;i++) + { + if (g(b, i) != (i&0x7)) + abort (); + } + + /* Check vec_extract with a constant element numbering */ + if (g0(b) != 0) + abort (); + if (g1(b) != 1) + abort (); + if (g2(b) != 2) + abort (); + if (g3(b) != 3) + abort (); + if (g4(b) != 4) + abort (); + if (g5(b) != 5) + abort (); + if (g6(b) != 6) + abort (); + if (g7(b) != 7) + abort (); + /* Check that vec_extract works with a constant element higher than + the number of elements. */ + if (g8(b) != 0) + abort (); + + return 0; +} + +int main(void) +{ + altivec_check(); /* Exits if AltiVec not supported */ + return main1 (); +} diff --git a/gcc/testsuite/g++.dg/ext/altivec-cell-3.C b/gcc/testsuite/g++.dg/ext/altivec-cell-3.C new file mode 100644 index 00000000000..f7ebcae054e --- /dev/null +++ b/gcc/testsuite/g++.dg/ext/altivec-cell-3.C @@ -0,0 +1,38 @@ +/* { dg-do run { target powerpc*-*-* } } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec" } */ +/* Test the vec_splats and vec_promote VMX intrinsics. */ +#include <altivec.h> +#include "altivec_check.h" + +extern "C" void abort (void); + +vector int a = {0, 0, 0, 0}; +int main1(int t) __attribute__((noinline)); +int main1(int t) +{ + int i; + vector int b = vec_splats(0); + if (__builtin_memcmp (&a, &b, sizeof(vector int))) + abort (); + + b = vec_splats(t); + if (__builtin_memcmp (&a, &b, sizeof(vector int))) + abort (); + + b = vec_promote(0, 1); + if (vec_extract (b, 1) != 0) + abort (); + + b = vec_promote(t, t); + if (vec_extract (b, t) != 0) + abort (); + + return 0; +} + +int main(void) +{ + altivec_check(); /* Exits if AltiVec not supported */ + return main1 (0); +} diff --git a/gcc/testsuite/g++.dg/ext/altivec-cell-4.C b/gcc/testsuite/g++.dg/ext/altivec-cell-4.C new file mode 100644 index 00000000000..10ab162dad2 --- /dev/null +++ b/gcc/testsuite/g++.dg/ext/altivec-cell-4.C @@ -0,0 +1,43 @@ +/* { dg-do run { target powerpc*-*-* } } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec" } */ + +/* Test the vec_splats and vec_promote VMX intrinsics. */ +#include <altivec.h> +#include "altivec_check.h" + +extern "C" void abort (void); + +vector int a[] = {{0, 0, 0, 0}, {1,0,0,0}, {1,2,0,0},{1,2,3,0},{1,2,3,4},{5,2,3,4},{5,6,3,4}}; +vector int c = {0,6,3,4}; +vector int d = {0,0,3,4}; +int main1(int t) __attribute__((noinline)); +int main1(int t) +{ + int i; + vector int b = vec_splats(0); + for(i = 0;i<sizeof(a)/sizeof(a[0])-1;i++) + { + if (__builtin_memcmp (&b, &a[i], sizeof(vector int))) + abort (); + b = vec_insert(i+1, b, i); + } + if (__builtin_memcmp (&b, &a[i], sizeof(vector int))) + abort (); + + b = vec_insert(0, b, 0); + if (__builtin_memcmp (&b, &c, sizeof(vector int))) + abort (); + + b = vec_insert(0, b, 1); + if (__builtin_memcmp (&b, &d, sizeof(vector int))) + abort (); + + return 0; +} + +int main(void) +{ + altivec_check(); /* Exits if AltiVec not supported */ + return main1 (0); +} diff --git a/gcc/testsuite/g++.dg/ext/altivec-cell-5.C b/gcc/testsuite/g++.dg/ext/altivec-cell-5.C new file mode 100644 index 00000000000..95f109d1abe --- /dev/null +++ b/gcc/testsuite/g++.dg/ext/altivec-cell-5.C @@ -0,0 +1,25 @@ +/* { dg-do compile { target powerpc*-*-* } } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec" } */ + +/* Basic test for the new VMX intrinsics and error messages. */ +#include <altivec.h> + +int main(int argc, char **argv) +{ +vector float t; + vec_promote(); /* { dg-error "vec_promote only accepts 2" } */ + vec_promote(1.0f); /* { dg-error "vec_promote only accepts 2" } */ + vec_promote(1.0f, 2, 3); /* { dg-error "vec_promote only accepts 2" } */ + vec_extract (); /* { dg-error "vec_extract only accepts 2" } */ + vec_extract (t); /* { dg-error "vec_extract only accepts 2" } */ + vec_extract (t, 2); + vec_extract (t, 2, 5, 6); /* { dg-error "vec_extract only accepts 2" } */ + vec_splats (); /* { dg-error "vec_splats only accepts 1" } */ + vec_splats (t, 3); /* { dg-error "vec_splats only accepts 1" } */ + vec_insert (); /* { dg-error "vec_insert only accepts 3" } */ + vec_insert (t); /* { dg-error "vec_insert only accepts 3" } */ + vec_insert (t, 3); /* { dg-error "vec_insert only accepts 3" } */ + vec_insert (t, 3, 2, 4, 6, 6); /* { dg-error "vec_insert only accepts 3" } */ + return 0; +} diff --git a/gcc/testsuite/gcc.c-torture/compile/pr37285.c b/gcc/testsuite/gcc.c-torture/compile/pr37285.c new file mode 100644 index 00000000000..972478b1879 --- /dev/null +++ b/gcc/testsuite/gcc.c-torture/compile/pr37285.c @@ -0,0 +1,15 @@ +_bfd_xcoff_canonicalize_dynamic_reloc (unsigned long long l_symndx) +{ + if (l_symndx < 3) + { + switch (l_symndx) + { + case 0: + case 1: + break; + case 2: + _bfd_abort ("HI"); + } + } +} + diff --git a/gcc/testsuite/gcc.c-torture/compile/pr37617.c b/gcc/testsuite/gcc.c-torture/compile/pr37617.c new file mode 100644 index 00000000000..901b8cabf22 --- /dev/null +++ b/gcc/testsuite/gcc.c-torture/compile/pr37617.c @@ -0,0 +1,19 @@ +typedef union +{ + char *string; + double dval; + float fval; +} yystype; +char *f(void) +{ + yystype tok; + tok.dval = 0; + return (tok.string); +} +char *f1(void) +{ + yystype tok; + tok.fval = 0; + return (tok.string); +} + diff --git a/gcc/testsuite/gcc.c-torture/compile/pr37713.c b/gcc/testsuite/gcc.c-torture/compile/pr37713.c new file mode 100644 index 00000000000..04b4394dc56 --- /dev/null +++ b/gcc/testsuite/gcc.c-torture/compile/pr37713.c @@ -0,0 +1,10 @@ +void add_opush(void) +{ + unsigned char formats[] = { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0xff }; + void *dtds[sizeof(formats)]; + unsigned int i; + unsigned char dtd = 0x08; + for (i = 0; i < sizeof(formats); i++) + dtds[i] = &dtd; + sdp_seq_alloc(dtds); +} diff --git a/gcc/testsuite/gcc.dg/torture/pr36891.c b/gcc/testsuite/gcc.dg/torture/pr36891.c index 4efdfc3e1d5..31f7e173142 100644 --- a/gcc/testsuite/gcc.dg/torture/pr36891.c +++ b/gcc/testsuite/gcc.dg/torture/pr36891.c @@ -16,3 +16,6 @@ void RRB( __vector float vdist, __vector float vx) g(pullx); } } + +/* Ignore a warning that is irrelevant to the purpose of this test. */ +/* { dg-prune-output ".*GCC vector returned by reference.*" } */ diff --git a/gcc/testsuite/gcc.target/powerpc/altivec-cell-1.c b/gcc/testsuite/gcc.target/powerpc/altivec-cell-1.c new file mode 100644 index 00000000000..20d29bf0529 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/altivec-cell-1.c @@ -0,0 +1,34 @@ +/* { dg-do compile { target powerpc*-*-* } } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec" } */ + +/* Basic test for the new VMX intrinsics. */ +#include <altivec.h> + +int f(vector int a, int b) +{ + return vec_extract (a, b); +} +short f1(vector short a, int b) +{ + return vec_extract (a, b); +} +vector short f2(vector short a, int b) +{ + return vec_insert (b, a, b); +} +vector float f3(vector float a, int b) +{ + return vec_insert (b, a, b); +} + +float g(void); + +vector float f4(float b, int t) +{ + return vec_promote (g(), t); +} +vector float f5(float b) +{ + return vec_splats (g()); +} diff --git a/gcc/testsuite/gcc.target/powerpc/altivec-cell-2.c b/gcc/testsuite/gcc.target/powerpc/altivec-cell-2.c new file mode 100644 index 00000000000..b9c7c90b303 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/altivec-cell-2.c @@ -0,0 +1,142 @@ +/* { dg-do run { target powerpc*-*-* } } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec" } */ +/* Test the vec_extract VMX intrinsics. */ +#include <altivec.h> +#include "altivec_check.h" + +extern void abort (void); + +vector int a = {0, 1, 2, 3}; +vector short b = {0, 1, 2, 3, 4, 5, 6, 7}; + +int f(vector int a, int b) +{ + return vec_extract (a, b); +} + +int f0 (vector int a) +{ + return vec_extract (a, 0); +} +int f1 (vector int a) +{ + return vec_extract (a, 1); +} +int f2 (vector int a) +{ + return vec_extract (a, 2); +} +int f3 (vector int a) +{ + return vec_extract (a, 3); +} +int f4 (vector int a) +{ + return vec_extract (a, 4); +} + +int g(vector short a, int b) +{ + return vec_extract (a, b); +} + +int g0 (vector short a) +{ + return vec_extract (a, 0); +} +int g1 (vector short a) +{ + return vec_extract (a, 1); +} +int g2 (vector short a) +{ + return vec_extract (a, 2); +} +int g3 (vector short a) +{ + return vec_extract (a, 3); +} + +int g4 (vector short a) +{ + return vec_extract (a, 4); +} +int g5 (vector short a) +{ + return vec_extract (a, 5); +} +int g6 (vector short a) +{ + return vec_extract (a, 6); +} +int g7 (vector short a) +{ + return vec_extract (a, 7); +} +int g8 (vector short a) +{ + return vec_extract (a, 8); +} +int main1(void) __attribute__((noinline)); +int main1(void) +{ + int i; + /* Check vec_extract with a non constant element numbering */ + for(i=0;i<10;i++) + { + if (f(a, i) != (i&0x3)) + abort (); + } + + /* Check vec_extract with a constant element numbering */ + if (f0(a) != 0) + abort (); + if (f1(a) != 1) + abort (); + if (f2(a) != 2) + abort (); + if (f3(a) != 3) + abort (); + /* Check that vec_extract works with a constant element higher than + the number of elements. */ + if (f4(a) != 0) + abort (); + + /* Check vec_extract with a non constant element numbering */ + for(i=0;i<10;i++) + { + if (g(b, i) != (i&0x7)) + abort (); + } + + /* Check vec_extract with a constant element numbering */ + if (g0(b) != 0) + abort (); + if (g1(b) != 1) + abort (); + if (g2(b) != 2) + abort (); + if (g3(b) != 3) + abort (); + if (g4(b) != 4) + abort (); + if (g5(b) != 5) + abort (); + if (g6(b) != 6) + abort (); + if (g7(b) != 7) + abort (); + /* Check that vec_extract works with a constant element higher than + the number of elements. */ + if (g8(b) != 0) + abort (); + + return 0; +} + +int main(void) +{ + altivec_check(); /* Exits if AltiVec not supported */ + return main1 (); +} diff --git a/gcc/testsuite/gcc.target/powerpc/altivec-cell-3.c b/gcc/testsuite/gcc.target/powerpc/altivec-cell-3.c new file mode 100644 index 00000000000..abaf56f2770 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/altivec-cell-3.c @@ -0,0 +1,38 @@ +/* { dg-do run { target powerpc*-*-* } } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec" } */ +/* Test the vec_splats and vec_promote VMX intrinsics. */ +#include <altivec.h> +#include "altivec_check.h" + +extern void abort (void); + +vector int a = {0, 0, 0, 0}; +int main1(int t) __attribute__((noinline)); +int main1(int t) +{ + int i; + vector int b = vec_splats(0); + if (__builtin_memcmp (&a, &b, sizeof(vector int))) + abort (); + + b = vec_splats(t); + if (__builtin_memcmp (&a, &b, sizeof(vector int))) + abort (); + + b = vec_promote(0, 1); + if (vec_extract (b, 1) != 0) + abort (); + + b = vec_promote(t, t); + if (vec_extract (b, t) != 0) + abort (); + + return 0; +} + +int main(void) +{ + altivec_check(); /* Exits if AltiVec not supported */ + return main1 (0); +} diff --git a/gcc/testsuite/gcc.target/powerpc/altivec-cell-4.c b/gcc/testsuite/gcc.target/powerpc/altivec-cell-4.c new file mode 100644 index 00000000000..b800ea51105 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/altivec-cell-4.c @@ -0,0 +1,43 @@ +/* { dg-do run { target powerpc*-*-* } } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec" } */ + +/* Test the vec_splats and vec_promote VMX intrinsics. */ +#include <altivec.h> +#include "altivec_check.h" + +extern void abort (void); + +vector int a[] = {{0, 0, 0, 0}, {1,0,0,0}, {1,2,0,0},{1,2,3,0},{1,2,3,4},{5,2,3,4},{5,6,3,4}}; +vector int c = {0,6,3,4}; +vector int d = {0,0,3,4}; +int main1(int t) __attribute__((noinline)); +int main1(int t) +{ + int i; + vector int b = vec_splats(0); + for(i = 0;i<sizeof(a)/sizeof(a[0])-1;i++) + { + if (__builtin_memcmp (&b, &a[i], sizeof(vector int))) + abort (); + b = vec_insert(i+1, b, i); + } + if (__builtin_memcmp (&b, &a[i], sizeof(vector int))) + abort (); + + b = vec_insert(0, b, 0); + if (__builtin_memcmp (&b, &c, sizeof(vector int))) + abort (); + + b = vec_insert(0, b, 1); + if (__builtin_memcmp (&b, &d, sizeof(vector int))) + abort (); + + return 0; +} + +int main(void) +{ + altivec_check(); /* Exits if AltiVec not supported */ + return main1 (0); +} diff --git a/gcc/testsuite/gcc.target/powerpc/altivec-cell-5.c b/gcc/testsuite/gcc.target/powerpc/altivec-cell-5.c new file mode 100644 index 00000000000..95f109d1abe --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/altivec-cell-5.c @@ -0,0 +1,25 @@ +/* { dg-do compile { target powerpc*-*-* } } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-maltivec" } */ + +/* Basic test for the new VMX intrinsics and error messages. */ +#include <altivec.h> + +int main(int argc, char **argv) +{ +vector float t; + vec_promote(); /* { dg-error "vec_promote only accepts 2" } */ + vec_promote(1.0f); /* { dg-error "vec_promote only accepts 2" } */ + vec_promote(1.0f, 2, 3); /* { dg-error "vec_promote only accepts 2" } */ + vec_extract (); /* { dg-error "vec_extract only accepts 2" } */ + vec_extract (t); /* { dg-error "vec_extract only accepts 2" } */ + vec_extract (t, 2); + vec_extract (t, 2, 5, 6); /* { dg-error "vec_extract only accepts 2" } */ + vec_splats (); /* { dg-error "vec_splats only accepts 1" } */ + vec_splats (t, 3); /* { dg-error "vec_splats only accepts 1" } */ + vec_insert (); /* { dg-error "vec_insert only accepts 3" } */ + vec_insert (t); /* { dg-error "vec_insert only accepts 3" } */ + vec_insert (t, 3); /* { dg-error "vec_insert only accepts 3" } */ + vec_insert (t, 3, 2, 4, 6, 6); /* { dg-error "vec_insert only accepts 3" } */ + return 0; +} diff --git a/gcc/testsuite/gcc.target/powerpc/altivec-cell-6.c b/gcc/testsuite/gcc.target/powerpc/altivec-cell-6.c new file mode 100644 index 00000000000..5d62f18e13f --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/altivec-cell-6.c @@ -0,0 +1,12 @@ +/* { dg-do compile } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-O2 -maltivec -mabi=altivec -mcpu=cell" } */ +#include <altivec.h> + +/* This used to ICE with reloading of a constant address. */ + +vector float f(void) +{ + vector float * a = (void*)16; + return vec_lvlx (0, a); +} diff --git a/gcc/testsuite/gcc.target/powerpc/altivec-cell-7.c b/gcc/testsuite/gcc.target/powerpc/altivec-cell-7.c new file mode 100644 index 00000000000..ae77694008e --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/altivec-cell-7.c @@ -0,0 +1,28 @@ +/* { dg-do compile } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-O2 -maltivec -mabi=altivec -mcpu=cell" } */ +/* { dg-final { scan-assembler-times "vor" 2 } } */ +#include <altivec.h> + +/* Make sure that lvlx and lvrx are not combined into one insn and + we still get a vor. */ + +vector unsigned char +lvx_float (long off, float *p) +{ + vector unsigned char l, r; + + l = (vector unsigned char) vec_lvlx (off, p); + r = (vector unsigned char) vec_lvrx (off, p); + return vec_or(l, r); +} + +vector unsigned char +lvxl_float (long off, float *p) +{ + vector unsigned char l, r; + + l = (vector unsigned char) vec_lvlxl (off, p); + r = (vector unsigned char) vec_lvrxl (off, p); + return vec_or(l, r); +} diff --git a/gcc/testsuite/gcc.target/powerpc/altivec-cell-8.c b/gcc/testsuite/gcc.target/powerpc/altivec-cell-8.c new file mode 100644 index 00000000000..778cd11f793 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/altivec-cell-8.c @@ -0,0 +1,56 @@ +/* { dg-do run } */ +/* { dg-require-effective-target powerpc_altivec_ok } */ +/* { dg-options "-O2 -maltivec -mabi=altivec -mcpu=cell" } */ +#include <altivec.h> +#include <string.h> +#include "altivec_check.h" + +typedef short int sint16; +typedef signed char int8; + +int main1(void) __attribute__((noinline)); +int main1(void) +{ + sint16 test_vector[4] = { 1678, -2356, 19246, -17892 }; + int8 test_dst[128] __attribute__(( aligned( 16 ))); + float test_out[4] __attribute__(( aligned( 16 ))); + int p; + + for( p = 0; p < 24; ++p ) + { + memset( test_dst, 0, 128 ); + memcpy( &test_dst[p], test_vector, 8 ); + { + vector float VR, VL, V; + /* load the righthand section of the misaligned vector */ + VR = (vector float) vec_lvrx( 8, &test_dst[p] ); + VL = (vector float) vec_lvlx( 0, &test_dst[p] ); + /* Vector Shift Left Double by Octet Immediate, move the right hand section into the bytes */ + VR = vec_vsldoi( VR, VR, 2 << 2 ); + /* or those two together */ + V = vec_vor( VL, VR ); + /* sign extend */ + V = (vector float) vec_vupkhsh((vector bool short)V ); + /* fixed to float by S16_SHIFT_BITS bits */ + V = (vector float) vec_vcfsx ((vector signed int)V, 5 ); + + vec_stvx( V, 0, &test_out[0] ); + if (test_out[0] != 52.437500) + abort (); + if (test_out[1] != -73.625000) + abort (); + if (test_out[2] != 601.437500) + abort (); + if (test_out[3] != -559.125000) + abort (); + } + } +return 0; +} + + +int main(void) +{ + altivec_cell_check (); + return main1(); +} diff --git a/gcc/testsuite/gcc.target/powerpc/altivec_check.h b/gcc/testsuite/gcc.target/powerpc/altivec_check.h index 736054821f1..cadcd365d6d 100644 --- a/gcc/testsuite/gcc.target/powerpc/altivec_check.h +++ b/gcc/testsuite/gcc.target/powerpc/altivec_check.h @@ -22,3 +22,17 @@ void altivec_check(void) { #endif signal (SIGILL, SIG_DFL); } + +void altivec_cell_check (void) +{ + /* Exit on systems without the Cell Altivec instructions. */ + signal (SIGILL, sig_ill_handler); +#ifdef __MACH__ + asm volatile ("vor v0,v0,v0"); + asm volatile ("lvlx v0,r0,r0"); +#else + asm volatile ("vor 0,0,0"); + asm volatile ("lvlx 0,0,0"); +#endif + signal (SIGILL, SIG_DFL); +} diff --git a/gcc/testsuite/gcc.target/powerpc/ppc64-abi-3.c b/gcc/testsuite/gcc.target/powerpc/ppc64-abi-3.c index 51e636419fb..8c78c9e2b45 100644 --- a/gcc/testsuite/gcc.target/powerpc/ppc64-abi-3.c +++ b/gcc/testsuite/gcc.target/powerpc/ppc64-abi-3.c @@ -21,8 +21,8 @@ g(v2si v) int main() { - v4si v; - v2si w; + v4si v = { 1, 2, 3, 4 }; + v2si w = { 5, 6 }; v = f (v); /* { dg-error "altivec instructions are disabled" "PR18631" { xfail *-*-* } } */ w = g (w); return 0; diff --git a/gcc/testsuite/gfortran.fortran-torture/execute/intrinsic_leadz.f90 b/gcc/testsuite/gfortran.fortran-torture/execute/intrinsic_leadz.f90 new file mode 100644 index 00000000000..80b61c83d29 --- /dev/null +++ b/gcc/testsuite/gfortran.fortran-torture/execute/intrinsic_leadz.f90 @@ -0,0 +1,46 @@ +program test_intrinsic_leadz + implicit none + + call test_leadz(0_1,0_2,0_4,0_8,1_1,1_2,1_4,1_8,8_1,8_2,8_4,8_8) + stop + + contains + + subroutine test_leadz(z1,z2,z4,z8,i1,i2,i4,i8,e1,e2,e4,e8) + integer(kind=1) :: z1, i1, e1 + integer(kind=2) :: z2, i2, e2 + integer(kind=4) :: z4, i4, e4 + integer(kind=8) :: z8, i8, e8 + + if (leadz(0_1) /= 8) call abort() + if (leadz(0_2) /= 16) call abort() + if (leadz(0_4) /= 32) call abort() + if (leadz(0_8) /= 64) call abort() + + if (leadz(1_1) /= 7) call abort() + if (leadz(1_2) /= 15) call abort() + if (leadz(1_4) /= 31) call abort() + if (leadz(1_8) /= 63) call abort() + + if (leadz(8_1) /= 4) call abort() + if (leadz(8_2) /= 12) call abort() + if (leadz(8_4) /= 28) call abort() + if (leadz(8_8) /= 60) call abort() + + if (leadz(z1) /= 8) call abort() + if (leadz(z2) /= 16) call abort() + if (leadz(z4) /= 32) call abort() + if (leadz(z8) /= 64) call abort() + + if (leadz(i1) /= 7) call abort() + if (leadz(i2) /= 15) call abort() + if (leadz(i4) /= 31) call abort() + if (leadz(i8) /= 63) call abort() + + if (leadz(e1) /= 4) call abort() + if (leadz(e2) /= 12) call abort() + if (leadz(e4) /= 28) call abort() + if (leadz(e8) /= 60) call abort() + end subroutine test_leadz + +end program diff --git a/gcc/testsuite/gfortran.fortran-torture/execute/intrinsic_trailz.f90 b/gcc/testsuite/gfortran.fortran-torture/execute/intrinsic_trailz.f90 new file mode 100644 index 00000000000..948c806b4ac --- /dev/null +++ b/gcc/testsuite/gfortran.fortran-torture/execute/intrinsic_trailz.f90 @@ -0,0 +1,46 @@ +program test_intrinsic_trailz + implicit none + + call test_trailz(0_1,0_2,0_4,0_8,1_1,1_2,1_4,1_8,8_1,8_2,8_4,8_8) + stop + + contains + + subroutine test_trailz(z1,z2,z4,z8,i1,i2,i4,i8,e1,e2,e4,e8) + integer(kind=1) :: z1, i1, e1 + integer(kind=2) :: z2, i2, e2 + integer(kind=4) :: z4, i4, e4 + integer(kind=8) :: z8, i8, e8 + + if (trailz(0_1) /= 8) call abort() + if (trailz(0_2) /= 16) call abort() + if (trailz(0_4) /= 32) call abort() + if (trailz(0_8) /= 64) call abort() + + if (trailz(1_1) /= 0) call abort() + if (trailz(1_2) /= 0) call abort() + if (trailz(1_4) /= 0) call abort() + if (trailz(1_8) /= 0) call abort() + + if (trailz(8_1) /= 3) call abort() + if (trailz(8_2) /= 3) call abort() + if (trailz(8_4) /= 3) call abort() + if (trailz(8_8) /= 3) call abort() + + if (trailz(z1) /= 8) call abort() + if (trailz(z2) /= 16) call abort() + if (trailz(z4) /= 32) call abort() + if (trailz(z8) /= 64) call abort() + + if (trailz(i1) /= 0) call abort() + if (trailz(i2) /= 0) call abort() + if (trailz(i4) /= 0) call abort() + if (trailz(i8) /= 0) call abort() + + if (trailz(e1) /= 3) call abort() + if (trailz(e2) /= 3) call abort() + if (trailz(e4) /= 3) call abort() + if (trailz(e8) /= 3) call abort() + end subroutine test_trailz + +end program diff --git a/gcc/testsuite/gnat.dg/test_overflow_sum.adb b/gcc/testsuite/gnat.dg/test_overflow_sum.adb new file mode 100644 index 00000000000..fc70ac7e9e3 --- /dev/null +++ b/gcc/testsuite/gnat.dg/test_overflow_sum.adb @@ -0,0 +1,45 @@ +-- { dg-do run } +-- { dg-options "-gnato" } + +procedure test_overflow_sum is + pragma Unsuppress (Overflow_Check); + function sum (a, b, c, d, e, f, g, h, i, j, k, l, m, + n, o, p, q, r, s, t, u, v, w, x, y, z : Integer) + return Integer + is + begin + return a + b + c + d + e + f + g + h + i + j + k + l + m + + n + o + p + q + r + s + t + u + v + w + x + y + z; + end; + + f : integer; +begin + f := sum (a => -2**31, b => 1, c => 2**31 - 1, -- 0 + d => 1, e => -2**31, f => 2**31 - 1, -- 0 + g => 2**0, h => 2, i => 4, -- 2**3 - 1 + j => 2**3, k => 2**4, l => 2**5, -- 2**6 - 1 + m => 2**6, n => 2**7, o => 2**8, -- 2**9 - 1 + p => 2**9, q => 2**10, r => 2**11, -- 2**12 - 1 + s => 2**12, t => 2**13, u => 2**14, -- 2**15 - 1 + v => 2**15, w => 2**16, x => 2**17, -- 2**18 - 1 + y => 2**31 - 2**18, z => 0); -- 2**31 - 1 + + if f /= 2**31 - 1 then + raise Program_Error; + end if; + + begin + f := sum (a => f, b => -2**31, c => 1, -- 0 + d => -2**31, e => 1, f => f, -- 0 + g => 2**0, h => 2, i => 4, -- 2**3 - 1 + j => 2**3, k => 2**4, l => 2**5, -- 2**6 - 1 + m => 2**6, n => 2**7, o => 2**8, -- 2**9 - 1 + p => 2**9, q => 2**10, r => 2**11, -- 2**12 - 1 + s => 2**12, t => 2**13, u => 2**14, -- 2**15 - 1 + v => 2**15, w => 2**16, x => 2**17, -- 2**18 - 1 + y => 2**31 - 2**18, z => 1); -- 2**31 (overflow) + raise Program_Error; + exception + when Constraint_Error => null; + end; +end test_overflow_sum; diff --git a/gcc/tree-ssa-pre.c b/gcc/tree-ssa-pre.c index cd344af2d10..84c884b060c 100644 --- a/gcc/tree-ssa-pre.c +++ b/gcc/tree-ssa-pre.c @@ -2885,7 +2885,8 @@ create_expression_by_pieces (basic_block block, pre_expr expr, VN_INFO (forcedname)->value_id = get_next_value_id (); nameexpr = get_or_alloc_expr_for_name (forcedname); add_to_value (VN_INFO (forcedname)->value_id, nameexpr); - bitmap_value_replace_in_set (NEW_SETS (block), nameexpr); + if (!in_fre) + bitmap_value_replace_in_set (NEW_SETS (block), nameexpr); bitmap_value_replace_in_set (AVAIL_OUT (block), nameexpr); } mark_symbols_for_renaming (stmt); diff --git a/gcc/tree-ssa.c b/gcc/tree-ssa.c index 073e1290b3c..c53c5287453 100644 --- a/gcc/tree-ssa.c +++ b/gcc/tree-ssa.c @@ -1159,15 +1159,15 @@ useless_type_conversion_p_1 (tree outer_type, tree inner_type) /* Recurse for complex types. */ else if (TREE_CODE (inner_type) == COMPLEX_TYPE && TREE_CODE (outer_type) == COMPLEX_TYPE) - return useless_type_conversion_p_1 (TREE_TYPE (outer_type), - TREE_TYPE (inner_type)); + return useless_type_conversion_p (TREE_TYPE (outer_type), + TREE_TYPE (inner_type)); /* Recurse for vector types with the same number of subparts. */ else if (TREE_CODE (inner_type) == VECTOR_TYPE && TREE_CODE (outer_type) == VECTOR_TYPE && TYPE_PRECISION (inner_type) == TYPE_PRECISION (outer_type)) - return useless_type_conversion_p_1 (TREE_TYPE (outer_type), - TREE_TYPE (inner_type)); + return useless_type_conversion_p (TREE_TYPE (outer_type), + TREE_TYPE (inner_type)); /* For aggregates we may need to fall back to structural equality checks. */ diff --git a/gcc/tree-vrp.c b/gcc/tree-vrp.c index 4f1c3288ce7..949b73c2d0a 100644 --- a/gcc/tree-vrp.c +++ b/gcc/tree-vrp.c @@ -7149,9 +7149,16 @@ execute_vrp (void) { size_t j; size_t n = TREE_VEC_LENGTH (su->vec); + tree label; gimple_switch_set_num_labels (su->stmt, n); for (j = 0; j < n; j++) gimple_switch_set_label (su->stmt, j, TREE_VEC_ELT (su->vec, j)); + /* As we may have replaced the default label with a regular one + make sure to make it a real default label again. This ensures + optimal expansion. */ + label = gimple_switch_default_label (su->stmt); + CASE_LOW (label) = NULL_TREE; + CASE_HIGH (label) = NULL_TREE; } if (VEC_length (edge, to_remove_edges) > 0) diff --git a/gcc/tree.c b/gcc/tree.c index 3d2f3e1fe3d..4b178d5073f 100644 --- a/gcc/tree.c +++ b/gcc/tree.c @@ -2492,6 +2492,11 @@ contains_placeholder_p (const_tree exp) || CONTAINS_PLACEHOLDER_P (TREE_OPERAND (exp, 1)) || CONTAINS_PLACEHOLDER_P (TREE_OPERAND (exp, 2))); + case SAVE_EXPR: + /* The save_expr function never wraps anything containing + a PLACEHOLDER_EXPR. */ + return 0; + default: break; } |