These trap on linux but under Windows userspace will write 0 to the destination register. Fixes recent versions of VC redist that use this unconditionally.
From: Billy Laws blaws05@gmail.com
These trap on linux but under Windows userspace will write 0 to the destination register. Fixes recent versions of VC redist that use this unconditionally. --- dlls/ntdll/tests/exception.c | 19 +++++++++++++++++++ dlls/ntdll/unix/signal_arm64.c | 13 +++++++++++++ 2 files changed, 32 insertions(+)
diff --git a/dlls/ntdll/tests/exception.c b/dlls/ntdll/tests/exception.c index 4a89cf6a5dc..73ab39474c4 100644 --- a/dlls/ntdll/tests/exception.c +++ b/dlls/ntdll/tests/exception.c @@ -8296,6 +8296,24 @@ static void test_restore_context(void) ok(0, "unexpected pass %ld\n", pass); }
+static void test_mrs_currentel(void) +{ + DWORD64 (*func_ptr)(void) = code_mem; + DWORD64 result; + + static const DWORD call_func[] = + { + 0xd5384240, /* mrs x0, CurrentEL */ + 0xd65f03c0, /* ret */ + }; + + memcpy( func_ptr, call_func, sizeof(call_func) ); + FlushInstructionCache( GetCurrentProcess(), func_ptr, sizeof(call_func) ); + result = func_ptr(); + ok( result == 0, "expected 0, got %llx\n", result ); +} + + #endif /* __aarch64__ */
#if defined(__i386__) || defined(__x86_64__) @@ -12024,6 +12042,7 @@ START_TEST(exception) test_nested_exception(); test_collided_unwind(); test_restore_context(); + test_mrs_currentel();
#elif defined(__arm__)
diff --git a/dlls/ntdll/unix/signal_arm64.c b/dlls/ntdll/unix/signal_arm64.c index 8ec4251feca..71719b78694 100644 --- a/dlls/ntdll/unix/signal_arm64.c +++ b/dlls/ntdll/unix/signal_arm64.c @@ -1097,6 +1097,19 @@ static void segv_handler( int signal, siginfo_t *siginfo, void *sigcontext ) static void ill_handler( int signal, siginfo_t *siginfo, void *sigcontext ) { EXCEPTION_RECORD rec = { EXCEPTION_ILLEGAL_INSTRUCTION }; + ucontext_t *context = sigcontext; + + if (!(PSTATE_sig( context ) & 0x10) && /* AArch64 (not WoW) */ + !(PC_sig( context ) & 3)) + { + ULONG instr = *(ULONG *)PC_sig( context ); + /* emulate mrs xN, CurrentEL */ + if ((instr & ~0x1f) == 0xd5384240) { + REGn_sig(instr & 0x1f, context) = 0; + PC_sig(context) += 4; + return; + } + }
setup_exception( sigcontext, &rec ); }
Hi,
It looks like your patch introduced the new failures shown below. Please investigate and fix them before resubmitting your patch. If they are not new, fixing them anyway would help a lot. Otherwise please ask for the known failures list to be updated.
The tests also ran into some preexisting test failures. If you know how to fix them that would be helpful. See the TestBot job for the details:
The full results can be found at: https://testbot.winehq.org/JobDetails.pl?Key=150363
Your paranoid android.
=== debian11b (64 bit WoW report) ===
user32: input.c:4305: Test succeeded inside todo block: button_down_hwnd_todo 1: got MSG_TEST_WIN hwnd 00000000010400DE, msg WM_LBUTTONDOWN, wparam 0x1, lparam 0x320032
Jinoh Kang (@iamahuman) commented about dlls/ntdll/unix/signal_arm64.c:
static void ill_handler( int signal, siginfo_t *siginfo, void *sigcontext ) { EXCEPTION_RECORD rec = { EXCEPTION_ILLEGAL_INSTRUCTION };
- ucontext_t *context = sigcontext;
- if (!(PSTATE_sig( context ) & 0x10) && /* AArch64 (not WoW) */
!(PC_sig( context ) & 3))
- {
ULONG instr = *(ULONG *)PC_sig( context );
/* emulate mrs xN, CurrentEL */
if ((instr & ~0x1f) == 0xd5384240) {
REGn_sig(instr & 0x1f, context) = 0;
For MRS, register 31 is XZR, not SP:
```suggestion:-0+0 ULONG reg = instr & 0x1f; if (reg != 31) /* 31: XZR */ REGn_sig(reg, context) = 0; ```
`mrs xzr, CurrentEL` could be emitted by volatile inline asm `mrs %0, CurrentEL` where the compiler optimized out the destination. It could also be part of incorrect JIT code, and such deviation could be difficult to debug.