]> git.ipfire.org Git - thirdparty/glibc.git/commitdiff
aarch64: Add glibc.cpu.aarch64_gcs tunable
authorSzabolcs Nagy <szabolcs.nagy@arm.com>
Mon, 17 Jul 2023 07:31:05 +0000 (08:31 +0100)
committerYury Khrustalev <yury.khrustalev@arm.com>
Mon, 20 Jan 2025 09:31:33 +0000 (09:31 +0000)
This tunable controls Guarded Control Stack (GCS) for the process.

0 = disabled: do not enable GCS
1 = enforced: check markings and fail if any binary is not marked
2 = optional: check markings but keep GCS off if a binary is unmarked
3 = override: enable GCS, markings are ignored

By default it is 0, so GCS is disabled, value 1 will enable GCS.

The status is stored into GL(dl_aarch64_gcs) early and only applied
later, since enabling GCS is tricky: it must happen on a top level
stack frame. Using GL instead of GLRO because it may need updates
depending on loaded libraries that happen after readonly protection
is applied, however library marking based GCS setting is not yet
implemented.

Describe new tunable in the manual.

Co-authored-by: Yury Khrustalev <yury.khrustalev@arm.com>
Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org>
manual/tunables.texi
sysdeps/aarch64/dl-tunables.list
sysdeps/unix/sysv/linux/aarch64/cpu-features.c
sysdeps/unix/sysv/linux/aarch64/dl-procruntime.c [new file with mode: 0644]

index 1ac58b9ae9e0ba93b80b890d8495ad58d322f1da..7f0246c7895962aac6b67160ba8c21ee93c8b9fb 100644 (file)
@@ -669,6 +669,49 @@ This tunable is specific to x86-64 and effective only when the lazy
 binding is disabled.
 @end deftp
 
+@deftp Tunable glibc.cpu.aarch64_gcs
+This tunable controls Guarded Control Stack (GCS) for the process.
+
+Accepted values are:
+
+0 = disabled: do not enable GCS.
+
+1 = enforced: check markings and fail if any binary is not marked.
+
+2 = optional: check markings but keep GCS off if any binary is unmarked.
+
+3 = override: enable GCS, markings are ignored.
+
+If unmarked binary is loaded via @code{dlopen} when GCS is enabled and
+markings are not ignored (@code{aarch64_gcs == 1} or @code{2}), then
+the process will be aborted.
+
+Default is @code{0}, so GCS is disabled by default.
+
+This tunable is specific to AArch64. On systems that do not support
+Guarded Control Stack this tunable has no effect.
+
+Before enabling GCS for the process the value of this tunable is checked
+and depending on it the following outcomes are possible.
+
+@code{aarch64_gcs == 0}: GCS will not be enabled and GCS markings will not be
+checked for any binaries.
+
+@code{aarch64_gcs == 1}: GCS markings will be checked for all binaries loaded
+at startup and, only if all binaries are GCS-marked, GCS will be enabled. If
+any of the binaries are not GCS-marked, the process will abort. Subsequent call
+to @code{dlopen} for an unmarked binary will also result in abort.
+
+@code{aarch64_gcs == 2}: GCS markings will be checked for all binaries loaded
+at startup and, if any of such binaries are not GCS-marked, GCS will not be
+enabled and there will be no more checks for GCS marking. If all binaries
+loaded at startup are GCS-marked, then GCS will be enabled, in which case a
+call to @code{dlopen} for an unmarked binary will also result in abort.
+
+@code{aarch64_gcs == 3}: GCS will be enabled and GCS markings will not be
+checked for any binaries.
+@end deftp
+
 @node Memory Related Tunables
 @section Memory Related Tunables
 @cindex memory related tunables
index 5c1a172559d83f0a9e461d22ab7061d0f9200dc2..d461c1e9db9834a39a497ca8c7da2624985f5022 100644 (file)
@@ -21,5 +21,11 @@ glibc {
     name {
       type: STRING
     }
+    aarch64_gcs {
+      type: UINT_64
+      minval: 0
+      maxval: 3
+      default: 0
+    }
   }
 }
index 7ac228303f2fbd9c085a64378622fc275ec9a977..1ecf6cd1766f00d35fbdf82a17f4a278b47239c5 100644 (file)
@@ -176,4 +176,12 @@ init_cpu_features (struct cpu_features *cpu_features)
 
   /* Check if MOPS is supported.  */
   cpu_features->mops = GLRO (dl_hwcap2) & HWCAP2_MOPS;
+
+#ifndef HWCAP_GCS
+#define HWCAP_GCS (1UL << 32)
+#endif
+
+  if (GLRO (dl_hwcap) & HWCAP_GCS)
+    /* GCS status may be updated later by binary compatibility checks.  */
+    GL (dl_aarch64_gcs) = TUNABLE_GET (glibc, cpu, aarch64_gcs, uint64_t, 0);
 }
diff --git a/sysdeps/unix/sysv/linux/aarch64/dl-procruntime.c b/sysdeps/unix/sysv/linux/aarch64/dl-procruntime.c
new file mode 100644 (file)
index 0000000..044544a
--- /dev/null
@@ -0,0 +1,37 @@
+/* Data for processor runtime information.  AArch64 version.
+   Copyright (C) 2024-2025 Free Software Foundation, Inc.
+   This file is part of the GNU C Library.
+
+   The GNU C Library is free software; you can redistribute it and/or
+   modify it under the terms of the GNU Lesser General Public
+   License as published by the Free Software Foundation; either
+   version 2.1 of the License, or (at your option) any later version.
+
+   The GNU C Library is distributed in the hope that it will be useful,
+   but WITHOUT ANY WARRANTY; without even the implied warranty of
+   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+   Lesser General Public License for more details.
+
+   You should have received a copy of the GNU Lesser General Public
+   License along with the GNU C Library; if not, see
+   <https://www.gnu.org/licenses/>.  */
+
+#ifndef PROCINFO_CLASS
+# define PROCINFO_CLASS
+#endif
+
+#if !IS_IN (ldconfig)
+# if !defined PROCINFO_DECL && defined SHARED
+  ._dl_aarch64_gcs
+# else
+PROCINFO_CLASS unsigned long _dl_aarch64_gcs
+# endif
+# ifndef PROCINFO_DECL
+= 0
+# endif
+# if !defined SHARED || defined PROCINFO_DECL
+;
+# else
+,
+# endif
+#endif