Ping for https://gcc.gnu.org/pipermail/gcc-patches/2024-August/659796.html
For clarity's sake, here's the full patch with the adjustment I mentioned earlier: -- >8 -- This patch goes through all .cc files in gcc/cp and adds in any auto_diagnostic_groups that seem to be missing by looking for any 'inform' calls that aren't grouped with their respective error/warning. Now with SARIF output support this seems to be a bit more important. The patch isn't complete; I've tried to also track helper functions used for diagnostics to group them, but some may have been missed. Additionally there are a few functions that are definitely missing groupings but I wasn't able to see an obvious way to add them without potentially grouping together unrelated messages. This list includes: - lazy_load_{binding,pendings} "during load of {binding,pendings} for" - cp_finish_decomp "in initialization of structured binding variable" - require_deduced_type "using __builtin_source_location" - convert_nontype_argument "in template argument for type %qT" - coerce_template_params "so any instantiation with a non-empty parameter pack" - tsubst_default_argument "when instantiating default argument" - invalid_nontype_parm_type_p "invalid template non-type parameter" gcc/cp/ChangeLog: * class.cc (add_method): Add missing auto_diagnostic_group. (handle_using_decl): Likewise. (maybe_warn_about_overly_private_class): Likewise. (check_field_decl): Likewise. (check_field_decls): Likewise. (resolve_address_of_overloaded_function): Likewise. (note_name_declared_in_class): Likewise. * constraint.cc (associate_classtype_constraints): Likewise. (diagnose_trait_expr): Clean up whitespace. * coroutines.cc (find_coro_traits_template_decl): Add missing auto_diagnostic_group. (coro_promise_type_found_p): Likewise. (coro_diagnose_throwing_fn): Likewise. * cvt.cc (build_expr_type_conversion): Likewise. * decl.cc (validate_constexpr_redeclaration): Likewise. (duplicate_function_template_decls): Likewise. (duplicate_decls): Likewise. (lookup_label_1): Likewise. (check_previous_goto_1): Likewise. (check_goto_1): Likewise. (make_typename_type): Likewise. (make_unbound_class_template): Likewise. (check_tag_decl): Likewise. (start_decl): Likewise. (maybe_commonize_var): Likewise. (check_for_uninitialized_const_var): Likewise. (reshape_init_class): Likewise. (check_initializer): Likewise. (cp_finish_decl): Likewise. (find_decomp_class_base): Likewise. (cp_finish_decomp): Likewise. (expand_static_init): Likewise. (grokfndecl): Likewise. (grokdeclarator): Likewise. (check_elaborated_type_specifier): Likewise. (lookup_and_check_tag): Likewise. (xref_tag): Likewise. (cxx_simulate_enum_decl): Likewise. (finish_function): Likewise. * decl2.cc (check_classfn): Likewise. (record_mangling): Likewise. (mark_used): Likewise. * error.cc (qualified_name_lookup_error): Likewise. * except.cc (build_throw): Likewise. * init.cc (get_nsdmi): Likewise. (diagnose_uninitialized_cst_or_ref_member_1): Likewise. (warn_placement_new_too_small): Likewise. (build_new_1): Likewise. (build_vec_delete_1): Likewise. (build_delete): Likewise. * lambda.cc (add_capture): Likewise. (add_default_capture): Likewise. * lex.cc (unqualified_fn_lookup_error): Likewise. * method.cc (synthesize_method): Likewise. (defaulted_late_check): Likewise. * module.cc (trees_in::is_matching_decl): Likewise. (trees_in::read_enum_def): Likewise. (module_state::check_not_purview): Likewise. (module_state::deferred_macro): Likewise. (module_state::read_config): Likewise. (module_state::check_read): Likewise. (declare_module): Likewise. (init_modules): Likewise. * name-lookup.cc (diagnose_name_conflict): Likewise. (lookup_using_decl): Likewise. (set_decl_namespace): Likewise. (finish_using_directive): Likewise. (push_namespace): Likewise. (add_imported_namespace): Likewise. * parser.cc (cp_parser_check_for_definition_in_return_type): Likewise. (cp_parser_userdef_numeric_literal): Likewise. (cp_parser_nested_name_specifier_opt): Likewise. (cp_parser_new_expression): Likewise. (cp_parser_binary_expression): Likewise. (cp_parser_lambda_introducer): Likewise. (cp_parser_module_declaration): Likewise. (cp_parser_import_declaration): Likewise, removing gotos to support this. (cp_parser_declaration): Add missing auto_diagnostic_group. (cp_parser_decl_specifier_seq): Likewise. (cp_parser_template_id): Likewise. (cp_parser_template_name): Likewise. (cp_parser_explicit_specialization): Likewise. (cp_parser_placeholder_type_specifier): Likewise. (cp_parser_elaborated_type_specifier): Likewise. (cp_parser_enum_specifier): Likewise. (cp_parser_asm_definition): Likewise. (cp_parser_init_declarator): Likewise. (cp_parser_direct_declarator): Likewise. (cp_parser_class_head): Likewise. (cp_parser_member_declaration): Likewise. (cp_parser_lookup_name): Likewise. (cp_parser_explicit_template_declaration): Likewise. (cp_parser_check_class_key): Likewise. * pt.cc (maybe_process_partial_specialization): Likewise. (determine_specialization): Likewise. (check_for_bare_parameter_packs): Likewise. (check_template_shadow): Likewise. (process_partial_specialization): Likewise. (push_template_decl): Likewise. (redeclare_class_template): Likewise. (convert_nontype_argument_function): Likewise. (check_valid_ptrmem_cst_expr): Likewise. (convert_nontype_argument): Likewise. (convert_template_argument): Likewise. (coerce_template_parms): Likewise. (tsubst_qualified_id): Likewise. (tsubst_expr): Likewise. (most_specialized_partial_spec): Likewise. (do_class_deduction): Likewise. (do_auto_deduction): Likewise. * search.cc (lookup_member): Likewise. * semantics.cc (finish_non_static_data_member): Likewise. (process_outer_var_ref): Likewise. (finish_id_expression_1): Likewise. (finish_offsetof): Likewise. (omp_reduction_lookup): Likewise. (finish_omp_clauses): Likewise. * tree.cc (check_abi_tag_redeclaration): Likewise. (check_abi_tag_args): Likewise. * typeck.cc (invalid_nonstatic_memfn_p): Likewise. (complain_about_unrecognized_member): Likewise. (finish_class_member_access_expr): Likewise. (error_args_num): Likewise. (warn_for_null_address): Likewise. (cp_build_binary_op): Likewise. (build_x_unary_op): Likewise. (cp_build_unary_op): Likewise. (build_static_cast): Likewise. (cp_build_modify_expr): Likewise. (get_delta_difference): Likewise. (convert_for_assignment): Widen scope of auto_diagnostic_group. (check_return_expr): Add missing auto_diagnostic_group. * typeck2.cc (cxx_incomplete_type_diagnostic): Likewise. Signed-off-by: Nathaniel Shead <nathanielosh...@gmail.com> Reviewed-by: Marek Polacek <pola...@redhat.com> --- gcc/cp/class.cc | 12 +++++ gcc/cp/constraint.cc | 21 +++++---- gcc/cp/coroutines.cc | 3 ++ gcc/cp/cvt.cc | 1 + gcc/cp/decl.cc | 59 +++++++++++++++++++++-- gcc/cp/decl2.cc | 3 ++ gcc/cp/error.cc | 2 + gcc/cp/except.cc | 1 + gcc/cp/init.cc | 8 ++++ gcc/cp/lambda.cc | 3 ++ gcc/cp/lex.cc | 1 + gcc/cp/method.cc | 3 ++ gcc/cp/module.cc | 8 ++++ gcc/cp/name-lookup.cc | 7 +++ gcc/cp/parser.cc | 107 ++++++++++++++++++++++++++++-------------- gcc/cp/pt.cc | 65 ++++++++++++++++++------- gcc/cp/search.cc | 1 + gcc/cp/semantics.cc | 9 ++++ gcc/cp/tree.cc | 3 ++ gcc/cp/typeck.cc | 79 +++++++++++++++++++------------ gcc/cp/typeck2.cc | 1 + 21 files changed, 303 insertions(+), 94 deletions(-) diff --git a/gcc/cp/class.cc b/gcc/cp/class.cc index fb6c3370950..950d83b0ea4 100644 --- a/gcc/cp/class.cc +++ b/gcc/cp/class.cc @@ -1431,6 +1431,7 @@ add_method (tree type, tree method, bool via_using) continue; } + auto_diagnostic_group d; error_at (DECL_SOURCE_LOCATION (method), "%q#D conflicts with version inherited from %qT", method, basef); @@ -1453,6 +1454,7 @@ add_method (tree type, tree method, bool via_using) } else { + auto_diagnostic_group d; error_at (DECL_SOURCE_LOCATION (method), "%q#D cannot be overloaded with %q#D", method, fn); inform (DECL_SOURCE_LOCATION (fn), @@ -1604,6 +1606,7 @@ handle_using_decl (tree using_decl, tree t) ; else if (is_overloaded_fn (old_value)) { + auto_diagnostic_group d; error_at (DECL_SOURCE_LOCATION (using_decl), "%qD invalid in %q#T " "because of local method %q#D with same name", using_decl, t, old_value); @@ -1613,6 +1616,7 @@ handle_using_decl (tree using_decl, tree t) } else if (!DECL_ARTIFICIAL (old_value)) { + auto_diagnostic_group d; error_at (DECL_SOURCE_LOCATION (using_decl), "%qD invalid in %q#T " "because of local member %q#D with same name", using_decl, t, old_value); @@ -2547,6 +2551,7 @@ maybe_warn_about_overly_private_class (tree t) if (!nonprivate_ctor) { + auto_diagnostic_group d; bool w = warning (OPT_Wctor_dtor_privacy, "%q#T only defines private constructors and has " "no friends", t); @@ -3815,6 +3820,7 @@ check_field_decl (tree field, if (TREE_CODE (t) == UNION_TYPE && cxx_dialect < cxx11) { static bool warned; + auto_diagnostic_group d; int oldcount = errorcount; if (TYPE_NEEDS_CONSTRUCTING (type)) error ("member %q+#D with constructor not allowed in union", @@ -4131,6 +4137,7 @@ check_field_decls (tree t, tree *access_decls, if (default_init_member && TREE_CODE (t) == UNION_TYPE) { + auto_diagnostic_group d; error ("multiple fields in union %qT initialized", t); inform (DECL_SOURCE_LOCATION (default_init_member), "initialized member %q+D declared here", @@ -4209,6 +4216,7 @@ check_field_decls (tree t, tree *access_decls, && TYPE_HAS_NONTRIVIAL_DESTRUCTOR (t) && !(TYPE_HAS_COPY_CTOR (t) && TYPE_HAS_COPY_ASSIGN (t))) { + auto_diagnostic_group d; if (warning (OPT_Weffc__, "%q#T has pointer data members", t)) { if (! TYPE_HAS_COPY_CTOR (t)) @@ -8913,6 +8921,7 @@ resolve_address_of_overloaded_function (tree target_type, /* There were *no* matches. */ if (complain & tf_error) { + auto_diagnostic_group d; error ("no matches converting function %qD to type %q#T", OVL_NAME (overload), target_type); @@ -8940,6 +8949,7 @@ resolve_address_of_overloaded_function (tree target_type, { if (complain & tf_error) { + auto_diagnostic_group d; error ("converting overloaded function %qD to type %q#T is ambiguous", OVL_NAME (overload), target_type); @@ -9397,6 +9407,8 @@ note_name_declared_in_class (tree name, tree decl) else /* Make it an error. */ global_dc->m_pedantic_errors = 1; + + auto_diagnostic_group d; if (pedwarn (location_of (decl), OPT_Wchanges_meaning, "declaration of %q#D changes meaning of %qD", decl, OVL_NAME (decl))) diff --git a/gcc/cp/constraint.cc b/gcc/cp/constraint.cc index f79407f2cdb..ebfcdefd284 100644 --- a/gcc/cp/constraint.cc +++ b/gcc/cp/constraint.cc @@ -1005,6 +1005,7 @@ associate_classtype_constraints (tree type) } if (!equivalent_constraints (ci, orig_ci)) { + auto_diagnostic_group d; error ("%qT does not match original declaration", type); tree tmpl = CLASSTYPE_TI_TEMPLATE (type); location_t loc = DECL_SOURCE_LOCATION (tmpl); @@ -3183,9 +3184,9 @@ diagnose_trait_expr (tree expr, tree args) break; case CPTK_IS_CONSTRUCTIBLE: if (!t2) - inform (loc, " %qT is not default constructible", t1); + inform (loc, " %qT is not default constructible", t1); else - inform (loc, " %qT is not constructible from %qE", t1, t2); + inform (loc, " %qT is not constructible from %qE", t1, t2); break; case CPTK_IS_CONVERTIBLE: inform (loc, " %qT is not convertible from %qE", t2, t1); @@ -3204,9 +3205,9 @@ diagnose_trait_expr (tree expr, tree args) break; case CPTK_IS_INVOCABLE: if (!t2) - inform (loc, " %qT is not invocable", t1); + inform (loc, " %qT is not invocable", t1); else - inform (loc, " %qT is not invocable by %qE", t1, t2); + inform (loc, " %qT is not invocable by %qE", t1, t2); break; case CPTK_IS_LAYOUT_COMPATIBLE: inform (loc, " %qT is not layout compatible with %qT", t1, t2); @@ -3233,14 +3234,14 @@ diagnose_trait_expr (tree expr, tree args) inform (loc, " %qT is not nothrow constructible from %qE", t1, t2); break; case CPTK_IS_NOTHROW_CONVERTIBLE: - inform (loc, " %qT is not nothrow convertible from %qE", t2, t1); + inform (loc, " %qT is not nothrow convertible from %qE", t2, t1); break; case CPTK_IS_NOTHROW_INVOCABLE: - if (!t2) - inform (loc, " %qT is not nothrow invocable", t1); - else - inform (loc, " %qT is not nothrow invocable by %qE", t1, t2); - break; + if (!t2) + inform (loc, " %qT is not nothrow invocable", t1); + else + inform (loc, " %qT is not nothrow invocable by %qE", t1, t2); + break; case CPTK_IS_OBJECT: inform (loc, " %qT is not an object type", t1); break; diff --git a/gcc/cp/coroutines.cc b/gcc/cp/coroutines.cc index 20bda5520c0..e605eaec7a4 100644 --- a/gcc/cp/coroutines.cc +++ b/gcc/cp/coroutines.cc @@ -305,6 +305,7 @@ find_coro_traits_template_decl (location_t kw) { if (!traits_error_emitted) { + auto_diagnostic_group d; gcc_rich_location richloc (kw); error_at (&richloc, "coroutines require a traits template; cannot" " find %<%E::%E%>", std_node, coro_traits_identifier); @@ -632,6 +633,7 @@ coro_promise_type_found_p (tree fndecl, location_t loc) tf_none); if (has_ret_void && has_ret_val) { + auto_diagnostic_group d; location_t ploc = DECL_SOURCE_LOCATION (fndecl); if (!coro_info->coro_co_return_error_emitted) error_at (ploc, "the coroutine promise type %qT declares both" @@ -1025,6 +1027,7 @@ coro_diagnose_throwing_fn (tree fndecl) { if (!TYPE_NOTHROW_P (TREE_TYPE (fndecl))) { + auto_diagnostic_group d; location_t f_loc = cp_expr_loc_or_loc (fndecl, DECL_SOURCE_LOCATION (fndecl)); error_at (f_loc, "the expression %qE is required to be non-throwing", diff --git a/gcc/cp/cvt.cc b/gcc/cp/cvt.cc index 7b4bd8a9dc4..df02b8faaf5 100644 --- a/gcc/cp/cvt.cc +++ b/gcc/cp/cvt.cc @@ -1933,6 +1933,7 @@ build_expr_type_conversion (int desires, tree expr, bool complain) { if (complain) { + auto_diagnostic_group d; error ("ambiguous default type conversion from %qT", basetype); inform (input_location, diff --git a/gcc/cp/decl.cc b/gcc/cp/decl.cc index 6458e96bded..7bad3047ad9 100644 --- a/gcc/cp/decl.cc +++ b/gcc/cp/decl.cc @@ -1457,6 +1457,7 @@ validate_constexpr_redeclaration (tree old_decl, tree new_decl) if (DECL_IMMEDIATE_FUNCTION_P (old_decl) || DECL_IMMEDIATE_FUNCTION_P (new_decl)) kind = "consteval"; + auto_diagnostic_group d; error_at (DECL_SOURCE_LOCATION (new_decl), "redeclaration %qD differs in %qs " "from previous declaration", new_decl, @@ -1567,6 +1568,7 @@ duplicate_function_template_decls (tree newdecl, tree olddecl) if (template_heads_equivalent_p (newdecl, olddecl) && function_requirements_equivalent_p (newres, oldres)) { + auto_diagnostic_group d; error ("ambiguating new declaration %q+#D", newdecl); inform (DECL_SOURCE_LOCATION (olddecl), "old declaration %q#D", olddecl); @@ -1902,6 +1904,7 @@ duplicate_decls (tree newdecl, tree olddecl, bool hiding, bool was_hidden) return NULL_TREE; /* There can only be one! */ + auto_diagnostic_group d; if (TREE_CODE (newdecl) == TEMPLATE_DECL && check_raw_literal_operator (olddecl)) error_at (newdecl_loc, @@ -1924,6 +1927,7 @@ duplicate_decls (tree newdecl, tree olddecl, bool hiding, bool was_hidden) /* One is an implicit typedef, that's ok. */ return NULL_TREE; + auto_diagnostic_group d; error ("%q#D redeclared as different kind of entity", newdecl); inform (olddecl_loc, "previous declaration %q#D", olddecl); @@ -1947,6 +1951,7 @@ duplicate_decls (tree newdecl, tree olddecl, bool hiding, bool was_hidden) if (TREE_CODE (oldres) == TYPE_DECL || TREE_CODE (newres) == TYPE_DECL) { + auto_diagnostic_group d; error_at (newdecl_loc, "conflicting declaration of template %q#D", newdecl); inform (olddecl_loc, @@ -1967,6 +1972,7 @@ duplicate_decls (tree newdecl, tree olddecl, bool hiding, bool was_hidden) { if (DECL_EXTERN_C_P (newdecl) && DECL_EXTERN_C_P (olddecl)) { + auto_diagnostic_group d; error_at (newdecl_loc, "conflicting declaration of C function %q#D", newdecl); @@ -1988,6 +1994,7 @@ duplicate_decls (tree newdecl, tree olddecl, bool hiding, bool was_hidden) // And the same constraints. && equivalently_constrained (newdecl, olddecl)) { + auto_diagnostic_group d; error_at (newdecl_loc, "ambiguating new declaration of %q#D", newdecl); inform (olddecl_loc, @@ -1999,6 +2006,7 @@ duplicate_decls (tree newdecl, tree olddecl, bool hiding, bool was_hidden) } else { + auto_diagnostic_group d; error_at (newdecl_loc, "conflicting declaration %q#D", newdecl); inform (olddecl_loc, "previous declaration as %q#D", olddecl); @@ -2010,6 +2018,7 @@ duplicate_decls (tree newdecl, tree olddecl, bool hiding, bool was_hidden) { /* OMP UDRs are never duplicates. */ gcc_assert (DECL_OMP_DECLARE_REDUCTION_P (olddecl)); + auto_diagnostic_group d; error_at (newdecl_loc, "redeclaration of %<pragma omp declare reduction%>"); inform (olddecl_loc, @@ -2311,10 +2320,13 @@ duplicate_decls (tree newdecl, tree olddecl, bool hiding, bool was_hidden) { if (merge_attr) { - if (diagnose_mismatched_attributes (olddecl, newdecl)) - inform (olddecl_loc, DECL_INITIAL (olddecl) - ? G_("previous definition of %qD here") - : G_("previous declaration of %qD here"), olddecl); + { + auto_diagnostic_group d; + if (diagnose_mismatched_attributes (olddecl, newdecl)) + inform (olddecl_loc, DECL_INITIAL (olddecl) + ? G_("previous definition of %qD here") + : G_("previous declaration of %qD here"), olddecl); + } /* [dcl.attr.noreturn]: The first declaration of a function shall specify the noreturn attribute if any declaration of that function @@ -2327,6 +2339,7 @@ duplicate_decls (tree newdecl, tree olddecl, bool hiding, bool was_hidden) && cxx11_attribute_p (a) && get_attribute_namespace (a) == NULL_TREE) { + auto_diagnostic_group d; error_at (newdecl_loc, "function %qD declared %<[[noreturn]]%> " "but its first declaration was not", newdecl); inform (olddecl_loc, "previous declaration of %qD", olddecl); @@ -3597,6 +3610,7 @@ lookup_label_1 (tree id, bool making_local_p) if (old->binding_level == current_binding_level) { + auto_diagnostic_group d; error ("local label %qE conflicts with existing label", id); inform (DECL_SOURCE_LOCATION (old->label_decl), "previous label"); return NULL; @@ -3712,6 +3726,7 @@ check_previous_goto_1 (tree decl, cp_binding_level* level, tree names, bool exited_omp, const location_t *locus, vec<tree,va_gc> *computed) { + auto_diagnostic_group d; cp_binding_level *b; bool complained = false; int identified = 0; @@ -3858,6 +3873,7 @@ check_switch_goto (cp_binding_level* level) void check_goto_1 (named_label_entry *ent, bool computed) { + auto_diagnostic_group d; tree decl = ent->label_decl; /* If the label hasn't been defined yet, defer checking. */ @@ -4531,6 +4547,7 @@ make_typename_type (tree context, tree name, enum tag_types tag_type, { if (complain & tf_error) { + auto_diagnostic_group d; error ("lookup of %qT in %qT is ambiguous", name, context); print_candidates (t); } @@ -4626,6 +4643,7 @@ make_unbound_class_template (tree context, tree name, tree parm_list, { if (complain & tf_error) { + auto_diagnostic_group d; error ("template parameters do not match template %qD", tmpl); inform (DECL_SOURCE_LOCATION (tmpl), "%qD declared here", tmpl); @@ -5764,6 +5782,7 @@ check_tag_decl (cp_decl_specifier_seq *declspecs, No attribute-specifier-seq shall appertain to an explicit instantiation. */ { + auto_diagnostic_group d; if (warning_at (loc, OPT_Wattributes, "attribute ignored in explicit instantiation %q#T", declared_type)) @@ -5999,6 +6018,7 @@ start_decl (const cp_declarator *declarator, /* OK, specialization was already checked. */; else if (variable_template_p (field) && !this_tmpl) { + auto_diagnostic_group d; error_at (DECL_SOURCE_LOCATION (decl), "non-member-template declaration of %qD", decl); inform (DECL_SOURCE_LOCATION (field), "does not match " @@ -6661,6 +6681,7 @@ maybe_commonize_var (tree decl) msg = G_("sorry: semantics of inline function " "static data %q#D are wrong (you%'ll wind " "up with multiple copies)"); + auto_diagnostic_group d; if (warning_at (DECL_SOURCE_LOCATION (decl), 0, msg, decl)) inform (DECL_SOURCE_LOCATION (decl), @@ -6698,6 +6719,7 @@ check_for_uninitialized_const_var (tree decl, bool constexpr_context_p, if (!field) return true; + auto_diagnostic_group d; bool show_notes = true; if (!constexpr_context_p || cxx_dialect >= cxx20) @@ -7062,6 +7084,7 @@ reshape_init_class (tree type, reshape_iter *d, bool first_initializer_p, { if (field && TREE_CODE (field) == TREE_LIST) { + auto_diagnostic_group g; error ("request for member %qD is ambiguous", d->cur->index); print_candidates (field); @@ -7884,6 +7907,7 @@ check_initializer (tree decl, tree init, int flags, vec<tree, va_gc> **cleanups) { static int explained = 0; + auto_diagnostic_group d; if (cxx_dialect < cxx11) error ("initializer invalid for static member with constructor"); else if (cxx_dialect < cxx17) @@ -8560,6 +8584,7 @@ cp_finish_decl (tree decl, tree init, bool init_const_expr_p, && !type_uses_auto (type) && !COMPLETE_TYPE_P (complete_type (type))) { + auto_diagnostic_group d; error_at (location_of (decl), "deduced type %qT for %qD is incomplete", type, decl); cxx_incomplete_type_inform (type); @@ -9059,6 +9084,7 @@ cp_finish_decl (tree decl, tree init, bool init_const_expr_p, complete_type (TREE_TYPE (decl)); if (!omp_mappable_type (TREE_TYPE (decl))) { + auto_diagnostic_group d; error ("%q+D in declare target directive does not have mappable" " type", decl); if (TREE_TYPE (decl) != error_mark_node @@ -9114,6 +9140,7 @@ find_decomp_class_base (location_t loc, tree type, tree ret) return type; else if (ANON_AGGR_TYPE_P (TREE_TYPE (field))) { + auto_diagnostic_group d; if (TREE_CODE (TREE_TYPE (field)) == RECORD_TYPE) error_at (loc, "cannot decompose class type %qT because it has an " "anonymous struct member", type); @@ -9125,6 +9152,7 @@ find_decomp_class_base (location_t loc, tree type, tree ret) } else if (!accessible_p (type, field, true)) { + auto_diagnostic_group d; error_at (loc, "cannot decompose inaccessible member %qD of %qT", field, type); inform (DECL_SOURCE_LOCATION (field), @@ -9425,6 +9453,7 @@ cp_finish_decomp (tree decl, cp_decomp *decomp) if (count != eltscnt) { cnt_mismatch: + auto_diagnostic_group d; if (count > eltscnt) error_n (loc, count, "%u name provided for structured binding", @@ -9505,6 +9534,7 @@ cp_finish_decomp (tree decl, cp_decomp *decomp) } if (!tree_fits_uhwi_p (tsize)) { + auto_diagnostic_group d; error_n (loc, count, "%u name provided for structured binding", "%u names provided for structured binding", count); @@ -10096,6 +10126,7 @@ expand_static_init (tree decl, tree init) if (CP_DECL_THREAD_LOCAL_P (decl) && DECL_GNU_TLS_P (decl) && !DECL_FUNCTION_SCOPE_P (decl)) { + auto_diagnostic_group d; location_t dloc = DECL_SOURCE_LOCATION (decl); if (init) error_at (dloc, "non-local variable %qD declared %<__thread%> " @@ -10870,6 +10901,7 @@ grokfndecl (tree ctype, if (in_namespace == NULL_TREE && CP_DECL_CONTEXT (decl) != CP_TYPE_CONTEXT (type)) { + auto_diagnostic_group d; error_at (location, "deduction guide %qD must be declared in the " "same scope as %qT", decl, type); inform (location_of (type), " declared here"); @@ -10878,6 +10910,7 @@ grokfndecl (tree ctype, if (DECL_CLASS_SCOPE_P (decl) && current_access_specifier != declared_access (TYPE_NAME (type))) { + auto_diagnostic_group d; error_at (location, "deduction guide %qD must have the same access " "as %qT", decl, type); inform (location_of (type), " declared here"); @@ -10897,6 +10930,7 @@ grokfndecl (tree ctype, /* [over.literal]/6: Literal operators shall not have C linkage. */ if (DECL_LANGUAGE (decl) == lang_c) { + auto_diagnostic_group d; error_at (location, "literal operator with C linkage"); maybe_show_extern_c_location (); return NULL_TREE; @@ -11063,6 +11097,7 @@ grokfndecl (tree ctype, } else if (DECL_DEFAULTED_FN (old_decl)) { + auto_diagnostic_group d; error ("definition of explicitly-defaulted %q+D", decl); inform (DECL_SOURCE_LOCATION (old_decl), "%q#D explicitly defaulted here", old_decl); @@ -13219,6 +13254,7 @@ grokdeclarator (const cp_declarator *declarator, && !diagnose_misapplied_contracts (declspecs->std_attributes)) { location_t attr_loc = declspecs->locations[ds_std_attribute]; + auto_diagnostic_group d; if (any_nonignored_attribute_p (declspecs->std_attributes) && warning_at (attr_loc, OPT_Wattributes, "attribute ignored")) inform (attr_loc, "an attribute that appertains to a type-specifier " @@ -13290,6 +13326,7 @@ grokdeclarator (const cp_declarator *declarator, && (MAYBE_CLASS_TYPE_P (type) || TREE_CODE (type) == ENUMERAL_TYPE))) { + auto_diagnostic_group d; if (warning_at (declarator->parenthesized, OPT_Wparentheses, "unnecessary parentheses in declaration of %qs", name)) @@ -13450,6 +13487,7 @@ grokdeclarator (const cp_declarator *declarator, /* OK for C++11 lambdas. */; else if (cxx_dialect < cxx14) { + auto_diagnostic_group d; error_at (typespec_loc, "%qs function uses " "%<auto%> type specifier without " "trailing return type", name); @@ -13501,6 +13539,7 @@ grokdeclarator (const cp_declarator *declarator, } else if (!late_return_type) { + auto_diagnostic_group d; error_at (declarator->id_loc, "deduction guide " "for %qT must have trailing return " "type", TREE_TYPE (tmpl)); @@ -14737,6 +14776,7 @@ grokdeclarator (const cp_declarator *declarator, tree tmpl = TREE_OPERAND (unqualified_id, 0); if (variable_template_p (tmpl)) { + auto_diagnostic_group d; error_at (id_loc, "specialization of variable template " "%qD declared as function", tmpl); inform (DECL_SOURCE_LOCATION (tmpl), @@ -14803,6 +14843,7 @@ grokdeclarator (const cp_declarator *declarator, { if (unqualified_id) { + auto_diagnostic_group d; error_at (id_loc, "field %qD has incomplete type %qT", unqualified_id, type); cxx_incomplete_type_inform (strip_array_types (type)); @@ -14848,6 +14889,7 @@ grokdeclarator (const cp_declarator *declarator, && !all_attributes_are_contracts_p (*attrlist)) { *attrlist = NULL_TREE; + auto_diagnostic_group d; if (warning_at (id_loc, OPT_Wattributes, "attribute ignored")) inform (id_loc, "an attribute that appertains to a friend " "declaration that is not a definition is ignored"); @@ -16359,6 +16401,7 @@ check_elaborated_type_specifier (enum tag_types tag_code, && !DECL_SELF_REFERENCE_P (decl) && tag_code != typename_type) { + auto_diagnostic_group d; if (alias_template_specialization_p (type, nt_opaque)) error ("using alias template specialization %qT after %qs", type, tag_name (tag_code)); @@ -16373,6 +16416,7 @@ check_elaborated_type_specifier (enum tag_types tag_code, && tag_code != enum_type && tag_code != typename_type) { + auto_diagnostic_group d; error ("%qT referred to as %qs", type, tag_name (tag_code)); inform (location_of (type), "%qT has a previous declaration here", type); return error_mark_node; @@ -16380,6 +16424,7 @@ check_elaborated_type_specifier (enum tag_types tag_code, else if (TREE_CODE (type) != ENUMERAL_TYPE && tag_code == enum_type) { + auto_diagnostic_group d; error ("%qT referred to as enum", type); inform (location_of (type), "%qT has a previous declaration here", type); return error_mark_node; @@ -16437,6 +16482,7 @@ lookup_and_check_tag (enum tag_types tag_code, tree name, if (TREE_CODE (decl) == TREE_LIST) { + auto_diagnostic_group d; error ("reference to %qD is ambiguous", name); print_candidates (decl); return error_mark_node; @@ -16446,6 +16492,7 @@ lookup_and_check_tag (enum tag_types tag_code, tree name, && !template_header_p && how == TAG_how::CURRENT_ONLY) { + auto_diagnostic_group d; error ("class template %qD redeclared as non-template", name); inform (location_of (decl), "previous declaration here"); CLASSTYPE_ERRONEOUS (TREE_TYPE (decl)) = true; @@ -16496,6 +16543,7 @@ lookup_and_check_tag (enum tag_types tag_code, tree name, && (!CLASSTYPE_TEMPLATE_INFO (t) || (!PRIMARY_TEMPLATE_P (CLASSTYPE_TI_TEMPLATE (t))))) { + auto_diagnostic_group d; error ("%qT is not a template", t); inform (location_of (t), "previous declaration here"); if (TYPE_CLASS_SCOPE_P (t) @@ -16632,6 +16680,7 @@ xref_tag (enum tag_types tag_code, tree name, && CLASS_TYPE_P (t) && CLASSTYPE_IS_TEMPLATE (t)) { + auto_diagnostic_group d; error ("redeclaration of %qT as a non-template", t); inform (location_of (t), "previous declaration %qD", t); return error_mark_node; @@ -17623,6 +17672,7 @@ cxx_simulate_enum_decl (location_t loc, const char *name, NULL_TREE, false, NULL); if (!OPAQUE_ENUM_P (enumtype)) { + auto_diagnostic_group d; error_at (loc, "multiple definition of %q#T", enumtype); inform (DECL_SOURCE_LOCATION (TYPE_MAIN_DECL (enumtype)), "previous definition here"); @@ -18679,6 +18729,7 @@ finish_function (bool inline_p) else if (!current_function_returns_value && !current_function_returns_null) { + auto_diagnostic_group d; error ("no return statements in function returning %qT", DECL_SAVED_AUTO_RETURN_TYPE (fndecl)); inform (input_location, "only plain %<auto%> return type can be " diff --git a/gcc/cp/decl2.cc b/gcc/cp/decl2.cc index c67e3e0c15f..3c4f34868ee 100644 --- a/gcc/cp/decl2.cc +++ b/gcc/cp/decl2.cc @@ -911,6 +911,7 @@ check_classfn (tree ctype, tree function, tree template_parms) if (DECL_CONV_FN_P (function)) fns = get_class_binding (ctype, conv_op_identifier); + auto_diagnostic_group d; error_at (DECL_SOURCE_LOCATION (function), "no declaration matches %q#D", function); if (fns) @@ -5120,6 +5121,7 @@ record_mangling (tree decl, bool need_warning) *slot = decl; else if (need_warning) { + auto_diagnostic_group d; error_at (DECL_SOURCE_LOCATION (decl), "mangling of %q#D as %qE conflicts with a previous mangle", decl, id); @@ -6078,6 +6080,7 @@ mark_used (tree decl, tsubst_flags_t complain /* = tf_warning_or_error */) sorry ("converting lambda that uses %<...%> to function pointer"); else if (complain & tf_error) { + auto_diagnostic_group d; if (DECL_INITIAL (decl) && TREE_CODE (DECL_INITIAL (decl)) == STRING_CST) { diff --git a/gcc/cp/error.cc b/gcc/cp/error.cc index 420fad26b7b..60d1e8bdb32 100644 --- a/gcc/cp/error.cc +++ b/gcc/cp/error.cc @@ -4796,12 +4796,14 @@ qualified_name_lookup_error (tree scope, tree name, scope); else if (TREE_CODE (decl) == TREE_LIST) { + auto_diagnostic_group d; error_at (location, "reference to %<%T::%D%> is ambiguous", scope, name); print_candidates (decl); } else { + auto_diagnostic_group d; name_hint hint; if (SCOPED_ENUM_P (scope) && TREE_CODE (name) == IDENTIFIER_NODE) hint = suggest_alternative_in_scoped_enum (name, scope); diff --git a/gcc/cp/except.cc b/gcc/cp/except.cc index 0231bd2507d..7b4abd1f56e 100644 --- a/gcc/cp/except.cc +++ b/gcc/cp/except.cc @@ -736,6 +736,7 @@ build_throw (location_t loc, tree exp, tsubst_flags_t complain) exp = moved; /* Call the copy constructor. */ + auto_diagnostic_group d; releasing_vec exp_vec (make_tree_vector_single (exp)); exp = build_special_member_call (object, complete_ctor_identifier, &exp_vec, TREE_TYPE (object), flags, diff --git a/gcc/cp/init.cc b/gcc/cp/init.cc index 20373d26988..be7fdb40dd6 100644 --- a/gcc/cp/init.cc +++ b/gcc/cp/init.cc @@ -662,6 +662,7 @@ get_nsdmi (tree member, bool in_ctor, tsubst_flags_t complain) { if (complain & tf_error) { + auto_diagnostic_group d; error ("default member initializer for %qD required before the end " "of its enclosing class", member); inform (location_of (init), "defined here"); @@ -2736,6 +2737,7 @@ diagnose_uninitialized_cst_or_ref_member_1 (tree type, tree origin, ++ error_count; if (complain) { + auto_diagnostic_group d; if (DECL_CONTEXT (field) == origin) { if (using_new) @@ -2764,6 +2766,7 @@ diagnose_uninitialized_cst_or_ref_member_1 (tree type, tree origin, ++ error_count; if (complain) { + auto_diagnostic_group d; if (DECL_CONTEXT (field) == origin) { if (using_new) @@ -2890,6 +2893,8 @@ warn_placement_new_too_small (tree type, tree nelts, tree size, tree oper) bool warned = false; if (nelts) nelts = fold_for_warn (nelts); + + auto_diagnostic_group d; if (nelts) if (CONSTANT_CLASS_P (nelts)) warned = warning_at (loc, OPT_Wplacement_new_, @@ -3408,6 +3413,7 @@ build_new_1 (vec<tree, va_gc> **placement, tree type, tree nelts, { if (complain & tf_error) { + auto_diagnostic_group d; error ("request for member %qD is ambiguous", fnname); print_candidates (fns); } @@ -4125,6 +4131,7 @@ build_vec_delete_1 (location_t loc, tree base, tree maxindex, tree type, { if (complain & tf_error) { + auto_diagnostic_group d; int saved_errorcount = errorcount; if (permerror_opt (loc, OPT_Wdelete_incomplete, "operator %<delete []%> used on " @@ -5209,6 +5216,7 @@ build_delete (location_t loc, tree otype, tree addr, { if (complain & tf_error) { + auto_diagnostic_group d; int saved_errorcount = errorcount; if (permerror_opt (loc, OPT_Wdelete_incomplete, "operator %<delete%> used on " diff --git a/gcc/cp/lambda.cc b/gcc/cp/lambda.cc index 0770417810e..e17c00217b2 100644 --- a/gcc/cp/lambda.cc +++ b/gcc/cp/lambda.cc @@ -562,6 +562,7 @@ add_capture (tree lambda, tree id, tree orig_init, bool by_reference_p, else if (!dependent_type_p (type) && variably_modified_type_p (type, NULL_TREE)) { + auto_diagnostic_group d; sorry ("capture of variably-modified type %qT that is not an N3639 array " "of runtime bound", type); if (TREE_CODE (type) == ARRAY_TYPE @@ -600,6 +601,7 @@ add_capture (tree lambda, tree id, tree orig_init, bool by_reference_p, type = complete_type (type); if (!COMPLETE_TYPE_P (type)) { + auto_diagnostic_group d; error ("capture by copy of incomplete type %qT", type); cxx_incomplete_type_inform (type); return error_mark_node; @@ -757,6 +759,7 @@ add_default_capture (tree lambda_stack, tree id, tree initializer) && this_capture_p && LAMBDA_EXPR_DEFAULT_CAPTURE_MODE (lambda) == CPLD_COPY) { + auto_diagnostic_group d; if (warning_at (LAMBDA_EXPR_LOCATION (lambda), OPT_Wdeprecated, "implicit capture of %qE via %<[=]%> is deprecated " "in C++20", this_identifier)) diff --git a/gcc/cp/lex.cc b/gcc/cp/lex.cc index 1110db7f8d0..79d9490c4ad 100644 --- a/gcc/cp/lex.cc +++ b/gcc/cp/lex.cc @@ -807,6 +807,7 @@ unqualified_fn_lookup_error (cp_expr name_expr) Note that we have the exact wording of the following message in the manual (trouble.texi, node "Name lookup"), so they need to be kept in synch. */ + auto_diagnostic_group d; permerror (loc, "there are no arguments to %qD that depend on a template " "parameter, so a declaration of %qD must be available", name, name); diff --git a/gcc/cp/method.cc b/gcc/cp/method.cc index 0b21656ed61..68a776d2c5a 100644 --- a/gcc/cp/method.cc +++ b/gcc/cp/method.cc @@ -1787,6 +1787,7 @@ synthesize_method (tree fndecl) int error_count = errorcount; int warning_count = warningcount + werrorcount; special_function_kind sfk = special_function_p (fndecl); + auto_diagnostic_group d; /* Reset the source location, we might have been previously deferred, and thus have saved where we were first needed. */ @@ -3558,6 +3559,7 @@ defaulted_late_check (tree fn) TREE_TYPE (TREE_TYPE (implicit_fn))) || !compare_fn_params (fn, implicit_fn)) { + auto_diagnostic_group d; error ("defaulted declaration %q+D does not match the " "expected signature", fn); inform (DECL_SOURCE_LOCATION (fn), @@ -3593,6 +3595,7 @@ defaulted_late_check (tree fn) { if (!CLASSTYPE_TEMPLATE_INSTANTIATION (ctx)) { + auto_diagnostic_group d; error ("explicitly defaulted function %q+D cannot be declared " "%qs because the implicit declaration is not %qs:", fn, DECL_IMMEDIATE_FUNCTION_P (fn) ? "consteval" : "constexpr", diff --git a/gcc/cp/module.cc b/gcc/cp/module.cc index 95c2405fcd4..647208944da 100644 --- a/gcc/cp/module.cc +++ b/gcc/cp/module.cc @@ -11627,6 +11627,7 @@ trees_in::is_matching_decl (tree existing, tree decl, bool is_typedef) { // FIXME:QOI Might be template specialization from a module, // not necessarily global module + auto_diagnostic_group d; error_at (DECL_SOURCE_LOCATION (decl), "conflicting global module declaration %#qD", decl); inform (DECL_SOURCE_LOCATION (existing), @@ -12682,6 +12683,7 @@ trees_in::read_enum_def (tree defn, tree maybe_template) if (known || values) { + auto_diagnostic_group d; error_at (DECL_SOURCE_LOCATION (maybe_dup), "definition of %qD does not match", maybe_dup); inform (DECL_SOURCE_LOCATION (defn), @@ -14497,6 +14499,7 @@ module_state::check_not_purview (location_t from) if (imp == this) { /* Cannot import the current module. */ + auto_diagnostic_group d; error_at (from, "cannot import module in its own purview"); inform (loc, "module %qs declared here", get_flatname ()); return false; @@ -17859,6 +17862,7 @@ module_state::deferred_macro (cpp_reader *reader, location_t loc, { /* If LOC is the first loc, this is the end of file check, which is a warning. */ + auto_diagnostic_group d; if (loc == MAP_START_LOCATION (LINEMAPS_ORDINARY_MAP_AT (line_table, 0))) warning_at (loc, OPT_Winvalid_imported_macros, "inconsistent imported macro definition %qE", @@ -18133,6 +18137,7 @@ module_state::read_config (module_state_config &config) /* Reject when either is non-experimental or when experimental major versions differ. */ + auto_diagnostic_group d; bool reject_p = ((!IS_EXPERIMENTAL (my_ver) || !IS_EXPERIMENTAL (their_ver) || MODULE_MAJOR (my_ver) != MODULE_MAJOR (their_ver)) @@ -18945,6 +18950,7 @@ module_state::check_read (bool outermost, bool ok) if (int e = from ()->get_error ()) { + auto_diagnostic_group d; error_at (loc, "failed to read compiled module: %s", from ()->get_error (filename)); note_cmi_name (); @@ -19878,6 +19884,7 @@ declare_module (module_state *module, location_t from_loc, bool exporting_p, module_state *current = (*modules)[0]; if (module_purview_p () || module->loadedness > ML_CONFIG) { + auto_diagnostic_group d; error_at (from_loc, module_purview_p () ? G_("module already declared") : G_("module already imported")); @@ -20535,6 +20542,7 @@ init_modules (cpp_reader *reader) || (cpp_opts->deps.style != DEPS_NONE && !cpp_opts->deps.need_preprocessor_output)) { + auto_diagnostic_group d; warning (0, flag_dump_macros == 'M' ? G_("macro debug output may be incomplete with modules") : G_("module dependencies require preprocessing")); diff --git a/gcc/cp/name-lookup.cc b/gcc/cp/name-lookup.cc index 70ad4cbf3b5..7a6cc244c15 100644 --- a/gcc/cp/name-lookup.cc +++ b/gcc/cp/name-lookup.cc @@ -2893,6 +2893,7 @@ supplement_binding (cxx_binding *binding, tree decl) void diagnose_name_conflict (tree decl, tree bval) { + auto_diagnostic_group d; if (TREE_CODE (decl) == TREE_CODE (bval) && TREE_CODE (decl) != NAMESPACE_DECL && !DECL_DECLARES_FUNCTION_P (decl) @@ -6213,6 +6214,7 @@ lookup_using_decl (tree scope, name_lookup &lookup) /* We can (independently) have ambiguous implicit typedefs. */ || (lookup.type && TREE_CODE (lookup.type) == TREE_LIST)) { + auto_diagnostic_group d; error ("reference to %qD is ambiguous", lookup.name); print_candidates (TREE_CODE (lookup.value) == TREE_LIST ? lookup.value : lookup.type); @@ -6344,6 +6346,7 @@ set_decl_namespace (tree decl, tree scope, bool friendp) if (TREE_CODE (old) == TREE_LIST) { ambiguous: + auto_diagnostic_group d; DECL_CONTEXT (decl) = FROB_CONTEXT (scope); error ("reference to %qD is ambiguous", decl); print_candidates (old); @@ -6443,6 +6446,7 @@ set_decl_namespace (tree decl, tree scope, bool friendp) { if (hidden_p) { + auto_diagnostic_group d; pedwarn (DECL_SOURCE_LOCATION (decl), 0, "%qD has not been declared within %qD", decl, scope); inform (DECL_SOURCE_LOCATION (found), @@ -8927,6 +8931,7 @@ finish_using_directive (tree target, tree attribs) if (current_binding_level->kind == sk_namespace && is_attribute_p ("strong", name)) { + auto_diagnostic_group d; if (warning (0, "%<strong%> using directive no longer supported") && CP_DECL_CONTEXT (target) == current_namespace) inform (DECL_SOURCE_LOCATION (target), @@ -9246,6 +9251,7 @@ push_namespace (tree name, bool make_inline) if (make_inline && !DECL_NAMESPACE_INLINE_P (ns)) { + auto_diagnostic_group d; error_at (input_location, "inline namespace must be specified at initial definition"); inform (DECL_SOURCE_LOCATION (ns), "%qD defined here", ns); @@ -9296,6 +9302,7 @@ add_imported_namespace (tree ctx, tree name, location_t loc, unsigned import, } else if (DECL_NAMESPACE_INLINE_P (decl) != inline_p) { + auto_diagnostic_group d; error_at (loc, "%s namespace %qD conflicts with reachable definition", inline_p ? "inline" : "non-inline", decl); inform (DECL_SOURCE_LOCATION (decl), "reachable %s definition here", diff --git a/gcc/cp/parser.cc b/gcc/cp/parser.cc index edfa5a49440..8391ce431f3 100644 --- a/gcc/cp/parser.cc +++ b/gcc/cp/parser.cc @@ -3504,6 +3504,7 @@ cp_parser_check_for_definition_in_return_type (cp_declarator *declarator, if (declarator && declarator->kind == cdk_function) { + auto_diagnostic_group d; error_at (type_location, "new types may not be defined in a return type"); inform (type_location, @@ -5086,24 +5087,27 @@ cp_parser_userdef_numeric_literal (cp_parser *parser) } } - bool complained - = emit_diagnostic (kind, input_location, opt, - "unable to find numeric literal operator %qD", name); - - if (!complained) - /* Don't inform either. */; - else if (i14) - { - inform (token->location, "add %<using namespace std::complex_literals%> " - "(from %<<complex>%>) to enable the C++14 user-defined literal " - "suffixes"); - if (ext) - inform (token->location, "or use %<j%> instead of %<i%> for the " - "GNU built-in suffix"); - } - else if (!ext) - inform (token->location, "use %<-fext-numeric-literals%> " - "to enable more built-in suffixes"); + { + auto_diagnostic_group d; + bool complained + = emit_diagnostic (kind, input_location, opt, + "unable to find numeric literal operator %qD", name); + + if (!complained) + /* Don't inform either. */; + else if (i14) + { + inform (token->location, "add %<using namespace std::complex_literals%> " + "(from %<<complex>%>) to enable the C++14 user-defined literal " + "suffixes"); + if (ext) + inform (token->location, "or use %<j%> instead of %<i%> for the " + "GNU built-in suffix"); + } + else if (!ext) + inform (token->location, "use %<-fext-numeric-literals%> " + "to enable more built-in suffixes"); + } if (kind == DK_ERROR) value = error_mark_node; @@ -7159,6 +7163,7 @@ cp_parser_nested_name_specifier_opt (cp_parser *parser, if (TREE_CODE (tid) == TEMPLATE_ID_EXPR && TREE_CODE (TREE_OPERAND (tid, 0)) != IDENTIFIER_NODE) { + auto_diagnostic_group d; tree tmpl = NULL_TREE; if (is_overloaded_fn (tid)) { @@ -9641,10 +9646,13 @@ cp_parser_new_expression (cp_parser* parser) message for this case. */ if (cp_lexer_next_token_is (parser->lexer, CPP_OPEN_SQUARE)) { - error_at (token->location, - "array bound forbidden after parenthesized type-id"); - inform (token->location, - "try removing the parentheses around the type-id"); + { + auto_diagnostic_group d; + error_at (token->location, + "array bound forbidden after parenthesized type-id"); + inform (token->location, + "try removing the parentheses around the type-id"); + } cp_parser_direct_new_declarator (parser); } } @@ -10450,6 +10458,7 @@ cp_parser_binary_expression (cp_parser* parser, bool cast_p, && token->type == CPP_RSHIFT && !parser->greater_than_is_operator_p) { + auto_diagnostic_group d; if (warning_at (token->location, OPT_Wc__11_compat, "%<>>%> operator is treated" " as two right angle brackets in C++11")) @@ -11724,6 +11733,7 @@ cp_parser_lambda_introducer (cp_parser* parser, tree lambda_expr) else if (!VAR_P (capture_init_expr) && TREE_CODE (capture_init_expr) != PARM_DECL) { + auto_diagnostic_group d; error_at (capture_token->location, "capture of non-variable %qE", capture_init_expr); @@ -11735,6 +11745,7 @@ cp_parser_lambda_introducer (cp_parser* parser, tree lambda_expr) if (VAR_P (capture_init_expr) && decl_storage_duration (capture_init_expr) != dk_auto) { + auto_diagnostic_group d; if (pedwarn (capture_token->location, 0, "capture of variable " "%qD with non-automatic storage duration", capture_init_expr)) @@ -15238,6 +15249,7 @@ cp_parser_module_declaration (cp_parser *parser, module_parse mp_state, } else if (scope != global_namespace) { + auto_diagnostic_group d; error_at (token->location, "module-declaration must be at global scope"); inform (DECL_SOURCE_LOCATION (scope), "scope opened here"); goto skip_eol; @@ -15315,19 +15327,22 @@ cp_parser_import_declaration (cp_parser *parser, module_parse mp_state, if (mp_state == MP_PURVIEW || mp_state == MP_PRIVATE) { + auto_diagnostic_group d; error_at (token->location, "post-module-declaration" " imports must be contiguous"); - note_lexer: inform (token->location, "perhaps insert a line break after" " %<import%>, or other disambiguation, to prevent this" " being considered a module control-line"); - skip_eol: cp_parser_skip_to_pragma_eol (parser, token); } else if (current_scope () != global_namespace) { + auto_diagnostic_group d; error_at (token->location, "import-declaration must be at global scope"); - goto note_lexer; + inform (token->location, "perhaps insert a line break after" + " %<import%>, or other disambiguation, to prevent this" + " being considered a module control-line"); + cp_parser_skip_to_pragma_eol (parser, token); } else { @@ -15355,7 +15370,10 @@ cp_parser_import_declaration (cp_parser *parser, module_parse mp_state, tree attrs = cp_parser_attributes_opt (parser); if (!mod || !cp_parser_require (parser, CPP_SEMICOLON, RT_SEMICOLON)) - goto skip_eol; + { + cp_parser_skip_to_pragma_eol (parser, token); + return; + } cp_parser_require_pragma_eol (parser, token); if (mp_state == MP_PURVIEW_IMPORTS || mp_state == MP_PRIVATE_IMPORTS) @@ -15648,6 +15666,7 @@ cp_parser_declaration (cp_parser* parser, tree prefix_attrs) if (!c_dialect_objc ()) { location_t where = get_finish (t2->location); + auto_diagnostic_group d; warning_at (token1->location, OPT_Wattributes, "attributes are" " not permitted in this position"); where = linemap_position_for_loc_and_offset (line_table, @@ -16899,6 +16918,7 @@ cp_parser_decl_specifier_seq (cp_parser* parser, if (decl_specs->std_attributes) { + auto_diagnostic_group d; error_at (decl_specs->locations[ds_std_attribute], "standard attributes in middle of decl-specifiers"); inform (decl_specs->locations[ds_std_attribute], @@ -19148,6 +19168,7 @@ cp_parser_template_id (cp_parser *parser, } /* Otherwise, emit an error about the invalid digraph, but continue parsing because we got our argument list. */ + auto_diagnostic_group d; if (permerror (next_token->location, "%<<::%> cannot begin a template-argument list")) { @@ -19187,6 +19208,7 @@ cp_parser_template_id (cp_parser *parser, /* C++20 says that "function-name < a;" is now ill-formed. */ if (cp_parser_error_occurred (parser)) { + auto_diagnostic_group d; error_at (token->location, "invalid template-argument-list"); inform (token->location, "function name as the left hand " "operand of %<<%> is ill-formed in C++20; wrap the " @@ -19432,10 +19454,13 @@ cp_parser_template_name (cp_parser* parser, cp_token_position start = 0; /* Explain what went wrong. */ - error_at (token->location, "non-template %qD used as template", - identifier); - inform (token->location, "use %<%T::template %D%> to indicate that it is a template", - parser->scope, identifier); + { + auto_diagnostic_group d; + error_at (token->location, "non-template %qD used as template", + identifier); + inform (token->location, "use %<%T::template %D%> to indicate " + "that it is a template", parser->scope, identifier); + } /* If parsing tentatively, find the location of the "<" token. */ if (cp_parser_simulate_error (parser)) start = cp_lexer_token_position (parser->lexer, true); @@ -20103,6 +20128,7 @@ cp_parser_explicit_specialization (cp_parser* parser) bool need_lang_pop = current_lang_name == lang_name_c; if (need_lang_pop) { + auto_diagnostic_group d; error_at (token->location, "template specialization with C linkage"); maybe_show_extern_c_location (); @@ -20935,6 +20961,7 @@ cp_parser_placeholder_type_specifier (cp_parser *parser, location_t loc, { if (!tentative) { + auto_diagnostic_group d; error_at (loc, "%qE does not constrain a type", DECL_NAME (con)); inform (DECL_SOURCE_LOCATION (con), "concept defined here"); } @@ -21548,6 +21575,7 @@ cp_parser_elaborated_type_specifier (cp_parser* parser, "attributes ignored on template instantiation"); else if (is_friend && cxx11_attribute_p (attributes)) { + auto_diagnostic_group d; if (warning (OPT_Wattributes, "attribute ignored")) inform (input_location, "an attribute that appertains to a friend " "declaration that is not a definition is ignored"); @@ -21900,6 +21928,7 @@ cp_parser_enum_specifier (cp_parser* parser) } else { + auto_diagnostic_group d; error_at (type_start_token->location, "multiple definition of %q#T", type); inform (DECL_SOURCE_LOCATION (TYPE_MAIN_DECL (type)), @@ -22947,6 +22976,7 @@ cp_parser_asm_definition (cp_parser* parser) case RID_VOLATILE: if (volatile_loc) { + auto_diagnostic_group d; error_at (loc, "duplicate %<asm%> qualifier %qT", token->u.value); inform (volatile_loc, "first seen here"); @@ -22964,6 +22994,7 @@ cp_parser_asm_definition (cp_parser* parser) case RID_INLINE: if (inline_loc) { + auto_diagnostic_group d; error_at (loc, "duplicate %<asm%> qualifier %qT", token->u.value); inform (inline_loc, "first seen here"); @@ -22978,6 +23009,7 @@ cp_parser_asm_definition (cp_parser* parser) case RID_GOTO: if (goto_loc) { + auto_diagnostic_group d; error_at (loc, "duplicate %<asm%> qualifier %qT", token->u.value); inform (goto_loc, "first seen here"); @@ -23791,12 +23823,13 @@ cp_parser_init_declarator (cp_parser* parser, attributes -- but ignores them. Made a permerror in GCC 8. */ if (cp_parser_allow_gnu_extensions_p (parser) && initialization_kind == CPP_OPEN_PAREN - && cp_parser_attributes_opt (parser) - && permerror (input_location, - "attributes after parenthesized initializer ignored")) + && cp_parser_attributes_opt (parser)) { static bool hint; - if (flag_permissive && !hint) + auto_diagnostic_group d; + if (permerror (input_location, + "attributes after parenthesized initializer ignored") + && flag_permissive && !hint) { hint = true; inform (input_location, @@ -24496,6 +24529,7 @@ cp_parser_direct_declarator (cp_parser* parser, else if (qualifying_scope && CLASSTYPE_USE_TEMPLATE (name_type)) { + auto_diagnostic_group d; error_at (declarator_id_start_token->location, "invalid use of constructor as a template"); inform (declarator_id_start_token->location, @@ -27890,6 +27924,7 @@ cp_parser_class_head (cp_parser* parser, if (type != error_mark_node && (COMPLETE_TYPE_P (type) || TYPE_BEING_DEFINED (type))) { + auto_diagnostic_group d; error_at (type_start_token->location, "redefinition of %q#T", type); inform (location_of (type), "previous definition of %q#T", @@ -28344,6 +28379,7 @@ cp_parser_member_declaration (cp_parser* parser) && cxx11_attribute_p (decl_specifiers.attributes)) { decl_specifiers.attributes = NULL_TREE; + auto_diagnostic_group d; if (warning_at (decl_spec_token_start->location, OPT_Wattributes, "attribute ignored")) inform (decl_spec_token_start->location, "an attribute " @@ -32449,6 +32485,7 @@ cp_parser_lookup_name (cp_parser *parser, tree name, cp_parser_error, so we incorporate its actions directly. */ if (!cp_parser_simulate_error (parser)) { + auto_diagnostic_group d; error_at (name_location, "reference to %qD is ambiguous", name); print_candidates (decl); @@ -33260,6 +33297,7 @@ cp_parser_explicit_template_declaration (cp_parser* parser, bool member_p) A template ... shall not have C linkage. */ if (current_lang_name == lang_name_c) { + auto_diagnostic_group d; error_at (location, "template with C linkage"); maybe_show_extern_c_location (); /* Give it C++ linkage to avoid confusing other parts of the @@ -35236,6 +35274,7 @@ cp_parser_check_class_key (cp_parser *parser, location_t key_loc, bool seen_as_union = TREE_CODE (type) == UNION_TYPE; if (seen_as_union != (class_key == union_type)) { + auto_diagnostic_group d; if (permerror (input_location, "%qs tag used in naming %q#T", class_key == union_type ? "union" : class_key == record_type ? "struct" : "class", diff --git a/gcc/cp/pt.cc b/gcc/cp/pt.cc index 024fa8a5529..f60b1069d6d 100644 --- a/gcc/cp/pt.cc +++ b/gcc/cp/pt.cc @@ -1124,6 +1124,7 @@ maybe_process_partial_specialization (tree type) if (current_namespace != decl_namespace_context (tmpl)) { + auto_diagnostic_group d; if (permerror (input_location, "specialization of %qD in different namespace", type)) @@ -2471,6 +2472,7 @@ determine_specialization (tree template_id, if (templates == NULL_TREE && candidates == NULL_TREE) { + auto_diagnostic_group d; error ("template-id %qD for %q+D does not match any template " "declaration", template_id, decl); if (header_mismatch) @@ -2485,6 +2487,7 @@ determine_specialization (tree template_id, || (candidates && TREE_CHAIN (candidates)) || (templates && candidates)) { + auto_diagnostic_group d; error ("ambiguous template specialization %qD for %q+D", template_id, decl); candidates = chainon (candidates, templates); @@ -4311,6 +4314,7 @@ check_for_bare_parameter_packs (tree t, location_t loc /* = UNKNOWN_LOCATION */) if (parameter_packs) { + auto_diagnostic_group d; error_at (loc, "parameter packs not expanded with %<...%>:"); while (parameter_packs) { @@ -4455,6 +4459,7 @@ check_template_shadow (tree decl) if (DECL_SELF_REFERENCE_P (decl)) return false; + auto_diagnostic_group d; if (DECL_TEMPLATE_PARM_P (decl)) error ("declaration of template parameter %q+D shadows " "template parameter", decl); @@ -5141,7 +5146,6 @@ process_partial_specialization (tree decl) int nargs = TREE_VEC_LENGTH (inner_args); int ntparms; int i; - bool did_error_intro = false; struct template_parm_data tpd; struct template_parm_data tpd2; @@ -5195,24 +5199,29 @@ process_partial_specialization (tree decl) NULL, /*include_nondeduced_p=*/false); } - for (i = 0; i < ntparms; ++i) - if (tpd.parms[i] == 0) - { - /* One of the template parms was not used in a deduced context in the - specialization. */ - if (!did_error_intro) - { - error ("template parameters not deducible in " - "partial specialization:"); - did_error_intro = true; - } - inform (input_location, " %qD", - TREE_VALUE (TREE_VEC_ELT (inner_parms, i))); - } + { + auto_diagnostic_group d; + bool did_error_intro = false; + for (i = 0; i < ntparms; ++i) + if (tpd.parms[i] == 0) + { + /* One of the template parms was not used in a deduced context in the + specialization. */ + if (!did_error_intro) + { + error ("template parameters not deducible in " + "partial specialization:"); + did_error_intro = true; + } - if (did_error_intro) - return error_mark_node; + inform (input_location, " %qD", + TREE_VALUE (TREE_VEC_ELT (inner_parms, i))); + } + + if (did_error_intro) + return error_mark_node; + } /* [temp.class.spec] @@ -5224,6 +5233,7 @@ process_partial_specialization (tree decl) && (!flag_concepts || !strictly_subsumes (current_template_constraints (), maintmpl))) { + auto_diagnostic_group d; if (!flag_concepts) error ("partial specialization %q+D does not specialize " "any template arguments; to define the primary template, " @@ -5241,6 +5251,7 @@ process_partial_specialization (tree decl) parameters. */ if (nargs < DECL_NTPARMS (maintmpl)) { + auto_diagnostic_group d; error ("partial specialization is not more specialized than the " "primary template because it replaces multiple parameters " "with a pack expansion"); @@ -5251,6 +5262,7 @@ process_partial_specialization (tree decl) else if (nargs > DECL_NTPARMS (maintmpl)) { + auto_diagnostic_group d; error ("too many arguments for partial specialization %qT", type); inform (DECL_SOURCE_LOCATION (maintmpl), "primary template here"); /* Avoid crash below. */ @@ -6141,6 +6153,7 @@ push_template_decl (tree decl, bool is_friend) (TI_ARGS (tinfo), TI_ARGS (get_template_info (DECL_TEMPLATE_RESULT (tmpl))))) { + auto_diagnostic_group d; error ("template arguments to %qD do not match original " "template %qD", decl, DECL_TEMPLATE_RESULT (tmpl)); if (!uses_template_parms (TI_ARGS (tinfo))) @@ -6346,6 +6359,7 @@ redeclare_class_template (tree type, tree parms, tree cons) if (TREE_VEC_LENGTH (parms) != TREE_VEC_LENGTH (tmpl_parms)) { + auto_diagnostic_group d; error_n (input_location, TREE_VEC_LENGTH (parms), "redeclared with %d template parameter", "redeclared with %d template parameters", @@ -6862,6 +6876,7 @@ convert_nontype_argument_function (tree type, tree expr, { if (complain & tf_error) { + auto_diagnostic_group d; location_t loc = cp_expr_loc_or_input_loc (expr); error_at (loc, "%qE is not a valid template argument for type %qT", expr, type); @@ -6932,6 +6947,7 @@ check_valid_ptrmem_cst_expr (tree type, tree expr, return true; if (complain & tf_error) { + auto_diagnostic_group d; location_t loc = cp_expr_loc_or_input_loc (orig_expr); error_at (loc, "%qE is not a valid template argument for type %qT", orig_expr, type); @@ -7805,6 +7821,7 @@ convert_nontype_argument (tree type, tree expr, tsubst_flags_t complain) { if (complain & tf_error) { + auto_diagnostic_group d; error ("%qE is not a valid template argument for type %qT " "because it is a pointer", expr, type); inform (input_location, "try using %qE instead", @@ -8663,6 +8680,7 @@ convert_template_argument (tree parm, { if (complain & tf_error) { + auto_diagnostic_group d; error ("type/value mismatch at argument %d in template " "parameter list for %qD", i + 1, in_decl); @@ -8697,6 +8715,7 @@ convert_template_argument (tree parm, { if (in_decl && (complain & tf_error)) { + auto_diagnostic_group d; error ("type/value mismatch at argument %d in template " "parameter list for %qD", i + 1, in_decl); @@ -8747,6 +8766,7 @@ convert_template_argument (tree parm, { if (in_decl && (complain & tf_error)) { + auto_diagnostic_group d; error ("type/value mismatch at argument %d in " "template parameter list for %qD", i + 1, in_decl); @@ -8765,6 +8785,7 @@ convert_template_argument (tree parm, { if (in_decl && (complain & tf_error)) { + auto_diagnostic_group d; error ("constraint mismatch at argument %d in " "template parameter list for %qD", i + 1, in_decl); @@ -9147,6 +9168,7 @@ coerce_template_parms (tree parms, bad_nargs: if (complain & tf_error) { + auto_diagnostic_group d; if (variadic_p || default_p) { nparms -= variadic_p + default_p; @@ -9182,6 +9204,7 @@ coerce_template_parms (tree parms, if (PACK_EXPANSION_P (arg) && !template_parameter_pack_p (parm)) { + auto_diagnostic_group d; if (DECL_ALIAS_TEMPLATE_P (in_decl)) error_at (location_of (arg), "pack expansion argument for non-pack parameter " @@ -17373,6 +17396,7 @@ tsubst_qualified_id (tree qualified_id, tree args, { if (complain & tf_error) { + auto_diagnostic_group d; error ("dependent-name %qE is parsed as a non-type, but " "instantiation yields a type", qualified_id); inform (input_location, "say %<typename %E%> if a type is meant", qualified_id); @@ -20965,6 +20989,7 @@ tsubst_expr (tree t, tree args, tsubst_flags_t complain, tree in_decl) if (unq != function) { + auto_diagnostic_group d; char const *const msg = G_("%qD was not declared in this scope, " "and no declarations were found by " @@ -26400,6 +26425,7 @@ most_specialized_partial_spec (tree target, tsubst_flags_t complain, char *spaces = NULL; if (!(complain & tf_error)) return error_mark_node; + auto_diagnostic_group d; if (TYPE_P (target)) error ("ambiguous template instantiation for %q#T", target); else @@ -30866,6 +30892,7 @@ do_class_deduction (tree ptype, tree tmpl, tree init, tree outer_targs, { /* Be permissive with equivalent alias templates. */ tree u = get_underlying_template (tmpl); + auto_diagnostic_group d; diagnostic_t dk = (u == tmpl) ? DK_ERROR : DK_PEDWARN; bool complained = emit_diagnostic (dk, input_location, 0, @@ -31022,6 +31049,7 @@ do_class_deduction (tree ptype, tree tmpl, tree init, tree outer_targs, { if (complain & tf_warning_or_error) { + auto_diagnostic_group d; error ("class template argument deduction failed:"); perform_dguide_overload_resolution (cands, args, complain); if (elided) @@ -31039,6 +31067,7 @@ do_class_deduction (tree ptype, tree tmpl, tree init, tree outer_targs, if (complain & tf_warning_or_error) { // TODO: Pass down location from cp_finish_decl. + auto_diagnostic_group d; error ("class template argument deduction for %qT failed: " "explicit deduction guide selected in " "copy-list-initialization", type); @@ -31054,6 +31083,7 @@ do_class_deduction (tree ptype, tree tmpl, tree init, tree outer_targs, guides, this deduction might not be what the user intended. */ if (fndecl != error_mark_node && !any_dguides_p && (complain & tf_warning)) { + auto_diagnostic_group d; if ((!DECL_IN_SYSTEM_HEADER (fndecl) || global_dc->m_warn_system_headers) && warning (OPT_Wctad_maybe_unsupported, @@ -31181,6 +31211,7 @@ do_auto_deduction (tree type, tree init, tree auto_node, { if (complain & tf_warning_or_error) { + auto_diagnostic_group d; if (permerror (loc, "direct-list-initialization of " "%<auto%> requires exactly one element")) inform (loc, diff --git a/gcc/cp/search.cc b/gcc/cp/search.cc index 827f48e8604..60c30ecb881 100644 --- a/gcc/cp/search.cc +++ b/gcc/cp/search.cc @@ -1227,6 +1227,7 @@ lookup_member (tree xbasetype, tree name, int protect, bool want_type, { if (complain & tf_error) { + auto_diagnostic_group d; error ("request for member %qD is ambiguous", name); print_candidates (lfi.ambiguous); } diff --git a/gcc/cp/semantics.cc b/gcc/cp/semantics.cc index 5ab2076b673..3e117c216da 100644 --- a/gcc/cp/semantics.cc +++ b/gcc/cp/semantics.cc @@ -2383,6 +2383,7 @@ finish_non_static_data_member (tree decl, tree object, tree qualifying_scope, { if (complain & tf_error) { + auto_diagnostic_group d; if (current_function_decl && DECL_STATIC_FUNCTION_P (current_function_decl)) error ("invalid use of member %qD in static member function", decl); @@ -4248,6 +4249,7 @@ process_outer_var_ref (tree decl, tsubst_flags_t complain, bool odr_use) { if (complain & tf_error) { + auto_diagnostic_group d; error ("%qD is not captured", decl); tree closure = LAMBDA_EXPR_CLOSURE (lambda_expr); if (LAMBDA_EXPR_DEFAULT_CAPTURE_MODE (lambda_expr) == CPLD_NONE) @@ -4268,6 +4270,7 @@ process_outer_var_ref (tree decl, tsubst_flags_t complain, bool odr_use) { if (complain & tf_error) { + auto_diagnostic_group d; error (VAR_P (decl) ? G_("use of local variable with automatic storage from " "containing function") @@ -4503,6 +4506,7 @@ finish_id_expression_1 (tree id_expression, if (TREE_CODE (decl) == TREE_LIST) { /* Ambiguous reference to base members. */ + auto_diagnostic_group d; error ("request for member %qD is ambiguous in " "multiple inheritance lattice", id_expression); print_candidates (decl); @@ -4909,6 +4913,7 @@ finish_offsetof (tree object_ptr, tree expr, location_t loc) if (DECL_P (expr)) { + auto_diagnostic_group d; error ("cannot apply %<offsetof%> to member function %qD", expr); inform (DECL_SOURCE_LOCATION (expr), "declared here"); } @@ -6321,6 +6326,7 @@ omp_reduction_lookup (location_t loc, tree id, tree type, tree *baselinkp, return ret; if (!ambiguous.is_empty ()) { + auto_diagnostic_group d; const char *str = _("candidates are:"); unsigned int idx; tree udr; @@ -8393,6 +8399,7 @@ finish_omp_clauses (tree clauses, enum c_omp_region_type ort) && !type_dependent_expression_p (t) && !omp_mappable_type (TREE_TYPE (t))) { + auto_diagnostic_group d; error_at (OMP_CLAUSE_LOCATION (c), "array section does not have mappable type " "in %qs clause", @@ -8615,6 +8622,7 @@ finish_omp_clauses (tree clauses, enum c_omp_region_type ort) ? TREE_TYPE (TREE_TYPE (t)) : TREE_TYPE (t))) { + auto_diagnostic_group d; error_at (OMP_CLAUSE_LOCATION (c), "%qD does not have a mappable type in %qs clause", t, omp_clause_code_name[OMP_CLAUSE_CODE (c)]); @@ -8782,6 +8790,7 @@ finish_omp_clauses (tree clauses, enum c_omp_region_type ort) } else if (!omp_mappable_type (TREE_TYPE (t))) { + auto_diagnostic_group d; error_at (OMP_CLAUSE_LOCATION (c), "%qD does not have a mappable type in %qs clause", t, cname); diff --git a/gcc/cp/tree.cc b/gcc/cp/tree.cc index 31ecbb1ac79..c3a38de4f48 100644 --- a/gcc/cp/tree.cc +++ b/gcc/cp/tree.cc @@ -5223,6 +5223,7 @@ check_abi_tag_redeclaration (const_tree decl, const_tree old, const_tree new_) if (new_ && TREE_CODE (TREE_VALUE (new_)) == TREE_LIST) new_ = TREE_VALUE (new_); bool err = false; + auto_diagnostic_group d; for (const_tree t = new_; t; t = TREE_CHAIN (t)) { tree str = TREE_VALUE (t); @@ -5276,6 +5277,7 @@ check_abi_tag_args (tree args, tree name) { if (!ISALPHA (c) && c != '_') { + auto_diagnostic_group d; error ("arguments to the %qE attribute must contain valid " "identifiers", name); inform (input_location, "%<%c%> is not a valid first " @@ -5289,6 +5291,7 @@ check_abi_tag_args (tree args, tree name) { if (!ISALNUM (c) && c != '_') { + auto_diagnostic_group d; error ("arguments to the %qE attribute must contain valid " "identifiers", name); inform (input_location, "%<%c%> is not a valid character " diff --git a/gcc/cp/typeck.cc b/gcc/cp/typeck.cc index f26b5b2a1f4..e4e260645f6 100644 --- a/gcc/cp/typeck.cc +++ b/gcc/cp/typeck.cc @@ -2365,6 +2365,7 @@ invalid_nonstatic_memfn_p (location_t loc, tree expr, tsubst_flags_t complain) { if (DECL_P (expr)) { + auto_diagnostic_group d; error_at (loc, "invalid use of non-static member function %qD", expr); inform (DECL_SOURCE_LOCATION (expr), "declared here"); @@ -3309,6 +3310,7 @@ complain_about_unrecognized_member (tree access_path, tree name, { /* The guessed name isn't directly accessible, and no accessor member function could be found. */ + auto_diagnostic_group d; error_at (&rich_loc, "%q#T has no member named %qE;" " did you mean %q#D? (not accessible from this context)", @@ -3534,21 +3536,24 @@ finish_class_member_access_expr (cp_expr object, tree name, bool template_p, else { /* Look up the member. */ - access_failure_info afi; - if (processing_template_decl) - /* Even though this class member access expression is at this - point not dependent, the member itself may be dependent, and - we must not potentially push a access check for a dependent - member onto TI_DEFERRED_ACCESS_CHECKS. So don't check access - ahead of time here; we're going to redo this member lookup at - instantiation time anyway. */ - push_deferring_access_checks (dk_no_check); - member = lookup_member (access_path, name, /*protect=*/1, - /*want_type=*/false, complain, - &afi); - if (processing_template_decl) - pop_deferring_access_checks (); - afi.maybe_suggest_accessor (TYPE_READONLY (object_type)); + { + auto_diagnostic_group d; + access_failure_info afi; + if (processing_template_decl) + /* Even though this class member access expression is at this + point not dependent, the member itself may be dependent, and + we must not potentially push a access check for a dependent + member onto TI_DEFERRED_ACCESS_CHECKS. So don't check access + ahead of time here; we're going to redo this member lookup at + instantiation time anyway. */ + push_deferring_access_checks (dk_no_check); + member = lookup_member (access_path, name, /*protect=*/1, + /*want_type=*/false, complain, + &afi); + if (processing_template_decl) + pop_deferring_access_checks (); + afi.maybe_suggest_accessor (TYPE_READONLY (object_type)); + } if (member == NULL_TREE) { if (dependentish_scope_p (object_type)) @@ -4504,6 +4509,7 @@ error_args_num (location_t loc, tree fndecl, bool too_many_p) { if (fndecl) { + auto_diagnostic_group d; if (TREE_CODE (TREE_TYPE (fndecl)) == METHOD_TYPE) { if (DECL_NAME (fndecl) == NULL_TREE @@ -4952,6 +4958,7 @@ warn_for_null_address (location_t location, tree op, tsubst_flags_t complain) STRIP_NOPS (cop); } + auto_diagnostic_group d; bool warned = false; if (TREE_CODE (cop) == ADDR_EXPR) { @@ -6106,6 +6113,7 @@ cp_build_binary_op (const op_location_t &location, { if (complain & tf_error) { + auto_diagnostic_group d; error_at (location, "comparing vectors with different " "element types"); inform (location, "operand types are %qT and %qT", @@ -6119,6 +6127,7 @@ cp_build_binary_op (const op_location_t &location, { if (complain & tf_error) { + auto_diagnostic_group d; error_at (location, "comparing vectors with different " "number of elements"); inform (location, "operand types are %qT and %qT", @@ -6964,6 +6973,7 @@ build_x_unary_op (location_t loc, enum tree_code code, cp_expr xarg, { if (complain & tf_error) { + auto_diagnostic_group d; error_at (loc, "invalid use of %qE to form a " "pointer-to-member-function", xarg.get_value ()); if (TREE_CODE (xarg) != OFFSET_REF) @@ -7498,10 +7508,13 @@ cp_build_unary_op (enum tree_code code, tree xarg, bool noconvert, { /* Warn if the expression has boolean value. */ if (TREE_CODE (TREE_TYPE (arg)) == BOOLEAN_TYPE - && (complain & tf_warning) - && warning_at (location, OPT_Wbool_operation, - "%<~%> on an expression of type %<bool%>")) - inform (location, "did you mean to use logical not (%<!%>)?"); + && (complain & tf_warning)) + { + auto_diagnostic_group d; + if (warning_at (location, OPT_Wbool_operation, + "%<~%> on an expression of type %<bool%>")) + inform (location, "did you mean to use logical not (%<!%>)?"); + } arg = cp_perform_integral_promotions (arg, complain); } else if (!noconvert && VECTOR_TYPE_P (TREE_TYPE (arg))) @@ -8723,6 +8736,7 @@ build_static_cast (location_t loc, tree type, tree oexpr, if (complain & tf_error) { + auto_diagnostic_group d; error_at (loc, "invalid %<static_cast%> from type %qT to type %qT", TREE_TYPE (expr), type); if ((TYPE_PTR_P (type) || TYPE_REF_P (type)) @@ -9682,15 +9696,19 @@ cp_build_modify_expr (location_t loc, tree lhs, enum tree_code modifycode, rhs = decay_conversion (rhs, complain); if (rhs == error_mark_node) return error_mark_node; - rhs = stabilize_expr (rhs, &init); - newrhs = cp_build_binary_op (loc, modifycode, lhs, rhs, complain); - if (newrhs == error_mark_node) - { - if (complain & tf_error) - inform (loc, " in evaluation of %<%Q(%#T, %#T)%>", - modifycode, TREE_TYPE (lhs), TREE_TYPE (rhs)); - return error_mark_node; - } + + { + auto_diagnostic_group d; + rhs = stabilize_expr (rhs, &init); + newrhs = cp_build_binary_op (loc, modifycode, lhs, rhs, complain); + if (newrhs == error_mark_node) + { + if (complain & tf_error) + inform (loc, " in evaluation of %<%Q(%#T, %#T)%>", + modifycode, TREE_TYPE (lhs), TREE_TYPE (rhs)); + return error_mark_node; + } + } if (init) newrhs = build2 (COMPOUND_EXPR, TREE_TYPE (newrhs), init, newrhs); @@ -9970,6 +9988,7 @@ get_delta_difference (tree from, tree to, bool allow_inverse_p, bool c_cast_p, tsubst_flags_t complain) { + auto_diagnostic_group d; tree result; if (same_type_ignoring_top_level_qualifiers_p (from, to)) @@ -10384,6 +10403,8 @@ convert_for_assignment (tree type, tree rhs, { if (complain & tf_error) { + auto_diagnostic_group d; + /* If the right-hand side has unknown type, then it is an overloaded function. Call instantiate_type to get error messages. */ @@ -10406,7 +10427,6 @@ convert_for_assignment (tree type, tree rhs, (rhs_loc, has_loc ? &label : NULL, has_loc ? highlight_colors::percent_h : NULL); - auto_diagnostic_group d; switch (errtype) { @@ -11150,6 +11170,7 @@ check_return_expr (tree retval, bool *no_warning, bool *dangling) if (!retval && !is_auto (pattern)) { /* Give a helpful error message. */ + auto_diagnostic_group d; error ("return-statement with no value, in function returning %qT", pattern); inform (input_location, "only plain %<auto%> return type can be " diff --git a/gcc/cp/typeck2.cc b/gcc/cp/typeck2.cc index a0c8f833ac1..79b397a69fa 100644 --- a/gcc/cp/typeck2.cc +++ b/gcc/cp/typeck2.cc @@ -302,6 +302,7 @@ cxx_incomplete_type_diagnostic (location_t loc, const_tree value, if (TREE_CODE (type) == ERROR_MARK) return false; + auto_diagnostic_group d; if (value) { STRIP_ANY_LOCATION_WRAPPER (value); -- 2.46.0