bug-hurd
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[PATCH gnumach] Align the user stack correctly for 64 bit programs.


From: Flavio Cruz
Subject: [PATCH gnumach] Align the user stack correctly for 64 bit programs.
Date: Sun, 2 Apr 2023 23:56:31 -0400

* i386/i386/thread.h: Define USER_STACK_ALIGN which is 16-byte for 64 bit
  programs as recommended by the System V AMD64 guidelines. Also define
  KERNEL_STACK_ALIGN which can differ from user land.
* i386/i386/pcb.c: Use USER_STACK_ALIGN to align the bootstrap arguments and
  ultimately the stack where the program starts on.
* kern/bootstrap.c: Do not align arg_len here since it will be aligned
  in set_user_regs.
---
 i386/i386/pcb.c    | 13 +++++--------
 i386/i386/thread.h | 13 +++++++++++++
 kern/bootstrap.c   |  3 +--
 3 files changed, 19 insertions(+), 10 deletions(-)

diff --git a/i386/i386/pcb.c b/i386/i386/pcb.c
index 9210656b..61125fe8 100644
--- a/i386/i386/pcb.c
+++ b/i386/i386/pcb.c
@@ -379,12 +379,7 @@ thread_t switch_context(
 void pcb_module_init(void)
 {
        kmem_cache_init(&pcb_cache, "pcb", sizeof(struct pcb),
-#ifdef __x86_64__
-                       16,
-#else
-                       0,
-#endif
-                       NULL, 0);
+                       KERNEL_STACK_ALIGN, NULL, 0);
 
        fpu_module_init();
 }
@@ -893,11 +888,13 @@ set_user_regs(vm_offset_t stack_base, /* low address */
        vm_offset_t     arg_addr;
        struct i386_saved_state *saved_state;
 
-       arg_size = (arg_size + sizeof(int) - 1) & ~(sizeof(int)-1);
+       assert(P2ALIGNED(stack_size, USER_STACK_ALIGN));
+       assert(P2ALIGNED(stack_base, USER_STACK_ALIGN));
+       arg_size = P2ROUND(arg_size, USER_STACK_ALIGN);
        arg_addr = stack_base + stack_size - arg_size;
 
        saved_state = USER_REGS(current_thread());
-       saved_state->uesp = (long)arg_addr;
+       saved_state->uesp = (rpc_vm_offset_t)arg_addr;
        saved_state->eip = exec_info->entry;
 
        return (arg_addr);
diff --git a/i386/i386/thread.h b/i386/i386/thread.h
index cb317bee..933b43d8 100644
--- a/i386/i386/thread.h
+++ b/i386/i386/thread.h
@@ -225,6 +225,19 @@ typedef struct pcb {
 #define STACK_IEL(stack)       \
        ((struct i386_exception_link *)STACK_IKS(stack) - 1)
 
+#ifdef __x86_64__
+#define KERNEL_STACK_ALIGN 16
+#else
+#define KERNEL_STACK_ALIGN 4
+#endif
+
+#if defined(__x86_64__) && !defined(USER32)
+/* Follow System V AMD64 ABI guidelines. */
+#define USER_STACK_ALIGN 16
+#else
+#define USER_STACK_ALIGN 4
+#endif
+
 #define USER_REGS(thread)      (&(thread)->pcb->iss)
 
 
diff --git a/kern/bootstrap.c b/kern/bootstrap.c
index 8f66a4b5..49358ac6 100644
--- a/kern/bootstrap.c
+++ b/kern/bootstrap.c
@@ -610,17 +610,16 @@ build_args_and_stack(struct exec_info *boot_exec_info,
         *      trailing 0 pointer
         *      pointers to environment variables
         *      trailing 0 pointer
-        *      and align to integer boundary
         */
        arg_len += (sizeof(rpc_vm_offset_t)
                    + (arg_count + 1 + envc + 1) * sizeof(rpc_vm_offset_t));
-       arg_len = (arg_len + sizeof(integer_t) - 1) & ~(sizeof(integer_t)-1);
 
        /*
         * Allocate the stack.
         */
        stack_size = round_page(STACK_SIZE);
        stack_base = user_stack_low(stack_size);
+
        (void) vm_allocate(current_task()->map,
                        &stack_base,
                        stack_size,
-- 
2.39.2




reply via email to

[Prev in Thread] Current Thread [Next in Thread]