On Mon, Jul 3, 2017 at 8:23 PM, Nadav Amit via iovisor-dev
<iovisor-dev@lists.iovisor.org> wrote:
> I get a strange phenomenon with packed structs in which each byte is
> loaded in a different instruction.
>
> Consider for example xdp_prog1 for Linux samples. After building it, the
> disassembly starts with:
>
> xdp_prog1:
>        0:       61 12 04 00 00 00 00 00         r2 = *(u32 *)(r1 + 4)
>        1:       61 11 00 00 00 00 00 00         r1 = *(u32 *)(r1 + 0)
>        2:       bf 13 00 00 00 00 00 00         r3 = r1
>        3:       07 03 00 00 0e 00 00 00         r3 += 14
>        4:       2d 23 37 00 00 00 00 00         if r3 > r2 goto 55
>        5:       71 13 0c 00 00 00 00 00         r3 = *(u8 *)(r1 + 12)
>        6:       71 14 0d 00 00 00 00 00         r4 = *(u8 *)(r1 + 13)
>        7:       67 04 00 00 08 00 00 00         r4 <<= 8
>        8:       4f 34 00 00 00 00 00 00         r4 |= r3
>        9:       15 04 02 00 88 a8 00 00         if r4 == 43144 goto 2
>       10:       b7 03 00 00 0e 00 00 00         r3 = 14
>       11:       55 04 05 00 81 00 00 00         if r4 != 129 goto 5
>
>
> As you can see, the games in instructions 5-8 that access h_proto (u16) are
> very unnecessary. Redefining 'struct ethhdr’ as “unpacked” (i.e., without
> the packed attribute), eliminates this behavior.
>
> xdp_prog1:
>        0:       61 12 04 00 00 00 00 00         r2 = *(u32 *)(r1 + 4)
>        1:       61 11 00 00 00 00 00 00         r1 = *(u32 *)(r1 + 0)
>        2:       bf 13 00 00 00 00 00 00         r3 = r1
>        3:       07 03 00 00 0e 00 00 00         r3 += 14
>        4:       2d 23 34 00 00 00 00 00         if r3 > r2 goto 52
>        5:       69 14 0c 00 00 00 00 00         r4 = *(u16 *)(r1 + 12)
>        6:       15 04 02 00 88 a8 00 00         if r4 == 43144 goto 2
>        7:       b7 03 00 00 0e 00 00 00         r3 = 14
>        8:       55 04 05 00 81 00 00 00         if r4 != 129 goto 5
>
> As you can see, now the the variable is accessed in one chunk, as expected.
>
> Any clues to what went wrong?

This is expected from current llvm implementation. For unpacked, the
compiler is able to use field natural alignment to decide which load
variant to use.
For packed, the field alignment is assumed to be 1, so it use load-byte.

>
> Thanks,
> Nadav
> _______________________________________________
> iovisor-dev mailing list
> iovisor-dev@lists.iovisor.org
> https://lists.iovisor.org/mailman/listinfo/iovisor-dev
_______________________________________________
iovisor-dev mailing list
iovisor-dev@lists.iovisor.org
https://lists.iovisor.org/mailman/listinfo/iovisor-dev

Reply via email to