Module: wine Branch: master Commit: 455a3c1796d9a1bc9c049637c37b50fabc48488f URL: https://gitlab.winehq.org/wine/wine/-/commit/455a3c1796d9a1bc9c049637c37b50f...
Author: Alexandre Julliard julliard@winehq.org Date: Thu May 23 11:46:59 2024 +0200
winecrt0: Initialize the Unix call dispatcher on first use.
---
dlls/winecrt0/unix_lib.c | 31 +++++++++++++++++++++---------- 1 file changed, 21 insertions(+), 10 deletions(-)
diff --git a/dlls/winecrt0/unix_lib.c b/dlls/winecrt0/unix_lib.c index 5b809b6949d..fd5087cbe48 100644 --- a/dlls/winecrt0/unix_lib.c +++ b/dlls/winecrt0/unix_lib.c @@ -43,18 +43,29 @@ static NTSTATUS WINAPI unix_call_fallback( unixlib_handle_t handle, unsigned int return STATUS_DLL_NOT_FOUND; }
+static inline void *get_dispatcher( const char *name ) +{ + UNICODE_STRING ntdll_name = RTL_CONSTANT_STRING( L"ntdll.dll" ); + HMODULE module; + void **dispatcher; + + LdrGetDllHandle( NULL, 0, &ntdll_name, &module ); + dispatcher = RtlFindExportedRoutineByName( module, "__wine_unix_call_dispatcher" ); + return dispatcher ? *dispatcher : (void *)unix_call_fallback; +} + +static NTSTATUS WINAPI unix_call_init( unixlib_handle_t handle, unsigned int code, void *args ) +{ + InterlockedExchangePointer( (void **)&__wine_unix_call_dispatcher, + get_dispatcher( "__wine_unix_call_dispatcher" )); + return __wine_unix_call_dispatcher( handle, code, args ); +} + unixlib_handle_t __wine_unixlib_handle = 0; -NTSTATUS (WINAPI *__wine_unix_call_dispatcher)( unixlib_handle_t, unsigned int, void * ) = unix_call_fallback; +NTSTATUS (WINAPI *__wine_unix_call_dispatcher)( unixlib_handle_t, unsigned int, void * ) = unix_call_init;
NTSTATUS WINAPI __wine_init_unix_call(void) { - NTSTATUS status; - HMODULE module = GetModuleHandleW( L"ntdll.dll" ); - void **p__wine_unix_call_dispatcher = (void **)GetProcAddress( module, "__wine_unix_call_dispatcher" ); - - if (!p__wine_unix_call_dispatcher) return STATUS_DLL_NOT_FOUND; - status = NtQueryVirtualMemory( GetCurrentProcess(), image_base(), MemoryWineUnixFuncs, - &__wine_unixlib_handle, sizeof(__wine_unixlib_handle), NULL ); - if (!status) __wine_unix_call_dispatcher = *p__wine_unix_call_dispatcher; - return status; + return NtQueryVirtualMemory( GetCurrentProcess(), image_base(), MemoryWineUnixFuncs, + &__wine_unixlib_handle, sizeof(__wine_unixlib_handle), NULL ); }