On Mon, Jan 07, 2019 at 09:52:55PM -0500, Jason Merrill wrote: > On 1/7/19 6:56 PM, Marek Polacek wrote: > > At the risk of seeming overly eager, I thought it would be reasonable to > > go with the following: enabling braced-init-list as a template-argument. > > As the discussion on the reflector clearly indicates, this was the intent > > from the get-go. > > > > I know, it's not a regression. But I restricted the change to C++20, and it > > should strictly allow code that wasn't accepted before -- when a template > > argument starts with {. Perhaps we could even drop the C++20 check. > > > > What's your preference? > > Let's keep the C++20 check for now at least. I'd suggest moving the change > further down, with this code:
Okay. I've experimented with checking expr_non_constant_p, but this version gives better diagnostics. Bootstrapped/regtested running on x86_64-linux, ok for trunk if it passes? 2019-01-08 Marek Polacek <pola...@redhat.com> PR c++/88538 - braced-init-list in template-argument-list. * parser.c (cp_parser_template_argument): Handle braced-init-list when in C++20. * g++.dg/cpp2a/nontype-class11.C: New test. diff --git gcc/cp/parser.c gcc/cp/parser.c index bca1739ace3..87f37d8ab2b 100644 --- gcc/cp/parser.c +++ gcc/cp/parser.c @@ -17020,6 +17020,18 @@ cp_parser_template_argument (cp_parser* parser) argument = cp_parser_constant_expression (parser); else { + /* In C++20, we can encounter a braced-init-list. */ + if (cxx_dialect >= cxx2a + && cp_lexer_next_token_is (parser->lexer, CPP_OPEN_BRACE)) + { + cp_parser_parse_tentatively (parser); + bool expr_non_constant_p; + argument = cp_parser_braced_list (parser, &expr_non_constant_p); + if (cp_parser_parse_definitely (parser)) + /* Yup, it was a braced-init-list. */ + return argument; + } + /* With C++17 generalized non-type template arguments we need to handle lvalue constant expressions, too. */ argument = cp_parser_assignment_expression (parser); diff --git gcc/testsuite/g++.dg/cpp2a/nontype-class11.C gcc/testsuite/g++.dg/cpp2a/nontype-class11.C new file mode 100644 index 00000000000..8a06d23904b --- /dev/null +++ gcc/testsuite/g++.dg/cpp2a/nontype-class11.C @@ -0,0 +1,21 @@ +// PR c++/88538 +// { dg-do compile { target c++2a } } + +struct S { + unsigned a; + unsigned b; + constexpr S(unsigned _a, unsigned _b) noexcept: a{_a}, b{_b} { } +}; + +template <S p> +void fnc() +{ +} + +template<S s> struct X { }; + +void f() +{ + fnc<{10,20}>(); + X<{1, 2}> x; +}