tavianator added a comment.
In http://reviews.llvm.org/D21803#470086, @bcraig wrote:
> It also intentionally leaks the pthread key. Does the __thread_specific_ptr
> rationale hold for this change as well?
Hmm, maybe? If other global destructors run after ~DtorListHolder(), and they
cause a thread_local to be initialized for the first time,
__cxa_thread_atexit() might be called again. I was thinking that dtors would
get re-initialized in that case but it appears it does not. So yeah, I think
I'll need to leak the pthread_key_t.
I'm not sure how to avoid leaking the actual thread_local objects that get
created in that situation. There's nothing left to trigger run_dtors() a
second time.
================
Comment at: src/cxa_thread_atexit.cpp:64-90
@@ -18,8 +63,29 @@
+_LIBCXXABI_FUNC_VIS int __cxa_thread_atexit(Dtor dtor, void *obj,
void *dso_symbol) throw() {
- extern int __cxa_thread_atexit_impl(void (*)(void *), void *, void *);
- return __cxa_thread_atexit_impl(dtor, obj, dso_symbol);
-}
+ extern int __cxa_thread_atexit_impl(Dtor, void *, void *)
+ __attribute__((__weak__));
+
+ if (__cxa_thread_atexit_impl) {
+ return __cxa_thread_atexit_impl(dtor, obj, dso_symbol);
+ } else {
+ static DtorListHolder dtors;
+
+ auto head = static_cast<DtorList*>(std::malloc(sizeof(DtorList)));
+ if (!head) {
+ return -1;
+ }
+
+ head->dtor = dtor;
+ head->obj = obj;
+ head->next = dtors.get();
+
+ if (!dtors.set(head)) {
+ std::free(head);
+ return -1;
+ }
-#endif // HAVE__CXA_THREAD_ATEXIT_IMPL
+ return 0;
+ }
+}
} // extern "C"
----------------
majnemer wrote:
> I think that this should be an opt-in mechanism, there are platforms that
> presumably never need to pay the cost of the unused code (macOS comes to
> mind).
This file is only built for UNIX AND NOT (APPLE OR CYGWIN). Other platforms
use something other than __cxa_thread_atexit() I assume.
http://reviews.llvm.org/D21803
_______________________________________________
cfe-commits mailing list
[email protected]
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits