[vlc-commits] qsv: only enqueue packets that are successfully encoded
Steve Lhomme
git at videolan.org
Wed Apr 4 18:28:29 CEST 2018
vlc | branch: master | Steve Lhomme <robux4 at videolabs.io> | Mon Sep 4 14:58:36 2017 +0200| [37f415512eea877c2902784d07836ca228fd0e9f] | committer: Steve Lhomme
qsv: only enqueue packets that are successfully encoded
And fix leaks in case the packet won't be enqueued.
> http://git.videolan.org/gitweb.cgi/vlc.git/?a=commit;h=37f415512eea877c2902784d07836ca228fd0e9f
---
modules/codec/qsv.c | 47 ++++++++++++++++++++++++-----------------------
1 file changed, 24 insertions(+), 23 deletions(-)
diff --git a/modules/codec/qsv.c b/modules/codec/qsv.c
index 0226c3a1d3..074455e206 100644
--- a/modules/codec/qsv.c
+++ b/modules/codec/qsv.c
@@ -753,19 +753,23 @@ static block_t *qsv_synchronize_block(encoder_t *enc, async_task_t *task)
return block;
}
-static void qsv_queue_encode_picture(encoder_t *enc, picture_t *pic)
+static async_task_t *qsv_encode_picture(encoder_t *enc, picture_t *pic)
{
encoder_sys_t *sys = enc->p_sys;
- mfxStatus sts;
+ mfxStatus sts = MFX_ERR_MEMORY_ALLOC;
mfxFrameSurface1 *frame = NULL;
async_task_t *task = calloc(1, sizeof(*task));
if (unlikely(task == NULL))
- return;
+ goto done;
- if (!(task->syncp = calloc(1, sizeof(*task->syncp)))) {
- msg_Err(enc, "Unable to allocate syncpoint for encoder output");
- return;
+ /* Allocate block_t and prepare mfxBitstream for encoder */
+ if (!(task->block = block_Alloc(sys->params.mfx.BufferSizeInKB * 1000))) {
+ msg_Err(enc, "Unable to allocate block for encoder output");
+ goto done;
}
+ memset(&task->bs, 0, sizeof(task->bs));
+ task->bs.MaxLength = task->block->i_buffer;
+ task->bs.Data = task->block->p_buffer;
if (pic) {
/* To avoid qsv -> vlc timestamp conversion overflow, we use timestamp relative
@@ -777,23 +781,10 @@ static void qsv_queue_encode_picture(encoder_t *enc, picture_t *pic)
frame = qsv_frame_pool_Get(sys, pic);
if (!frame) {
msg_Warn(enc, "Unable to find an unlocked surface in the pool");
- free(task->syncp);
- task->syncp = NULL;
- return;
+ goto done;
}
}
- /* Allocate block_t and prepare mfxBitstream for encoder */
- if (!(task->block = block_Alloc(sys->params.mfx.BufferSizeInKB * 1000))) {
- msg_Err(enc, "Unable to allocate block for encoder output");
- free(task->syncp);
- task->syncp = NULL;
- return;
- }
- memset(&task->bs, 0, sizeof(task->bs));
- task->bs.MaxLength = task->block->i_buffer;
- task->bs.Data = task->block->p_buffer;
-
if (!(task->syncp = calloc(1, sizeof(*task->syncp)))) {
msg_Err(enc, "Unable to allocate syncpoint for encoder output");
goto done;
@@ -820,12 +811,19 @@ static void qsv_queue_encode_picture(encoder_t *enc, picture_t *pic)
msg_Dbg(enc, "Encoder feeding phase, more data is needed.");
else
msg_Dbg(enc, "Encoder is empty");
- else if (sts == MFX_ERR_NONE)
- async_task_t_fifo_Put(&sys->packets, task);
else if (sts < MFX_ERR_NONE) {
msg_Err(enc, "Encoder not ready or error (%d), trying a reset...", sts);
MFXVideoENCODE_Reset(sys->session, &sys->params);
}
+
+done:
+ if (sts < MFX_ERR_NONE || (task != NULL && !task->syncp)) {
+ if (task->block != NULL)
+ block_Release(task->block);
+ free(task);
+ task = NULL;
+ }
+ return task;
}
/*
@@ -839,9 +837,12 @@ static block_t *Encode(encoder_t *this, picture_t *pic)
{
encoder_t *enc = (encoder_t *)this;
encoder_sys_t *sys = enc->p_sys;
+ async_task_t *task;
block_t *block = NULL;
- qsv_queue_encode_picture( enc, pic );
+ task = qsv_encode_picture( enc, pic );
+ if (likely(task != NULL))
+ async_task_t_fifo_Put(&sys->packets, task);
if ( async_task_t_fifo_GetCount(&sys->packets) == sys->async_depth ||
(!pic && async_task_t_fifo_GetCount(&sys->packets)))
More information about the vlc-commits
mailing list