diff options
author | Ian Lance Taylor <ian@gcc.gnu.org> | 2017-09-20 03:42:56 +0000 |
---|---|---|
committer | Ian Lance Taylor <ian@gcc.gnu.org> | 2017-09-20 03:42:56 +0000 |
commit | e91ee0faa811b6cae44d146aa16c379797ad191e (patch) | |
tree | 794215d28861c475d4faa92a4ee00bf5ca51f43e | |
parent | d2b4864f55092b342dae9f2d147939f7ce08dfdc (diff) | |
parent | 8fca13953b551bb75af0a31d737a297de97676a7 (diff) | |
download | gcc-e91ee0faa811b6cae44d146aa16c379797ad191e.zip gcc-e91ee0faa811b6cae44d146aa16c379797ad191e.tar.gz gcc-e91ee0faa811b6cae44d146aa16c379797ad191e.tar.bz2 |
Merge from trunk revision 252991.
From-SVN: r252993
50 files changed, 949 insertions, 262 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 2267d2e..9576c8c 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,59 @@ +2017-09-19 Uros Bizjak <ubizjak@gmail.com> + + * config/i386/i386.md (*scc_bt<mode>): New insn_and_split pattern. + (*scc_bt<mode>_1): Ditto. + (*scc_bt<mode>_mask): Ditto. + +2017-09-19 Uros Bizjak <ubizjak@gmail.com> + + * config/i386/i386.c (ix86_split_long_move): Do not handle + address used for LEA in a special way. + +2017-09-19 Segher Boessenkool <segher@kernel.crashing.org> + + * simplify-rtx.c (simplify_binary_operation_1): Fix typo in comment. + +2017-09-19 Martin Sebor <msebor@redhat.com> + + PR c/81854 + * cgraphunit.c (handle_alias_pairs): Reject aliases between functions + of incompatible types. + +2017-09-19 Will Schmidt <will_schmidt@vnet.ibm.com> + + * config/rs6000/rs6000.c (rs6000_gimple_fold_builtin): Add handling + for early folding of vector loads (ALTIVEC_BUILTIN_LVX_*). + * config/rs6000/rs6000-c.c (altivec_resolve_overloaded_builtin): + Remove obsoleted code for handling ALTIVEC_BUILTIN_VEC_LD. + +2017-09-19 Richard Biener <rguenther@suse.de> + + PR tree-optimization/82244 + * tree-vrp.c (remove_range_assertions): Do not propagate + a constant to abnormals but replace the assert with a copy. + +2017-09-19 Alexander Monakov <amonakov@ispras.ru> + + PR rtl-optimization/57878 + PR rtl-optimization/68988 + * lra-assigns.c (reload_pseudo_compare_func): Remove fragmentation + avoidance test involving non_reload_pseudos. Move frequency test + below the general fragmentation avoidance test. + +2017-09-19 Richard Biener <rguenther@suse.de> + + PR tree-optimization/69728 + * graphite-sese-to-poly.c (schedule_error): New global. + (add_loop_schedule): Handle empty domain by failing the + schedule. + (build_original_schedule): Handle schedule_error. + +2017-09-19 Richard Biener <rguenther@suse.de> + + * graphite-scop-detection.c (scop_detection::can_represent_loop): + Do not iterate to sibling loops but only to siblings of inner + loops. + 2017-09-18 Andreas Schwab <schwab@linux-m68k.org> PR target/81613 diff --git a/gcc/DATESTAMP b/gcc/DATESTAMP index 83e2213..b46c5f0 100644 --- a/gcc/DATESTAMP +++ b/gcc/DATESTAMP @@ -1 +1 @@ -20170918 +20170920 diff --git a/gcc/cgraphunit.c b/gcc/cgraphunit.c index a287f0d..8c1acf7 100644 --- a/gcc/cgraphunit.c +++ b/gcc/cgraphunit.c @@ -1352,6 +1352,66 @@ handle_alias_pairs (void) if (TREE_CODE (p->decl) == FUNCTION_DECL && target_node && is_a <cgraph_node *> (target_node)) { + tree t1 = TREE_TYPE (p->decl); + tree t2 = TREE_TYPE (target_node->decl); + + if (lookup_attribute ("ifunc", DECL_ATTRIBUTES (p->decl))) + { + t2 = TREE_TYPE (t2); + if (POINTER_TYPE_P (t2)) + { + t2 = TREE_TYPE (t2); + if (!FUNC_OR_METHOD_TYPE_P (t2)) + { + if (warning_at (DECL_SOURCE_LOCATION (p->decl), + OPT_Wattributes, + "%q+D %<ifunc%> resolver should return " + "a function pointer", + p->decl)) + inform (DECL_SOURCE_LOCATION (target_node->decl), + "resolver declaration here"); + + t2 = NULL_TREE; + } + } + else + { + /* Deal with static member function pointers. */ + if (TREE_CODE (t2) == RECORD_TYPE + && TYPE_FIELDS (t2) + && TREE_CODE (TREE_TYPE (TYPE_FIELDS (t2))) == POINTER_TYPE + && (TREE_CODE (TREE_TYPE (TREE_TYPE (TYPE_FIELDS (t2)))) + == METHOD_TYPE)) + t2 = TREE_TYPE (TREE_TYPE (TYPE_FIELDS (t2))); + else + { + error ("%q+D %<ifunc%> resolver must return a function " + "pointer", + p->decl); + inform (DECL_SOURCE_LOCATION (target_node->decl), + "resolver declaration here"); + + t2 = NULL_TREE; + } + } + } + + if (t2 + && (!FUNC_OR_METHOD_TYPE_P (t2) + || (prototype_p (t1) + && prototype_p (t2) + && !types_compatible_p (t1, t2)))) + { + /* Warn for incompatibilities. Avoid warning for functions + without a prototype to make it possible to declare aliases + without knowing the exact type, as libstdc++ does. */ + if (warning_at (DECL_SOURCE_LOCATION (p->decl), OPT_Wattributes, + "%q+D alias between functions of incompatible " + "types %qT and %qT", p->decl, t1, t2)) + inform (DECL_SOURCE_LOCATION (target_node->decl), + "aliased declaration here"); + } + cgraph_node *src_node = cgraph_node::get (p->decl); if (src_node && src_node->definition) src_node->reset (); @@ -1366,10 +1426,11 @@ handle_alias_pairs (void) } else { - error ("%q+D alias in between function and variable is not supported", + error ("%q+D alias between function and variable is not supported", p->decl); - warning (0, "%q+D aliased declaration", - target_node->decl); + inform (DECL_SOURCE_LOCATION (target_node->decl), + "aliased declaration here"); + alias_pairs->unordered_remove (i); } } diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c index c80c0de..1c765fb 100644 --- a/gcc/config/i386/i386.c +++ b/gcc/config/i386/i386.c @@ -26706,7 +26706,7 @@ ix86_split_long_move (rtx operands[]) Do an lea to the last part and use only one colliding move. */ else if (collisions > 1) { - rtx base, addr, tls_base = NULL_RTX; + rtx base, addr; collisions = 1; @@ -26723,44 +26723,13 @@ ix86_split_long_move (rtx operands[]) struct ix86_address parts; int ok = ix86_decompose_address (addr, &parts); gcc_assert (ok); - if (parts.seg == DEFAULT_TLS_SEG_REG) - { - /* It is not valid to use %gs: or %fs: in - lea though, so we need to remove it from the - address used for lea and add it to each individual - memory loads instead. */ - addr = copy_rtx (addr); - rtx *x = &addr; - while (GET_CODE (*x) == PLUS) - { - for (i = 0; i < 2; i++) - { - rtx u = XEXP (*x, i); - if (GET_CODE (u) == ZERO_EXTEND) - u = XEXP (u, 0); - if (GET_CODE (u) == UNSPEC - && XINT (u, 1) == UNSPEC_TP) - { - tls_base = XEXP (*x, i); - *x = XEXP (*x, 1 - i); - break; - } - } - if (tls_base) - break; - x = &XEXP (*x, 0); - } - gcc_assert (tls_base); - } + /* It is not valid to use %gs: or %fs: in lea. */ + gcc_assert (parts.seg == ADDR_SPACE_GENERIC); } emit_insn (gen_rtx_SET (base, addr)); - if (tls_base) - base = gen_rtx_PLUS (GET_MODE (base), base, tls_base); part[1][0] = replace_equiv_address (part[1][0], base); for (i = 1; i < nparts; i++) { - if (tls_base) - base = copy_rtx (base); tmp = plus_constant (Pmode, base, UNITS_PER_WORD * i); part[1][i] = replace_equiv_address (part[1][i], tmp); } diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index 43227dc..b1bde14 100644 --- a/gcc/config/i386/i386.md +++ b/gcc/config/i386/i386.md @@ -11246,6 +11246,98 @@ (const_string "SI") (const_string "<MODE>")))]) +(define_insn_and_split "*scc_bt<mode>" + [(set (match_operand:QI 0 "nonimmediate_operand") + (match_operator 1 "bt_comparison_operator" + [(zero_extract:SWI48 + (match_operand:SWI48 2 "nonimmediate_operand") + (const_int 1) + (match_operand:SI 3 "nonmemory_operand")) + (const_int 0)])) + (clobber (reg:CC FLAGS_REG))] + "(TARGET_USE_BT || optimize_function_for_size_p (cfun)) + && (CONST_INT_P (operands[3]) + ? (INTVAL (operands[3]) < GET_MODE_BITSIZE (<MODE>mode) + && INTVAL (operands[3]) + >= (optimize_function_for_size_p (cfun) ? 8 : 32)) + : !memory_operand (operands[2], <MODE>mode)) + && can_create_pseudo_p ()" + "#" + "&& 1" + [(set (reg:CCC FLAGS_REG) + (compare:CCC + (zero_extract:SWI48 + (match_dup 2) + (const_int 1) + (match_dup 3)) + (const_int 0))) + (set (match_dup 0) + (match_op_dup 1 [(reg:CCC FLAGS_REG) (const_int 0)]))] +{ + operands[1] = shallow_copy_rtx (operands[1]); + PUT_CODE (operands[1], reverse_condition (GET_CODE (operands[1]))); +}) + +(define_insn_and_split "*scc_bt<mode>_1" + [(set (match_operand:QI 0 "nonimmediate_operand") + (match_operator 1 "bt_comparison_operator" + [(zero_extract:SWI48 + (match_operand:SWI48 2 "register_operand") + (const_int 1) + (zero_extend:SI + (match_operand:QI 3 "register_operand"))) + (const_int 0)])) + (clobber (reg:CC FLAGS_REG))] + "(TARGET_USE_BT || optimize_function_for_size_p (cfun)) + && can_create_pseudo_p ()" + "#" + "&& 1" + [(set (reg:CCC FLAGS_REG) + (compare:CCC + (zero_extract:SWI48 + (match_dup 2) + (const_int 1) + (match_dup 3)) + (const_int 0))) + (set (match_dup 0) + (match_op_dup 1 [(reg:CCC FLAGS_REG) (const_int 0)]))] +{ + operands[3] = lowpart_subreg (SImode, operands[3], QImode); + operands[1] = shallow_copy_rtx (operands[1]); + PUT_CODE (operands[1], reverse_condition (GET_CODE (operands[1]))); +}) + +;; Avoid useless masking of bit offset operand. +(define_insn_and_split "*scc_bt<mode>_mask" + [(set (match_operand:QI 0 "nonimmediate_operand") + (match_operator 1 "bt_comparison_operator" + [(zero_extract:SWI48 + (match_operand:SWI48 2 "register_operand") + (const_int 1) + (and:SI + (match_operand:SI 3 "register_operand") + (match_operand 4 "const_int_operand")))])) + (clobber (reg:CC FLAGS_REG))] + "(TARGET_USE_BT || optimize_function_for_size_p (cfun)) + && (INTVAL (operands[4]) & (GET_MODE_BITSIZE (<MODE>mode)-1)) + == GET_MODE_BITSIZE (<MODE>mode)-1 + && can_create_pseudo_p ()" + "#" + "&& 1" + [(set (reg:CCC FLAGS_REG) + (compare:CCC + (zero_extract:SWI48 + (match_dup 2) + (const_int 1) + (match_dup 3)) + (const_int 0))) + (set (match_dup 0) + (match_op_dup 1 [(reg:CCC FLAGS_REG) (const_int 0)]))] +{ + operands[1] = shallow_copy_rtx (operands[1]); + PUT_CODE (operands[1], reverse_condition (GET_CODE (operands[1]))); +}) + (define_insn_and_split "*jcc_bt<mode>" [(set (pc) (if_then_else (match_operator 0 "bt_comparison_operator" diff --git a/gcc/config/rs6000/rs6000-c.c b/gcc/config/rs6000/rs6000-c.c index d27f563..a49db97 100644 --- a/gcc/config/rs6000/rs6000-c.c +++ b/gcc/config/rs6000/rs6000-c.c @@ -6472,85 +6472,15 @@ altivec_resolve_overloaded_builtin (location_t loc, tree fndecl, return stmt; } - /* Expand vec_ld into an expression that masks the address and - performs the load. We need to expand this early to allow + /* Expand vec_st into an expression that masks the address and + performs the store. We need to expand this early to allow the best aliasing, as by the time we get into RTL we no longer are able to honor __restrict__, for example. We may want to consider this for all memory access built-ins. When -maltivec=be is specified, or the wrong number of arguments is provided, simply punt to existing built-in processing. */ - if (fcode == ALTIVEC_BUILTIN_VEC_LD - && (BYTES_BIG_ENDIAN || !VECTOR_ELT_ORDER_BIG) - && nargs == 2) - { - tree arg0 = (*arglist)[0]; - tree arg1 = (*arglist)[1]; - - /* Strip qualifiers like "const" from the pointer arg. */ - tree arg1_type = TREE_TYPE (arg1); - if (TREE_CODE (arg1_type) == ARRAY_TYPE && c_dialect_cxx ()) - { - /* Force array-to-pointer decay for C++. */ - arg1 = default_conversion (arg1); - arg1_type = TREE_TYPE (arg1); - } - if (!POINTER_TYPE_P (arg1_type)) - goto bad; - - tree inner_type = TREE_TYPE (arg1_type); - if (TYPE_QUALS (TREE_TYPE (arg1_type)) != 0) - { - arg1_type = build_pointer_type (build_qualified_type (inner_type, - 0)); - arg1 = fold_convert (arg1_type, arg1); - } - - /* Construct the masked address. Let existing error handling take - over if we don't have a constant offset. */ - arg0 = fold (arg0); - - if (TREE_CODE (arg0) == INTEGER_CST) - { - if (!ptrofftype_p (TREE_TYPE (arg0))) - arg0 = build1 (NOP_EXPR, sizetype, arg0); - - tree addr = fold_build2_loc (loc, POINTER_PLUS_EXPR, arg1_type, - arg1, arg0); - tree aligned = fold_build2_loc (loc, BIT_AND_EXPR, arg1_type, addr, - build_int_cst (arg1_type, -16)); - - /* Find the built-in to get the return type so we can convert - the result properly (or fall back to default handling if the - arguments aren't compatible). */ - for (desc = altivec_overloaded_builtins; - desc->code && desc->code != fcode; desc++) - continue; - - for (; desc->code == fcode; desc++) - if (rs6000_builtin_type_compatible (TREE_TYPE (arg0), desc->op1) - && (rs6000_builtin_type_compatible (TREE_TYPE (arg1), - desc->op2))) - { - tree ret_type = rs6000_builtin_type (desc->ret_type); - if (TYPE_MODE (ret_type) == V2DImode) - /* Type-based aliasing analysis thinks vector long - and vector long long are different and will put them - in distinct alias classes. Force our return type - to be a may-alias type to avoid this. */ - ret_type - = build_pointer_type_for_mode (ret_type, Pmode, - true/*can_alias_all*/); - else - ret_type = build_pointer_type (ret_type); - aligned = build1 (NOP_EXPR, ret_type, aligned); - tree ret_val = build_indirect_ref (loc, aligned, RO_NULL); - return ret_val; - } - } - } - /* Similarly for stvx. */ if (fcode == ALTIVEC_BUILTIN_VEC_ST && (BYTES_BIG_ENDIAN || !VECTOR_ELT_ORDER_BIG) && nargs == 3) diff --git a/gcc/config/rs6000/rs6000.c b/gcc/config/rs6000/rs6000.c index bc1c4db..1978634 100644 --- a/gcc/config/rs6000/rs6000.c +++ b/gcc/config/rs6000/rs6000.c @@ -16546,6 +16546,48 @@ rs6000_gimple_fold_builtin (gimple_stmt_iterator *gsi) update_call_from_tree (gsi, res); return true; } + /* Vector loads. */ + case ALTIVEC_BUILTIN_LVX_V16QI: + case ALTIVEC_BUILTIN_LVX_V8HI: + case ALTIVEC_BUILTIN_LVX_V4SI: + case ALTIVEC_BUILTIN_LVX_V4SF: + case ALTIVEC_BUILTIN_LVX_V2DI: + case ALTIVEC_BUILTIN_LVX_V2DF: + { + arg0 = gimple_call_arg (stmt, 0); // offset + arg1 = gimple_call_arg (stmt, 1); // address + /* Do not fold for -maltivec=be on LE targets. */ + if (VECTOR_ELT_ORDER_BIG && !BYTES_BIG_ENDIAN) + return false; + lhs = gimple_call_lhs (stmt); + location_t loc = gimple_location (stmt); + /* Since arg1 may be cast to a different type, just use ptr_type_node + here instead of trying to enforce TBAA on pointer types. */ + tree arg1_type = ptr_type_node; + tree lhs_type = TREE_TYPE (lhs); + /* POINTER_PLUS_EXPR wants the offset to be of type 'sizetype'. Create + the tree using the value from arg0. The resulting type will match + the type of arg1. */ + gimple_seq stmts = NULL; + tree temp_offset = gimple_convert (&stmts, loc, sizetype, arg0); + tree temp_addr = gimple_build (&stmts, loc, POINTER_PLUS_EXPR, + arg1_type, arg1, temp_offset); + /* Mask off any lower bits from the address. */ + tree aligned_addr = gimple_build (&stmts, loc, BIT_AND_EXPR, + arg1_type, temp_addr, + build_int_cst (arg1_type, -16)); + gsi_insert_seq_before (gsi, stmts, GSI_SAME_STMT); + /* Use the build2 helper to set up the mem_ref. The MEM_REF could also + take an offset, but since we've already incorporated the offset + above, here we just pass in a zero. */ + gimple *g; + g = gimple_build_assign (lhs, build2 (MEM_REF, lhs_type, aligned_addr, + build_int_cst (arg1_type, 0))); + gimple_set_location (g, loc); + gsi_replace (gsi, g, true); + return true; + } + default: if (TARGET_DEBUG_BUILTIN) fprintf (stderr, "gimple builtin intrinsic not matched:%d %s %s\n", diff --git a/gcc/go/gofrontend/MERGE b/gcc/go/gofrontend/MERGE index 27bcb6e..f6b5361 100644 --- a/gcc/go/gofrontend/MERGE +++ b/gcc/go/gofrontend/MERGE @@ -1,4 +1,4 @@ -be69546afcac182cc93c569bc96665f0ef72d66a +5fb74cd7192123a9ea06dcae0d5d8d0b3538db8f The first line of this file holds the git revision number of the last merge done from the gofrontend repository. diff --git a/gcc/graphite-scop-detection.c b/gcc/graphite-scop-detection.c index 71ddfd8..3ed6afd 100644 --- a/gcc/graphite-scop-detection.c +++ b/gcc/graphite-scop-detection.c @@ -975,11 +975,9 @@ scop_detection::can_represent_loop (loop_p loop, sese_l scop) { if (!can_represent_loop_1 (loop, scop)) return false; - if (loop->inner && !can_represent_loop (loop->inner, scop)) - return false; - if (loop->next && !can_represent_loop (loop->next, scop)) - return false; - + for (loop_p inner = loop->inner; inner; inner = inner->next) + if (!can_represent_loop (inner, scop)) + return false; return true; } diff --git a/gcc/graphite-sese-to-poly.c b/gcc/graphite-sese-to-poly.c index 8ff9a22..6e64f13 100644 --- a/gcc/graphite-sese-to-poly.c +++ b/gcc/graphite-sese-to-poly.c @@ -1030,6 +1030,8 @@ outer_projection_mupa (__isl_take isl_union_set *set, int n) return isl_multi_union_pw_aff_from_union_pw_multi_aff (data.res); } +static bool schedule_error; + /* Embed SCHEDULE in the constraints of the LOOP domain. */ static isl_schedule * @@ -1043,6 +1045,16 @@ add_loop_schedule (__isl_take isl_schedule *schedule, loop_p loop, if (empty < 0 || empty) return empty < 0 ? isl_schedule_free (schedule) : schedule; + isl_union_set *domain = isl_schedule_get_domain (schedule); + /* We cannot apply an empty domain to pbbs in this loop so fail. + ??? Somehow drop pbbs in the loop instead. */ + if (isl_union_set_is_empty (domain)) + { + schedule_error = true; + isl_union_set_free (domain); + return schedule; + } + isl_space *space = isl_set_get_space (iterators); int loop_index = isl_space_dim (space, isl_dim_set) - 1; @@ -1063,7 +1075,6 @@ add_loop_schedule (__isl_take isl_schedule *schedule, loop_p loop, prefix = isl_multi_aff_set_tuple_id (prefix, isl_dim_out, label); int n = isl_multi_aff_dim (prefix, isl_dim_in); - isl_union_set *domain = isl_schedule_get_domain (schedule); isl_multi_union_pw_aff *mupa = outer_projection_mupa (domain, n); mupa = isl_multi_union_pw_aff_apply_multi_aff (mupa, prefix); return isl_schedule_insert_partial_schedule (schedule, mupa); @@ -1169,6 +1180,8 @@ build_schedule_loop_nest (scop_p scop, int *index, loop_p context_loop) static bool build_original_schedule (scop_p scop) { + schedule_error = false; + int i = 0; int n = scop->pbbs.length (); while (i < n) @@ -1183,6 +1196,14 @@ build_original_schedule (scop_p scop) scop->original_schedule = add_in_sequence (scop->original_schedule, s); } + if (schedule_error) + { + if (dump_file) + fprintf (dump_file, "[sese-to-poly] failed to build " + "original schedule\n"); + return false; + } + if (dump_file) { fprintf (dump_file, "[sese-to-poly] original schedule:\n"); diff --git a/gcc/lra-assigns.c b/gcc/lra-assigns.c index 9208fcc..5a65c7c 100644 --- a/gcc/lra-assigns.c +++ b/gcc/lra-assigns.c @@ -211,24 +211,15 @@ reload_pseudo_compare_func (const void *v1p, const void *v2p) if ((diff = (ira_class_hard_regs_num[cl1] - ira_class_hard_regs_num[cl2])) != 0) return diff; - if ((diff - = (ira_reg_class_max_nregs[cl2][lra_reg_info[r2].biggest_mode] - - ira_reg_class_max_nregs[cl1][lra_reg_info[r1].biggest_mode])) != 0 - /* The code below executes rarely as nregs == 1 in most cases. - So we should not worry about using faster data structures to - check reload pseudos. */ - && ! bitmap_bit_p (&non_reload_pseudos, r1) - && ! bitmap_bit_p (&non_reload_pseudos, r2)) - return diff; - if ((diff = (regno_assign_info[regno_assign_info[r2].first].freq - - regno_assign_info[regno_assign_info[r1].first].freq)) != 0) - return diff; /* Allocate bigger pseudos first to avoid register file fragmentation. */ if ((diff = (ira_reg_class_max_nregs[cl2][lra_reg_info[r2].biggest_mode] - ira_reg_class_max_nregs[cl1][lra_reg_info[r1].biggest_mode])) != 0) return diff; + if ((diff = (regno_assign_info[regno_assign_info[r2].first].freq + - regno_assign_info[regno_assign_info[r1].first].freq)) != 0) + return diff; /* Put pseudos from the thread nearby. */ if ((diff = regno_assign_info[r1].first - regno_assign_info[r2].first) != 0) return diff; diff --git a/gcc/simplify-rtx.c b/gcc/simplify-rtx.c index 97a0652..1b960b9 100644 --- a/gcc/simplify-rtx.c +++ b/gcc/simplify-rtx.c @@ -2665,7 +2665,7 @@ simplify_binary_operation_1 (enum rtx_code code, machine_mode mode, HOST_WIDE_INT c1 = INTVAL (XEXP (op0, 1)); HOST_WIDE_INT c2 = INTVAL (trueop1); - /* If (C1&C2) == C1, then (X&C1)|C2 becomes X. */ + /* If (C1&C2) == C1, then (X&C1)|C2 becomes C2. */ if ((c1 & c2) == c1 && !side_effects_p (XEXP (op0, 0))) return trueop1; diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index c0de42a..0114205 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,52 @@ +2017-09-19 Uros Bizjak <ubizjak@gmail.com> + + * gcc.target/i386/bt-5.c: New test. + * gcc.target/i386/bt-6.c: Ditto. + * gcc.target/i386/bt-mask-3.c: Ditto. + * gcc.target/i386/bt-mask-4.c: Ditto. + +2017-09-19 Jakub Jelinek <jakub@redhat.com> + + * g++.dg/tree-ssa/pr31146-2.C: Only do scan-tree-dump for c++14_down. + * g++.dg/tree-ssa/pr41428.C: Likewise. + * g++.dg/expr/bool1.C: Only do dg-do compile instead of dg-do run for + c++17 and up. + * g++.dg/expr/bool3.C: Likewise. + * g++.dg/expr/bitfield5.C: Likewise. + * g++.old-deja/g++.jason/bool5.C: Likewise. + +2017-09-18 Martin Sebor <msebor@redhat.com> + + PR c/81854 + * gcc.dg/pr81854.c: New test. + * g++.dg/ext/attr-ifunc-5.C: New test. + * g++.dg/ext/attr-ifunc-1.C: Adjust. + * g++.dg/ext/attr-ifunc-2.C: Same. + * g++.dg/ext/attr-ifunc-3.C: Same. + * g++.dg/ext/attr-ifunc-4.C: Same. + * g++.old-deja/g++.abi/vtable2.C: Same. + * gcc.dg/attr-ifunc-1.c: Same. + +2017-09-19 Will Schmidt <will_schmidt@vnet.ibm.com> + + * gcc.target/powerpc/fold-vec-ld-misc.c: New. + +2017-09-19 Richard Biener <rguenther@suse.de> + + PR tree-optimization/82244 + * gcc.dg/torture/pr82244.c: New testcase. + +2017-09-19 Richard Biener <rguenther@suse.de> + + PR tree-optimization/69728 + * gfortran.dg/graphite/pr69728.f90: New testcase. + * gcc.dg/graphite/pr69728.c: Likewise. + +2017-09-18 Paolo Carlini <paolo.carlini@oracle.com> + + PR c++/80947 + * g++.dg/cpp0x/lambda/lambda-80947.C: New. + 2017-09-18 Richard Sandiford <richard.sandiford@linaro.org> * gcc.dg/vect/slp-multitypes-13.c: New test. diff --git a/gcc/testsuite/g++.dg/cpp0x/lambda/lambda-80947.C b/gcc/testsuite/g++.dg/cpp0x/lambda/lambda-80947.C new file mode 100644 index 0000000..fe6faa7 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/lambda/lambda-80947.C @@ -0,0 +1,16 @@ +// { dg-do compile { target c++11 } } +// { dg-require-visibility "" } +// { dg-options "-fvisibility=hidden" } + +template<class T> +class MyClass { +public: + MyClass() { + auto outer = [this]() + { + auto fn = [this] { }; + }; + } +}; + +int main() { MyClass<int> r; } diff --git a/gcc/testsuite/g++.dg/expr/bitfield5.C b/gcc/testsuite/g++.dg/expr/bitfield5.C index 9565828..1921b19 100644 --- a/gcc/testsuite/g++.dg/expr/bitfield5.C +++ b/gcc/testsuite/g++.dg/expr/bitfield5.C @@ -1,5 +1,6 @@ // PR c++/30274 -// { dg-do run } +// { dg-do run { target c++14_down } } +// { dg-do compile { target c++17 } } struct S { bool x : 4; diff --git a/gcc/testsuite/g++.dg/expr/bool1.C b/gcc/testsuite/g++.dg/expr/bool1.C index 98984d6..7b120e1 100644 --- a/gcc/testsuite/g++.dg/expr/bool1.C +++ b/gcc/testsuite/g++.dg/expr/bool1.C @@ -1,5 +1,6 @@ -// { dg-do run } -// PR C++/29295 +// PR c++/29295 +// { dg-do run { target c++14_down } } +// { dg-do compile { target c++17 } } // make sure that a typedef for a bool will have the // the same results as a bool itself. diff --git a/gcc/testsuite/g++.dg/expr/bool3.C b/gcc/testsuite/g++.dg/expr/bool3.C index bff4b7b..373c202 100644 --- a/gcc/testsuite/g++.dg/expr/bool3.C +++ b/gcc/testsuite/g++.dg/expr/bool3.C @@ -1,5 +1,6 @@ -// { dg-do run } -// PR C++/29295 +// PR c++/29295 +// { dg-do run { target c++14_down } } +// { dg-do compile { target c++17 } } // make sure that a typedef for a bool will have the // the same results as a bool itself. diff --git a/gcc/testsuite/g++.dg/ext/attr-ifunc-1.C b/gcc/testsuite/g++.dg/ext/attr-ifunc-1.C index d41fa7d..2c7bba1 100644 --- a/gcc/testsuite/g++.dg/ext/attr-ifunc-1.C +++ b/gcc/testsuite/g++.dg/ext/attr-ifunc-1.C @@ -2,33 +2,41 @@ /* { dg-require-ifunc "" } */ /* { dg-options "-Wno-pmf-conversions" } */ -#include <stdio.h> - struct Klass { int implementation (); int magic (); - static void *resolver (); + + typedef int (Klass::*MemFuncPtr)(); + + static MemFuncPtr resolver (); }; +Klass::MemFuncPtr p = &Klass::implementation; + int Klass::implementation (void) { - printf ("'ere I am JH\n"); - return 0; + __builtin_printf ("'ere I am JH\n"); + return 1234; } -void *Klass::resolver (void) + +Klass::MemFuncPtr Klass::resolver (void) { - int (Klass::*pmf) () = &Klass::implementation; - - return (void *)(int (*)(Klass *))(((Klass *)0)->*pmf); + return &Klass::implementation; } +int f (void) __attribute__ ((ifunc ("foo"))); + +typedef int (F)(void); +extern "C" F* foo () { return 0; } + + int Klass::magic (void) __attribute__ ((ifunc ("_ZN5Klass8resolverEv"))); int main () { Klass obj; - - return obj.magic () != 0; + + return !(obj.magic () == 1234); } diff --git a/gcc/testsuite/g++.dg/ext/attr-ifunc-2.C b/gcc/testsuite/g++.dg/ext/attr-ifunc-2.C index e205a2a..49872e0 100644 --- a/gcc/testsuite/g++.dg/ext/attr-ifunc-2.C +++ b/gcc/testsuite/g++.dg/ext/attr-ifunc-2.C @@ -8,7 +8,10 @@ struct Klass { int implementation (); int magic (); - static void *resolver (); + + typedef int (Klass::*MemFuncPtr)(); + + static MemFuncPtr resolver (); }; int Klass::implementation (void) @@ -17,11 +20,9 @@ int Klass::implementation (void) return 0; } -void *Klass::resolver (void) +Klass::memFuncPtr Klass::resolver (void) { - int (Klass::*pmf) () = &Klass::implementation; - - return (void *)(int (*)(Klass *))(((Klass *)0)->*pmf); + return &Klass::implementation; } int Klass::magic (void) __attribute__ ((ifunc ("_ZN5Klass8resolverEv"))); @@ -33,6 +34,6 @@ struct Klassier : Klass int main () { Klassier obj; - + return obj.magic () != 0; } diff --git a/gcc/testsuite/g++.dg/ext/attr-ifunc-3.C b/gcc/testsuite/g++.dg/ext/attr-ifunc-3.C index ba65976..04206a1 100644 --- a/gcc/testsuite/g++.dg/ext/attr-ifunc-3.C +++ b/gcc/testsuite/g++.dg/ext/attr-ifunc-3.C @@ -8,7 +8,10 @@ struct Klass { int implementation (); int magic (); - static void *resolver (); + + typedef int (Klass::*MemFuncPtr)(); + + static MemFuncPtr resolver (); }; int Klass::implementation (void) @@ -17,11 +20,9 @@ int Klass::implementation (void) return 0; } -void *Klass::resolver (void) +Klass::MemFuncPtr Klass::resolver (void) { - int (Klass::*pmf) () = &Klass::implementation; - - return (void *)(int (*)(Klass *))(((Klass *)0)->*pmf); + return &Klass::implementation; } int Klass::magic (void) __attribute__ ((ifunc ("_ZN5Klass8resolverEv"))); @@ -34,6 +35,6 @@ int Foo (Klass &obj, int (Klass::*pmf) ()) int main () { Klass obj; - + return Foo (obj, &Klass::magic) != 0; } diff --git a/gcc/testsuite/g++.dg/ext/attr-ifunc-4.C b/gcc/testsuite/g++.dg/ext/attr-ifunc-4.C index 0cae410..b8d8e58 100644 --- a/gcc/testsuite/g++.dg/ext/attr-ifunc-4.C +++ b/gcc/testsuite/g++.dg/ext/attr-ifunc-4.C @@ -13,7 +13,10 @@ struct Klassier : Klass { int implementation (); int magic (); - static void *resolver (); + + typedef int (Klass::*MemFuncPtr)(); + + static MemFuncPtr resolver (); }; int Klassier::implementation (void) @@ -22,11 +25,9 @@ int Klassier::implementation (void) return 0; } -void *Klassier::resolver (void) +Klassier::MemFuncPtr Klassier::resolver (void) { - int (Klassier::*pmf) () = &Klassier::implementation; - - return (void *)(int (*)(Klassier *))(((Klassier *)0)->*pmf); + return &Klassier::implementation; } int Klassier::magic (void) __attribute__ ((ifunc ("_ZN8Klassier8resolverEv"))); @@ -39,6 +40,6 @@ int __attribute__ ((weak)) Foo (Klass &base) int main () { Klassier obj; - + return Foo (obj) != 0; } diff --git a/gcc/testsuite/g++.dg/ext/attr-ifunc-5.C b/gcc/testsuite/g++.dg/ext/attr-ifunc-5.C new file mode 100644 index 0000000..05855dd --- /dev/null +++ b/gcc/testsuite/g++.dg/ext/attr-ifunc-5.C @@ -0,0 +1,29 @@ +// PR c/81854 - weak alias of an incompatible symbol accepted +// { dg-do compile } +// { dg-require-ifunc "" } */ + +struct Klass +{ + int implementation (); + const char* magic (); + + typedef int (Klass::*MemFuncPtr)(); + + static MemFuncPtr resolver (); +}; + +int Klass::implementation (void) +{ + return 0; +} + +const char* __attribute__ ((ifunc ("_ZN5Klass8resolverEv"))) + Klass::magic (); // { dg-warning "alias between functions of incompatible types" } + + + +Klass::MemFuncPtr +Klass::resolver (void) // { dg-message "aliased declaration here" } +{ + return &Klass::implementation; +} diff --git a/gcc/testsuite/g++.dg/tree-ssa/pr31146-2.C b/gcc/testsuite/g++.dg/tree-ssa/pr31146-2.C index cf4ed33..500d8b6 100644 --- a/gcc/testsuite/g++.dg/tree-ssa/pr31146-2.C +++ b/gcc/testsuite/g++.dg/tree-ssa/pr31146-2.C @@ -20,4 +20,6 @@ double foo (void) return v.a[2]; } -/* { dg-final { scan-tree-dump "Replaced .* != 0B. with .1" "forwprop1" } } */ +/* -std=c++17 and above doesn't emit operator new () != NULL, so there is + nothing to fold anymore. */ +/* { dg-final { scan-tree-dump "Replaced .* != 0B. with .1" "forwprop1" { target c++14_down } } } */ diff --git a/gcc/testsuite/g++.dg/tree-ssa/pr41428.C b/gcc/testsuite/g++.dg/tree-ssa/pr41428.C index dd96dfc..c0a5eb6 100644 --- a/gcc/testsuite/g++.dg/tree-ssa/pr41428.C +++ b/gcc/testsuite/g++.dg/tree-ssa/pr41428.C @@ -11,4 +11,6 @@ int foo(void) return *(int *)&f; } -/* { dg-final { scan-tree-dump "Folded into: if \\\(1 != 0\\\)" "ccp1" } } */ +/* -std=c++17 and above doesn't emit operator new () != NULL, so there is + nothing to fold anymore. */ +/* { dg-final { scan-tree-dump "Folded into: if \\\(1 != 0\\\)" "ccp1" { target c++14_down } } } */ diff --git a/gcc/testsuite/g++.old-deja/g++.abi/vtable2.C b/gcc/testsuite/g++.old-deja/g++.abi/vtable2.C index 3022875..2c88a95 100644 --- a/gcc/testsuite/g++.old-deja/g++.abi/vtable2.C +++ b/gcc/testsuite/g++.old-deja/g++.abi/vtable2.C @@ -1,5 +1,5 @@ // { dg-do run } -// { dg-options "-fno-strict-aliasing" } +// { dg-options "-Wno-attributes -fno-strict-aliasing" } // Origin: Mark Mitchell <mark@codesourcery.com> #if defined (__GXX_ABI_VERSION) && __GXX_ABI_VERSION >= 100 @@ -126,7 +126,8 @@ void S4::s1 () extern "C" { /* We can use weakref here without dg-require-weak, because we know the symbols are defined, so we don't actually issue the .weak - directives. */ + directives. The references to the incompatible virtual S3::s3() + and S4::s1() trigger -Wattributes. */ static void S3_s3 () __attribute__((__weakref__ ("_ZN2S32s3Ev"))); static void S4_s1 () __attribute__((__weakref__ ("_ZN2S42s1Ev"))); } diff --git a/gcc/testsuite/g++.old-deja/g++.jason/bool5.C b/gcc/testsuite/g++.old-deja/g++.jason/bool5.C index ce57b0c..c64784b 100644 --- a/gcc/testsuite/g++.old-deja/g++.jason/bool5.C +++ b/gcc/testsuite/g++.old-deja/g++.jason/bool5.C @@ -1,4 +1,5 @@ -// { dg-do run } +// { dg-do run { target c++14_down } } +// { dg-do compile { target c++17 } } int main () { bool b = false; diff --git a/gcc/testsuite/gcc.dg/attr-ifunc-1.c b/gcc/testsuite/gcc.dg/attr-ifunc-1.c index f9c6482..3f7450e 100644 --- a/gcc/testsuite/gcc.dg/attr-ifunc-1.c +++ b/gcc/testsuite/gcc.dg/attr-ifunc-1.c @@ -2,17 +2,17 @@ /* { dg-require-ifunc "" } */ /* { dg-options "" } */ -#include <stdio.h> +typedef int F (void); static int implementation (void) { - printf ("'ere I am JH\n"); + __builtin_printf ("'ere I am JH\n"); return 0; } -static void *resolver (void) +static F* resolver (void) { - return (void *)implementation; + return implementation; } extern int magic (void) __attribute__ ((ifunc ("resolver"))); diff --git a/gcc/testsuite/gcc.dg/graphite/pr69728.c b/gcc/testsuite/gcc.dg/graphite/pr69728.c new file mode 100644 index 0000000..35ea5bd1 --- /dev/null +++ b/gcc/testsuite/gcc.dg/graphite/pr69728.c @@ -0,0 +1,21 @@ +/* { dg-do compile } */ +/* { dg-options "-O3 -floop-nest-optimize" } */ + +int a[1]; +int b, c, d, e; +void +fn1 () +{ + d = 9; + for (; c; c++) + { + ++d; + b = 8; + for (; b; b--) + { + if (d) + break; + a[b] = e; + } + } +} diff --git a/gcc/testsuite/gcc.dg/pr81854.c b/gcc/testsuite/gcc.dg/pr81854.c new file mode 100644 index 0000000..4b0f4da --- /dev/null +++ b/gcc/testsuite/gcc.dg/pr81854.c @@ -0,0 +1,63 @@ +/* PR c/81854 - weak alias of an incompatible symbol accepted + { dg-do compile } */ + +const char* __attribute__ ((weak, alias ("f0_target"))) +f0 (void); /* { dg-error "alias between function and variable" } */ + +int f0_target; /* { dg-message "aliased declaration here" } */ + + +const char* __attribute__ ((weak, alias ("f1_target"))) +f1 (void); /* { dg-warning "alias between functions of incompatible types" } */ + +void f1_target (int *p) /* { dg-message "aliased declaration here" } */ +{ + *p = 0; +} + + +const char* __attribute__ ((alias ("f2_target"))) +f2 (void*); /* { dg-warning "alias between functions of incompatible types" } */ + +const char* f2_target (int i) /* { dg-message "aliased declaration here" } */ +{ + (void)&i; + return 0; +} + + +int __attribute__ ((ifunc ("f3_resolver"))) +f3 (void); /* { dg-error ".ifunc. resolver must return a function pointer" } */ + +int f3_resolver (void) /* { dg-message "resolver declaration here" } */ +{ + return 0; +} + + +int __attribute__ ((ifunc ("f4_resolver"))) +f4 (void); /* { dg-warning ".ifunc. resolver should return a function pointer" } */ + +void* f4_resolver (void) /* { dg-message "resolver declaration here" } */ +{ + return 0; +} + + +int __attribute__ ((ifunc ("f5_resolver"))) +f5 (void); /* { dg-warning "alias between functions of incompatible types" } */ + +typedef void F5 (void); +F5* f5_resolver (void) /* { dg-message "aliased declaration here" } */ +{ + return 0; +} + +const char* __attribute__ ((ifunc ("f6_resolver"))) +f6 (void); + +typedef const char* F6 (void); +F6* f6_resolver (void) +{ + return 0; +} diff --git a/gcc/testsuite/gcc.dg/torture/pr82244.c b/gcc/testsuite/gcc.dg/torture/pr82244.c new file mode 100644 index 0000000..3b385f9 --- /dev/null +++ b/gcc/testsuite/gcc.dg/torture/pr82244.c @@ -0,0 +1,31 @@ +/* { dg-do compile } */ + +typedef struct a { + struct a *b; +} a; + +extern int d(void); +extern int g(void); +extern int h(void); +extern int _setjmp(void *); + +int c(void) +{ + 1 ? d() : 0; + + a *e; + while (e) { + e = (e == (a *) c) ? 0 : e->b; + while (e) { + int f = 0; + g(); + if (_setjmp(0)) { + if (f & 6) { + ; + } else if (f & 2) { + h(); + } + } + } + } +} diff --git a/gcc/testsuite/gcc.target/i386/bt-5.c b/gcc/testsuite/gcc.target/i386/bt-5.c new file mode 100644 index 0000000..309adfe --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/bt-5.c @@ -0,0 +1,11 @@ +/* PR target/36473 */ +/* { dg-do compile } */ +/* { dg-options "-O2 -mtune=core2" } */ +/* { dg-additional-options "-mregparm=2" { target ia32 } } */ + +int test(unsigned x, unsigned n) +{ + return !(x & ( 0x01 << n )); +} + +/* { dg-final { scan-assembler "btl\[ \t\]" } } */ diff --git a/gcc/testsuite/gcc.target/i386/bt-6.c b/gcc/testsuite/gcc.target/i386/bt-6.c new file mode 100644 index 0000000..994ec43 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/bt-6.c @@ -0,0 +1,12 @@ +/* PR target/36473 */ +/* { dg-do compile } */ +/* { dg-options "-O2 -mtune=core2" } */ +/* { dg-additional-options "-mregparm=2" { target ia32 } } */ + +int test(unsigned long x, unsigned long n) +{ + return !(x & ( (long)0x01 << n )); +} + +/* { dg-final { scan-assembler "btl\[ \t\]" { target { ! lp64 } } } } */ +/* { dg-final { scan-assembler "btq\[ \t\]" { target lp64 } } } */ diff --git a/gcc/testsuite/gcc.target/i386/bt-mask-3.c b/gcc/testsuite/gcc.target/i386/bt-mask-3.c new file mode 100644 index 0000000..bf3a404 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/bt-mask-3.c @@ -0,0 +1,12 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -mtune=core2" } */ +/* { dg-additional-options "-mregparm=2" { target ia32 } } */ + +int test (unsigned x, unsigned n) +{ + n &= 0x1f; + + return !(x & (0x01 << n)); +} + +/* { dg-final { scan-assembler-not "and\[lq\]\[ \t\]" } } */ diff --git a/gcc/testsuite/gcc.target/i386/bt-mask-4.c b/gcc/testsuite/gcc.target/i386/bt-mask-4.c new file mode 100644 index 0000000..8198646 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/bt-mask-4.c @@ -0,0 +1,12 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -mtune=core2" } */ +/* { dg-additional-options "-mregparm=2" { target ia32 } } */ + +int test (unsigned long x, unsigned long n) +{ + n &= 0x3f; + + return !(x & ((long)0x01 << n)); +} + +/* { dg-final { scan-assembler-not "and\[lq\]\[ \t\]" } } */ diff --git a/gcc/testsuite/gcc.target/powerpc/fold-vec-ld-misc.c b/gcc/testsuite/gcc.target/powerpc/fold-vec-ld-misc.c new file mode 100644 index 0000000..4b86a81 --- /dev/null +++ b/gcc/testsuite/gcc.target/powerpc/fold-vec-ld-misc.c @@ -0,0 +1,54 @@ +/* Verify that overloaded built-ins for vec_ld with + structure pointer / double inputs produce the right code. */ + +/* This test is to ensure that when a cast is associated with arg1 on a + call to vec_ld (arg0, arg1), that the arg1 type is properly handled + through the gimple folding code. + We want something like this: + D.2736 = MEM[(voidD.44 *)D.2739]; + We specifically do not want 'struct S' showing up: + D.3212 = MEM[(struct S *)D.3215]; +*/ + +/* { dg-do compile { target lp64 } } */ +/* { dg-require-effective-target powerpc_vsx_ok } */ +/* { dg-options "-mvsx -O2 -fdump-tree-gimple" } */ + +#include <altivec.h> +#include <stdio.h> + +struct S { + vector int *i1,*i2; + vector long long *ll1; + vector double *vd1; + vector double *vd2; + vector double *vd3; + vector double *vd4; +}; + +vector double +testld_struct1 (long long ll1, struct S *p) +{ + return __builtin_altivec_lvx_v2df (ll1, (double *)p); +} + +vector double +testld_struct1b (long long ll1, struct S *p) +{ + return vec_ld (ll1, (vector double *)p); +} + +vector double +testld_struct2 (struct S *p) +{ + return vec_ld (16, (vector double *)p); +} + +vector double +testld_struct3 (struct S *p) +{ + return vec_ld (16, (vector double *)p->vd2); +} + +// We do not want the "struct S" reference to show up. +/* { dg-final { scan-tree-dump-times "MEM\[\(struct S *\)D.\[0-9\]+\]" 0 "gimple" } } */ diff --git a/gcc/testsuite/gfortran.dg/graphite/pr69728.f90 b/gcc/testsuite/gfortran.dg/graphite/pr69728.f90 new file mode 100644 index 0000000..6a3aec4 --- /dev/null +++ b/gcc/testsuite/gfortran.dg/graphite/pr69728.f90 @@ -0,0 +1,26 @@ +! { dg-do compile } +! { dg-options "-O3 -floop-nest-optimize" } +SUBROUTINE rk_addtend_dry ( t_tend, t_tendf, t_save, rk_step, & + h_diabatic, mut, msft, ide, jde, & + ims,ime, jms,jme, kms,kme, & + its,ite, jts,jte, kts,kte) + IMPLICIT NONE + INTEGER , INTENT(IN ) :: ide, jde, ims, ime, jms, jme, kms, kme, & + its, ite, jts, jte, kts, kte + INTEGER , INTENT(IN ) :: rk_step + REAL , DIMENSION( ims:ime , kms:kme, jms:jme ), & + INTENT(INOUT) :: t_tend, t_tendf + REAL , DIMENSION( ims:ime , kms:kme, jms:jme ) , & + INTENT(IN ) :: t_save, h_diabatic + REAL , DIMENSION( ims:ime , jms:jme ) , INTENT(IN ) :: mut, msft + INTEGER :: i, j, k + DO j = jts,MIN(jte,jde-1) + DO k = kts,kte-1 + DO i = its,MIN(ite,ide-1) + IF(rk_step == 1)t_tendf(i,k,j) = t_tendf(i,k,j) + t_save(i,k,j) + t_tend(i,k,j) = t_tend(i,k,j) + t_tendf(i,k,j)/msft(i,j) & + + mut(i,j)*h_diabatic(i,k,j)/msft(i,j) + ENDDO + ENDDO + ENDDO +END SUBROUTINE rk_addtend_dry diff --git a/gcc/testsuite/gnat.dg/validity_check.adb b/gcc/testsuite/gnat.dg/validity_check.adb index a37a595..1bcc084 100644 --- a/gcc/testsuite/gnat.dg/validity_check.adb +++ b/gcc/testsuite/gnat.dg/validity_check.adb @@ -1,5 +1,5 @@ -- { dg-do run } --- { dg-options "-cargs -O -gnatn -gnatVa -gnatws -margs" } +-- { dg-options "-O -gnatn -gnatVa -gnatws" } pragma Initialize_Scalars; diff --git a/gcc/tree-vrp.c b/gcc/tree-vrp.c index 84cdd17..221a07b 100644 --- a/gcc/tree-vrp.c +++ b/gcc/tree-vrp.c @@ -7039,6 +7039,14 @@ remove_range_assertions (void) FOR_EACH_IMM_USE_ON_STMT (use_p, iter) SET_USE (use_p, var); } + /* But do not propagate constants as that is invalid. */ + else if (SSA_NAME_OCCURS_IN_ABNORMAL_PHI (lhs)) + { + gassign *ass = gimple_build_assign (lhs, var); + gsi_replace (&si, ass, true); + gsi_next (&si); + continue; + } else replace_uses_by (lhs, var); diff --git a/gotools/ChangeLog b/gotools/ChangeLog index 8fac16e..a78e762 100644 --- a/gotools/ChangeLog +++ b/gotools/ChangeLog @@ -1,3 +1,14 @@ +2017-09-19 Rainer Orth <ro@CeBiTec.Uni-Bielefeld.DE> + + * Makefile.am (GOTESTFLAGS): New variable. + (check-runtime): Pass it to gotest. + (check-go-tools): Sort summary. + (check-runtime): Likewise. + (check-cgo-test): Likewise. + (check-carchive-test): Likewise. + (check): Likewise. + * Makefile.in: Regenerate. + 2017-09-14 Ian Lance Taylor <iant@golang.org> * Makefile.am (LIBGOTOOL): Define. diff --git a/gotools/Makefile.am b/gotools/Makefile.am index 4f13ffe..7ed5bc3 100644 --- a/gotools/Makefile.am +++ b/gotools/Makefile.am @@ -115,6 +115,8 @@ install-exec-local: cgo$(EXEEXT) uninstall-local: rm -f $(DESTDIR)$(libexecsubdir)/cgo$(exeext) +GOTESTFLAGS = + # Run tests using the go tool, and frob the output to look like that # generated by DejaGNU. The main output of this is two files: # gotools.sum and gotools.log. @@ -192,7 +194,7 @@ check-go-tool: go$(EXEEXT) cgo$(EXEEXT) check-head check-gccgo check-gcc GOPATH=`cd check-go-dir && $(PWD_COMMAND)`; \ export GOPATH; \ (cd check-go-dir/src/cmd/go && $(abs_builddir)/go$(EXEEXT) test -test.short -test.v) >> cmd_go-testlog 2>&1 || echo "--- $${fl} go test cmd/go (0.00s)" >> cmd_go-testlog - grep '^--- ' cmd_go-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' + grep '^--- ' cmd_go-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' | sort -k 2 # check-runtime runs `go test runtime` in our environment. # The runtime package is also tested as part of libgo, @@ -206,15 +208,15 @@ check-runtime: go$(EXEEXT) cgo$(EXEEXT) check-head check-gccgo check-gcc GOARCH=`$(abs_builddir)/go$(EXEEXT) env GOARCH`; \ GOOS=`$(abs_builddir)/go$(EXEEXT) env GOOS`; \ files=`$(SHELL) $(libgosrcdir)/../match.sh --goarch=$${GOARCH} --goos=$${GOOS} --srcdir=$(libgosrcdir)/runtime --extrafiles="$(libgodir)/runtime_sysinfo.go $(libgodir)/sigtab.go" --tag=libffi`; \ - echo "$(ECHO_ENV) GC='$(abs_builddir)/check-gccgo -fgo-compiling-runtime' GOARCH=$${GOARCH} GOOS=$${GOOS} $(SHELL) $(libgosrcdir)/../testsuite/gotest --goarch=$${GOARCH} --goos=$${GOOS} --basedir=$(libgosrcdir)/.. --srcdir=$(libgosrcdir)/runtime --pkgpath=runtime --pkgfiles='$${files}' -test.v" > runtime-testlog + echo "$(ECHO_ENV) GC='$(abs_builddir)/check-gccgo -fgo-compiling-runtime' GOARCH=$${GOARCH} GOOS=$${GOOS} $(SHELL) $(libgosrcdir)/../testsuite/gotest --goarch=$${GOARCH} --goos=$${GOOS} --basedir=$(libgosrcdir)/.. --srcdir=$(libgosrcdir)/runtime --pkgpath=runtime --pkgfiles='$${files}' $(GOTESTFLAGS) -test.v" > runtime-testlog $(CHECK_ENV) \ GC="$${GCCGO} -fgo-compiling-runtime"; \ export GC; \ GOARCH=`$(abs_builddir)/go$(EXEEXT) env GOARCH`; \ GOOS=`$(abs_builddir)/go$(EXEEXT) env GOOS`; \ files=`$(SHELL) $(libgosrcdir)/../match.sh --goarch=$${GOARCH} --goos=$${GOOS} --srcdir=$(libgosrcdir)/runtime --extrafiles="$(libgodir)/runtime_sysinfo.go $(libgodir)/sigtab.go" --tag=libffi`; \ - $(SHELL) $(libgosrcdir)/../testsuite/gotest --goarch=$${GOARCH} --goos=$${GOOS} --basedir=$(libgosrcdir)/.. --srcdir=$(libgosrcdir)/runtime --pkgpath=runtime --pkgfiles="$${files}" -test.v >> runtime-testlog 2>&1 || echo "--- $${fl} go test runtime (0.00s)" >> runtime-testlog - grep '^--- ' runtime-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' + $(SHELL) $(libgosrcdir)/../testsuite/gotest --goarch=$${GOARCH} --goos=$${GOOS} --basedir=$(libgosrcdir)/.. --srcdir=$(libgosrcdir)/runtime --pkgpath=runtime --pkgfiles="$${files}" $(GOTESTFLAGS) -test.v >> runtime-testlog 2>&1 || echo "--- $${fl} go test runtime (0.00s)" >> runtime-testlog + grep '^--- ' runtime-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' | sort -k 2 # check-cgo-test runs `go test misc/cgo/test` in our environment. check-cgo-test: go$(EXEEXT) cgo$(EXEEXT) check-head check-gccgo check-gcc @@ -227,7 +229,7 @@ check-cgo-test: go$(EXEEXT) cgo$(EXEEXT) check-head check-gccgo check-gcc GOTRACEBACK=2; \ export GOTRACEBACK; \ (cd cgo-test-dir/misc/cgo/test && $(abs_builddir)/go$(EXEEXT) test -test.short -test.v) >> cgo-testlog 2>&1 || echo "--- $${fl} go test misc/cgo/test (0.00s)" >> cgo-testlog - grep '^--- ' cgo-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' + grep '^--- ' cgo-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' | sort -k 2 # check-carchive-test runs `go test misc/cgo/testcarchive/carchive_test.go` # in our environment. @@ -241,7 +243,7 @@ check-carchive-test: go$(EXEEXT) cgo$(EXEEXT) check-head check-gccgo check-gcc LIBRARY_PATH=`echo $${abs_libgodir}/.libs:$${LIBRARY_PATH} | sed 's,::*,:,g;s,^:*,,;s,:*$$,,'`; \ export LIBRARY_PATH; \ (cd carchive-test-dir/misc/cgo/testcarchive && $(abs_builddir)/go$(EXEEXT) test -test.v carchive_test.go) >> carchive-testlog 2>&1 || echo "--- $${fl} go test misc/cgo/testcarchive (0.00s)" >> carchive-testlog - grep '^--- ' carchive-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' + grep '^--- ' carchive-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' | sort -k 2 # The check targets runs the tests and assembles the output files. check: check-head check-go-tool check-runtime check-cgo-test check-carchive-test @@ -252,7 +254,7 @@ check: check-head check-go-tool check-runtime check-cgo-test check-carchive-test echo "Running $${testname}" >> gotools.sum; \ echo "Running $${testname}" >> gotools.log; \ sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' < $${file} >> gotools.log; \ - grep '^--- ' $${file} | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' -e 's/SKIP/UNTESTED/' >> gotools.sum; \ + grep '^--- ' $${file} | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' -e 's/SKIP/UNTESTED/' | sort -k 2 >> gotools.sum; \ done @echo >> gotools.sum @echo " === gotools Summary ===" >> gotools.sum diff --git a/gotools/Makefile.in b/gotools/Makefile.in index b9734f1..ad0fc2e 100644 --- a/gotools/Makefile.in +++ b/gotools/Makefile.in @@ -302,6 +302,7 @@ MOSTLYCLEANFILES = \ @NATIVE_TRUE@bin_PROGRAMS = go$(EXEEXT) gofmt$(EXEEXT) @NATIVE_TRUE@noinst_PROGRAMS = cgo$(EXEEXT) @NATIVE_TRUE@man_MANS = go.1 gofmt.1 +@NATIVE_TRUE@GOTESTFLAGS = # CHECK_ENV sets up the environment to run the newly built go tool. # If you change this, change ECHO_ENV, below. @@ -576,8 +577,8 @@ distclean-generic: maintainer-clean-generic: @echo "This command is intended for maintainers to use" @echo "it deletes files that may require special tools to rebuild." -@NATIVE_FALSE@install-exec-local: @NATIVE_FALSE@uninstall-local: +@NATIVE_FALSE@install-exec-local: clean: clean-am clean-am: clean-binPROGRAMS clean-generic clean-noinstPROGRAMS \ @@ -751,7 +752,7 @@ mostlyclean-local: @NATIVE_TRUE@ GOPATH=`cd check-go-dir && $(PWD_COMMAND)`; \ @NATIVE_TRUE@ export GOPATH; \ @NATIVE_TRUE@ (cd check-go-dir/src/cmd/go && $(abs_builddir)/go$(EXEEXT) test -test.short -test.v) >> cmd_go-testlog 2>&1 || echo "--- $${fl} go test cmd/go (0.00s)" >> cmd_go-testlog -@NATIVE_TRUE@ grep '^--- ' cmd_go-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' +@NATIVE_TRUE@ grep '^--- ' cmd_go-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' | sort -k 2 # check-runtime runs `go test runtime` in our environment. # The runtime package is also tested as part of libgo, @@ -765,15 +766,15 @@ mostlyclean-local: @NATIVE_TRUE@ GOARCH=`$(abs_builddir)/go$(EXEEXT) env GOARCH`; \ @NATIVE_TRUE@ GOOS=`$(abs_builddir)/go$(EXEEXT) env GOOS`; \ @NATIVE_TRUE@ files=`$(SHELL) $(libgosrcdir)/../match.sh --goarch=$${GOARCH} --goos=$${GOOS} --srcdir=$(libgosrcdir)/runtime --extrafiles="$(libgodir)/runtime_sysinfo.go $(libgodir)/sigtab.go" --tag=libffi`; \ -@NATIVE_TRUE@ echo "$(ECHO_ENV) GC='$(abs_builddir)/check-gccgo -fgo-compiling-runtime' GOARCH=$${GOARCH} GOOS=$${GOOS} $(SHELL) $(libgosrcdir)/../testsuite/gotest --goarch=$${GOARCH} --goos=$${GOOS} --basedir=$(libgosrcdir)/.. --srcdir=$(libgosrcdir)/runtime --pkgpath=runtime --pkgfiles='$${files}' -test.v" > runtime-testlog +@NATIVE_TRUE@ echo "$(ECHO_ENV) GC='$(abs_builddir)/check-gccgo -fgo-compiling-runtime' GOARCH=$${GOARCH} GOOS=$${GOOS} $(SHELL) $(libgosrcdir)/../testsuite/gotest --goarch=$${GOARCH} --goos=$${GOOS} --basedir=$(libgosrcdir)/.. --srcdir=$(libgosrcdir)/runtime --pkgpath=runtime --pkgfiles='$${files}' $(GOTESTFLAGS) -test.v" > runtime-testlog @NATIVE_TRUE@ $(CHECK_ENV) \ @NATIVE_TRUE@ GC="$${GCCGO} -fgo-compiling-runtime"; \ @NATIVE_TRUE@ export GC; \ @NATIVE_TRUE@ GOARCH=`$(abs_builddir)/go$(EXEEXT) env GOARCH`; \ @NATIVE_TRUE@ GOOS=`$(abs_builddir)/go$(EXEEXT) env GOOS`; \ @NATIVE_TRUE@ files=`$(SHELL) $(libgosrcdir)/../match.sh --goarch=$${GOARCH} --goos=$${GOOS} --srcdir=$(libgosrcdir)/runtime --extrafiles="$(libgodir)/runtime_sysinfo.go $(libgodir)/sigtab.go" --tag=libffi`; \ -@NATIVE_TRUE@ $(SHELL) $(libgosrcdir)/../testsuite/gotest --goarch=$${GOARCH} --goos=$${GOOS} --basedir=$(libgosrcdir)/.. --srcdir=$(libgosrcdir)/runtime --pkgpath=runtime --pkgfiles="$${files}" -test.v >> runtime-testlog 2>&1 || echo "--- $${fl} go test runtime (0.00s)" >> runtime-testlog -@NATIVE_TRUE@ grep '^--- ' runtime-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' +@NATIVE_TRUE@ $(SHELL) $(libgosrcdir)/../testsuite/gotest --goarch=$${GOARCH} --goos=$${GOOS} --basedir=$(libgosrcdir)/.. --srcdir=$(libgosrcdir)/runtime --pkgpath=runtime --pkgfiles="$${files}" $(GOTESTFLAGS) -test.v >> runtime-testlog 2>&1 || echo "--- $${fl} go test runtime (0.00s)" >> runtime-testlog +@NATIVE_TRUE@ grep '^--- ' runtime-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' | sort -k 2 # check-cgo-test runs `go test misc/cgo/test` in our environment. @NATIVE_TRUE@check-cgo-test: go$(EXEEXT) cgo$(EXEEXT) check-head check-gccgo check-gcc @@ -786,7 +787,7 @@ mostlyclean-local: @NATIVE_TRUE@ GOTRACEBACK=2; \ @NATIVE_TRUE@ export GOTRACEBACK; \ @NATIVE_TRUE@ (cd cgo-test-dir/misc/cgo/test && $(abs_builddir)/go$(EXEEXT) test -test.short -test.v) >> cgo-testlog 2>&1 || echo "--- $${fl} go test misc/cgo/test (0.00s)" >> cgo-testlog -@NATIVE_TRUE@ grep '^--- ' cgo-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' +@NATIVE_TRUE@ grep '^--- ' cgo-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' | sort -k 2 # check-carchive-test runs `go test misc/cgo/testcarchive/carchive_test.go` # in our environment. @@ -800,7 +801,7 @@ mostlyclean-local: @NATIVE_TRUE@ LIBRARY_PATH=`echo $${abs_libgodir}/.libs:$${LIBRARY_PATH} | sed 's,::*,:,g;s,^:*,,;s,:*$$,,'`; \ @NATIVE_TRUE@ export LIBRARY_PATH; \ @NATIVE_TRUE@ (cd carchive-test-dir/misc/cgo/testcarchive && $(abs_builddir)/go$(EXEEXT) test -test.v carchive_test.go) >> carchive-testlog 2>&1 || echo "--- $${fl} go test misc/cgo/testcarchive (0.00s)" >> carchive-testlog -@NATIVE_TRUE@ grep '^--- ' carchive-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' +@NATIVE_TRUE@ grep '^--- ' carchive-testlog | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' | sort -k 2 # The check targets runs the tests and assembles the output files. @NATIVE_TRUE@check: check-head check-go-tool check-runtime check-cgo-test check-carchive-test @@ -811,7 +812,7 @@ mostlyclean-local: @NATIVE_TRUE@ echo "Running $${testname}" >> gotools.sum; \ @NATIVE_TRUE@ echo "Running $${testname}" >> gotools.log; \ @NATIVE_TRUE@ sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' < $${file} >> gotools.log; \ -@NATIVE_TRUE@ grep '^--- ' $${file} | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' -e 's/SKIP/UNTESTED/' >> gotools.sum; \ +@NATIVE_TRUE@ grep '^--- ' $${file} | sed -e 's/^--- \(.*\) ([^)]*)$$/\1/' -e 's/SKIP/UNTESTED/' | sort -k 2 >> gotools.sum; \ @NATIVE_TRUE@ done @NATIVE_TRUE@ @echo >> gotools.sum @NATIVE_TRUE@ @echo " === gotools Summary ===" >> gotools.sum diff --git a/libgo/go/runtime/testdata/testprogcgo/numgoroutine.go b/libgo/go/runtime/testdata/testprogcgo/numgoroutine.go index 12fda49..68f1738 100644 --- a/libgo/go/runtime/testdata/testprogcgo/numgoroutine.go +++ b/libgo/go/runtime/testdata/testprogcgo/numgoroutine.go @@ -75,6 +75,7 @@ func checkNumGoroutine(label string, want int) (string, bool) { sbuf := make([]byte, 32<<10) sbuf = sbuf[:runtime.Stack(sbuf, true)] n = strings.Count(string(sbuf), "goroutine ") + n -= strings.Count(string(sbuf), "goroutine in C code") if n != want { fmt.Printf("%s Stack: want %d; got %d:\n%s\n", label, want, n, string(sbuf)) return "", false diff --git a/libgo/go/runtime/traceback_gccgo.go b/libgo/go/runtime/traceback_gccgo.go index f29ccd7..37c5698 100644 --- a/libgo/go/runtime/traceback_gccgo.go +++ b/libgo/go/runtime/traceback_gccgo.go @@ -216,7 +216,7 @@ func tracebackothers(me *g) { print("\tgoroutine running on other thread; stack unavailable\n") printcreatedby(gp) } else if readgstatus(gp)&^_Gscan == _Gsyscall { - print("\tin C code; stack unavailable\n") + print("\tgoroutine in C code; stack unavailable\n") printcreatedby(gp) } else { gp.traceback = &tb diff --git a/libstdc++-v3/ChangeLog b/libstdc++-v3/ChangeLog index 28a9609..f9424a5 100644 --- a/libstdc++-v3/ChangeLog +++ b/libstdc++-v3/ChangeLog @@ -1,3 +1,27 @@ +2017-09-19 Jonathan Wakely <jwakely@redhat.com> + + PR libstdc++/71500 + * include/bits/regex_executor.tcc + (_Backref_matcher<BidIt, regex_traits<C>>::_M_apply): Use + std::__equal4 instead of C++14 4-iterator overloads of std::equal. + * include/bits/stl_algobase.h (__equal4): New functions implementing + 4-iterator overloads of std::equal for use in C++11. + (equal(It1, It1, It2, It2), equal(It1, It1, It2, It2, BinaryPred)): + Move function bodies to new __equal4 functions. + * testsuite/28_regex/simple_c++11.cc: New. + + PR libstdc++/82254 + * include/std/type_traits (__is_invocable): Add partial specialization + for INVOKE<void> case and remove is_void<R> check from partial + specialization for INVOKE<R> case. + (__is_nt_invocable_impl): New helper for is_nothrow_invocable_r. + (is_nothrow_invocable_r): Use __is_nt_invocable_impl. + * testsuite/20_util/is_nothrow_invocable/value.cc: Add tests for + conversions that can throw or fail to convert. Use static assert + strings to explain negative results. + * testsuite/20_util/is_nothrow_invocable/value_ext.cc: Use + is_nothrow_constructible in is_nt_invocable_conv. + 2017-09-18 Jonathan Wakely <jwakely@redhat.com> PR libstdc++/81468 @@ -342,7 +366,7 @@ 2017-09-11 Tim Shen <timshen@google.com> PR libstdc++/71500 - * include/bits/regex_executor.tcc: Support icase in regex_tratis<...> + * include/bits/regex_executor.tcc: Support icase in regex_traits<...> for back reference matches. * testsuite/28_regex/regression.cc: Test case. diff --git a/libstdc++-v3/include/bits/regex_executor.tcc b/libstdc++-v3/include/bits/regex_executor.tcc index f6149fe..2ceba35 100644 --- a/libstdc++-v3/include/bits/regex_executor.tcc +++ b/libstdc++-v3/include/bits/regex_executor.tcc @@ -366,17 +366,17 @@ namespace __detail _BiIter __actual_end) { if (!_M_icase) - return std::equal(__expected_begin, __expected_end, - __actual_begin, __actual_end); + return std::__equal4(__expected_begin, __expected_end, + __actual_begin, __actual_end); typedef std::ctype<_CharT> __ctype_type; const auto& __fctyp = use_facet<__ctype_type>(_M_traits.getloc()); - return std::equal(__expected_begin, __expected_end, - __actual_begin, __actual_end, - [this, &__fctyp](_CharT __lhs, _CharT __rhs) - { - return __fctyp.tolower(__lhs) - == __fctyp.tolower(__rhs); - }); + return std::__equal4(__expected_begin, __expected_end, + __actual_begin, __actual_end, + [this, &__fctyp](_CharT __lhs, _CharT __rhs) + { + return __fctyp.tolower(__lhs) + == __fctyp.tolower(__rhs); + }); } bool _M_icase; diff --git a/libstdc++-v3/include/bits/stl_algobase.h b/libstdc++-v3/include/bits/stl_algobase.h index f68ecb2..a80934c 100644 --- a/libstdc++-v3/include/bits/stl_algobase.h +++ b/libstdc++-v3/include/bits/stl_algobase.h @@ -1082,6 +1082,60 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO return true; } +#if __cplusplus >= 201103L + // 4-iterator version of std::equal<It1, It2> for use in C++11. + template<typename _II1, typename _II2> + inline bool + __equal4(_II1 __first1, _II1 __last1, _II2 __first2, _II2 __last2) + { + using _RATag = random_access_iterator_tag; + using _Cat1 = typename iterator_traits<_II1>::iterator_category; + using _Cat2 = typename iterator_traits<_II2>::iterator_category; + using _RAIters = __and_<is_same<_Cat1, _RATag>, is_same<_Cat2, _RATag>>; + if (_RAIters()) + { + auto __d1 = std::distance(__first1, __last1); + auto __d2 = std::distance(__first2, __last2); + if (__d1 != __d2) + return false; + return _GLIBCXX_STD_A::equal(__first1, __last1, __first2); + } + + for (; __first1 != __last1 && __first2 != __last2; + ++__first1, (void)++__first2) + if (!(*__first1 == *__first2)) + return false; + return __first1 == __last1 && __first2 == __last2; + } + + // 4-iterator version of std::equal<It1, It2, BinaryPred> for use in C++11. + template<typename _II1, typename _II2, typename _BinaryPredicate> + inline bool + __equal4(_II1 __first1, _II1 __last1, _II2 __first2, _II2 __last2, + _BinaryPredicate __binary_pred) + { + using _RATag = random_access_iterator_tag; + using _Cat1 = typename iterator_traits<_II1>::iterator_category; + using _Cat2 = typename iterator_traits<_II2>::iterator_category; + using _RAIters = __and_<is_same<_Cat1, _RATag>, is_same<_Cat2, _RATag>>; + if (_RAIters()) + { + auto __d1 = std::distance(__first1, __last1); + auto __d2 = std::distance(__first2, __last2); + if (__d1 != __d2) + return false; + return _GLIBCXX_STD_A::equal(__first1, __last1, __first2, + __binary_pred); + } + + for (; __first1 != __last1 && __first2 != __last2; + ++__first1, (void)++__first2) + if (!bool(__binary_pred(*__first1, *__first2))) + return false; + return __first1 == __last1 && __first2 == __last2; + } +#endif // C++11 + #if __cplusplus > 201103L #define __cpp_lib_robust_nonmodifying_seq_ops 201304 @@ -1112,24 +1166,7 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO __glibcxx_requires_valid_range(__first1, __last1); __glibcxx_requires_valid_range(__first2, __last2); - using _RATag = random_access_iterator_tag; - using _Cat1 = typename iterator_traits<_II1>::iterator_category; - using _Cat2 = typename iterator_traits<_II2>::iterator_category; - using _RAIters = __and_<is_same<_Cat1, _RATag>, is_same<_Cat2, _RATag>>; - if (_RAIters()) - { - auto __d1 = std::distance(__first1, __last1); - auto __d2 = std::distance(__first2, __last2); - if (__d1 != __d2) - return false; - return _GLIBCXX_STD_A::equal(__first1, __last1, __first2); - } - - for (; __first1 != __last1 && __first2 != __last2; - ++__first1, (void)++__first2) - if (!(*__first1 == *__first2)) - return false; - return __first1 == __last1 && __first2 == __last2; + return _GLIBCXX_STD_A::__equal4(__first1, __last1, __first2, __last2); } /** @@ -1159,27 +1196,10 @@ _GLIBCXX_BEGIN_NAMESPACE_ALGO __glibcxx_requires_valid_range(__first1, __last1); __glibcxx_requires_valid_range(__first2, __last2); - using _RATag = random_access_iterator_tag; - using _Cat1 = typename iterator_traits<_IIter1>::iterator_category; - using _Cat2 = typename iterator_traits<_IIter2>::iterator_category; - using _RAIters = __and_<is_same<_Cat1, _RATag>, is_same<_Cat2, _RATag>>; - if (_RAIters()) - { - auto __d1 = std::distance(__first1, __last1); - auto __d2 = std::distance(__first2, __last2); - if (__d1 != __d2) - return false; - return _GLIBCXX_STD_A::equal(__first1, __last1, __first2, - __binary_pred); - } - - for (; __first1 != __last1 && __first2 != __last2; - ++__first1, (void)++__first2) - if (!bool(__binary_pred(*__first1, *__first2))) - return false; - return __first1 == __last1 && __first2 == __last2; + return _GLIBCXX_STD_A::__equal4(__first1, __last1, __first2, __last2, + __binary_pred); } -#endif +#endif // C++14 /** * @brief Performs @b dictionary comparison on ranges. diff --git a/libstdc++-v3/include/std/type_traits b/libstdc++-v3/include/std/type_traits index 15b0d92..036f766 100644 --- a/libstdc++-v3/include/std/type_traits +++ b/libstdc++-v3/include/std/type_traits @@ -2592,7 +2592,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION template<typename _Result, typename _Ret> struct __is_invocable_impl<_Result, _Ret, __void_t<typename _Result::type>> - : __or_<is_void<_Ret>, is_convertible<typename _Result::type, _Ret>>::type + : is_convertible<typename _Result::type, _Ret>::type + { }; + + template<typename _Result> + struct __is_invocable_impl<_Result, void, __void_t<typename _Result::type>> + : true_type { }; template<typename _Fn, typename... _ArgTypes> @@ -2691,10 +2696,26 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION __call_is_nothrow_<_Fn, _ArgTypes...>>::type { }; + template<typename _Result, typename _Ret, typename = void> + struct __is_nt_invocable_impl : false_type { }; + + template<typename _Result, typename _Ret> + struct __is_nt_invocable_impl<_Result, _Ret, + __void_t<typename _Result::type>> + : __and_<is_convertible<typename _Result::type, _Ret>, + is_nothrow_constructible<_Ret, typename _Result::type>> + { }; + + template<typename _Result> + struct __is_nt_invocable_impl<_Result, void, + __void_t<typename _Result::type>> + : true_type + { }; + /// std::is_nothrow_invocable_r template<typename _Ret, typename _Fn, typename... _ArgTypes> struct is_nothrow_invocable_r - : __and_<__is_invocable_impl<__invoke_result<_Fn, _ArgTypes...>, _Ret>, + : __and_<__is_nt_invocable_impl<__invoke_result<_Fn, _ArgTypes...>, _Ret>, __call_is_nothrow_<_Fn, _ArgTypes...>>::type { }; diff --git a/libstdc++-v3/testsuite/20_util/is_nothrow_invocable/value.cc b/libstdc++-v3/testsuite/20_util/is_nothrow_invocable/value.cc index 4ccb459..dfa76aa 100644 --- a/libstdc++-v3/testsuite/20_util/is_nothrow_invocable/value.cc +++ b/libstdc++-v3/testsuite/20_util/is_nothrow_invocable/value.cc @@ -40,6 +40,10 @@ template<typename R, typename... T> void test01() { + struct T { T(int) { } }; + struct NT { NT(int) noexcept { } }; + struct Ex { explicit Ex(int) noexcept { } }; + using func_type = void(*)(); static_assert( ! is_nt_invocable< func_type>(), ""); @@ -55,28 +59,46 @@ void test01() static_assert( ! is_nt_invocable< mem_type, int >(), ""); static_assert( ! is_nt_invocable< mem_type, int& >(), ""); - static_assert( is_nt_invocable< mem_type, X& >(), ""); - static_assert( is_nt_invocable_r< int, mem_type, X& >(), ""); - static_assert( is_nt_invocable_r< int&, mem_type, X& >(), ""); - static_assert( is_nt_invocable_r< long, mem_type, X& >(), ""); - static_assert( is_nt_invocable_r< int&, mem_type, X* >(), ""); + static_assert( is_nt_invocable< mem_type, X& >(), ""); + static_assert( is_nt_invocable_r< int, mem_type, X& >(), ""); + static_assert( is_nt_invocable_r< int&, mem_type, X& >(), ""); + static_assert( is_nt_invocable_r< long, mem_type, X& >(), ""); + static_assert( ! is_nt_invocable_r< long&, mem_type, X& >(), + "conversion fails, cannot bind long& to int"); + static_assert( is_nt_invocable_r< int&, mem_type, X* >(), ""); + + static_assert( ! is_nt_invocable_r< T, mem_type, X& >(), + "conversion throws"); + static_assert( is_nt_invocable_r< NT, mem_type, X& >(), ""); + static_assert( ! is_nt_invocable_r< Ex, mem_type, X& >(), + "conversion fails, would use explicit constructor"); using memfun_type = int (X::*)(); - static_assert( ! is_nt_invocable< memfun_type >(), ""); - static_assert( ! is_nt_invocable< memfun_type, int >(), ""); - static_assert( ! is_nt_invocable< memfun_type, int& >(), ""); - static_assert( ! is_nt_invocable< memfun_type, X& >(), ""); - static_assert( ! is_nt_invocable< memfun_type, X* >(), ""); + static_assert( ! is_nt_invocable< memfun_type >(), "no object"); + static_assert( ! is_nt_invocable< memfun_type, int >(), "no object"); + static_assert( ! is_nt_invocable< memfun_type, int& >(), "no object"); + static_assert( ! is_nt_invocable< memfun_type, X& >(), "call throws"); + static_assert( ! is_nt_invocable< memfun_type, X* >(), "call throws"); + + static_assert( ! is_nt_invocable_r< T, memfun_type, X& >(), "call throws"); + static_assert( ! is_nt_invocable_r< NT, memfun_type, X& >(), "call throws"); + static_assert( ! is_nt_invocable_r< Ex, memfun_type, X& >(), "call throws"); #if __cpp_noexcept_function_type using memfun_type_nt = int (X::*)() noexcept; - static_assert( ! is_nt_invocable< memfun_type_nt >(), ""); - static_assert( ! is_nt_invocable< memfun_type_nt, int >(), ""); - static_assert( ! is_nt_invocable< memfun_type_nt, int& >(), ""); + static_assert( ! is_nt_invocable< memfun_type_nt >(), "no object"); + static_assert( ! is_nt_invocable< memfun_type_nt, int >(), "no object"); + static_assert( ! is_nt_invocable< memfun_type_nt, int& >(), "no object"); static_assert( is_nt_invocable< memfun_type_nt, X& >(), ""); static_assert( is_nt_invocable< memfun_type_nt, X* >(), ""); + + static_assert( ! is_nt_invocable_r< T, memfun_type_nt, X& >(), + "conversion throws"); + static_assert( is_nt_invocable_r< NT, memfun_type_nt, X& >(), ""); + static_assert( ! is_nt_invocable_r< Ex, memfun_type_nt, X& >(), + "conversion fails, would use explicit constructor"); #endif struct F { @@ -89,12 +111,44 @@ void test01() }; using CF = const F; - static_assert( ! is_nt_invocable_r< int&, F >(), ""); - static_assert( is_nt_invocable_r< long&, CF >(), ""); - static_assert( ! is_nt_invocable_r< short&, F, int >(), "" ); - static_assert( is_nt_invocable_r< char&, F&, int >(), "" ); - static_assert( is_nt_invocable_r< char&, CF, int >(), "" ); - static_assert( is_nt_invocable_r< char&, CF&, int >(), "" ); - - static_assert( ! is_nt_invocable< F, int, int >(), ""); + static_assert( ! is_nt_invocable< F >(), "call throws"); + static_assert( is_nt_invocable< CF >(), ""); + + static_assert( ! is_nt_invocable_r< int&, F >(), "call throws"); + static_assert( is_nt_invocable_r< long&, CF >(), ""); + static_assert( ! is_nt_invocable_r< T, F >(), "call throws"); + static_assert( ! is_nt_invocable_r< NT, F >(), "call throws"); + static_assert( ! is_nt_invocable_r< Ex, F >(), "call throws"); + static_assert( ! is_nt_invocable_r< T, CF >(), "conversion throws"); + static_assert( is_nt_invocable_r< NT, CF >(), "" ); + static_assert( ! is_nt_invocable_r< Ex, CF >(), "conversion fails"); + + static_assert( ! is_nt_invocable< F, int >(), "call throws"); + static_assert( is_nt_invocable< F&, int >(), ""); + + static_assert( ! is_nt_invocable_r< short&, F, int >(), + "call throws" ); + static_assert( is_nt_invocable_r< char&, F&, int >(), ""); + static_assert( ! is_nt_invocable_r< T, F&, int >(), + "conversion throws"); + static_assert( is_nt_invocable_r< NT, F&, int >(), ""); + static_assert( ! is_nt_invocable_r< Ex, F&, int >(), + "conversion fails, would use explicit constructor"); + + static_assert( is_nt_invocable< CF, int >(), ""); + static_assert( is_nt_invocable< CF&, int >(), ""); + + static_assert( is_nt_invocable_r< char&, CF, int >(), ""); + static_assert( is_nt_invocable_r< char&, CF&, int >(), ""); + + static_assert( ! is_nt_invocable_r< T, CF&, int >(), + "conversion throws"); + static_assert( is_nt_invocable_r< NT, CF&, int >(), ""); + static_assert( ! is_nt_invocable_r< Ex, CF&, int >(), + "conversion fails, would use explicit constructor"); + + static_assert( ! is_nt_invocable< F, int, int >(), + "would call private member"); + static_assert( ! is_nt_invocable_r<void, F, int, int >(), + "would call private member"); } diff --git a/libstdc++-v3/testsuite/20_util/is_nothrow_invocable/value_ext.cc b/libstdc++-v3/testsuite/20_util/is_nothrow_invocable/value_ext.cc index 7217324..7fd3d92 100644 --- a/libstdc++-v3/testsuite/20_util/is_nothrow_invocable/value_ext.cc +++ b/libstdc++-v3/testsuite/20_util/is_nothrow_invocable/value_ext.cc @@ -27,7 +27,9 @@ template<typename... T> constexpr bool is_nt_invocable_conv(std::true_type) { using result_type = typename std::__invoke_result<T...>::type; - return std::is_void<R>::value || std::is_convertible<result_type, R>::value; + return std::is_void<R>::value + || (std::is_convertible<result_type, R>::value + && std::is_nothrow_constructible<R, result_type>::value); } template<typename R, typename... T> diff --git a/libstdc++-v3/testsuite/28_regex/simple_c++11.cc b/libstdc++-v3/testsuite/28_regex/simple_c++11.cc new file mode 100644 index 0000000..2cfa503 --- /dev/null +++ b/libstdc++-v3/testsuite/28_regex/simple_c++11.cc @@ -0,0 +1,27 @@ +// Copyright (C) 2017 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/>. + +// { dg-options "-std=gnu++11" } +// { dg-do compile } + +#include <regex> + +// Ensure compilation of trivial example still works with C++11. +// https://gcc.gnu.org/ml/libstdc++/2017-09/msg00040.html +std::regex r{""}; +std::cmatch m; +bool b = regex_match("", m, r); |