summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--libavfilter/vf_vpp_qsv.c59
1 files changed, 47 insertions, 12 deletions
diff --git a/libavfilter/vf_vpp_qsv.c b/libavfilter/vf_vpp_qsv.c
index ab58a5777e..5c96703fd3 100644
--- a/libavfilter/vf_vpp_qsv.c
+++ b/libavfilter/vf_vpp_qsv.c
@@ -26,6 +26,7 @@
#include "libavutil/opt.h"
#include "libavutil/eval.h"
#include "libavutil/hwcontext.h"
+#include "libavutil/hwcontext_qsv.h"
#include "libavutil/pixdesc.h"
#include "libavutil/mathematics.h"
@@ -139,8 +140,9 @@ static const AVOption options[] = {
{ "height", "Output video height", OFFSET(oh), AV_OPT_TYPE_STRING, { .str="w*ch/cw" }, 0, 255, .flags = FLAGS },
{ "format", "Output pixel format", OFFSET(output_format_str), AV_OPT_TYPE_STRING, { .str = "same" }, .flags = FLAGS },
{ "async_depth", "Internal parallelization depth, the higher the value the higher the latency.", OFFSET(async_depth), AV_OPT_TYPE_INT, { .i64 = 0 }, 0, INT_MAX, .flags = FLAGS },
+#ifdef QSV_HAVE_SCALING_CONFIG
{ "scale_mode", "scale mode: 0=auto, 1=low power, 2=high quality", OFFSET(scale_mode), AV_OPT_TYPE_INT, { .i64 = MFX_SCALING_MODE_DEFAULT }, MFX_SCALING_MODE_DEFAULT, MFX_SCALING_MODE_QUALITY, .flags = FLAGS, "scale mode" },
-
+#endif
{ NULL }
};
@@ -297,6 +299,32 @@ static int config_input(AVFilterLink *inlink)
return 0;
}
+static mfxStatus get_mfx_version(const AVFilterContext *ctx, mfxVersion *mfx_version)
+{
+ const AVFilterLink *inlink = ctx->inputs[0];
+ AVBufferRef *device_ref;
+ AVHWDeviceContext *device_ctx;
+ AVQSVDeviceContext *device_hwctx;
+
+ if (inlink->hw_frames_ctx) {
+ AVHWFramesContext *frames_ctx = (AVHWFramesContext *)inlink->hw_frames_ctx->data;
+ device_ref = frames_ctx->device_ref;
+ } else if (ctx->hw_device_ctx) {
+ device_ref = ctx->hw_device_ctx;
+ } else {
+ // Unavailable hw context doesn't matter in pass-through mode,
+ // so don't error here but let runtime version checks fail by setting to 0.0
+ mfx_version->Major = 0;
+ mfx_version->Minor = 0;
+ return MFX_ERR_NONE;
+ }
+
+ device_ctx = (AVHWDeviceContext *)device_ref->data;
+ device_hwctx = device_ctx->hwctx;
+
+ return MFXQueryVersion(device_hwctx->session, mfx_version);
+}
+
static int config_output(AVFilterLink *outlink)
{
AVFilterContext *ctx = outlink->src;
@@ -304,6 +332,7 @@ static int config_output(AVFilterLink *outlink)
QSVVPPParam param = { NULL };
QSVVPPCrop crop = { 0 };
mfxExtBuffer *ext_buf[ENH_FILTERS_COUNT];
+ mfxVersion mfx_version;
AVFilterLink *inlink = ctx->inputs[0];
enum AVPixelFormat in_format;
@@ -317,6 +346,11 @@ static int config_output(AVFilterLink *outlink)
param.ext_buf = ext_buf;
param.async_depth = vpp->async_depth;
+ if (get_mfx_version(ctx, &mfx_version) != MFX_ERR_NONE) {
+ av_log(ctx, AV_LOG_ERROR, "Failed to query mfx version.\n");
+ return AVERROR(EINVAL);
+ }
+
if (inlink->format == AV_PIX_FMT_QSV) {
if (!inlink->hw_frames_ctx || !inlink->hw_frames_ctx->data)
return AVERROR(EINVAL);
@@ -467,19 +501,20 @@ static int config_output(AVFilterLink *outlink)
#endif
}
- if (inlink->w != outlink->w || inlink->h != outlink->h) {
#ifdef QSV_HAVE_SCALING_CONFIG
- memset(&vpp->scale_conf, 0, sizeof(mfxExtVPPScaling));
- vpp->scale_conf.Header.BufferId = MFX_EXTBUFF_VPP_SCALING;
- vpp->scale_conf.Header.BufferSz = sizeof(mfxExtVPPScaling);
- vpp->scale_conf.ScalingMode = vpp->scale_mode;
-
- param.ext_buf[param.num_ext_buf++] = (mfxExtBuffer*)&vpp->scale_conf;
-#else
- av_log(ctx, AV_LOG_WARNING, "The QSV VPP Scale option is "
- "not supported with this MSDK version.\n");
-#endif
+ if (inlink->w != outlink->w || inlink->h != outlink->h) {
+ if (QSV_RUNTIME_VERSION_ATLEAST(mfx_version, 1, 19)) {
+ memset(&vpp->scale_conf, 0, sizeof(mfxExtVPPScaling));
+ vpp->scale_conf.Header.BufferId = MFX_EXTBUFF_VPP_SCALING;
+ vpp->scale_conf.Header.BufferSz = sizeof(mfxExtVPPScaling);
+ vpp->scale_conf.ScalingMode = vpp->scale_mode;
+
+ param.ext_buf[param.num_ext_buf++] = (mfxExtBuffer*)&vpp->scale_conf;
+ } else
+ av_log(ctx, AV_LOG_WARNING, "The QSV VPP Scale option is "
+ "not supported with this MSDK version.\n");
}
+#endif
if (vpp->use_frc || vpp->use_crop || vpp->deinterlace || vpp->denoise ||
vpp->detail || vpp->procamp || vpp->rotate || vpp->hflip ||