Commit 68d01920 by Jason Merrill Committed by Jason Merrill

PR c++/77945 - constexpr and trivial copy

	* constexpr.c (maybe_simplify_trivial_copy): New.
	(cxx_eval_store_expression): Call it.
	* call.c (build_over_call): Use unsigned char for trivial copy.

From-SVN: r241204
parent f9e9d32f
2016-10-15 Jason Merrill <jason@redhat.com>
PR c++/77945
* constexpr.c (maybe_simplify_trivial_copy): New.
(cxx_eval_store_expression): Call it.
* call.c (build_over_call): Use unsigned char for trivial copy.
2016-10-14 Jason Merrill <jason@redhat.com>
Implement P0017R1, C++17 aggregates with bases.
......
......@@ -7909,7 +7909,7 @@ build_over_call (struct z_candidate *cand, int flags, tsubst_flags_t complain)
arg2 = TYPE_SIZE_UNIT (as_base);
arg0 = cp_build_addr_expr (to, complain);
array_type = build_array_type (char_type_node,
array_type = build_array_type (unsigned_char_type_node,
build_index_type
(size_binop (MINUS_EXPR,
arg2, size_int (1))));
......
......@@ -3206,6 +3206,26 @@ var_in_maybe_constexpr_fn (tree t)
return var_in_constexpr_fn (t);
}
/* We're assigning INIT to TARGET. In do_build_copy_constructor and
build_over_call we implement trivial copy of a class with tail padding using
assignment of character arrays, which is valid in normal code, but not in
constexpr evaluation. We don't need to worry about clobbering tail padding
in constexpr evaluation, so strip the type punning. */
static void
maybe_simplify_trivial_copy (tree &target, tree &init)
{
if (TREE_CODE (target) == MEM_REF
&& TREE_CODE (init) == MEM_REF
&& TREE_TYPE (target) == TREE_TYPE (init)
&& TREE_CODE (TREE_TYPE (target)) == ARRAY_TYPE
&& TREE_TYPE (TREE_TYPE (target)) == unsigned_char_type_node)
{
target = build_fold_indirect_ref (TREE_OPERAND (target, 0));
init = build_fold_indirect_ref (TREE_OPERAND (init, 0));
}
}
/* Evaluate an INIT_EXPR or MODIFY_EXPR. */
static tree
......@@ -3222,6 +3242,9 @@ cxx_eval_store_expression (const constexpr_ctx *ctx, tree t,
/* First we figure out where we're storing to. */
tree target = TREE_OPERAND (t, 0);
maybe_simplify_trivial_copy (target, init);
tree type = TREE_TYPE (target);
target = cxx_eval_constant_expression (ctx, target,
true,
......
// PR c++/77945
// { dg-do compile { target c++11 } }
struct T
{
int x = 0;
bool y = 0;
constexpr T() {}
};
int main()
{
constexpr T t = (T{} = T{});
}
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