diff mbox

[FFmpeg-devel] lavfi: make ff_framequeue_skip_samples() more useful.

Message ID 20170129091703.16745-1-george@nsup.org
State Accepted
Commit 383057f8e744efeaaa3648a59bc577b25b055835
Headers show

Commit Message

Nicolas George Jan. 29, 2017, 9:17 a.m. UTC
Instead of just updating statistics, have it actually do the work
instead of leaving that job to the call site.

Also: skip the samples by updating the frame data pointers
instead of moving the samples. More efficient and avoid writing
into shared frames.
Found-By: Muhammad Faiz <mfcc64@gmail.com>

Signed-off-by: Nicolas George <george@nsup.org>
---
 libavfilter/avfilter.c   |  8 +-------
 libavfilter/framequeue.c | 27 +++++++++++++++++++++++++++
 libavfilter/framequeue.h | 11 +++++------
 3 files changed, 33 insertions(+), 13 deletions(-)

Comments

Muhammad Faiz Jan. 29, 2017, 1:58 p.m. UTC | #1
On 1/29/17, Nicolas George <george@nsup.org> wrote:
> Instead of just updating statistics, have it actually do the work
> instead of leaving that job to the call site.
>
> Also: skip the samples by updating the frame data pointers
> instead of moving the samples. More efficient and avoid writing
> into shared frames.
> Found-By: Muhammad Faiz <mfcc64@gmail.com>
>
> Signed-off-by: Nicolas George <george@nsup.org>
> ---
>  libavfilter/avfilter.c   |  8 +-------
>  libavfilter/framequeue.c | 27 +++++++++++++++++++++++++++
>  libavfilter/framequeue.h | 11 +++++------
>  3 files changed, 33 insertions(+), 13 deletions(-)
>

LGTM

Thank's
Nicolas George Jan. 29, 2017, 5:54 p.m. UTC | #2
Le decadi 10 pluviôse, an CCXXV, Muhammad Faiz a écrit :
> LGTM

Thanks, pushed.

Regards,
Kyle Swanson April 25, 2017, 2:42 p.m. UTC | #3
Hi,

On Sun, Jan 29, 2017 at 11:54 AM, Nicolas George <george@nsup.org> wrote:
>
> Le decadi 10 pluviôse, an CCXXV, Muhammad Faiz a écrit :
> > LGTM
>
> Thanks, pushed.
>
> Regards,
>
> --
>   Nicolas George
>
> _______________________________________________
> ffmpeg-devel mailing list
> ffmpeg-devel@ffmpeg.org
> http://ffmpeg.org/mailman/listinfo/ffmpeg-devel
>

Forwarding here so it doesn't get lost in trac. It appears that this
patch caused a bug: https://trac.ffmpeg.org/ticket/6349#comment:3

Thanks,
Kyle
Muhammad Faiz April 26, 2017, 10:18 a.m. UTC | #4
On Tue, Apr 25, 2017 at 9:42 PM, Kyle Swanson <k@ylo.ph> wrote:
> Hi,
>
> On Sun, Jan 29, 2017 at 11:54 AM, Nicolas George <george@nsup.org> wrote:
>>
>> Le decadi 10 pluviôse, an CCXXV, Muhammad Faiz a écrit :
>> > LGTM
>>
>> Thanks, pushed.
>>
>> Regards,
>>
>> --
>>   Nicolas George
>>
>> _______________________________________________
>> ffmpeg-devel mailing list
>> ffmpeg-devel@ffmpeg.org
>> http://ffmpeg.org/mailman/listinfo/ffmpeg-devel
>>
>
> Forwarding here so it doesn't get lost in trac. It appears that this
> patch caused a bug: https://trac.ffmpeg.org/ticket/6349#comment:3

a patch is posted

thx
diff mbox

Patch

diff --git a/libavfilter/avfilter.c b/libavfilter/avfilter.c
index c12d4912a8..b431990edc 100644
--- a/libavfilter/avfilter.c
+++ b/libavfilter/avfilter.c
@@ -1235,13 +1235,7 @@  static int take_samples(AVFilterLink *link, unsigned min, unsigned max,
         frame = ff_framequeue_peek(&link->fifo, 0);
         av_samples_copy(buf->extended_data, frame->extended_data, p, 0, n,
                         link->channels, link->format);
-        frame->nb_samples -= n;
-        av_samples_copy(frame->extended_data, frame->extended_data, 0, n,
-                        frame->nb_samples, link->channels, link->format);
-        if (frame->pts != AV_NOPTS_VALUE)
-            frame->pts += av_rescale_q(n, av_make_q(1, link->sample_rate), link->time_base);
-        ff_framequeue_update_peeked(&link->fifo, 0);
-        ff_framequeue_skip_samples(&link->fifo, n);
+        ff_framequeue_skip_samples(&link->fifo, n, link->time_base);
     }
 
     *rframe = buf;
diff --git a/libavfilter/framequeue.c b/libavfilter/framequeue.c
index a4ffa86c95..26bfa49967 100644
--- a/libavfilter/framequeue.c
+++ b/libavfilter/framequeue.c
@@ -121,3 +121,30 @@  AVFrame *ff_framequeue_peek(FFFrameQueue *fq, size_t idx)
     check_consistency(fq);
     return b->frame;
 }
+
+void ff_framequeue_skip_samples(FFFrameQueue *fq, size_t samples, AVRational time_base)
+{
+    FFFrameBucket *b;
+    size_t bytes;
+    int planar, planes, i;
+
+    check_consistency(fq);
+    av_assert1(fq->queued);
+    b = bucket(fq, 0);
+    av_assert1(samples < b->frame->nb_samples);
+    planar = av_sample_fmt_is_planar(b->frame->format);
+    planes = planar ? b->frame->channels : 1;
+    bytes = samples * av_get_bytes_per_sample(b->frame->format);
+    if (!planar)
+        bytes *= b->frame->channels;
+    if (b->frame->pts != AV_NOPTS_VALUE)
+        b->frame->pts += av_rescale_q(samples, av_make_q(1, b->frame->sample_rate), time_base);
+    b->frame->nb_samples -= samples;
+    b->frame->linesize[0] -= bytes;
+    for (i = 0; i < planes; i++)
+        b->frame->extended_data[i] += bytes;
+    for (i = 0; i < planes && i < AV_NUM_DATA_POINTERS; i++)
+        b->frame->data[i] = b->frame->extended_data[i];
+    fq->total_samples_tail += samples;
+    ff_framequeue_update_peeked(fq, 0);
+}
diff --git a/libavfilter/framequeue.h b/libavfilter/framequeue.h
index f5ef744638..5aa2c725a7 100644
--- a/libavfilter/framequeue.h
+++ b/libavfilter/framequeue.h
@@ -161,14 +161,13 @@  static inline void ff_framequeue_update_peeked(FFFrameQueue *fq, size_t idx)
 }
 
 /**
- * Update the sample count in the queue.
+ * Skip samples from the first frame in the queue.
  *
  * This function must be used when the first frame was accessed using
- * ff_framequeue_peek() and samples were removed from it.
+ * ff_framequeue_peek() and samples were consumed from it.
+ * It adapts the data pointers and timestamps of the head frame to account
+ * for the skipped samples.
  */
-static inline void ff_framequeue_skip_samples(FFFrameQueue *fq, size_t n)
-{
-    fq->total_samples_tail += n;
-}
+void ff_framequeue_skip_samples(FFFrameQueue *fq, size_t samples, AVRational time_base);
 
 #endif /* AVFILTER_FRAMEQUEUE_H */