diff mbox series

[PR,c++/84835] ICE with generic lambda in extern "C"

Message ID 19c432c2-63ae-216c-5514-2893e4bc3e85@acm.org
State New
Headers show
Series [PR,c++/84835] ICE with generic lambda in extern "C" | expand

Commit Message

Nathan Sidwell March 19, 2018, 6:54 p.m. UTC
In an extern "C" region the lambda member fns were getting C linkage. 
and triggering an assert I added.  I'm not sure why just the generic 
case was being triggered, but the fix is to just force the language to 
be C++ -- this is what we do in finish_member_declaration.

We were also not copying the linkage into the template header.  Mostly 
that was ok, because we then ignored it.  But sometimes, like this, 
things went wrong.

applying to trunk.

nathan
diff mbox series

Patch

2018-03-19  Nathan Sidwell  <nathan@acm.org>

	PR c++/84835
	* lambda.c (maybe_add_lambda_conv_op): Force C++ linkage.
	* pt.c (build_template_decl): Propagate language linkage.

	PR c++/84835
	* g++.dg/cpp1y/pr84835.C: New.

Index: cp/lambda.c
===================================================================
--- cp/lambda.c	(revision 258642)
+++ cp/lambda.c	(working copy)
@@ -1176,6 +1176,7 @@  maybe_add_lambda_conv_op (tree type)
   tree thistype = cp_build_qualified_type (type, TYPE_QUAL_CONST);
   tree fntype = build_method_type_directly (thistype, rettype, void_list_node);
   tree convfn = build_lang_decl (FUNCTION_DECL, name, fntype);
+  SET_DECL_LANGUAGE (convfn, lang_cplusplus);
   tree fn = convfn;
   DECL_SOURCE_LOCATION (fn) = DECL_SOURCE_LOCATION (callop);
   SET_DECL_ALIGN (fn, MINIMUM_METHOD_BOUNDARY);
@@ -1208,6 +1209,7 @@  maybe_add_lambda_conv_op (tree type)
 
   name = get_identifier ("_FUN");
   tree statfn = build_lang_decl (FUNCTION_DECL, name, stattype);
+  SET_DECL_LANGUAGE (statfn, lang_cplusplus);
   fn = statfn;
   DECL_SOURCE_LOCATION (fn) = DECL_SOURCE_LOCATION (callop);
   grokclassfn (type, fn, NO_SPECIAL);
Index: cp/pt.c
===================================================================
--- cp/pt.c	(revision 258642)
+++ cp/pt.c	(working copy)
@@ -4677,6 +4677,7 @@  tree
 build_template_decl (tree decl, tree parms, bool member_template_p)
 {
   tree tmpl = build_lang_decl (TEMPLATE_DECL, DECL_NAME (decl), NULL_TREE);
+  SET_DECL_LANGUAGE (tmpl, DECL_LANGUAGE (decl));
   DECL_TEMPLATE_PARMS (tmpl) = parms;
   DECL_CONTEXT (tmpl) = DECL_CONTEXT (decl);
   DECL_SOURCE_LOCATION (tmpl) = DECL_SOURCE_LOCATION (decl);
Index: testsuite/g++.dg/cpp1y/pr84835.C
===================================================================
--- testsuite/g++.dg/cpp1y/pr84835.C	(revision 0)
+++ testsuite/g++.dg/cpp1y/pr84835.C	(working copy)
@@ -0,0 +1,20 @@ 
+// { dg-do compile { target c++14 } }
+// PR c++/84835
+// ICE with generic lambda inside extern "C"
+
+extern "C" 
+{
+  auto r = [] (auto x) 
+  {
+    void baz (); // extern "C"
+    baz ();
+  };
+  
+}
+
+void g ()
+{
+  r (0);
+}
+
+//  { dg-final { scan-assembler "\[^0-9\]baz" } }