From: Andriy Gelman <andriy.gel...@gmail.com> Currently if the frame buffers are full, the frame is unrefed and dropped. Instead buffer the frame so that it is enqueued in the following v4l2_receive_packet() call. The behavior was observed on DragonBoard 410c.
Signed-off-by: Andriy Gelman <andriy.gel...@gmail.com> --- libavcodec/v4l2_m2m.c | 1 + libavcodec/v4l2_m2m_enc.c | 8 ++++++-- 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/libavcodec/v4l2_m2m.c b/libavcodec/v4l2_m2m.c index d8d872ea099..6b545045100 100644 --- a/libavcodec/v4l2_m2m.c +++ b/libavcodec/v4l2_m2m.c @@ -329,6 +329,7 @@ static void v4l2_m2m_destroy_context(void *opaque, uint8_t *context) sem_destroy(&s->refsync); close(s->fd); + av_frame_unref(s->frame); av_frame_free(&s->frame); av_free(s); diff --git a/libavcodec/v4l2_m2m_enc.c b/libavcodec/v4l2_m2m_enc.c index 56df4286add..6d74c4c083d 100644 --- a/libavcodec/v4l2_m2m_enc.c +++ b/libavcodec/v4l2_m2m_enc.c @@ -295,16 +295,20 @@ static int v4l2_receive_packet(AVCodecContext *avctx, AVPacket *avpkt) if (s->draining) goto dequeue; + if (!frame->buf[0]) { ret = ff_encode_get_frame(avctx, frame); if (ret < 0 && ret != AVERROR_EOF) return ret; if (ret == AVERROR_EOF) frame = NULL; + } ret = v4l2_send_frame(avctx, frame); - av_frame_unref(frame); - if (ret < 0) + if (ret != AVERROR(EAGAIN)) + av_frame_unref(frame); + + if (ret < 0 && ret != AVERROR(EAGAIN)) return ret; if (!output->streamon) { -- 2.27.0 _______________________________________________ ffmpeg-devel mailing list ffmpeg-devel@ffmpeg.org https://ffmpeg.org/mailman/listinfo/ffmpeg-devel To unsubscribe, visit link above, or email ffmpeg-devel-requ...@ffmpeg.org with subject "unsubscribe".