static void
cp_parser_declaration_seq_opt (cp_parser* parser)
{
+ bool saved_in_unbraced_linkage_specification_p
+ = parser->in_unbraced_linkage_specification_p;
+ bool saved_in_unbraced_export_declaration_p
+ = parser->in_unbraced_export_declaration_p;
+
+ /* We're not in an unbraced linkage-specification
+ or export-declaration anymore. */
+ parser->in_unbraced_linkage_specification_p = false;
+ parser->in_unbraced_export_declaration_p = false;
+
while (true)
{
cp_token *token = cp_lexer_peek_token (parser->lexer);
else
cp_parser_toplevel_declaration (parser);
}
+
+ parser->in_unbraced_linkage_specification_p
+ = saved_in_unbraced_linkage_specification_p;
+ parser->in_unbraced_export_declaration_p
+ = saved_in_unbraced_export_declaration_p;
}
/* Parse a declaration. The distinction between name-declaration
--- /dev/null
+// PR c++/114917
+// { dg-additional-options "-fmodules-ts" }
+// { dg-module-cmi M }
+
+export module M;
+
+export namespace ns {
+ template <typename T> struct S {};
+ template <typename T> struct S<T*> { using a = int; };
+ template <> struct S<int*> { using b = int; };
+ template struct S<int>;
+};
+
+export extern "C++" namespace ns {
+ template <typename T> void foo() {}
+ template <> void foo<int>() {}
+}
--- /dev/null
+// PR c++/114917
+// { dg-do compile }
+
+extern "C++" namespace ns {
+ struct Incomplete;
+ Incomplete foo; // { dg-error "incomplete type" }
+}
+
+extern "C" extern "C" {
+ static int bar; // { dg-bogus "invalid" }
+}