[PR c++/81060] ICE with invalid initialzer via lambda
authorNathan Sidwell <nathan@acm.org>
Thu, 16 Nov 2017 12:11:36 +0000 (12:11 +0000)
committerNathan Sidwell <nathan@gcc.gnu.org>
Thu, 16 Nov 2017 12:11:36 +0000 (12:11 +0000)
https://gcc.gnu.org/ml/gcc-patches/2017-11/msg01323.html
PR c++/81060
* decl.c (xref_tag_1): Push lambda into current scope.
* name-lookup.c (do_pushtag): Don't deal with ts_lambda here.

PR c++81060
* g++.dg/cpp0x/lambda/lambda-template13.C: Avoid undefined
template using local type error.
* g++.dg/cpp0x/pr81060.C: New.

From-SVN: r254817

gcc/cp/ChangeLog
gcc/cp/decl.c
gcc/cp/name-lookup.c
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/cpp0x/lambda/lambda-template13.C
gcc/testsuite/g++.dg/cpp0x/pr81060.C [new file with mode: 0644]

index e8c882f2253984389630fc526c495d390fb1cf80..31de2a66182a647d3988f06f33d375f297db6f5f 100644 (file)
@@ -1,3 +1,9 @@
+2017-11-16  Nathan Sidwell  <nathan@acm.org>
+
+       PR c++/81060
+       * decl.c (xref_tag_1): Push lambda into current scope.
+       * name-lookup.c (do_pushtag): Don't deal with ts_lambda here.
+
 2017-11-15  Nathan Sidwell  <nathan@acm.org>
 
        PR c++/81574
index 7e16f7b415bb079666f59e834ab20a545597db5d..54e06568e4662b343691e261e2ca06e2695935e6 100644 (file)
@@ -13546,8 +13546,12 @@ xref_tag_1 (enum tag_types tag_code, tree name,
          t = make_class_type (code);
          TYPE_CONTEXT (t) = context;
          if (scope == ts_lambda)
-           /* Mark it as a lambda type.  */
-           CLASSTYPE_LAMBDA_EXPR (t) = error_mark_node;
+           {
+             /* Mark it as a lambda type.  */
+             CLASSTYPE_LAMBDA_EXPR (t) = error_mark_node;
+             /* And push it into current scope.  */
+             scope = ts_current;
+           }
          t = pushtag (name, t, scope);
        }
     }
index b4976d8b7ccf420d3da5d2b9cd5f8dd21721d2b1..e9d44e4a594dd43befeb2ef45678898ab9f62b75 100644 (file)
@@ -6242,9 +6242,7 @@ do_pushtag (tree name, tree type, tag_scope scope)
            view of the language.  */
         || (b->kind == sk_template_parms
             && (b->explicit_spec_p || scope == ts_global))
-        /* Pushing into a class is ok for lambdas or when we want current  */
         || (b->kind == sk_class
-            && scope != ts_lambda
             && (scope != ts_current
                 /* We may be defining a new type in the initializer
                    of a static member variable. We allow this when
@@ -6267,7 +6265,6 @@ do_pushtag (tree name, tree type, tag_scope scope)
          tree cs = current_scope ();
 
          if (scope == ts_current
-             || scope == ts_lambda
              || (cs && TREE_CODE (cs) == FUNCTION_DECL))
            context = cs;
          else if (cs && TYPE_P (cs))
@@ -6304,8 +6301,7 @@ do_pushtag (tree name, tree type, tag_scope scope)
 
       if (b->kind == sk_class)
        {
-         if (!TYPE_BEING_DEFINED (current_class_type)
-             && scope != ts_lambda)
+         if (!TYPE_BEING_DEFINED (current_class_type))
            return error_mark_node;
 
          if (!PROCESSING_REAL_TEMPLATE_DECL_P ())
index 57bdc1c5ccc3c101e2e6122a3bc319a8301f3186..36a8449a81558aca53e6306fb719c52782fe9219 100644 (file)
@@ -1,3 +1,10 @@
+2017-11-16  Nathan Sidwell  <nathan@acm.org>
+
+       PR c++81060
+       * g++.dg/cpp0x/lambda/lambda-template13.C: Avoid undefined
+       template using local type error.
+       * g++.dg/cpp0x/pr81060.C: New.
+
 2017-11-16  Wilco Dijkstra  <wdijkstr@arm.com>
            Jackson Woodruff  <jackson.woodruff@arm.com>
 
index 01fe3f66cf4bee53422ccebe5c759052b06c38ef..8aaf5b2800f0c3c4198f9e3868462627b6214595 100644 (file)
@@ -4,7 +4,7 @@
 struct function
 {
   template < typename _Functor>
-  function (_Functor);
+  function (_Functor) {}
 };
 
 template <class U>
diff --git a/gcc/testsuite/g++.dg/cpp0x/pr81060.C b/gcc/testsuite/g++.dg/cpp0x/pr81060.C
new file mode 100644 (file)
index 0000000..67b2b38
--- /dev/null
@@ -0,0 +1,11 @@
+// { dg-do compile  { target c++11 } }
+// PR 81050 ICE in invalid after error
+
+template<typename... T> struct A
+{
+  static const int i;
+};
+
+template<typename... T>
+const int A<T>::i // { dg-error "template definition of non-template" }
+= []{ return 0; }(); // BOOM!