aboutsummaryrefslogtreecommitdiffstats
path: root/src/output
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--src/output_all.c4
-rw-r--r--src/output_control.c37
-rw-r--r--src/output_internal.h3
-rw-r--r--src/output_thread.c15
4 files changed, 36 insertions, 23 deletions
diff --git a/src/output_all.c b/src/output_all.c
index 5b066ba26..19c0f0166 100644
--- a/src/output_all.c
+++ b/src/output_all.c
@@ -323,7 +323,7 @@ audio_output_all_open(const struct audio_format *audio_format,
else
/* if the pipe hasn't been cleared, the the audio
format must not have changed */
- assert(music_pipe_size(g_mp) == 0 ||
+ assert(music_pipe_empty(g_mp) ||
audio_format_equals(audio_format,
&input_audio_format));
@@ -436,7 +436,7 @@ audio_output_all_check(void)
assert(g_mp != NULL);
while ((chunk = music_pipe_peek(g_mp)) != NULL) {
- assert(music_pipe_size(g_mp) > 0);
+ assert(!music_pipe_empty(g_mp));
if (!chunk_is_consumed(chunk))
/* at least one output is not finished playing
diff --git a/src/output_control.c b/src/output_control.c
index 5b9b2b902..161404f78 100644
--- a/src/output_control.c
+++ b/src/output_control.c
@@ -102,6 +102,12 @@ audio_output_disable(struct audio_output *ao)
g_mutex_unlock(ao->mutex);
}
+static void
+audio_output_close_locked(struct audio_output *ao);
+
+/**
+ * Object must be locked (and unlocked) by the caller.
+ */
static bool
audio_output_open(struct audio_output *ao,
const struct audio_format *audio_format,
@@ -173,6 +179,8 @@ audio_output_open(struct audio_output *ao,
static void
audio_output_close_locked(struct audio_output *ao)
{
+ assert(ao != NULL);
+
if (ao->mixer != NULL)
mixer_auto_close(ao->mixer);
@@ -251,25 +259,6 @@ void audio_output_cancel(struct audio_output *ao)
g_mutex_unlock(ao->mutex);
}
-void audio_output_close(struct audio_output *ao)
-{
- if (ao->mixer != NULL)
- mixer_auto_close(ao->mixer);
-
- g_mutex_lock(ao->mutex);
-
- assert(!ao->open || ao->fail_timer == NULL);
-
- if (ao->open)
- ao_command(ao, AO_COMMAND_CLOSE);
- else if (ao->fail_timer != NULL) {
- g_timer_destroy(ao->fail_timer);
- ao->fail_timer = NULL;
- }
-
- g_mutex_unlock(ao->mutex);
-}
-
void
audio_output_release(struct audio_output *ao)
{
@@ -279,6 +268,16 @@ audio_output_release(struct audio_output *ao)
audio_output_close(ao);
}
+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)
{
audio_output_close(ao);
diff --git a/src/output_internal.h b/src/output_internal.h
index 9e4d1f25d..18d431352 100644
--- a/src/output_internal.h
+++ b/src/output_internal.h
@@ -196,7 +196,8 @@ struct audio_output {
const struct music_pipe *pipe;
/**
- * This mutex protects #open, #chunk and #chunk_finished.
+ * This mutex protects #open, #fail_timer, #chunk and
+ * #chunk_finished.
*/
GMutex *mutex;
diff --git a/src/output_thread.c b/src/output_thread.c
index 8b120325c..380956fac 100644
--- a/src/output_thread.c
+++ b/src/output_thread.c
@@ -134,10 +134,18 @@ ao_open(struct audio_output *ao)
struct audio_format_string af_string;
assert(!ao->open);
- assert(ao->fail_timer == NULL);
assert(ao->pipe != NULL);
assert(ao->chunk == NULL);
+ if (ao->fail_timer != NULL) {
+ /* this can only happen when this
+ output thread fails while
+ audio_output_open() is run in the
+ player thread */
+ g_timer_destroy(ao->fail_timer);
+ ao->fail_timer = NULL;
+ }
+
/* enable the device (just in case the last enable has failed) */
if (!ao_enable(ao))
@@ -455,7 +463,12 @@ ao_play_chunk(struct audio_output *ao, const struct music_chunk *chunk)
/* don't automatically reopen this device for
10 seconds */
+ g_mutex_lock(ao->mutex);
+
+ assert(ao->fail_timer == NULL);
ao->fail_timer = g_timer_new();
+
+ g_mutex_unlock(ao->mutex);
return false;
}