#30
ntdll ARM64EC: no emulator callbacks after its DLL_PROCESS_DETACH
Problem
When Rocket League (64-bit, ARM64EC session) quit from its own menu, it ended with an access violation instead of exiting:
NtTerminateProcess(0, 0), thenLdrShutdownProcesssendsDLL_PROCESS_DETACHto every module, including the emulator,xtajit64.dll.- Its CRT runs FEX's C++ static destructors in that detach: the FEX context is destroyed.
- Modules detached after it (
ucrtbase, andntdll's heap) still free memory. EachNtFreeVirtualMemorygoes through the ARM64EC hook to FEX'sNotifyMemoryFree→InvalidationTracker::InvalidateAlignedInterval, which calls through the destroyed context's vtable: a null read at+0xf0(libarm64ecfex.dll+0x12d058, called fromntdll.dll+0x5ba30,NtFreeVirtualMemory).
Change
load_arm64ec_modulerecords the emulator module.process_detachcallsarm64ec_emulator_detach()just before the emulator's detach notification.- From then on
enter_syscall_callback()returns FALSE, so every hook makes the plain syscall and nothing calls into the emulator again. Only native ARM64EC code (ucrtbase, ntdll) runs after that point, so no translation is lost.
No DLL should get callbacks after its own DLL_PROCESS_DETACH, so this is fixed in the loader, not in FEX.
Testing
iPad Pro 12.9" (6th generation), iPadOS 27.0.1: Rocket League → QUIT in the game's menu. Before: access violation at exit. After: exit_process(0), "Wine exited with code 0", and Madeira returns to its library.
Independent of #29 (UCRT); willfaust/Madeira#265 pins a branch with both.
Conflicts with madeira-lgpl now; could you rebase?