tcpdump mailing list archives

Re: ARMv7 unaligned access


From: Andrew Lunn via tcpdump-workers <tcpdump-workers () lists tcpdump org>
Date: Sun, 21 Aug 2022 17:56:24 +0200

--- Begin Message --- From: Andrew Lunn <andrew () lunn ch>
Date: Sun, 21 Aug 2022 17:56:24 +0200
On Sun, Aug 21, 2022 at 11:10:53AM +0100, Denis Ovsienko via tcpdump-workers wrote:
Date: Sun, 21 Aug 2022 11:10:53 +0100
From: Denis Ovsienko <denis () ovsienko info>
To: tcpdump-workers () lists tcpdump org
Subject: ARMv7 unaligned access

Hello list.

Based on some prior online research, I used to think that ARMv7 is a
hardware that allows (by default or after simple tweaking) to terminate
a userspace process when it tries to perform an unaligned memory
access.  Which is exactly the behaviour wanted for the CI purposes.

Not long ago I moved the linux-armv7l Buildbot worker to a true ARMv7
board (RPI2B v1.1).  Consistent with the documentation [1], the kernel
seems to have the right knob in place, which a boot-time script sets to
the desired position:

$ cat /proc/cpu/alignment
User:         0
System:               0 (0x0)
Skipped:      0
Half:         0
Word:         0
DWord:                0
Multi:                0
User faults:  4 (signal)

You should probably ask Russell King.

    Andrew



However, this does not seem to have any effect, in that this short C
program, which does trigger a SIGBUS/SIGILL on other OSes and
architectures that do not like unaligned access, just completes
successfully on linux-armv7l:

---------------------------------------------------------------------
#include <stdint.h>
#include <stddef.h>
/*
#include <sys/sysmips.h>
*/

int main (void)
{
/*
      sysmips (MIPS_FIXADE, 0);
*/
      uint32_t *p;
      union
      {
              uint32_t u32[2];
              uint8_t u8[8];
      } u;
      u.u32[0] = 0;
      u.u32[1] = 1;
      p = (uint32_t *)(u.u8 + 0);
      *p = 3;
      p = (uint32_t *)(u.u8 + 1);
      *p = 3;
      p = (uint32_t *)(u.u8 + 2);
      *p = 3;
      p = (uint32_t *)(u.u8 + 3);
      *p = 3;

      uint8_t u8[20];
      for (size_t i = 0; i < 10; i++)
      {
              p = (uint32_t *)(u8 + i);
              *p = 4;
      }

      return 0;
}

Have you disassembled this to see what instructions it is using? The
compiler has enough information to see you are doing unaligned
accesses, and to use instructions which are efficient and avoid the
unaligned access.

If you do find the compiler is not optimising this, i suggest you ask
Russell King.

          Andrew

--- End Message ---
_______________________________________________
tcpdump-workers mailing list
tcpdump-workers () lists tcpdump org
https://lists.sandelman.ca/mailman/listinfo/tcpdump-workers

Current thread: