[PATCH 4/4] ntdll: Implement arm64 sigcontext access for macOS
Martin Storsjo
martin at martin.st
Fri Aug 14 06:54:17 CDT 2020
Signed-off-by: Martin Storsjo <martin at martin.st>
---
dlls/ntdll/unix/signal_arm64.c | 46 ++++++++++++++++++++++++++++++++++
1 file changed, 46 insertions(+)
diff --git a/dlls/ntdll/unix/signal_arm64.c b/dlls/ntdll/unix/signal_arm64.c
index cc34690f96..f1c6cdc5fa 100644
--- a/dlls/ntdll/unix/signal_arm64.c
+++ b/dlls/ntdll/unix/signal_arm64.c
@@ -110,6 +110,20 @@ static DWORD64 get_fault_esr( ucontext_t *sigcontext )
return 0;
}
+#elif defined(__APPLE__)
+
+/* Special Registers access */
+# define SP_sig(context) ((context)->uc_mcontext->__ss.__sp) /* Stack pointer */
+# define PC_sig(context) ((context)->uc_mcontext->__ss.__pc) /* Program counter */
+# define PSTATE_sig(context) ((context)->uc_mcontext->__ss.__cpsr) /* Current State Register */
+# define FP_sig(context) ((context)->uc_mcontext->__ss.__fp) /* Frame pointer */
+# define LR_sig(context) ((context)->uc_mcontext->__ss.__lr) /* Link Register */
+
+static DWORD64 get_fault_esr( ucontext_t *sigcontext )
+{
+ return sigcontext->uc_mcontext->__es.__esr;
+}
+
#endif /* linux */
static pthread_key_t teb_key;
@@ -299,7 +313,11 @@ static void save_context( CONTEXT *context, const ucontext_t *sigcontext )
context->Sp = SP_sig(sigcontext); /* Stack pointer */
context->Pc = PC_sig(sigcontext); /* Program Counter */
context->Cpsr = PSTATE_sig(sigcontext); /* Current State Register */
+#ifdef linux
for (i = 0; i <= 28; i++) context->u.X[i] = REGn_sig( i, sigcontext );
+#elif defined(__APPLE__)
+ for (i = 0; i <= 28; i++) context->u.X[i] = sigcontext->uc_mcontext->__ss.__x[i];
+#endif
}
@@ -317,7 +335,11 @@ static void restore_context( const CONTEXT *context, ucontext_t *sigcontext )
SP_sig(sigcontext) = context->Sp; /* Stack pointer */
PC_sig(sigcontext) = context->Pc; /* Program Counter */
PSTATE_sig(sigcontext) = context->Cpsr; /* Current State Register */
+#ifdef linux
for (i = 0; i <= 28; i++) REGn_sig( i, sigcontext ) = context->u.X[i];
+#elif defined(__APPLE__)
+ for (i = 0; i <= 28; i++) sigcontext->uc_mcontext->__ss.__x[i] = context->u.X[i];
+#endif
}
@@ -328,6 +350,7 @@ static void restore_context( const CONTEXT *context, ucontext_t *sigcontext )
*/
static void save_fpu( CONTEXT *context, ucontext_t *sigcontext )
{
+#ifdef linux
struct fpsimd_context *fp = get_fpsimd_context( sigcontext );
if (!fp) return;
@@ -335,6 +358,12 @@ static void save_fpu( CONTEXT *context, ucontext_t *sigcontext )
context->Fpcr = fp->fpcr;
context->Fpsr = fp->fpsr;
memcpy( context->V, fp->vregs, sizeof(context->V) );
+#elif defined(__APPLE__)
+ context->ContextFlags |= CONTEXT_FLOATING_POINT;
+ context->Fpcr = sigcontext->uc_mcontext->__ns.__fpcr;
+ context->Fpsr = sigcontext->uc_mcontext->__ns.__fpsr;
+ memcpy( context->V, sigcontext->uc_mcontext->__ns.__v, sizeof(context->V) );
+#endif
}
@@ -345,12 +374,18 @@ static void save_fpu( CONTEXT *context, ucontext_t *sigcontext )
*/
static void restore_fpu( CONTEXT *context, ucontext_t *sigcontext )
{
+#ifdef linux
struct fpsimd_context *fp = get_fpsimd_context( sigcontext );
if (!fp) return;
fp->fpcr = context->Fpcr;
fp->fpsr = context->Fpsr;
memcpy( fp->vregs, context->V, sizeof(fp->vregs) );
+#elif defined(__APPLE__)
+ sigcontext->uc_mcontext->__ns.__fpcr = context->Fpcr;
+ sigcontext->uc_mcontext->__ns.__fpsr = context->Fpsr;
+ memcpy( sigcontext->uc_mcontext->__ns.__v, context->V, sizeof(context->V) );
+#endif
}
@@ -594,6 +629,7 @@ static void setup_exception( ucontext_t *sigcontext, EXCEPTION_RECORD *rec )
stack->rec = *rec;
stack->context = context;
+#ifdef linux
REGn_sig(3, sigcontext) = SP_sig(sigcontext); /* original stack pointer, fourth arg for raise_func_trampoline */
SP_sig(sigcontext) = (ULONG_PTR)stack;
LR_sig(sigcontext) = PC_sig(sigcontext);
@@ -602,6 +638,16 @@ static void setup_exception( ucontext_t *sigcontext, EXCEPTION_RECORD *rec )
REGn_sig(1, sigcontext) = (ULONG_PTR)&stack->context; /* second arg for KiUserExceptionDispatcher */
REGn_sig(2, sigcontext) = (ULONG_PTR)pKiUserExceptionDispatcher; /* dispatcher arg for raise_func_trampoline */
REGn_sig(18, sigcontext) = (ULONG_PTR)NtCurrentTeb();
+#elif defined(__APPLE__)
+ sigcontext->uc_mcontext->__ss.__x[3] = sigcontext->uc_mcontext->__ss.__sp; /* original stack pointer, fourth arg for raise_func_trampoline */
+ sigcontext->uc_mcontext->__ss.__sp = (ULONG_PTR)stack;
+ sigcontext->uc_mcontext->__ss.__lr = sigcontext->uc_mcontext->__ss.__pc;
+ sigcontext->uc_mcontext->__ss.__pc = (ULONG_PTR)raise_func_trampoline;
+ sigcontext->uc_mcontext->__ss.__x[0] = (ULONG_PTR)&stack->rec; /* first arg for KiUserExceptionDispatcher */
+ sigcontext->uc_mcontext->__ss.__x[1] = (ULONG_PTR)&stack->context; /* second arg for KiUserExceptionDispatcher */
+ sigcontext->uc_mcontext->__ss.__x[2] = (ULONG_PTR)pKiUserExceptionDispatcher; /* dispatcher arg for raise_func_trampoline */
+ sigcontext->uc_mcontext->__ss.__x[18] = (ULONG_PTR)NtCurrentTeb();
+#endif
}
--
2.17.1
More information about the wine-devel
mailing list