From 5c67ef9aef20c1be9e6214b2cf8ea86df1af5415 Mon Sep 17 00:00:00 2001 From: Jason Merrill Date: Sat, 6 Aug 2011 00:34:21 -0400 Subject: [PATCH] re PR c++/49988 (constexpr on ctor invokes improper initialization) PR c++/49988 * semantics.c (cxx_eval_array_reference): Handle failure to reduce the array operand to something we can work with. From-SVN: r177496 --- gcc/cp/ChangeLog | 6 +++++ gcc/cp/semantics.c | 9 +++++++- gcc/testsuite/ChangeLog | 5 ++++ .../g++.dg/cpp0x/constexpr-non-const-arg3.C | 23 +++++++++++++++++++ 4 files changed, 42 insertions(+), 1 deletion(-) create mode 100644 gcc/testsuite/g++.dg/cpp0x/constexpr-non-const-arg3.C diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 9fe645003ea..3c1ad7f5959 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,9 @@ +2011-08-05 Jason Merrill + + PR c++/49988 + * semantics.c (cxx_eval_array_reference): Handle failure to + reduce the array operand to something we can work with. + 2011-08-05 Gabriel Charette * decl.c (finish_function): Remove unecessary line 0 hack. diff --git a/gcc/cp/semantics.c b/gcc/cp/semantics.c index ac24b779dd2..2f02e696dba 100644 --- a/gcc/cp/semantics.c +++ b/gcc/cp/semantics.c @@ -6428,12 +6428,19 @@ cxx_eval_array_reference (const constexpr_call *call, tree t, elem_type = TREE_TYPE (TREE_TYPE (ary)); if (TREE_CODE (ary) == CONSTRUCTOR) len = CONSTRUCTOR_NELTS (ary); - else + else if (TREE_CODE (ary) == STRING_CST) { elem_nchars = (TYPE_PRECISION (elem_type) / TYPE_PRECISION (char_type_node)); len = (unsigned) TREE_STRING_LENGTH (ary) / elem_nchars; } + else + { + /* We can't do anything with other tree codes, so use + VERIFY_CONSTANT to complain and fail. */ + VERIFY_CONSTANT (ary); + gcc_unreachable (); + } if (compare_tree_int (index, len) >= 0) { if (tree_int_cst_lt (index, array_type_nelts_top (TREE_TYPE (ary)))) diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index e6f0cd78c95..af49861a64b 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2011-08-05 Jason Merrill + + PR c++/49988 + * g++.dg/cpp0x/constexpr-non-const-arg3.C: New. + 2011-08-05 H.J. Lu PR target/47369 diff --git a/gcc/testsuite/g++.dg/cpp0x/constexpr-non-const-arg3.C b/gcc/testsuite/g++.dg/cpp0x/constexpr-non-const-arg3.C new file mode 100644 index 00000000000..581be6d15ce --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/constexpr-non-const-arg3.C @@ -0,0 +1,23 @@ +// PR c++/49988 +// { dg-options -std=c++0x } +// { dg-do run } + +template struct X { }; + +struct A { + char data[3]; + template + constexpr + A(const char (&s)[3], X x) : data{ s[I]...} { } +}; +struct B { + A a; + B(const char (&s)[3]) : a{s,X<0,1,2>{}} { } +}; + +int main() +{ + B b{"12"}; + if (b.a.data[0] != '1') + return 1; +} -- 2.30.2