Commit fd2bfee5 by Jason Merrill Committed by Jason Merrill

PR c++/71972 - constexpr array self-modification

	* constexpr.c (cxx_eval_array_reference): Handle looking for the
	value of an element we're currently modifying.

From-SVN: r238729
parent 8d683375
2016-07-25 Jason Merrill <jason@redhat.com>
PR c++/71972
* constexpr.c (cxx_eval_array_reference): Handle looking for the
value of an element we're currently modifying.
2016-07-24 Jason Merrill <jason@redhat.com> 2016-07-24 Jason Merrill <jason@redhat.com>
PR c++/71515 PR c++/71515
......
...@@ -2129,8 +2129,32 @@ cxx_eval_array_reference (const constexpr_ctx *ctx, tree t, ...@@ -2129,8 +2129,32 @@ cxx_eval_array_reference (const constexpr_ctx *ctx, tree t,
else else
found = (i < len); found = (i < len);
if (!found) if (found)
{
tree r;
if (TREE_CODE (ary) == CONSTRUCTOR)
r = (*CONSTRUCTOR_ELTS (ary))[i].value;
else if (TREE_CODE (ary) == VECTOR_CST)
r = VECTOR_CST_ELT (ary, i);
else if (elem_nchars == 1)
r = build_int_cst (cv_unqualified (TREE_TYPE (TREE_TYPE (ary))),
TREE_STRING_POINTER (ary)[i]);
else
{ {
tree type = cv_unqualified (TREE_TYPE (TREE_TYPE (ary)));
r = native_interpret_expr (type, (const unsigned char *)
TREE_STRING_POINTER (ary)
+ i * elem_nchars, elem_nchars);
}
if (r)
/* Don't VERIFY_CONSTANT here. */
return r;
/* Otherwise the element doesn't have a value yet. */
}
/* Not found. */
if (TREE_CODE (ary) == CONSTRUCTOR if (TREE_CODE (ary) == CONSTRUCTOR
&& CONSTRUCTOR_NO_IMPLICIT_ZERO (ary)) && CONSTRUCTOR_NO_IMPLICIT_ZERO (ary))
{ {
...@@ -2148,23 +2172,6 @@ cxx_eval_array_reference (const constexpr_ctx *ctx, tree t, ...@@ -2148,23 +2172,6 @@ cxx_eval_array_reference (const constexpr_ctx *ctx, tree t,
tree val = build_value_init (elem_type, tf_warning_or_error); tree val = build_value_init (elem_type, tf_warning_or_error);
return cxx_eval_constant_expression (ctx, val, lval, non_constant_p, return cxx_eval_constant_expression (ctx, val, lval, non_constant_p,
overflow_p); overflow_p);
}
if (TREE_CODE (ary) == CONSTRUCTOR)
return (*CONSTRUCTOR_ELTS (ary))[i].value;
else if (TREE_CODE (ary) == VECTOR_CST)
return VECTOR_CST_ELT (ary, i);
else if (elem_nchars == 1)
return build_int_cst (cv_unqualified (TREE_TYPE (TREE_TYPE (ary))),
TREE_STRING_POINTER (ary)[i]);
else
{
tree type = cv_unqualified (TREE_TYPE (TREE_TYPE (ary)));
return native_interpret_expr (type, (const unsigned char *)
TREE_STRING_POINTER (ary)
+ i * elem_nchars, elem_nchars);
}
/* Don't VERIFY_CONSTANT here. */
} }
/* Subroutine of cxx_eval_constant_expression. /* Subroutine of cxx_eval_constant_expression.
......
// PR c++/71972
// { dg-do compile { target c++14 } }
typedef int size_t;
template <int N> struct S {
template <size_t M> constexpr S(const char (&)[M]) : data{} {
data[0] = data[0];
}
char data[N];
};
int main() {
constexpr S<1> s1("");
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment