client: merge can_terminate() function

This has some tricky interactions. In particular, it requires the core
to be locked due to reading outstanding_async, which is documented on
the only caller only. It's probably better to merge it with its only
caller.

The new code should be strictly equivalent, other than the fact that it
doesn't temporarily unlock+lock when entering the loop for the first
time (which doesn't matter here).
This commit is contained in:
wm4 2018-05-06 13:32:50 +02:00
parent 22c002138d
commit a0308d3169
1 changed files with 13 additions and 16 deletions

View File

@ -483,32 +483,29 @@ void mpv_terminate_destroy(mpv_handle *ctx)
mp_destroy_client(ctx, true);
}
static bool can_terminate(struct MPContext *mpctx)
{
struct mp_client_api *clients = mpctx->clients;
pthread_mutex_lock(&clients->lock);
bool ok = clients->num_clients == 0 && mpctx->outstanding_async == 0 &&
(mpctx->is_cli || clients->terminate_core_thread);
pthread_mutex_unlock(&clients->lock);
return ok;
}
// Can be called on the core thread only. Idempotent.
void mp_shutdown_clients(struct MPContext *mpctx)
{
struct mp_client_api *clients = mpctx->clients;
// Prevent that new clients can appear.
pthread_mutex_lock(&clients->lock);
clients->shutting_down = true;
pthread_mutex_unlock(&clients->lock);
while (!can_terminate(mpctx)) {
// Prevent that new clients can appear.
clients->shutting_down = true;
// Wait until we can terminate.
while (clients->num_clients || mpctx->outstanding_async ||
!(mpctx->is_cli || clients->terminate_core_thread))
{
pthread_mutex_unlock(&clients->lock);
mp_client_broadcast_event(mpctx, MPV_EVENT_SHUTDOWN, NULL);
mp_wait_events(mpctx);
pthread_mutex_lock(&clients->lock);
}
pthread_mutex_unlock(&clients->lock);
}
static void *core_thread(void *p)