[FFmpeg-cvslog] qsv{dec, enc}: use a struct as a memory id with internal memory allocator
Anton Khirnov
git at videolan.org
Fri Mar 31 00:06:09 EEST 2017
ffmpeg | branch: master | Anton Khirnov <anton at khirnov.net> | Wed Aug 10 08:29:23 2016 +0200| [00aeedd84105a17f414185bd33ecadebeddb3a27] | committer: Anton Khirnov
qsv{dec,enc}: use a struct as a memory id with internal memory allocator
This will allow implementing the allocator more fully, which is needed
by the HEVC encoder plugin with video memory input.
Signed-off-by: Maxym Dmytrychenko <maxym.dmytrychenko at intel.com>
> http://git.videolan.org/gitweb.cgi/ffmpeg.git/?a=commit;h=00aeedd84105a17f414185bd33ecadebeddb3a27
---
libavcodec/qsv.c | 26 +++++++++++++++++++++++---
libavcodec/qsv_internal.h | 10 ++++++++--
libavcodec/qsvdec.c | 8 ++++++++
libavcodec/qsvenc.c | 8 ++++++++
4 files changed, 47 insertions(+), 5 deletions(-)
diff --git a/libavcodec/qsv.c b/libavcodec/qsv.c
index 9119586..f433b8b 100644
--- a/libavcodec/qsv.c
+++ b/libavcodec/qsv.c
@@ -144,6 +144,17 @@ int ff_qsv_map_pixfmt(enum AVPixelFormat format, uint32_t *fourcc)
}
}
+int ff_qsv_find_surface_idx(QSVFramesContext *ctx, QSVFrame *frame)
+{
+ int i;
+ for (i = 0; i < ctx->nb_mids; i++) {
+ QSVMid *mid = &ctx->mids[i];
+ if (mid->handle == frame->surface.Data.MemId)
+ return i;
+ }
+ return AVERROR_BUG;
+}
+
static int qsv_load_plugins(mfxSession session, const char *load_plugins,
void *logctx)
{
@@ -244,6 +255,7 @@ static mfxStatus qsv_frame_alloc(mfxHDL pthis, mfxFrameAllocRequest *req,
QSVFramesContext *ctx = pthis;
mfxFrameInfo *i = &req->Info;
mfxFrameInfo *i1 = &ctx->info;
+ int j;
if (!(req->Type & MFX_MEMTYPE_VIDEO_MEMORY_DECODER_TARGET) ||
!(req->Type & (MFX_MEMTYPE_FROM_DECODE | MFX_MEMTYPE_FROM_ENCODE)) ||
@@ -258,7 +270,13 @@ static mfxStatus qsv_frame_alloc(mfxHDL pthis, mfxFrameAllocRequest *req,
return MFX_ERR_UNSUPPORTED;
}
- resp->mids = ctx->mids;
+ resp->mids = av_mallocz_array(ctx->nb_mids, sizeof(*resp->mids));
+ if (!resp->mids)
+ return MFX_ERR_MEMORY_ALLOC;
+
+ for (j = 0; j < ctx->nb_mids; j++)
+ resp->mids[j] = &ctx->mids[j];
+
resp->NumFrameActual = ctx->nb_mids;
return MFX_ERR_NONE;
@@ -266,6 +284,7 @@ static mfxStatus qsv_frame_alloc(mfxHDL pthis, mfxFrameAllocRequest *req,
static mfxStatus qsv_frame_free(mfxHDL pthis, mfxFrameAllocResponse *resp)
{
+ av_freep(&resp->mids);
return MFX_ERR_NONE;
}
@@ -281,7 +300,8 @@ static mfxStatus qsv_frame_unlock(mfxHDL pthis, mfxMemId mid, mfxFrameData *ptr)
static mfxStatus qsv_frame_get_hdl(mfxHDL pthis, mfxMemId mid, mfxHDL *hdl)
{
- *hdl = mid;
+ QSVMid *qsv_mid = (QSVMid*)mid;
+ *hdl = qsv_mid->handle;
return MFX_ERR_NONE;
}
@@ -365,7 +385,7 @@ int ff_qsv_init_session_hwcontext(AVCodecContext *avctx, mfxSession *psession,
qsv_frames_ctx->info = frames_hwctx->surfaces[0].Info;
qsv_frames_ctx->nb_mids = frames_hwctx->nb_surfaces;
for (i = 0; i < frames_hwctx->nb_surfaces; i++)
- qsv_frames_ctx->mids[i] = frames_hwctx->surfaces[i].Data.MemId;
+ qsv_frames_ctx->mids[i].handle = frames_hwctx->surfaces[i].Data.MemId;
err = MFXVideoCORE_SetFrameAllocator(session, &frame_allocator);
if (err != MFX_ERR_NONE)
diff --git a/libavcodec/qsv_internal.h b/libavcodec/qsv_internal.h
index 5b015a6..8b69891 100644
--- a/libavcodec/qsv_internal.h
+++ b/libavcodec/qsv_internal.h
@@ -36,6 +36,10 @@
(MFX_VERSION_MAJOR > (MAJOR) || \
MFX_VERSION_MAJOR == (MAJOR) && MFX_VERSION_MINOR >= (MINOR))
+typedef struct QSVMid {
+ mfxHDL handle;
+} QSVMid;
+
typedef struct QSVFrame {
AVFrame *frame;
mfxFrameSurface1 surface;
@@ -49,8 +53,8 @@ typedef struct QSVFrame {
typedef struct QSVFramesContext {
AVBufferRef *hw_frames_ctx;
mfxFrameInfo info;
- mfxMemId *mids;
- int nb_mids;
+ QSVMid *mids;
+ int nb_mids;
} QSVFramesContext;
/**
@@ -75,4 +79,6 @@ int ff_qsv_init_session_hwcontext(AVCodecContext *avctx, mfxSession *session,
QSVFramesContext *qsv_frames_ctx,
const char *load_plugins, int opaque);
+int ff_qsv_find_surface_idx(QSVFramesContext *ctx, QSVFrame *frame);
+
#endif /* AVCODEC_QSV_INTERNAL_H */
diff --git a/libavcodec/qsvdec.c b/libavcodec/qsvdec.c
index 8353d25..398c319 100644
--- a/libavcodec/qsvdec.c
+++ b/libavcodec/qsvdec.c
@@ -188,6 +188,14 @@ static int alloc_frame(AVCodecContext *avctx, QSVContext *q, QSVFrame *frame)
frame->surface.Data.UV = frame->frame->data[1];
}
+ if (q->frames_ctx.mids) {
+ ret = ff_qsv_find_surface_idx(&q->frames_ctx, frame);
+ if (ret < 0)
+ return ret;
+
+ frame->surface.Data.MemId = &q->frames_ctx.mids[ret];
+ }
+
frame->used = 1;
return 0;
diff --git a/libavcodec/qsvenc.c b/libavcodec/qsvenc.c
index 3d99e84..be8cbee 100644
--- a/libavcodec/qsvenc.c
+++ b/libavcodec/qsvenc.c
@@ -872,6 +872,14 @@ static int submit_frame(QSVEncContext *q, const AVFrame *frame,
return ret;
qf->surface = *(mfxFrameSurface1*)qf->frame->data[3];
+
+ if (q->frames_ctx.mids) {
+ ret = ff_qsv_find_surface_idx(&q->frames_ctx, qf);
+ if (ret < 0)
+ return ret;
+
+ qf->surface.Data.MemId = &q->frames_ctx.mids[ret];
+ }
} else {
/* make a copy if the input is not padded as libmfx requires */
if (frame->height & 31 || frame->linesize[0] & (q->width_align - 1)) {
More information about the ffmpeg-cvslog
mailing list