From 8b5d34fc0687dcf53c80c7fa2baa285ebf753708 Mon Sep 17 00:00:00 2001 From: Jason Merrill Date: Fri, 3 Jan 2020 17:10:56 -0500 Subject: [PATCH] PR c++/93033 - incorrect tree node sharing with array init. The split_nonconstant_init piece is the only one necessary to fix the testcase, but it occurred to me that we might as well not split when -fno-exceptions. * typeck2.c (split_nonconstant_init): Unshare non-decl. * cp-gimplify.c (cp_gimplify_init_expr): Only split if -fexceptions. From-SVN: r279871 --- gcc/cp/ChangeLog | 6 ++++++ gcc/cp/cp-gimplify.c | 1 + gcc/cp/typeck2.c | 4 +++- gcc/testsuite/g++.dg/cpp0x/initlist-array9.C | 20 ++++++++++++++++++++ 4 files changed, 30 insertions(+), 1 deletion(-) create mode 100644 gcc/testsuite/g++.dg/cpp0x/initlist-array9.C diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 9b607b2f073..421048b79d0 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,9 @@ +2020-01-03 Jason Merrill + + PR c++/93033 - incorrect tree node sharing with array init. + * typeck2.c (split_nonconstant_init): Unshare non-decl. + * cp-gimplify.c (cp_gimplify_init_expr): Only split if -fexceptions. + 2020-01-02 Jason Merrill * pt.c (invalid_nontype_parm_type_p): Reject class placeholder in diff --git a/gcc/cp/cp-gimplify.c b/gcc/cp/cp-gimplify.c index 3eca3591e01..eb552767f61 100644 --- a/gcc/cp/cp-gimplify.c +++ b/gcc/cp/cp-gimplify.c @@ -529,6 +529,7 @@ cp_gimplify_init_expr (tree *expr_p, gimple_seq *pre_p) /* If we might need to clean up a partially constructed object, break down the CONSTRUCTOR with split_nonconstant_init. */ if (TREE_CODE (from) == CONSTRUCTOR + && flag_exceptions && TREE_SIDE_EFFECTS (from) && TYPE_HAS_NONTRIVIAL_DESTRUCTOR (TREE_TYPE (to))) { diff --git a/gcc/cp/typeck2.c b/gcc/cp/typeck2.c index f36a5649ae6..955669727c3 100644 --- a/gcc/cp/typeck2.c +++ b/gcc/cp/typeck2.c @@ -34,6 +34,7 @@ along with GCC; see the file COPYING3. If not see #include "intl.h" #include "gcc-rich-location.h" #include "target.h" +#include "gimplify.h" static tree process_init_constructor (tree type, tree init, int nested, int flags, @@ -791,7 +792,8 @@ split_nonconstant_init (tree dest, tree init) } else if (init) { - tree ie = build2 (INIT_EXPR, void_type_node, dest, init); + tree ie = build2 (INIT_EXPR, void_type_node, + unshare_expr (dest), init); code = add_stmt_to_compound (ie, code); } } diff --git a/gcc/testsuite/g++.dg/cpp0x/initlist-array9.C b/gcc/testsuite/g++.dg/cpp0x/initlist-array9.C new file mode 100644 index 00000000000..4a5d74f6166 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/initlist-array9.C @@ -0,0 +1,20 @@ +// PR c++/93033 +// { dg-do compile { target c++11 } } + +struct A { + A (); + ~A (); +}; + +A f(); + +struct B { + A a; + bool b; +}; + +void +foo () +{ + B i[] { f() }; +}