From 4f5e2b745ea357e2b5c815ff33a556505a7d1f18 Mon Sep 17 00:00:00 2001 From: Lennart Poettering Date: Thu, 30 Jul 2009 23:46:25 +0200 Subject: threaded-mainloop: loop around pa_cond_wait() invocation in pa_threaded_mainloop_signal() --- src/pulse/thread-mainloop.c | 13 ++++++++++--- src/pulse/thread-mainloop.h | 4 +++- 2 files changed, 13 insertions(+), 4 deletions(-) diff --git a/src/pulse/thread-mainloop.c b/src/pulse/thread-mainloop.c index 6916d867..a2b98ce1 100644 --- a/src/pulse/thread-mainloop.c +++ b/src/pulse/thread-mainloop.c @@ -51,7 +51,7 @@ struct pa_threaded_mainloop { pa_mainloop *real_mainloop; - int n_waiting; + int n_waiting, n_waiting_for_accept; pa_thread* thread; pa_mutex* mutex; @@ -190,8 +190,12 @@ void pa_threaded_mainloop_signal(pa_threaded_mainloop *m, int wait_for_accept) { pa_cond_signal(m->cond, 1); - if (wait_for_accept && m->n_waiting > 0) - pa_cond_wait(m->accept_cond, m->mutex); + if (wait_for_accept) { + m->n_waiting_for_accept ++; + + while (m->n_waiting_for_accept > 0) + pa_cond_wait(m->accept_cond, m->mutex); + } } void pa_threaded_mainloop_wait(pa_threaded_mainloop *m) { @@ -214,6 +218,9 @@ void pa_threaded_mainloop_accept(pa_threaded_mainloop *m) { /* Make sure that this function is not called from the helper thread */ pa_assert(!m->thread || !pa_thread_is_running(m->thread) || !in_worker(m)); + pa_assert(m->n_waiting_for_accept > 0); + m->n_waiting_for_accept --; + pa_cond_signal(m->accept_cond, 0); } diff --git a/src/pulse/thread-mainloop.h b/src/pulse/thread-mainloop.h index 8eddce4c..41159d98 100644 --- a/src/pulse/thread-mainloop.h +++ b/src/pulse/thread-mainloop.h @@ -274,7 +274,9 @@ void pa_threaded_mainloop_unlock(pa_threaded_mainloop *m); * inside the event loop thread. Prior to this call the event loop * object needs to be locked using pa_threaded_mainloop_lock(). While * waiting the lock will be released, immediately before returning it - * will be acquired again. */ + * will be acquired again. This function may spuriously wake up even + * without _signal() being called. You need to make sure to handle + * that! */ void pa_threaded_mainloop_wait(pa_threaded_mainloop *m); /** Signal all threads waiting for a signalling event in -- cgit