summaryrefslogtreecommitdiff
path: root/lib/libpthread/pthread.c
diff options
context:
space:
mode:
authorjoerg <joerg@NetBSD.org>2011-03-30 00:03:26 +0000
committerjoerg <joerg@NetBSD.org>2011-03-30 00:03:26 +0000
commit8473168ff421f7e4df7ce73d3f033cce2a882fd9 (patch)
treebfccc79201390a9b8e055c4e76c788928a608c7f /lib/libpthread/pthread.c
parent619bc4769faf00035b50079fde2f9a6ae52b1d4d (diff)
Rework TLS initialisation:
- Update TCB for the initial thread in pthread__initthread, not pthread__init to get it valid as soon as possible. - Don't overwrite the pt_tls field in pthread__initthread. - Don't deallocate pt_tls in pthread__scrubthread. This worked more by chance than by design. - Handle freeing the TLS area in pthread_create after removing the thread instance from the dead queue.
Diffstat (limited to 'lib/libpthread/pthread.c')
-rw-r--r--lib/libpthread/pthread.c40
1 files changed, 19 insertions, 21 deletions
diff --git a/lib/libpthread/pthread.c b/lib/libpthread/pthread.c
index 0fe53e5c1f2..b1a453af277 100644
--- a/lib/libpthread/pthread.c
+++ b/lib/libpthread/pthread.c
@@ -1,4 +1,4 @@
-/* $NetBSD: pthread.c,v 1.122 2011/03/12 07:46:29 matt Exp $ */
+/* $NetBSD: pthread.c,v 1.123 2011/03/30 00:03:26 joerg Exp $ */
/*-
* Copyright (c) 2001, 2002, 2003, 2006, 2007, 2008 The NetBSD Foundation, Inc.
@@ -30,7 +30,7 @@
*/
#include <sys/cdefs.h>
-__RCSID("$NetBSD: pthread.c,v 1.122 2011/03/12 07:46:29 matt Exp $");
+__RCSID("$NetBSD: pthread.c,v 1.123 2011/03/30 00:03:26 joerg Exp $");
#define __EXPOSE_STACK 1
@@ -195,15 +195,6 @@ pthread__init(void)
pthread__initthread(first);
pthread__scrubthread(first, NULL, 0);
-#if defined(__HAVE_TLS_VARIANT_I) || defined(__HAVE_TLS_VARIANT_II)
-#ifdef __HAVE___LWP_GETTCB_FAST
- first->pt_tls = __lwp_gettcb_fast();
-#else
- first->pt_tls = _lwp_getprivate();
-#endif
- first->pt_tls->tcb_pthread = first;
-#endif
-
first->pt_lid = _lwp_self();
PTQ_INSERT_HEAD(&pthread__allqueue, first, pt_allq);
RB_INSERT(__pthread__alltree, &pthread__alltree, first);
@@ -294,9 +285,6 @@ pthread__initthread(pthread_t t)
{
t->pt_self = t;
-#if defined(__HAVE_TLS_VARIANT_I) || defined(__HAVE_TLS_VARIANT_II)
- t->pt_tls = NULL;
-#endif
t->pt_magic = PT_MAGIC;
t->pt_willpark = 0;
t->pt_unpark = 0;
@@ -320,12 +308,6 @@ static void
pthread__scrubthread(pthread_t t, char *name, int flags)
{
-#if defined(__HAVE_TLS_VARIANT_I) || defined(__HAVE_TLS_VARIANT_II)
- if (t->pt_tls) {
- _rtld_tls_free(t->pt_tls);
- t->pt_tls = NULL;
- }
-#endif
t->pt_state = PT_STATE_RUNNING;
t->pt_exitval = NULL;
t->pt_flags = flags;
@@ -389,6 +371,12 @@ pthread_create(pthread_t *thread, const pthread_attr_t *attr,
if (newthread)
PTQ_REMOVE(&pthread__deadqueue, newthread, pt_deadq);
pthread_mutex_unlock(&pthread__deadqueue_lock);
+#if defined(__HAVE_TLS_VARIANT_I) || defined(__HAVE_TLS_VARIANT_II)
+ if (newthread && newthread->pt_tls) {
+ _rtld_tls_free(newthread->pt_tls);
+ newthread->pt_tls = NULL;
+ }
+#endif
}
/*
@@ -410,6 +398,9 @@ pthread_create(pthread_t *thread, const pthread_attr_t *attr,
#endif
newthread->pt_uc.uc_stack = newthread->pt_stack;
newthread->pt_uc.uc_link = NULL;
+#if defined(__HAVE_TLS_VARIANT_I) || defined(__HAVE_TLS_VARIANT_II)
+ newthread->pt_tls = NULL;
+#endif
/* Add to list of all threads. */
pthread_rwlock_wrlock(&pthread__alltree_lock);
@@ -1267,7 +1258,14 @@ pthread__initmain(pthread_t *newt)
}
*newt = t;
-#if !defined(__HAVE_TLS_VARIANT_I) && !defined(__HAVE_TLS_VARIANT_II)
+#if defined(__HAVE_TLS_VARIANT_I) || defined(__HAVE_TLS_VARIANT_II)
+# ifdef __HAVE___LWP_GETTCB_FAST
+ t->pt_tls = __lwp_gettcb_fast();
+# else
+ t->pt_tls = _lwp_getprivate();
+# endif
+ t->pt_tls->tcb_pthread = t;
+#else
_lwp_setprivate(t);
#endif
}