hwcontext_qsv: Support derivation from child devices
This commit is contained in:
parent
e669db7610
commit
aa51bb3d27
@ -792,21 +792,96 @@ static mfxIMPL choose_implementation(const char *device)
|
|||||||
return impl;
|
return impl;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int qsv_device_create(AVHWDeviceContext *ctx, const char *device,
|
static int qsv_device_derive_from_child(AVHWDeviceContext *ctx,
|
||||||
AVDictionary *opts, int flags)
|
mfxIMPL implementation,
|
||||||
|
AVHWDeviceContext *child_device_ctx,
|
||||||
|
int flags)
|
||||||
{
|
{
|
||||||
AVQSVDeviceContext *hwctx = ctx->hwctx;
|
AVQSVDeviceContext *hwctx = ctx->hwctx;
|
||||||
QSVDevicePriv *priv;
|
QSVDeviceContext *s = ctx->internal->priv;
|
||||||
enum AVHWDeviceType child_device_type;
|
|
||||||
AVDictionaryEntry *e;
|
|
||||||
|
|
||||||
mfxVersion ver = { { 3, 1 } };
|
mfxVersion ver = { { 3, 1 } };
|
||||||
mfxIMPL impl;
|
|
||||||
mfxHDL handle;
|
mfxHDL handle;
|
||||||
mfxHandleType handle_type;
|
mfxHandleType handle_type;
|
||||||
mfxStatus err;
|
mfxStatus err;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
|
switch (child_device_ctx->type) {
|
||||||
|
#if CONFIG_VAAPI
|
||||||
|
case AV_HWDEVICE_TYPE_VAAPI:
|
||||||
|
{
|
||||||
|
AVVAAPIDeviceContext *child_device_hwctx = child_device_ctx->hwctx;
|
||||||
|
handle_type = MFX_HANDLE_VA_DISPLAY;
|
||||||
|
handle = (mfxHDL)child_device_hwctx->display;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
#endif
|
||||||
|
#if CONFIG_DXVA2
|
||||||
|
case AV_HWDEVICE_TYPE_DXVA2:
|
||||||
|
{
|
||||||
|
AVDXVA2DeviceContext *child_device_hwctx = child_device_ctx->hwctx;
|
||||||
|
handle_type = MFX_HANDLE_D3D9_DEVICE_MANAGER;
|
||||||
|
handle = (mfxHDL)child_device_hwctx->devmgr;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
#endif
|
||||||
|
default:
|
||||||
|
ret = AVERROR(ENOSYS);
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
|
||||||
|
err = MFXInit(implementation, &ver, &hwctx->session);
|
||||||
|
if (err != MFX_ERR_NONE) {
|
||||||
|
av_log(ctx, AV_LOG_ERROR, "Error initializing an MFX session: "
|
||||||
|
"%d.\n", err);
|
||||||
|
ret = AVERROR_UNKNOWN;
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
|
||||||
|
err = MFXVideoCORE_SetHandle(hwctx->session, handle_type, handle);
|
||||||
|
if (err != MFX_ERR_NONE) {
|
||||||
|
av_log(ctx, AV_LOG_ERROR, "Error setting child device handle: "
|
||||||
|
"%d\n", err);
|
||||||
|
ret = AVERROR_UNKNOWN;
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
|
||||||
|
ret = qsv_device_init(ctx);
|
||||||
|
if (ret < 0)
|
||||||
|
goto fail;
|
||||||
|
if (s->handle_type != handle_type) {
|
||||||
|
av_log(ctx, AV_LOG_ERROR, "Error in child device handle setup: "
|
||||||
|
"type mismatch (%d != %d).\n", s->handle_type, handle_type);
|
||||||
|
err = AVERROR_UNKNOWN;
|
||||||
|
goto fail;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
fail:
|
||||||
|
if (hwctx->session)
|
||||||
|
MFXClose(hwctx->session);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int qsv_device_derive(AVHWDeviceContext *ctx,
|
||||||
|
AVHWDeviceContext *child_device_ctx, int flags)
|
||||||
|
{
|
||||||
|
return qsv_device_derive_from_child(ctx, MFX_IMPL_HARDWARE_ANY,
|
||||||
|
child_device_ctx, flags);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int qsv_device_create(AVHWDeviceContext *ctx, const char *device,
|
||||||
|
AVDictionary *opts, int flags)
|
||||||
|
{
|
||||||
|
QSVDevicePriv *priv;
|
||||||
|
enum AVHWDeviceType child_device_type;
|
||||||
|
AVHWDeviceContext *child_device;
|
||||||
|
AVDictionaryEntry *e;
|
||||||
|
|
||||||
|
mfxIMPL impl;
|
||||||
|
int ret;
|
||||||
|
|
||||||
priv = av_mallocz(sizeof(*priv));
|
priv = av_mallocz(sizeof(*priv));
|
||||||
if (!priv)
|
if (!priv)
|
||||||
return AVERROR(ENOMEM);
|
return AVERROR(ENOMEM);
|
||||||
@ -830,32 +905,11 @@ static int qsv_device_create(AVHWDeviceContext *ctx, const char *device,
|
|||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
return ret;
|
return ret;
|
||||||
|
|
||||||
{
|
child_device = (AVHWDeviceContext*)priv->child_device_ctx->data;
|
||||||
AVHWDeviceContext *child_device_ctx = (AVHWDeviceContext*)priv->child_device_ctx->data;
|
|
||||||
#if CONFIG_VAAPI
|
|
||||||
AVVAAPIDeviceContext *child_device_hwctx = child_device_ctx->hwctx;
|
|
||||||
handle_type = MFX_HANDLE_VA_DISPLAY;
|
|
||||||
handle = (mfxHDL)child_device_hwctx->display;
|
|
||||||
#elif CONFIG_DXVA2
|
|
||||||
AVDXVA2DeviceContext *child_device_hwctx = child_device_ctx->hwctx;
|
|
||||||
handle_type = MFX_HANDLE_D3D9_DEVICE_MANAGER;
|
|
||||||
handle = (mfxHDL)child_device_hwctx->devmgr;
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
impl = choose_implementation(device);
|
impl = choose_implementation(device);
|
||||||
|
|
||||||
err = MFXInit(impl, &ver, &hwctx->session);
|
return qsv_device_derive_from_child(ctx, impl, child_device, 0);
|
||||||
if (err != MFX_ERR_NONE) {
|
|
||||||
av_log(ctx, AV_LOG_ERROR, "Error initializing an MFX session\n");
|
|
||||||
return AVERROR_UNKNOWN;
|
|
||||||
}
|
|
||||||
|
|
||||||
err = MFXVideoCORE_SetHandle(hwctx->session, handle_type, handle);
|
|
||||||
if (err != MFX_ERR_NONE)
|
|
||||||
return AVERROR_UNKNOWN;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const HWContextType ff_hwcontext_type_qsv = {
|
const HWContextType ff_hwcontext_type_qsv = {
|
||||||
@ -868,6 +922,7 @@ const HWContextType ff_hwcontext_type_qsv = {
|
|||||||
.frames_priv_size = sizeof(QSVFramesContext),
|
.frames_priv_size = sizeof(QSVFramesContext),
|
||||||
|
|
||||||
.device_create = qsv_device_create,
|
.device_create = qsv_device_create,
|
||||||
|
.device_derive = qsv_device_derive,
|
||||||
.device_init = qsv_device_init,
|
.device_init = qsv_device_init,
|
||||||
.frames_get_constraints = qsv_frames_get_constraints,
|
.frames_get_constraints = qsv_frames_get_constraints,
|
||||||
.frames_init = qsv_frames_init,
|
.frames_init = qsv_frames_init,
|
||||||
|
Loading…
x
Reference in New Issue
Block a user