diff options
author | Yvan Roux <yvan.roux@linaro.org> | 2014-06-25 13:10:09 +0000 |
---|---|---|
committer | Yvan Roux <yvan.roux@linaro.org> | 2014-06-25 13:10:09 +0000 |
commit | 8d05d946138a1ef75e4cc8b3bbe6aca74305ed07 (patch) | |
tree | b4e606101891d7d8557eb22261a7cb486764822a | |
parent | 3172e89f41dd407cd91d52561829e851d8d789a8 (diff) | |
parent | bb43c0576eb2e1b3806b9997520a7cb2d8527fd7 (diff) |
Merge branches/gcc-4_9-branch rev 211964
git-svn-id: https://gcc.gnu.org/svn/gcc/branches/linaro/gcc-4_9-branch@211979 138bc75d-0d04-0410-961f-82ee72b054a4
142 files changed, 3774 insertions, 554 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index b3d8033a3e6..cb0d5e44140 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,363 @@ +2014-06-24 Jakub Jelinek <jakub@redhat.com> + + PR target/61570 + * config/i386/driver-i386.c (host_detect_local_cpu): For unknown + model family 6 CPU with has_longmode never use a CPU without + 64-bit support. + + * gimplify.c (gimplify_omp_for): For #pragma omp for simd iterator + not mentioned in clauses use private clause if the iterator is + declared in #pragma omp for simd, and when adding lastprivate + instead, add it to the outer #pragma omp for too. Diagnose + if the variable is private in outer context. For simd collapse > 1 + loops, replace all iterators with temporaries. + * omp-low.c (lower_rec_input_clauses): Handle LINEAR clause the + same even in collapse > 1 loops. + +2014-06-23 Alan Modra <amodra@gmail.com> + + PR bootstrap/61583 + * tree-vrp.c (remove_range_assertions): Do not set is_unreachable + to zero on debug statements. + +2014-06-10 Kyrylo Tkachov <kyrylo.tkachov@arm.com> + + * config/aarch64/aarch64-simd.md (aarch64_sqdmulh_lane<mode>): + New expander. + (aarch64_sqrdmulh_lane<mode>): Likewise. + (aarch64_sq<r>dmulh_lane<mode>): Rename to... + (aarch64_sq<r>dmulh_lane<mode>_interna): ...this. + (aarch64_sqdmulh_laneq<mode>): New expander. + (aarch64_sqrdmulh_laneq<mode>): Likewise. + (aarch64_sq<r>dmulh_laneq<mode>): Rename to... + (aarch64_sq<r>dmulh_laneq<mode>_internal): ...this. + (aarch64_sqdmulh_lane<mode>): New expander. + (aarch64_sqrdmulh_lane<mode>): Likewise. + (aarch64_sq<r>dmulh_lane<mode>): Rename to... + (aarch64_sq<r>dmulh_lane<mode>_internal): ...this. + (aarch64_sqdmlal_lane<mode>): Add lane flip for big-endian. + (aarch64_sqdmlal_laneq<mode>): Likewise. + (aarch64_sqdmlsl_lane<mode>): Likewise. + (aarch64_sqdmlsl_laneq<mode>): Likewise. + (aarch64_sqdmlal2_lane<mode>): Likewise. + (aarch64_sqdmlal2_laneq<mode>): Likewise. + (aarch64_sqdmlsl2_lane<mode>): Likewise. + (aarch64_sqdmlsl2_laneq<mode>): Likewise. + (aarch64_sqdmull_lane<mode>): Likewise. + (aarch64_sqdmull_laneq<mode>): Likewise. + (aarch64_sqdmull2_lane<mode>): Likewise. + (aarch64_sqdmull2_laneq<mode>): Likewise. + +2014-06-20 Martin Jambor <mjambor@suse.cz> + + PR ipa/61540 + * ipa-prop.c (impossible_devirt_target): New function. + (try_make_edge_direct_virtual_call): Use it, also instead of + asserting. + +2014-06-20 Martin Jambor <mjambor@suse.cz> + + PR ipa/61211 + * cgraph.c (clone_of_p): Allow skipped_branch to deal with + expanded clones. + +2014-06-20 Chung-Lin Tang <cltang@codesourcery.com> + + Backport from mainline + + 2014-06-20 Julian Brown <julian@codesourcery.com> + Chung-Lin Tang <cltang@codesourcery.com> + + * config/arm/arm.c (arm_output_mi_thunk): Fix offset for + TARGET_THUMB1_ONLY. Add comments. + +2014-06-18 Uros Bizjak <ubizjak@gmail.com> + + Backport from mainline + 2014-06-16 Uros Bizjak <ubizjak@gmail.com> + + * config/i386/i386.c (decide_alg): Correctly handle + maximum size of stringop algorithm. + +2014-06-18 Richard Henderson <rth@redhat.com> + + PR target/61545 + * config/aarch64/aarch64.md (tlsdesc_small): Clobber CC_REGNUM. + +2014-06-17 Yufeng Zhang <yufeng.zhang@arm.com> + + PR target/61483 + * config/aarch64/aarch64.c (aarch64_layout_arg): Add new local + variable 'size'; calculate 'size' right in the front; use + 'size' to compute 'nregs' (when 'allocate_ncrn != 0') and + pcum->aapcs_stack_words. + +2014-06-17 Nick Clifton <nickc@redhat.com> + + * config/msp430/msp430.md (mulhisi3): Add a NOP after the DINT. + (umulhi3, mulsidi3, umulsidi3): Likewise. + +2014-06-17 Uros Bizjak <ubizjak@gmail.com> + + Backport from mainline + 2014-06-06 Uros Bizjak <ubizjak@gmail.com> + + PR target/61423 + * config/i386/i386.md (*floatunssi<mode>2_i387_with_xmm): New + define_insn_and_split pattern, merged from *floatunssi<mode>2_1 + and corresponding splitters. Zero extend general register + or memory input operand to XMM temporary. Enable for + TARGET_SSE2 and TARGET_INTER_UNIT_MOVES_TO_VEC only. + (floatunssi<mode>2): Update expander predicate. + +2014-06-16 Vladimir Makarov <vmakarov@redhat.com> + + PR rtl-optimization/61325 + * lra-constraints.c (valid_address_p): Add forward declaration. + (simplify_operand_subreg): Check address validity before and after + alter_reg of memory subreg. + +2014-06-18 Jakub Jelinek <jakub@redhat.com> + + PR plugins/45078 + * config.gcc (arm*-*-linux-*): Include vxworks-dummy.h in tm_file. + +2014-06-13 Peter Bergner <bergner@vnet.ibm.com> + + Backport from mainline + + 2014-06-13 Peter Bergner <bergner@vnet.ibm.com> + PR target/61415 + * config/rs6000/rs6000-builtin.def (BU_MISC_1): Delete. + (BU_MISC_2): Rename to ... + (BU_LDBL128_2): ... this. + * config/rs6000/rs6000.h (RS6000_BTM_LDBL128): New define. + (RS6000_BTM_COMMON): Add RS6000_BTM_LDBL128. + * config/rs6000/rs6000.c (rs6000_builtin_mask_calculate): Handle + RS6000_BTM_LDBL128. + (rs6000_invalid_builtin): Add long double 128-bit builtin support. + (rs6000_builtin_mask_names): Add RS6000_BTM_LDBL128. + * config/rs6000/rs6000.md (unpacktf_0): Remove define)expand. + (unpacktf_1): Likewise. + * doc/extend.texi (__builtin_longdouble_dw0): Remove documentation. + (__builtin_longdouble_dw1): Likewise. + * doc/sourcebuild.texi (longdouble128): Document. + +2014-06-13 Jeff Law <law@redhat.com> + + Backports from mainline: + 2014-06-13 Jeff Law <law@redhat.com> + + PR rtl-optimization/61094 + PR rtl-optimization/61446 + * ree.c (combine_reaching_defs): Get the mode for the copy from + the extension insn rather than the defining insn. + + 2014-06-02 Jeff Law <law@redhat.com> + + PR rtl-optimization/61094 + * ree.c (combine_reaching_defs): Do not reextend an insn if it + was marked as do_no_reextend. If a copy is needed to eliminate + an extension, then mark it as do_not_reextend. + +2014-06-13 Martin Jambor <mjambor@suse.cz> + + PR ipa/61186 + * ipa-devirt.c (possible_polymorphic_call_targets): Store NULL to + cache_token if returning early. + +2014-06-12 Jakub Jelinek <jakub@redhat.com> + + PR middle-end/61486 + * gimplify.c (struct gimplify_omp_ctx): Add distribute field. + (gimplify_adjust_omp_clauses): Don't or in GOVD_LASTPRIVATE + if outer combined construct is distribute. + (gimplify_omp_for): For OMP_DISTRIBUTE set + gimplify_omp_ctxp->distribute. + * omp-low.c (scan_sharing_clauses) <case OMP_CLAUSE_SHARED>: For + GIMPLE_OMP_TEAMS, if decl isn't global in outer context, record + mapping into decl map. + +2014-06-12 Jeff Law <law@redhat.com> + + Backports from mainline: + + 2014-06-12 Jeff Law <law@redhat.com> + + PR tree-optimization/61009 + * tree-ssa-threadedge.c (thread_through_normal_block): Correct return + value when we stop processing a block due to problematic PHIs. + + 2014-06-05 Jeff Law <law@redhat.com> + + PR tree-optimization/61289 + * tree-ssa-threadedge.c (invalidate_equivalences): Remove SRC_MAP and + DST_MAP parameters. Invalidate by walking all the SSA_NAME_VALUES + looking for those which match LHS. All callers changed. + (record_temporary_equivalences_from_phis): Remove SRC_MAP and DST_MAP + parameters and code which manipulated them. All callers changed. + (record_temporary_equivalences_from_stmts_at_dest): Remove SRC_MAP + and DST_MAP parameters. Simplify invalidation code by just calling + invalidate_equivalences. All callers changed. + (thread_across_edge): Simplify now that we don't need to maintain + the map of equivalences to invalidate. + +2014-06-12 Eric Botcazou <ebotcazou@adacore.com> + + * tree-core.h (DECL_NONALIASED): Use proper spelling in comment. + +2014-06-12 Georg-Johann Lay <avr@gjlay.de> + + Backport from 2014-05-14 trunk r210418 + * config/avr/avr.h (REG_CLASS_CONTENTS): Use unsigned suffix for + shifted values to avoid build warning. + +2014-06-12 Georg-Johann Lay <avr@gjlay.de> + + Backport from 2014-05-09 trunk r210272 + + * config/avr/avr-fixed.md (round<mode>3): Use -1U instead of -1 in + unsigned int initializers for regno_in, regno_out. + + Backport from 2014-06-12 trunk r211491 + + PR target/61443 + * config/avr/avr.md (push<mode>1): Avoid (subreg(mem)) when + loading from address spaces. + +2014-06-12 Alan Modra <amodra@gmail.com> + + PR target/61300 + * doc/tm.texi.in (INCOMING_REG_PARM_STACK_SPACE): Document. + * doc/tm.texi: Regenerate. + * function.c (INCOMING_REG_PARM_STACK_SPACE): Provide default. + Use throughout in place of REG_PARM_STACK_SPACE. + * config/rs6000/rs6000.c (rs6000_reg_parm_stack_space): Add + "incoming" param. Pass to rs6000_function_parms_need_stack. + (rs6000_function_parms_need_stack): Add "incoming" param, ignore + prototype_p when incoming. Use function decl when incoming + to handle K&R style functions. + * config/rs6000/rs6000.h (REG_PARM_STACK_SPACE): Adjust. + (INCOMING_REG_PARM_STACK_SPACE): Define. + +2014-06-11 Richard Biener <rguenther@suse.de> + + PR tree-optimization/61452 + * tree-ssa-sccvn.c (visit_phi): Remove pointless setting of + expr and has_constants in case we found a leader. + (simplify_binary_expression): Always valueize operands first. + (simplify_unary_expression): Likewise. + +2014-06-11 Richard Biener <rguenther@suse.de> + + PR middle-end/61456 + * tree-ssa-alias.c (nonoverlapping_component_refs_of_decl_p): + Do not use the main variant for the type comparison. + +2014-06-10 Kyrylo Tkachov <kyrylo.tkachov@arm.com> + + * doc/arm-acle-intrinsics.texi: Specify when CRC32 intrinsics are + available. + Simplify description of __crc32d and __crc32cd intrinsics. + * doc/extend.texi (ARM ACLE Intrinsics): Remove comment about CRC32 + availability. + +2014-06-07 Eric Botcazou <ebotcazou@adacore.com> + + * tree-ssa-tail-merge.c (same_succ_hash): Hash the static chain of a + call statement, if any. + (gimple_equal_p) <GIMPLE_CALL>: Compare the static chain of the call + statements, if any. Tidy up. + +2014-06-06 Michael Meissner <meissner@linux.vnet.ibm.com> + + Back port from trunk + 2014-06-06 Michael Meissner <meissner@linux.vnet.ibm.com> + + PR target/61431 + * config/rs6000/vsx.md (VSX_LE): Split VSX_D into 2 separate + iterators, VSX_D that handles 64-bit types, and VSX_LE that + handles swapping the two 64-bit double words on little endian + systems. Include V1TImode and optionally TImode in VSX_LE so that + these types are properly swapped. Change all of the insns and + splits that do the 64-bit swaps to use VSX_LE. + (vsx_le_perm_load_<mode>): Likewise. + (vsx_le_perm_store_<mode>): Likewise. + (splitters for little endian memory operations): Likewise. + (vsx_xxpermdi2_le_<mode>): Likewise. + (vsx_lxvd2x2_le_<mode>): Likewise. + (vsx_stxvd2x2_le_<mode>): Likewise. + +2014-06-06 Vladimir Makarov <vmakarov@redhat.com> + + PR rtl-optimization/61325 + * lra-constraints.c (process_address_1): Check scale equal to one + to prevent transformation: base + scale * index => base + new_reg. + +2014-06-05 Martin Jambor <mjambor@suse.cz> + + PR ipa/61393 + * ipa-cp.c (determine_versionability): Pretend that tm_clones are + not versionable. + +2014-06-04 Richard Biener <rguenther@suse.de> + + PR tree-optimization/61383 + * tree-ssa-ifcombine.c (bb_no_side_effects_p): Make sure + stmts can't trap. + +2014-06-02 Jason Merrill <jason@redhat.com> + + PR c++/61020 + * varpool.c (ctor_for_folding): Handle uninitialized vtables. + +2014-06-03 Martin Jambor <mjambor@suse.cz> + + PR ipa/61160 + * ipa-cp.c (cgraph_edge_brings_value_p): Handle edges leading to + thunks. + +2014-06-03 Andrey Belevantsev <abel@ispras.ru> + + Backport from mainline + 2014-05-14 Andrey Belevantsev <abel@ispras.ru> + + PR rtl-optimization/60866 + * sel-sched-ir (sel_init_new_insn): New parameter old_seqno. + Default it to -1. Pass it down to init_simplejump_data. + (init_simplejump_data): New parameter old_seqno. Pass it down + to get_seqno_for_a_jump. + (get_seqno_for_a_jump): New parameter old_seqno. Use it for + initializing new jump seqno as a last resort. Add comment. + (sel_redirect_edge_and_branch): Save old seqno of the conditional + jump and pass it down to sel_init_new_insn. + (sel_redirect_edge_and_branch_force): Likewise. + +2014-06-03 Andrey Belevantsev <abel@ispras.ru> + + Backport from mainline + 2014-05-14 Andrey Belevantsev <abel@ispras.ru> + + PR rtl-optimization/60901 + * config/i386/i386.c (ix86_dependencies_evaluation_hook): Check that + bb predecessor belongs to the same scheduling region. Adjust comment. + +2014-06-03 Uros Bizjak <ubizjak@gmail.com> + + Backport from mainline + 2014-06-02 Uros Bizjak <ubizjak@gmail.com> + + PR target/61239 + * config/i386/i386.c (ix86_expand_vec_perm) [case V32QImode]: Use + GEN_INT (-128) instead of GEN_INT (128) to set MSB of QImode constant. + +2014-05-29 Vladimir Makarov <vmakarov@redhat.com> + + PR rtl-optimization/61325 + * lra-constraints.c (process_address): Rename to + process_address_1. + (process_address): New function. + 2014-05-29 Uros Bizjak <ubizjak@gmail.com> Backport from mainline @@ -1922,10 +2282,10 @@ PR tree-optimization/60577 * tree-core.h (struct tree_base): Document nothrow_flag use - in VAR_DECL_NONALIASED. - * tree.h (VAR_DECL_NONALIASED): New. + in DECL_NONALIASED. + * tree.h (DECL_NONALIASED): New. (may_be_aliased): Adjust. - * coverage.c (build_var): Set VAR_DECL_NONALIASED. + * coverage.c (build_var): Set DECL_NONALIASED. 2014-03-20 Eric Botcazou <ebotcazou@adacore.com> diff --git a/gcc/DATESTAMP b/gcc/DATESTAMP index 7b43bbd3451..42831acc9b1 100644 --- a/gcc/DATESTAMP +++ b/gcc/DATESTAMP @@ -1 +1 @@ -20140529 +20140625 diff --git a/gcc/c-family/ChangeLog b/gcc/c-family/ChangeLog index 4f277de6830..1e406e448b4 100644 --- a/gcc/c-family/ChangeLog +++ b/gcc/c-family/ChangeLog @@ -1,3 +1,20 @@ +2014-06-12 Jakub Jelinek <jakub@redhat.com> + + PR middle-end/61486 + * c-omp.c (c_omp_split_clauses): Don't crash on firstprivate in + #pragma omp target teams or + #pragma omp {,target }teams distribute simd. + +2014-06-04 Marek Polacek <polacek@redhat.com> + + Backport from mainline + 2014-05-08 Marek Polacek <polacek@redhat.com> + + PR c/61053 + * c-common.c (min_align_of_type): New function factored out from... + (c_sizeof_or_alignof_type): ...here. + * c-common.h (min_align_of_type): Declare. + 2014-05-06 Richard Biener <rguenther@suse.de> * c-opts.c (c_common_post_options): For -freestanding, diff --git a/gcc/c-family/c-common.c b/gcc/c-family/c-common.c index f7f2bb3e30e..f3c0dea234a 100644 --- a/gcc/c-family/c-common.c +++ b/gcc/c-family/c-common.c @@ -4927,6 +4927,26 @@ c_common_get_alias_set (tree t) return -1; } +/* Return the least alignment required for type TYPE. */ + +unsigned int +min_align_of_type (tree type) +{ + unsigned int align = TYPE_ALIGN (type); + align = MIN (align, BIGGEST_ALIGNMENT); +#ifdef BIGGEST_FIELD_ALIGNMENT + align = MIN (align, BIGGEST_FIELD_ALIGNMENT); +#endif + unsigned int field_align = align; +#ifdef ADJUST_FIELD_ALIGN + tree field = build_decl (UNKNOWN_LOCATION, FIELD_DECL, NULL_TREE, + type); + field_align = ADJUST_FIELD_ALIGN (field, field_align); +#endif + align = MIN (align, field_align); + return align / BITS_PER_UNIT; +} + /* Compute the value of 'sizeof (TYPE)' or '__alignof__ (TYPE)', where the IS_SIZEOF parameter indicates which operator is being applied. The COMPLAIN flag controls whether we should diagnose possibly @@ -5005,21 +5025,7 @@ c_sizeof_or_alignof_type (location_t loc, size_int (TYPE_PRECISION (char_type_node) / BITS_PER_UNIT)); else if (min_alignof) - { - unsigned int align = TYPE_ALIGN (type); - align = MIN (align, BIGGEST_ALIGNMENT); -#ifdef BIGGEST_FIELD_ALIGNMENT - align = MIN (align, BIGGEST_FIELD_ALIGNMENT); -#endif - unsigned int field_align = align; -#ifdef ADJUST_FIELD_ALIGN - tree field = build_decl (UNKNOWN_LOCATION, FIELD_DECL, NULL_TREE, - type); - field_align = ADJUST_FIELD_ALIGN (field, field_align); -#endif - align = MIN (align, field_align); - value = size_int (align / BITS_PER_UNIT); - } + value = size_int (min_align_of_type (type)); else value = size_int (TYPE_ALIGN_UNIT (type)); } diff --git a/gcc/c-family/c-common.h b/gcc/c-family/c-common.h index 24959d83e33..06dcb7c2803 100644 --- a/gcc/c-family/c-common.h +++ b/gcc/c-family/c-common.h @@ -758,6 +758,7 @@ extern tree c_wrap_maybe_const (tree, bool); extern tree c_save_expr (tree); extern tree c_common_truthvalue_conversion (location_t, tree); extern void c_apply_type_quals_to_decl (int, tree); +extern unsigned int min_align_of_type (tree); extern tree c_sizeof_or_alignof_type (location_t, tree, bool, bool, int); extern tree c_alignof_expr (location_t, tree); /* Print an error message for invalid operands to arith operation CODE. diff --git a/gcc/c-family/c-omp.c b/gcc/c-family/c-omp.c index dd0a45d968a..6a0e41988a7 100644 --- a/gcc/c-family/c-omp.c +++ b/gcc/c-family/c-omp.c @@ -789,8 +789,13 @@ c_omp_split_clauses (location_t loc, enum tree_code code, else if ((mask & (OMP_CLAUSE_MASK_1 << PRAGMA_OMP_CLAUSE_NUM_TEAMS)) != 0) { - /* This must be #pragma omp {,target }teams distribute. */ - gcc_assert (code == OMP_DISTRIBUTE); + /* This must be one of + #pragma omp {,target }teams distribute + #pragma omp target teams + #pragma omp {,target }teams distribute simd. */ + gcc_assert (code == OMP_DISTRIBUTE + || code == OMP_TEAMS + || code == OMP_SIMD); s = C_OMP_CLAUSE_SPLIT_TEAMS; } else if ((mask & (OMP_CLAUSE_MASK_1 diff --git a/gcc/c/ChangeLog b/gcc/c/ChangeLog index 847b51e4977..acfb3704cd0 100644 --- a/gcc/c/ChangeLog +++ b/gcc/c/ChangeLog @@ -1,3 +1,24 @@ +2014-06-24 Jakub Jelinek <jakub@redhat.com> + + * c-parser.c (c_parser_omp_for_loop): For + #pragma omp parallel for simd move lastprivate clause from parallel + to for rather than simd. + +2014-06-04 Igor Zamyatin <igor.zamyatin@intel.com> + + PR c/58942 + * c-array-notation.c (fix_builtin_array_notation_fn): Handle the case + with a pointer. + +2014-06-04 Marek Polacek <polacek@redhat.com> + + Backport from mainline + 2014-05-08 Marek Polacek <polacek@redhat.com> + + PR c/61053 + * c-decl.c (grokdeclarator): Use min_align_of_type instead of + TYPE_ALIGN_UNIT. + 2014-05-26 Igor Zamyatin <igor.zamyatin@intel.com> PR c/61191 diff --git a/gcc/c/c-array-notation.c b/gcc/c/c-array-notation.c index 127f9a15c34..f8cebbaa3c8 100644 --- a/gcc/c/c-array-notation.c +++ b/gcc/c/c-array-notation.c @@ -310,7 +310,9 @@ fix_builtin_array_notation_fn (tree an_builtin_fn, tree *new_var) || an_type == BUILT_IN_CILKPLUS_SEC_REDUCE_MIN_IND) array_ind_value = build_decl (location, VAR_DECL, NULL_TREE, TREE_TYPE (func_parm)); - array_op0 = (*array_operand)[0]; + array_op0 = (*array_operand)[0]; + if (TREE_CODE (array_op0) == INDIRECT_REF) + array_op0 = TREE_OPERAND (array_op0, 0); switch (an_type) { case BUILT_IN_CILKPLUS_SEC_REDUCE_ADD: diff --git a/gcc/c/c-decl.c b/gcc/c/c-decl.c index df84980e309..47907d5ec7f 100644 --- a/gcc/c/c-decl.c +++ b/gcc/c/c-decl.c @@ -5911,7 +5911,7 @@ grokdeclarator (const struct c_declarator *declarator, else if (declspecs->align_log != -1) { alignas_align = 1U << declspecs->align_log; - if (alignas_align < TYPE_ALIGN_UNIT (type)) + if (alignas_align < min_align_of_type (type)) { if (name) error_at (loc, "%<_Alignas%> specifiers cannot reduce " diff --git a/gcc/c/c-parser.c b/gcc/c/c-parser.c index 6eb235c5c43..99ff5466dbb 100644 --- a/gcc/c/c-parser.c +++ b/gcc/c/c-parser.c @@ -11881,8 +11881,17 @@ c_parser_omp_for_loop (location_t loc, c_parser *parser, enum tree_code code, tree l = build_omp_clause (OMP_CLAUSE_LOCATION (*c), OMP_CLAUSE_LASTPRIVATE); OMP_CLAUSE_DECL (l) = OMP_CLAUSE_DECL (*c); - OMP_CLAUSE_CHAIN (l) = clauses; - clauses = l; + if (code == OMP_SIMD) + { + OMP_CLAUSE_CHAIN (l) + = cclauses[C_OMP_CLAUSE_SPLIT_FOR]; + cclauses[C_OMP_CLAUSE_SPLIT_FOR] = l; + } + else + { + OMP_CLAUSE_CHAIN (l) = clauses; + clauses = l; + } OMP_CLAUSE_SET_CODE (*c, OMP_CLAUSE_SHARED); } } diff --git a/gcc/cgraph.c b/gcc/cgraph.c index be3661af6d3..ac9b460370b 100644 --- a/gcc/cgraph.c +++ b/gcc/cgraph.c @@ -2566,11 +2566,16 @@ clone_of_p (struct cgraph_node *node, struct cgraph_node *node2) skipped_thunk = true; } - if (skipped_thunk - && (!node2->clone_of - || !node2->clone.args_to_skip - || !bitmap_bit_p (node2->clone.args_to_skip, 0))) - return false; + if (skipped_thunk) + { + if (!node2->clone.args_to_skip + || !bitmap_bit_p (node2->clone.args_to_skip, 0)) + return false; + if (node2->former_clone_of == node->decl) + return true; + else if (!node2->clone_of) + return false; + } while (node != node2 && node2) node2 = node2->clone_of; diff --git a/gcc/config.gcc b/gcc/config.gcc index 37d3e14cd51..63e1222535c 100644 --- a/gcc/config.gcc +++ b/gcc/config.gcc @@ -1021,7 +1021,7 @@ arm*-*-linux-*) # ARM GNU/Linux with ELF ;; esac tmake_file="${tmake_file} arm/t-arm arm/t-arm-elf arm/t-bpabi arm/t-linux-eabi" - tm_file="$tm_file arm/bpabi.h arm/linux-eabi.h arm/aout.h arm/arm.h" + tm_file="$tm_file arm/bpabi.h arm/linux-eabi.h arm/aout.h vxworks-dummy.h arm/arm.h" # Define multilib configuration for arm-linux-androideabi. case ${target} in *-androideabi) diff --git a/gcc/config/aarch64/aarch64-simd.md b/gcc/config/aarch64/aarch64-simd.md index e84de9dcbe0..825c748b5b0 100644 --- a/gcc/config/aarch64/aarch64-simd.md +++ b/gcc/config/aarch64/aarch64-simd.md @@ -2650,7 +2650,41 @@ ;; sq<r>dmulh_lane -(define_insn "aarch64_sq<r>dmulh_lane<mode>" +(define_expand "aarch64_sqdmulh_lane<mode>" + [(match_operand:VDQHS 0 "register_operand" "") + (match_operand:VDQHS 1 "register_operand" "") + (match_operand:<VCOND> 2 "register_operand" "") + (match_operand:SI 3 "immediate_operand" "")] + "TARGET_SIMD" + { + aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<VCOND>mode)); + operands[3] = GEN_INT (ENDIAN_LANE_N (<VCOND>mode, INTVAL (operands[3]))); + emit_insn (gen_aarch64_sqdmulh_lane<mode>_internal (operands[0], + operands[1], + operands[2], + operands[3])); + DONE; + } +) + +(define_expand "aarch64_sqrdmulh_lane<mode>" + [(match_operand:VDQHS 0 "register_operand" "") + (match_operand:VDQHS 1 "register_operand" "") + (match_operand:<VCOND> 2 "register_operand" "") + (match_operand:SI 3 "immediate_operand" "")] + "TARGET_SIMD" + { + aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<VCOND>mode)); + operands[3] = GEN_INT (ENDIAN_LANE_N (<VCOND>mode, INTVAL (operands[3]))); + emit_insn (gen_aarch64_sqrdmulh_lane<mode>_internal (operands[0], + operands[1], + operands[2], + operands[3])); + DONE; + } +) + +(define_insn "aarch64_sq<r>dmulh_lane<mode>_internal" [(set (match_operand:VDQHS 0 "register_operand" "=w") (unspec:VDQHS [(match_operand:VDQHS 1 "register_operand" "w") @@ -2666,7 +2700,41 @@ [(set_attr "type" "neon_sat_mul_<Vetype>_scalar<q>")] ) -(define_insn "aarch64_sq<r>dmulh_laneq<mode>" +(define_expand "aarch64_sqdmulh_laneq<mode>" + [(match_operand:VDQHS 0 "register_operand" "") + (match_operand:VDQHS 1 "register_operand" "") + (match_operand:<VCONQ> 2 "register_operand" "") + (match_operand:SI 3 "immediate_operand" "")] + "TARGET_SIMD" + { + aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<VCONQ>mode)); + operands[3] = GEN_INT (ENDIAN_LANE_N (<VCONQ>mode, INTVAL (operands[3]))); + emit_insn (gen_aarch64_sqdmulh_laneq<mode>_internal (operands[0], + operands[1], + operands[2], + operands[3])); + DONE; + } +) + +(define_expand "aarch64_sqrdmulh_laneq<mode>" + [(match_operand:VDQHS 0 "register_operand" "") + (match_operand:VDQHS 1 "register_operand" "") + (match_operand:<VCONQ> 2 "register_operand" "") + (match_operand:SI 3 "immediate_operand" "")] + "TARGET_SIMD" + { + aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<VCONQ>mode)); + operands[3] = GEN_INT (ENDIAN_LANE_N (<VCONQ>mode, INTVAL (operands[3]))); + emit_insn (gen_aarch64_sqrdmulh_laneq<mode>_internal (operands[0], + operands[1], + operands[2], + operands[3])); + DONE; + } +) + +(define_insn "aarch64_sq<r>dmulh_laneq<mode>_internal" [(set (match_operand:VDQHS 0 "register_operand" "=w") (unspec:VDQHS [(match_operand:VDQHS 1 "register_operand" "w") @@ -2676,13 +2744,46 @@ VQDMULH))] "TARGET_SIMD" "* - aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<VCONQ>mode)); operands[3] = GEN_INT (ENDIAN_LANE_N (<VCONQ>mode, INTVAL (operands[3]))); return \"sq<r>dmulh\\t%0.<Vtype>, %1.<Vtype>, %2.<Vetype>[%3]\";" [(set_attr "type" "neon_sat_mul_<Vetype>_scalar<q>")] ) -(define_insn "aarch64_sq<r>dmulh_lane<mode>" +(define_expand "aarch64_sqdmulh_lane<mode>" + [(match_operand:SD_HSI 0 "register_operand" "") + (match_operand:SD_HSI 1 "register_operand" "") + (match_operand:<VCONQ> 2 "register_operand" "") + (match_operand:SI 3 "immediate_operand" "")] + "TARGET_SIMD" + { + aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<VCONQ>mode)); + operands[3] = GEN_INT (ENDIAN_LANE_N (<VCONQ>mode, INTVAL (operands[3]))); + emit_insn (gen_aarch64_sqdmulh_lane<mode>_internal (operands[0], + operands[1], + operands[2], + operands[3])); + DONE; + } +) + +(define_expand "aarch64_sqrdmulh_lane<mode>" + [(match_operand:SD_HSI 0 "register_operand" "") + (match_operand:SD_HSI 1 "register_operand" "") + (match_operand:<VCONQ> 2 "register_operand" "") + (match_operand:SI 3 "immediate_operand" "")] + "TARGET_SIMD" + { + aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<VCONQ>mode)); + operands[3] = GEN_INT (ENDIAN_LANE_N (<VCONQ>mode, INTVAL (operands[3]))); + emit_insn (gen_aarch64_sqrdmulh_lane<mode>_internal (operands[0], + operands[1], + operands[2], + operands[3])); + DONE; + } +) + +(define_insn "aarch64_sq<r>dmulh_lane<mode>_internal" [(set (match_operand:SD_HSI 0 "register_operand" "=w") (unspec:SD_HSI [(match_operand:SD_HSI 1 "register_operand" "w") @@ -2692,7 +2793,6 @@ VQDMULH))] "TARGET_SIMD" "* - aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<VCONQ>mode)); operands[3] = GEN_INT (ENDIAN_LANE_N (<VCONQ>mode, INTVAL (operands[3]))); return \"sq<r>dmulh\\t%<v>0, %<v>1, %2.<v>[%3]\";" [(set_attr "type" "neon_sat_mul_<Vetype>_scalar<q>")] @@ -2774,6 +2874,7 @@ "TARGET_SIMD" { aarch64_simd_lane_bounds (operands[4], 0, GET_MODE_NUNITS (<VCON>mode) / 2); + operands[4] = GEN_INT (ENDIAN_LANE_N (<VCONQ>mode, INTVAL (operands[4]))); emit_insn (gen_aarch64_sqdmlal_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3], operands[4])); @@ -2789,6 +2890,7 @@ "TARGET_SIMD" { aarch64_simd_lane_bounds (operands[4], 0, GET_MODE_NUNITS (<VCON>mode)); + operands[4] = GEN_INT (ENDIAN_LANE_N (<VCON>mode, INTVAL (operands[4]))); emit_insn (gen_aarch64_sqdmlal_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3], operands[4])); @@ -2804,6 +2906,7 @@ "TARGET_SIMD" { aarch64_simd_lane_bounds (operands[4], 0, GET_MODE_NUNITS (<VCON>mode) / 2); + operands[4] = GEN_INT (ENDIAN_LANE_N (<VCON>mode, INTVAL (operands[4]))); emit_insn (gen_aarch64_sqdmlsl_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3], operands[4])); @@ -2819,6 +2922,7 @@ "TARGET_SIMD" { aarch64_simd_lane_bounds (operands[4], 0, GET_MODE_NUNITS (<VCON>mode)); + operands[4] = GEN_INT (ENDIAN_LANE_N (<VCON>mode, INTVAL (operands[4]))); emit_insn (gen_aarch64_sqdmlsl_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3], operands[4])); @@ -2930,6 +3034,7 @@ { rtx p = aarch64_simd_vect_par_cnst_half (<MODE>mode, true); aarch64_simd_lane_bounds (operands[4], 0, GET_MODE_NUNITS (<MODE>mode) / 2); + operands[4] = GEN_INT (ENDIAN_LANE_N (<MODE>mode, INTVAL (operands[4]))); emit_insn (gen_aarch64_sqdmlal2_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3], operands[4], p)); @@ -2946,6 +3051,7 @@ { rtx p = aarch64_simd_vect_par_cnst_half (<MODE>mode, true); aarch64_simd_lane_bounds (operands[4], 0, GET_MODE_NUNITS (<MODE>mode)); + operands[4] = GEN_INT (ENDIAN_LANE_N (<MODE>mode, INTVAL (operands[4]))); emit_insn (gen_aarch64_sqdmlal2_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3], operands[4], p)); @@ -2962,6 +3068,7 @@ { rtx p = aarch64_simd_vect_par_cnst_half (<MODE>mode, true); aarch64_simd_lane_bounds (operands[4], 0, GET_MODE_NUNITS (<MODE>mode) / 2); + operands[4] = GEN_INT (ENDIAN_LANE_N (<MODE>mode, INTVAL (operands[4]))); emit_insn (gen_aarch64_sqdmlsl2_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3], operands[4], p)); @@ -2978,6 +3085,7 @@ { rtx p = aarch64_simd_vect_par_cnst_half (<MODE>mode, true); aarch64_simd_lane_bounds (operands[4], 0, GET_MODE_NUNITS (<MODE>mode)); + operands[4] = GEN_INT (ENDIAN_LANE_N (<MODE>mode, INTVAL (operands[4]))); emit_insn (gen_aarch64_sqdmlsl2_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3], operands[4], p)); @@ -3098,6 +3206,7 @@ "TARGET_SIMD" { aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<VCON>mode) / 2); + operands[3] = GEN_INT (ENDIAN_LANE_N (<VCON>mode, INTVAL (operands[3]))); emit_insn (gen_aarch64_sqdmull_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3])); DONE; @@ -3111,6 +3220,7 @@ "TARGET_SIMD" { aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<VCON>mode)); + operands[3] = GEN_INT (ENDIAN_LANE_N (<VCONQ>mode, INTVAL (operands[3]))); emit_insn (gen_aarch64_sqdmull_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3])); DONE; @@ -3203,6 +3313,7 @@ { rtx p = aarch64_simd_vect_par_cnst_half (<MODE>mode, true); aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<MODE>mode) / 2); + operands[3] = GEN_INT (ENDIAN_LANE_N (<MODE>mode, INTVAL (operands[3]))); emit_insn (gen_aarch64_sqdmull2_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3], p)); @@ -3218,6 +3329,7 @@ { rtx p = aarch64_simd_vect_par_cnst_half (<MODE>mode, true); aarch64_simd_lane_bounds (operands[3], 0, GET_MODE_NUNITS (<MODE>mode)); + operands[3] = GEN_INT (ENDIAN_LANE_N (<MODE>mode, INTVAL (operands[3]))); emit_insn (gen_aarch64_sqdmull2_lane<mode>_internal (operands[0], operands[1], operands[2], operands[3], p)); diff --git a/gcc/config/aarch64/aarch64.c b/gcc/config/aarch64/aarch64.c index 2dcee5aea6d..4ee773e9d2e 100644 --- a/gcc/config/aarch64/aarch64.c +++ b/gcc/config/aarch64/aarch64.c @@ -1493,6 +1493,7 @@ aarch64_layout_arg (cumulative_args_t pcum_v, enum machine_mode mode, CUMULATIVE_ARGS *pcum = get_cumulative_args (pcum_v); int ncrn, nvrn, nregs; bool allocate_ncrn, allocate_nvrn; + HOST_WIDE_INT size; /* We need to do this once per argument. */ if (pcum->aapcs_arg_processed) @@ -1500,6 +1501,11 @@ aarch64_layout_arg (cumulative_args_t pcum_v, enum machine_mode mode, pcum->aapcs_arg_processed = true; + /* Size in bytes, rounded to the nearest multiple of 8 bytes. */ + size + = AARCH64_ROUND_UP (type ? int_size_in_bytes (type) : GET_MODE_SIZE (mode), + UNITS_PER_WORD); + allocate_ncrn = (type) ? !(FLOAT_TYPE_P (type)) : !FLOAT_MODE_P (mode); allocate_nvrn = aarch64_vfp_is_call_candidate (pcum_v, mode, @@ -1550,9 +1556,7 @@ aarch64_layout_arg (cumulative_args_t pcum_v, enum machine_mode mode, } ncrn = pcum->aapcs_ncrn; - nregs = ((type ? int_size_in_bytes (type) : GET_MODE_SIZE (mode)) - + UNITS_PER_WORD - 1) / UNITS_PER_WORD; - + nregs = size / UNITS_PER_WORD; /* C6 - C9. though the sign and zero extension semantics are handled elsewhere. This is the case where the argument fits @@ -1601,13 +1605,12 @@ aarch64_layout_arg (cumulative_args_t pcum_v, enum machine_mode mode, pcum->aapcs_nextncrn = NUM_ARG_REGS; /* The argument is passed on stack; record the needed number of words for - this argument (we can re-use NREGS) and align the total size if - necessary. */ + this argument and align the total size if necessary. */ on_stack: - pcum->aapcs_stack_words = nregs; + pcum->aapcs_stack_words = size / UNITS_PER_WORD; if (aarch64_function_arg_alignment (mode, type) == 16 * BITS_PER_UNIT) pcum->aapcs_stack_size = AARCH64_ROUND_UP (pcum->aapcs_stack_size, - 16 / UNITS_PER_WORD) + 1; + 16 / UNITS_PER_WORD); return; } diff --git a/gcc/config/aarch64/aarch64.md b/gcc/config/aarch64/aarch64.md index 05b278deb5f..30f87b5059c 100644 --- a/gcc/config/aarch64/aarch64.md +++ b/gcc/config/aarch64/aarch64.md @@ -3793,6 +3793,7 @@ (unspec:PTR [(match_operand 0 "aarch64_valid_symref" "S")] UNSPEC_TLSDESC)) (clobber (reg:DI LR_REGNUM)) + (clobber (reg:CC CC_REGNUM)) (clobber (match_scratch:DI 1 "=r"))] "TARGET_TLS_DESC" "adrp\\tx0, %A0\;ldr\\t%<w>1, [x0, #%L0]\;add\\t<w>0, <w>0, %L0\;.tlsdesccall\\t%0\;blr\\t%1" diff --git a/gcc/config/arm/arm.c b/gcc/config/arm/arm.c index c30892550fc..58a128e1ca6 100644 --- a/gcc/config/arm/arm.c +++ b/gcc/config/arm/arm.c @@ -28428,9 +28428,13 @@ arm_output_mi_thunk (FILE *file, tree thunk ATTRIBUTE_UNUSED, fputs (":\n", file); if (flag_pic) { - /* Output ".word .LTHUNKn-7-.LTHUNKPCn". */ + /* Output ".word .LTHUNKn-[3,7]-.LTHUNKPCn". */ rtx tem = XEXP (DECL_RTL (function), 0); - tem = plus_constant (GET_MODE (tem), tem, -7); + /* For TARGET_THUMB1_ONLY the thunk is in Thumb mode, so the PC + pipeline offset is four rather than eight. Adjust the offset + accordingly. */ + tem = plus_constant (GET_MODE (tem), tem, + TARGET_THUMB1_ONLY ? -3 : -7); tem = gen_rtx_MINUS (GET_MODE (tem), tem, gen_rtx_SYMBOL_REF (Pmode, diff --git a/gcc/config/avr/avr-fixed.md b/gcc/config/avr/avr-fixed.md index 1652415b1d0..9c8489edd8e 100644 --- a/gcc/config/avr/avr-fixed.md +++ b/gcc/config/avr/avr-fixed.md @@ -430,8 +430,8 @@ } // Input and output of the libgcc function - const unsigned int regno_in[] = { -1, 22, 22, -1, 18 }; - const unsigned int regno_out[] = { -1, 24, 24, -1, 22 }; + const unsigned int regno_in[] = { -1U, 22, 22, -1U, 18 }; + const unsigned int regno_out[] = { -1U, 24, 24, -1U, 22 }; operands[3] = gen_rtx_REG (<MODE>mode, regno_out[(size_t) GET_MODE_SIZE (<MODE>mode)]); operands[4] = gen_rtx_REG (<MODE>mode, regno_in[(size_t) GET_MODE_SIZE (<MODE>mode)]); diff --git a/gcc/config/avr/avr.h b/gcc/config/avr/avr.h index 78434ec5e0d..9d34983e497 100644 --- a/gcc/config/avr/avr.h +++ b/gcc/config/avr/avr.h @@ -251,18 +251,18 @@ enum reg_class { #define REG_CLASS_CONTENTS { \ {0x00000000,0x00000000}, /* NO_REGS */ \ {0x00000001,0x00000000}, /* R0_REG */ \ - {3 << REG_X,0x00000000}, /* POINTER_X_REGS, r26 - r27 */ \ - {3 << REG_Y,0x00000000}, /* POINTER_Y_REGS, r28 - r29 */ \ - {3 << REG_Z,0x00000000}, /* POINTER_Z_REGS, r30 - r31 */ \ + {3u << REG_X,0x00000000}, /* POINTER_X_REGS, r26 - r27 */ \ + {3u << REG_Y,0x00000000}, /* POINTER_Y_REGS, r28 - r29 */ \ + {3u << REG_Z,0x00000000}, /* POINTER_Z_REGS, r30 - r31 */ \ {0x00000000,0x00000003}, /* STACK_REG, STACK */ \ - {(3 << REG_Y) | (3 << REG_Z), \ + {(3u << REG_Y) | (3u << REG_Z), \ 0x00000000}, /* BASE_POINTER_REGS, r28 - r31 */ \ - {(3 << REG_X) | (3 << REG_Y) | (3 << REG_Z), \ + {(3u << REG_X) | (3u << REG_Y) | (3u << REG_Z), \ 0x00000000}, /* POINTER_REGS, r26 - r31 */ \ - {(3 << REG_X) | (3 << REG_Y) | (3 << REG_Z) | (3 << REG_W), \ + {(3u << REG_X) | (3u << REG_Y) | (3u << REG_Z) | (3u << REG_W), \ 0x00000000}, /* ADDW_REGS, r24 - r31 */ \ {0x00ff0000,0x00000000}, /* SIMPLE_LD_REGS r16 - r23 */ \ - {(3 << REG_X)|(3 << REG_Y)|(3 << REG_Z)|(3 << REG_W)|(0xff << 16), \ + {(3u << REG_X)|(3u << REG_Y)|(3u << REG_Z)|(3u << REG_W)|(0xffu << 16),\ 0x00000000}, /* LD_REGS, r16 - r31 */ \ {0x0000ffff,0x00000000}, /* NO_LD_REGS r0 - r15 */ \ {0xffffffff,0x00000000}, /* GENERAL_REGS, r0 - r31 */ \ diff --git a/gcc/config/avr/avr.md b/gcc/config/avr/avr.md index 2c59bf3f93b..3bb2a914a33 100644 --- a/gcc/config/avr/avr.md +++ b/gcc/config/avr/avr.md @@ -368,6 +368,15 @@ "" { int i; + + // Avoid (subreg (mem)) for non-generic address spaces below. Because + // of the poor addressing capabilities of these spaces it's better to + // load them in one chunk. And it avoids PR61443. + + if (MEM_P (operands[0]) + && !ADDR_SPACE_GENERIC_P (MEM_ADDR_SPACE (operands[0]))) + operands[0] = copy_to_mode_reg (<MODE>mode, operands[0]); + for (i = GET_MODE_SIZE (<MODE>mode) - 1; i >= 0; --i) { rtx part = simplify_gen_subreg (QImode, operands[0], <MODE>mode, i); diff --git a/gcc/config/i386/driver-i386.c b/gcc/config/i386/driver-i386.c index 1f5a11c9c08..80f6a087925 100644 --- a/gcc/config/i386/driver-i386.c +++ b/gcc/config/i386/driver-i386.c @@ -739,6 +739,11 @@ const char *host_detect_local_cpu (int argc, const char **argv) /* Assume Core 2. */ cpu = "core2"; } + else if (has_longmode) + /* Perhaps some emulator? Assume x86-64, otherwise gcc + -march=native would be unusable for 64-bit compilations, + as all the CPUs below are 32-bit only. */ + cpu = "x86-64"; else if (has_sse3) /* It is Core Duo. */ cpu = "pentium-m"; diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c index 2d4a2800b20..6dc6888764b 100644 --- a/gcc/config/i386/i386.c +++ b/gcc/config/i386/i386.c @@ -21507,7 +21507,7 @@ ix86_expand_vec_perm (rtx operands[]) t1 = gen_reg_rtx (V32QImode); t2 = gen_reg_rtx (V32QImode); t3 = gen_reg_rtx (V32QImode); - vt2 = GEN_INT (128); + vt2 = GEN_INT (-128); for (i = 0; i < 32; i++) vec[i] = vt2; vt = gen_rtx_CONST_VECTOR (V32QImode, gen_rtvec_v (32, vec)); @@ -23794,7 +23794,7 @@ decide_alg (HOST_WIDE_INT count, HOST_WIDE_INT expected_size, { const struct stringop_algs * algs; bool optimize_for_speed; - int max = -1; + int max = 0; const struct processor_costs *cost; int i; bool any_alg_usable_p = false; @@ -23832,7 +23832,7 @@ decide_alg (HOST_WIDE_INT count, HOST_WIDE_INT expected_size, /* If expected size is not known but max size is small enough so inline version is a win, set expected size into the range. */ - if (max > 1 && (unsigned HOST_WIDE_INT) max >= max_size + if (((max > 1 && (unsigned HOST_WIDE_INT) max >= max_size) || max == -1) && expected_size == -1) expected_size = min_size / 2 + max_size / 2; @@ -23921,7 +23921,7 @@ decide_alg (HOST_WIDE_INT count, HOST_WIDE_INT expected_size, *dynamic_check = 128; return loop_1_byte; } - if (max == -1) + if (max <= 0) max = 4096; alg = decide_alg (count, max / 2, min_size, max_size, memset, zero_memset, dynamic_check, noalign); @@ -26238,13 +26238,17 @@ ix86_dependencies_evaluation_hook (rtx head, rtx tail) { edge e; edge_iterator ei; - /* Assume that region is SCC, i.e. all immediate predecessors - of non-head block are in the same region. */ + + /* Regions are SCCs with the exception of selective + scheduling with pipelining of outer blocks enabled. + So also check that immediate predecessors of a non-head + block are in the same region. */ FOR_EACH_EDGE (e, ei, bb->preds) { /* Avoid creating of loop-carried dependencies through - using topological odering in region. */ - if (BLOCK_TO_BB (bb->index) > BLOCK_TO_BB (e->src->index)) + using topological ordering in the region. */ + if (rgn == CONTAINING_RGN (e->src->index) + && BLOCK_TO_BB (bb->index) > BLOCK_TO_BB (e->src->index)) add_dependee_for_func_arg (first_arg, e->src); } } diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index fde0a93e68f..e6bf58f0b08 100644 --- a/gcc/config/i386/i386.md +++ b/gcc/config/i386/i386.md @@ -4933,66 +4933,37 @@ ;; Avoid store forwarding (partial memory) stall penalty by extending ;; SImode value to DImode through XMM register instead of pushing two -;; SImode values to stack. Note that even !TARGET_INTER_UNIT_MOVES_TO_VEC -;; targets benefit from this optimization. Also note that fild -;; loads from memory only. +;; SImode values to stack. Also note that fild loads from memory only. -(define_insn "*floatunssi<mode>2_1" - [(set (match_operand:X87MODEF 0 "register_operand" "=f,f") +(define_insn_and_split "*floatunssi<mode>2_i387_with_xmm" + [(set (match_operand:X87MODEF 0 "register_operand" "=f") (unsigned_float:X87MODEF - (match_operand:SI 1 "nonimmediate_operand" "x,m"))) - (clobber (match_operand:DI 2 "memory_operand" "=m,m")) - (clobber (match_scratch:SI 3 "=X,x"))] + (match_operand:SI 1 "nonimmediate_operand" "rm"))) + (clobber (match_scratch:DI 3 "=x")) + (clobber (match_operand:DI 2 "memory_operand" "=m"))] "!TARGET_64BIT && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode) - && TARGET_SSE" + && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES_TO_VEC" "#" - [(set_attr "type" "multi") - (set_attr "mode" "<MODE>")]) - -(define_split - [(set (match_operand:X87MODEF 0 "register_operand") - (unsigned_float:X87MODEF - (match_operand:SI 1 "register_operand"))) - (clobber (match_operand:DI 2 "memory_operand")) - (clobber (match_scratch:SI 3))] - "!TARGET_64BIT - && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode) - && TARGET_SSE - && reload_completed" - [(set (match_dup 2) (match_dup 1)) - (set (match_dup 0) - (float:X87MODEF (match_dup 2)))] - "operands[1] = simplify_gen_subreg (DImode, operands[1], SImode, 0);") - -(define_split - [(set (match_operand:X87MODEF 0 "register_operand") - (unsigned_float:X87MODEF - (match_operand:SI 1 "memory_operand"))) - (clobber (match_operand:DI 2 "memory_operand")) - (clobber (match_scratch:SI 3))] - "!TARGET_64BIT - && TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode) - && TARGET_SSE - && reload_completed" - [(set (match_dup 2) (match_dup 3)) + "&& reload_completed" + [(set (match_dup 3) (zero_extend:DI (match_dup 1))) + (set (match_dup 2) (match_dup 3)) (set (match_dup 0) (float:X87MODEF (match_dup 2)))] -{ - emit_move_insn (operands[3], operands[1]); - operands[3] = simplify_gen_subreg (DImode, operands[3], SImode, 0); -}) + "" + [(set_attr "type" "multi") + (set_attr "mode" "<MODE>")]) (define_expand "floatunssi<mode>2" [(parallel [(set (match_operand:X87MODEF 0 "register_operand") (unsigned_float:X87MODEF (match_operand:SI 1 "nonimmediate_operand"))) - (clobber (match_dup 2)) - (clobber (match_scratch:SI 3))])] + (clobber (match_scratch:DI 3)) + (clobber (match_dup 2))])] "!TARGET_64BIT && ((TARGET_80387 && X87_ENABLE_FLOAT (<X87MODEF:MODE>mode, DImode) - && TARGET_SSE) + && TARGET_SSE2 && TARGET_INTER_UNIT_MOVES_TO_VEC) || (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH))" { if (SSE_FLOAT_MODE_P (<MODE>mode) && TARGET_SSE_MATH) diff --git a/gcc/config/msp430/msp430.md b/gcc/config/msp430/msp430.md index b5114f9279c..5e890ecedc1 100644 --- a/gcc/config/msp430/msp430.md +++ b/gcc/config/msp430/msp430.md @@ -1330,9 +1330,9 @@ "optimize > 2 && msp430_hwmult_type != NONE" "* if (msp430_use_f5_series_hwmult ()) - return \"PUSH.W sr { DINT { MOV.W %1, &0x04C2 { MOV.W %2, &0x04C8 { MOV.W &0x04CA, %L0 { MOV.W &0x04CC, %H0 { POP.W sr\"; + return \"PUSH.W sr { DINT { NOP { MOV.W %1, &0x04C2 { MOV.W %2, &0x04C8 { MOV.W &0x04CA, %L0 { MOV.W &0x04CC, %H0 { POP.W sr\"; else - return \"PUSH.W sr { DINT { MOV.W %1, &0x0132 { MOV.W %2, &0x0138 { MOV.W &0x013A, %L0 { MOV.W &0x013C, %H0 { POP.W sr\"; + return \"PUSH.W sr { DINT { NOP { MOV.W %1, &0x0132 { MOV.W %2, &0x0138 { MOV.W &0x013A, %L0 { MOV.W &0x013C, %H0 { POP.W sr\"; " ) @@ -1343,9 +1343,9 @@ "optimize > 2 && msp430_hwmult_type != NONE" "* if (msp430_use_f5_series_hwmult ()) - return \"PUSH.W sr { DINT { MOV.W %1, &0x04C0 { MOV.W %2, &0x04C8 { MOV.W &0x04CA, %L0 { MOV.W &0x04CC, %H0 { POP.W sr\"; + return \"PUSH.W sr { DINT { NOP { MOV.W %1, &0x04C0 { MOV.W %2, &0x04C8 { MOV.W &0x04CA, %L0 { MOV.W &0x04CC, %H0 { POP.W sr\"; else - return \"PUSH.W sr { DINT { MOV.W %1, &0x0130 { MOV.W %2, &0x0138 { MOV.W &0x013A, %L0 { MOV.W &0x013C, %H0 { POP.W sr\"; + return \"PUSH.W sr { DINT { NOP { MOV.W %1, &0x0130 { MOV.W %2, &0x0138 { MOV.W &0x013A, %L0 { MOV.W &0x013C, %H0 { POP.W sr\"; " ) @@ -1356,9 +1356,9 @@ "optimize > 2 && msp430_hwmult_type != NONE" "* if (msp430_use_f5_series_hwmult ()) - return \"PUSH.W sr { DINT { MOV.W %L1, &0x04D4 { MOV.W %H1, &0x04D6 { MOV.W %L2, &0x04E0 { MOV.W %H2, &0x04E2 { MOV.W &0x04E4, %A0 { MOV.W &0x04E6, %B0 { MOV.W &0x04E8, %C0 { MOV.W &0x04EA, %D0 { POP.W sr\"; + return \"PUSH.W sr { DINT { NOP { MOV.W %L1, &0x04D4 { MOV.W %H1, &0x04D6 { MOV.W %L2, &0x04E0 { MOV.W %H2, &0x04E2 { MOV.W &0x04E4, %A0 { MOV.W &0x04E6, %B0 { MOV.W &0x04E8, %C0 { MOV.W &0x04EA, %D0 { POP.W sr\"; else - return \"PUSH.W sr { DINT { MOV.W %L1, &0x0144 { MOV.W %H1, &0x0146 { MOV.W %L2, &0x0150 { MOV.W %H2, &0x0152 { MOV.W &0x0154, %A0 { MOV.W &0x0156, %B0 { MOV.W &0x0158, %C0 { MOV.W &0x015A, %D0 { POP.W sr\"; + return \"PUSH.W sr { DINT { NOP { MOV.W %L1, &0x0144 { MOV.W %H1, &0x0146 { MOV.W %L2, &0x0150 { MOV.W %H2, &0x0152 { MOV.W &0x0154, %A0 { MOV.W &0x0156, %B0 { MOV.W &0x0158, %C0 { MOV.W &0x015A, %D0 { POP.W sr\"; " ) @@ -1369,8 +1369,8 @@ "optimize > 2 && msp430_hwmult_type != NONE" "* if (msp430_use_f5_series_hwmult ()) - return \"PUSH.W sr { DINT { MOV.W %L1, &0x04D0 { MOV.W %H1, &0x04D2 { MOV.W %L2, &0x04E0 { MOV.W %H2, &0x04E2 { MOV.W &0x04E4, %A0 { MOV.W &0x04E6, %B0 { MOV.W &0x04E8, %C0 { MOV.W &0x04EA, %D0 { POP.W sr\"; + return \"PUSH.W sr { DINT { NOP { MOV.W %L1, &0x04D0 { MOV.W %H1, &0x04D2 { MOV.W %L2, &0x04E0 { MOV.W %H2, &0x04E2 { MOV.W &0x04E4, %A0 { MOV.W &0x04E6, %B0 { MOV.W &0x04E8, %C0 { MOV.W &0x04EA, %D0 { POP.W sr\"; else - return \"PUSH.W sr { DINT { MOV.W %L1, &0x0140 { MOV.W %H1, &0x0142 { MOV.W %L2, &0x0150 { MOV.W %H2, &0x0152 { MOV.W &0x0154, %A0 { MOV.W &0x0156, %B0 { MOV.W &0x0158, %C0 { MOV.W &0x015A, %D0 { POP.W sr\"; + return \"PUSH.W sr { DINT { NOP { MOV.W %L1, &0x0140 { MOV.W %H1, &0x0142 { MOV.W %L2, &0x0150 { MOV.W %H2, &0x0152 { MOV.W &0x0154, %A0 { MOV.W &0x0156, %B0 { MOV.W &0x0158, %C0 { MOV.W &0x015A, %D0 { POP.W sr\"; " ) diff --git a/gcc/config/rs6000/rs6000-builtin.def b/gcc/config/rs6000/rs6000-builtin.def index 8e15bdf1619..220d1e97065 100644 --- a/gcc/config/rs6000/rs6000-builtin.def +++ b/gcc/config/rs6000/rs6000-builtin.def @@ -622,19 +622,12 @@ | RS6000_BTC_TERNARY), \ CODE_FOR_ ## ICODE) /* ICODE */ -/* Miscellaneous builtins. */ -#define BU_MISC_1(ENUM, NAME, ATTR, ICODE) \ - RS6000_BUILTIN_2 (MISC_BUILTIN_ ## ENUM, /* ENUM */ \ - "__builtin_" NAME, /* NAME */ \ - RS6000_BTM_HARD_FLOAT, /* MASK */ \ - (RS6000_BTC_ ## ATTR /* ATTR */ \ - | RS6000_BTC_UNARY), \ - CODE_FOR_ ## ICODE) /* ICODE */ - -#define BU_MISC_2(ENUM, NAME, ATTR, ICODE) \ +/* 128-bit long double floating point builtins. */ +#define BU_LDBL128_2(ENUM, NAME, ATTR, ICODE) \ RS6000_BUILTIN_2 (MISC_BUILTIN_ ## ENUM, /* ENUM */ \ "__builtin_" NAME, /* NAME */ \ - RS6000_BTM_HARD_FLOAT, /* MASK */ \ + (RS6000_BTM_HARD_FLOAT /* MASK */ \ + | RS6000_BTM_LDBL128), \ (RS6000_BTC_ ## ATTR /* ATTR */ \ | RS6000_BTC_BINARY), \ CODE_FOR_ ## ICODE) /* ICODE */ @@ -1593,10 +1586,8 @@ BU_P8V_MISC_3 (BCDSUB_OV, "bcdsub_ov", CONST, bcdsub_unordered) BU_DFP_MISC_2 (PACK_TD, "pack_dec128", CONST, packtd) BU_DFP_MISC_2 (UNPACK_TD, "unpack_dec128", CONST, unpacktd) -BU_MISC_2 (PACK_TF, "pack_longdouble", CONST, packtf) -BU_MISC_2 (UNPACK_TF, "unpack_longdouble", CONST, unpacktf) -BU_MISC_1 (UNPACK_TF_0, "longdouble_dw0", CONST, unpacktf_0) -BU_MISC_1 (UNPACK_TF_1, "longdouble_dw1", CONST, unpacktf_1) +BU_LDBL128_2 (PACK_TF, "pack_longdouble", CONST, packtf) +BU_LDBL128_2 (UNPACK_TF, "unpack_longdouble", CONST, unpacktf) BU_P7_MISC_2 (PACK_V1TI, "pack_vector_int128", CONST, packv1ti) BU_P7_MISC_2 (UNPACK_V1TI, "unpack_vector_int128", CONST, unpackv1ti) diff --git a/gcc/config/rs6000/rs6000-protos.h b/gcc/config/rs6000/rs6000-protos.h index 69bb26331f3..785f6ce1b64 100644 --- a/gcc/config/rs6000/rs6000-protos.h +++ b/gcc/config/rs6000/rs6000-protos.h @@ -163,7 +163,7 @@ extern tree altivec_resolve_overloaded_builtin (location_t, tree, void *); extern rtx rs6000_libcall_value (enum machine_mode); extern rtx rs6000_va_arg (tree, tree); extern int function_ok_for_sibcall (tree); -extern int rs6000_reg_parm_stack_space (tree); +extern int rs6000_reg_parm_stack_space (tree, bool); extern void rs6000_elf_declare_function_name (FILE *, const char *, tree); extern bool rs6000_elf_in_small_data_p (const_tree); #ifdef ARGS_SIZE_RTX diff --git a/gcc/config/rs6000/rs6000.c b/gcc/config/rs6000/rs6000.c index fcb884f05ac..bf67e72981c 100644 --- a/gcc/config/rs6000/rs6000.c +++ b/gcc/config/rs6000/rs6000.c @@ -3037,7 +3037,8 @@ rs6000_builtin_mask_calculate (void) | ((TARGET_CRYPTO) ? RS6000_BTM_CRYPTO : 0) | ((TARGET_HTM) ? RS6000_BTM_HTM : 0) | ((TARGET_DFP) ? RS6000_BTM_DFP : 0) - | ((TARGET_HARD_FLOAT) ? RS6000_BTM_HARD_FLOAT : 0)); + | ((TARGET_HARD_FLOAT) ? RS6000_BTM_HARD_FLOAT : 0) + | ((TARGET_LONG_DOUBLE_128) ? RS6000_BTM_LDBL128 : 0)); } /* Override command line options. Mostly we process the processor type and @@ -10478,35 +10479,65 @@ rs6000_parm_needs_stack (cumulative_args_t args_so_far, tree type) list, or passes any parameter in memory. */ static bool -rs6000_function_parms_need_stack (tree fun) +rs6000_function_parms_need_stack (tree fun, bool incoming) { - function_args_iterator args_iter; - tree arg_type; + tree fntype, result; CUMULATIVE_ARGS args_so_far_v; cumulative_args_t args_so_far; if (!fun) /* Must be a libcall, all of which only use reg parms. */ return false; + + fntype = fun; if (!TYPE_P (fun)) - fun = TREE_TYPE (fun); + fntype = TREE_TYPE (fun); /* Varargs functions need the parameter save area. */ - if (!prototype_p (fun) || stdarg_p (fun)) + if ((!incoming && !prototype_p (fntype)) || stdarg_p (fntype)) return true; - INIT_CUMULATIVE_INCOMING_ARGS (args_so_far_v, fun, NULL_RTX); + INIT_CUMULATIVE_INCOMING_ARGS (args_so_far_v, fntype, NULL_RTX); args_so_far = pack_cumulative_args (&args_so_far_v); - if (aggregate_value_p (TREE_TYPE (fun), fun)) + /* When incoming, we will have been passed the function decl. + It is necessary to use the decl to handle K&R style functions, + where TYPE_ARG_TYPES may not be available. */ + if (incoming) { - tree type = build_pointer_type (TREE_TYPE (fun)); - rs6000_parm_needs_stack (args_so_far, type); + gcc_assert (DECL_P (fun)); + result = DECL_RESULT (fun); } + else + result = TREE_TYPE (fntype); - FOREACH_FUNCTION_ARGS (fun, arg_type, args_iter) - if (rs6000_parm_needs_stack (args_so_far, arg_type)) - return true; + if (result && aggregate_value_p (result, fntype)) + { + if (!TYPE_P (result)) + result = TREE_TYPE (result); + result = build_pointer_type (result); + rs6000_parm_needs_stack (args_so_far, result); + } + + if (incoming) + { + tree parm; + + for (parm = DECL_ARGUMENTS (fun); + parm && parm != void_list_node; + parm = TREE_CHAIN (parm)) + if (rs6000_parm_needs_stack (args_so_far, TREE_TYPE (parm))) + return true; + } + else + { + function_args_iterator args_iter; + tree arg_type; + + FOREACH_FUNCTION_ARGS (fntype, arg_type, args_iter) + if (rs6000_parm_needs_stack (args_so_far, arg_type)) + return true; + } return false; } @@ -10518,7 +10549,7 @@ rs6000_function_parms_need_stack (tree fun) all parameters in registers. */ int -rs6000_reg_parm_stack_space (tree fun) +rs6000_reg_parm_stack_space (tree fun, bool incoming) { int reg_parm_stack_space; @@ -10536,7 +10567,7 @@ rs6000_reg_parm_stack_space (tree fun) case ABI_ELFv2: /* ??? Recomputing this every time is a bit expensive. Is there a place to cache this information? */ - if (rs6000_function_parms_need_stack (fun)) + if (rs6000_function_parms_need_stack (fun, incoming)) reg_parm_stack_space = TARGET_64BIT ? 64 : 32; else reg_parm_stack_space = 0; @@ -13560,11 +13591,15 @@ rs6000_invalid_builtin (enum rs6000_builtins fncode) else if ((fnmask & (RS6000_BTM_DFP | RS6000_BTM_P8_VECTOR)) == (RS6000_BTM_DFP | RS6000_BTM_P8_VECTOR)) error ("Builtin function %s requires the -mhard-dfp and" - "-mpower8-vector options", name); + " -mpower8-vector options", name); else if ((fnmask & RS6000_BTM_DFP) != 0) error ("Builtin function %s requires the -mhard-dfp option", name); else if ((fnmask & RS6000_BTM_P8_VECTOR) != 0) error ("Builtin function %s requires the -mpower8-vector option", name); + else if ((fnmask & (RS6000_BTM_HARD_FLOAT | RS6000_BTM_LDBL128)) + == (RS6000_BTM_HARD_FLOAT | RS6000_BTM_LDBL128)) + error ("Builtin function %s requires the -mhard-float and" + " -mlong-double-128 options", name); else if ((fnmask & RS6000_BTM_HARD_FLOAT) != 0) error ("Builtin function %s requires the -mhard-float option", name); else @@ -31314,6 +31349,7 @@ static struct rs6000_opt_mask const rs6000_builtin_mask_names[] = { "htm", RS6000_BTM_HTM, false, false }, { "hard-dfp", RS6000_BTM_DFP, false, false }, { "hard-float", RS6000_BTM_HARD_FLOAT, false, false }, + { "long-double-128", RS6000_BTM_LDBL128, false, false }, }; /* Option variables that we want to support inside attribute((target)) and diff --git a/gcc/config/rs6000/rs6000.h b/gcc/config/rs6000/rs6000.h index 21330dc657d..2b5d033f802 100644 --- a/gcc/config/rs6000/rs6000.h +++ b/gcc/config/rs6000/rs6000.h @@ -1602,7 +1602,14 @@ extern enum reg_class rs6000_constraints[RS6000_CONSTRAINT_MAX]; /* Define this if stack space is still allocated for a parameter passed in a register. The value is the number of bytes allocated to this area. */ -#define REG_PARM_STACK_SPACE(FNDECL) rs6000_reg_parm_stack_space((FNDECL)) +#define REG_PARM_STACK_SPACE(FNDECL) \ + rs6000_reg_parm_stack_space ((FNDECL), false) + +/* Define this macro if space guaranteed when compiling a function body + is different to space required when making a call, a situation that + can arise with K&R style function definitions. */ +#define INCOMING_REG_PARM_STACK_SPACE(FNDECL) \ + rs6000_reg_parm_stack_space ((FNDECL), true) /* Define this if the above stack space is to be considered part of the space allocated by the caller. */ @@ -2501,8 +2508,8 @@ extern int frame_pointer_needed; #define RS6000_BTC_SAT RS6000_BTC_MISC /* saturate sets VSCR. */ /* Builtin targets. For now, we reuse the masks for those options that are in - target flags, and pick two random bits for SPE and paired which aren't in - target_flags. */ + target flags, and pick three random bits for SPE, paired and ldbl128 which + aren't in target_flags. */ #define RS6000_BTM_ALWAYS 0 /* Always enabled. */ #define RS6000_BTM_ALTIVEC MASK_ALTIVEC /* VMX/altivec vectors. */ #define RS6000_BTM_VSX MASK_VSX /* VSX (vector/scalar). */ @@ -2519,6 +2526,7 @@ extern int frame_pointer_needed; #define RS6000_BTM_CELL MASK_FPRND /* Target is cell powerpc. */ #define RS6000_BTM_DFP MASK_DFP /* Decimal floating point. */ #define RS6000_BTM_HARD_FLOAT MASK_SOFT_FLOAT /* Hardware floating point. */ +#define RS6000_BTM_LDBL128 MASK_MULTIPLE /* 128-bit long double. */ #define RS6000_BTM_COMMON (RS6000_BTM_ALTIVEC \ | RS6000_BTM_VSX \ @@ -2532,7 +2540,8 @@ extern int frame_pointer_needed; | RS6000_BTM_POPCNTD \ | RS6000_BTM_CELL \ | RS6000_BTM_DFP \ - | RS6000_BTM_HARD_FLOAT) + | RS6000_BTM_HARD_FLOAT \ + | RS6000_BTM_LDBL128) /* Define builtin enum index. */ diff --git a/gcc/config/rs6000/rs6000.md b/gcc/config/rs6000/rs6000.md index d737195744b..26d0d153032 100644 --- a/gcc/config/rs6000/rs6000.md +++ b/gcc/config/rs6000/rs6000.md @@ -15806,26 +15806,6 @@ "" "") -;; The Advance Toolchain 7.0-3 added private builtins: __builtin_longdouble_dw0 -;; and __builtin_longdouble_dw1 to optimize glibc. Add support for these -;; builtins here. - -(define_expand "unpacktf_0" - [(set (match_operand:DF 0 "nonimmediate_operand" "") - (unspec:DF [(match_operand:TF 1 "register_operand" "") - (const_int 0)] - UNSPEC_UNPACK_128BIT))] - "" - "") - -(define_expand "unpacktf_1" - [(set (match_operand:DF 0 "nonimmediate_operand" "") - (unspec:DF [(match_operand:TF 1 "register_operand" "") - (const_int 1)] - UNSPEC_UNPACK_128BIT))] - "" - "") - (define_insn_and_split "unpack<mode>_dm" [(set (match_operand:<FP128_64> 0 "nonimmediate_operand" "=d,m,d,r,m") (unspec:<FP128_64> diff --git a/gcc/config/rs6000/vsx.md b/gcc/config/rs6000/vsx.md index 23d85ab0628..61ed99cea41 100644 --- a/gcc/config/rs6000/vsx.md +++ b/gcc/config/rs6000/vsx.md @@ -24,6 +24,13 @@ ;; Iterator for the 2 64-bit vector types (define_mode_iterator VSX_D [V2DF V2DI]) +;; Iterator for the 2 64-bit vector types + 128-bit types that are loaded with +;; lxvd2x to properly handle swapping words on little endian +(define_mode_iterator VSX_LE [V2DF + V2DI + V1TI + (TI "VECTOR_MEM_VSX_P (TImode)")]) + ;; Iterator for the 2 32-bit vector types (define_mode_iterator VSX_W [V4SF V4SI]) @@ -228,8 +235,8 @@ ;; The patterns for LE permuted loads and stores come before the general ;; VSX moves so they match first. (define_insn_and_split "*vsx_le_perm_load_<mode>" - [(set (match_operand:VSX_D 0 "vsx_register_operand" "=wa") - (match_operand:VSX_D 1 "memory_operand" "Z"))] + [(set (match_operand:VSX_LE 0 "vsx_register_operand" "=wa") + (match_operand:VSX_LE 1 "memory_operand" "Z"))] "!BYTES_BIG_ENDIAN && TARGET_VSX" "#" "!BYTES_BIG_ENDIAN && TARGET_VSX" @@ -342,16 +349,16 @@ (set_attr "length" "8")]) (define_insn "*vsx_le_perm_store_<mode>" - [(set (match_operand:VSX_D 0 "memory_operand" "=Z") - (match_operand:VSX_D 1 "vsx_register_operand" "+wa"))] + [(set (match_operand:VSX_LE 0 "memory_operand" "=Z") + (match_operand:VSX_LE 1 "vsx_register_operand" "+wa"))] "!BYTES_BIG_ENDIAN && TARGET_VSX" "#" [(set_attr "type" "vecstore") (set_attr "length" "12")]) (define_split - [(set (match_operand:VSX_D 0 "memory_operand" "") - (match_operand:VSX_D 1 "vsx_register_operand" ""))] + [(set (match_operand:VSX_LE 0 "memory_operand" "") + (match_operand:VSX_LE 1 "vsx_register_operand" ""))] "!BYTES_BIG_ENDIAN && TARGET_VSX && !reload_completed" [(set (match_dup 2) (vec_select:<MODE> @@ -369,8 +376,8 @@ ;; The post-reload split requires that we re-permute the source ;; register in case it is still live. (define_split - [(set (match_operand:VSX_D 0 "memory_operand" "") - (match_operand:VSX_D 1 "vsx_register_operand" ""))] + [(set (match_operand:VSX_LE 0 "memory_operand" "") + (match_operand:VSX_LE 1 "vsx_register_operand" ""))] "!BYTES_BIG_ENDIAN && TARGET_VSX && reload_completed" [(set (match_dup 1) (vec_select:<MODE> @@ -1352,9 +1359,9 @@ ;; xxpermdi for little endian loads and stores. We need several of ;; these since the form of the PARALLEL differs by mode. (define_insn "*vsx_xxpermdi2_le_<mode>" - [(set (match_operand:VSX_D 0 "vsx_register_operand" "=wa") - (vec_select:VSX_D - (match_operand:VSX_D 1 "vsx_register_operand" "wa") + [(set (match_operand:VSX_LE 0 "vsx_register_operand" "=wa") + (vec_select:VSX_LE + (match_operand:VSX_LE 1 "vsx_register_operand" "wa") (parallel [(const_int 1) (const_int 0)])))] "!BYTES_BIG_ENDIAN && VECTOR_MEM_VSX_P (<MODE>mode)" "xxpermdi %x0,%x1,%x1,2" @@ -1401,9 +1408,9 @@ ;; lxvd2x for little endian loads. We need several of ;; these since the form of the PARALLEL differs by mode. (define_insn "*vsx_lxvd2x2_le_<mode>" - [(set (match_operand:VSX_D 0 "vsx_register_operand" "=wa") - (vec_select:VSX_D - (match_operand:VSX_D 1 "memory_operand" "Z") + [(set (match_operand:VSX_LE 0 "vsx_register_operand" "=wa") + (vec_select:VSX_LE + (match_operand:VSX_LE 1 "memory_operand" "Z") (parallel [(const_int 1) (const_int 0)])))] "!BYTES_BIG_ENDIAN && VECTOR_MEM_VSX_P (<MODE>mode)" "lxvd2x %x0,%y1" @@ -1450,9 +1457,9 @@ ;; stxvd2x for little endian stores. We need several of ;; these since the form of the PARALLEL differs by mode. (define_insn "*vsx_stxvd2x2_le_<mode>" - [(set (match_operand:VSX_D 0 "memory_operand" "=Z") - (vec_select:VSX_D - (match_operand:VSX_D 1 "vsx_register_operand" "wa") + [(set (match_operand:VSX_LE 0 "memory_operand" "=Z") + (vec_select:VSX_LE + (match_operand:VSX_LE 1 "vsx_register_operand" "wa") (parallel [(const_int 1) (const_int 0)])))] "!BYTES_BIG_ENDIAN && VECTOR_MEM_VSX_P (<MODE>mode)" "stxvd2x %x1,%y0" diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 7aeede93ae4..6e523c859df 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,56 @@ +2014-06-24 Jakub Jelinek <jakub@redhat.com> + + * parser.c (cp_parser_omp_for_loop): For + #pragma omp parallel for simd move lastprivate clause from parallel + to for rather than simd. + +2014-06-20 Jason Merrill <jason@redhat.com> + + PR c++/59296 + * call.c (add_function_candidate): Avoid special 'this' handling + if we have a ref-qualifier. + + PR c++/61556 + * call.c (build_over_call): Call build_this in template path. + +2014-06-19 Jason Merrill <jason@redhat.com> + + PR c++/59296 + * call.c (add_function_candidate): Set LOOKUP_NO_RVAL_BIND + |LOOKUP_NO_TEMP_BIND for ref-qualifier handling. + + PR c++/61507 + * pt.c (resolve_overloaded_unification): Preserve + ARGUMENT_PACK_EXPLICIT_ARGS. + +2014-06-18 Jason Merrill <jason@redhat.com> + + PR c++/60605 + * pt.c (check_default_tmpl_args): Check DECL_LOCAL_FUNCTION_P. + +2014-06-18 Siva Chandra Reddy <sivachandra@google.com> + + PR debug/57519 + * class.c (handle_using_decl): Pass the correct scope to + cp_emit_debug_info_for_using. + +2014-06-09 Jason Merrill <jason@redhat.com> + + PR c++/61343 + * decl.c (check_initializer): Maybe clear + DECL_INITIALIZED_BY_CONSTANT_EXPRESSION_P. + +2014-06-04 Igor Zamyatin <igor.zamyatin@intel.com> + + PR c/58942 + * c-c++-common/cilk-plus/AN/pr58942.c: Check for correct handling of + the case with a pointer. + +2014-06-02 Jason Merrill <jason@redhat.com> + + PR c++/61134 + * pt.c (pack_deducible_p): Handle canonicalization. + 2014-05-21 Igor Zamyatin <igor.zamyatin@intel.com> PR c/60189 diff --git a/gcc/cp/call.c b/gcc/cp/call.c index 39f910d2293..ae955ef3bfd 100644 --- a/gcc/cp/call.c +++ b/gcc/cp/call.c @@ -1994,6 +1994,9 @@ add_function_candidate (struct z_candidate **candidates, object parameter has reference type. */ bool rv = FUNCTION_RVALUE_QUALIFIED (TREE_TYPE (fn)); parmtype = cp_build_reference_type (parmtype, rv); + /* The special handling of 'this' conversions in compare_ics + does not apply if there is a ref-qualifier. */ + is_this = false; } else { @@ -6760,7 +6763,7 @@ build_over_call (struct z_candidate *cand, int flags, tsubst_flags_t complain) ++nargs; alcarray = XALLOCAVEC (tree, nargs); - alcarray[0] = first_arg; + alcarray[0] = build_this (first_arg); FOR_EACH_VEC_SAFE_ELT (args, ix, arg) alcarray[ix + 1] = arg; argarray = alcarray; @@ -8455,10 +8458,11 @@ compare_ics (conversion *ics1, conversion *ics2) /* [over.ics.rank] --S1 and S2 are reference bindings (_dcl.init.ref_) and neither refers - to an implicit object parameter, and either S1 binds an lvalue reference - to an lvalue and S2 binds an rvalue reference or S1 binds an rvalue - reference to an rvalue and S2 binds an lvalue reference - (C++0x draft standard, 13.3.3.2) + to an implicit object parameter of a non-static member function + declared without a ref-qualifier, and either S1 binds an lvalue + reference to an lvalue and S2 binds an rvalue reference or S1 binds an + rvalue reference to an rvalue and S2 binds an lvalue reference (C++0x + draft standard, 13.3.3.2) --S1 and S2 are reference bindings (_dcl.init.ref_), and the types to which the references refer are the same type except for diff --git a/gcc/cp/class.c b/gcc/cp/class.c index 334bfd5eee7..f4fb4c97290 100644 --- a/gcc/cp/class.c +++ b/gcc/cp/class.c @@ -1300,7 +1300,7 @@ handle_using_decl (tree using_decl, tree t) old_value = NULL_TREE; } - cp_emit_debug_info_for_using (decl, USING_DECL_SCOPE (using_decl)); + cp_emit_debug_info_for_using (decl, t); if (is_overloaded_fn (decl)) flist = decl; diff --git a/gcc/cp/cp-array-notation.c b/gcc/cp/cp-array-notation.c index 65b8bcb8169..71312db80bf 100644 --- a/gcc/cp/cp-array-notation.c +++ b/gcc/cp/cp-array-notation.c @@ -340,6 +340,8 @@ expand_sec_reduce_builtin (tree an_builtin_fn, tree *new_var) array_ind_value = get_temp_regvar (TREE_TYPE (func_parm), func_parm); array_op0 = (*array_operand)[0]; + if (TREE_CODE (array_op0) == INDIRECT_REF) + array_op0 = TREE_OPERAND (array_op0, 0); switch (an_type) { case BUILT_IN_CILKPLUS_SEC_REDUCE_ADD: diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c index 34005944246..19944abd186 100644 --- a/gcc/cp/decl.c +++ b/gcc/cp/decl.c @@ -5797,6 +5797,13 @@ check_initializer (tree decl, tree init, int flags, vec<tree, va_gc> **cleanups) if (init && init != error_mark_node) init_code = build2 (INIT_EXPR, type, decl, init); + if (init_code) + { + /* We might have set these in cp_finish_decl. */ + DECL_INITIALIZED_BY_CONSTANT_EXPRESSION_P (decl) = false; + TREE_CONSTANT (decl) = false; + } + if (init_code && DECL_IN_AGGR_P (decl)) { static int explained = 0; diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c index 06353ceb71e..30c924db910 100644 --- a/gcc/cp/parser.c +++ b/gcc/cp/parser.c @@ -29365,9 +29365,17 @@ cp_parser_omp_for_loop (cp_parser *parser, enum tree_code code, tree clauses, change it to shared (decl) in OMP_PARALLEL_CLAUSES. */ tree l = build_omp_clause (loc, OMP_CLAUSE_LASTPRIVATE); OMP_CLAUSE_DECL (l) = real_decl; - OMP_CLAUSE_CHAIN (l) = clauses; CP_OMP_CLAUSE_INFO (l) = CP_OMP_CLAUSE_INFO (*c); - clauses = l; + if (code == OMP_SIMD) + { + OMP_CLAUSE_CHAIN (l) = cclauses[C_OMP_CLAUSE_SPLIT_FOR]; + cclauses[C_OMP_CLAUSE_SPLIT_FOR] = l; + } + else + { + OMP_CLAUSE_CHAIN (l) = clauses; + clauses = l; + } OMP_CLAUSE_SET_CODE (*c, OMP_CLAUSE_SHARED); CP_OMP_CLAUSE_INFO (*c) = NULL; add_private_clause = false; diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c index 3951997b0a4..b20a79d3614 100644 --- a/gcc/cp/pt.c +++ b/gcc/cp/pt.c @@ -4423,7 +4423,8 @@ check_default_tmpl_args (tree decl, tree parms, bool is_primary, in the template-parameter-list of the definition of a member of a class template. */ - if (TREE_CODE (CP_DECL_CONTEXT (decl)) == FUNCTION_DECL) + if (TREE_CODE (CP_DECL_CONTEXT (decl)) == FUNCTION_DECL + || (TREE_CODE (decl) == FUNCTION_DECL && DECL_LOCAL_FUNCTION_P (decl))) /* You can't have a function template declaration in a local scope, nor you can you define a member of a class template in a local scope. */ @@ -15636,7 +15637,7 @@ pack_deducible_p (tree parm, tree fn) continue; for (packs = PACK_EXPANSION_PARAMETER_PACKS (type); packs; packs = TREE_CHAIN (packs)) - if (TREE_VALUE (packs) == parm) + if (template_args_equal (TREE_VALUE (packs), parm)) { /* The template parameter pack is used in a function parameter pack. If this is the end of the parameter list, the @@ -16697,7 +16698,16 @@ resolve_overloaded_unification (tree tparms, int i = TREE_VEC_LENGTH (targs); for (; i--; ) if (TREE_VEC_ELT (tempargs, i)) - TREE_VEC_ELT (targs, i) = TREE_VEC_ELT (tempargs, i); + { + tree old = TREE_VEC_ELT (targs, i); + tree new_ = TREE_VEC_ELT (tempargs, i); + if (new_ && old && ARGUMENT_PACK_P (old) + && ARGUMENT_PACK_EXPLICIT_ARGS (old)) + /* Don't forget explicit template arguments in a pack. */ + ARGUMENT_PACK_EXPLICIT_ARGS (new_) + = ARGUMENT_PACK_EXPLICIT_ARGS (old); + TREE_VEC_ELT (targs, i) = new_; + } } if (good) return true; diff --git a/gcc/doc/arm-acle-intrinsics.texi b/gcc/doc/arm-acle-intrinsics.texi index e68f4cd2017..8c5523ed57e 100644 --- a/gcc/doc/arm-acle-intrinsics.texi +++ b/gcc/doc/arm-acle-intrinsics.texi @@ -4,6 +4,10 @@ @subsubsection CRC32 intrinsics +These intrinsics are available when the CRC32 architecture extension is +specified, e.g. when the @option{-march=armv8-a+crc} switch is used, or when +the target processor specified with @option{-mcpu} supports it. + @itemize @bullet @item uint32_t __crc32b (uint32_t, uint8_t) @*@emph{Form of expected instruction(s):} @code{crc32b @var{r0}, @var{r0}, @var{r0}} @@ -25,8 +29,7 @@ @itemize @bullet @item uint32_t __crc32d (uint32_t, uint64_t) @*@emph{Form of expected instruction(s):} Two @code{crc32w @var{r0}, @var{r0}, @var{r0}} -instructions for AArch32. One @code{crc32w @var{w0}, @var{w0}, @var{x0}} instruction for -AArch64. +instructions. @end itemize @itemize @bullet @@ -50,6 +53,5 @@ AArch64. @itemize @bullet @item uint32_t __crc32cd (uint32_t, uint64_t) @*@emph{Form of expected instruction(s):} Two @code{crc32cw @var{r0}, @var{r0}, @var{r0}} -instructions for AArch32. One @code{crc32cw @var{w0}, @var{w0}, @var{x0}} instruction for -AArch64. +instructions. @end itemize diff --git a/gcc/doc/extend.texi b/gcc/doc/extend.texi index 23c7b4986bc..10ad6e4faf8 100644 --- a/gcc/doc/extend.texi +++ b/gcc/doc/extend.texi @@ -9915,9 +9915,6 @@ when the @option{-mfpu=neon} switch is used: @node ARM ACLE Intrinsics @subsection ARM ACLE Intrinsics -These built-in intrinsics for the ARMv8-A CRC32 extension are available when -the @option{-march=armv8-a+crc} switch is used: - @include arm-acle-intrinsics.texi @node AVR Built-in Functions @@ -12792,8 +12789,6 @@ double __builtin_rsqrt (double); uint64_t __builtin_ppc_get_timebase (); unsigned long __builtin_ppc_mftb (); double __builtin_unpack_longdouble (long double, int); -double __builtin_longdouble_dw0 (long double); -double __builtin_longdouble_dw1 (long double); long double __builtin_pack_longdouble (double, double); @end smallexample diff --git a/gcc/doc/sourcebuild.texi b/gcc/doc/sourcebuild.texi index 7438980f08e..39152df272a 100644 --- a/gcc/doc/sourcebuild.texi +++ b/gcc/doc/sourcebuild.texi @@ -1295,6 +1295,9 @@ Target has 64-bit @code{double}. @item double64plus Target has @code{double} that is 64 bits or longer. +@item longdouble128 +Target has 128-bit @code{long double}. + @item int32plus Target has @code{int} that is at 32 bits or longer. diff --git a/gcc/doc/tm.texi b/gcc/doc/tm.texi index f7024a74579..0221870cd97 100644 --- a/gcc/doc/tm.texi +++ b/gcc/doc/tm.texi @@ -3947,6 +3947,13 @@ which. @c above is overfull. not sure what to do. --mew 5feb93 did @c something, not sure if it looks good. --mew 10feb93 +@defmac INCOMING_REG_PARM_STACK_SPACE (@var{fndecl}) +Like @code{REG_PARM_STACK_SPACE}, but for incoming register arguments. +Define this macro if space guaranteed when compiling a function body +is different to space required when making a call, a situation that +can arise with K&R style function definitions. +@end defmac + @defmac OUTGOING_REG_PARM_STACK_SPACE (@var{fntype}) Define this to a nonzero value if it is the responsibility of the caller to allocate the area reserved for arguments passed in registers diff --git a/gcc/doc/tm.texi.in b/gcc/doc/tm.texi.in index 6dcbde45cf2..0c7c9aa96c1 100644 --- a/gcc/doc/tm.texi.in +++ b/gcc/doc/tm.texi.in @@ -3498,6 +3498,13 @@ which. @c above is overfull. not sure what to do. --mew 5feb93 did @c something, not sure if it looks good. --mew 10feb93 +@defmac INCOMING_REG_PARM_STACK_SPACE (@var{fndecl}) +Like @code{REG_PARM_STACK_SPACE}, but for incoming register arguments. +Define this macro if space guaranteed when compiling a function body +is different to space required when making a call, a situation that +can arise with K&R style function definitions. +@end defmac + @defmac OUTGOING_REG_PARM_STACK_SPACE (@var{fntype}) Define this to a nonzero value if it is the responsibility of the caller to allocate the area reserved for arguments passed in registers diff --git a/gcc/fortran/ChangeLog b/gcc/fortran/ChangeLog index 15da2d6bd40..ff08edc3cbf 100644 --- a/gcc/fortran/ChangeLog +++ b/gcc/fortran/ChangeLog @@ -1,3 +1,26 @@ +2014-06-15 Francois-Xavier Coudert <fxcoudert@gcc.gnu.org> + + Backport from trunk. + PR fortran/45187 + * trans-decl.c (gfc_create_module_variable): Don't create + Cray-pointee decls twice. + +2014-06-09 Paul Thomas <pault@gcc.gnu.org> + + Backport from trunk. + PR fortran/61406 + * trans-stmt.c (trans_associate_var): Check that array + constructors are constant for direct reference. + +2014-06-05 Richard Biener <rguenther@suse.de> + + PR fortran/61418 + * gfortranspec.c (spec_file): Remove. + (find_spec_file): Likewise. + (lang_specific_driver): Do not look for specs file in -L + or append -specs command line argument. + (lang_specific_pre_link): Always %:include libgfortran.spec. + 2014-05-29 Thomas Koenig <tkoenig@gcc.gnu.org> PR fortran/60834 diff --git a/gcc/fortran/gfortranspec.c b/gcc/fortran/gfortranspec.c index a6296efbf4d..cceee6d2d39 100644 --- a/gcc/fortran/gfortranspec.c +++ b/gcc/fortran/gfortranspec.c @@ -73,34 +73,11 @@ static void append_arg (const struct cl_decoded_option *); static unsigned int g77_newargc; static struct cl_decoded_option *g77_new_decoded_options; -/* The path to the spec file. */ -static char *spec_file = NULL; - /* This will be NULL if we encounter a situation where we should not link in the fortran libraries. */ static const char *library = NULL; -/* Return full path name of spec file if it is in DIR, or NULL if - not. */ -static char * -find_spec_file (const char *dir) -{ - const char dirsep_string[] = { DIR_SEPARATOR, '\0' }; - char *spec; - struct stat sb; - - spec = XNEWVEC (char, strlen (dir) + sizeof (SPEC_FILE) + 4); - strcpy (spec, dir); - strcat (spec, dirsep_string); - strcat (spec, SPEC_FILE); - if (!stat (spec, &sb)) - return spec; - free (spec); - return NULL; -} - - /* Return whether strings S1 and S2 are both NULL or both the same string. */ @@ -313,12 +290,6 @@ For more information about these matters, see the file named COPYING\n\n")); cool facility for handling --help and --verbose --help. */ return; - case OPT_L: - if (!spec_file) - spec_file = find_spec_file (decoded_options[i].arg); - break; - - default: break; } @@ -449,12 +420,6 @@ For more information about these matters, see the file named COPYING\n\n")); #endif - /* Read the specs file corresponding to libgfortran. - If we didn't find the spec file on the -L path, we load it - via lang_specific_pre_link. */ - if (spec_file) - append_option (OPT_specs_, spec_file, 1); - if (verbose && g77_new_decoded_options != g77_x_decoded_options) { fprintf (stderr, _("Driving:")); @@ -473,8 +438,7 @@ For more information about these matters, see the file named COPYING\n\n")); int lang_specific_pre_link (void) { - free (spec_file); - if (spec_file == NULL && library) + if (library) do_spec ("%:include(libgfortran.spec)"); return 0; diff --git a/gcc/fortran/trans-decl.c b/gcc/fortran/trans-decl.c index cf7b661d8e9..b1f66c01982 100644 --- a/gcc/fortran/trans-decl.c +++ b/gcc/fortran/trans-decl.c @@ -4237,8 +4237,8 @@ gfc_create_module_variable (gfc_symbol * sym) } /* Don't generate variables from other modules. Variables from - COMMONs will already have been generated. */ - if (sym->attr.use_assoc || sym->attr.in_common) + COMMONs and Cray pointees will already have been generated. */ + if (sym->attr.use_assoc || sym->attr.in_common || sym->attr.cray_pointee) return; /* Equivalenced variables arrive here after creation. */ diff --git a/gcc/fortran/trans-stmt.c b/gcc/fortran/trans-stmt.c index 00c99fcfb5b..6d2db5ef70f 100644 --- a/gcc/fortran/trans-stmt.c +++ b/gcc/fortran/trans-stmt.c @@ -1164,13 +1164,16 @@ trans_associate_var (gfc_symbol *sym, gfc_wrapped_block *block) { gfc_se se; tree desc; + bool cst_array_ctor; desc = sym->backend_decl; + cst_array_ctor = e->expr_type == EXPR_ARRAY + && gfc_constant_array_constructor_p (e->value.constructor); /* If association is to an expression, evaluate it and create temporary. Otherwise, get descriptor of target for pointer assignment. */ gfc_init_se (&se, NULL); - if (sym->assoc->variable || e->expr_type == EXPR_ARRAY) + if (sym->assoc->variable || cst_array_ctor) { se.direct_byref = 1; se.use_offset = 1; @@ -1181,7 +1184,7 @@ trans_associate_var (gfc_symbol *sym, gfc_wrapped_block *block) /* If we didn't already do the pointer assignment, set associate-name descriptor to the one generated for the temporary. */ - if (!sym->assoc->variable && e->expr_type != EXPR_ARRAY) + if (!sym->assoc->variable && !cst_array_ctor) { int dim; diff --git a/gcc/function.c b/gcc/function.c index a61e4757c7a..8cdf0beaecc 100644 --- a/gcc/function.c +++ b/gcc/function.c @@ -1347,9 +1347,13 @@ static int cfa_offset; #define STACK_POINTER_OFFSET 0 #endif +#if defined (REG_PARM_STACK_SPACE) && !defined (INCOMING_REG_PARM_STACK_SPACE) +#define INCOMING_REG_PARM_STACK_SPACE REG_PARM_STACK_SPACE +#endif + /* If not defined, pick an appropriate default for the offset of dynamically allocated memory depending on the value of ACCUMULATE_OUTGOING_ARGS, - REG_PARM_STACK_SPACE, and OUTGOING_REG_PARM_STACK_SPACE. */ + INCOMING_REG_PARM_STACK_SPACE, and OUTGOING_REG_PARM_STACK_SPACE. */ #ifndef STACK_DYNAMIC_OFFSET @@ -1361,12 +1365,12 @@ static int cfa_offset; `crtl->outgoing_args_size'. Nevertheless, we must allow for it when allocating stack dynamic objects. */ -#if defined(REG_PARM_STACK_SPACE) +#ifdef INCOMING_REG_PARM_STACK_SPACE #define STACK_DYNAMIC_OFFSET(FNDECL) \ ((ACCUMULATE_OUTGOING_ARGS \ ? (crtl->outgoing_args_size \ + (OUTGOING_REG_PARM_STACK_SPACE ((!(FNDECL) ? NULL_TREE : TREE_TYPE (FNDECL))) ? 0 \ - : REG_PARM_STACK_SPACE (FNDECL))) \ + : INCOMING_REG_PARM_STACK_SPACE (FNDECL))) \ : 0) + (STACK_POINTER_OFFSET)) #else #define STACK_DYNAMIC_OFFSET(FNDECL) \ @@ -2221,8 +2225,9 @@ assign_parms_initialize_all (struct assign_parm_data_all *all) #endif all->args_so_far = pack_cumulative_args (&all->args_so_far_v); -#ifdef REG_PARM_STACK_SPACE - all->reg_parm_stack_space = REG_PARM_STACK_SPACE (current_function_decl); +#ifdef INCOMING_REG_PARM_STACK_SPACE + all->reg_parm_stack_space + = INCOMING_REG_PARM_STACK_SPACE (current_function_decl); #endif } diff --git a/gcc/gimplify.c b/gcc/gimplify.c index e2e7e24b8a5..9eaaaa86913 100644 --- a/gcc/gimplify.c +++ b/gcc/gimplify.c @@ -138,6 +138,7 @@ struct gimplify_omp_ctx enum omp_clause_default_kind default_kind; enum omp_region_type region_type; bool combined_loop; + bool distribute; }; static struct gimplify_ctx *gimplify_ctxp; @@ -6329,7 +6330,11 @@ gimplify_adjust_omp_clauses (tree *list_p) if (n == NULL || (n->value & GOVD_DATA_SHARE_CLASS) == 0) { - int flags = GOVD_FIRSTPRIVATE | GOVD_LASTPRIVATE; + int flags = GOVD_FIRSTPRIVATE; + /* #pragma omp distribute does not allow + lastprivate clause. */ + if (!ctx->outer_context->distribute) + flags |= GOVD_LASTPRIVATE; if (n == NULL) omp_add_variable (ctx->outer_context, decl, flags | GOVD_SEEN); @@ -6610,6 +6615,8 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p) || TREE_CODE (for_stmt) == CILK_SIMD); gimplify_scan_omp_clauses (&OMP_FOR_CLAUSES (for_stmt), pre_p, simd ? ORT_SIMD : ORT_WORKSHARE); + if (TREE_CODE (for_stmt) == OMP_DISTRIBUTE) + gimplify_omp_ctxp->distribute = true; /* Handle OMP_FOR_INIT. */ for_pre_body = NULL; @@ -6693,6 +6700,31 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p) bool lastprivate = (!has_decl_expr || !bitmap_bit_p (has_decl_expr, DECL_UID (decl))); + if (lastprivate + && gimplify_omp_ctxp->outer_context + && gimplify_omp_ctxp->outer_context->region_type + == ORT_WORKSHARE + && gimplify_omp_ctxp->outer_context->combined_loop + && !gimplify_omp_ctxp->outer_context->distribute) + { + struct gimplify_omp_ctx *outer + = gimplify_omp_ctxp->outer_context; + n = splay_tree_lookup (outer->variables, + (splay_tree_key) decl); + if (n != NULL + && (n->value & GOVD_DATA_SHARE_CLASS) == GOVD_LOCAL) + lastprivate = false; + else if (omp_check_private (outer, decl, false)) + error ("lastprivate variable %qE is private in outer " + "context", DECL_NAME (decl)); + else + { + omp_add_variable (outer, decl, + GOVD_LASTPRIVATE | GOVD_SEEN); + if (outer->outer_context) + omp_notice_variable (outer->outer_context, decl, true); + } + } c = build_omp_clause (input_location, lastprivate ? OMP_CLAUSE_LASTPRIVATE : OMP_CLAUSE_PRIVATE); @@ -6712,10 +6744,13 @@ gimplify_omp_for (tree *expr_p, gimple_seq *pre_p) /* If DECL is not a gimple register, create a temporary variable to act as an iteration counter. This is valid, since DECL cannot be - modified in the body of the loop. */ + modified in the body of the loop. Similarly for any iteration vars + in simd with collapse > 1 where the iterator vars must be + lastprivate. */ if (orig_for_stmt != for_stmt) var = decl; - else if (!is_gimple_reg (decl)) + else if (!is_gimple_reg (decl) + || (simd && TREE_VEC_LENGTH (OMP_FOR_INIT (for_stmt)) > 1)) { var = create_tmp_var (TREE_TYPE (decl), get_name (decl)); TREE_OPERAND (t, 0) = var; diff --git a/gcc/ipa-cp.c b/gcc/ipa-cp.c index 689378a736f..93b60d62b35 100644 --- a/gcc/ipa-cp.c +++ b/gcc/ipa-cp.c @@ -433,6 +433,8 @@ determine_versionability (struct cgraph_node *node) else if (!opt_for_fn (node->decl, optimize) || !opt_for_fn (node->decl, flag_ipa_cp)) reason = "non-optimized function"; + else if (node->tm_clone) + reason = "transactional memory clone"; else if (lookup_attribute ("omp declare simd", DECL_ATTRIBUTES (node->decl))) { /* Ideally we should clone the SIMD clones themselves and create @@ -2482,7 +2484,8 @@ cgraph_edge_brings_value_p (struct cgraph_edge *cs, struct ipcp_value_source *src) { struct ipa_node_params *caller_info = IPA_NODE_REF (cs->caller); - struct ipa_node_params *dst_info = IPA_NODE_REF (cs->callee); + cgraph_node *real_dest = cgraph_function_node (cs->callee); + struct ipa_node_params *dst_info = IPA_NODE_REF (real_dest); if ((dst_info->ipcp_orig_node && !dst_info->is_all_contexts_clone) || caller_info->node_dead) diff --git a/gcc/ipa-devirt.c b/gcc/ipa-devirt.c index 7f07d2f94ae..0671a8b781c 100644 --- a/gcc/ipa-devirt.c +++ b/gcc/ipa-devirt.c @@ -1449,6 +1449,8 @@ possible_polymorphic_call_targets (tree otr_type, { if (completep) *completep = false; + if (cache_token) + *cache_token = NULL; if (nonconstruction_targetsp) *nonconstruction_targetsp = 0; return nodes; @@ -1459,6 +1461,8 @@ possible_polymorphic_call_targets (tree otr_type, { if (completep) *completep = true; + if (cache_token) + *cache_token = NULL; if (nonconstruction_targetsp) *nonconstruction_targetsp = 0; return nodes; @@ -1472,6 +1476,8 @@ possible_polymorphic_call_targets (tree otr_type, { if (completep) *completep = false; + if (cache_token) + *cache_token = NULL; if (nonconstruction_targetsp) *nonconstruction_targetsp = 0; return nodes; diff --git a/gcc/ipa-prop.c b/gcc/ipa-prop.c index 9f45c76f734..a8ec291ce87 100644 --- a/gcc/ipa-prop.c +++ b/gcc/ipa-prop.c @@ -2701,6 +2701,29 @@ try_make_edge_direct_simple_call (struct cgraph_edge *ie, return cs; } +/* Return the target to be used in cases of impossible devirtualization. IE + and target (the latter can be NULL) are dumped when dumping is enabled. */ + +static tree +impossible_devirt_target (struct cgraph_edge *ie, tree target) +{ + if (dump_file) + { + if (target) + fprintf (dump_file, + "Type inconsident devirtualization: %s/%i->%s\n", + ie->caller->name (), ie->caller->order, + IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (target))); + else + fprintf (dump_file, + "No devirtualization target in %s/%i\n", + ie->caller->name (), ie->caller->order); + } + tree new_target = builtin_decl_implicit (BUILT_IN_UNREACHABLE); + cgraph_get_create_node (new_target); + return new_target; +} + /* Try to find a destination for indirect edge IE that corresponds to a virtual call based on a formal parameter which is described by jump function JFUNC and if it can be determined, make it direct and return the direct edge. @@ -2735,15 +2758,7 @@ try_make_edge_direct_virtual_call (struct cgraph_edge *ie, && DECL_FUNCTION_CODE (target) == BUILT_IN_UNREACHABLE) || !possible_polymorphic_call_target_p (ie, cgraph_get_node (target))) - { - if (dump_file) - fprintf (dump_file, - "Type inconsident devirtualization: %s/%i->%s\n", - ie->caller->name (), ie->caller->order, - IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (target))); - target = builtin_decl_implicit (BUILT_IN_UNREACHABLE); - cgraph_get_create_node (target); - } + target = impossible_devirt_target (ie, target); return ipa_make_edge_direct_to_target (ie, target); } } @@ -2773,10 +2788,7 @@ try_make_edge_direct_virtual_call (struct cgraph_edge *ie, if (targets.length () == 1) target = targets[0]->decl; else - { - target = builtin_decl_implicit (BUILT_IN_UNREACHABLE); - cgraph_get_create_node (target); - } + target = impossible_devirt_target (ie, NULL_TREE); } else { @@ -2791,10 +2803,8 @@ try_make_edge_direct_virtual_call (struct cgraph_edge *ie, if (target) { -#ifdef ENABLE_CHECKING - gcc_assert (possible_polymorphic_call_target_p - (ie, cgraph_get_node (target))); -#endif + if (!possible_polymorphic_call_target_p (ie, cgraph_get_node (target))) + target = impossible_devirt_target (ie, target); return ipa_make_edge_direct_to_target (ie, target); } else diff --git a/gcc/lra-constraints.c b/gcc/lra-constraints.c index aac50876d21..39700810cca 100644 --- a/gcc/lra-constraints.c +++ b/gcc/lra-constraints.c @@ -1231,6 +1231,8 @@ insert_move_for_subreg (rtx *before, rtx *after, rtx origreg, rtx newreg) } } +static int valid_address_p (enum machine_mode mode, rtx addr, addr_space_t as); + /* Make reloads for subreg in operand NOP with internal subreg mode REG_MODE, add new reloads for further processing. Return true if any reload was generated. */ @@ -1261,10 +1263,26 @@ simplify_operand_subreg (int nop, enum machine_mode reg_mode) equivalences in function lra_constraints) and because for spilled pseudos we allocate stack memory enough for the biggest corresponding paradoxical subreg. */ - if ((MEM_P (reg) - && (! SLOW_UNALIGNED_ACCESS (mode, MEM_ALIGN (reg)) - || MEM_ALIGN (reg) >= GET_MODE_ALIGNMENT (mode))) - || (REG_P (reg) && REGNO (reg) < FIRST_PSEUDO_REGISTER)) + if (MEM_P (reg) + && (! SLOW_UNALIGNED_ACCESS (mode, MEM_ALIGN (reg)) + || MEM_ALIGN (reg) >= GET_MODE_ALIGNMENT (mode))) + { + rtx subst, old = *curr_id->operand_loc[nop]; + + alter_subreg (curr_id->operand_loc[nop], false); + subst = *curr_id->operand_loc[nop]; + lra_assert (MEM_P (subst)); + if (! valid_address_p (GET_MODE (reg), XEXP (reg, 0), + MEM_ADDR_SPACE (reg)) + || valid_address_p (GET_MODE (subst), XEXP (subst, 0), + MEM_ADDR_SPACE (subst))) + return true; + /* If the address was valid and became invalid, prefer to reload + the memory. Typical case is when the index scale should + correspond the memory. */ + *curr_id->operand_loc[nop] = old; + } + else if (REG_P (reg) && REGNO (reg) < FIRST_PSEUDO_REGISTER) { alter_subreg (curr_id->operand_loc[nop], false); return true; @@ -2787,9 +2805,14 @@ equiv_address_substitution (struct address_info *ad) Add reloads to the lists *BEFORE and *AFTER. We might need to add reloads to *AFTER because of inc/dec, {pre, post} modify in the - address. Return true for any RTL change. */ + address. Return true for any RTL change. + + The function is a helper function which does not produce all + transformations which can be necessary. It does just basic steps. + To do all necessary transformations use function + process_address. */ static bool -process_address (int nop, rtx *before, rtx *after) +process_address_1 (int nop, rtx *before, rtx *after) { struct address_info ad; rtx new_reg; @@ -2972,6 +2995,13 @@ process_address (int nop, rtx *before, rtx *after) *ad.inner = simplify_gen_binary (PLUS, GET_MODE (new_reg), new_reg, *ad.index); } + else if (get_index_scale (&ad) == 1) + { + /* The last transformation to one reg will be made in + curr_insn_transform function. */ + end_sequence (); + return false; + } else { /* base + scale * index => base + new_reg, @@ -2989,6 +3019,18 @@ process_address (int nop, rtx *before, rtx *after) return true; } +/* Do address reloads until it is necessary. Use process_address_1 as + a helper function. Return true for any RTL changes. */ +static bool +process_address (int nop, rtx *before, rtx *after) +{ + bool res = false; + + while (process_address_1 (nop, before, after)) + res = true; + return res; +} + /* Emit insns to reload VALUE into a new register. VALUE is an auto-increment or auto-decrement RTX whose operand is a register or memory location; so reloading involves incrementing that location. @@ -3273,7 +3315,7 @@ curr_insn_transform (void) change_p = true; lra_update_dup (curr_id, i); } - + if (change_p) /* If we've changed the instruction then any alternative that we chose previously may no longer be valid. */ diff --git a/gcc/omp-low.c b/gcc/omp-low.c index 99f79ba6313..580a8ba94ad 100644 --- a/gcc/omp-low.c +++ b/gcc/omp-low.c @@ -1509,11 +1509,19 @@ scan_sharing_clauses (tree clauses, omp_context *ctx) break; case OMP_CLAUSE_SHARED: + decl = OMP_CLAUSE_DECL (c); /* Ignore shared directives in teams construct. */ if (gimple_code (ctx->stmt) == GIMPLE_OMP_TEAMS) - break; + { + /* Global variables don't need to be copied, + the receiver side will use them directly. */ + tree odecl = maybe_lookup_decl_in_outer_ctx (decl, ctx); + if (is_global_var (odecl)) + break; + insert_decl_map (&ctx->cb, decl, odecl); + break; + } gcc_assert (is_taskreg_ctx (ctx)); - decl = OMP_CLAUSE_DECL (c); gcc_assert (!COMPLETE_TYPE_P (TREE_TYPE (decl)) || !is_variable_sized (decl)); /* Global variables don't need to be copied, @@ -3383,24 +3391,20 @@ lower_rec_input_clauses (tree clauses, gimple_seq *ilist, gimple_seq *dlist, OMP_CLAUSE__LOOPTEMP_); gcc_assert (c); tree l = OMP_CLAUSE_DECL (c); - if (fd->collapse == 1) - { - tree n1 = fd->loop.n1; - tree step = fd->loop.step; - tree itype = TREE_TYPE (l); - if (POINTER_TYPE_P (itype)) - itype = signed_type_for (itype); - l = fold_build2 (MINUS_EXPR, itype, l, n1); - if (TYPE_UNSIGNED (itype) - && fd->loop.cond_code == GT_EXPR) - l = fold_build2 (TRUNC_DIV_EXPR, itype, - fold_build1 (NEGATE_EXPR, - itype, l), - fold_build1 (NEGATE_EXPR, - itype, step)); - else - l = fold_build2 (TRUNC_DIV_EXPR, itype, l, step); - } + tree n1 = fd->loop.n1; + tree step = fd->loop.step; + tree itype = TREE_TYPE (l); + if (POINTER_TYPE_P (itype)) + itype = signed_type_for (itype); + l = fold_build2 (MINUS_EXPR, itype, l, n1); + if (TYPE_UNSIGNED (itype) + && fd->loop.cond_code == GT_EXPR) + l = fold_build2 (TRUNC_DIV_EXPR, itype, + fold_build1 (NEGATE_EXPR, itype, l), + fold_build1 (NEGATE_EXPR, + itype, step)); + else + l = fold_build2 (TRUNC_DIV_EXPR, itype, l, step); t = fold_build2 (MULT_EXPR, stept, fold_convert (stept, l), t); if (POINTER_TYPE_P (TREE_TYPE (x))) diff --git a/gcc/ree.c b/gcc/ree.c index fcde9a0f399..0d5090bc290 100644 --- a/gcc/ree.c +++ b/gcc/ree.c @@ -507,6 +507,8 @@ struct ATTRIBUTE_PACKED ext_modified /* Kind of modification of the insn. */ ENUM_BITFIELD(ext_modified_kind) kind : 2; + unsigned int do_not_reextend : 1; + /* True if the insn is scheduled to be deleted. */ unsigned int deleted : 1; }; @@ -712,8 +714,10 @@ combine_reaching_defs (ext_cand *cand, const_rtx set_pat, ext_state *state) register than the source operand, then additional restrictions are needed. Note we have to handle cases where we have nested extensions in the source operand. */ - if (REGNO (SET_DEST (PATTERN (cand->insn))) - != REGNO (get_extended_src_reg (SET_SRC (PATTERN (cand->insn))))) + bool copy_needed + = (REGNO (SET_DEST (PATTERN (cand->insn))) + != REGNO (get_extended_src_reg (SET_SRC (PATTERN (cand->insn))))); + if (copy_needed) { /* In theory we could handle more than one reaching def, it just makes the code to update the insn stream more complex. */ @@ -722,7 +726,7 @@ combine_reaching_defs (ext_cand *cand, const_rtx set_pat, ext_state *state) /* We require the candidate not already be modified. It may, for example have been changed from a (sign_extend (reg)) - into (zero_extend (sign_extend (reg)). + into (zero_extend (sign_extend (reg))). Handling that case shouldn't be terribly difficult, but the code here and the code to emit copies would need auditing. Until @@ -777,6 +781,34 @@ combine_reaching_defs (ext_cand *cand, const_rtx set_pat, ext_state *state) || reg_set_between_p (SET_DEST (PATTERN (cand->insn)), def_insn, cand->insn)) return false; + + /* We must be able to copy between the two registers. Generate, + recognize and verify constraints of the copy. Also fail if this + generated more than one insn. + + This generates garbage since we throw away the insn when we're + done, only to recreate it later if this test was successful. + + Make sure to get the mode from the extension (cand->insn). This + is different than in the code to emit the copy as we have not + modified the defining insn yet. */ + start_sequence (); + rtx pat = PATTERN (cand->insn); + rtx new_dst = gen_rtx_REG (GET_MODE (SET_DEST (pat)), + REGNO (XEXP (SET_SRC (pat), 0))); + rtx new_src = gen_rtx_REG (GET_MODE (SET_DEST (pat)), + REGNO (SET_DEST (pat))); + emit_move_insn (new_dst, new_src); + + rtx insn = get_insns(); + end_sequence (); + if (NEXT_INSN (insn)) + return false; + if (recog_memoized (insn) == -1) + return false; + extract_insn (insn); + if (!constrain_operands (1)) + return false; } @@ -843,11 +875,15 @@ combine_reaching_defs (ext_cand *cand, const_rtx set_pat, ext_state *state) fprintf (dump_file, "All merges were successful.\n"); FOR_EACH_VEC_ELT (state->modified_list, i, def_insn) - if (state->modified[INSN_UID (def_insn)].kind == EXT_MODIFIED_NONE) - state->modified[INSN_UID (def_insn)].kind - = (cand->code == ZERO_EXTEND - ? EXT_MODIFIED_ZEXT : EXT_MODIFIED_SEXT); + { + ext_modified *modified = &state->modified[INSN_UID (def_insn)]; + if (modified->kind == EXT_MODIFIED_NONE) + modified->kind = (cand->code == ZERO_EXTEND ? EXT_MODIFIED_ZEXT + : EXT_MODIFIED_SEXT); + if (copy_needed) + modified->do_not_reextend = 1; + } return true; } else diff --git a/gcc/sel-sched-ir.c b/gcc/sel-sched-ir.c index f5a4ee03543..e1408b488a6 100644 --- a/gcc/sel-sched-ir.c +++ b/gcc/sel-sched-ir.c @@ -162,7 +162,7 @@ static void create_initial_data_sets (basic_block); static void free_av_set (basic_block); static void invalidate_av_set (basic_block); static void extend_insn_data (void); -static void sel_init_new_insn (insn_t, int); +static void sel_init_new_insn (insn_t, int, int = -1); static void finish_insns (void); /* Various list functions. */ @@ -4007,9 +4007,10 @@ get_seqno_by_succs (rtx insn) return seqno; } -/* Compute seqno for INSN by its preds or succs. */ +/* Compute seqno for INSN by its preds or succs. Use OLD_SEQNO to compute + seqno in corner cases. */ static int -get_seqno_for_a_jump (insn_t insn) +get_seqno_for_a_jump (insn_t insn, int old_seqno) { int seqno; @@ -4065,8 +4066,16 @@ get_seqno_for_a_jump (insn_t insn) if (seqno < 0) seqno = get_seqno_by_succs (insn); - gcc_assert (seqno >= 0); + if (seqno < 0) + { + /* The only case where this could be here legally is that the only + unscheduled insn was a conditional jump that got removed and turned + into this unconditional one. Initialize from the old seqno + of that jump passed down to here. */ + seqno = old_seqno; + } + gcc_assert (seqno >= 0); return seqno; } @@ -4246,22 +4255,24 @@ init_insn_data (insn_t insn) } /* This is used to initialize spurious jumps generated by - sel_redirect_edge (). */ + sel_redirect_edge (). OLD_SEQNO is used for initializing seqnos + in corner cases within get_seqno_for_a_jump. */ static void -init_simplejump_data (insn_t insn) +init_simplejump_data (insn_t insn, int old_seqno) { init_expr (INSN_EXPR (insn), vinsn_create (insn, false), 0, REG_BR_PROB_BASE, 0, 0, 0, 0, 0, 0, vNULL, true, false, false, false, true); - INSN_SEQNO (insn) = get_seqno_for_a_jump (insn); + INSN_SEQNO (insn) = get_seqno_for_a_jump (insn, old_seqno); init_first_time_insn_data (insn); } /* Perform deferred initialization of insns. This is used to process - a new jump that may be created by redirect_edge. */ -void -sel_init_new_insn (insn_t insn, int flags) + a new jump that may be created by redirect_edge. OLD_SEQNO is used + for initializing simplejumps in init_simplejump_data. */ +static void +sel_init_new_insn (insn_t insn, int flags, int old_seqno) { /* We create data structures for bb when the first insn is emitted in it. */ if (INSN_P (insn) @@ -4288,7 +4299,7 @@ sel_init_new_insn (insn_t insn, int flags) if (flags & INSN_INIT_TODO_SIMPLEJUMP) { extend_insn_data (); - init_simplejump_data (insn); + init_simplejump_data (insn, old_seqno); } gcc_assert (CONTAINING_RGN (BLOCK_NUM (insn)) @@ -5575,14 +5586,14 @@ sel_merge_blocks (basic_block a, basic_block b) } /* A wrapper for redirect_edge_and_branch_force, which also initializes - data structures for possibly created bb and insns. Returns the newly - added bb or NULL, when a bb was not needed. */ + data structures for possibly created bb and insns. */ void sel_redirect_edge_and_branch_force (edge e, basic_block to) { basic_block jump_bb, src, orig_dest = e->dest; int prev_max_uid; rtx jump; + int old_seqno = -1; /* This function is now used only for bookkeeping code creation, where we'll never get the single pred of orig_dest block and thus will not @@ -5591,8 +5602,13 @@ sel_redirect_edge_and_branch_force (edge e, basic_block to) && !single_pred_p (orig_dest)); src = e->src; prev_max_uid = get_max_uid (); - jump_bb = redirect_edge_and_branch_force (e, to); + /* Compute and pass old_seqno down to sel_init_new_insn only for the case + when the conditional jump being redirected may become unconditional. */ + if (any_condjump_p (BB_END (src)) + && INSN_SEQNO (BB_END (src)) >= 0) + old_seqno = INSN_SEQNO (BB_END (src)); + jump_bb = redirect_edge_and_branch_force (e, to); if (jump_bb != NULL) sel_add_bb (jump_bb); @@ -5604,7 +5620,8 @@ sel_redirect_edge_and_branch_force (edge e, basic_block to) jump = find_new_jump (src, jump_bb, prev_max_uid); if (jump) - sel_init_new_insn (jump, INSN_INIT_TODO_LUID | INSN_INIT_TODO_SIMPLEJUMP); + sel_init_new_insn (jump, INSN_INIT_TODO_LUID | INSN_INIT_TODO_SIMPLEJUMP, + old_seqno); set_immediate_dominator (CDI_DOMINATORS, to, recompute_dominator (CDI_DOMINATORS, to)); set_immediate_dominator (CDI_DOMINATORS, orig_dest, @@ -5623,6 +5640,7 @@ sel_redirect_edge_and_branch (edge e, basic_block to) edge redirected; bool recompute_toporder_p = false; bool maybe_unreachable = single_pred_p (orig_dest); + int old_seqno = -1; latch_edge_p = (pipelining_p && current_loop_nest @@ -5631,6 +5649,12 @@ sel_redirect_edge_and_branch (edge e, basic_block to) src = e->src; prev_max_uid = get_max_uid (); + /* Compute and pass old_seqno down to sel_init_new_insn only for the case + when the conditional jump being redirected may become unconditional. */ + if (any_condjump_p (BB_END (src)) + && INSN_SEQNO (BB_END (src)) >= 0) + old_seqno = INSN_SEQNO (BB_END (src)); + redirected = redirect_edge_and_branch (e, to); gcc_assert (redirected && !last_added_blocks.exists ()); @@ -5651,7 +5675,7 @@ sel_redirect_edge_and_branch (edge e, basic_block to) jump = find_new_jump (src, NULL, prev_max_uid); if (jump) - sel_init_new_insn (jump, INSN_INIT_TODO_LUID | INSN_INIT_TODO_SIMPLEJUMP); + sel_init_new_insn (jump, INSN_INIT_TODO_LUID | INSN_INIT_TODO_SIMPLEJUMP, old_seqno); /* Only update dominator info when we don't have unreachable blocks. Otherwise we'll update in maybe_tidy_empty_bb. */ diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index a0504febd6e..694e4a21d9a 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,163 @@ +2014-06-23 Alan Modra <amodra@gmail.com> + + * gcc.dg/pr61583.c: New. + +2014-06-20 Martin Jambor <mjambor@suse.cz> + + PR ipa/61540 + * g++.dg/ipa/pr61540.C: New test. + +2014-06-17 Yufeng Zhang <yufeng.zhang@arm.com> + + PR target/61483 + * gcc.target/aarch64/aapcs64/type-def.h (struct hfa_fx2_t): New type. + * gcc.target/aarch64/aapcs64/va_arg-13.c: New test. + * gcc.target/aarch64/aapcs64/va_arg-14.c: Ditto. + * gcc.target/aarch64/aapcs64/va_arg-15.c: Ditto. + +2014-06-17 Richard Biener <rguenther@suse.de> + + PR lto/61012 + * gcc.dg/lto/pr61526_0.c: New testcase. + * gcc.dg/lto/pr61526_1.c: Likewise. + +2014-06-17 Uros Bizjak <ubizjak@gmail.com> + + Backport from mainline + 2014-06-06 Uros Bizjak <ubizjak@gmail.com> + + PR target/61423 + * gcc.target/i386/pr61423.c: New test. + +2014-06-15 Francois-Xavier Coudert <fxcoudert@gcc.gnu.org> + + Backport from trunk. + PR fortran/45187 + * gfortran.dg/cray_pointers_10.f90: New file. + +2014-06-13 Peter Bergner <bergner@vnet.ibm.com> + + Backport from mainline + + 2014-06-13 Peter Bergner <bergner@vnet.ibm.com> + PR target/61415 + * lib/target-supports.exp (check_effective_target_longdouble128): New. + * gcc.target/powerpc/pack02.c: Use it. + * gcc.target/powerpc/tfmode_off.c: Likewise. + +2014-06-13 Jeff Law <law@redhat.com> + + Backports from mainline: + + 2014-06-13 Ilya Enkovich <ilya.enkovich@intel.com> + + PR rtl-optimization/61094 + PR rtl-optimization/61446 + * gcc.target/i386/pr61446.c : New. + + 2014-06-02 Jeff Law <law@redhat.com> + + PR rtl-optimization/61094 + * g++.dg/pr61094: New test. + +2014-06-12 Jakub Jelinek <jakub@redhat.com> + + PR middle-end/61486 + * c-c++-common/gomp/pr61486-1.c: New test. + * c-c++-common/gomp/pr61486-2.c: New test. + +2014-06-12 Jeff Law <law@redhat.com> + + Backports from mainline: + 2014-06-05 Jeff Law <law@redhat.com> + + PR tree-optimization/61289 + * g++.dg/pr61289.C: New test. + * g++.dg/pr61289-2.C: New test. + +2014-06-12 Georg-Johann Lay <avr@gjlay.de> + + Backport from 2014-06-12 trunk r211491 + + PR target/61443 + * gcc.target/avr/torture/pr61443.c: New test. + +2014-06-11 Richard Biener <rguenther@suse.de> + + PR tree-optimization/61452 + * gcc.dg/torture/pr61452.c: New testcase. + +2014-06-11 Richard Biener <rguenther@suse.de> + + PR middle-end/61456 + * g++.dg/opt/pr61456.C: New testcase. + +2014-06-09 Paul Thomas <pault@gcc.gnu.org> + + Backport from trunk. + PR fortran/61406 + * gfortran.dg/associate_17.f90 : New test + +2014-06-07 Jerry DeLisle <jvdelisle@gcc.gnu> + + Backport from trunk. + PR libfortran/61173 + * gfortran.dg/arrayio_14.f90: New test. + +2014-06-07 Eric Botcazou <ebotcazou@adacore.com> + + * gnat.dg/opt38.adb: New test. + * gnat.dg/opt38_pkg.ad[sb]: New helper. + +2014-06-04 Richard Biener <rguenther@suse.de> + + PR tree-optimization/61383 + * gcc.dg/torture/pr61383-1.c: New testcase. + +2014-06-04 Igor Zamyatin <igor.zamyatin@intel.com> + + PR c/58942 + * c-c++-common/cilk-plus/AN/pr58942.c: Check for correct handling of + the case with a pointer. + +2014-06-04 Marek Polacek <polacek@redhat.com> + + Backport from mainline + 2014-05-08 Marek Polacek <polacek@redhat.com> + + PR c/61053 + * gcc.dg/pr61053.c: New test. + +2014-06-03 Martin Jambor <mjambor@suse.cz> + + PR ipa/61160 + * g++.dg/ipa/pr61160-1.C: New test. + +2014-06-03 Andrey Belevantsev <abel@ispras.ru> + + Backport from mainline + 2014-05-14 Andrey Belevantsev <abel@ispras.ru> + + PR rtl-optimization/60866 + * gcc.dg/pr60866.c: New test. + +2014-06-03 Andrey Belevantsev <abel@ispras.ru> + + Backport from mainline + 2014-05-14 Andrey Belevantsev <abel@ispras.ru> + + PR rtl-optimization/60901 + * gcc.target/i386/pr60901.c: New test. + +2014-06-01 Uros Bizjak <ubizjak@gmail.com> + + * g++.dg/pr60969.C (dg-do compile): Change ilp32 target to ia32. + +2014-05-29 Vladimir Makarov <vmakarov@redhat.com> + + PR rtl-optimization/61325 + * gcc.target/aarch64/pr61325.c: New. + 2014-05-29 Thomas Koenig <tkoenig@gcc.gnu.org> PR fortran/60834 diff --git a/gcc/testsuite/c-c++-common/cilk-plus/AN/pr58942.c b/gcc/testsuite/c-c++-common/cilk-plus/AN/pr58942.c new file mode 100644 index 00000000000..87903af3c86 --- /dev/null +++ b/gcc/testsuite/c-c++-common/cilk-plus/AN/pr58942.c @@ -0,0 +1,8 @@ +/* PR c/58942 */ +/* { dg-do compile } */ +/* { dg-options "-fcilkplus" } */ + +int foo (int*p, int i) +{ + return __sec_reduce_max_ind(p[1:i]); +} diff --git a/gcc/testsuite/c-c++-common/gomp/pr61486-1.c b/gcc/testsuite/c-c++-common/gomp/pr61486-1.c new file mode 100644 index 00000000000..9ada58c8ccf --- /dev/null +++ b/gcc/testsuite/c-c++-common/gomp/pr61486-1.c @@ -0,0 +1,13 @@ +/* PR middle-end/61486 */ +/* { dg-do compile } */ +/* { dg-options "-fopenmp" } */ + +int +foo (int *a) +{ + int i, j = 0; + #pragma omp target teams distribute simd linear(i, j) map(a[:10]) + for (i = 0; i < 10; i++) + a[i] = j++; + return i + j; +} diff --git a/gcc/testsuite/c-c++-common/gomp/pr61486-2.c b/gcc/testsuite/c-c++-common/gomp/pr61486-2.c new file mode 100644 index 00000000000..729438101e2 --- /dev/null +++ b/gcc/testsuite/c-c++-common/gomp/pr61486-2.c @@ -0,0 +1,458 @@ +/* PR middle-end/61486 */ +/* { dg-do compile } */ +/* { dg-options "-fopenmp" } */ + +#pragma omp declare target +void dosomething (int *a, int n, int m); +#pragma omp end declare target + +void +test (int n, int o, int p, int q, int r, int s, int *pp) +{ + int a[o], i, j; + #pragma omp target data device (n + 1) if (n != 6) map (tofrom: n, r) + { + #pragma omp target device (n + 1) if (n != 6) map (from: n) map (alloc: a[2:o-2]) + dosomething (a, n, 0); + #pragma omp target teams device (n + 1) num_teams (n + 4) thread_limit (n * 2) \ + if (n != 6)map (from: n) map (alloc: a[2:o-2]) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp target teams distribute device (n + 1) num_teams (n + 4) collapse (2) \ + if (n != 6)map (from: n) map (alloc: a[2:o-2]) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp target teams distribute device (n + 1) num_teams (n + 4) \ + if (n != 6)map (from: n) map (alloc: a[2:o-2]) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp target teams distribute parallel for device (n + 1) num_teams (n + 4) \ + if (n != 6)map (from: n) map (alloc: a[2:o-2]) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) collapse (2) \ + num_threads (n + 4) proc_bind (spread) lastprivate (s) \ + ordered schedule (static, 8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + #pragma omp ordered + p = q; + s = i * 10 + j; + } + #pragma omp target teams distribute parallel for device (n + 1) num_teams (n + 4) \ + if (n != 6)map (from: n) map (alloc: a[2:o-2]) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) num_threads (n + 4) \ + proc_bind (master) lastprivate (s) ordered schedule (static, 8) + for (i = 0; i < 10; i++) + { + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp ordered + p = q; + s = i * 10; + } + #pragma omp target teams distribute parallel for simd device (n + 1) \ + if (n != 6)map (from: n) map (alloc: a[2:o-2]) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) collapse (2) \ + num_threads (n + 4) proc_bind (spread) lastprivate (s) \ + schedule (static, 8) num_teams (n + 4) safelen(8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + a[2+i*10+j] = p + q; + s = i * 10 + j; + } + #pragma omp target teams distribute parallel for simd device (n + 1) \ + if (n != 6)map (from: n) map (alloc: a[2:o-2]) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) num_threads (n + 4) \ + proc_bind (master) lastprivate (s) schedule (static, 8) \ + num_teams (n + 4) safelen(16) linear(i:1) aligned (pp:4) + for (i = 0; i < 10; i++) + { + r = r + 1; + p = q; + a[2+i] = p + q; + s = i * 10; + } + #pragma omp target teams distribute simd device (n + 1) \ + if (n != 6)map (from: n) map (alloc: a[2:o-2]) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) collapse (2) \ + lastprivate (s) num_teams (n + 4) safelen(8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + a[2+i*10+j] = p + q; + s = i * 10 + j; + } + #pragma omp target teams distribute simd device (n + 1) \ + if (n != 6)map (from: n) map (alloc: a[2:o-2]) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) lastprivate (s) \ + num_teams (n + 4) safelen(16) linear(i:1) aligned (pp:4) + for (i = 0; i < 10; i++) + { + r = r + 1; + p = q; + a[2+i] = p + q; + s = i * 10; + } + #pragma omp target device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) + #pragma omp teams num_teams (n + 4) thread_limit (n * 2) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp target device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) + #pragma omp teams distribute num_teams (n + 4) collapse (2) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp target device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) + #pragma omp teams distribute num_teams (n + 4) default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp target device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) + #pragma omp teams distribute parallel for num_teams (n + 4) if (n != 6) \ + default(shared) private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) collapse (2) \ + num_threads (n + 4) proc_bind (spread) lastprivate (s) \ + ordered schedule (static, 8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + #pragma omp ordered + p = q; + s = i * 10 + j; + } + #pragma omp target device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) + #pragma omp teams distribute parallel for num_teams (n + 4) if (n != 6) \ + default(shared) private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) num_threads (n + 4) \ + proc_bind (master) lastprivate (s) ordered schedule (static, 8) + for (i = 0; i < 10; i++) + { + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp ordered + p = q; + s = i * 10; + } + #pragma omp target device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) + #pragma omp teams distribute parallel for simd if (n != 6)default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) collapse (2) \ + num_threads (n + 4) proc_bind (spread) lastprivate (s) \ + schedule (static, 8) num_teams (n + 4) safelen(8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + a[2+i*10+j] = p + q; + s = i * 10 + j; + } + #pragma omp target device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) + #pragma omp teams distribute parallel for simd if (n != 6)default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) num_threads (n + 4) \ + proc_bind (master) lastprivate (s) schedule (static, 8) \ + num_teams (n + 4) safelen(16) linear(i:1) aligned (pp:4) + for (i = 0; i < 10; i++) + { + r = r + 1; + p = q; + a[2+i] = p + q; + s = i * 10; + } + #pragma omp target device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) + #pragma omp teams distribute simd default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) collapse (2) \ + lastprivate (s) num_teams (n + 4) safelen(8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + a[2+i*10+j] = p + q; + s = i * 10 + j; + } + #pragma omp target device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) + #pragma omp teams distribute simd default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + thread_limit (n * 2) dist_schedule (static, 4) lastprivate (s) \ + num_teams (n + 4) safelen(16) linear(i:1) aligned (pp:4) + for (i = 0; i < 10; i++) + { + r = r + 1; + p = q; + a[2+i] = p + q; + s = i * 10; + } + #pragma omp target teams device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) \ + num_teams (n + 4) thread_limit (n * 2)default(shared) shared(n) \ + private (p) reduction (+: r) + #pragma omp distribute collapse (2) dist_schedule (static, 4) firstprivate (q) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp target teams device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) \ + num_teams (n + 4) thread_limit (n * 2) shared(n) private(p) reduction (+ : r) \ + default(shared) + #pragma omp distribute dist_schedule (static, 4) firstprivate (q) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp target teams device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) \ + num_teams (n + 4) thread_limit (n * 2) + #pragma omp distribute parallel for if (n != 6) \ + default(shared) private (p) firstprivate (q) shared (n) reduction (+: r) \ + collapse (2) dist_schedule (static, 4) \ + num_threads (n + 4) proc_bind (spread) lastprivate (s) \ + ordered schedule (static, 8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + #pragma omp ordered + p = q; + s = i * 10 + j; + } + #pragma omp target teams device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) \ + num_teams (n + 4) thread_limit (n * 2) + #pragma omp distribute parallel for if (n != 6) \ + default(shared) private (p) firstprivate (q) shared (n) reduction (+: r) \ + num_threads (n + 4) dist_schedule (static, 4) \ + proc_bind (master) lastprivate (s) ordered schedule (static, 8) + for (i = 0; i < 10; i++) + { + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp ordered + p = q; + s = i * 10; + } + #pragma omp target teams device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) \ + num_teams (n + 4) thread_limit (n * 2) + #pragma omp distribute parallel for simd if (n != 6)default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + collapse (2) dist_schedule (static, 4) \ + num_threads (n + 4) proc_bind (spread) lastprivate (s) \ + schedule (static, 8) safelen(8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + a[2+i*10+j] = p + q; + s = i * 10 + j; + } + #pragma omp target teams device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) \ + num_teams (n + 4) thread_limit (n * 2) + #pragma omp distribute parallel for simd if (n != 6)default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + num_threads (n + 4) dist_schedule (static, 4) \ + proc_bind (master) lastprivate (s) schedule (static, 8) \ + safelen(16) linear(i:1) aligned (pp:4) + for (i = 0; i < 10; i++) + { + r = r + 1; + p = q; + a[2+i] = p + q; + s = i * 10; + } + #pragma omp target teams device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) \ + num_teams (n + 4) thread_limit (n * 2) default(shared) shared(n) private(p) \ + reduction(+:r) + #pragma omp distribute simd private (p) firstprivate (q) reduction (+: r) \ + collapse (2) dist_schedule (static, 4) lastprivate (s) safelen(8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + a[2+i*10+j] = p + q; + s = i * 10 + j; + } + #pragma omp target teams device (n + 1) if (n != 6)map(from:n) map(alloc:a[2:o-2]) \ + num_teams (n + 4) thread_limit (n * 2) default(shared) shared(n) private(p) \ + reduction(+:r) + #pragma omp distribute simd private (p) firstprivate (q) reduction (+: r) \ + lastprivate (s) dist_schedule (static, 4) safelen(16) linear(i:1) aligned (pp:4) + for (i = 0; i < 10; i++) + { + r = r + 1; + p = q; + a[2+i] = p + q; + s = i * 10; + } + } +} + +int q, i, j; + +void +test2 (int n, int o, int p, int r, int s, int *pp) +{ + int a[o]; + #pragma omp distribute collapse (2) dist_schedule (static, 4) firstprivate (q) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp distribute dist_schedule (static, 4) firstprivate (q) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp distribute parallel for if (n != 6) \ + default(shared) private (p) firstprivate (q) shared (n) reduction (+: r) \ + collapse (2) dist_schedule (static, 4) \ + num_threads (n + 4) proc_bind (spread) lastprivate (s) \ + ordered schedule (static, 8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + #pragma omp ordered + p = q; + s = i * 10 + j; + } + #pragma omp distribute parallel for if (n != 6) \ + default(shared) private (p) firstprivate (q) shared (n) reduction (+: r) \ + num_threads (n + 4) dist_schedule (static, 4) \ + proc_bind (master) lastprivate (s) ordered schedule (static, 8) + for (i = 0; i < 10; i++) + { + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + dosomething (a, n, p + q); + } + #pragma omp ordered + p = q; + s = i * 10; + } + #pragma omp distribute parallel for simd if (n != 6)default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + collapse (2) dist_schedule (static, 4) \ + num_threads (n + 4) proc_bind (spread) lastprivate (s) \ + schedule (static, 8) safelen(8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + a[2+i*10+j] = p + q; + s = i * 10 + j; + } + #pragma omp distribute parallel for simd if (n != 6)default(shared) \ + private (p) firstprivate (q) shared (n) reduction (+: r) \ + num_threads (n + 4) dist_schedule (static, 4) \ + proc_bind (master) lastprivate (s) schedule (static, 8) \ + safelen(16) linear(i:1) aligned (pp:4) + for (i = 0; i < 10; i++) + { + r = r + 1; + p = q; + a[2+i] = p + q; + s = i * 10; + } + #pragma omp distribute simd private (p) firstprivate (q) reduction (+: r) \ + collapse (2) dist_schedule (static, 4) lastprivate (s) safelen(8) + for (i = 0; i < 10; i++) + for (j = 0; j < 10; j++) + { + r = r + 1; + p = q; + a[2+i*10+j] = p + q; + s = i * 10 + j; + } + #pragma omp distribute simd private (p) firstprivate (q) reduction (+: r) \ + lastprivate (s) dist_schedule (static, 4) safelen(16) linear(i:1) aligned (pp:4) + for (i = 0; i < 10; i++) + { + r = r + 1; + p = q; + a[2+i] = p + q; + s = i * 10; + } +} diff --git a/gcc/testsuite/g++.dg/cpp0x/constexpr-template7.C b/gcc/testsuite/g++.dg/cpp0x/constexpr-template7.C new file mode 100644 index 00000000000..e835dbf4db7 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/constexpr-template7.C @@ -0,0 +1,32 @@ +// PR c++/61556 +// { dg-do compile { target c++11 } } + +class ValueType { +public: + constexpr operator int() const {return m_ID;}; + constexpr ValueType(const int v) + : m_ID(v) {} +private: + int m_ID; +}; + +class ValueTypeEnum { +public: + static constexpr ValueType doubleval = ValueType(1); +}; + +template <int format> +class ValueTypeInfo { +}; + +template <typename Format> +class FillFunctor { +public: + FillFunctor() { + ValueTypeInfo<ValueTypeEnum::doubleval> v; + } +}; + +int main() { + ValueTypeInfo<ValueTypeEnum::doubleval> v; +} diff --git a/gcc/testsuite/g++.dg/cpp0x/ref-qual15.C b/gcc/testsuite/g++.dg/cpp0x/ref-qual15.C new file mode 100644 index 00000000000..ca333c2e287 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/ref-qual15.C @@ -0,0 +1,13 @@ +// PR c++/59296 +// { dg-do compile { target c++11 } } + +struct Type +{ + void get() const& { } + void get() const&& { } +}; + +int main() +{ + Type{}.get(); +} diff --git a/gcc/testsuite/g++.dg/cpp0x/variadic158.C b/gcc/testsuite/g++.dg/cpp0x/variadic158.C new file mode 100644 index 00000000000..cc5c24ddc67 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/variadic158.C @@ -0,0 +1,24 @@ +// PR c++/61134 +// { dg-do compile { target c++11 } } + +struct Base { }; + +template <typename> +struct Fixed { + typedef const char* name; +}; + +template <typename VT, typename... Fields> +void New(const char* name, + typename Fixed<Fields>::name... field_names); + +template <typename VT, typename... Fields> +void CreateMetric(const char* name, + typename Fixed<Fields>::name... field_names, + const Base&) { } + + +void Fn() +{ + CreateMetric<int, const char*>("abcd", "def", Base()); +} diff --git a/gcc/testsuite/g++.dg/cpp0x/variadic159.C b/gcc/testsuite/g++.dg/cpp0x/variadic159.C new file mode 100644 index 00000000000..2b14d3005f0 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/variadic159.C @@ -0,0 +1,14 @@ +// PR c++/61507 +// { dg-do compile { target c++11 } } + +struct A { + void foo(const int &); + void foo(float); +}; + +template <typename... Args> +void bar(void (A::*memfun)(Args...), Args... args); + +void go(const int& i) { + bar<const int &>(&A::foo, i); +} diff --git a/gcc/testsuite/g++.dg/debug/dwarf2/imported-decl-2.C b/gcc/testsuite/g++.dg/debug/dwarf2/imported-decl-2.C new file mode 100644 index 00000000000..ce01f72382a --- /dev/null +++ b/gcc/testsuite/g++.dg/debug/dwarf2/imported-decl-2.C @@ -0,0 +1,32 @@ +// { dg-do compile } +// { dg-options "-gdwarf-2 -dA -O0 -fno-merge-debug-strings" } + +class AAAA +{ + public: + int method (void); + int a; +}; + +int +AAAA::method (void) +{ + return a; +} + +class BBBB : public AAAA +{ + public: + using AAAA::method; + + int method (int b); +}; + +int +BBBB::method (int b) +{ + return a + b; +} + +// { dg-final { scan-assembler-not "ascii \"BBBB\\\\0\".*ascii \"AAAA\\\\0\".*DW_TAG_imported_declaration" } } +// { dg-final { scan-assembler-times "ascii \"AAAA\\\\0\".*ascii \"BBBB\\\\0\".*DIE .0x\[0-9a-f\]*. DW_TAG_imported_declaration" 1 } } diff --git a/gcc/testsuite/g++.dg/ipa/pr61160-1.C b/gcc/testsuite/g++.dg/ipa/pr61160-1.C new file mode 100644 index 00000000000..a0fbb5f42bd --- /dev/null +++ b/gcc/testsuite/g++.dg/ipa/pr61160-1.C @@ -0,0 +1,31 @@ +/* { dg-do compile } */ +/* { dg-options "-O3" } */ + +struct CBase { + virtual void BaseFunc () {} +}; + +struct MMixin { + virtual void * MixinFunc (int, void *) = 0; +}; + +struct CExample: CBase, public MMixin +{ + void *MixinFunc (int arg, void *arg2) + { + if (arg != 1 || arg2) + return 0; + return this; + } +}; + +void *test (MMixin & anExample) +{ + return anExample.MixinFunc (1, 0); +} + +int main () +{ + CExample c; + return (test (c) != &c); +} diff --git a/gcc/testsuite/g++.dg/ipa/pr61540.C b/gcc/testsuite/g++.dg/ipa/pr61540.C new file mode 100644 index 00000000000..d298964bf22 --- /dev/null +++ b/gcc/testsuite/g++.dg/ipa/pr61540.C @@ -0,0 +1,41 @@ +/* { dg-do compile } */ +/* { dg-options "-O3 -fno-early-inlining -fdump-ipa-cp" } */ + +struct data { + data(int) {} +}; + +struct top { + virtual int topf() {} +}; + +struct intermediate: top { + int topf() /* override */ { return 0; } +}; + +struct child1: top { + void childf() + { + data d(topf()); + } +}; + +struct child2: intermediate {}; + +void test(top& t) +{ + child1& c = static_cast<child1&>(t); + c.childf(); + child2 d; + test(d); +} + +int main (int argc, char **argv) +{ + child1 c; + test (c); + return 0; +} + +/* { dg-final { scan-ipa-dump "Type inconsident devirtualization" "cp" } } */ +/* { dg-final { cleanup-ipa-dump "cp" } } */ diff --git a/gcc/testsuite/g++.dg/opt/pr61456.C b/gcc/testsuite/g++.dg/opt/pr61456.C new file mode 100644 index 00000000000..14a118b5720 --- /dev/null +++ b/gcc/testsuite/g++.dg/opt/pr61456.C @@ -0,0 +1,26 @@ +// { dg-do compile } +// { dg-options "-O2 -std=c++11 -Werror=uninitialized" } + +int rand (); + +class Funcs +{ +public: + int *f1 (); + int *f2 (); +}; +typedef decltype (&Funcs::f1) pfunc; + +static int Set (Funcs * f, const pfunc & fp) +{ + (f->*fp) (); +} + +void +Foo () +{ + pfunc fp = &Funcs::f1; + if (rand ()) + fp = &Funcs::f2; + Set (0, fp); +} diff --git a/gcc/testsuite/g++.dg/opt/typeinfo1.C b/gcc/testsuite/g++.dg/opt/typeinfo1.C new file mode 100644 index 00000000000..efac4cbd1e3 --- /dev/null +++ b/gcc/testsuite/g++.dg/opt/typeinfo1.C @@ -0,0 +1,27 @@ +// PR c++/61020 +// { dg-options "-O2" } +// { dg-do run } + +#include <typeinfo> + +struct Base { + virtual ~Base() { } +}; + +struct Derived : public Base { +}; + +int compare(const Base& base) +{ + return typeid(base) == typeid(typeid(Derived)); +} + +int main() +{ + Base base; + Derived derived; + + if (compare(base)) return 1; + if (compare(derived)) return 2; + return 0; +} diff --git a/gcc/testsuite/g++.dg/pr60969.C b/gcc/testsuite/g++.dg/pr60969.C index bea0801d461..4012e2ce72f 100644 --- a/gcc/testsuite/g++.dg/pr60969.C +++ b/gcc/testsuite/g++.dg/pr60969.C @@ -1,4 +1,4 @@ -/* { dg-do compile { target { { i?86-*-* x86_64-*-* } && ilp32 } } } */ +/* { dg-do compile { target { { i?86-*-* x86_64-*-* } && ia32 } } } */ /* { dg-options "-O2 -ftree-vectorize -march=pentium4 -mfpmath=387" } */ struct A diff --git a/gcc/testsuite/g++.dg/pr61094.C b/gcc/testsuite/g++.dg/pr61094.C new file mode 100644 index 00000000000..35adc256c21 --- /dev/null +++ b/gcc/testsuite/g++.dg/pr61094.C @@ -0,0 +1,31 @@ +/* { dg-do compile } */ +/* { dg-options "-O3" } */ + +template <typename> struct A { + unsigned _width, _height, _depth, _spectrum; + template <typename t> A(t p1) { + int a = p1.size(); + if (a) { + _width = p1._width; + _depth = _height = _spectrum = p1._spectrum; + } + } + long size() { return (long)_width * _height * _depth * _spectrum; } +}; + +int d; +void fn1(void *); +A<int> *fn2(); +void fn3() { + int b; + for (;;) { + A<char> c(*fn2()); + fn1(&c); + if (d || !b) + throw; + } +} + + + + diff --git a/gcc/testsuite/g++.dg/pr61289-2.c b/gcc/testsuite/g++.dg/pr61289-2.c new file mode 100644 index 00000000000..4cc3ebe468d --- /dev/null +++ b/gcc/testsuite/g++.dg/pr61289-2.c @@ -0,0 +1,62 @@ +/* { dg-do run } */ +/* { dg-options "-O2 -fno-exceptions" } */ +struct S +{ + inline int fn1 () const { return s; } + __attribute__ ((noinline, noclone)) S *fn2 (int); + __attribute__ ((noinline, noclone)) void fn3 (); + __attribute__ ((noinline, noclone)) static S *fn4 (int); + S (int i) : s (i) {} + int s; +}; + +int a = 0; +S *b = 0; + +S * +S::fn2 (int i) +{ + a++; + if (a == 1) + return b; + if (a > 3) + __builtin_abort (); + b = this; + return new S (i + s); +} + +S * +S::fn4 (int i) +{ + b = new S (i); + return b; +} + +void +S::fn3 () +{ + delete this; +} + +void +foo () +{ + S *c = S::fn4 (20); + for (int i = 0; i < 2;) + { + S *d = c->fn2 (c->fn1 () + 10); + if (c != d) +{ + c->fn3 (); + c = d; + ++i; +} + } + c->fn3 (); +} + +int +main () +{ + foo (); +} diff --git a/gcc/testsuite/g++.dg/pr61289.C b/gcc/testsuite/g++.dg/pr61289.C new file mode 100644 index 00000000000..ea7ccea304d --- /dev/null +++ b/gcc/testsuite/g++.dg/pr61289.C @@ -0,0 +1,63 @@ +/* { dg-do run } */ +/* { dg-options "-O2 -fno-exceptions" } */ + +struct S +{ + inline int fn1 () const { return s; } + __attribute__ ((noinline, noclone)) S *fn2 (int); + __attribute__ ((noinline, noclone)) void fn3 (); + __attribute__ ((noinline, noclone)) static S *fn4 (int); + S (int i) : s (i) {} + int s; +}; + +int a = 0; +S *b = 0; + +S * +S::fn2 (int i) +{ + a++; + if (a == 1) + return b; + if (a > 3) + __builtin_abort (); + b = this; + return new S (i + s); +} + +S * +S::fn4 (int i) +{ + b = new S (i); + return b; +} + +void +S::fn3 () +{ + delete this; +} + +void +foo () +{ + S *c = S::fn4 (20); + for (int i = 0; i < 2;) + { + S *d = c->fn2 (c->fn1 () + 10); + if (d != c) +{ + c->fn3 (); + c = d; + ++i; +} + } + c->fn3 (); +} + +int +main () +{ + foo (); +} diff --git a/gcc/testsuite/g++.dg/template/local-fn1.C b/gcc/testsuite/g++.dg/template/local-fn1.C new file mode 100644 index 00000000000..88acd17d741 --- /dev/null +++ b/gcc/testsuite/g++.dg/template/local-fn1.C @@ -0,0 +1,8 @@ +// PR c++/60605 + +template <typename T = int> +struct Foo { + void bar() { + void bug(); + } +}; diff --git a/gcc/testsuite/g++.dg/tls/thread_local9.C b/gcc/testsuite/g++.dg/tls/thread_local9.C new file mode 100644 index 00000000000..c75528a0291 --- /dev/null +++ b/gcc/testsuite/g++.dg/tls/thread_local9.C @@ -0,0 +1,23 @@ +// PR c++/61343 + +// { dg-do run { target c++11 } } +// { dg-add-options tls } +// { dg-require-effective-target tls_runtime } + +struct Foo { + int value; + + Foo() noexcept { + value = 12; + } +}; + +static thread_local Foo a{}; + +static __attribute__((noinline)) void UseA() { + if (a.value != 12) __builtin_abort(); +} + +int main() { + UseA(); +} diff --git a/gcc/testsuite/gcc.dg/lto/pr61526_0.c b/gcc/testsuite/gcc.dg/lto/pr61526_0.c new file mode 100644 index 00000000000..6324c8c5bda --- /dev/null +++ b/gcc/testsuite/gcc.dg/lto/pr61526_0.c @@ -0,0 +1,6 @@ +/* { dg-lto-do link } */ +/* { dg-lto-options { { -fPIC -flto -flto-partition=1to1 } } } */ +/* { dg-extra-ld-options { -shared } } */ + +static void *master; +void *foo () { return master; } diff --git a/gcc/testsuite/gcc.dg/lto/pr61526_1.c b/gcc/testsuite/gcc.dg/lto/pr61526_1.c new file mode 100644 index 00000000000..bb2893b738d --- /dev/null +++ b/gcc/testsuite/gcc.dg/lto/pr61526_1.c @@ -0,0 +1,2 @@ +extern void *master; +void *bar () { return master; } diff --git a/gcc/testsuite/gcc.dg/pr60866.c b/gcc/testsuite/gcc.dg/pr60866.c new file mode 100644 index 00000000000..020878d41de --- /dev/null +++ b/gcc/testsuite/gcc.dg/pr60866.c @@ -0,0 +1,18 @@ +/* { dg-do compile { target powerpc*-*-* ia64-*-* x86_64-*-* } } */ +/* { dg-options "-O -fselective-scheduling -fno-if-conversion -fschedule-insns" } */ + +int n; + +void +foo (int w, int **dnroot, int **dn) +{ + int *child; + int *xchild = xchild; + for (; w < n; w++) + if (!dnroot) + { + dnroot = dn; + for (child = *dn; child; child = xchild) + ; + } +} diff --git a/gcc/testsuite/gcc.dg/pr61053.c b/gcc/testsuite/gcc.dg/pr61053.c new file mode 100644 index 00000000000..4fd531974f7 --- /dev/null +++ b/gcc/testsuite/gcc.dg/pr61053.c @@ -0,0 +1,75 @@ +/* PR c/61053 */ +/* { dg-do compile { target i?86-*-* x86_64-*-* } } */ +/* { dg-options "-std=c11 -pedantic-errors" } */ + +_Alignas (char) char cc; +_Alignas (short int) char cs; +_Alignas (int) char ci; +_Alignas (long int) char cl; +_Alignas (long long int) char cll; +_Alignas (float) char cf; +_Alignas (double) char cd; +_Alignas (long double) char cld; + +_Alignas (char) short int sc; /* { dg-error "cannot reduce alignment" } */ +_Alignas (short int) short int ss; +_Alignas (int) short int si; +_Alignas (long int) short int sl; +_Alignas (long long int) short int sll; +_Alignas (float) short int sf; +_Alignas (double) short int sd; +_Alignas (long double) short int sld; + +_Alignas (char) int ic; /* { dg-error "cannot reduce alignment" } */ +_Alignas (short int) int is; /* { dg-error "cannot reduce alignment" } */ +_Alignas (int) int ii; +_Alignas (long int) int il; +_Alignas (long long int) int ill; +_Alignas (float) int if_; +_Alignas (double) int id; +_Alignas (long double) int ild; + +_Alignas (char) long int lic; /* { dg-error "cannot reduce alignment" } */ +_Alignas (short int) long int lis; /* { dg-error "cannot reduce alignment" } */ +_Alignas (int) long int lii; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (long int) long int lil; +_Alignas (long long int) long int lill; +_Alignas (float) long int lif; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (double) long int lid; +_Alignas (long double) long int lild; + +_Alignas (char) long long int llic; /* { dg-error "cannot reduce alignment" } */ +_Alignas (short int) long long int llis; /* { dg-error "cannot reduce alignment" } */ +_Alignas (int) long long int llii; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (long int) long long int llil; +_Alignas (long long int) long long int llill; +_Alignas (float) long long int llif; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (double) long long int llid; +_Alignas (long double) long long int llild; + +_Alignas (char) float fc; /* { dg-error "cannot reduce alignment" } */ +_Alignas (short int) float fs; /* { dg-error "cannot reduce alignment" } */ +_Alignas (int) float fi; +_Alignas (long int) float fl; +_Alignas (long long int) float fll; +_Alignas (float) float ff; +_Alignas (double) float fd; +_Alignas (long double) float fld; + +_Alignas (char) double dc; /* { dg-error "cannot reduce alignment" } */ +_Alignas (short int) double ds; /* { dg-error "cannot reduce alignment" } */ +_Alignas (int) double di; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (long int) double dl; +_Alignas (long long int) double dll; +_Alignas (float) double df; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (double) double dd; +_Alignas (long double) double dld; + +_Alignas (char) long double ldc; /* { dg-error "cannot reduce alignment" } */ +_Alignas (short int) long double lds; /* { dg-error "cannot reduce alignment" } */ +_Alignas (int) long double ldi; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (long int) long double ldl; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (long long int) long double ldll; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (float) long double ldf; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (double) long double ldd; /* { dg-error "cannot reduce alignment" "" { target { ! { ia32 } } } } */ +_Alignas (long double) long double ldld; diff --git a/gcc/testsuite/gcc.dg/pr61583.c b/gcc/testsuite/gcc.dg/pr61583.c new file mode 100644 index 00000000000..8424293c176 --- /dev/null +++ b/gcc/testsuite/gcc.dg/pr61583.c @@ -0,0 +1,18 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -fcompare-debug" } */ + +void +f1 (int n, int b) +{ + extern void f2 (int); + int j; + + if (b) + n = 1; + + if (n < 1) + __builtin_unreachable (); + + for (j = 0; j < n; j++) + f2 (j); +} diff --git a/gcc/testsuite/gcc.dg/torture/pr61383-1.c b/gcc/testsuite/gcc.dg/torture/pr61383-1.c new file mode 100644 index 00000000000..d9a0a0b398b --- /dev/null +++ b/gcc/testsuite/gcc.dg/torture/pr61383-1.c @@ -0,0 +1,35 @@ +/* { dg-do run } */ + +int a, b = 1, c, d, e, f, g; + +int +fn1 () +{ + int h; + for (;;) + { + g = b; + g = g ? 0 : 1 % g; + e = a + 1; + for (; d < 1; d = e) + { + if (f == 0) + h = 0; + else + h = 1 % f; + if (f < 1) + c = 0; + else if (h) + break; + } + if (b) + return 0; + } +} + +int +main () +{ + fn1 (); + return 0; +} diff --git a/gcc/testsuite/gcc.dg/torture/pr61452.c b/gcc/testsuite/gcc.dg/torture/pr61452.c new file mode 100644 index 00000000000..a62de30fd84 --- /dev/null +++ b/gcc/testsuite/gcc.dg/torture/pr61452.c @@ -0,0 +1,31 @@ +/* { dg-do run } */ + +int a, b; +short c, d; +char e, f; + +int +fn1 (int p1, char p2) +{ + return p1 || p2 ? 0 : p2; +} + +void +fn2 () +{ + for (; a;) + { + int g; + g = c = e; + for (; a;) + b = fn1 (g = d = e, g); + f = g; + } +} + +int +main () +{ + fn2 (); + return 0; +} diff --git a/gcc/testsuite/gcc.target/aarch64/aapcs64/type-def.h b/gcc/testsuite/gcc.target/aarch64/aapcs64/type-def.h index a95d06aa2ed..07e56fff857 100644 --- a/gcc/testsuite/gcc.target/aarch64/aapcs64/type-def.h +++ b/gcc/testsuite/gcc.target/aarch64/aapcs64/type-def.h @@ -34,6 +34,13 @@ struct hfa_fx2_t float b; }; +struct hfa_fx3_t +{ + float a; + float b; + float c; +}; + struct hfa_dx2_t { double a; diff --git a/gcc/testsuite/gcc.target/aarch64/aapcs64/va_arg-13.c b/gcc/testsuite/gcc.target/aarch64/aapcs64/va_arg-13.c new file mode 100644 index 00000000000..ae1e3ec45cf --- /dev/null +++ b/gcc/testsuite/gcc.target/aarch64/aapcs64/va_arg-13.c @@ -0,0 +1,59 @@ +/* Test AAPCS64 layout and __builtin_va_start. + + Pass named HFA/HVA argument on stack. */ + +/* { dg-do run { target aarch64*-*-* } } */ + +#ifndef IN_FRAMEWORK +#define AAPCS64_TEST_STDARG +#define TESTFILE "va_arg-13.c" + +struct float_float_t +{ + float a; + float b; +} float_float; + +union float_int_t +{ + float b8; + int b5; +} float_int; + +#define HAS_DATA_INIT_FUNC +void +init_data () +{ + float_float.a = 1.2f; + float_float.b = 2.2f; + + float_int.b8 = 4983.80f; +} + +#include "abitest.h" +#else + ARG (float, 1.0f, S0, 0) + ARG (float, 2.0f, S1, 1) + ARG (float, 3.0f, S2, 2) + ARG (float, 4.0f, S3, 3) + ARG (float, 5.0f, S4, 4) + ARG (float, 6.0f, S5, 5) + ARG (float, 7.0f, S6, 6) + ARG (struct float_float_t, float_float, STACK, 7) + ARG (int, 9, W0, 8) + ARG (int, 10, W1, 9) + ARG (int, 11, W2, 10) + ARG (int, 12, W3, 11) + ARG (int, 13, W4, 12) + ARG (int, 14, W5, 13) + ARG (int, 15, W6, LAST_NAMED_ARG_ID) + DOTS + /* Note on the reason of using 'X7' instead of 'W7' here: + Using 'X7' makes sure the test works in the big-endian mode. + According to PCS rules B.4 and C.10, the size of float_int is rounded + to 8 bytes and prepared in the register X7 as if loaded via LDR from + the memory, with the content of the other 4 bytes unspecified. The + test framework will only compare the 4 relavent bytes. */ + ANON (union float_int_t, float_int, X7, 15) + LAST_ANON (long long, 12683143434LL, STACK + 8, 16) +#endif diff --git a/gcc/testsuite/gcc.target/aarch64/aapcs64/va_arg-14.c b/gcc/testsuite/gcc.target/aarch64/aapcs64/va_arg-14.c new file mode 100644 index 00000000000..91080d5afa4 --- /dev/null +++ b/gcc/testsuite/gcc.target/aarch64/aapcs64/va_arg-14.c @@ -0,0 +1,35 @@ +/* Test AAPCS64 layout and __builtin_va_start. + + Pass named HFA/HVA argument on stack. */ + +/* { dg-do run { target aarch64*-*-* } } */ + +#ifndef IN_FRAMEWORK +#define AAPCS64_TEST_STDARG +#define TESTFILE "va_arg-14.c" +#include "type-def.h" + +struct hfa_fx2_t hfa_fx2 = {1.2f, 2.2f}; +struct hfa_fx3_t hfa_fx3 = {3.2f, 4.2f, 5.2f}; +vf4_t float32x4 = {6.2f, 7.2f, 8.2f, 9.2f}; +vf4_t float32x4_2 = {10.2f, 11.2f, 12.2f, 13.2f}; + +#include "abitest.h" +#else + ARG (float, 1.0f, S0, 0) + ARG (float, 2.0f, S1, 1) + ARG (float, 3.0f, S2, 2) + ARG (float, 4.0f, S3, 3) + ARG (float, 5.0f, S4, 4) + ARG (float, 6.0f, S5, 5) + ARG (float, 7.0f, S6, 6) + ARG (struct hfa_fx3_t, hfa_fx3, STACK, 7) + /* Previous argument size has been rounded up to the nearest multiple of + 8 bytes. */ + ARG (struct hfa_fx2_t, hfa_fx2, STACK + 16, 8) + /* NSAA is rounded up to the nearest natural alignment of float32x4. */ + ARG (vf4_t, float32x4, STACK + 32, 9) + ARG (vf4_t, float32x4_2, STACK + 48, LAST_NAMED_ARG_ID) + DOTS + LAST_ANON (double, 123456789.987, STACK + 64, 11) +#endif diff --git a/gcc/testsuite/gcc.target/aarch64/aapcs64/va_arg-15.c b/gcc/testsuite/gcc.target/aarch64/aapcs64/va_arg-15.c new file mode 100644 index 00000000000..d8fdb322b2f --- /dev/null +++ b/gcc/testsuite/gcc.target/aarch64/aapcs64/va_arg-15.c @@ -0,0 +1,39 @@ +/* Test AAPCS64 layout and __builtin_va_start. + + Pass named __128int argument on stack. */ + +/* { dg-do run { target aarch64*-*-* } } */ + +#ifndef IN_FRAMEWORK +#define AAPCS64_TEST_STDARG +#define TESTFILE "va_arg-15.c" +#include "type-def.h" + +union int128_t qword; + +#define HAS_DATA_INIT_FUNC +void +init_data () +{ + /* Init signed quad-word integer. */ + qword.l64 = 0xfdb9753102468aceLL; + qword.h64 = 0xeca8642013579bdfLL; +} + +#include "abitest.h" +#else + ARG (int, 1, W0, 0) + ARG (int, 2, W1, 1) + ARG (int, 3, W2, 2) + ARG (int, 4, W3, 3) + ARG (int, 5, W4, 4) + ARG (int, 6, W5, 5) + ARG (int, 7, W6, 6) + ARG (__int128, qword.i, STACK, LAST_NAMED_ARG_ID) + DOTS +#ifndef __AAPCS64_BIG_ENDIAN__ + LAST_ANON (int, 8, STACK + 16, 8) +#else + LAST_ANON (int, 8, STACK + 20, 8) +#endif +#endif diff --git a/gcc/testsuite/gcc.target/aarch64/pr61325.c b/gcc/testsuite/gcc.target/aarch64/pr61325.c new file mode 100644 index 00000000000..45ece53446f --- /dev/null +++ b/gcc/testsuite/gcc.target/aarch64/pr61325.c @@ -0,0 +1,19 @@ +/* { dg-do compile } */ +/* { dg-options "-O2" } */ +typedef unsigned int wchar_t; +typedef long unsigned int size_t; + +size_t +wcstombs(char *s , const wchar_t *pwcs , size_t n) +{ + int count = 0; + + if (n != 0) { + do { + if ((*s++ = (char) *pwcs++) == 0) + break; + count++; + } while (--n != 0); + } + return count; +} diff --git a/gcc/testsuite/gcc.target/avr/torture/pr61443.c b/gcc/testsuite/gcc.target/avr/torture/pr61443.c new file mode 100644 index 00000000000..12c6bca6663 --- /dev/null +++ b/gcc/testsuite/gcc.target/avr/torture/pr61443.c @@ -0,0 +1,134 @@ +/* { dg-do run } */ +/* { dg-options "-std=gnu99" } */ + +#include <stdlib.h> +#include <stdarg.h> + +#define NC __attribute__((noinline,noclone)) + +void NC vfun (char n, ...) +{ + va_list ap; + + va_start (ap, n); + + switch (n) + { + default: + abort(); + case 1: + if (11 != va_arg (ap, int)) + abort(); + break; + case 2: + if (2222 != va_arg (ap, int)) + abort(); + break; + case 3: + if (333333 != va_arg (ap, __int24)) + abort(); + break; + case 4: + if (44444444 != va_arg (ap, long)) + abort(); + break; + case 8: + if (8888888888888888 != va_arg (ap, long long)) + abort(); + break; + } + + va_end (ap); +} + + +void NC boo_qi (const __flash char *p) +{ + vfun (1, *p); +} + +void NC boox_qi (const __memx char *p) +{ + vfun (1, *p); +} + +void NC boo_hi (const __flash int *p) +{ + vfun (2, *p); +} + +void NC boox_hi (const __memx int *p) +{ + vfun (2, *p); +} + +void NC boo_psi (const __flash __int24 *p) +{ + vfun (3, *p); +} + +void NC boox_psi (const __memx __int24 *p) +{ + vfun (3, *p); +} + +void NC boo_si (const __flash long *p) +{ + vfun (4, *p); +} + +void NC boox_si (const __memx long *p) +{ + vfun (4, *p); +} + +void NC boo_di (const __flash long long *p) +{ + vfun (8, *p); +} + +void NC boox_di (const __memx long long *p) +{ + vfun (8, *p); +} + +const __flash char f_qi = 11; +const __flash int f_hi = 2222; +const __flash __int24 f_psi = 333333; +const __flash long f_si = 44444444; +const __flash long long f_di = 8888888888888888; + +const __memx char x_qi = 11; +const __memx int x_hi = 2222; +const __memx __int24 x_psi = 333333; +const __memx long x_si = 44444444; +const __memx long long x_di = 8888888888888888; + +char r_qi = 11; +int r_hi = 2222; +__int24 r_psi = 333333; +long r_si = 44444444; +long long r_di = 8888888888888888; + +int main (void) +{ + boo_qi (&f_qi); + boo_hi (&f_hi); + boo_psi (&f_psi); + boo_si (&f_si); + boo_di (&f_di); + + boox_qi (&x_qi); + boox_hi (&x_hi); + boox_psi (&x_psi); + boox_si (&x_si); + boox_di (&x_di); + + boox_qi (&r_qi); + boox_hi (&r_hi); + boox_psi (&r_psi); + boox_si (&r_si); + boox_di (&r_di); + + exit (0); +} diff --git a/gcc/testsuite/gcc.target/i386/pr60901.c b/gcc/testsuite/gcc.target/i386/pr60901.c new file mode 100644 index 00000000000..f0f25a1dc2c --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr60901.c @@ -0,0 +1,17 @@ +/* { dg-options "-O -fselective-scheduling -fschedule-insns -fsel-sched-pipelining -fsel-sched-pipelining-outer-loops -fno-tree-dominator-opts" } */ + +extern int n; +extern void bar (void); +extern int baz (int); + +void +foo (void) +{ + int i, j; + for (j = 0; j < n; j++) + { + for (i = 1; i < j; i++) + bar (); + baz (0); + } +} diff --git a/gcc/testsuite/gcc.target/i386/pr61423.c b/gcc/testsuite/gcc.target/i386/pr61423.c new file mode 100644 index 00000000000..5b538a26508 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr61423.c @@ -0,0 +1,38 @@ +/* PR target/61423 */ +/* { dg-do run { target ia32 } } */ +/* { dg-options "-O1 -ftree-vectorize -msse2 -mfpmath=387 -mtune=core2" } */ + +#define N 1024 +static unsigned int A[N]; + +double +__attribute__((noinline)) +func (void) +{ + unsigned int sum = 0; + unsigned i; + double t; + + for (i = 0; i < N; i++) + sum += A[i]; + + t = sum; + return t; +} + +int +main () +{ + unsigned i; + double d; + + for(i = 0; i < N; i++) + A[i] = 1; + + d = func(); + + if (d != 1024.0) + __builtin_abort (); + + return 0; +} diff --git a/gcc/testsuite/gcc.target/i386/pr61446.c b/gcc/testsuite/gcc.target/i386/pr61446.c new file mode 100644 index 00000000000..fc32f63ee69 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr61446.c @@ -0,0 +1,14 @@ +/* PR rtl-optimization/61446 */ + +/* { dg-do compile { target { ia32 } } } */ +/* { dg-options "-O2 -march=corei7 -mfpmath=387" } */ + +unsigned long long +foo (float a) +{ + const double dfa = a; + const unsigned int hi = dfa / 0x1p32f; + const unsigned int lo = dfa - (double) hi * 0x1p32f; + + return ((unsigned long long) hi << (4 * (8))) | lo; +} diff --git a/gcc/testsuite/gcc.target/powerpc/pack02.c b/gcc/testsuite/gcc.target/powerpc/pack02.c index 584d6c29205..f85d3ff00b0 100644 --- a/gcc/testsuite/gcc.target/powerpc/pack02.c +++ b/gcc/testsuite/gcc.target/powerpc/pack02.c @@ -2,6 +2,7 @@ /* { dg-skip-if "" { powerpc*-*-darwin* } { "*" } { "" } } */ /* { dg-skip-if "" { powerpc*-*-*spe* } { "*" } { "" } } */ /* { dg-require-effective-target powerpc_fprs } */ +/* { dg-require-effective-target longdouble128 } */ /* { dg-options "-O2 -mhard-float" } */ #include <stddef.h> diff --git a/gcc/testsuite/gcc.target/powerpc/tfmode_off.c b/gcc/testsuite/gcc.target/powerpc/tfmode_off.c index e6578ef31a8..ea703f0ee0a 100644 --- a/gcc/testsuite/gcc.target/powerpc/tfmode_off.c +++ b/gcc/testsuite/gcc.target/powerpc/tfmode_off.c @@ -1,6 +1,7 @@ /* { dg-do assemble } */ /* { dg-skip-if "" { powerpc-ibm-aix* } { "*" } { "" } } */ /* { dg-skip-if "no TFmode" { powerpc-*-eabi* } { "*" } { "" } } */ +/* { dg-require-effective-target longdouble128 } */ /* { dg-options "-O2 -fno-align-functions -mtraceback=no -save-temps" } */ typedef float TFmode __attribute__ ((mode (TF))); diff --git a/gcc/testsuite/gfortran.dg/arrayio_14.f90 b/gcc/testsuite/gfortran.dg/arrayio_14.f90 new file mode 100644 index 00000000000..3d878c75644 --- /dev/null +++ b/gcc/testsuite/gfortran.dg/arrayio_14.f90 @@ -0,0 +1,18 @@ +! { dg-do run } +! PR61173.f90 Bogus END condition +module bd + character(len=25, kind=1), dimension(:), allocatable, save :: source + contains + subroutine init_data + allocate(source(2)) + source=[" 1 1 1 ", " 4 4 4 "] + end subroutine init_data +end module bd +program read_internal + use bd + integer :: x(6),i + + call init_data + read(source,*) (x(i), i=1,6) + if (any(x/=[1,1,1,4,4,4])) call abort +end program read_internal diff --git a/gcc/testsuite/gfortran.dg/associate_17.f90 b/gcc/testsuite/gfortran.dg/associate_17.f90 new file mode 100644 index 00000000000..5c39cf06247 --- /dev/null +++ b/gcc/testsuite/gfortran.dg/associate_17.f90 @@ -0,0 +1,12 @@ +! { dg-do run } +! Test the fix for PR61406 +! Contributed by Adam Hirst <adam@aphirst.karoo.co.uk> +program test + implicit none + real :: theta = 1.0 + + associate (n => [cos(theta), sin(theta)]) + if (abs (norm2(n) - 1.0) .gt. 1.0e-4) call abort + end associate + +end program test diff --git a/gcc/testsuite/gfortran.dg/cray_pointers_10.f90 b/gcc/testsuite/gfortran.dg/cray_pointers_10.f90 new file mode 100644 index 00000000000..1ac98f3ea46 --- /dev/null +++ b/gcc/testsuite/gfortran.dg/cray_pointers_10.f90 @@ -0,0 +1,18 @@ +! { dg-do run } +! { dg-options "-fcray-pointer" } +! +! PR fortran/45187 +! +module foo + implicit none + real :: a + pointer(c_a, a) +end module foo + +program test + use foo + real :: z + c_a = loc(z) + a = 42 + if (z /= 42) call abort +end program test diff --git a/gcc/testsuite/gnat.dg/opt38.adb b/gcc/testsuite/gnat.dg/opt38.adb new file mode 100644 index 00000000000..143f4fade19 --- /dev/null +++ b/gcc/testsuite/gnat.dg/opt38.adb @@ -0,0 +1,9 @@ +-- { dg-do run } +-- { dg-options "-O2 -gnatn" } + +with Opt38_Pkg; use Opt38_Pkg; + +procedure Opt38 is +begin + Test (-1); +end; diff --git a/gcc/testsuite/gnat.dg/opt38_pkg.adb b/gcc/testsuite/gnat.dg/opt38_pkg.adb new file mode 100644 index 00000000000..7cbbeeab328 --- /dev/null +++ b/gcc/testsuite/gnat.dg/opt38_pkg.adb @@ -0,0 +1,33 @@ +package body Opt38_Pkg is + + procedure Proc (I : Integer); + pragma Inline (Proc); + + procedure Proc (I : Integer) is + + procedure Inner; + pragma No_Inline (Inner); + + procedure Inner is + begin + if I /= 110 then + raise Program_Error; + end if; + end; + + begin + if I > 0 then + Inner; + end if; + end; + + procedure Test (I : Integer) is + begin + if I > -1 then + Proc (I); + else + Proc (I + 111); + end if; + end; + +end Opt38_Pkg; diff --git a/gcc/testsuite/gnat.dg/opt38_pkg.ads b/gcc/testsuite/gnat.dg/opt38_pkg.ads new file mode 100644 index 00000000000..b6cb4e6bc72 --- /dev/null +++ b/gcc/testsuite/gnat.dg/opt38_pkg.ads @@ -0,0 +1,5 @@ +package Opt38_Pkg is + + procedure Test (I : Integer); + +end Opt38_Pkg; diff --git a/gcc/testsuite/lib/target-supports.exp b/gcc/testsuite/lib/target-supports.exp index 4585ce3d369..665636c6b80 100644 --- a/gcc/testsuite/lib/target-supports.exp +++ b/gcc/testsuite/lib/target-supports.exp @@ -1862,6 +1862,15 @@ proc check_effective_target_large_double { } { }] } +# Return 1 if the target supports long double of 128 bits, +# 0 otherwise. + +proc check_effective_target_longdouble128 { } { + return [check_no_compiler_messages longdouble128 object { + int dummy[sizeof(long double) == 16 ? 1 : -1]; + }] +} + # Return 1 if the target supports double of 64 bits, # 0 otherwise. diff --git a/gcc/tree-core.h b/gcc/tree-core.h index 1719c7e664e..75c1e3fc275 100644 --- a/gcc/tree-core.h +++ b/gcc/tree-core.h @@ -987,7 +987,7 @@ struct GTY(()) tree_base { SSA_NAME_IN_FREELIST in SSA_NAME - VAR_DECL_NONALIASED in + DECL_NONALIASED in VAR_DECL deprecated_flag: diff --git a/gcc/tree-ssa-alias.c b/gcc/tree-ssa-alias.c index e70627589cc..cdf3166db82 100644 --- a/gcc/tree-ssa-alias.c +++ b/gcc/tree-ssa-alias.c @@ -835,8 +835,8 @@ nonoverlapping_component_refs_of_decl_p (tree ref1, tree ref2) /* ??? We cannot simply use the type of operand #0 of the refs here as the Fortran compiler smuggles type punning into COMPONENT_REFs for common blocks instead of using unions like everyone else. */ - tree type1 = TYPE_MAIN_VARIANT (DECL_CONTEXT (field1)); - tree type2 = TYPE_MAIN_VARIANT (DECL_CONTEXT (field2)); + tree type1 = DECL_CONTEXT (field1); + tree type2 = DECL_CONTEXT (field2); /* We cannot disambiguate fields in a union or qualified union. */ if (type1 != type2 || TREE_CODE (type1) != RECORD_TYPE) diff --git a/gcc/tree-ssa-ifcombine.c b/gcc/tree-ssa-ifcombine.c index be28fb00417..6d8349c3156 100644 --- a/gcc/tree-ssa-ifcombine.c +++ b/gcc/tree-ssa-ifcombine.c @@ -127,7 +127,11 @@ bb_no_side_effects_p (basic_block bb) { gimple stmt = gsi_stmt (gsi); + if (is_gimple_debug (stmt)) + continue; + if (gimple_has_side_effects (stmt) + || gimple_could_trap_p (stmt) || gimple_vuse (stmt)) return false; } diff --git a/gcc/tree-ssa-sccvn.c b/gcc/tree-ssa-sccvn.c index f7ec8b6d60b..5bf4e9289ad 100644 --- a/gcc/tree-ssa-sccvn.c +++ b/gcc/tree-ssa-sccvn.c @@ -3074,33 +3074,12 @@ visit_phi (gimple phi) /* If all value numbered to the same value, the phi node has that value. */ if (allsame) - { - if (is_gimple_min_invariant (sameval)) - { - VN_INFO (PHI_RESULT (phi))->has_constants = true; - VN_INFO (PHI_RESULT (phi))->expr = sameval; - } - else - { - VN_INFO (PHI_RESULT (phi))->has_constants = false; - VN_INFO (PHI_RESULT (phi))->expr = sameval; - } - - if (TREE_CODE (sameval) == SSA_NAME) - return visit_copy (PHI_RESULT (phi), sameval); - - return set_ssa_val_to (PHI_RESULT (phi), sameval); - } + return set_ssa_val_to (PHI_RESULT (phi), sameval); /* Otherwise, see if it is equivalent to a phi node in this block. */ result = vn_phi_lookup (phi); if (result) - { - if (TREE_CODE (result) == SSA_NAME) - changed = visit_copy (PHI_RESULT (phi), result); - else - changed = set_ssa_val_to (PHI_RESULT (phi), result); - } + changed = set_ssa_val_to (PHI_RESULT (phi), result); else { vn_phi_insert (phi, PHI_RESULT (phi)); @@ -3214,24 +3193,18 @@ simplify_binary_expression (gimple stmt) catch those with constants. The goal here is to simultaneously combine constants between expressions, but avoid infinite expansion of expressions during simplification. */ - if (TREE_CODE (op0) == SSA_NAME) - { - if (VN_INFO (op0)->has_constants + op0 = vn_valueize (op0); + if (TREE_CODE (op0) == SSA_NAME + && (VN_INFO (op0)->has_constants || TREE_CODE_CLASS (code) == tcc_comparison - || code == COMPLEX_EXPR) - op0 = valueize_expr (vn_get_expr_for (op0)); - else - op0 = vn_valueize (op0); - } + || code == COMPLEX_EXPR)) + op0 = valueize_expr (vn_get_expr_for (op0)); - if (TREE_CODE (op1) == SSA_NAME) - { - if (VN_INFO (op1)->has_constants - || code == COMPLEX_EXPR) - op1 = valueize_expr (vn_get_expr_for (op1)); - else - op1 = vn_valueize (op1); - } + op1 = vn_valueize (op1); + if (TREE_CODE (op1) == SSA_NAME + && (VN_INFO (op1)->has_constants + || code == COMPLEX_EXPR)) + op1 = valueize_expr (vn_get_expr_for (op1)); /* Pointer plus constant can be represented as invariant address. Do so to allow further propatation, see also tree forwprop. */ @@ -3289,24 +3262,28 @@ simplify_unary_expression (gimple stmt) return NULL_TREE; orig_op0 = op0; - if (VN_INFO (op0)->has_constants) - op0 = valueize_expr (vn_get_expr_for (op0)); - else if (CONVERT_EXPR_CODE_P (code) - || code == REALPART_EXPR - || code == IMAGPART_EXPR - || code == VIEW_CONVERT_EXPR - || code == BIT_FIELD_REF) + op0 = vn_valueize (op0); + if (TREE_CODE (op0) == SSA_NAME) { - /* We want to do tree-combining on conversion-like expressions. - Make sure we feed only SSA_NAMEs or constants to fold though. */ - tree tem = valueize_expr (vn_get_expr_for (op0)); - if (UNARY_CLASS_P (tem) - || BINARY_CLASS_P (tem) - || TREE_CODE (tem) == VIEW_CONVERT_EXPR - || TREE_CODE (tem) == SSA_NAME - || TREE_CODE (tem) == CONSTRUCTOR - || is_gimple_min_invariant (tem)) - op0 = tem; + if (VN_INFO (op0)->has_constants) + op0 = valueize_expr (vn_get_expr_for (op0)); + else if (CONVERT_EXPR_CODE_P (code) + || code == REALPART_EXPR + || code == IMAGPART_EXPR + || code == VIEW_CONVERT_EXPR + || code == BIT_FIELD_REF) + { + /* We want to do tree-combining on conversion-like expressions. + Make sure we feed only SSA_NAMEs or constants to fold though. */ + tree tem = valueize_expr (vn_get_expr_for (op0)); + if (UNARY_CLASS_P (tem) + || BINARY_CLASS_P (tem) + || TREE_CODE (tem) == VIEW_CONVERT_EXPR + || TREE_CODE (tem) == SSA_NAME + || TREE_CODE (tem) == CONSTRUCTOR + || is_gimple_min_invariant (tem)) + op0 = tem; + } } /* Avoid folding if nothing changed, but remember the expression. */ diff --git a/gcc/tree-ssa-tail-merge.c b/gcc/tree-ssa-tail-merge.c index f6b1ba08154..aa7f829d18c 100644 --- a/gcc/tree-ssa-tail-merge.c +++ b/gcc/tree-ssa-tail-merge.c @@ -481,7 +481,11 @@ same_succ_hash (const_same_succ e) hashval = iterative_hash_hashval_t ((hashval_t) gimple_call_internal_fn (stmt), hashval); else - hashval = iterative_hash_expr (gimple_call_fn (stmt), hashval); + { + hashval = iterative_hash_expr (gimple_call_fn (stmt), hashval); + if (gimple_call_chain (stmt)) + hashval = iterative_hash_expr (gimple_call_chain (stmt), hashval); + } for (i = 0; i < gimple_call_num_args (stmt); i++) { arg = gimple_call_arg (stmt, i); @@ -1121,18 +1125,23 @@ gimple_equal_p (same_succ same_succ, gimple s1, gimple s2) switch (gimple_code (s1)) { case GIMPLE_CALL: - if (gimple_call_num_args (s1) != gimple_call_num_args (s2)) - return false; if (!gimple_call_same_target_p (s1, s2)) return false; + t1 = gimple_call_chain (s1); + t2 = gimple_call_chain (s2); + if (!gimple_operand_equal_value_p (t1, t2)) + return false; + + if (gimple_call_num_args (s1) != gimple_call_num_args (s2)) + return false; + for (i = 0; i < gimple_call_num_args (s1); ++i) { t1 = gimple_call_arg (s1, i); t2 = gimple_call_arg (s2, i); - if (gimple_operand_equal_value_p (t1, t2)) - continue; - return false; + if (!gimple_operand_equal_value_p (t1, t2)) + return false; } lhs1 = gimple_get_lhs (s1); diff --git a/gcc/tree-ssa-threadedge.c b/gcc/tree-ssa-threadedge.c index 8e628d5535d..c715e842d99 100644 --- a/gcc/tree-ssa-threadedge.c +++ b/gcc/tree-ssa-threadedge.c @@ -199,9 +199,7 @@ record_temporary_equivalence (tree x, tree y, vec<tree> *stack) traversing back edges less painful. */ static bool -record_temporary_equivalences_from_phis (edge e, vec<tree> *stack, - bool backedge_seen, - bitmap src_map, bitmap dst_map) +record_temporary_equivalences_from_phis (edge e, vec<tree> *stack) { gimple_stmt_iterator gsi; @@ -229,14 +227,6 @@ record_temporary_equivalences_from_phis (edge e, vec<tree> *stack, stmt_count++; record_temporary_equivalence (dst, src, stack); - - /* If we have crossed a backedge, then start recording equivalences - we might need to invalidate. */ - if (backedge_seen && TREE_CODE (src) == SSA_NAME) - { - bitmap_set_bit (src_map, SSA_NAME_VERSION (src)); - bitmap_set_bit (dst_map, SSA_NAME_VERSION (dst)); - } } return true; } @@ -294,29 +284,15 @@ fold_assignment_stmt (gimple stmt) /* A new value has been assigned to LHS. If necessary, invalidate any equivalences that are no longer valid. */ static void -invalidate_equivalences (tree lhs, vec<tree> *stack, - bitmap src_map, bitmap dst_map) +invalidate_equivalences (tree lhs, vec<tree> *stack) { - /* SRC_MAP contains the source SSA_NAMEs for equivalences created by PHI - nodes. If an entry in SRC_MAP changes, there's some destination that - has been recorded as equivalent to the source and that equivalency - needs to be eliminated. */ - if (bitmap_bit_p (src_map, SSA_NAME_VERSION (lhs))) - { - unsigned int i; - bitmap_iterator bi; - - /* We know that the LHS of STMT was used as the RHS in an equivalency - created by a PHI. All the LHS of such PHIs were recorded into DST_MAP. - So we can iterate over them to see if any have the LHS of STMT as - an equivalence, and if so, remove the equivalence as it is no longer - valid. */ - EXECUTE_IF_SET_IN_BITMAP (dst_map, 0, i, bi) - { - if (SSA_NAME_VALUE (ssa_name (i)) == lhs) - record_temporary_equivalence (ssa_name (i), NULL_TREE, stack); - } - } + + for (unsigned int i = 1; i < num_ssa_names; i++) + if (ssa_name (i) && SSA_NAME_VALUE (ssa_name (i)) == lhs) + record_temporary_equivalence (ssa_name (i), NULL_TREE, stack); + + if (SSA_NAME_VALUE (lhs)) + record_temporary_equivalence (lhs, NULL_TREE, stack); } /* Try to simplify each statement in E->dest, ultimately leading to @@ -341,9 +317,7 @@ record_temporary_equivalences_from_stmts_at_dest (edge e, vec<tree> *stack, tree (*simplify) (gimple, gimple), - bool backedge_seen, - bitmap src_map, - bitmap dst_map) + bool backedge_seen) { gimple stmt = NULL; gimple_stmt_iterator gsi; @@ -399,19 +373,7 @@ record_temporary_equivalences_from_stmts_at_dest (edge e, if (backedge_seen) FOR_EACH_SSA_TREE_OPERAND (op, stmt, iter, SSA_OP_DEF) - { - /* This call only invalidates equivalences created by - PHI nodes. This is by design to keep the cost of - of invalidation reasonable. */ - invalidate_equivalences (op, stack, src_map, dst_map); - - /* However, conditionals can imply values for real - operands as well. And those won't be recorded in the - maps. In fact, those equivalences may be recorded totally - outside the threading code. We can just create a new - temporary NULL equivalence here. */ - record_temporary_equivalence (op, NULL_TREE, stack); - } + invalidate_equivalences (op, stack); continue; } @@ -451,8 +413,7 @@ record_temporary_equivalences_from_stmts_at_dest (edge e, if (backedge_seen) { tree lhs = gimple_get_lhs (stmt); - record_temporary_equivalence (lhs, NULL_TREE, stack); - invalidate_equivalences (lhs, stack, src_map, dst_map); + invalidate_equivalences (lhs, stack); } continue; } @@ -530,11 +491,7 @@ record_temporary_equivalences_from_stmts_at_dest (edge e, || is_gimple_min_invariant (cached_lhs))) record_temporary_equivalence (gimple_get_lhs (stmt), cached_lhs, stack); else if (backedge_seen) - record_temporary_equivalence (gimple_get_lhs (stmt), NULL_TREE, stack); - - if (backedge_seen) - invalidate_equivalences (gimple_get_lhs (stmt), stack, - src_map, dst_map); + invalidate_equivalences (gimple_get_lhs (stmt), stack); } return stmt; } @@ -981,9 +938,7 @@ thread_through_normal_block (edge e, tree (*simplify) (gimple, gimple), vec<jump_thread_edge *> *path, bitmap visited, - bool *backedge_seen_p, - bitmap src_map, - bitmap dst_map) + bool *backedge_seen_p) { /* If we have traversed a backedge, then we do not want to look at certain expressions in the table that can not be relied upon. @@ -992,17 +947,18 @@ thread_through_normal_block (edge e, if (*backedge_seen_p) simplify = dummy_simplify; - /* PHIs create temporary equivalences. */ - if (!record_temporary_equivalences_from_phis (e, stack, *backedge_seen_p, - src_map, dst_map)) - return 0; + /* PHIs create temporary equivalences. + Note that if we found a PHI that made the block non-threadable, then + we need to bubble that up to our caller in the same manner we do + when we prematurely stop processing statements below. */ + if (!record_temporary_equivalences_from_phis (e, stack)) + return -1; /* Now walk each statement recording any context sensitive temporary equivalences we can detect. */ gimple stmt = record_temporary_equivalences_from_stmts_at_dest (e, stack, simplify, - *backedge_seen_p, - src_map, dst_map); + *backedge_seen_p); /* If we didn't look at all the statements, the most likely reason is there were too many and thus duplicating this block is not profitable. @@ -1111,8 +1067,6 @@ thread_across_edge (gimple dummy_cond, tree (*simplify) (gimple, gimple)) { bitmap visited = BITMAP_ALLOC (NULL); - bitmap src_map = BITMAP_ALLOC (NULL); - bitmap dst_map = BITMAP_ALLOC (NULL); bool backedge_seen; stmt_count = 0; @@ -1128,16 +1082,13 @@ thread_across_edge (gimple dummy_cond, int threaded = thread_through_normal_block (e, dummy_cond, handle_dominating_asserts, stack, simplify, path, - visited, &backedge_seen, - src_map, dst_map); + visited, &backedge_seen); if (threaded > 0) { propagate_threaded_block_debug_into (path->last ()->e->dest, e->dest); remove_temporary_equivalences (stack); BITMAP_FREE (visited); - BITMAP_FREE (src_map); - BITMAP_FREE (dst_map); register_jump_thread (path); return; } @@ -1159,8 +1110,6 @@ thread_across_edge (gimple dummy_cond, if (threaded < 0) { BITMAP_FREE (visited); - BITMAP_FREE (src_map); - BITMAP_FREE (dst_map); remove_temporary_equivalences (stack); return; } @@ -1189,26 +1138,15 @@ thread_across_edge (gimple dummy_cond, { remove_temporary_equivalences (stack); BITMAP_FREE (visited); - BITMAP_FREE (src_map); - BITMAP_FREE (dst_map); return; } - /* We need to restore the state of the maps to this point each loop - iteration. */ - bitmap src_map_copy = BITMAP_ALLOC (NULL); - bitmap dst_map_copy = BITMAP_ALLOC (NULL); - bitmap_copy (src_map_copy, src_map); - bitmap_copy (dst_map_copy, dst_map); - /* Look at each successor of E->dest to see if we can thread through it. */ FOR_EACH_EDGE (taken_edge, ei, e->dest->succs) { /* Push a fresh marker so we can unwind the equivalences created for each of E->dest's successors. */ stack->safe_push (NULL_TREE); - bitmap_copy (src_map, src_map_copy); - bitmap_copy (dst_map, dst_map_copy); /* Avoid threading to any block we have already visited. */ bitmap_clear (visited); @@ -1244,8 +1182,7 @@ thread_across_edge (gimple dummy_cond, found = thread_through_normal_block (path->last ()->e, dummy_cond, handle_dominating_asserts, stack, simplify, path, visited, - &backedge_seen, - src_map, dst_map) > 0; + &backedge_seen) > 0; /* If we were able to thread through a successor of E->dest, then record the jump threading opportunity. */ @@ -1264,10 +1201,6 @@ thread_across_edge (gimple dummy_cond, remove_temporary_equivalences (stack); } BITMAP_FREE (visited); - BITMAP_FREE (src_map); - BITMAP_FREE (dst_map); - BITMAP_FREE (src_map_copy); - BITMAP_FREE (dst_map_copy); } remove_temporary_equivalences (stack); diff --git a/gcc/tree-vrp.c b/gcc/tree-vrp.c index 14f1526fa98..8fcb9d15eef 100644 --- a/gcc/tree-vrp.c +++ b/gcc/tree-vrp.c @@ -6661,8 +6661,9 @@ remove_range_assertions (void) } else { + if (!is_gimple_debug (gsi_stmt (si))) + is_unreachable = 0; gsi_next (&si); - is_unreachable = 0; } } } diff --git a/gcc/varpool.c b/gcc/varpool.c index b5493ab5a84..dc869e2512d 100644 --- a/gcc/varpool.c +++ b/gcc/varpool.c @@ -304,7 +304,16 @@ ctor_for_folding (tree decl) if (DECL_VIRTUAL_P (real_decl)) { gcc_checking_assert (TREE_READONLY (real_decl)); - return DECL_INITIAL (real_decl); + if (DECL_INITIAL (real_decl)) + return DECL_INITIAL (real_decl); + else + { + /* The C++ front end creates VAR_DECLs for vtables of typeinfo + classes not defined in the current TU so that it can refer + to them from typeinfo objects. Avoid returning NULL_TREE. */ + gcc_checking_assert (!COMPLETE_TYPE_P (DECL_CONTEXT (real_decl))); + return error_mark_node; + } } /* If there is no constructor, we have nothing to do. */ diff --git a/libgfortran/ChangeLog b/libgfortran/ChangeLog index 9f6304d4935..6cf4258844b 100644 --- a/libgfortran/ChangeLog +++ b/libgfortran/ChangeLog @@ -1,3 +1,10 @@ +2014-06-07 Jerry DeLisle <jvdelisle@gcc.gnu> + + Backport from trunk. + PR libfortran/61173 + * io/list_read.c (eat_spaces): If the next character pointed to + is a space, don't seek, must be at the end. + 2014-05-26 Janne Blomqvist <jb@gcc.gnu.org> Backport from mainline diff --git a/libgfortran/io/list_read.c b/libgfortran/io/list_read.c index 2e739f2dabd..93b3d3c43c5 100644 --- a/libgfortran/io/list_read.c +++ b/libgfortran/io/list_read.c @@ -271,7 +271,7 @@ eat_spaces (st_parameter_dt *dtp) if (is_array_io (dtp)) { gfc_offset offset = stell (dtp->u.p.current_unit->s); - gfc_offset limit = dtp->u.p.current_unit->bytes_left; + gfc_offset limit = offset + dtp->u.p.current_unit->bytes_left; if (dtp->common.unit) /* kind=4 */ { @@ -283,13 +283,15 @@ eat_spaces (st_parameter_dt *dtp) offset += (sizeof (gfc_char4_t)); dtp->u.p.current_unit->bytes_left--; } - while (offset < limit && (cc == (gfc_char4_t)' ' - || cc == (gfc_char4_t)'\t')); + while (offset < limit && cc == (gfc_char4_t)' '); /* Back up, seek ahead, and fall through to complete the process so that END conditions are handled correctly. */ dtp->u.p.current_unit->bytes_left++; - sseek (dtp->u.p.current_unit->s, - offset-(sizeof (gfc_char4_t)), SEEK_SET); + + cc = dtp->internal_unit[offset]; + if (cc != (gfc_char4_t)' ') + sseek (dtp->u.p.current_unit->s, + offset-(sizeof (gfc_char4_t)), SEEK_SET); } else { @@ -298,11 +300,13 @@ eat_spaces (st_parameter_dt *dtp) c = dtp->internal_unit[offset++]; dtp->u.p.current_unit->bytes_left--; } - while (offset < limit && (c == ' ' || c == '\t')); + while (offset < limit && c == ' '); /* Back up, seek ahead, and fall through to complete the process so that END conditions are handled correctly. */ dtp->u.p.current_unit->bytes_left++; - sseek (dtp->u.p.current_unit->s, offset-1, SEEK_SET); + + if (dtp->internal_unit[offset] != ' ') + sseek (dtp->u.p.current_unit->s, offset - 1, SEEK_SET); } } /* Now skip spaces, EOF and EOL are handled in next_char. */ diff --git a/libgomp/ChangeLog b/libgomp/ChangeLog index 1f14a8d5d7f..aaa7ddec68f 100644 --- a/libgomp/ChangeLog +++ b/libgomp/ChangeLog @@ -1,3 +1,21 @@ +2014-06-24 Jakub Jelinek <jakub@redhat.com> + + * testsuite/libgomp.c/for-2.c: Define SC to static for + #pragma omp for simd testing. + * testsuite/libgomp.c/for-2.h (SC): Define if not defined. + (N(f5), N(f6), N(f7), N(f8), N(f10), N(f12), N(f14)): Use + SC macro. + * testsuite/libgomp.c/simd-14.c: New test. + * testsuite/libgomp.c/simd-15.c: New test. + * testsuite/libgomp.c/simd-16.c: New test. + * testsuite/libgomp.c/simd-17.c: New test. + * testsuite/libgomp.c++/for-10.C: Define SC to static for + #pragma omp for simd testing. + * testsuite/libgomp.c++/simd10.C: New test. + * testsuite/libgomp.c++/simd11.C: New test. + * testsuite/libgomp.c++/simd12.C: New test. + * testsuite/libgomp.c++/simd13.C: New test. + 2014-05-21 Jakub Jelinek <jakub@redhat.com> PR middle-end/61252 diff --git a/libgomp/testsuite/libgomp.c++/for-10.C b/libgomp/testsuite/libgomp.c++/for-10.C index fb1a3e952b1..c67096ac92a 100644 --- a/libgomp/testsuite/libgomp.c++/for-10.C +++ b/libgomp/testsuite/libgomp.c++/for-10.C @@ -19,11 +19,14 @@ extern "C" void abort (); #undef F #undef G +#undef SC +#define SC static #define F for simd #define G f_simd #include "../libgomp.c/for-1.h" #undef F #undef G +#undef SC int main () diff --git a/libgomp/testsuite/libgomp.c++/simd10.C b/libgomp/testsuite/libgomp.c++/simd10.C new file mode 100644 index 00000000000..390e65ffea3 --- /dev/null +++ b/libgomp/testsuite/libgomp.c++/simd10.C @@ -0,0 +1,6 @@ +// { dg-do run } +// { dg-options "-O2" } +// { dg-additional-options "-msse2" { target sse2_runtime } } +// { dg-additional-options "-mavx" { target avx_runtime } } + +#include "../libgomp.c/simd-14.c" diff --git a/libgomp/testsuite/libgomp.c++/simd11.C b/libgomp/testsuite/libgomp.c++/simd11.C new file mode 100644 index 00000000000..b9668685601 --- /dev/null +++ b/libgomp/testsuite/libgomp.c++/simd11.C @@ -0,0 +1,6 @@ +// { dg-do run } +// { dg-options "-O2" } +// { dg-additional-options "-msse2" { target sse2_runtime } } +// { dg-additional-options "-mavx" { target avx_runtime } } + +#include "../libgomp.c/simd-15.c" diff --git a/libgomp/testsuite/libgomp.c++/simd12.C b/libgomp/testsuite/libgomp.c++/simd12.C new file mode 100644 index 00000000000..ecfc912aeea --- /dev/null +++ b/libgomp/testsuite/libgomp.c++/simd12.C @@ -0,0 +1,6 @@ +// { dg-do run } +// { dg-options "-O2" } +// { dg-additional-options "-msse2" { target sse2_runtime } } +// { dg-additional-options "-mavx" { target avx_runtime } } + +#include "../libgomp.c/simd-16.c" diff --git a/libgomp/testsuite/libgomp.c++/simd13.C b/libgomp/testsuite/libgomp.c++/simd13.C new file mode 100644 index 00000000000..f7496209680 --- /dev/null +++ b/libgomp/testsuite/libgomp.c++/simd13.C @@ -0,0 +1,6 @@ +// { dg-do run } +// { dg-options "-O2" } +// { dg-additional-options "-msse2" { target sse2_runtime } } +// { dg-additional-options "-mavx" { target avx_runtime } } + +#include "../libgomp.c/simd-17.c" diff --git a/libgomp/testsuite/libgomp.c/for-2.c b/libgomp/testsuite/libgomp.c/for-2.c index f5a01ab05ec..ae810087454 100644 --- a/libgomp/testsuite/libgomp.c/for-2.c +++ b/libgomp/testsuite/libgomp.c/for-2.c @@ -21,11 +21,14 @@ extern void abort (void); #undef F #undef G +#undef SC +#define SC static #define F for simd #define G f_simd #include "for-1.h" #undef F #undef G +#undef SC int main () diff --git a/libgomp/testsuite/libgomp.c/for-2.h b/libgomp/testsuite/libgomp.c/for-2.h index 57c385ec876..920d23b5202 100644 --- a/libgomp/testsuite/libgomp.c/for-2.h +++ b/libgomp/testsuite/libgomp.c/for-2.h @@ -8,6 +8,9 @@ noreturn (void) for (;;); } #endif +#ifndef SC +#define SC +#endif __attribute__((noinline, noclone)) void N(f0) (void) @@ -57,7 +60,7 @@ __attribute__((noinline, noclone)) void N(f5) (int n11, int n12, int n21, int n22, int n31, int n32, int s1, int s2, int s3) { - int v1, v2, v3; + SC int v1, v2, v3; #pragma omp F S collapse(3) for (v1 = n11; v1 < n12; v1 += s1) for (v2 = n21; v2 < n22; v2 += s2) @@ -69,8 +72,8 @@ __attribute__((noinline, noclone)) void N(f6) (int n11, int n12, int n21, int n22, long long n31, long long n32, int s1, int s2, long long int s3) { - int v1, v2; - long long v3; + SC int v1, v2; + SC long long v3; #pragma omp F S collapse(3) for (v1 = n11; v1 > n12; v1 += s1) for (v2 = n21; v2 > n22; v2 += s2) @@ -81,8 +84,8 @@ N(f6) (int n11, int n12, int n21, int n22, long long n31, long long n32, __attribute__((noinline, noclone)) void N(f7) (void) { - unsigned int v1, v3; - unsigned long long v2; + SC unsigned int v1, v3; + SC unsigned long long v2; #pragma omp F S collapse(3) for (v1 = 0; v1 < 20; v1 += 2) for (v2 = __LONG_LONG_MAX__ + 16ULL; @@ -94,7 +97,7 @@ N(f7) (void) __attribute__((noinline, noclone)) void N(f8) (void) { - long long v1, v2, v3; + SC long long v1, v2, v3; #pragma omp F S collapse(3) for (v1 = 0; v1 < 20; v1 += 2) for (v2 = 30; v2 < 20; v2++) @@ -118,7 +121,7 @@ N(f9) (void) __attribute__((noinline, noclone)) void N(f10) (void) { - int i; + SC int i; #pragma omp F S collapse(3) for (i = 0; i < 10; i++) for (int j = 10; j < 8; j++) @@ -146,7 +149,7 @@ N(f11) (int n) __attribute__((noinline, noclone)) void N(f12) (int n) { - int i; + SC int i; #pragma omp F S collapse(3) for (i = 0; i < 10; i++) for (int j = n; j < 8; j++) @@ -170,7 +173,7 @@ N(f13) (void) __attribute__((noinline, noclone)) void N(f14) (void) { - float *i; + SC float *i; #pragma omp F S collapse(3) for (i = &b[0][0][0]; i < &b[0][0][10]; i++) for (float *j = &b[0][15][0]; j > &b[0][0][0]; j -= 10) diff --git a/libgomp/testsuite/libgomp.c/simd-14.c b/libgomp/testsuite/libgomp.c/simd-14.c new file mode 100644 index 00000000000..50e8d5e9011 --- /dev/null +++ b/libgomp/testsuite/libgomp.c/simd-14.c @@ -0,0 +1,123 @@ +/* { dg-do run } */ +/* { dg-options "-O2" } */ +/* { dg-additional-options "-msse2" { target sse2_runtime } } */ +/* { dg-additional-options "-mavx" { target avx_runtime } } */ + +int +main () +{ + int i, j, b, c = 0; + i = 4; j = 4; b = 7; + #pragma omp simd linear(b:2) reduction(+:c) + for (i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + b = b + 2; + } + if (c || i != 64 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp simd linear(b:3) reduction(+:c) + for (i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + b = b + 3; + } + if (c || i != 64 || b != 7 + 16 * 3) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp simd linear(i) linear(b:2) reduction(+:c) + for (i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + b = b + 2; + } + if (c || i != 64 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp simd linear(i:4) linear(b:3) reduction(+:c) + for (i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + b = b + 3; + } + if (c || i != 64 || b != 7 + 16 * 3) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp simd collapse (2) linear(b:2) reduction(+:c) + for (i = 0; i < 8; i++) + for (j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + b = b + 2; + } + if (c || i != 8 || j != 8 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp simd collapse (2) lastprivate (i, j) linear(b:2) reduction(+:c) + for (i = 0; i < 8; i++) + for (j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + b = b + 2; + } + if (c || i != 8 || j != 8 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(b:2) reduction(+:c) + for (i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + b = b + 2; + } + if (c || i != 64 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(b:3) reduction(+:c) + for (i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + b = b + 3; + } + if (c || i != 64 || b != 7 + 16 * 3) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(i) linear(b:2) reduction(+:c) + for (i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + b = b + 2; + } + if (c || i != 64 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(i:4) linear(b:3) reduction(+:c) + for (i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + b = b + 3; + } + if (c || i != 64 || b != 7 + 16 * 3) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd lastprivate (i, j) collapse (2) schedule (static, 4) linear(b:2) reduction(+:c) + for (i = 0; i < 8; i++) + for (j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + b = b + 2; + } + if (c || i != 8 || j != 8 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd collapse (2) schedule (static, 4) linear(b:2) reduction(+:c) + for (i = 0; i < 8; i++) + for (j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + b = b + 2; + } + if (c || i != 8 || j != 8 || b != 7 + 64 * 2) + __builtin_abort (); + return 0; +} diff --git a/libgomp/testsuite/libgomp.c/simd-15.c b/libgomp/testsuite/libgomp.c/simd-15.c new file mode 100644 index 00000000000..e474b81fa44 --- /dev/null +++ b/libgomp/testsuite/libgomp.c/simd-15.c @@ -0,0 +1,129 @@ +/* { dg-do run } */ +/* { dg-options "-O2" } */ +/* { dg-additional-options "-msse2" { target sse2_runtime } } */ +/* { dg-additional-options "-mavx" { target avx_runtime } } */ + +static inline void +foo (int *b, int *i, int *j, int x) +{ + *b = *b + x + (*i - *i) + (*j - *j); +} + +int +main () +{ + int i, j, b, c = 0; + i = 4; j = 4; b = 7; + #pragma omp simd linear(b:2) reduction(+:c) + for (i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + foo (&b, &i, &j, 2); + } + if (c || i != 64 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp simd linear(b:3) reduction(+:c) + for (i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + foo (&b, &i, &j, 3); + } + if (c || i != 64 || b != 7 + 16 * 3) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp simd linear(i) linear(b:2) reduction(+:c) + for (i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + foo (&b, &i, &j, 2); + } + if (c || i != 64 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp simd linear(i:4) linear(b:3) reduction(+:c) + for (i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + foo (&b, &i, &j, 3); + } + if (c || i != 64 || b != 7 + 16 * 3) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp simd collapse (2) linear(b:2) reduction(+:c) + for (i = 0; i < 8; i++) + for (j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + foo (&b, &i, &j, 2); + } + if (c || i != 8 || j != 8 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp simd collapse (2) lastprivate (i, j) linear(b:2) reduction(+:c) + for (i = 0; i < 8; i++) + for (j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + foo (&b, &i, &j, 2); + } + if (c || i != 8 || j != 8 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(b:2) reduction(+:c) + for (i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + foo (&b, &i, &j, 2); + } + if (c || i != 64 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(b:3) reduction(+:c) + for (i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + foo (&b, &i, &j, 3); + } + if (c || i != 64 || b != 7 + 16 * 3) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(i) linear(b:2) reduction(+:c) + for (i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + foo (&b, &i, &j, 2); + } + if (c || i != 64 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(i:4) linear(b:3) reduction(+:c) + for (i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + foo (&b, &i, &j, 3); + } + if (c || i != 64 || b != 7 + 16 * 3) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd lastprivate (i, j) collapse (2) schedule (static, 4) linear(b:2) reduction(+:c) + for (i = 0; i < 8; i++) + for (j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + foo (&b, &i, &j, 2); + } + if (c || i != 8 || j != 8 || b != 7 + 64 * 2) + __builtin_abort (); + i = 4; j = 4; b = 7; + #pragma omp parallel for simd collapse (2) schedule (static, 4) linear(b:2) reduction(+:c) + for (i = 0; i < 8; i++) + for (j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + foo (&b, &i, &j, 2); + } + if (c || i != 8 || j != 8 || b != 7 + 64 * 2) + __builtin_abort (); + return 0; +} diff --git a/libgomp/testsuite/libgomp.c/simd-16.c b/libgomp/testsuite/libgomp.c/simd-16.c new file mode 100644 index 00000000000..c8c29c744d7 --- /dev/null +++ b/libgomp/testsuite/libgomp.c/simd-16.c @@ -0,0 +1,67 @@ +/* { dg-do run } */ +/* { dg-options "-O2 -std=c99" } */ +/* { dg-additional-options "-msse2" { target sse2_runtime } } */ +/* { dg-additional-options "-mavx" { target avx_runtime } } */ + +int +main () +{ + int b, c = 0; + b = 7; + #pragma omp simd linear(b:2) reduction(+:c) + for (int i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + b = b + 2; + } + if (c || b != 7 + 64 * 2) + __builtin_abort (); + b = 7; + #pragma omp simd linear(b:3) reduction(+:c) + for (int i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + b = b + 3; + } + if (c || b != 7 + 16 * 3) + __builtin_abort (); + b = 7; + #pragma omp simd collapse (2) linear(b:2) reduction(+:c) + for (int i = 0; i < 8; i++) + for (int j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + b = b + 2; + } + if (c || b != 7 + 64 * 2) + __builtin_abort (); + b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(b:2) reduction(+:c) + for (int i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + b = b + 2; + } + if (c || b != 7 + 64 * 2) + __builtin_abort (); + b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(b:3) reduction(+:c) + for (int i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + b = b + 3; + } + if (c || b != 7 + 16 * 3) + __builtin_abort (); + b = 7; + #pragma omp parallel for simd collapse (2) schedule (static, 4) linear(b:2) reduction(+:c) + for (int i = 0; i < 8; i++) + for (int j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + b = b + 2; + } + if (c || b != 7 + 64 * 2) + __builtin_abort (); + return 0; +} diff --git a/libgomp/testsuite/libgomp.c/simd-17.c b/libgomp/testsuite/libgomp.c/simd-17.c new file mode 100644 index 00000000000..136e6e64ade --- /dev/null +++ b/libgomp/testsuite/libgomp.c/simd-17.c @@ -0,0 +1,73 @@ +/* { dg-do run } */ +/* { dg-options "-O2 -std=c99" } */ +/* { dg-additional-options "-msse2" { target sse2_runtime } } */ +/* { dg-additional-options "-mavx" { target avx_runtime } } */ + +static inline void +foo (int *b, int *i, int *j, int x) +{ + *b = *b + x + (*i - *i) + (*j - *j); +} + +int +main () +{ + int b, c = 0; + b = 7; + #pragma omp simd linear(b:2) reduction(+:c) + for (int i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + foo (&b, &i, &i, 2); + } + if (c || b != 7 + 64 * 2) + __builtin_abort (); + b = 7; + #pragma omp simd linear(b:3) reduction(+:c) + for (int i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + foo (&b, &i, &i, 3); + } + if (c || b != 7 + 16 * 3) + __builtin_abort (); + b = 7; + #pragma omp simd collapse (2) linear(b:2) reduction(+:c) + for (int i = 0; i < 8; i++) + for (int j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + foo (&b, &i, &j, 2); + } + if (c || b != 7 + 64 * 2) + __builtin_abort (); + b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(b:2) reduction(+:c) + for (int i = 0; i < 64; i++) + { + c = c + (b != 7 + 2 * i); + foo (&b, &i, &i, 2); + } + if (c || b != 7 + 64 * 2) + __builtin_abort (); + b = 7; + #pragma omp parallel for simd schedule (static, 4) linear(b:3) reduction(+:c) + for (int i = 0; i < 64; i += 4) + { + c = c + (b != 7 + i / 4 * 3); + foo (&b, &i, &i, 3); + } + if (c || b != 7 + 16 * 3) + __builtin_abort (); + b = 7; + #pragma omp parallel for simd collapse (2) schedule (static, 4) linear(b:2) reduction(+:c) + for (int i = 0; i < 8; i++) + for (int j = 0; j < 8; j++) + { + c = c + (b != 7 + 2 * j + 2 * 8 * i); + foo (&b, &i, &j, 2); + } + if (c || b != 7 + 64 * 2) + __builtin_abort (); + return 0; +} diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog index 31b4ab41798..7662fa12fb0 100644 --- a/libstdc++-v3/ChangeLog +++ b/libstdc++-v3/ChangeLog @@ -1,3 +1,84 @@ +2014-06-23 Jonathan Wakely <jwakely@redhat.com> + + PR libstdc++/61532 + * testsuite/20_util/make_signed/requirements/typedefs-1.cc: Do not + apply the signed specifier to wchar_t. + * testsuite/20_util/make_signed/requirements/typedefs-2.cc: Likewise. + * testsuite/20_util/make_unsigned/requirements/typedefs-1.cc: Do not + apply the unsigned specifier to wchar_t. + * testsuite/20_util/make_unsigned/requirements/typedefs-2.cc: + Likewise. + +2014-06-13 Jonathan Wakely <jwakely@redhat.com> + + Backport from mainline + PR libstdc++/60326 + * include/std/type_traits (__make_unsigned, __make_signed): Define + specializations for wchar_t, char16_t and char32_t. + * testsuite/20_util/make_signed/requirements/typedefs-4.cc: New. + * testsuite/20_util/make_unsigned/requirements/typedefs-1.cc: Correct + test for make_unsigned<volatile wchar_t>. + * testsuite/20_util/make_unsigned/requirements/typedefs-2.cc: + Likewise. + * testsuite/20_util/declval/requirements/1_neg.cc: Adjust dg-error + line number. + * testsuite/20_util/make_signed/requirements/typedefs_neg.cc: + Likewise. + * testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc: + Likewise. + + Backport from mainline + PR libstdc++/61269 + * include/std/type_traits: Move include outside namespace std. + * testsuite/20_util/declval/requirements/1_neg.cc: Adjust dg-error. + * testsuite/20_util/make_signed/requirements/typedefs_neg.cc: Likewise. + * testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc: + Likewise. + + * include/std/tuple (tuple_size<cv _Tp>): Implement LWG 2313. + (get<_Tp>(tuple<_Types...>&&)): Use forward instead of move. + * testsuite/20_util/tuple/element_access/get_by_type.cc: Test rvalues. + +2014-06-07 Ed Smith-Rowland <3dw4rd@verizon.net> + + Backport from mainline + DR 2344 - std::quoted doesn't respect padding + * include/std/iomanip: Allow for padding in quoted inserters. + * testsuite/27_io/manipulators/standard/char/dr2344.cc: New. + * testsuite/27_io/manipulators/standard/wchar_t/dr2344.cc: New. + +2014-06-03 Jonathan Wakely <jwakely@redhat.com> + + * include/bits/regex_executor.tcc (_Executor<>::_M_main): Move instead + of copying. + +2014-06-03 Jonathan Wakely <jwakely@redhat.com> + + Backport from mainline + 2014-04-15 Jonathan Wakely <jwakely@redhat.com> + + PR libstdc++/60734 + * include/bits/stl_tree.h (_Rb_tree::_M_end): Fix invalid cast. + + Backport from mainline + 2014-04-24 Tim Shen <timshen91@gmail.com> + + * include/bits/regex_automaton.tcc (_StateSeq<>::_M_clone()): + Do _M_alt before _M_next. + * testsuite/28_regex/basic_regex/multiple_quantifiers.cc: Add testcases. + + Backport from mainline + 2014-05-20 Tim Shen <timshen91@gmail.com> + + PR libstdc++/61227 + * include/bits/regex_compiler.h + (_BracketMatcher<>::_M_add_character_class): Add negative character + class support. + * include/bits/regex_compiler.tcc (_BracketMatcher<>::_M_apply): + Likewise. + * testsuite/28_regex/algorithms/regex_match/ecma/char/quoted_char.cc: + Add more testcases. + 2014-05-29 Jonathan Wakely <jwakely@redhat.com> * include/tr2/bool_set: Use UTF-8 for accented characters. diff --git a/libstdc++-v3/include/bits/regex_automaton.tcc b/libstdc++-v3/include/bits/regex_automaton.tcc index 1a5bf08026f..6e68fca82f1 100644 --- a/libstdc++-v3/include/bits/regex_automaton.tcc +++ b/libstdc++-v3/include/bits/regex_automaton.tcc @@ -197,20 +197,18 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION // _M_insert_state() never return -1 auto __id = _M_nfa._M_insert_state(__dup); __m[__u] = __id; - if (__u == _M_end) - continue; - if (__dup._M_next != _S_invalid_state_id && __m[__dup._M_next] == -1) - __stack.push(__dup._M_next); if (__dup._M_opcode == _S_opcode_alternative || __dup._M_opcode == _S_opcode_subexpr_lookahead) if (__dup._M_alt != _S_invalid_state_id && __m[__dup._M_alt] == -1) __stack.push(__dup._M_alt); + if (__u == _M_end) + continue; + if (__dup._M_next != _S_invalid_state_id && __m[__dup._M_next] == -1) + __stack.push(__dup._M_next); } - long __size = static_cast<long>(__m.size()); - for (long __k = 0; __k < __size; __k++) + for (auto __v : __m) { - long __v; - if ((__v = __m[__k]) == -1) + if (__v == -1) continue; auto& __ref = _M_nfa[__v]; if (__ref._M_next != _S_invalid_state_id) diff --git a/libstdc++-v3/include/bits/regex_compiler.h b/libstdc++-v3/include/bits/regex_compiler.h index f5a198f65e9..af76f55054a 100644 --- a/libstdc++-v3/include/bits/regex_compiler.h +++ b/libstdc++-v3/include/bits/regex_compiler.h @@ -369,15 +369,19 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION #endif } + // __neg should be true for \D, \S and \W only. void - _M_add_character_class(const _StringT& __s) + _M_add_character_class(const _StringT& __s, bool __neg) { auto __mask = _M_traits.lookup_classname(__s.data(), __s.data() + __s.size(), __icase); if (__mask == 0) __throw_regex_error(regex_constants::error_ctype); - _M_class_set |= __mask; + if (!__neg) + _M_class_set |= __mask; + else + _M_neg_class_set.push_back(__mask); #ifdef _GLIBCXX_DEBUG _M_is_ready = false; #endif @@ -387,7 +391,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION _M_make_range(_CharT __l, _CharT __r) { _M_range_set.push_back(make_pair(_M_translator._M_transform(__l), - _M_translator._M_transform(__r))); + _M_translator._M_transform(__r))); #ifdef _GLIBCXX_DEBUG _M_is_ready = false; #endif @@ -435,6 +439,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION std::vector<_CharT> _M_char_set; std::vector<_StringT> _M_equiv_set; std::vector<pair<_StrTransT, _StrTransT>> _M_range_set; + std::vector<_CharClassT> _M_neg_class_set; _CharClassT _M_class_set; _TransT _M_translator; const _TraitsT& _M_traits; diff --git a/libstdc++-v3/include/bits/regex_compiler.tcc b/libstdc++-v3/include/bits/regex_compiler.tcc index 128dac12bd7..14e40c0cd19 100644 --- a/libstdc++-v3/include/bits/regex_compiler.tcc +++ b/libstdc++-v3/include/bits/regex_compiler.tcc @@ -397,7 +397,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION _GLIBCXX_DEBUG_ASSERT(_M_value.size() == 1); _BracketMatcher<_TraitsT, __icase, __collate> __matcher (_M_ctype.is(_CtypeT::upper, _M_value[0]), _M_traits); - __matcher._M_add_character_class(_M_value); + __matcher._M_add_character_class(_M_value, false); __matcher._M_ready(); _M_stack.push(_StateSeqT(_M_nfa, _M_nfa._M_insert_matcher(std::move(__matcher)))); @@ -428,7 +428,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION else if (_M_match_token(_ScannerT::_S_token_equiv_class_name)) __matcher._M_add_equivalence_class(_M_value); else if (_M_match_token(_ScannerT::_S_token_char_class_name)) - __matcher._M_add_character_class(_M_value); + __matcher._M_add_character_class(_M_value, false); else if (_M_try_char()) // [a { auto __ch = _M_value[0]; @@ -451,6 +451,10 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION } __matcher._M_add_char(__ch); } + else if (_M_match_token(_ScannerT::_S_token_quoted_class)) + __matcher._M_add_character_class(_M_value, + _M_ctype.is(_CtypeT::upper, + _M_value[0])); else __throw_regex_error(regex_constants::error_brack); } @@ -527,6 +531,15 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION _M_traits.transform_primary(&__ch, &__ch+1)) != _M_equiv_set.end()) __ret = true; + else + { + for (auto& __it : _M_neg_class_set) + if (!_M_traits.isctype(__ch, __it)) + { + __ret = true; + break; + } + } } if (_M_is_non_matching) return !__ret; diff --git a/libstdc++-v3/include/bits/regex_executor.tcc b/libstdc++-v3/include/bits/regex_executor.tcc index 68a5e0490f9..052302b91f7 100644 --- a/libstdc++-v3/include/bits/regex_executor.tcc +++ b/libstdc++-v3/include/bits/regex_executor.tcc @@ -120,10 +120,10 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION if (_M_match_queue->empty()) break; _M_visited->assign(_M_visited->size(), false); - auto _M_old_queue = std::move(*_M_match_queue); - for (auto __task : _M_old_queue) + auto __old_queue = std::move(*_M_match_queue); + for (auto& __task : __old_queue) { - _M_cur_results = __task.second; + _M_cur_results = std::move(__task.second); _M_dfs<__match_mode>(__task.first); } if (!__match_mode) diff --git a/libstdc++-v3/include/bits/stl_tree.h b/libstdc++-v3/include/bits/stl_tree.h index cac917ea35b..ce43ab84686 100644 --- a/libstdc++-v3/include/bits/stl_tree.h +++ b/libstdc++-v3/include/bits/stl_tree.h @@ -526,11 +526,11 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION _Link_type _M_end() _GLIBCXX_NOEXCEPT - { return static_cast<_Link_type>(&this->_M_impl._M_header); } + { return reinterpret_cast<_Link_type>(&this->_M_impl._M_header); } _Const_Link_type _M_end() const _GLIBCXX_NOEXCEPT - { return static_cast<_Const_Link_type>(&this->_M_impl._M_header); } + { return reinterpret_cast<_Const_Link_type>(&this->_M_impl._M_header); } static const_reference _S_value(_Const_Link_type __x) diff --git a/libstdc++-v3/include/std/iomanip b/libstdc++-v3/include/std/iomanip index 73822db9b20..cc6f60cdeeb 100644 --- a/libstdc++-v3/include/std/iomanip +++ b/libstdc++-v3/include/std/iomanip @@ -41,6 +41,9 @@ #if __cplusplus >= 201103L #include <locale> +#if __cplusplus > 201103L +#include <sstream> // used in quoted. +#endif #endif namespace std _GLIBCXX_VISIBILITY(default) @@ -342,7 +345,6 @@ _GLIBCXX_END_NAMESPACE_VERSION /** * @brief Struct for delimited strings. - * The left and right delimiters can be different. */ template<typename _String, typename _CharT> struct _Quoted_string @@ -364,45 +366,51 @@ _GLIBCXX_END_NAMESPACE_VERSION }; /** - * @brief Inserter for delimited strings. - * The left and right delimiters can be different. + * @brief Inserter for quoted strings. + * + * _GLIBCXX_RESOLVE_LIB_DEFECTS + * DR 2344 quoted()'s interaction with padding is unclear */ template<typename _CharT, typename _Traits> auto& operator<<(std::basic_ostream<_CharT, _Traits>& __os, const _Quoted_string<const _CharT*, _CharT>& __str) { - __os << __str._M_delim; + std::basic_ostringstream<_CharT, _Traits> __ostr; + __ostr << __str._M_delim; for (const _CharT* __c = __str._M_string; *__c; ++__c) { if (*__c == __str._M_delim || *__c == __str._M_escape) - __os << __str._M_escape; - __os << *__c; + __ostr << __str._M_escape; + __ostr << *__c; } - __os << __str._M_delim; + __ostr << __str._M_delim; - return __os; + return __os << __ostr.str(); } /** - * @brief Inserter for delimited strings. - * The left and right delimiters can be different. + * @brief Inserter for quoted strings. + * + * _GLIBCXX_RESOLVE_LIB_DEFECTS + * DR 2344 quoted()'s interaction with padding is unclear */ template<typename _CharT, typename _Traits, typename _String> auto& operator<<(std::basic_ostream<_CharT, _Traits>& __os, const _Quoted_string<_String, _CharT>& __str) { - __os << __str._M_delim; + std::basic_ostringstream<_CharT, _Traits> __ostr; + __ostr << __str._M_delim; for (auto& __c : __str._M_string) { if (__c == __str._M_delim || __c == __str._M_escape) - __os << __str._M_escape; - __os << __c; + __ostr << __str._M_escape; + __ostr << __c; } - __os << __str._M_delim; + __ostr << __str._M_delim; - return __os; + return __os << __ostr.str(); } /** diff --git a/libstdc++-v3/include/std/tuple b/libstdc++-v3/include/std/tuple index 03d87d77aa0..103c99e066e 100644 --- a/libstdc++-v3/include/std/tuple +++ b/libstdc++-v3/include/std/tuple @@ -719,23 +719,19 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION template<typename _Tp> struct tuple_size; + // _GLIBCXX_RESOLVE_LIB_DEFECTS + // 2313. tuple_size should always derive from integral_constant<size_t, N> template<typename _Tp> struct tuple_size<const _Tp> - : public integral_constant< - typename remove_cv<decltype(tuple_size<_Tp>::value)>::type, - tuple_size<_Tp>::value> { }; + : public integral_constant<size_t, tuple_size<_Tp>::value> { }; template<typename _Tp> struct tuple_size<volatile _Tp> - : public integral_constant< - typename remove_cv<decltype(tuple_size<_Tp>::value)>::type, - tuple_size<_Tp>::value> { }; + : public integral_constant<size_t, tuple_size<_Tp>::value> { }; template<typename _Tp> struct tuple_size<const volatile _Tp> - : public integral_constant< - typename remove_cv<decltype(tuple_size<_Tp>::value)>::type, - tuple_size<_Tp>::value> { }; + : public integral_constant<size_t, tuple_size<_Tp>::value> { }; /// class tuple_size template<typename... _Elements> @@ -752,9 +748,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION __get_helper(const _Tuple_impl<__i, _Head, _Tail...>& __t) noexcept { return _Tuple_impl<__i, _Head, _Tail...>::_M_head(__t); } - // Return a reference (const reference, rvalue reference) to the ith element - // of a tuple. Any const or non-const ref elements are returned with their - // original type. + /// Return a reference to the ith element of a tuple. template<std::size_t __i, typename... _Elements> constexpr typename __add_ref< typename tuple_element<__i, tuple<_Elements...>>::type @@ -762,6 +756,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION get(tuple<_Elements...>& __t) noexcept { return std::__get_helper<__i>(__t); } + /// Return a const reference to the ith element of a const tuple. template<std::size_t __i, typename... _Elements> constexpr typename __add_c_ref< typename tuple_element<__i, tuple<_Elements...>>::type @@ -769,6 +764,7 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION get(const tuple<_Elements...>& __t) noexcept { return std::__get_helper<__i>(__t); } + /// Return an rvalue reference to the ith element of a tuple rvalue. template<std::size_t __i, typename... _Elements> constexpr typename __add_r_ref< typename tuple_element<__i, tuple<_Elements...>>::type @@ -788,22 +784,26 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION __get_helper2(const _Tuple_impl<__i, _Head, _Tail...>& __t) noexcept { return _Tuple_impl<__i, _Head, _Tail...>::_M_head(__t); } + /// Return a reference to the unique element of type _Tp of a tuple. template <typename _Tp, typename... _Types> constexpr _Tp& get(tuple<_Types...>& __t) noexcept { return std::__get_helper2<_Tp>(__t); } + /// Return a reference to the unique element of type _Tp of a tuple rvalue. template <typename _Tp, typename... _Types> constexpr _Tp&& get(tuple<_Types...>&& __t) noexcept - { return std::move(std::__get_helper2<_Tp>(__t)); } + { return std::forward<_Tp&&>(std::__get_helper2<_Tp>(__t)); } + /// Return a const reference to the unique element of type _Tp of a tuple. template <typename _Tp, typename... _Types> constexpr const _Tp& get(const tuple<_Types...>& __t) noexcept { return std::__get_helper2<_Tp>(__t); } #endif + // This class helps construct the various comparison operations on tuples template<std::size_t __check_equal_size, std::size_t __i, std::size_t __j, typename _Tp, typename _Up> diff --git a/libstdc++-v3/include/std/type_traits b/libstdc++-v3/include/std/type_traits index 4b434a6025b..1ff2e625a73 100644 --- a/libstdc++-v3/include/std/type_traits +++ b/libstdc++-v3/include/std/type_traits @@ -37,6 +37,18 @@ #include <bits/c++config.h> +#ifdef _GLIBCXX_USE_C99_STDINT_TR1 +# if defined (__UINT_LEAST16_TYPE__) && defined(__UINT_LEAST32_TYPE__) +namespace std +{ + typedef __UINT_LEAST16_TYPE__ uint_least16_t; + typedef __UINT_LEAST32_TYPE__ uint_least32_t; +} +# else +# include <cstdint> +# endif +#endif + namespace std _GLIBCXX_VISIBILITY(default) { _GLIBCXX_BEGIN_NAMESPACE_VERSION @@ -1583,6 +1595,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION struct __make_unsigned<long long> { typedef unsigned long long __type; }; +#if defined(_GLIBCXX_USE_WCHAR_T) && !defined(__WCHAR_UNSIGNED__) + template<> + struct __make_unsigned<wchar_t> : __make_unsigned<__WCHAR_TYPE__> + { }; +#endif + #if !defined(__STRICT_ANSI__) && defined(_GLIBCXX_USE_INT128) template<> struct __make_unsigned<__int128> @@ -1665,6 +1683,21 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION struct __make_signed<unsigned long long> { typedef signed long long __type; }; +#if defined(_GLIBCXX_USE_WCHAR_T) && defined(__WCHAR_UNSIGNED__) + template<> + struct __make_signed<wchar_t> : __make_signed<__WCHAR_TYPE__> + { }; +#endif + +#ifdef _GLIBCXX_USE_C99_STDINT_TR1 + template<> + struct __make_signed<char16_t> : __make_signed<uint_least16_t> + { }; + template<> + struct __make_signed<char32_t> : __make_signed<uint_least32_t> + { }; +#endif + #if !defined(__STRICT_ANSI__) && defined(_GLIBCXX_USE_INT128) template<> struct __make_signed<unsigned __int128> diff --git a/libstdc++-v3/testsuite/20_util/declval/requirements/1_neg.cc b/libstdc++-v3/testsuite/20_util/declval/requirements/1_neg.cc index a744d832637..04e6b711906 100644 --- a/libstdc++-v3/testsuite/20_util/declval/requirements/1_neg.cc +++ b/libstdc++-v3/testsuite/20_util/declval/requirements/1_neg.cc @@ -19,7 +19,7 @@ // with this library; see the file COPYING3. If not see // <http://www.gnu.org/licenses/>. -// { dg-error "static assertion failed" "" { target *-*-* } 2003 } +// { dg-error "static assertion failed" "" { target *-*-* } 2036 } #include <utility> diff --git a/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-1.cc b/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-1.cc index e3b84d649aa..5b094d9a4f9 100644 --- a/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-1.cc +++ b/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-1.cc @@ -29,6 +29,7 @@ void test01() using std::make_signed; using std::is_same; using std::is_signed; + using std::is_volatile; // Positive tests. typedef make_signed<const int>::type test2_type; @@ -53,7 +54,9 @@ void test01() #ifdef _GLIBCXX_USE_WCHAR_T typedef make_signed<volatile wchar_t>::type test23_type; - static_assert( is_same<test23_type, volatile signed wchar_t>::value, + static_assert( is_signed<test23_type>::value + && is_volatile<test23_type>::value + && sizeof(test23_type) == sizeof(volatile wchar_t), "make_signed<volatile wchar_t>" ); #endif diff --git a/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-2.cc b/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-2.cc index 654b3759ca0..3f47dba5bf0 100644 --- a/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-2.cc +++ b/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-2.cc @@ -30,6 +30,8 @@ void test01() { using std::make_signed; using std::is_same; + using std::is_signed; + using std::is_volatile; // Positive tests. typedef make_signed<const int>::type test2_type; @@ -50,7 +52,9 @@ void test01() #ifdef _GLIBCXX_USE_WCHAR_T typedef make_signed<volatile wchar_t>::type test23_type; - static_assert(is_same<test23_type, volatile signed wchar_t>::value, ""); + static_assert(is_signed<test23_type>::value + && is_volatile<test23_type>::value + && sizeof(test23_type) == sizeof(volatile wchar_t), ""); #endif typedef make_signed<test_enum>::type test24_type; diff --git a/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-4.cc b/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-4.cc new file mode 100644 index 00000000000..4950e5470cd --- /dev/null +++ b/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs-4.cc @@ -0,0 +1,33 @@ +// { dg-options "-std=gnu++11" } +// { dg-do compile } +// { dg-require-cstdint "" } + +// Copyright (C) 2014 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library is free +// software; you can redistribute it and/or modify it under the +// terms of the GNU General Public License as published by the +// Free Software Foundation; either version 3, or (at your option) +// any later version. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License along +// with this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +#include <type_traits> + +// libstdc++/60326 + +using namespace std; +#ifdef _GLIBCXX_USE_WCHAR_T +using wchar_signed = make_signed<wchar_t>::type; +using wchar_unsigned = make_unsigned<wchar_t>::type; +static_assert( !is_same<wchar_signed, wchar_unsigned>::value, "wchar_t" ); +#endif +static_assert( is_signed<make_signed<char16_t>::type>::value, "char16_t"); +static_assert( is_signed<make_signed<char32_t>::type>::value, "char32_t"); diff --git a/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs_neg.cc b/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs_neg.cc index 9f155ea92e2..d711546050d 100644 --- a/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs_neg.cc +++ b/libstdc++-v3/testsuite/20_util/make_signed/requirements/typedefs_neg.cc @@ -48,5 +48,5 @@ void test01() // { dg-error "required from here" "" { target *-*-* } 40 } // { dg-error "required from here" "" { target *-*-* } 42 } -// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1714 } -// { dg-error "declaration of" "" { target *-*-* } 1678 } +// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1747 } +// { dg-error "declaration of" "" { target *-*-* } 1711 } diff --git a/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs-1.cc b/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs-1.cc index f07cf4a621b..de655048fdf 100644 --- a/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs-1.cc +++ b/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs-1.cc @@ -29,6 +29,7 @@ void test01() using std::make_unsigned; using std::is_same; using std::is_unsigned; + using std::is_volatile; // Positive tests. typedef make_unsigned<const unsigned int>::type test2_type; @@ -49,7 +50,9 @@ void test01() #ifdef _GLIBCXX_USE_WCHAR_T typedef make_unsigned<volatile wchar_t>::type test23_type; - static_assert(is_same<test23_type, volatile wchar_t>::value, ""); + static_assert(is_unsigned<test23_type>::value + && is_volatile<test23_type>::value + && sizeof(test23_type) == sizeof(volatile wchar_t), ""); #endif // Chapter 48, chapter 20. Smallest rank such that new unsigned type diff --git a/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs-2.cc b/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs-2.cc index 8997fb7d812..7801dca94c5 100644 --- a/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs-2.cc +++ b/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs-2.cc @@ -30,6 +30,8 @@ void test01() { using std::make_unsigned; using std::is_same; + using std::is_unsigned; + using std::is_volatile; // Positive tests. typedef make_unsigned<const unsigned int>::type test2_type; @@ -50,7 +52,9 @@ void test01() #ifdef _GLIBCXX_USE_WCHAR_T typedef make_unsigned<volatile wchar_t>::type test23_type; - static_assert(is_same<test23_type, volatile wchar_t>::value, ""); + static_assert(is_unsigned<test23_type>::value + && is_volatile<test23_type>::value + && sizeof(test23_type) == sizeof(volatile wchar_t), ""); #endif typedef make_unsigned<test_enum>::type test24_type; diff --git a/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc b/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc index 57a5c616714..c77205be01d 100644 --- a/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc +++ b/libstdc++-v3/testsuite/20_util/make_unsigned/requirements/typedefs_neg.cc @@ -48,5 +48,5 @@ void test01() // { dg-error "required from here" "" { target *-*-* } 40 } // { dg-error "required from here" "" { target *-*-* } 42 } -// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1632 } -// { dg-error "declaration of" "" { target *-*-* } 1596 } +// { dg-error "invalid use of incomplete type" "" { target *-*-* } 1650 } +// { dg-error "declaration of" "" { target *-*-* } 1614 } diff --git a/libstdc++-v3/testsuite/20_util/tuple/element_access/get_by_type.cc b/libstdc++-v3/testsuite/20_util/tuple/element_access/get_by_type.cc index 226e9e4a89c..042f2149a0d 100644 --- a/libstdc++-v3/testsuite/20_util/tuple/element_access/get_by_type.cc +++ b/libstdc++-v3/testsuite/20_util/tuple/element_access/get_by_type.cc @@ -41,4 +41,8 @@ main() get<1>(b)=5; VERIFY(get<int>(b)==1 && get<int&>(b)==5 && get<const int&>(b)==2); VERIFY(j==5); + // test rvalue overload: + VERIFY(get<int>(std::move(b))==1); + VERIFY(get<int&>(std::move(b))==5); + VERIFY(get<const int&>(std::move(b))==2); } diff --git a/libstdc++-v3/testsuite/27_io/manipulators/standard/char/dr2344.cc b/libstdc++-v3/testsuite/27_io/manipulators/standard/char/dr2344.cc new file mode 100644 index 00000000000..e220d35b2be --- /dev/null +++ b/libstdc++-v3/testsuite/27_io/manipulators/standard/char/dr2344.cc @@ -0,0 +1,50 @@ +// { dg-do run } +// { dg-options "-std=gnu++14" } + +// Copyright (C) 2014 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library is free +// software; you can redistribute it and/or modify it under the +// terms of the GNU General Public License as published by the +// Free Software Foundation; either version 3, or (at your option) +// any later version. + +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License along +// with this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// 27.7.6 - Quoted manipulators [quoted.manip] + +#include <sstream> +#include <iomanip> +#include <testsuite_hooks.h> + +void +test01() +{ + bool test [[gnu::unused]] = true; + + std::ostringstream ssx; + ssx << "[" << std::left << std::setfill('x') << std::setw(20) << R"("AB \"CD\" EF")" << "]"; + VERIFY( ssx.str() == R"(["AB \"CD\" EF"xxxxxx])" ); + + std::ostringstream ssy; + ssy << "[" << std::left << std::setfill('y') << std::setw(20) << std::quoted(R"(GH "IJ" KL)") << "]"; + VERIFY( ssy.str() == R"(["GH \"IJ\" KL"yyyyyy])" ); + + std::ostringstream ssz; + ssz << "[" << std::right << std::setfill('z') << std::setw(20) << std::quoted(R"(PQ "RS" TU)") << "]"; + VERIFY( ssz.str() == R"([zzzzzz"PQ \"RS\" TU"])" ); +} + +int +main() +{ + test01(); + return 0; +} diff --git a/libstdc++-v3/testsuite/27_io/manipulators/standard/wchar_t/dr2344.cc b/libstdc++-v3/testsuite/27_io/manipulators/standard/wchar_t/dr2344.cc new file mode 100644 index 00000000000..5bdabacc2f5 --- /dev/null +++ b/libstdc++-v3/testsuite/27_io/manipulators/standard/wchar_t/dr2344.cc @@ -0,0 +1,50 @@ +// { dg-do run } +// { dg-options "-std=gnu++14" } + +// Copyright (C) 2014 Free Software Foundation, Inc. +// +// This file is part of the GNU ISO C++ Library. This library is free +// software; you can redistribute it and/or modify it under the +// terms of the GNU General Public License as published by the +// Free Software Foundation; either version 3, or (at your option) +// any later version. + +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. + +// You should have received a copy of the GNU General Public License along +// with this library; see the file COPYING3. If not see +// <http://www.gnu.org/licenses/>. + +// 27.7.6 - Quoted manipulators [quoted.manip] + +#include <sstream> +#include <iomanip> +#include <testsuite_hooks.h> + +void +test01() +{ + bool test [[gnu::unused]] = true; + + std::wostringstream ssx; + ssx << L"[" << std::left << std::setfill(L'x') << std::setw(20) << LR"("AB \"CD\" EF")" << L"]"; + VERIFY( ssx.str() == LR"(["AB \"CD\" EF"xxxxxx])" ); + + std::wostringstream ssy; + ssy << L"[" << std::left << std::setfill(L'y') << std::setw(20) << std::quoted(LR"(GH "IJ" KL)") << L"]"; + VERIFY( ssy.str() == LR"(["GH \"IJ\" KL"yyyyyy])" ); + + std::wostringstream ssz; + ssz << L"[" << std::right << std::setfill(L'z') << std::setw(20) << std::quoted(LR"(PQ "RS" TU)") << L"]"; + VERIFY( ssz.str() == LR"([zzzzzz"PQ \"RS\" TU"])" ); +} + +int +main() +{ + test01(); + return 0; +} diff --git a/libstdc++-v3/testsuite/28_regex/algorithms/regex_match/ecma/char/quoted_char.cc b/libstdc++-v3/testsuite/28_regex/algorithms/regex_match/ecma/char/quoted_char.cc index e7280acbdbd..86417323516 100644 --- a/libstdc++-v3/testsuite/28_regex/algorithms/regex_match/ecma/char/quoted_char.cc +++ b/libstdc++-v3/testsuite/28_regex/algorithms/regex_match/ecma/char/quoted_char.cc @@ -44,6 +44,16 @@ test01() VERIFY(regex_match_debug("_az", regex("\\w*"))); VERIFY(regex_match_debug("!@#$%", regex("\\W*"))); VERIFY(!regex_match_debug("_01234", regex("\\W*"))); + + VERIFY(regex_match_debug("01", regex("[\\d]*"))); + VERIFY(regex_match_debug("asdfjkl", regex("[\\D]*"))); + VERIFY(!regex_match_debug("asdfjkl0", regex("[\\D]*"))); + VERIFY(regex_match_debug("\r\t\v\f ", regex("[\\s]*"))); + VERIFY(regex_match_debug("asdfjkl", regex("[\\S]*"))); + VERIFY(!regex_match_debug("asdfjkl\r", regex("[\\S]*"))); + VERIFY(regex_match_debug("_az", regex("[\\w]*"))); + VERIFY(regex_match_debug("!@#$%", regex("[\\W]*"))); + VERIFY(!regex_match_debug("_01234", regex("[\\W]*"))); } int diff --git a/libstdc++-v3/testsuite/28_regex/basic_regex/multiple_quantifiers.cc b/libstdc++-v3/testsuite/28_regex/basic_regex/multiple_quantifiers.cc index 5670cbb8e3b..8243eea930a 100644 --- a/libstdc++-v3/testsuite/28_regex/basic_regex/multiple_quantifiers.cc +++ b/libstdc++-v3/testsuite/28_regex/basic_regex/multiple_quantifiers.cc @@ -21,7 +21,10 @@ // Tests multiple consecutive quantifiers #include <regex> +#include <testsuite_hooks.h> +#include <testsuite_regex.h> +using namespace __gnu_test; using namespace std; int @@ -29,5 +32,6 @@ main() { regex re1("a++"); regex re2("(a+)+"); + VERIFY(regex_match_debug("aa", regex("(a)*{3}"))); return 0; } |