- Force a reference to _tls_used to make the linker create the TLS
directory if it's not already there. (e.g. if __declspec(thread) is
not used).
- Force a reference to __xl_f to prevent whole program optimization
from discarding the variable.
- On x86, symbols are prefixed with an underscore.
- Using const_seg [1] is required for x64 and works everywhere else.
- Mark the TLS callback as const since we use const_seg.
- Use WINPTHREADS_ATTRIBUTE(WINPTHREADS_SECTION(".CRT$XLF") only with
GNUC, it's not needed with MSVC as we don't use #pragma section.
[1]: https://learn.microsoft.com/en-us/cpp/preprocessor/const-seg?view=msvc-170
Signed-off-by: Antonin Décimo
---
mingw-w64-libraries/winpthreads/src/thread.c | 41 +---
1 file changed, 36 insertions(+), 5 deletions(-)
diff --git a/mingw-w64-libraries/winpthreads/src/thread.c
b/mingw-w64-libraries/winpthreads/src/thread.c
index 19855ffb1..bb7ee1f8d 100644
--- a/mingw-w64-libraries/winpthreads/src/thread.c
+++ b/mingw-w64-libraries/winpthreads/src/thread.c
@@ -507,13 +507,44 @@ __dyn_tls_pthread (HANDLE hDllHandle, DWORD dwReason,
LPVOID lpreserved)
}
/* TLS-runtime section variable. */
-#ifdef _MSC_VER
-#pragma section(".CRT$XLF", shared)
+
+#if defined(_MSC_VER)
+/* Force a reference to _tls_used to make the linker create the TLS
+ * directory if it's not already there. (e.g. if __declspec(thread)
+ * is not used).
+ * Force a reference to __xl_f to prevent whole program optimization
+ * from discarding the variable. */
+
+/* On x86, symbols are prefixed with an underscore. */
+# if defined(_M_IX86)
+# pragma comment(linker, "/INCLUDE:__tls_used")
+# pragma comment(linker, "/INCLUDE:___xl_f")
+# elif defined(_M_ARM) || defined(_M_ARM64) || defined(_M_X64)
+# pragma comment(linker, "/INCLUDE:_tls_used")
+# pragma comment(linker, "/INCLUDE:__xl_f")
+# endif
+
+/* .CRT$XLA to .CRT$XLZ is an array of PIMAGE_TLS_CALLBACK
+ * pointers. Pick an arbitrary location for our callback.
+ *
+ * See VC\...\crt\src\vcruntime\tlssup.cpp for reference. */
+
+/* .CRT section is merged with .rdata on x64 so it must be constant
+ * data. Also works on all other architectures.*/
+# pragma const_seg(push, old_seg)
+# pragma const_seg(".CRT$XLF")
#endif
-PIMAGE_TLS_CALLBACK WINPTHREADS_ATTRIBUTE((WINPTHREADS_SECTION(".CRT$XLF")))
__xl_f = __dyn_tls_pthread;
-#ifdef _MSC_VER
-#pragma data_seg()
+
+const PIMAGE_TLS_CALLBACK
+#if defined(__GNUC__)
+ WINPTHREADS_ATTRIBUTE((WINPTHREADS_SECTION(".CRT$XLF")))
#endif
+ __xl_f = __dyn_tls_pthread;
+
+#if defined(_MSC_VER)
+# pragma const_seg(pop, old_seg)
+#endif
+
#ifdef WINPTHREAD_DBG
static int print_state = 0;
--
2.43.0
___
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public