diff options
author | Martin Liska <mliska@suse.cz> | 2022-10-13 15:54:17 +0200 |
---|---|---|
committer | Martin Liska <mliska@suse.cz> | 2022-10-13 15:54:17 +0200 |
commit | bd21c04269deded2c7476ceca1100a26f28ea526 (patch) | |
tree | 197bf75eedac69362078a4ccc0afe5615c45c327 /gcc/cp | |
parent | d9e7934d25da4a78ffef1f738206aa1d897911df (diff) | |
parent | 786e4c024f941671a233f5779d73a5d22f4e9588 (diff) | |
download | gcc-bd21c04269deded2c7476ceca1100a26f28ea526.zip gcc-bd21c04269deded2c7476ceca1100a26f28ea526.tar.gz gcc-bd21c04269deded2c7476ceca1100a26f28ea526.tar.bz2 |
Merge branch 'master' into devel/sphinx
Diffstat (limited to 'gcc/cp')
-rw-r--r-- | gcc/cp/ChangeLog | 93 | ||||
-rw-r--r-- | gcc/cp/call.cc | 79 | ||||
-rw-r--r-- | gcc/cp/constexpr.cc | 20 | ||||
-rw-r--r-- | gcc/cp/cp-gimplify.cc | 7 | ||||
-rw-r--r-- | gcc/cp/cp-tree.h | 38 | ||||
-rw-r--r-- | gcc/cp/error.cc | 16 | ||||
-rw-r--r-- | gcc/cp/except.cc | 23 | ||||
-rw-r--r-- | gcc/cp/mangle.cc | 9 | ||||
-rw-r--r-- | gcc/cp/module.cc | 8 | ||||
-rw-r--r-- | gcc/cp/name-lookup.cc | 2 | ||||
-rw-r--r-- | gcc/cp/name-lookup.h | 5 | ||||
-rw-r--r-- | gcc/cp/parser.cc | 24 | ||||
-rw-r--r-- | gcc/cp/pt.cc | 11 | ||||
-rw-r--r-- | gcc/cp/tree.cc | 52 | ||||
-rw-r--r-- | gcc/cp/typeck.cc | 34 |
15 files changed, 218 insertions, 203 deletions
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 3aa9f03..320b465 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,96 @@ +2022-10-12 Marek Polacek <polacek@redhat.com> + + * call.cc (standard_conversion): Remove LOOKUP_PREFER_RVALUE code. + (reference_binding): Honor clk_implicit_rval even pre-C++20. + (implicit_conversion_1): Remove LOOKUP_PREFER_RVALUE code. + (build_user_type_conversion_1): Likewise. + (convert_like_internal): Likewise. + (build_over_call): Likewise. + * cp-tree.h (LOOKUP_PREFER_RVALUE): Remove. + (LOOKUP_NO_NARROWING): Adjust definition. + * except.cc (build_throw): Don't perform two overload resolutions. + * typeck.cc (maybe_warn_pessimizing_move): Don't use + LOOKUP_PREFER_RVALUE. + (check_return_expr): Don't perform two overload resolutions. + +2022-10-12 Jason Merrill <jason@redhat.com> + + DR 2631 + * cp-tree.h (source_location_current_p): Remove. + * name-lookup.h (struct cp_binding_level): Remove + immediate_fn_ctx_p. + * call.cc (in_immediate_context): All default args + and DMI are potentially immediate context. + (immediate_invocation_p): Don't treat source_location specially. + (struct in_consteval_if_p_temp_override): Move to cp-tree.h. + * constexpr.cc (get_nth_callarg): Move to cp-tree.h. + * cp-gimplify.cc (cp_fold_r): Don't fold consteval. + * name-lookup.cc (begin_scope): Don't set immediate_fn_ctx_p. + * parser.cc (cp_parser_lambda_declarator_opt): Likewise. + (cp_parser_direct_declarator): Likewise. + * pt.cc (tsubst_default_argument): Open sk_function_parms level. + * tree.cc (source_location_current_p): Remove. + (bot_replace): Fold consteval here. + (break_out_target_exprs): Handle errors. + +2022-10-11 Patrick Palka <ppalka@redhat.com> + + PR c++/100134 + * pt.cc (tsubst_friend_function): Propagate DECL_MODULE_PURVIEW_P + from the introduced namespace-scope function to the namespace. + +2022-10-11 Patrick Palka <ppalka@redhat.com> + + PR c++/99377 + * module.cc (lazy_load_binding): Clear processing_template_decl. + (lazy_load_pendings): Likewise. + +2022-10-10 Nathan Sidwell <nathan@acm.org> + + * mangle.cc (write_prefix): Add VAR_DECL & FIELD_DECL to + substitution table under abi=18. Note possible mismatch. + +2022-10-10 Marek Polacek <polacek@redhat.com> + + PR c++/106937 + * error.cc: Include "attribs.h". + (dump_type_prefix): Print only GNU attributes here. + (dump_type_suffix): Print standard attributes here. + +2022-10-08 Jason Merrill <jason@redhat.com> + + * cp-tree.h (TARGET_EXPR_ELIDING_P): New. + (unsafe_copy_elision_p, set_target_expr_eliding) + (cp_build_init_expr): Declare. + * call.cc (unsafe_copy_elision_p): No longer static. + (build_over_call, build_special_member_call) + (build_new_method_call): Use cp_build_init_expr. + * coroutines.cc (expand_one_await_expression) + (build_actor_fn, flatten_await_stmt, handle_nested_conditionals) + (await_statement_walker, morph_fn_to_coro): Use cp_build_init_expr. + * cp-gimplify.cc (cp_gimplify_init_expr) + (cp_gimplify_expr): Check TARGET_EXPR_ELIDING_P. + (cp_fold_r): Propagate it. + (cp_fold): Use cp_build_init_expr. + * decl.cc (check_initializer): Use cp_build_init_expr. + * except.cc (build_throw): Use cp_build_init_expr. + * init.cc (get_nsdmi): Call set_target_expr_eliding. + (perform_member_init, expand_default_init, expand_aggr_init_1) + (build_new_1, build_vec_init): Use cp_build_init_expr. + * method.cc (do_build_copy_constructor): Use cp_build_init_expr. + * semantics.cc (simplify_aggr_init_expr, finalize_nrv_r) + (finish_omp_reduction_clause): Use cp_build_init_expr. + * tree.cc (build_target_expr): Call set_target_expr_eliding. + (bot_manip): Copy TARGET_EXPR_ELIDING_P. + * typeck.cc (cp_build_modify_expr): Call set_target_expr_eliding. + (check_return_expr): Use cp_build_modify_expr. + * typeck2.cc (split_nonconstant_init_1) + (split_nonconstant_init): Use cp_build_init_expr. + (massage_init_elt): Call set_target_expr_eliding. + (process_init_constructor_record): Clear TARGET_EXPR_ELIDING_P on + unsafe copy elision. + (set_target_expr_eliding, cp_build_init_expr): New. + 2022-10-07 Marek Polacek <polacek@redhat.com> PR c++/107085 diff --git a/gcc/cp/call.cc b/gcc/cp/call.cc index 70ec964..b9c08d6 100644 --- a/gcc/cp/call.cc +++ b/gcc/cp/call.cc @@ -1272,9 +1272,6 @@ standard_conversion (tree to, tree from, tree expr, bool c_cast_p, } } conv = build_conv (ck_rvalue, from, conv); - if (flags & LOOKUP_PREFER_RVALUE) - /* Tell convert_like to set LOOKUP_PREFER_RVALUE. */ - conv->rvaluedness_matches_p = true; /* If we're performing copy-initialization, remember to skip explicit constructors. */ if (flags & LOOKUP_ONLYCONVERTING) @@ -1572,9 +1569,6 @@ standard_conversion (tree to, tree from, tree expr, bool c_cast_p, type. A temporary object is created to hold the result of the conversion unless we're binding directly to a reference. */ conv->need_temporary_p = !(flags & LOOKUP_NO_TEMP_BIND); - if (flags & LOOKUP_PREFER_RVALUE) - /* Tell convert_like to set LOOKUP_PREFER_RVALUE. */ - conv->rvaluedness_matches_p = true; /* If we're performing copy-initialization, remember to skip explicit constructors. */ if (flags & LOOKUP_ONLYCONVERTING) @@ -1883,7 +1877,7 @@ reference_binding (tree rto, tree rfrom, tree expr, bool c_cast_p, int flags, /* Unless it's really a C++20 lvalue being treated as an xvalue. But in C++23, such an expression is just an xvalue, not a special lvalue, so the binding is once again ill-formed. */ - && !(cxx_dialect == cxx20 + && !(cxx_dialect <= cxx20 && (gl_kind & clk_implicit_rval)) && (!CP_TYPE_CONST_NON_VOLATILE_P (to) || (flags & LOOKUP_NO_RVAL_BIND)) @@ -2044,9 +2038,8 @@ implicit_conversion_1 (tree to, tree from, tree expr, bool c_cast_p, /* Other flags only apply to the primary function in overload resolution, or after we've chosen one. */ flags &= (LOOKUP_ONLYCONVERTING|LOOKUP_NO_CONVERSION|LOOKUP_COPY_PARM - |LOOKUP_NO_TEMP_BIND|LOOKUP_NO_RVAL_BIND|LOOKUP_PREFER_RVALUE - |LOOKUP_NO_NARROWING|LOOKUP_PROTECT|LOOKUP_NO_NON_INTEGRAL - |LOOKUP_SHORTCUT_BAD_CONVS); + |LOOKUP_NO_TEMP_BIND|LOOKUP_NO_RVAL_BIND|LOOKUP_NO_NARROWING + |LOOKUP_PROTECT|LOOKUP_NO_NON_INTEGRAL|LOOKUP_SHORTCUT_BAD_CONVS); /* FIXME: actually we don't want warnings either, but we can't just have 'complain &= ~(tf_warning|tf_error)' because it would cause @@ -4451,14 +4444,6 @@ build_user_type_conversion_1 (tree totype, tree expr, int flags, if (cand->viable == -1) conv->bad_p = true; - /* We're performing the maybe-rvalue overload resolution and - a conversion function is in play. Reject converting the return - value of the conversion function to a base class. */ - if ((flags & LOOKUP_PREFER_RVALUE) && !DECL_CONSTRUCTOR_P (cand->fn)) - for (conversion *t = cand->second_conv; t; t = next_conversion (t)) - if (t->kind == ck_base) - return NULL; - /* Remember that this was a list-initialization. */ if (flags & LOOKUP_NO_NARROWING) conv->check_narrowing = true; @@ -8292,9 +8277,6 @@ convert_like_internal (conversion *convs, tree expr, tree fn, int argnum, explicit constructors. */ if (convs->copy_init_p) flags |= LOOKUP_ONLYCONVERTING; - if (convs->rvaluedness_matches_p) - /* standard_conversion got LOOKUP_PREFER_RVALUE. */ - flags |= LOOKUP_PREFER_RVALUE; expr = build_temp (expr, totype, flags, &diag_kind, complain); if (diag_kind && complain) { @@ -9301,7 +9283,8 @@ build_trivial_dtor_call (tree instance, bool no_ptr_deref) } /* Return true if in an immediate function context, or an unevaluated operand, - or a subexpression of an immediate invocation. */ + or a default argument/member initializer, or a subexpression of an immediate + invocation. */ bool in_immediate_context () @@ -9309,8 +9292,11 @@ in_immediate_context () return (cp_unevaluated_operand != 0 || (current_function_decl != NULL_TREE && DECL_IMMEDIATE_FUNCTION_P (current_function_decl)) - || (current_binding_level->kind == sk_function_parms - && current_binding_level->immediate_fn_ctx_p) + /* DR 2631: default args and DMI aren't immediately evaluated. + Return true here so immediate_invocation_p returns false. */ + || current_binding_level->kind == sk_function_parms + || current_binding_level->kind == sk_template_parms + || parsing_nsdmi () || in_consteval_if_p); } @@ -9318,28 +9304,12 @@ in_immediate_context () is an immediate invocation. */ static bool -immediate_invocation_p (tree fn, int nargs) +immediate_invocation_p (tree fn) { return (TREE_CODE (fn) == FUNCTION_DECL && DECL_IMMEDIATE_FUNCTION_P (fn) - && !in_immediate_context () - /* As an exception, we defer std::source_location::current () - invocations until genericization because LWG3396 mandates - special behavior for it. */ - && (nargs > 1 || !source_location_current_p (fn))); -} - -/* temp_override for in_consteval_if_p, which can't use make_temp_override - because it is a bitfield. */ - -struct in_consteval_if_p_temp_override { - bool save_in_consteval_if_p; - in_consteval_if_p_temp_override () - : save_in_consteval_if_p (in_consteval_if_p) {} - void reset () { in_consteval_if_p = save_in_consteval_if_p; } - ~in_consteval_if_p_temp_override () - { reset (); } -}; + && !in_immediate_context ()); +} /* Subroutine of the various build_*_call functions. Overload resolution has chosen a winning candidate CAND; build up a CALL_EXPR accordingly. @@ -9398,7 +9368,7 @@ build_over_call (struct z_candidate *cand, int flags, tsubst_flags_t complain) SET_EXPR_LOCATION (expr, input_location); if (TREE_THIS_VOLATILE (fn) && cfun) current_function_returns_abnormally = 1; - if (immediate_invocation_p (fn, vec_safe_length (args))) + if (immediate_invocation_p (fn)) { tree obj_arg = NULL_TREE, exprimm = expr; if (DECL_CONSTRUCTOR_P (fn)) @@ -9543,7 +9513,7 @@ build_over_call (struct z_candidate *cand, int flags, tsubst_flags_t complain) in_consteval_if_p_temp_override icip; /* If the call is immediate function invocation, make sure taking address of immediate functions is allowed in its arguments. */ - if (immediate_invocation_p (STRIP_TEMPLATE (fn), nargs)) + if (immediate_invocation_p (STRIP_TEMPLATE (fn))) in_consteval_if_p = true; /* The implicit parameters to a constructor are not considered by overload @@ -9572,23 +9542,6 @@ build_over_call (struct z_candidate *cand, int flags, tsubst_flags_t complain) ++arg_index; parm = TREE_CHAIN (parm); } - - if (cxx_dialect < cxx20 - && (cand->flags & LOOKUP_PREFER_RVALUE)) - { - /* The implicit move specified in 15.8.3/3 fails "...if the type of - the first parameter of the selected constructor is not an rvalue - reference to the object's type (possibly cv-qualified)...." */ - gcc_assert (!(complain & tf_error)); - tree ptype = convs[0]->type; - /* Allow calling a by-value converting constructor even though it - isn't permitted by the above, because we've allowed it since GCC 5 - (PR58051) and it's allowed in C++20. But don't call a copy - constructor. */ - if ((TYPE_REF_P (ptype) && !TYPE_REF_IS_RVALUE (ptype)) - || CONVERSION_RANK (convs[0]) > cr_exact) - return error_mark_node; - } } /* Bypass access control for 'this' parameter. */ else if (TREE_CODE (TREE_TYPE (fn)) == METHOD_TYPE) @@ -10072,7 +10025,7 @@ build_over_call (struct z_candidate *cand, int flags, tsubst_flags_t complain) if (TREE_CODE (fn) == ADDR_EXPR) { tree fndecl = STRIP_TEMPLATE (TREE_OPERAND (fn, 0)); - if (immediate_invocation_p (fndecl, nargs)) + if (immediate_invocation_p (fndecl)) { tree obj_arg = NULL_TREE; /* Undo convert_from_reference called by build_cxx_call. */ diff --git a/gcc/cp/constexpr.cc b/gcc/cp/constexpr.cc index 06dcd71..2038f43 100644 --- a/gcc/cp/constexpr.cc +++ b/gcc/cp/constexpr.cc @@ -1324,26 +1324,6 @@ save_fundef_copy (tree fun, tree copy) *slot = copy; } -/* We have an expression tree T that represents a call, either CALL_EXPR - or AGGR_INIT_EXPR. Return the Nth argument. */ - -static inline tree -get_nth_callarg (tree t, int n) -{ - switch (TREE_CODE (t)) - { - case CALL_EXPR: - return CALL_EXPR_ARG (t, n); - - case AGGR_INIT_EXPR: - return AGGR_INIT_EXPR_ARG (t, n); - - default: - gcc_unreachable (); - return NULL; - } -} - /* Whether our evaluation wants a prvalue (e.g. CONSTRUCTOR or _CST), a glvalue (e.g. VAR_DECL or _REF), or nothing. */ diff --git a/gcc/cp/cp-gimplify.cc b/gcc/cp/cp-gimplify.cc index d0e12c9..a937060 100644 --- a/gcc/cp/cp-gimplify.cc +++ b/gcc/cp/cp-gimplify.cc @@ -1010,13 +1010,6 @@ cp_fold_r (tree *stmt_p, int *walk_subtrees, void *data_) } break; - case CALL_EXPR: - if (tree fndecl = cp_get_callee_fndecl_nofold (stmt)) - if (DECL_IMMEDIATE_FUNCTION_P (fndecl) - && source_location_current_p (fndecl)) - *stmt_p = stmt = cxx_constant_value (stmt); - break; - default: break; } diff --git a/gcc/cp/cp-tree.h b/gcc/cp/cp-tree.h index ab6f85a..3b67be6 100644 --- a/gcc/cp/cp-tree.h +++ b/gcc/cp/cp-tree.h @@ -2030,6 +2030,18 @@ make_temp_override (T& var, type_identity_t<T> overrider) return { var, overrider }; } +/* temp_override for in_consteval_if_p, which can't use make_temp_override + because it is a bitfield. */ + +struct in_consteval_if_p_temp_override { + bool save_in_consteval_if_p; + in_consteval_if_p_temp_override () + : save_in_consteval_if_p (in_consteval_if_p) {} + void reset () { in_consteval_if_p = save_in_consteval_if_p; } + ~in_consteval_if_p_temp_override () + { reset (); } +}; + /* The cached class binding level, from the most recently exited class, or NULL if none. */ @@ -4201,6 +4213,25 @@ more_aggr_init_expr_args_p (const aggr_init_expr_arg_iterator *iter) for ((arg) = first_aggr_init_expr_arg ((call), &(iter)); (arg); \ (arg) = next_aggr_init_expr_arg (&(iter))) +/* We have an expression tree T that represents a call, either CALL_EXPR + or AGGR_INIT_EXPR. Return a reference to the Nth argument. */ + +static inline tree& +get_nth_callarg (tree t, int n) +{ + switch (TREE_CODE (t)) + { + case CALL_EXPR: + return CALL_EXPR_ARG (t, n); + + case AGGR_INIT_EXPR: + return AGGR_INIT_EXPR_ARG (t, n); + + default: + gcc_unreachable (); + } +} + /* VEC_INIT_EXPR accessors. */ #define VEC_INIT_EXPR_SLOT(NODE) TREE_OPERAND (VEC_INIT_EXPR_CHECK (NODE), 0) #define VEC_INIT_EXPR_INIT(NODE) TREE_OPERAND (VEC_INIT_EXPR_CHECK (NODE), 1) @@ -5843,12 +5874,8 @@ enum overload_flags { NO_SPECIAL = 0, DTOR_FLAG, TYPENAME_FLAG }; #define LOOKUP_DESTRUCTOR (1 << 5) /* Do not permit references to bind to temporaries. */ #define LOOKUP_NO_TEMP_BIND (1 << 6) -/* We're trying to treat an lvalue as an rvalue. */ -/* FIXME remove when we extend the P1825 semantics to all standard modes, the - C++20 approach uses IMPLICIT_RVALUE_P instead. */ -#define LOOKUP_PREFER_RVALUE (LOOKUP_NO_TEMP_BIND << 1) /* We're inside an init-list, so narrowing conversions are ill-formed. */ -#define LOOKUP_NO_NARROWING (LOOKUP_PREFER_RVALUE << 1) +#define LOOKUP_NO_NARROWING (LOOKUP_NO_TEMP_BIND << 1) /* We're looking up a constructor for list-initialization. */ #define LOOKUP_LIST_INIT_CTOR (LOOKUP_NO_NARROWING << 1) /* This is the first parameter of a copy constructor. */ @@ -7880,7 +7907,6 @@ extern tree bind_template_template_parm (tree, tree); extern tree array_type_nelts_total (tree); extern tree array_type_nelts_top (tree); extern bool array_of_unknown_bound_p (const_tree); -extern bool source_location_current_p (tree); extern tree break_out_target_exprs (tree, bool = false); extern tree build_ctor_subob_ref (tree, tree, tree); extern tree replace_placeholders (tree, tree, bool * = NULL); diff --git a/gcc/cp/error.cc b/gcc/cp/error.cc index 4514c8b..da8c95c 100644 --- a/gcc/cp/error.cc +++ b/gcc/cp/error.cc @@ -36,6 +36,7 @@ along with GCC; see the file COPYING3. If not see #include "internal-fn.h" #include "gcc-rich-location.h" #include "cp-name-hint.h" +#include "attribs.h" #define pp_separate_with_comma(PP) pp_cxx_separate_with (PP, ',') #define pp_separate_with_semicolon(PP) pp_cxx_separate_with (PP, ';') @@ -897,7 +898,12 @@ dump_type_prefix (cxx_pretty_printer *pp, tree t, int flags) { pp_cxx_whitespace (pp); pp_cxx_left_paren (pp); - pp_c_attributes_display (pp, TYPE_ATTRIBUTES (sub)); + /* If we're dealing with the GNU form of attributes, print this: + void (__attribute__((noreturn)) *f) (); + If it is the standard [[]] attribute, we'll print the attribute + in dump_type_suffix. */ + if (!cxx11_attribute_p (TYPE_ATTRIBUTES (sub))) + pp_c_attributes_display (pp, TYPE_ATTRIBUTES (sub)); } if (TYPE_PTR_P (t)) pp_star (pp); @@ -1030,6 +1036,14 @@ dump_type_suffix (cxx_pretty_printer *pp, tree t, int flags) if (tx_safe_fn_type_p (t)) pp_cxx_ws_string (pp, "transaction_safe"); dump_exception_spec (pp, TYPE_RAISES_EXCEPTIONS (t), flags); + /* If this is the standard [[]] attribute, print + void (*)() [[noreturn]]; */ + if (cxx11_attribute_p (TYPE_ATTRIBUTES (t))) + { + pp_space (pp); + pp_c_attributes_display (pp, TYPE_ATTRIBUTES (t)); + pp->padding = pp_before; + } dump_type_suffix (pp, TREE_TYPE (t), flags); break; } diff --git a/gcc/cp/except.cc b/gcc/cp/except.cc index b8a85ed..703d1d5 100644 --- a/gcc/cp/except.cc +++ b/gcc/cp/except.cc @@ -715,25 +715,10 @@ build_throw (location_t loc, tree exp) treated as an rvalue for the purposes of overload resolution to favor move constructors over copy constructors. */ if (tree moved = treat_lvalue_as_rvalue_p (exp, /*return*/false)) - { - if (cxx_dialect < cxx20) - { - releasing_vec exp_vec (make_tree_vector_single (moved)); - moved = (build_special_member_call - (object, complete_ctor_identifier, &exp_vec, - TREE_TYPE (object), flags|LOOKUP_PREFER_RVALUE, - tf_none)); - if (moved != error_mark_node) - { - exp = moved; - converted = true; - } - } - else - /* In C++20 we just treat the return value as an rvalue that - can bind to lvalue refs. */ - exp = moved; - } + /* In C++20 we treat the return value as an rvalue that + can bind to lvalue refs. In C++23, such an expression is just + an xvalue. */ + exp = moved; /* Call the copy constructor. */ if (!converted) diff --git a/gcc/cp/mangle.cc b/gcc/cp/mangle.cc index f051e76..1215463 100644 --- a/gcc/cp/mangle.cc +++ b/gcc/cp/mangle.cc @@ -1252,7 +1252,14 @@ write_prefix (const tree node) { /* <data-member-prefix> := <member source-name> M */ write_char ('M'); - return; + + /* Before ABI 18, we did not count these as substitution + candidates. This leads to incorrect demanglings (and + ABI divergence to other compilers). */ + if (abi_warn_or_compat_version_crosses (18)) + G.need_abi_warning = true; + if (!abi_version_at_least (18)) + return; } } diff --git a/gcc/cp/module.cc b/gcc/cp/module.cc index 4d27ceb..7ffeefa 100644 --- a/gcc/cp/module.cc +++ b/gcc/cp/module.cc @@ -19083,6 +19083,10 @@ lazy_load_binding (unsigned mod, tree ns, tree id, binding_slot *mslot) timevar_start (TV_MODULE_IMPORT); + /* Make sure lazy loading from a template context behaves as if + from a non-template context. */ + processing_template_decl_sentinel ptds; + /* Stop GC happening, even in outermost loads (because our caller could well be building up a lookup set). */ function_depth++; @@ -19131,6 +19135,10 @@ lazy_load_binding (unsigned mod, tree ns, tree id, binding_slot *mslot) void lazy_load_pendings (tree decl) { + /* Make sure lazy loading from a template context behaves as if + from a non-template context. */ + processing_template_decl_sentinel ptds; + tree key_decl; pending_key key; key.ns = find_pending_key (decl, &key_decl); diff --git a/gcc/cp/name-lookup.cc b/gcc/cp/name-lookup.cc index 25657cf..14e937d 100644 --- a/gcc/cp/name-lookup.cc +++ b/gcc/cp/name-lookup.cc @@ -4302,8 +4302,6 @@ begin_scope (scope_kind kind, tree entity) case sk_function_parms: scope->keep = keep_next_level_flag; - if (entity) - scope->immediate_fn_ctx_p = DECL_IMMEDIATE_FUNCTION_P (entity); break; case sk_namespace: diff --git a/gcc/cp/name-lookup.h b/gcc/cp/name-lookup.h index 7201ae8..9e3b698 100644 --- a/gcc/cp/name-lookup.h +++ b/gcc/cp/name-lookup.h @@ -307,13 +307,10 @@ struct GTY(()) cp_binding_level { 'this_entity'. */ unsigned defining_class_p : 1; - /* true for SK_FUNCTION_PARMS of immediate functions. */ - unsigned immediate_fn_ctx_p : 1; - /* True for SK_FUNCTION_PARMS of a requires-expression. */ unsigned requires_expression: 1; - /* 21 bits left to fill a 32-bit word. */ + /* 22 bits left to fill a 32-bit word. */ }; /* The binding level currently in effect. */ diff --git a/gcc/cp/parser.cc b/gcc/cp/parser.cc index dc3d17c..4e3ed66 100644 --- a/gcc/cp/parser.cc +++ b/gcc/cp/parser.cc @@ -11519,31 +11519,11 @@ cp_parser_lambda_declarator_opt (cp_parser* parser, tree lambda_expr) opening parenthesis if present. */ if (cp_lexer_next_token_is (parser->lexer, CPP_OPEN_PAREN)) { - bool is_consteval = false; - /* For C++20, before parsing the parameter list check if there is - a consteval specifier in the corresponding decl-specifier-seq. */ - if (cxx_dialect >= cxx20) - { - for (size_t n = cp_parser_skip_balanced_tokens (parser, 1); - cp_lexer_nth_token_is (parser->lexer, n, CPP_KEYWORD); n++) - { - if (cp_lexer_peek_nth_token (parser->lexer, n)->keyword - == RID_CONSTEVAL) - { - is_consteval = true; - break; - } - } - } - matching_parens parens; parens.consume_open (parser); begin_scope (sk_function_parms, /*entity=*/NULL_TREE); - if (is_consteval) - current_binding_level->immediate_fn_ctx_p = true; - /* Parse parameters. */ param_list = cp_parser_parameter_declaration_clause @@ -23186,10 +23166,6 @@ cp_parser_direct_declarator (cp_parser* parser, begin_scope (sk_function_parms, NULL_TREE); - /* Signal we are in the immediate function context. */ - if (flags & CP_PARSER_FLAGS_CONSTEVAL) - current_binding_level->immediate_fn_ctx_p = true; - /* Parse the parameter-declaration-clause. */ params = cp_parser_parameter_declaration_clause (parser, flags); diff --git a/gcc/cp/pt.cc b/gcc/cp/pt.cc index 5b9fc58..ec337e2 100644 --- a/gcc/cp/pt.cc +++ b/gcc/cp/pt.cc @@ -11448,6 +11448,14 @@ tsubst_friend_function (tree decl, tree args) by duplicate_decls. */ new_friend = old_decl; } + + /* We've just introduced a namespace-scope function in the purview + without necessarily having opened the enclosing namespace, so + make sure the namespace is in the purview now too. */ + if (modules_p () + && DECL_MODULE_PURVIEW_P (STRIP_TEMPLATE (new_friend)) + && TREE_CODE (DECL_CONTEXT (new_friend)) == NAMESPACE_DECL) + DECL_MODULE_PURVIEW_P (DECL_CONTEXT (new_friend)) = true; } else { @@ -13925,6 +13933,8 @@ tsubst_default_argument (tree fn, int parmnum, tree type, tree arg, push_to_top_level (); push_access_scope (fn); push_deferring_access_checks (dk_no_deferred); + /* So in_immediate_context knows this is a default argument. */ + begin_scope (sk_function_parms, fn); start_lambda_scope (parm); /* The default argument expression may cause implicitly defined @@ -13948,6 +13958,7 @@ tsubst_default_argument (tree fn, int parmnum, tree type, tree arg, inform (input_location, " when instantiating default argument for call to %qD", fn); + leave_scope (); pop_deferring_access_checks (); pop_access_scope (fn); pop_from_top_level (); diff --git a/gcc/cp/tree.cc b/gcc/cp/tree.cc index 3532e44..45348c5 100644 --- a/gcc/cp/tree.cc +++ b/gcc/cp/tree.cc @@ -3125,32 +3125,6 @@ array_type_nelts_total (tree type) return sz; } -/* Return true if FNDECL is std::source_location::current () method. */ - -bool -source_location_current_p (tree fndecl) -{ - gcc_checking_assert (TREE_CODE (fndecl) == FUNCTION_DECL - && DECL_IMMEDIATE_FUNCTION_P (fndecl)); - if (DECL_NAME (fndecl) == NULL_TREE - || TREE_CODE (TREE_TYPE (fndecl)) != FUNCTION_TYPE - || TREE_CODE (TREE_TYPE (TREE_TYPE (fndecl))) != RECORD_TYPE - || DECL_CONTEXT (fndecl) != TREE_TYPE (TREE_TYPE (fndecl)) - || !id_equal (DECL_NAME (fndecl), "current")) - return false; - - tree source_location = DECL_CONTEXT (fndecl); - if (TYPE_NAME (source_location) == NULL_TREE - || TREE_CODE (TYPE_NAME (source_location)) != TYPE_DECL - || TYPE_IDENTIFIER (source_location) == NULL_TREE - || !id_equal (TYPE_IDENTIFIER (source_location), - "source_location") - || !decl_in_std_namespace_p (TYPE_NAME (source_location))) - return false; - - return true; -} - struct bot_data { splay_tree target_remap; @@ -3298,7 +3272,7 @@ bot_manip (tree* tp, int* walk_subtrees, void* data_) variables. */ static tree -bot_replace (tree* t, int* /*walk_subtrees*/, void* data_) +bot_replace (tree* t, int* walk_subtrees, void* data_) { bot_data &data = *(bot_data*)data_; splay_tree target_remap = data.target_remap; @@ -3328,6 +3302,27 @@ bot_replace (tree* t, int* /*walk_subtrees*/, void* data_) /*check_access=*/false, /*nonnull=*/true, tf_warning_or_error); } + else if (cxx_dialect >= cxx20 + && (TREE_CODE (*t) == CALL_EXPR + || TREE_CODE (*t) == AGGR_INIT_EXPR) + && !in_immediate_context ()) + { + /* Expand immediate invocations. */ + if (tree fndecl = cp_get_callee_fndecl_nofold (*t)) + if (DECL_IMMEDIATE_FUNCTION_P (fndecl)) + { + /* Make in_immediate_context true within the args. */ + in_consteval_if_p_temp_override ito; + in_consteval_if_p = true; + int nargs = call_expr_nargs (*t); + for (int i = 0; i < nargs; ++i) + cp_walk_tree (&get_nth_callarg (*t, i), bot_replace, data_, NULL); + *t = cxx_constant_value (*t); + if (*t == error_mark_node) + return error_mark_node; + *walk_subtrees = 0; + } + } return NULL_TREE; } @@ -3353,7 +3348,8 @@ break_out_target_exprs (tree t, bool clear_location /* = false */) bot_data data = { target_remap, clear_location }; if (cp_walk_tree (&t, bot_manip, &data, NULL) == error_mark_node) t = error_mark_node; - cp_walk_tree (&t, bot_replace, &data, NULL); + if (cp_walk_tree (&t, bot_replace, &data, NULL) == error_mark_node) + t = error_mark_node; if (!--target_remap_count) { diff --git a/gcc/cp/typeck.cc b/gcc/cp/typeck.cc index b4a8e3c..69c378d 100644 --- a/gcc/cp/typeck.cc +++ b/gcc/cp/typeck.cc @@ -10697,21 +10697,12 @@ maybe_warn_pessimizing_move (tree expr, tree type, bool return_p) tree t = convert_for_initialization (NULL_TREE, type, moved, (LOOKUP_NORMAL - | LOOKUP_ONLYCONVERTING - | LOOKUP_PREFER_RVALUE), + | LOOKUP_ONLYCONVERTING), ICR_RETURN, NULL_TREE, 0, tf_none); /* If this worked, implicit rvalue would work, so the call to std::move is redundant. */ - if (t != error_mark_node - /* Trying to move something const will never succeed unless - there's T(const T&&), which it almost never is, and if - so, T wouldn't be error_mark_node now: the above convert_ - call with LOOKUP_PREFER_RVALUE returns an error if a const T& - overload is selected. */ - || (CP_TYPE_CONST_P (TREE_TYPE (arg)) - && same_type_ignoring_top_level_qualifiers_p - (TREE_TYPE (arg), type))) + if (t != error_mark_node) { auto_diagnostic_group d; if (warning_at (loc, OPT_Wredundant_move, @@ -11054,23 +11045,10 @@ check_return_expr (tree retval, bool *no_warning) ? CLASS_TYPE_P (functype) : !SCALAR_TYPE_P (functype) || !SCALAR_TYPE_P (TREE_TYPE (retval))) && (moved = treat_lvalue_as_rvalue_p (retval, /*return*/true))) - { - if (cxx_dialect < cxx20) - { - moved = convert_for_initialization - (NULL_TREE, functype, moved, flags|LOOKUP_PREFER_RVALUE, - ICR_RETURN, NULL_TREE, 0, tf_none); - if (moved != error_mark_node) - { - retval = moved; - converted = true; - } - } - else - /* In C++20 we just treat the return value as an rvalue that - can bind to lvalue refs. */ - retval = moved; - } + /* In C++20 and earlier we treat the return value as an rvalue + that can bind to lvalue refs. In C++23, such an expression is just + an xvalue (see reference_binding). */ + retval = moved; /* The call in a (lambda) thunk needs no conversions. */ if (TREE_CODE (retval) == CALL_EXPR |