re PR c++/54947 ([C++11] lambda cannot capture-by-copy inside braced-init-list)
authorJason Merrill <jason@redhat.com>
Thu, 6 Dec 2012 14:45:11 +0000 (09:45 -0500)
committerJason Merrill <jason@gcc.gnu.org>
Thu, 6 Dec 2012 14:45:11 +0000 (09:45 -0500)
PR c++/54947
* parser.c (cp_parser_initializer_list): Don't require an
expression in [] to be constant until we know it's a C99
designator.

From-SVN: r194256

gcc/cp/ChangeLog
gcc/cp/parser.c
gcc/testsuite/g++.dg/cpp0x/lambda/lambda-initlist2.C [new file with mode: 0644]

index 1a1f459f52f8bc783aadaa32b7a36725e6fc7f6e..96a88b92b197662e14296a8dcacea1c1ab838510 100644 (file)
@@ -1,5 +1,10 @@
 2012-12-06  Jason Merrill  <jason@redhat.com>
 
+       PR c++/54947
+       * parser.c (cp_parser_initializer_list): Don't require an
+       expression in [] to be constant until we know it's a C99
+       designator.
+
        PR c++/55015
        PR c++/53821
        * semantics.c (maybe_add_lambda_conv_op): Revert earlier change.
index 190b8d94113bd6ae3e9450994867d1abc66e24f0..a010f1fb30588e813657cf7f6ef99ae2fb3aaba8 100644 (file)
@@ -17923,11 +17923,14 @@ cp_parser_initializer_list (cp_parser* parser, bool* non_constant_p)
          /* In C++11, [ could start a lambda-introducer.  */
          cp_parser_parse_tentatively (parser);
          cp_lexer_consume_token (parser->lexer);
-         designator = cp_parser_constant_expression (parser, false, NULL);
+         bool non_const = false;
+         designator = cp_parser_constant_expression (parser, true, &non_const);
          cp_parser_require (parser, CPP_CLOSE_SQUARE, RT_CLOSE_SQUARE);
          cp_parser_require (parser, CPP_EQ, RT_EQ);
          if (!cp_parser_parse_definitely (parser))
            designator = NULL_TREE;
+         else if (non_const)
+           require_potential_rvalue_constant_expression (designator);
        }
       else
        designator = NULL_TREE;
diff --git a/gcc/testsuite/g++.dg/cpp0x/lambda/lambda-initlist2.C b/gcc/testsuite/g++.dg/cpp0x/lambda/lambda-initlist2.C
new file mode 100644 (file)
index 0000000..daaa339
--- /dev/null
@@ -0,0 +1,27 @@
+// PR c++/54947
+// { dg-options -std=gnu++11 }
+
+struct X
+{
+  template<typename L>
+    X(L)
+    { }
+};
+
+template<typename A>
+  void
+  test()
+  {
+    int i = 0;
+
+    A a_ok_1( [=] { return i; } );  // OK
+    A a_ok_2( [i] { return i; } );  // OK
+
+    A a_err_1{ [i] { return i; } };  // error
+    A a_err_2{ [=] { return i; } };  // error
+  }
+
+int main()
+{
+  test<X>();
+}