diff options
author | Konstantin Belousov <kib@FreeBSD.org> | 2025-01-14 22:11:48 +0000 |
---|---|---|
committer | Konstantin Belousov <kib@FreeBSD.org> | 2025-01-14 23:14:00 +0000 |
commit | 676be27133fa3296f3d9083732d8837a3eaa5ea4 (patch) | |
tree | ba75187033ae73e2fb76a83e1280caa2700fb2ea /lib | |
parent | 1cd455f39d886f27c33f7726f79fc4cc566da7b3 (diff) |
libpthread_init(): ensure curthread == NULL until set explicitly
Otherwise libthr::_get_curthread() returns a garbage kept there from
allocate_initial_tls(), until libthr initialization proceeds enough to
set initial pcb->pcb_thread. The garbage pcb_thread was dereferenced
as struct pthread and some memory read as TID. Since the read might not
be consistent between reads, thr_malloc_umtx unlock sometimes returned
EPERM instead of clearing the lock word.
Reported by: markj
Sponsored by: The FreeBSD Foundation
MFC after: 1 week
Diffstat (limited to 'lib')
-rw-r--r-- | lib/libthr/thread/thr_init.c | 2 |
1 files changed, 2 insertions, 0 deletions
diff --git a/lib/libthr/thread/thr_init.c b/lib/libthr/thread/thr_init.c index 708c425d69c1..8855491b91cb 100644 --- a/lib/libthr/thread/thr_init.c +++ b/lib/libthr/thread/thr_init.c @@ -334,6 +334,8 @@ _libpthread_init(struct pthread *curthread) /* Set the initial thread. */ if (curthread == NULL) { first = 1; + /* Force _get_curthread() return NULL until set. */ + _tcb_get()->tcb_thread = NULL; /* Create and initialize the initial thread. */ curthread = _thr_alloc(NULL); if (curthread == NULL) |