From bfd50906287d335598c92c34d0a963ce436efd1b Mon Sep 17 00:00:00 2001 From: Paul B Mahol Date: Thu, 8 Jun 2023 02:29:16 +0200 Subject: [PATCH] avfilter/af_rubberband: rewrite EOF handling Also pass correct EOF timestamp. --- libavfilter/af_rubberband.c | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) diff --git a/libavfilter/af_rubberband.c b/libavfilter/af_rubberband.c index c56bf5d82f..9f543051b9 100644 --- a/libavfilter/af_rubberband.c +++ b/libavfilter/af_rubberband.c @@ -38,7 +38,9 @@ typedef struct RubberBandContext { int64_t nb_samples_out; int64_t nb_samples_in; int64_t first_pts; + int64_t last_pts; int nb_samples; + int eof; } RubberBandContext; #define OFFSET(x) offsetof(RubberBandContext, x) @@ -100,7 +102,7 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in) if (s->first_pts == AV_NOPTS_VALUE) s->first_pts = in->pts; - rubberband_process(s->rbs, (const float *const *)in->extended_data, in->nb_samples, ff_outlink_get_status(inlink)); + rubberband_process(s->rbs, (const float *const *)in->extended_data, in->nb_samples, s->eof); s->nb_samples_in += in->nb_samples; nb_samples = rubberband_available(s->rbs); @@ -113,6 +115,7 @@ static int filter_frame(AVFilterLink *inlink, AVFrame *in) out->pts = s->first_pts + av_rescale_q(s->nb_samples_out, (AVRational){ 1, outlink->sample_rate }, outlink->time_base); + s->last_pts = out->pts; nb_samples = rubberband_retrieve(s->rbs, (float *const *)out->extended_data, nb_samples); out->nb_samples = nb_samples; ret = ff_filter_frame(outlink, out); @@ -151,11 +154,16 @@ static int activate(AVFilterContext *ctx) AVFilterLink *outlink = ctx->outputs[0]; RubberBandContext *s = ctx->priv; AVFrame *in = NULL; - int ret; + int64_t pts; + int status, ret; FF_FILTER_FORWARD_STATUS_BACK(outlink, inlink); ret = ff_inlink_consume_samples(inlink, s->nb_samples, s->nb_samples, &in); + + if (ff_inlink_acknowledge_status(inlink, &status, &pts)) + s->eof |= status == AVERROR_EOF; + if (ret < 0) return ret; if (ret > 0) { @@ -164,7 +172,11 @@ static int activate(AVFilterContext *ctx) return ret; } - FF_FILTER_FORWARD_STATUS(inlink, outlink); + if (s->eof) { + ff_outlink_set_status(outlink, AVERROR_EOF, s->last_pts); + return 0; + } + FF_FILTER_FORWARD_WANTED(outlink, inlink); return FFERROR_NOT_READY;