[glibc/azanella/arm-static-pie] arm: Enable static-pie support (BZ 34098)

Adhemerval Zanella via Glibc-cvs <[email protected]>
Newsgroups gmane.comp.lib.glibc.cvs
Message-ID <[email protected]>
https://sourceware.org/git/gitweb.cgi?p=glibc.git;h=84a9ee28371fecc09b775e81e89c19939229f254

commit 84a9ee28371fecc09b775e81e89c19939229f254
Author: Adhemerval Zanella <[email protected]>
Date:   Thu Apr 23 17:53:16 2026 -0300

    arm: Enable static-pie support (BZ 34098)
    
    It requires proper gcc support [1], without it the -static-pie does
    not pass the correct linker flags.  This is checked during configure,
    which disables SUPPORT_STATIC_PIE.
    
    The start.S requires some adjustment to avoid loading main from
    the GOT.
    
    Checked on arm-linux-gnueabihf.
    
    [1] https://gcc.gnu.org/pipermail/gcc-patches/2022-July/598610.html

Diff:
---
 NEWS                     |  3 +++
 sysdeps/arm/configure    | 52 ++++++++++++++++++++++++++++++++++++++++++++++++
 sysdeps/arm/configure.ac | 29 +++++++++++++++++++++++++++
 sysdeps/arm/start.S      | 16 +++++++++++++++
 4 files changed, 100 insertions(+)

diff --git a/NEWS b/NEWS
index eac9322161..6a45bb06ff 100644
--- a/NEWS
+++ b/NEWS
@@ -18,6 +18,9 @@ Major new features:
 
 * New locale added: hrx_BR (Hunsrik language spoken in Brazil).
 
+* Static PIE is ow support for arm-*-linux-gnueabi.  It requires toolchain
+  support to correctly set the expected linker options.
+
 Deprecated and removed features, and other changes affecting compatibility:
 
 * Although malloc and related functions currently return pointers
diff --git a/sysdeps/arm/configure b/sysdeps/arm/configure
index 935e022c74..b964c3917a 100644
--- a/sysdeps/arm/configure
+++ b/sysdeps/arm/configure
@@ -1,6 +1,58 @@
 # This file is generated from configure.ac by Autoconf.  DO NOT EDIT!
  # Local configure fragment for sysdeps/arm.
 
+{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: checking if compiler support static PIE" >&5
+printf %s "checking if compiler support static PIE... " >&6; }
+if test ${libc_cv_static_pie_on_arm+y}
+then :
+  printf %s "(cached) " >&6
+else case e in #(
+  e)
+cat > conftest.S <<\EOF
+.text
+.global _start
+.type _start,#function
+_start:
+
+.data
+.align 2
+ptr:
+  /* This shoul produce an R_ARM_RELATIVE.  */
+  .word _start
+EOF
+
+  libc_cv_static_pie_on_arm=no
+  if { ac_try='${CC-cc} $CFLAGS $CPPFLAGS $LDFLAGS -static-pie -nostdlib -fPIE -o conftest conftest.S'
+  { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_try\""; } >&5
+  (eval $ac_try) 2>&5
+  ac_status=$?
+  printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; }; } \
+     && { ac_try='LC_ALL=C $READELF -Wr conftest | grep -q R_ARM_RELATIVE'
+  { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_try\""; } >&5
+  (eval $ac_try) 2>&5
+  ac_status=$?
+  printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; }; } \
+     && ! { ac_try='LC_ALL=C $READELF -Wl conftest | grep -q INTERP'
+  { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_try\""; } >&5
+  (eval $ac_try) 2>&5
+  ac_status=$?
+  printf "%s\n" "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
+  test $ac_status = 0; }; }
+  then
+    libc_cv_static_pie_on_arm=yes
+  fi
+  rm -rf conftest*  ;;
+esac
+fi
+{ printf "%s\n" "$as_me:${as_lineno-$LINENO}: result: $libc_cv_static_pie_on_arm" >&5
+printf "%s\n" "$libc_cv_static_pie_on_arm" >&6; }
+if test "$libc_cv_static_pie_on_arm" = yes; then
+  printf "%s\n" "#define SUPPORT_STATIC_PIE 1" >>confdefs.h
+
+fi
+
 # We check to see if the compiler and flags are
 # selecting the hard-float ABI and if they are then
 # we set libc_cv_arm_pcs_vfp to yes which causes
diff --git a/sysdeps/arm/configure.ac b/sysdeps/arm/configure.ac
index cd00ddc9d9..7153994f42 100644
--- a/sysdeps/arm/configure.ac
+++ b/sysdeps/arm/configure.ac
@@ -1,6 +1,35 @@
 GLIBC_PROVIDES dnl See aclocal.m4 in the top level source directory.
 # Local configure fragment for sysdeps/arm.
 
+dnl Test if the foolchain support static PIE, and it if pass the
+dnl correct flags to the linker.
+AC_CACHE_CHECK([if compiler support static PIE],
+libc_cv_static_pie_on_arm, [
+cat > conftest.S <<\EOF
+.text
+.global _start
+.type _start,#function
+_start:
+
+.data
+.align 2
+ptr:
+  /* This shoul produce an R_ARM_RELATIVE.  */
+  .word _start
+EOF
+
+  libc_cv_static_pie_on_arm=no
+  if AC_TRY_COMMAND([${CC-cc} $CFLAGS $CPPFLAGS $LDFLAGS -static-pie -nostdlib -fPIE -o conftest conftest.S]) \
+     && AC_TRY_COMMAND([LC_ALL=C $READELF -Wr conftest | grep -q R_ARM_RELATIVE]) \
+     && ! AC_TRY_COMMAND([LC_ALL=C $READELF -Wl conftest | grep -q INTERP])
+  then
+    libc_cv_static_pie_on_arm=yes
+  fi
+  rm -rf conftest* ])
+if test "$libc_cv_static_pie_on_arm" = yes; then
+  AC_DEFINE(SUPPORT_STATIC_PIE)
+fi
+
 # We check to see if the compiler and flags are
 # selecting the hard-float ABI and if they are then
 # we set libc_cv_arm_pcs_vfp to yes which causes
diff --git a/sysdeps/arm/start.S b/sysdeps/arm/start.S
index a7e62b3934..68e032ef4d 100644
--- a/sysdeps/arm/start.S
+++ b/sysdeps/arm/start.S
@@ -90,6 +90,7 @@ _start:
 	push { a1 }
 
 #ifdef PIC
+# ifdef SHARED
 	ldr sl, .L_GOT
 	adr a4, .L_GOT
 	add sl, sl, a4
@@ -103,6 +104,16 @@ _start:
 	/* __libc_start_main (main, argc, argv, init, fini, rtld_fini, stack_end) */
 	/* Let the libc call main and exit with its return code.  */
 	bl __libc_start_main(PLT)
+# else
+	ldr a1, .L_main_rel	/* Load the relative offset of main. */
+	adr a4, .L_main_rel	/* Load the actual runtime address of the label. */
+	add a1, a4, a1		/* Add them together to get the absolute address. */
+
+	mov a4, #0		/* Used to be init. */
+	push { a4 }		/* Used to be fini. */
+
+	bl __libc_start_main
+# endif
 #else
 
 	mov a4, #0		/* Used to init.  */
@@ -119,9 +130,14 @@ _start:
 
 #ifdef PIC
 	.align 2
+# ifdef SHARED
 .L_GOT:
 	.word _GLOBAL_OFFSET_TABLE_ - .L_GOT
 	.word main(GOT)
+# else
+.L_main_rel:
+	.word main - .L_main_rel
+# endif
 #endif
 
        .cantunwind
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.