Skip to content

Commit 77eadca

Browse files
committed
al_run_detached_thread: fix segfault on detaching when the thread is already gone
detached_thread_func_trampoline freed the outer thread at its end. If outer->proc was really fast to finish, _al_thread_detach could get called with &outer->thread as its argument after outer was already freed. Usually it would be fast enough to not ever be overwritten after freeing, but tools like asan explicitly overwrite freed memory, leading to reproducible crash.
1 parent e816710 commit 77eadca

File tree

1 file changed

+20
-3
lines changed

1 file changed

+20
-3
lines changed

src/threads.c

Lines changed: 20 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,15 @@ static void detached_thread_func_trampoline(_AL_THREAD *inner, void *_outer)
9292
(void)inner;
9393

9494
((void *(*)(void *))outer->proc)(outer->arg);
95-
al_free(outer);
95+
96+
_al_mutex_lock(&outer->mutex);
97+
if (outer->thread_state == THREAD_STATE_DETACHED) {
98+
_al_mutex_destroy(&outer->mutex);
99+
al_free(outer);
100+
} else {
101+
outer->thread_state = THREAD_STATE_DESTROYED;
102+
_al_mutex_unlock(&outer->mutex);
103+
}
96104
}
97105

98106

@@ -147,11 +155,20 @@ ALLEGRO_THREAD *al_create_thread_with_stacksize(
147155
void al_run_detached_thread(void *(*proc)(void *arg), void *arg)
148156
{
149157
ALLEGRO_THREAD *outer = create_thread();
150-
outer->thread_state = THREAD_STATE_DETACHED;
158+
outer->thread_state = THREAD_STATE_CREATED;
151159
outer->arg = arg;
152160
outer->proc = proc;
161+
_al_mutex_init(&outer->mutex);
153162
_al_thread_create(&outer->thread, detached_thread_func_trampoline, outer);
154-
_al_thread_detach(&outer->thread);
163+
_al_mutex_lock(&outer->mutex);
164+
if (outer->thread_state == THREAD_STATE_DESTROYED) {
165+
_al_mutex_destroy(&outer->mutex);
166+
al_free(outer);
167+
} else {
168+
_al_thread_detach(&outer->thread);
169+
outer->thread_state = THREAD_STATE_DETACHED;
170+
_al_mutex_unlock(&outer->mutex);
171+
}
155172
}
156173

157174

0 commit comments

Comments
 (0)