Re: [PATCH 2/2] vaapi: add support for DRM modifiers
"Lin, Shuicheng" <[email protected]>
| Newsgroups | gmane.comp.video.videolan.vlc.devel |
|---|---|
| Message-ID | <DM4PR11MB54564D34E2D43D279D7EC0BCEA5A9@DM4PR11MB5456.namprd11.prod.outlook.com> |
Hi, In order to fix the same issue in 3.0.x branch, I cherry-pick the 2 patches from master to 3.0.x. I confirm issue could be fixed in 3.0.x branch with the patch. I have done the "Check List" [0] for the patches. Anything else should I do in order to get the patch merged to the 3.0.x branch? Thanks. [0]: https://wiki.videolan.org/Sending_Patches_VLC/#Check_List Best Regards Shuicheng -----Original Message----- From: Lin, Shuicheng <[email protected]> Sent: Wednesday, January 19, 2022 12:25 AM To: [email protected] Cc: Landwerlin, Lionel G <[email protected]>; Thomas Guillem <[email protected]>; Lin, Shuicheng <[email protected]> Subject: [PATCH 2/2] vaapi: add support for DRM modifiers From: Lionel Landwerlin <[email protected]> DRM modifiers communicate a description of the data layout in the buffers exported/imported through various API. On Intel HW this exports tiling information as well as potential compression. Signed-off-by: Thomas Guillem <[email protected]> (cherry picked from commit 3633417edb6330c335c7d3602e255534979c05e7) Signed-off-by: Shuicheng Lin <[email protected]> --- modules/hw/vaapi/vlc_vaapi.c | 15 +++ modules/hw/vaapi/vlc_vaapi.h | 10 ++ modules/video_output/opengl/converter_vaapi.c | 92 +++++++++++++++++-- 3 files changed, 109 insertions(+), 8 deletions(-) diff --git a/modules/hw/vaapi/vlc_vaapi.c b/modules/hw/vaapi/vlc_vaapi.c index 6af4932dd5..cb6e1a1f07 100644 --- a/modules/hw/vaapi/vlc_vaapi.c +++ b/modules/hw/vaapi/vlc_vaapi.c @@ -733,3 +733,18 @@ vlc_vaapi_PicGetDisplay(picture_t *pic) return ((struct vaapi_pic_ctx *)pic->context)->picref->p_sys->instance->va_dpy; } + +#if VA_CHECK_VERSION(1, 1, 0) +int +vlc_vaapi_ExportSurfaceHandle(vlc_object_t *o, + VADisplay dpy, + VASurfaceID surface, + uint32_t mem_type, + uint32_t flags, + void *descriptor) { + VA_CALL(o, vaExportSurfaceHandle, dpy, surface, mem_type, flags, descriptor); + return VLC_SUCCESS; +error: return VLC_EGENERIC; +} +#endif diff --git a/modules/hw/vaapi/vlc_vaapi.h b/modules/hw/vaapi/vlc_vaapi.h index 98737c6929..c02f76a1a6 100644 --- a/modules/hw/vaapi/vlc_vaapi.h +++ b/modules/hw/vaapi/vlc_vaapi.h @@ -228,4 +228,14 @@ vlc_vaapi_IsChromaOpaque(int i_vlc_chroma) || i_vlc_chroma == VLC_CODEC_VAAPI_420_10BPP; } +#if VA_CHECK_VERSION(1, 1, 0) +int +vlc_vaapi_ExportSurfaceHandle(vlc_object_t *o, + VADisplay dpy, + VASurfaceID surface, + uint32_t mem_type, + uint32_t flags, + void *descriptor); #endif + #endif /* VLC_VAAPI_H */ diff --git a/modules/video_output/opengl/converter_vaapi.c b/modules/video_output/opengl/converter_vaapi.c index 8b2d2acbfc..cd842f711c 100644 --- a/modules/video_output/opengl/converter_vaapi.c +++ b/modules/video_output/opengl/converter_vaapi.c @@ -47,6 +47,14 @@ # include <fcntl.h> #endif +#define DRM_FORMAT_MOD_VENDOR_NONE 0 +#define DRM_FORMAT_RESERVED ((1ULL << 56) - 1) + +#define fourcc_mod_code(vendor, val) \ + ((((EGLuint64KHR)DRM_FORMAT_MOD_VENDOR_## vendor) << 56) | +((val) & 0x00ffffffffffffffULL)) + +#define DRM_FORMAT_MOD_INVALID fourcc_mod_code(NONE, +DRM_FORMAT_RESERVED) + struct priv { struct vlc_vaapi_instance *vainst; @@ -58,16 +66,23 @@ struct priv EGLint drm_fourccs[3]; struct { - picture_t * pic; - VAImage va_image; - VABufferInfo va_buffer_info; - void * egl_images[3]; + picture_t * pic; +#if VA_CHECK_VERSION(1, 1, 0) + /* VADRMPRIMESurfaceDescriptor carries modifier information + * (GPU tiling, compression, etc...) */ + VADRMPRIMESurfaceDescriptor va_surface_descriptor; #else + VABufferInfo va_buffer_info; +#endif + VAImage va_image; + void * egl_images[3]; } last; }; static EGLImageKHR vaegl_image_create(const opengl_tex_converter_t *tc, EGLint w, EGLint h, - EGLint fourcc, EGLint fd, EGLint offset, EGLint pitch) + EGLint fourcc, EGLint fd, EGLint offset, EGLint pitch, + EGLuint64KHR modifier) { EGLint attribs[] = { EGL_WIDTH, w, @@ -76,6 +91,8 @@ vaegl_image_create(const opengl_tex_converter_t *tc, EGLint w, EGLint h, EGL_DMA_BUF_PLANE0_FD_EXT, fd, EGL_DMA_BUF_PLANE0_OFFSET_EXT, offset, EGL_DMA_BUF_PLANE0_PITCH_EXT, pitch, + EGL_DMA_BUF_PLANE0_MODIFIER_LO_EXT, modifier & 0xffffffff, + EGL_DMA_BUF_PLANE0_MODIFIER_HI_EXT, modifier >> 32, EGL_NONE }; @@ -97,7 +114,12 @@ vaegl_release_last_pic(const opengl_tex_converter_t *tc, struct priv *priv) for (unsigned i = 0; i < priv->last.va_image.num_planes; ++i) vaegl_image_destroy(tc, priv->last.egl_images[i]); +#if VA_CHECK_VERSION(1, 1, 0) + for (unsigned i = 0; i < priv->last.va_surface_descriptor.num_objects; ++i) + close(priv->last.va_surface_descriptor.objects[i].fd); +#else vlc_vaapi_ReleaseBufferHandle(o, priv->vadpy, priv->last.va_image.buf); +#endif vlc_vaapi_DestroyImage(o, priv->vadpy, priv->last.va_image.image_id); @@ -161,14 +183,20 @@ tc_vaegl_update(const opengl_tex_converter_t *tc, GLuint *textures, struct priv *priv = tc->priv; vlc_object_t *o = VLC_OBJECT(tc->gl); VAImage va_image; +#if VA_CHECK_VERSION(1, 1, 0) + VADRMPRIMESurfaceDescriptor va_surface_descriptor; #else VABufferInfo va_buffer_info; +#endif EGLImageKHR egl_images[3] = { }; bool release_image = false, release_buffer_info = false; if (pic == priv->last.pic) { va_image = priv->last.va_image; - va_buffer_info = priv->last.va_buffer_info; +#if VA_CHECK_VERSION(1, 1, 0) + va_surface_descriptor = priv->last.va_surface_descriptor; +#endif for (unsigned i = 0; i < priv->last.va_image.num_planes; ++i) egl_images[i] = priv->last.egl_images[i]; } @@ -181,21 +209,55 @@ tc_vaegl_update(const opengl_tex_converter_t *tc, GLuint *textures, assert(va_image.format.fourcc == priv->fourcc); +#if VA_CHECK_VERSION(1, 1, 0) + if (vlc_vaapi_ExportSurfaceHandle(o, priv->vadpy, vlc_vaapi_PicGetSurface(pic), + VA_SURFACE_ATTRIB_MEM_TYPE_DRM_PRIME_2, 0, + &va_surface_descriptor)) + goto error; +#else va_buffer_info = (VABufferInfo) { .mem_type = VA_SURFACE_ATTRIB_MEM_TYPE_DRM_PRIME }; if (vlc_vaapi_AcquireBufferHandle(o, priv->vadpy, va_image.buf, &va_buffer_info)) goto error; +#endif release_buffer_info = true; } +#if VA_CHECK_VERSION(1, 1, 0) + for (unsigned i = 0; i < va_surface_descriptor.num_layers; ++i) + { + unsigned obj_idx = +va_surface_descriptor.layers[i].object_index[0]; + + /* Since we don't ask for composite object through + * vaExportSurfaceHandle, we shouldn't get any multiplane + * layer. */ + if (va_surface_descriptor.layers[i].num_planes > 1) + goto error; + + egl_images[i] = + vaegl_image_create(tc, tex_width[i], tex_height[i], + priv->drm_fourccs[i], + va_surface_descriptor.objects[obj_idx].fd, + va_surface_descriptor.layers[i].offset[0], + va_surface_descriptor.layers[i].pitch[0], + va_surface_descriptor.objects[obj_idx].drm_format_modifier); + if (egl_images[i] == NULL) + goto error; + + tc->vt->BindTexture(tc->tex_target, textures[i]); + + priv->glEGLImageTargetTexture2DOES(tc->tex_target, egl_images[i]); + } +#else for (unsigned i = 0; i < va_image.num_planes; ++i) { egl_images[i] = vaegl_image_create(tc, tex_width[i], tex_height[i], priv->drm_fourccs[i], va_buffer_info.handle, - va_image.offsets[i], va_image.pitches[i]); + va_image.offsets[i], va_image.pitches[i], + DRM_FORMAT_MOD_INVALID); if (egl_images[i] == NULL) goto error; @@ -203,6 +265,7 @@ tc_vaegl_update(const opengl_tex_converter_t *tc, GLuint *textures, priv->glEGLImageTargetTexture2DOES(tc->tex_target, egl_images[i]); } +#endif if (pic != priv->last.pic) { @@ -210,7 +273,12 @@ tc_vaegl_update(const opengl_tex_converter_t *tc, GLuint *textures, vaegl_release_last_pic(tc, priv); priv->last.pic = picture_Hold(pic); priv->last.va_image = va_image; +#if VA_CHECK_VERSION(1, 1, 0) + priv->last.va_surface_descriptor = va_surface_descriptor; #else priv->last.va_buffer_info = va_buffer_info; +#endif + for (unsigned i = 0; i < va_image.num_planes; ++i) priv->last.egl_images[i] = egl_images[i]; } @@ -221,7 +289,14 @@ error: if (release_image) { if (release_buffer_info) + { +#if VA_CHECK_VERSION(1, 1, 0) + for (unsigned i = 0; i < va_surface_descriptor.num_objects; ++i) + close(va_surface_descriptor.objects[i].fd); +#else vlc_vaapi_ReleaseBufferHandle(o, priv->vadpy, va_image.buf); +#endif + } for (unsigned i = 0; i < 3 && egl_images[i] != NULL; ++i) vaegl_image_destroy(tc, egl_images[i]); @@ -267,7 +342,8 @@ tc_vaegl_get_pool(const opengl_tex_converter_t *tc, unsigned requested_count) EGLint h = (va_image.height * tc->texs[i].h.num) / tc->texs[i].h.den; EGLImageKHR egl_image = vaegl_image_create(tc, w, h, priv->drm_fourccs[i], va_buffer_info.handle, - va_image.offsets[i], va_image.pitches[i]); + va_image.offsets[i], va_image.pitches[i], + DRM_FORMAT_MOD_INVALID); if (egl_image == NULL) { msg_Warn(o, "Can't create Image KHR: kernel too old ?"); -- 2.25.1 _______________________________________________ vlc-devel mailing list To unsubscribe or modify your subscription options: https://mailman.videolan.org/listinfo/vlc-devel