Browse Source

package/elfutils: handle missing user_pac_mask on aarch64

Since Buildroot commit [1] "package/elfutils: bump to version 0.192"
elfutils fails to build on Aarch64 with toolchain including Kernel older
than version 5.0. Error shows:

    aarch64_initreg.c: In function 'aarch64_set_initial_registers_tid':
    aarch64_initreg.c:61:24: error: storage size of 'pac_mask' isn't
    known
       61 |   struct user_pac_mask pac_mask;
          |                        ^~~~~~~~

elfutils 0.192 introduced a Aarch64 pointer authentication support in
upstream commit [2].

For reference, the user_pac_mask structure was introduced in Kernel
upstream commit [3], included in Kernel v5.0.

This is fixed in the upstream [4] so bring that patch in.

Fixes:
- e.g https://autobuild.buildroot.org/results/5156901a73be52ce8ffbf10729e6852499a300be/
- 4/6 of the failures here: https://autobuild.buildroot.org/?reason=elfutils-0.192&arch=aarch64

[1] https://gitlab.com/buildroot.org/buildroot/-/commit/5eb734766b24de5fce6e586897cd4827f8855442
[2] https://sourceware.org/git/?p=elfutils.git;a=commitdiff;h=64e3b451ad2cec8d45661b1816e3d2dc4431f3ca
[3] https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/commit/?id=ec6e822d1a22d0eef1d1fa260dff751dba9a4258
[4] https://sourceware.org/git/?p=elfutils.git;a=commit;h=52a747a316042e70a22acb489df9e51bfc6bf2d5

Signed-off-by: Alex Bennée <alex.bennee@linaro.org>
Signed-off-by: Julien Olivain <ju.o@free.fr>
Alex Bennée 4 months ago
parent
commit
ae884111d2
1 changed files with 97 additions and 0 deletions
  1. 97 0
      package/elfutils/0003-define-user_pac_mask-if-needed.patch

+ 97 - 0
package/elfutils/0003-define-user_pac_mask-if-needed.patch

@@ -0,0 +1,97 @@
+From 52a747a316042e70a22acb489df9e51bfc6bf2d5 Mon Sep 17 00:00:00 2001
+From: Markus Mayer <mmayer@broadcom.com>
+Date: Fri, 21 Feb 2025 11:19:34 -0800
+Subject: [PATCH] aarch64: define struct user_pac_mask if needed
+
+On Aarch64, Linux is using Pointer Authentication Code (PAC) for pointer
+authentication.[1] The struct "user_pac_mask" has been part of the Linux
+kernel since version 5.0 as part of this feature. However, older kernels
+do not define it.
+
+Therefore, we want to check if the definition is present in the kernel
+headers and provide one if it isn't. This ensures two things:
+
+* elfutils will continue to compile against kernel headers from 4.x
+* binaries built against older kernel headers will still be fully
+  functional if used on a newer system
+
+For reference, the build error that is being avoided looks like this:
+
+[...]
+  CC       aarch64_initreg.o
+aarch64_initreg.c: In function 'aarch64_set_initial_registers_tid':
+aarch64_initreg.c:61:24: error: storage size of 'pac_mask' isn't known
+   struct user_pac_mask pac_mask;
+                        ^~~~~~~~
+aarch64_initreg.c:61:24: warning: unused variable 'pac_mask' [-Wunused-variable]
+make[4]: *** [Makefile:831: aarch64_initreg.o] Error 1
+make[3]: *** [Makefile:547: all-recursive] Error 1
+make[2]: *** [Makefile:463: all] Error 2
+
+[1] https://docs.kernel.org/arch/arm64/pointer-authentication.html
+
+https://sourceware.org/bugzilla/show_bug.cgi?id=32684
+
+Fixes: 64e3b451ad2c ("aarch64: extend dwfl_thread_state_registers to handle PAC")
+Signed-off-by: Markus Mayer <mmayer@broadcom.com>
+Signed-off-by: Alex Bennée <alex.bennee@linaro.org>
+Upstream: https://sourceware.org/git/?p=elfutils.git;a=commit;h=52a747a316042e70a22acb489df9e51bfc6bf2d5
+---
+ backends/aarch64_initreg.c | 21 +++++++++++++++++++++
+ configure.ac               |  8 ++++++++
+ 2 files changed, 29 insertions(+)
+
+diff --git a/backends/aarch64_initreg.c b/backends/aarch64_initreg.c
+index 5ec45ea60..a6badbb45 100644
+--- a/backends/aarch64_initreg.c
++++ b/backends/aarch64_initreg.c
+@@ -47,6 +47,27 @@
+ #define BACKEND aarch64_
+ #include "libebl_CPU.h"
+ 
++/*
++ * pointer authentication masks (NT_ARM_PAC_MASK)
++ *
++ * Defined by Linux kernel headers since Linux 5.0. Define it here if kernel
++ * headers are older than that, to ensure this file builds regardless.
++ */
++#if defined(__aarch64__) && defined(__linux__)
++
++#ifndef NT_ARM_PAC_MASK
++#define NT_ARM_PAC_MASK 0x406
++#endif
++
++#ifndef HAVE_USER_PACK_MASK
++struct user_pac_mask {
++  __u64 data_mask;
++  __u64 insn_mask;
++};
++#endif
++
++#endif /* __aarch64__ && __linux__ */
++
+ bool
+ aarch64_set_initial_registers_tid (pid_t tid __attribute__ ((unused)),
+ 			  ebl_tid_registers_t *setfunc __attribute__ ((unused)),
+diff --git a/configure.ac b/configure.ac
+index e57d39275..3298f7fc7 100644
+--- a/configure.ac
++++ b/configure.ac
+@@ -777,6 +777,14 @@ if test "$sys_user_has_user_regs" = "yes"; then
+             [Define to 1 if <sys/user.h> defines struct user_regs_struct])
+ fi
+ 
++AC_CHECK_TYPE([struct user_pac_mask],
++              [has_user_pac_mask=yes], [has_user_pac_mask=no],
++              [[#include <asm/ptrace.h>]])
++if test "$has_user_pac_mask" = "yes"; then
++  AC_DEFINE(HAVE_USER_PACK_MASK, 1,
++            [Defined if struct user_pac_mask exists.])
++fi
++
+ # On a 64-bit host where can can use $CC -m32, we'll run two sets of tests.
+ utrace_BIARCH
+ CC_BIARCH="$CC $utrace_biarch"
+-- 
+2.43.5
+