File 9306.patch of Package ruby3.2

From 36a574f661d4e3ad3d96d2eebfe48ca710660221 Mon Sep 17 00:00:00 2001
From: Yuta Saito <kateinoigakukun@gmail.com>
Date: Thu, 21 Dec 2023 14:42:39 +0900
Subject: [PATCH 1/4] coroutine/arm64: Sign return address if PAC enabled

---
 coroutine/arm64/Context.S | 24 ++++++++++++++++++++----
 coroutine/arm64/Context.h | 22 ++++++++++++++++++++--
 2 files changed, 40 insertions(+), 6 deletions(-)

diff --git a/coroutine/arm64/Context.S b/coroutine/arm64/Context.S
index 07d50d30df39e..2cf3e489877cb 100644
--- a/coroutine/arm64/Context.S
+++ b/coroutine/arm64/Context.S
@@ -18,9 +18,19 @@
 .align 2
 #endif
 
+## NOTE(PAC): Use we HINT mnemonics instead of PAC mnemonics to
+## keep compatibility with those assemblers that don't support PAC.
+##
+## See "Providing protection for complex software" for more details about PAC/BTI
+## https://developer.arm.com/architectures/learn-the-architecture/providing-protection-for-complex-software
+
 .global PREFIXED_SYMBOL(SYMBOL_PREFIX,coroutine_transfer)
 PREFIXED_SYMBOL(SYMBOL_PREFIX,coroutine_transfer):
 
+#if defined(__ARM_FEATURE_PAC_DEFAULT) && (__ARM_FEATURE_PAC_DEFAULT != 0)
+	# paciasp
+	hint #25
+#endif
 	# Make space on the stack for caller registers
 	sub sp, sp, 0xb0
 
@@ -59,14 +69,20 @@ PREFIXED_SYMBOL(SYMBOL_PREFIX,coroutine_transfer):
 	ldp x27, x28, [sp, 0x80]
 	ldp x29, x30, [sp, 0x90]
 
-	# Load return address into x4
-	ldr x4, [sp, 0xa0]
+	# Load return address into x17
+	ldr x17, [sp, 0xa0]
 
 	# Pop stack frame
 	add sp, sp, 0xb0
 
-	# Jump to return address (in x4)
-	ret x4
+#if defined(__ARM_FEATURE_PAC_DEFAULT) && (__ARM_FEATURE_PAC_DEFAULT != 0)
+	mov x16, sp
+	# autia1716
+	hint #12
+#endif
+
+	# Jump to return address (in x17)
+	ret x17
 
 #if defined(__linux__) && defined(__ELF__)
 .section .note.GNU-stack,"",%progbits
diff --git a/coroutine/arm64/Context.h b/coroutine/arm64/Context.h
index 1472621f48017..168ec18c4aa2d 100644
--- a/coroutine/arm64/Context.h
+++ b/coroutine/arm64/Context.h
@@ -50,6 +50,23 @@ static inline void coroutine_initialize_main(struct coroutine_context * context)
     context->stack_pointer = NULL;
 }
 
+#if defined(__ARM_FEATURE_PAC_DEFAULT) && __ARM_FEATURE_PAC_DEFAULT != 0
+// Sign the given instruction address with the given modifier and key A
+static inline void *ptrauth_sign_instruction_addr(void *addr, void *modifier) {
+    register void *r17 __asm("r17") = addr;
+    register void *r16 __asm("r16") = modifier;
+    // Use HINT mnemonic instead of PACIA1716 for compatibility with older assemblers.
+    asm ("hint #8;" : "+r"(r17) : "r"(r16));
+    addr = r17;
+    return addr;
+}
+#else
+// No-op if PAC is not enabled
+static inline void *ptrauth_sign_instruction_addr(void *addr, void *modifier) {
+    return addr;
+}
+#endif
+
 static inline void coroutine_initialize(
     struct coroutine_context *context,
     coroutine_start start,
@@ -66,12 +83,13 @@ static inline void coroutine_initialize(
 
     // Stack grows down. Force 16-byte alignment.
     char * top = (char*)stack + size;
-    context->stack_pointer = (void**)((uintptr_t)top & ~0xF);
+    top = (char *)((uintptr_t)top & ~0xF);
+    context->stack_pointer = (void**)top;
 
     context->stack_pointer -= COROUTINE_REGISTERS;
     memset(context->stack_pointer, 0, sizeof(void*) * COROUTINE_REGISTERS);
 
-    context->stack_pointer[0xa0 / 8] = (void*)start;
+    context->stack_pointer[0xa0 / 8] = ptrauth_sign_instruction_addr((void*)start, (void*)top);
 }
 
 struct coroutine_context * coroutine_transfer(struct coroutine_context * current, struct coroutine_context * target);

From 831e94893410749f187cb8a2316d21e546ad5715 Mon Sep 17 00:00:00 2001
From: Yuta Saito <kateinoigakukun@gmail.com>
Date: Thu, 21 Dec 2023 15:19:25 +0900
Subject: [PATCH 2/4] coroutine/arm64/Context.S: Insert `bti c` as BTI landing
 pad

---
 coroutine/arm64/Context.S | 6 +++++-
 1 file changed, 5 insertions(+), 1 deletion(-)

diff --git a/coroutine/arm64/Context.S b/coroutine/arm64/Context.S
index 2cf3e489877cb..0eb08e326d0b6 100644
--- a/coroutine/arm64/Context.S
+++ b/coroutine/arm64/Context.S
@@ -28,8 +28,12 @@
 PREFIXED_SYMBOL(SYMBOL_PREFIX,coroutine_transfer):
 
 #if defined(__ARM_FEATURE_PAC_DEFAULT) && (__ARM_FEATURE_PAC_DEFAULT != 0)
-	# paciasp
+	# paciasp (it also acts as BTI landing pad, so no need to insert BTI also)
 	hint #25
+#elif defined(__ARM_FEATURE_BTI_DEFAULT) && (__ARM_FEATURE_BTI_DEFAULT != 0)
+	# For the the case PAC is not enabled but BTI is.
+	# bti c
+	hint #34
 #endif
 	# Make space on the stack for caller registers
 	sub sp, sp, 0xb0

From 0298eaf76f0125523119c2ddaf0f752307dcf723 Mon Sep 17 00:00:00 2001
From: Yuta Saito <kateinoigakukun@gmail.com>
Date: Thu, 21 Dec 2023 15:21:37 +0900
Subject: [PATCH 3/4] coroutine/arm64/Context.S: Append PAC/BTI note section if
 needed

Fixes https://bugs.ruby-lang.org/issues/20029
---
 coroutine/arm64/Context.S | 34 ++++++++++++++++++++++++++++++++++
 1 file changed, 34 insertions(+)

diff --git a/coroutine/arm64/Context.S b/coroutine/arm64/Context.S
index 0eb08e326d0b6..cdcc6ca6dd4bf 100644
--- a/coroutine/arm64/Context.S
+++ b/coroutine/arm64/Context.S
@@ -91,3 +91,37 @@ PREFIXED_SYMBOL(SYMBOL_PREFIX,coroutine_transfer):
 #if defined(__linux__) && defined(__ELF__)
 .section .note.GNU-stack,"",%progbits
 #endif
+
+#if __ARM_FEATURE_BTI_DEFAULT != 0 || __ARM_FEATURE_PAC_DEFAULT != 0
+/*  See "ELF for the Arm 64-bit Architecture (AArch64)"
+    https://github.com/ARM-software/abi-aa/blob/2023Q3/aaelf64/aaelf64.rst#program-property */
+#  define GNU_PROPERTY_AARCH64_FEATURE_1_BTI (1<<0)
+#  define GNU_PROPERTY_AARCH64_FEATURE_1_PAC (1<<1)
+
+#  if __ARM_FEATURE_BTI_DEFAULT != 0
+#    define BTI_FLAG GNU_PROPERTY_AARCH64_FEATURE_1_BTI
+#  else
+#    define BTI_FLAG 0
+#  endif
+#  if __ARM_FEATURE_PAC_DEFAULT != 0
+#    define PAC_FLAG GNU_PROPERTY_AARCH64_FEATURE_1_PAC
+#  else
+#    define PAC_FLAG 0
+#  endif
+
+  # The note section format is described by Note Section in Chapter 5
+  # of "System V Application Binary Interface, Edition 4.1".
+  .pushsection .note.gnu.property, "a"
+  .p2align 3
+  .long 0x4        /* Name size ("GNU\0") */
+  .long 0x10       /* Descriptor size */
+  .long 0x5        /* Type: NT_GNU_PROPERTY_TYPE_0 */
+  .asciz "GNU"     /* Name */
+  # Begin descriptor
+  .long 0xc0000000 /* Property type: GNU_PROPERTY_AARCH64_FEATURE_1_AND */
+  .long 0x4        /* Property size */
+  .long (BTI_FLAG|PAC_FLAG)
+  .long 0x0        /* 8-byte alignment padding */
+  # End descriptor
+  .popsection
+#endif

From e13bfc020b15d5b1097d1036f5c900eb1479d45c Mon Sep 17 00:00:00 2001
From: Yuta Saito <kateinoigakukun@gmail.com>
Date: Fri, 22 Dec 2023 08:52:20 +0900
Subject: [PATCH 4/4] coroutine/arm64: Skip saving/restoring x30 twice and use
 `autiasp`

We don't need to save/restore x30 twice, and we can just use `ret`,
which uses x30 as return address register instead of explicit `ret <reg>`
instruction. This also allows us to use `autiasp` instead of `autia1716`
and we can skip setting SP/LR to x16/x17.

Also the size of register save area is shrunk by 16 bytes due to the
removal of extra x30 save/restore.
---
 coroutine/arm64/Context.S | 19 ++++++-------------
 coroutine/arm64/Context.h |  4 ++--
 2 files changed, 8 insertions(+), 15 deletions(-)

diff --git a/coroutine/arm64/Context.S b/coroutine/arm64/Context.S
index cdcc6ca6dd4bf..eeb0f774a37c3 100644
--- a/coroutine/arm64/Context.S
+++ b/coroutine/arm64/Context.S
@@ -36,7 +36,7 @@ PREFIXED_SYMBOL(SYMBOL_PREFIX,coroutine_transfer):
 	hint #34
 #endif
 	# Make space on the stack for caller registers
-	sub sp, sp, 0xb0
+	sub sp, sp, 0xa0
 
 	# Save caller registers
 	stp d8, d9, [sp, 0x00]
@@ -50,9 +50,6 @@ PREFIXED_SYMBOL(SYMBOL_PREFIX,coroutine_transfer):
 	stp x27, x28, [sp, 0x80]
 	stp x29, x30, [sp, 0x90]
 
-	# Save return address
-	str x30, [sp, 0xa0]
-
 	# Save stack pointer to x0 (first argument)
 	mov x2, sp
 	str x2, [x0, 0]
@@ -73,20 +70,16 @@ PREFIXED_SYMBOL(SYMBOL_PREFIX,coroutine_transfer):
 	ldp x27, x28, [sp, 0x80]
 	ldp x29, x30, [sp, 0x90]
 
-	# Load return address into x17
-	ldr x17, [sp, 0xa0]
-
 	# Pop stack frame
-	add sp, sp, 0xb0
+	add sp, sp, 0xa0
 
 #if defined(__ARM_FEATURE_PAC_DEFAULT) && (__ARM_FEATURE_PAC_DEFAULT != 0)
-	mov x16, sp
-	# autia1716
-	hint #12
+	# autiasp: Authenticate x30 (LR) with SP and key A
+	hint #29
 #endif
 
-	# Jump to return address (in x17)
-	ret x17
+	# Jump to return address (in x30)
+	ret
 
 #if defined(__linux__) && defined(__ELF__)
 .section .note.GNU-stack,"",%progbits
diff --git a/coroutine/arm64/Context.h b/coroutine/arm64/Context.h
index 168ec18c4aa2d..1819fa5be9328 100644
--- a/coroutine/arm64/Context.h
+++ b/coroutine/arm64/Context.h
@@ -17,7 +17,7 @@
 
 #define COROUTINE __attribute__((noreturn)) void
 
-enum {COROUTINE_REGISTERS = 0xb0 / 8};
+enum {COROUTINE_REGISTERS = 0xa0 / 8};
 
 #if defined(__SANITIZE_ADDRESS__)
     #define COROUTINE_SANITIZE_ADDRESS
@@ -89,7 +89,7 @@ static inline void coroutine_initialize(
     context->stack_pointer -= COROUTINE_REGISTERS;
     memset(context->stack_pointer, 0, sizeof(void*) * COROUTINE_REGISTERS);
 
-    context->stack_pointer[0xa0 / 8] = ptrauth_sign_instruction_addr((void*)start, (void*)top);
+    context->stack_pointer[0x98 / 8] = ptrauth_sign_instruction_addr((void*)start, (void*)top);
 }
 
 struct coroutine_context * coroutine_transfer(struct coroutine_context * current, struct coroutine_context * target);
openSUSE Build Service is sponsored by