diff options
Diffstat (limited to 'audio')
-rw-r--r-- | audio/decode/ad_lavc.c | 8 | ||||
-rw-r--r-- | audio/decode/ad_mpg123.c | 4 | ||||
-rw-r--r-- | audio/decode/ad_spdif.c | 5 | ||||
-rw-r--r-- | audio/decode/dec_audio.c | 47 | ||||
-rw-r--r-- | audio/decode/dec_audio.h | 7 |
5 files changed, 40 insertions, 31 deletions
diff --git a/audio/decode/ad_lavc.c b/audio/decode/ad_lavc.c index cb8cfa8c82..4ff69c3f20 100644 --- a/audio/decode/ad_lavc.c +++ b/audio/decode/ad_lavc.c @@ -309,8 +309,10 @@ static int decode_packet(struct dec_audio *da) mp_audio_set_null_data(&da->decoded); struct demux_packet *mpkt = priv->packet; - if (!mpkt) - mpkt = demux_read_packet(da->header); + if (!mpkt) { + if (demux_read_packet_async(da->header, &mpkt) == 0) + return AD_WAIT; + } priv->packet = talloc_steal(priv, mpkt); @@ -343,7 +345,7 @@ static int decode_packet(struct dec_audio *da) } // LATM may need many packets to find mux info if (ret == AVERROR(EAGAIN)) - return 0; + return AD_OK; } if (ret < 0) { MP_ERR(da, "Error decoding audio.\n"); diff --git a/audio/decode/ad_mpg123.c b/audio/decode/ad_mpg123.c index dc3ec69531..30a4790746 100644 --- a/audio/decode/ad_mpg123.c +++ b/audio/decode/ad_mpg123.c @@ -218,7 +218,9 @@ static int decode_packet(struct dec_audio *da) mp_audio_set_null_data(&da->decoded); - struct demux_packet *pkt = demux_read_packet(da->header); + struct demux_packet *pkt; + if (demux_read_packet_async(da->header, &pkt) == 0) + return AD_WAIT; if (!pkt) return AD_EOF; diff --git a/audio/decode/ad_spdif.c b/audio/decode/ad_spdif.c index c215f92e63..528e42fbc4 100644 --- a/audio/decode/ad_spdif.c +++ b/audio/decode/ad_spdif.c @@ -191,7 +191,10 @@ static int decode_packet(struct dec_audio *da) spdif_ctx->out_buffer_len = 0; - struct demux_packet *mpkt = demux_read_packet(da->header); + struct demux_packet *mpkt; + if (demux_read_packet_async(da->header, &mpkt) == 0) + return AD_WAIT; + if (!mpkt) return AD_EOF; diff --git a/audio/decode/dec_audio.c b/audio/decode/dec_audio.c index 38044b4657..c7580a23d8 100644 --- a/audio/decode/dec_audio.c +++ b/audio/decode/dec_audio.c @@ -89,27 +89,7 @@ static int init_audio_codec(struct dec_audio *d_audio, const char *decoder) return 0; } - // Decode enough until we know the audio format. - for (int tries = 1; ; tries++) { - if (mp_audio_config_valid(&d_audio->decoded)) { - MP_VERBOSE(d_audio, "Initial decode succeeded after %d packets.\n", - tries); - break; - } - if (tries >= 50) { - MP_ERR(d_audio, "initial decode failed\n"); - uninit_decoder(d_audio); - return 0; - } - d_audio->ad_driver->decode_packet(d_audio); - } - d_audio->decode_buffer = mp_audio_buffer_create(NULL); - if (!reinit_audio_buffer(d_audio)) { - uninit_decoder(d_audio); - return 0; - } - return 1; } @@ -171,9 +151,6 @@ int audio_init_best_codec(struct dec_audio *d_audio, char *audio_decoders) talloc_asprintf(d_audio, "%s [%s:%s]", decoder->desc, decoder->family, decoder->decoder); MP_VERBOSE(d_audio, "Selected audio codec: %s\n", d_audio->decoder_desc); - MP_VERBOSE(d_audio, "AUDIO: %d Hz, %d ch, %s\n", - d_audio->decoded.rate, d_audio->decoded.channels.num, - af_fmt_to_str(d_audio->decoded.format)); } else { MP_ERR(d_audio, "Failed to initialize an audio decoder for codec '%s'.\n", d_audio->header->codec ? d_audio->header->codec : "<unknown>"); @@ -238,6 +215,24 @@ int audio_init_filters(struct dec_audio *d_audio, int in_samplerate, return 1; } +/* Decode packets until we know the audio format. Then reinit the buffer. + * Returns AD_OK on success, negative AD_* code otherwise. + * Also returns AD_OK if already initialized (and does nothing). + */ +int initial_audio_decode(struct dec_audio *da) +{ + while (!mp_audio_config_valid(&da->decoded)) { + if (da->decoded.samples > 0) + return AD_ERR; // invalid format, rather than uninitialized + int ret = da->ad_driver->decode_packet(da); + if (ret < 0) + return ret; + } + if (mp_audio_buffer_samples(da->decode_buffer) > 0) // avoid accidental flush + return AD_OK; + return reinit_audio_buffer(da) ? AD_OK : AD_ERR; +} + // Filter len bytes of input, put result into outbuf. static int filter_n_bytes(struct dec_audio *da, struct mp_audio_buffer *outbuf, int len) @@ -270,6 +265,9 @@ static int filter_n_bytes(struct dec_audio *da, struct mp_audio_buffer *outbuf, break; } + if (error == AD_WAIT) + return error; + // Filter struct mp_audio filter_data; mp_audio_buffer_peek(da->decode_buffer, &filter_data); @@ -306,6 +304,9 @@ static int filter_n_bytes(struct dec_audio *da, struct mp_audio_buffer *outbuf, int audio_decode(struct dec_audio *d_audio, struct mp_audio_buffer *outbuf, int minsamples) { + if (!d_audio->afilter) + return AD_ERR; + // Indicates that a filter seems to be buffering large amounts of data int huge_filter_buffer = 0; diff --git a/audio/decode/dec_audio.h b/audio/decode/dec_audio.h index f9269b5272..6d2c61d862 100644 --- a/audio/decode/dec_audio.h +++ b/audio/decode/dec_audio.h @@ -51,15 +51,16 @@ struct dec_audio { enum { AD_OK = 0, AD_ERR = -1, - AD_NEW_FMT = -2, - AD_ASYNC_PLAY_DONE = -3, - AD_EOF = -4, + AD_EOF = -2, + AD_NEW_FMT = -3, + AD_WAIT = -4, }; struct mp_decoder_list *audio_decoder_list(void); int audio_init_best_codec(struct dec_audio *d_audio, char *audio_decoders); int audio_decode(struct dec_audio *d_audio, struct mp_audio_buffer *outbuf, int minsamples); +int initial_audio_decode(struct dec_audio *d_audio); void audio_reset_decoding(struct dec_audio *d_audio); void audio_uninit(struct dec_audio *d_audio); |