mirror of
https://github.com/mpv-player/mpv.git
synced 2024-09-20 03:52:22 +02:00
audio: move direct packet reading from decoders to common code
Another bit of preparation.
This commit is contained in:
parent
c365b44e19
commit
30031edce3
@ -35,7 +35,8 @@ struct ad_functions {
|
||||
int (*init)(struct dec_audio *da, const char *decoder);
|
||||
void (*uninit)(struct dec_audio *da);
|
||||
int (*control)(struct dec_audio *da, int cmd, void *arg);
|
||||
int (*decode_packet)(struct dec_audio *da, struct mp_audio **out);
|
||||
int (*decode_packet)(struct dec_audio *da, struct demux_packet *pkt,
|
||||
struct mp_audio **out);
|
||||
};
|
||||
|
||||
enum ad_ctrl {
|
||||
|
@ -42,7 +42,6 @@ struct priv {
|
||||
AVFrame *avframe;
|
||||
struct mp_audio frame;
|
||||
bool force_channel_map;
|
||||
struct demux_packet *packet;
|
||||
uint32_t skip_samples;
|
||||
};
|
||||
|
||||
@ -165,27 +164,18 @@ static int control(struct dec_audio *da, int cmd, void *arg)
|
||||
switch (cmd) {
|
||||
case ADCTRL_RESET:
|
||||
avcodec_flush_buffers(ctx->avctx);
|
||||
talloc_free(ctx->packet);
|
||||
ctx->packet = NULL;
|
||||
ctx->skip_samples = 0;
|
||||
return CONTROL_TRUE;
|
||||
}
|
||||
return CONTROL_UNKNOWN;
|
||||
}
|
||||
|
||||
static int decode_packet(struct dec_audio *da, struct mp_audio **out)
|
||||
static int decode_packet(struct dec_audio *da, struct demux_packet *mpkt,
|
||||
struct mp_audio **out)
|
||||
{
|
||||
struct priv *priv = da->priv;
|
||||
AVCodecContext *avctx = priv->avctx;
|
||||
|
||||
struct demux_packet *mpkt = priv->packet;
|
||||
if (!mpkt) {
|
||||
if (demux_read_packet_async(da->header, &mpkt) == 0)
|
||||
return AD_WAIT;
|
||||
}
|
||||
|
||||
priv->packet = talloc_steal(priv, mpkt);
|
||||
|
||||
int in_len = mpkt ? mpkt->len : 0;
|
||||
|
||||
AVPacket pkt;
|
||||
@ -203,13 +193,11 @@ static int decode_packet(struct dec_audio *da, struct mp_audio **out)
|
||||
mpkt->len -= ret;
|
||||
mpkt->pts = MP_NOPTS_VALUE; // don't reset PTS next time
|
||||
}
|
||||
if (mpkt->len == 0 || ret < 0) {
|
||||
talloc_free(mpkt);
|
||||
priv->packet = NULL;
|
||||
}
|
||||
// LATM may need many packets to find mux info
|
||||
if (ret == AVERROR(EAGAIN))
|
||||
if (ret == AVERROR(EAGAIN)) {
|
||||
mpkt->len = 0;
|
||||
return AD_OK;
|
||||
}
|
||||
}
|
||||
if (ret < 0) {
|
||||
MP_ERR(da, "Error decoding audio.\n");
|
||||
|
@ -242,16 +242,13 @@ fail:
|
||||
return -1;
|
||||
}
|
||||
|
||||
static int decode_packet(struct dec_audio *da, struct mp_audio **out)
|
||||
static int decode_packet(struct dec_audio *da, struct demux_packet *mpkt,
|
||||
struct mp_audio **out)
|
||||
{
|
||||
struct spdifContext *spdif_ctx = da->priv;
|
||||
|
||||
spdif_ctx->out_buffer_len = 0;
|
||||
|
||||
struct demux_packet *mpkt;
|
||||
if (demux_read_packet_async(da->header, &mpkt) == 0)
|
||||
return AD_WAIT;
|
||||
|
||||
if (!mpkt)
|
||||
return AD_EOF;
|
||||
|
||||
@ -259,13 +256,13 @@ static int decode_packet(struct dec_audio *da, struct mp_audio **out)
|
||||
|
||||
AVPacket pkt;
|
||||
mp_set_av_packet(&pkt, mpkt, NULL);
|
||||
mpkt->len = 0; // will be fully consumed
|
||||
pkt.pts = pkt.dts = 0;
|
||||
if (!spdif_ctx->lavf_ctx) {
|
||||
if (init_filter(da, &pkt) < 0)
|
||||
return AD_ERR;
|
||||
}
|
||||
int ret = av_write_frame(spdif_ctx->lavf_ctx, &pkt);
|
||||
talloc_free(mpkt);
|
||||
avio_flush(spdif_ctx->lavf_ctx->pb);
|
||||
if (ret < 0)
|
||||
return AD_ERR;
|
||||
|
@ -161,13 +161,23 @@ void audio_uninit(struct dec_audio *d_audio)
|
||||
uninit_decoder(d_audio);
|
||||
af_destroy(d_audio->afilter);
|
||||
talloc_free(d_audio->waiting);
|
||||
talloc_free(d_audio->packet);
|
||||
talloc_free(d_audio);
|
||||
}
|
||||
|
||||
static int decode_new_frame(struct dec_audio *da)
|
||||
{
|
||||
while (!da->waiting) {
|
||||
int ret = da->ad_driver->decode_packet(da, &da->waiting);
|
||||
if (!da->packet) {
|
||||
if (demux_read_packet_async(da->header, &da->packet) == 0)
|
||||
return AD_WAIT;
|
||||
}
|
||||
|
||||
int ret = da->ad_driver->decode_packet(da, da->packet, &da->waiting);
|
||||
if (ret < 0 || (da->packet && da->packet->len == 0)) {
|
||||
talloc_free(da->packet);
|
||||
da->packet = NULL;
|
||||
}
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
@ -285,8 +295,8 @@ void audio_reset_decoding(struct dec_audio *d_audio)
|
||||
d_audio->pts = MP_NOPTS_VALUE;
|
||||
d_audio->pts_offset = 0;
|
||||
d_audio->pts_reset = false;
|
||||
if (d_audio->waiting) {
|
||||
talloc_free(d_audio->waiting);
|
||||
d_audio->waiting = NULL;
|
||||
}
|
||||
talloc_free(d_audio->waiting);
|
||||
d_audio->waiting = NULL;
|
||||
talloc_free(d_audio->packet);
|
||||
d_audio->packet = NULL;
|
||||
}
|
||||
|
@ -48,6 +48,8 @@ struct dec_audio {
|
||||
bool pts_reset;
|
||||
// For free use by the ad_driver
|
||||
void *priv;
|
||||
// Strictly internal to dec_audio.c
|
||||
struct demux_packet *packet;
|
||||
};
|
||||
|
||||
enum {
|
||||
|
Loading…
Reference in New Issue
Block a user