https://gcc.gnu.org/bugzilla/show_bug.cgi?id=67246

Andrew Pinski <pinskia at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|UNCONFIRMED                 |RESOLVED
         Resolution|---                         |INVALID

--- Comment #3 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
(In reply to Thomas Martitz from comment #2)
> Thanks for your immediate reply.
> 
> In trying to provide a better test case I think I've found what the culprit
> is.
> 
> The full iphdr defintion is:
> 
> struct iphdr {
> #if defined(__LITTLE_ENDIAN_BITFIELD)
>       __u8    ihl:4,
>               version:4;
> #elif defined (__BIG_ENDIAN_BITFIELD)
>       __u8    version:4,
>               ihl:4;
> #else
> #error        "Please fix <asm/byteorder.h>"
> #endif
>       __u8    tos;
>       __be16  tot_len;
>       __be16  id;
>       __be16  frag_off;
>       __u8    ttl;
>       __u8    protocol;
>       __sum16 check;
>       __be32  saddr;
>       __be32  daddr;
>       /*The options start here. */
> };
> 
> Note that it ends with 32bit saddr and daddr fields.
> 
> If I change these to __be16, then the following code is generated:
>  248:   96220000        lhu     v0,0(s1)
>  24c:   8fa40044        lw      a0,68(sp)
>  250:   7c421a00        ext     v0,v0,0x8,0x4
>  254:   00021080        sll     v0,v0,0x2
>  258:   00821021        addu    v0,a0,v0
> 
> So I guess that means the 32bit fields change the alignment of the whole
> struct to 4 byte. And then the compiler assumes iph must be 4-byte aligned
> (in a conformant program).

yes that is correct.  The struct has alignment of 4 byte when there is a field
of 4 bytes long (unless you mark the struct to have a different alignment).

> 
> The linux code carefully avoids accessing saddr and daddr fields near this
> code (not shown above) so I guess it's aware of the potentially unaligned
> access.
> 
> So I'm not sure anymore who's on fault now

The linux kernel fault.  Does not matter what about the code around it or not.

Reply via email to