From 6fb12a5fdaf95bf5ded286c8db18a30e392964e1 Mon Sep 17 00:00:00 2001 From: wm4 Date: Wed, 5 Oct 2016 16:42:43 +0200 Subject: audio: move some fallback handling to common AO reload function Now a reload requested by an AO behaves in exactly the same way as changing an AO-related options (like --audio-channels or --audio-exclusive). This is good for testing and uniform behavior. (You could go as far as saying it's a necessity, because the spotty and obscure AO reload behavior is hard to reproduce and thus hard to test at all.) --- player/audio.c | 52 +++++++++++++++++++++++++++++++++------------------- player/command.c | 17 ++--------------- player/core.h | 1 + 3 files changed, 36 insertions(+), 34 deletions(-) diff --git a/player/audio.c b/player/audio.c index 29ad44e5ed..3f173f140d 100644 --- a/player/audio.c +++ b/player/audio.c @@ -861,33 +861,47 @@ static int filter_audio(struct MPContext *mpctx, struct mp_audio_buffer *outbuf, return res; } +void reload_audio_output(struct MPContext *mpctx) +{ + if (!mpctx->ao) + return; + + ao_reset(mpctx->ao); + uninit_audio_out(mpctx); + reinit_audio_filters(mpctx); // mostly to issue refresh seek + + // Whether we can use spdif might have changed. If we failed to use spdif + // in the previous initialization, try it with spdif again (we'll fallback + // to PCM again if necessary). + struct ao_chain *ao_c = mpctx->ao_chain; + if (ao_c) { + struct dec_audio *d_audio = ao_c->audio_src; + if (d_audio && ao_c->spdif_failed) { + ao_c->spdif_passthrough = true; + ao_c->spdif_failed = false; + d_audio->try_spdif = true; + ao_c->af->initialized = 0; + if (!audio_init_best_codec(d_audio)) { + MP_ERR(mpctx, "Error reinitializing audio.\n"); + error_on_track(mpctx, ao_c->track); + } + } + } + + mp_wakeup_core(mpctx); +} + void fill_audio_out_buffers(struct MPContext *mpctx) { struct MPOpts *opts = mpctx->opts; - struct ao_chain *ao_c = mpctx->ao_chain; bool was_eof = mpctx->audio_status == STATUS_EOF; dump_audio_stats(mpctx); - if (mpctx->ao && ao_query_and_reset_events(mpctx->ao, AO_EVENT_RELOAD)) { - ao_reset(mpctx->ao); - uninit_audio_out(mpctx); - if (ao_c) { - struct dec_audio *d_audio = ao_c->audio_src; - if (d_audio && ao_c->spdif_failed) { - ao_c->spdif_failed = false; - d_audio->try_spdif = true; - if (!audio_init_best_codec(d_audio)) { - MP_ERR(mpctx, "Error reinitializing audio.\n"); - error_on_track(mpctx, ao_c->track); - return; - } - } - reinit_audio_filters_and_output(mpctx); - ao_c = mpctx->ao_chain; - } - } + if (mpctx->ao && ao_query_and_reset_events(mpctx->ao, AO_EVENT_RELOAD)) + reload_audio_output(mpctx); + struct ao_chain *ao_c = mpctx->ao_chain; if (!ao_c) return; diff --git a/player/command.c b/player/command.c index e11f485056..96f60d70a9 100644 --- a/player/command.c +++ b/player/command.c @@ -1881,13 +1881,6 @@ static int get_device_entry(int item, int action, void *arg, void *ctx) return m_property_read_sub(props, action, arg); } -static void reload_audio_output(struct MPContext *mpctx) -{ - if (!mpctx->ao) - return; - ao_request_reload(mpctx->ao); -} - static void create_hotplug(struct MPContext *mpctx) { struct command_ctx *cmd = mpctx->command_ctx; @@ -5735,14 +5728,8 @@ void mp_option_change_callback(void *ctx, struct m_config_option *co, int flags) } } - if ((flags & UPDATE_AUDIO) && mpctx->ao_chain) { - // Force full mid-stream reinit. - if (mpctx->ao) - ao_reset(mpctx->ao); - uninit_audio_out(mpctx); - reinit_audio_filters(mpctx); // mostly to issue refresh seek - mp_wakeup_core(mpctx); - } + if (flags & UPDATE_AUDIO) + reload_audio_output(mpctx); if (flags & UPDATE_PRIORITY) update_priority(mpctx); diff --git a/player/core.h b/player/core.h index bf6a768e82..b33d367cec 100644 --- a/player/core.h +++ b/player/core.h @@ -445,6 +445,7 @@ int init_audio_decoder(struct MPContext *mpctx, struct track *track); void reinit_audio_chain_src(struct MPContext *mpctx, struct lavfi_pad *src); void audio_update_volume(struct MPContext *mpctx); void audio_update_balance(struct MPContext *mpctx); +void reload_audio_output(struct MPContext *mpctx); // configfiles.c void mp_parse_cfgfiles(struct MPContext *mpctx); -- cgit v1.2.3