Commit 21223154 authored by Max Kellermann's avatar Max Kellermann

output_control: lock object in audio_output_close()

Protect the attributes "open" and "fail_timer".
parent a549d871
...@@ -50,6 +50,20 @@ static void ao_command(struct audio_output *ao, enum audio_output_command cmd) ...@@ -50,6 +50,20 @@ static void ao_command(struct audio_output *ao, enum audio_output_command cmd)
ao_command_wait(ao); ao_command_wait(ao);
} }
/**
* Like ao_command(), but assumes the object is locked by the caller.
*/
static void
ao_command_locked(struct audio_output *ao, enum audio_output_command cmd)
{
assert(ao->command == AO_COMMAND_NONE);
ao->command = cmd;
g_mutex_unlock(ao->mutex);
ao_command_wait(ao);
g_mutex_lock(ao->mutex);
}
static void ao_command_async(struct audio_output *ao, static void ao_command_async(struct audio_output *ao,
enum audio_output_command cmd) enum audio_output_command cmd)
{ {
...@@ -162,21 +176,33 @@ void audio_output_cancel(struct audio_output *ao) ...@@ -162,21 +176,33 @@ void audio_output_cancel(struct audio_output *ao)
ao_command_async(ao, AO_COMMAND_CANCEL); ao_command_async(ao, AO_COMMAND_CANCEL);
} }
void audio_output_close(struct audio_output *ao) static void
audio_output_close_locked(struct audio_output *ao)
{ {
assert(ao != NULL);
assert(!ao->open || ao->fail_timer == NULL); assert(!ao->open || ao->fail_timer == NULL);
if (ao->mixer != NULL) if (ao->mixer != NULL)
mixer_auto_close(ao->mixer); mixer_auto_close(ao->mixer);
if (ao->open) if (ao->open)
ao_command(ao, AO_COMMAND_CLOSE); ao_command_locked(ao, AO_COMMAND_CLOSE);
else if (ao->fail_timer != NULL) { else if (ao->fail_timer != NULL) {
g_timer_destroy(ao->fail_timer); g_timer_destroy(ao->fail_timer);
ao->fail_timer = NULL; ao->fail_timer = NULL;
} }
} }
void audio_output_close(struct audio_output *ao)
{
assert(ao != NULL);
assert(!ao->open || ao->fail_timer == NULL);
g_mutex_lock(ao->mutex);
audio_output_close_locked(ao);
g_mutex_unlock(ao->mutex);
}
void audio_output_finish(struct audio_output *ao) void audio_output_finish(struct audio_output *ao)
{ {
audio_output_close(ao); audio_output_close(ao);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment