From 80cefb63b4e007cc8a2ad96af5a7a45a6b87b7af Mon Sep 17 00:00:00 2001 From: Timo Kreuzer Date: Tue, 17 Jun 2025 21:28:09 +0300 Subject: [PATCH] [MSVCRT_SHARED] Implement TLS support for ucrtbase --- dll/win32/msvcrt/CMakeLists.txt | 1 + dll/win32/msvcrt/reactos/ucrt_tls_sup.c | 81 +++++++++++++++++++++++++ 2 files changed, 82 insertions(+) create mode 100644 dll/win32/msvcrt/reactos/ucrt_tls_sup.c diff --git a/dll/win32/msvcrt/CMakeLists.txt b/dll/win32/msvcrt/CMakeLists.txt index 4d389ee5543..7028798e734 100644 --- a/dll/win32/msvcrt/CMakeLists.txt +++ b/dll/win32/msvcrt/CMakeLists.txt @@ -115,6 +115,7 @@ add_asm_files(msvcrt_shared_asm ${SHARED_ASM_SOURCE}) add_library(msvcrt_shared ${SHARED_SOURCE} ${msvcrt_shared_asm} + reactos/ucrt_tls_sup.c ) target_compile_definitions(msvcrt_shared PRIVATE _MSVCR_VER=0 __UCRTSUPPORT__) diff --git a/dll/win32/msvcrt/reactos/ucrt_tls_sup.c b/dll/win32/msvcrt/reactos/ucrt_tls_sup.c new file mode 100644 index 00000000000..c750f1f6bb3 --- /dev/null +++ b/dll/win32/msvcrt/reactos/ucrt_tls_sup.c @@ -0,0 +1,81 @@ +/* + * PROJECT: ReactOS msvcrt + * LICENSE: MIT (https://spdx.org/licenses/MIT) + * PURPOSE: TLS support code for use with ucrtbase + * COPYRIGHT: Copyright 2025 Timo Kreuzer + */ + +#include +#include +#include "msvcrt.h" +#include "wine/debug.h" + +WINE_DEFAULT_DEBUG_CHANNEL(msvcrt); + +DWORD msvcrt_tls_index; + +BOOL msvcrt_init_tls(void) +{ + msvcrt_tls_index = TlsAlloc(); + if (msvcrt_tls_index == TLS_OUT_OF_INDEXES) + { + ERR("TlsAlloc() failed!\n"); + return FALSE; + } + + return TRUE; +} + +BOOL msvcrt_free_tls(void) +{ + if (!TlsFree(msvcrt_tls_index)) + { + ERR("TlsFree() failed!\n"); + return FALSE; + } + + return TRUE; +} + +void msvcrt_free_tls_mem(void) +{ + thread_data_t *tls = TlsGetValue(msvcrt_tls_index); + if (tls) + { + free(tls->efcvt_buffer); + assert(tls->asctime_buffer == NULL); + assert(tls->wasctime_buffer == NULL); + assert(tls->strerror_buffer == NULL); + assert(tls->wcserror_buffer == NULL); + assert(tls->time_buffer == NULL); + assert(tls->tmpnam_buffer == NULL); + assert(tls->wtmpnam_buffer == NULL); + assert(tls->locinfo == NULL); + assert(tls->mbcinfo == NULL); + HeapFree(GetProcessHeap(), 0, tls); + } +} + +thread_data_t *CDECL msvcrt_get_thread_data(void) +{ + thread_data_t *ptr; + DWORD err = GetLastError(); /* need to preserve last error */ + + ptr = TlsGetValue(msvcrt_tls_index); + if (ptr == NULL) + { + ptr = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*ptr)); + if (ptr == NULL) + exit(_RT_THREAD); + + if (!TlsSetValue(msvcrt_tls_index, ptr)) + exit(_RT_THREAD); + + ptr->tid = GetCurrentThreadId(); + ptr->handle = INVALID_HANDLE_VALUE; + ptr->random_seed = 1; + } + + SetLastError(err); + return ptr; +}