This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[PATCH] Fix PR49937
- From: Richard Guenther <rguenther at suse dot de>
- To: gcc-patches at gcc dot gnu dot org
- Date: Tue, 9 Aug 2011 17:17:18 +0200 (CEST)
- Subject: [PATCH] Fix PR49937
This fixes PR49937 - callers of get_{pointer,object}_alignment
probably should not use BIGGEST_ALIGNMENT to limit what these
functions return (why do they do that? Maybe because formerly
the routines returned TYPE_ALIGN? But why wasn't that bound by
BIGGEST_ALIGNMENT?) - some targets define that as 8 (such as cris or avr).
At least CCP shouldn't care and with the following patch simply
trusts what DECL_ALIGN and friend tells us (which hopefully is correct
...).
Bootstrapped and tested on x86_64-unknown-linux-gnu.
Anybody know about BIGGEST_ALIGNMENTs implication on correctness?
Thanks,
Richard.
2011-08-09 Richard Guenther <rguenther@suse.de>
PR tree-optimization/49937
* tree-ssa-ccp.c (get_value_from_alignment): Re-implement
using get_object_alignment_1.
Index: gcc/tree-ssa-ccp.c
===================================================================
*** gcc/tree-ssa-ccp.c (revision 177558)
--- gcc/tree-ssa-ccp.c (working copy)
*************** value_to_double_int (prop_value_t val)
*** 505,578 ****
static prop_value_t
get_value_from_alignment (tree expr)
{
prop_value_t val;
! HOST_WIDE_INT bitsize, bitpos;
! tree base, offset;
! enum machine_mode mode;
! int align;
gcc_assert (TREE_CODE (expr) == ADDR_EXPR);
! base = get_inner_reference (TREE_OPERAND (expr, 0),
! &bitsize, &bitpos, &offset,
! &mode, &align, &align, false);
! if (TREE_CODE (base) == MEM_REF)
! val = bit_value_binop (PLUS_EXPR, TREE_TYPE (expr),
! TREE_OPERAND (base, 0), TREE_OPERAND (base, 1));
! else if (base
! && ((align = get_object_alignment (base, BIGGEST_ALIGNMENT))
! > BITS_PER_UNIT))
! {
! val.lattice_val = CONSTANT;
! /* We assume pointers are zero-extended. */
! val.mask = double_int_and_not
! (double_int_mask (TYPE_PRECISION (TREE_TYPE (expr))),
! uhwi_to_double_int (align / BITS_PER_UNIT - 1));
! val.value = build_int_cst (TREE_TYPE (expr), 0);
! }
else
! {
! val.lattice_val = VARYING;
! val.mask = double_int_minus_one;
! val.value = NULL_TREE;
! }
! if (bitpos != 0)
! {
! double_int value, mask;
! bit_value_binop_1 (PLUS_EXPR, TREE_TYPE (expr), &value, &mask,
! TREE_TYPE (expr), value_to_double_int (val), val.mask,
! TREE_TYPE (expr),
! shwi_to_double_int (bitpos / BITS_PER_UNIT),
! double_int_zero);
! val.lattice_val = double_int_minus_one_p (mask) ? VARYING : CONSTANT;
! val.mask = mask;
! if (val.lattice_val == CONSTANT)
! val.value = double_int_to_tree (TREE_TYPE (expr), value);
! else
! val.value = NULL_TREE;
! }
! /* ??? We should handle i * 4 and more complex expressions from
! the offset, possibly by just expanding get_value_for_expr. */
! if (offset != NULL_TREE)
! {
! double_int value, mask;
! prop_value_t oval = get_value_for_expr (offset, true);
! bit_value_binop_1 (PLUS_EXPR, TREE_TYPE (expr), &value, &mask,
! TREE_TYPE (expr), value_to_double_int (val), val.mask,
! TREE_TYPE (expr), value_to_double_int (oval),
! oval.mask);
! val.mask = mask;
! if (double_int_minus_one_p (mask))
! {
! val.lattice_val = VARYING;
! val.value = NULL_TREE;
! }
! else
! {
! val.lattice_val = CONSTANT;
! val.value = double_int_to_tree (TREE_TYPE (expr), value);
! }
! }
return val;
}
--- 505,530 ----
static prop_value_t
get_value_from_alignment (tree expr)
{
+ tree type = TREE_TYPE (expr);
prop_value_t val;
! unsigned HOST_WIDE_INT bitpos;
! unsigned int align;
gcc_assert (TREE_CODE (expr) == ADDR_EXPR);
! align = get_object_alignment_1 (TREE_OPERAND (expr, 0), &bitpos);
! gcc_assert ((bitpos & (align-1)) == bitpos);
! val.mask
! = double_int_and_not (POINTER_TYPE_P (type) || TYPE_UNSIGNED (type)
! ? double_int_mask (TYPE_PRECISION (type))
! : double_int_minus_one,
! uhwi_to_double_int (align / BITS_PER_UNIT - 1));
! val.lattice_val = double_int_minus_one_p (val.mask) ? VARYING : CONSTANT;
! if (val.lattice_val == CONSTANT)
! val.value
! = double_int_to_tree (type, uhwi_to_double_int (bitpos / BITS_PER_UNIT));
else
! val.value = NULL_TREE;
return val;
}