From: Marek Polacek Date: Tue, 1 Sep 2020 15:44:16 +0000 (-0400) Subject: c++: Allow new char[4]{"foo"} [PR77841] X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=b1c59b31ef7adc832405209e9e2a77212284abd7;p=gcc.git c++: Allow new char[4]{"foo"} [PR77841] Currently, we allow new char[]{"foo"}, but not new char[4]{"foo"}. We should accept the latter too: [dcl.init.list]p3.3 says to treat this as [dcl.init.string]. We were rejecting this code because we never called reshape_init before the digest_init in build_new_1. reshape_init handles [dcl.init.string] by unwrapping the STRING_CST from its enclosing { }, and digest_init assumes that reshape_init has been called for aggregates anyway, and an array is an aggregate. gcc/cp/ChangeLog: PR c++/77841 * init.c (build_new_1): Call reshape_init. gcc/testsuite/ChangeLog: PR c++/77841 * g++.dg/cpp0x/initlist-new4.C: New test. --- diff --git a/gcc/cp/init.c b/gcc/cp/init.c index 360ab8c0b52..d4540db3605 100644 --- a/gcc/cp/init.c +++ b/gcc/cp/init.c @@ -3575,6 +3575,12 @@ build_new_1 (vec **placement, tree type, tree nelts, /* We'll check the length at runtime. */ domain = NULL_TREE; arraytype = build_cplus_array_type (type, domain); + /* If we have new char[4]{"foo"}, we have to reshape + so that the STRING_CST isn't wrapped in { }. */ + vecinit = reshape_init (arraytype, vecinit, complain); + /* The middle end doesn't cope with the location wrapper + around a STRING_CST. */ + STRIP_ANY_LOCATION_WRAPPER (vecinit); vecinit = digest_init (arraytype, vecinit, complain); } } diff --git a/gcc/testsuite/g++.dg/cpp0x/initlist-new4.C b/gcc/testsuite/g++.dg/cpp0x/initlist-new4.C new file mode 100644 index 00000000000..d7b418426bb --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/initlist-new4.C @@ -0,0 +1,6 @@ +// PR c++/77841 +// { dg-do compile { target c++11 } } + +char *p1 = new char[4]{"foo"}; +char *p2 = new char[5]{"foo"}; +char *p3 = new char[3]{"foo"}; // { dg-error "too long" }