[C++ PATCH] c++/92878 - Parenthesized init of aggregates in new-expression.
Jason Merrill
jason@redhat.com
Wed Dec 11 18:30:00 GMT 2019
On 12/10/19 2:13 PM, Marek Polacek wrote:
> Ville pointed out that our paren init of aggregates doesn't work for
>
> auto a = new A(1, 2, 3);
>
> and I think it should:
>
> A new-expression that creates an object of type T initializes that object
> as follows:
> ...
> -- Otherwise, the new-initializer is interpreted according to the
> initialization rules of [dcl.init] for direct-initialization.
>
> so I think it follows that we should perform dcl.init#17.6.2.2.
>
> This doesn't work with new[]; we have:
> error ("parenthesized initializer in array new");
>
> Bootstrapped/regtested on x86_64-linux, ok for trunk?
OK.
> 2019-12-10 Marek Polacek <polacek@redhat.com>
>
> PR c++/92878 - Parenthesized init of aggregates in new-expression.
> * init.c (build_new_1): Handle parenthesized initialization of
> aggregates in new-expression.
>
> * g++.dg/cpp2a/paren-init20.C: New test.
>
> diff --git gcc/cp/init.c gcc/cp/init.c
> index e40afe27e1a..b0331b8ba53 100644
> --- gcc/cp/init.c
> +++ gcc/cp/init.c
> @@ -3608,10 +3608,22 @@ build_new_1 (vec<tree, va_gc> **placement, tree type, tree nelts,
> tree ie;
>
> /* We are processing something like `new int (10)', which
> - means allocate an int, and initialize it with 10. */
> + means allocate an int, and initialize it with 10.
>
> - ie = build_x_compound_expr_from_vec (*init, "new initializer",
> - complain);
> + In C++20, also handle `new A(1, 2)'. */
> + if (cxx_dialect >= cxx2a
> + && AGGREGATE_TYPE_P (type)
> + && (*init)->length () > 1)
> + {
> + ie = build_tree_list_vec (*init);
> + ie = build_constructor_from_list (init_list_type_node, ie);
> + CONSTRUCTOR_IS_DIRECT_INIT (ie) = true;
> + CONSTRUCTOR_IS_PAREN_INIT (ie) = true;
> + ie = digest_init (type, ie, complain);
> + }
> + else
> + ie = build_x_compound_expr_from_vec (*init, "new initializer",
> + complain);
> init_expr = cp_build_modify_expr (input_location, init_expr,
> INIT_EXPR, ie, complain);
> }
> diff --git gcc/testsuite/g++.dg/cpp2a/paren-init20.C gcc/testsuite/g++.dg/cpp2a/paren-init20.C
> new file mode 100644
> index 00000000000..05da7604686
> --- /dev/null
> +++ gcc/testsuite/g++.dg/cpp2a/paren-init20.C
> @@ -0,0 +1,54 @@
> +// PR c++/92878 - Parenthesized init of aggregates in new-expression.
> +// { dg-do compile { target c++2a } }
> +// Test new TYPE(...).
> +
> +int f ();
> +
> +struct A
> +{
> + int a;
> + int b;
> +};
> +
> +void
> +fn_A ()
> +{
> + int i = 0;
> + auto y = new A(1, 2);
> + auto x = new A(++i, ++i);
> + auto z = new A(1, { ++i });
> + auto u = new A(1, f());
> +}
> +
> +struct B
> +{
> + int a;
> + int b;
> + int c = 42;
> +};
> +
> +void
> +fn_B ()
> +{
> + int i = 0;
> + auto y = new B(1, 2);
> + auto x = new B(++i, ++i);
> + auto z = new B(1, { ++i });
> + auto u = new B(1, f());
> +}
> +
> +struct C
> +{
> + int a;
> + int b = 10;
> +};
> +
> +void
> +fn_C ()
> +{
> + int i = 0;
> + auto y = new C(1);
> + auto x = new C(++i);
> + auto z = new C({ ++i });
> + auto u = new C(f());
> +}
>
More information about the Gcc-patches
mailing list