------- Comment #7 from rguenth at gcc dot gnu dot org 2010-07-08 12:41 -------
(In reply to comment #6)
> With this short test case:
>
> struct s {
> double for_alignment;
> struct { int x, y, z; } a[16];
> };
>
> void f(struct s *s)
> {
> unsigned int i;
>
> for (i = 0; i < 16; ++i) {
> s->a[i].x = 0;
> s->a[i].y = 0;
> s->a[i].z = 0;
> }
> }
>
> revision 161840 changes the generated code as follows:
>
> --- pr44843.s-r161839 2010-07-08 14:00:06.000000000 +0200
> +++ pr44843.s-r161840 2010-07-08 14:00:26.000000000 +0200
> @@ -6,10 +6,9 @@
> .proc 020
> f:
> mov 16, %g1
> .LL2:
> - st %g0, [%o0+8]
> - st %g0, [%o0+12]
> + stx %g0, [%o0+8]
> st %g0, [%o0+16]
> addcc %g1, -1, %g1
> bne,pt %icc, .LL2
> add %o0, 12, %o0
>
> which will fail at runtime due to misalignment in the 2nd loop iteration.
>
> Removing the double which is there to align the struct and the start of the
> array eliminates the bug.
We end up with
MEM[(struct s *)D.2742_15 + 8B] = 0;
MEM[(struct s *)D.2742_15 + 12B] = 0;
MEM[(struct s *)D.2742_15 + 16B] = 0;
from which set_mem_attributes_minus_bitpos incorrectly concludes that
D.2742_15 points to sth that is aligned the same as struct s here:
else
/* This technically isn't correct. We can't really derive
alignment information from types. */
align = MAX (align,
TYPE_ALIGN (TREE_TYPE (TREE_TYPE (TREE_OPERAND (t, 1)))));
and the comment is correct.
--
http://gcc.gnu.org/bugzilla/show_bug.cgi?id=44843