On Dec 5, 2023, Alexandre Oliva <ol...@adacore.com> wrote: > Maybe we should narrow it down to targets in which weak undefined > symbols are available with the expected semantics, and where the symbol > is known to have ever been defined in libc. On it...
This patch reintroduces the weak symbol reference only on GNU systems, where they're most likely to be useful. If other systems could benefit, we can always add them later. > Or maybe a weak definition (or weak alias to a definition) in that file > would enable us to test whether the weak definition was preempted Uhh... 'cept libc wouldn't preempt from libstdc++; the opposite would occur, but that doesn't help. Regstrapped on x86_64-linux-gnu, also tested with ac_cv_func___cxa_thread_atexit_impl=no. Ok to (re)install? libsupc++: try cxa_thread_atexit_impl at runtime g++.dg/tls/thread_local-order2.C fails when the toolchain is built for a platform that lacks __cxa_thread_atexit_impl, even if the program is built and run using that toolchain on a (later) platform that offers __cxa_thread_atexit_impl. This patch adds runtime testing for __cxa_thread_atexit_impl on select platforms (GNU variants, for starters) that support weak symbols. for libstdc++-v3/ChangeLog * config/os/gnu-linux/os_defines.h (_GLIBCXX_MAY_HAVE___CXA_THREAD_ATEXIT_IMPL): Define. * libsupc++/atexit_thread.cc [__GXX_WEAK__ && _GLIBCXX_MAY_HAVE___CXA_THREAD_ATEXIT_IMPL] (__cxa_thread_atexit): Add dynamic detection of __cxa_thread_atexit_impl. --- libstdc++-v3/config/os/gnu-linux/os_defines.h | 5 +++++ libstdc++-v3/libsupc++/atexit_thread.cc | 23 ++++++++++++++++++++++- 2 files changed, 27 insertions(+), 1 deletion(-) diff --git a/libstdc++-v3/config/os/gnu-linux/os_defines.h b/libstdc++-v3/config/os/gnu-linux/os_defines.h index 87317031fcd71..a2e4baec069d5 100644 --- a/libstdc++-v3/config/os/gnu-linux/os_defines.h +++ b/libstdc++-v3/config/os/gnu-linux/os_defines.h @@ -60,6 +60,11 @@ # define _GLIBCXX_HAVE_FLOAT128_MATH 1 #endif +// Enable __cxa_thread_atexit to rely on a (presumably libc-provided) +// __cxa_thread_atexit_impl, if it happens to be defined, even if +// configure couldn't find it during the build. +#define _GLIBCXX_MAY_HAVE___CXA_THREAD_ATEXIT_IMPL 1 + #ifdef __linux__ // The following libpthread properties only apply to Linux, not GNU/Hurd. diff --git a/libstdc++-v3/libsupc++/atexit_thread.cc b/libstdc++-v3/libsupc++/atexit_thread.cc index 9346d50f5dafe..aa4ed5312bfe3 100644 --- a/libstdc++-v3/libsupc++/atexit_thread.cc +++ b/libstdc++-v3/libsupc++/atexit_thread.cc @@ -138,11 +138,32 @@ namespace { } } +#if __GXX_WEAK__ && _GLIBCXX_MAY_HAVE___CXA_THREAD_ATEXIT_IMPL +extern "C" +int __attribute__ ((__weak__)) +__cxa_thread_atexit_impl (void (_GLIBCXX_CDTOR_CALLABI *func) (void *), + void *arg, void *d); +#endif + +// ??? We can't make it an ifunc, can we? extern "C" int __cxxabiv1::__cxa_thread_atexit (void (_GLIBCXX_CDTOR_CALLABI *dtor)(void *), - void *obj, void */*dso_handle*/) + void *obj, void *dso_handle) _GLIBCXX_NOTHROW { +#if __GXX_WEAK__ && _GLIBCXX_MAY_HAVE___CXA_THREAD_ATEXIT_IMPL + if (__cxa_thread_atexit_impl) + // Rely on a (presumably libc-provided) __cxa_thread_atexit_impl, + // if it happens to be defined, even if configure couldn't find it + // during the build. _GLIBCXX_MAY_HAVE___CXA_THREAD_ATEXIT_IMPL + // may be defined e.g. in os_defines.h on platforms where some + // versions of libc have a __cxa_thread_atexit_impl definition, + // but whose earlier versions didn't. This enables programs build + // by toolchains compatible with earlier libc versions to still + // benefit from a libc-provided __cxa_thread_atexit_impl. + return __cxa_thread_atexit_impl (dtor, obj, dso_handle); +#endif + // Do this initialization once. if (__gthread_active_p ()) { -- Alexandre Oliva, happy hacker https://FSFLA.org/blogs/lxo/ Free Software Activist GNU Toolchain Engineer More tolerance and less prejudice are key for inclusion and diversity Excluding neuro-others for not behaving ""normal"" is *not* inclusive