--parser->num_template_parameter_lists;
}
+/* Preserve the attributes across a garbage collect (by making it a GC
+ root), which can occur when parsing a member function. */
+
+static GTY(()) vec<tree, va_gc> *cp_parser_decl_specs_attrs;
+
/* Parse a type-specifier.
type-specifier:
/* Parse tentatively so that we can back up if we don't find a
class-specifier. */
cp_parser_parse_tentatively (parser);
+ if (decl_specs->attributes)
+ vec_safe_push (cp_parser_decl_specs_attrs, decl_specs->attributes);
/* Look for the class-specifier. */
type_spec = cp_parser_class_specifier (parser);
+ if (decl_specs->attributes)
+ cp_parser_decl_specs_attrs->pop ();
invoke_plugin_callbacks (PLUGIN_FINISH_TYPE, type_spec);
/* If that worked, we're done. */
if (cp_parser_parse_definitely (parser))
--- /dev/null
+// PR c++/91416 - GC during late parsing collects live data.
+// { dg-do compile }
+// { dg-options "--param ggc-min-heapsize=0 --param ggc-min-expand=0" }
+
+__attribute__ ((unused)) struct S {
+ S() { }
+} s;
+
+__attribute__ ((unused)) struct X {
+ void fn ()
+ {
+ __attribute__ ((unused)) struct N {
+ N() { }
+ } n;
+ }
+} x;