aboutsummaryrefslogtreecommitdiff
path: root/gcc/cp/cp-gimplify.c
diff options
context:
space:
mode:
authorJason Merrill <jason@redhat.com>2010-05-05 12:32:20 -0400
committerJason Merrill <jason@gcc.gnu.org>2010-05-05 12:32:20 -0400
commit6d729f282c059987f966fc3d9c98eb74e2d92839 (patch)
tree76394a4dd6bd685ffee7f55fc84a357aecb19236 /gcc/cp/cp-gimplify.c
parenta2c9b836ba7e2781effde72da473534cb32743ee (diff)
downloadgcc-6d729f282c059987f966fc3d9c98eb74e2d92839.zip
gcc-6d729f282c059987f966fc3d9c98eb74e2d92839.tar.gz
gcc-6d729f282c059987f966fc3d9c98eb74e2d92839.tar.bz2
re PR c++/43787 (memory copy of empty class (sizeof is one))
PR c++/43787 gcc: * gimplify.c (gimplify_expr): Keep working if gimplify_modify_expr returns GS_OK. (gimplify_modify_expr_rhs): Return GS_OK if anything changed. gcc/cp: * cp-gimplify.c (cp_gimplify_expr): Remove copies of empty classes. * call.c (build_over_call): Don't try to avoid INIT_EXPR copies here. From-SVN: r159072
Diffstat (limited to 'gcc/cp/cp-gimplify.c')
-rw-r--r--gcc/cp/cp-gimplify.c20
1 files changed, 20 insertions, 0 deletions
diff --git a/gcc/cp/cp-gimplify.c b/gcc/cp/cp-gimplify.c
index 533d2d1..d6ae28f 100644
--- a/gcc/cp/cp-gimplify.c
+++ b/gcc/cp/cp-gimplify.c
@@ -569,6 +569,26 @@ cp_gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
&& !useless_type_conversion_p (TREE_TYPE (op1), TREE_TYPE (op0)))
TREE_OPERAND (*expr_p, 1) = build1 (VIEW_CONVERT_EXPR,
TREE_TYPE (op0), op1);
+
+ else if ((rhs_predicate_for (op0)) (op1)
+ && !(TREE_CODE (op1) == CALL_EXPR
+ && CALL_EXPR_RETURN_SLOT_OPT (op1))
+ && is_really_empty_class (TREE_TYPE (op0)))
+ {
+ /* Remove any copies of empty classes. We check that the RHS
+ has a simple form so that TARGET_EXPRs and CONSTRUCTORs get
+ reduced properly, and we leave the return slot optimization
+ alone because it isn't a copy.
+
+ Also drop volatile variables on the RHS to avoid infinite
+ recursion from gimplify_expr trying to load the value. */
+ if (!TREE_SIDE_EFFECTS (op1)
+ || (DECL_P (op1) && TREE_THIS_VOLATILE (op1)))
+ *expr_p = op0;
+ else
+ *expr_p = build2 (COMPOUND_EXPR, TREE_TYPE (*expr_p),
+ op0, op1);
+ }
}
ret = GS_OK;
break;