Re: [FFmpeg-devel] [PATCH 4/4] qsv: Merge libav implementation
On 31/10/16 13:50, Hendrik Leppkes wrote: > On Wed, Oct 26, 2016 at 9:50 PM, Mark Thompsonwrote: >> Merged as-at libav 398f015, and therefore includes outstanding >> skipped merges 04b17ff and 130e1f1. >> >> All features not in libav are preserved, and no options change. >> --- > > LGTM, this should make further work on this much easier and bring it > back to a point where its actually stable - and integrates with the > existing HW landscape (hwcontext et al). Applied. Thank you to everyone who assisted with testing and reviewing this series. - Mark ___ ffmpeg-devel mailing list ffmpeg-devel@ffmpeg.org http://ffmpeg.org/mailman/listinfo/ffmpeg-devel
Re: [FFmpeg-devel] [PATCH 4/4] qsv: Merge libav implementation
On Wed, Oct 26, 2016 at 9:50 PM, Mark Thompsonwrote: > Merged as-at libav 398f015, and therefore includes outstanding > skipped merges 04b17ff and 130e1f1. > > All features not in libav are preserved, and no options change. > --- LGTM, this should make further work on this much easier and bring it back to a point where its actually stable - and integrates with the existing HW landscape (hwcontext et al). - Hendrik ___ ffmpeg-devel mailing list ffmpeg-devel@ffmpeg.org http://ffmpeg.org/mailman/listinfo/ffmpeg-devel
[FFmpeg-devel] [PATCH 4/4] qsv: Merge libav implementation
Merged as-at libav 398f015, and therefore includes outstanding skipped merges 04b17ff and 130e1f1. All features not in libav are preserved, and no options change. --- v4 (patch 4/4 only, the others are unchanged). Changes from v3: - Revert to using the software decoder plugin by default for H.265; apparently the hardware decoder plugin segfaults if you load on unsupported hardware, so make the user request it explicitly. - Never pass FF_UNKNOWN_LEVEL to libmfx (MFX_LEVEL_UNKNOWN has a different value). - Minor cosmetics to make merging easier. libavcodec/qsv.c | 333 --- libavcodec/qsv_internal.h | 40 ++-- libavcodec/qsvdec.c | 568 +++--- libavcodec/qsvdec.h | 30 +-- libavcodec/qsvdec_h2645.c | 29 ++- libavcodec/qsvdec_mpeg2.c | 85 ++- libavcodec/qsvdec_vc1.c | 89 +++- libavcodec/qsvenc.c | 160 +++-- libavcodec/qsvenc.h | 6 +- libavcodec/qsvenc_h264.c | 3 +- 10 files changed, 746 insertions(+), 597 deletions(-) diff --git a/libavcodec/qsv.c b/libavcodec/qsv.c index 11d453d..efd7cea 100644 --- a/libavcodec/qsv.c +++ b/libavcodec/qsv.c @@ -25,7 +25,10 @@ #include #include "libavutil/avstring.h" +#include "libavutil/common.h" #include "libavutil/error.h" +#include "libavutil/hwcontext.h" +#include "libavutil/hwcontext_qsv.h" #include "avcodec.h" #include "qsv_internal.h" @@ -51,6 +54,22 @@ int ff_qsv_codec_id_to_mfx(enum AVCodecID codec_id) return AVERROR(ENOSYS); } +int ff_qsv_profile_to_mfx(enum AVCodecID codec_id, int profile) +{ +if (profile == FF_PROFILE_UNKNOWN) +return MFX_PROFILE_UNKNOWN; +switch (codec_id) { +case AV_CODEC_ID_H264: +case AV_CODEC_ID_HEVC: +return profile; +case AV_CODEC_ID_VC1: +return 4 * profile + 1; +case AV_CODEC_ID_MPEG2VIDEO: +return 0x10 * profile; +} +return MFX_PROFILE_UNKNOWN; +} + int ff_qsv_error(int mfx_err) { switch (mfx_err) { @@ -85,90 +104,58 @@ int ff_qsv_error(int mfx_err) return AVERROR_UNKNOWN; } } -static int ff_qsv_set_display_handle(AVCodecContext *avctx, QSVSession *qs) + +static int qsv_load_plugins(mfxSession session, const char *load_plugins, +void *logctx) { -// this code is only required for Linux. It searches for a valid -// display handle. First in /dev/dri/renderD then in /dev/dri/card -#ifdef AVCODEC_QSV_LINUX_SESSION_HANDLE -// VAAPI display handle -int ret = 0; -VADisplay va_dpy = NULL; -VAStatus va_res = VA_STATUS_SUCCESS; -int major_version = 0, minor_version = 0; -int fd = -1; -char adapterpath[256]; -int adapter_num; - -qs->fd_display = -1; -qs->va_display = NULL; - -//search for valid graphics device -for (adapter_num = 0;adapter_num < 6;adapter_num++) { - -if (adapter_num<3) { -snprintf(adapterpath,sizeof(adapterpath), -"/dev/dri/renderD%d", adapter_num+128); -} else { -snprintf(adapterpath,sizeof(adapterpath), -"/dev/dri/card%d", adapter_num-3); -} +if (!load_plugins || !*load_plugins) +return 0; -fd = open(adapterpath, O_RDWR); -if (fd < 0) { -av_log(avctx, AV_LOG_ERROR, -"mfx init: %s fd open failed\n", adapterpath); -continue; -} +while (*load_plugins) { +mfxPluginUID uid; +mfxStatus ret; +int i, err = 0; -va_dpy = vaGetDisplayDRM(fd); -if (!va_dpy) { -av_log(avctx, AV_LOG_ERROR, -"mfx init: %s vaGetDisplayDRM failed\n", adapterpath); -close(fd); -continue; +char *plugin = av_get_token(_plugins, ":"); +if (!plugin) +return AVERROR(ENOMEM); +if (strlen(plugin) != 2 * sizeof(uid.Data)) { +av_log(logctx, AV_LOG_ERROR, "Invalid plugin UID length\n"); +err = AVERROR(EINVAL); +goto load_plugin_fail; } -va_res = vaInitialize(va_dpy, _version, _version); -if (VA_STATUS_SUCCESS != va_res) { -av_log(avctx, AV_LOG_ERROR, -"mfx init: %s vaInitialize failed\n", adapterpath); -close(fd); -fd = -1; -continue; -} else { -av_log(avctx, AV_LOG_VERBOSE, -"mfx initialization: %s vaInitialize successful\n",adapterpath); -qs->fd_display = fd; -qs->va_display = va_dpy; -ret = MFXVideoCORE_SetHandle(qs->session, - (mfxHandleType)MFX_HANDLE_VA_DISPLAY, (mfxHDL)va_dpy); -if (ret < 0) { -av_log(avctx, AV_LOG_ERROR, -"Error %d during set display handle\n", ret); -return ff_qsv_error(ret); +for (i = 0; i < sizeof(uid.Data); i++) { +err = sscanf(plugin + 2 * i, "%2hhx",
[FFmpeg-devel] [PATCH 4/4] qsv: Merge libav implementation
Merged as-at libav 398f015, and therefore includes outstanding skipped merges 04b17ff and 130e1f1. All features not in libav are preserved, and no options change. --- v3. Changes from v2: - Profile seems to be required by the decoder in some cases; always pass in the correct value. - Fix parsing for MPEG-2; now works with streams which are not exactly macroblock-aligned. - Fix H.265 parsing when the decoder is enabled. - Add H.265 HW decode plugin ID for MSS 2017. libavcodec/qsv.c | 333 --- libavcodec/qsv_internal.h | 38 ++-- libavcodec/qsvdec.c | 569 +++--- libavcodec/qsvdec.h | 30 +-- libavcodec/qsvdec_h2645.c | 29 ++- libavcodec/qsvdec_mpeg2.c | 85 ++- libavcodec/qsvdec_vc1.c | 89 +++- libavcodec/qsvenc.c | 158 +++-- libavcodec/qsvenc.h | 6 +- libavcodec/qsvenc_h264.c | 3 +- 10 files changed, 744 insertions(+), 596 deletions(-) diff --git a/libavcodec/qsv.c b/libavcodec/qsv.c index 11d453d..efd7cea 100644 --- a/libavcodec/qsv.c +++ b/libavcodec/qsv.c @@ -25,7 +25,10 @@ #include #include "libavutil/avstring.h" +#include "libavutil/common.h" #include "libavutil/error.h" +#include "libavutil/hwcontext.h" +#include "libavutil/hwcontext_qsv.h" #include "avcodec.h" #include "qsv_internal.h" @@ -51,6 +54,22 @@ int ff_qsv_codec_id_to_mfx(enum AVCodecID codec_id) return AVERROR(ENOSYS); } +int ff_qsv_profile_to_mfx(enum AVCodecID codec_id, int profile) +{ +if (profile == FF_PROFILE_UNKNOWN) +return MFX_PROFILE_UNKNOWN; +switch (codec_id) { +case AV_CODEC_ID_H264: +case AV_CODEC_ID_HEVC: +return profile; +case AV_CODEC_ID_VC1: +return 4 * profile + 1; +case AV_CODEC_ID_MPEG2VIDEO: +return 0x10 * profile; +} +return MFX_PROFILE_UNKNOWN; +} + int ff_qsv_error(int mfx_err) { switch (mfx_err) { @@ -85,90 +104,58 @@ int ff_qsv_error(int mfx_err) return AVERROR_UNKNOWN; } } -static int ff_qsv_set_display_handle(AVCodecContext *avctx, QSVSession *qs) + +static int qsv_load_plugins(mfxSession session, const char *load_plugins, +void *logctx) { -// this code is only required for Linux. It searches for a valid -// display handle. First in /dev/dri/renderD then in /dev/dri/card -#ifdef AVCODEC_QSV_LINUX_SESSION_HANDLE -// VAAPI display handle -int ret = 0; -VADisplay va_dpy = NULL; -VAStatus va_res = VA_STATUS_SUCCESS; -int major_version = 0, minor_version = 0; -int fd = -1; -char adapterpath[256]; -int adapter_num; - -qs->fd_display = -1; -qs->va_display = NULL; - -//search for valid graphics device -for (adapter_num = 0;adapter_num < 6;adapter_num++) { - -if (adapter_num<3) { -snprintf(adapterpath,sizeof(adapterpath), -"/dev/dri/renderD%d", adapter_num+128); -} else { -snprintf(adapterpath,sizeof(adapterpath), -"/dev/dri/card%d", adapter_num-3); -} +if (!load_plugins || !*load_plugins) +return 0; -fd = open(adapterpath, O_RDWR); -if (fd < 0) { -av_log(avctx, AV_LOG_ERROR, -"mfx init: %s fd open failed\n", adapterpath); -continue; -} +while (*load_plugins) { +mfxPluginUID uid; +mfxStatus ret; +int i, err = 0; -va_dpy = vaGetDisplayDRM(fd); -if (!va_dpy) { -av_log(avctx, AV_LOG_ERROR, -"mfx init: %s vaGetDisplayDRM failed\n", adapterpath); -close(fd); -continue; +char *plugin = av_get_token(_plugins, ":"); +if (!plugin) +return AVERROR(ENOMEM); +if (strlen(plugin) != 2 * sizeof(uid.Data)) { +av_log(logctx, AV_LOG_ERROR, "Invalid plugin UID length\n"); +err = AVERROR(EINVAL); +goto load_plugin_fail; } -va_res = vaInitialize(va_dpy, _version, _version); -if (VA_STATUS_SUCCESS != va_res) { -av_log(avctx, AV_LOG_ERROR, -"mfx init: %s vaInitialize failed\n", adapterpath); -close(fd); -fd = -1; -continue; -} else { -av_log(avctx, AV_LOG_VERBOSE, -"mfx initialization: %s vaInitialize successful\n",adapterpath); -qs->fd_display = fd; -qs->va_display = va_dpy; -ret = MFXVideoCORE_SetHandle(qs->session, - (mfxHandleType)MFX_HANDLE_VA_DISPLAY, (mfxHDL)va_dpy); -if (ret < 0) { -av_log(avctx, AV_LOG_ERROR, -"Error %d during set display handle\n", ret); -return ff_qsv_error(ret); +for (i = 0; i < sizeof(uid.Data); i++) { +err = sscanf(plugin + 2 * i, "%2hhx", uid.Data + i); +if (err != 1) { +av_log(logctx,