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);