xserver: Branch 'master' - 4 commits

GitLab Mirror gitlab-mirror at kemper.freedesktop.org
Fri Oct 28 12:41:58 UTC 2022


 glamor/glamor_egl.c               |   29 ++++++++++++++-
 hw/xwayland/xwayland-glamor-gbm.c |   73 +++++++++++++++++++++++++++++++++-----
 2 files changed, 92 insertions(+), 10 deletions(-)

New commits:
commit e5b09f7a2cc3bd64a6ea207c7c75d4f05b79cf44
Author: Lucas Stach <l.stach at pengutronix.de>
Date:   Sun Jul 10 19:35:43 2022 +0200

    glamor_egl: properly get FDs from multiplanar GBM BOs
    
    Multiplanar GBM buffers can point to different objects from each plane.
    Use the _for_plane API when possible to retrieve the correct prime FD
    for each plane.
    
    Signed-off-by: Lucas Stach <l.stach at pengutronix.de>
    Reviewed-by: Simon Ser <contact at emersion.fr>
    Tested-by: Guido Günther <agx at sigxcpu.org>

diff --git a/glamor/glamor_egl.c b/glamor/glamor_egl.c
index fa5fcbd04..aa82a5608 100644
--- a/glamor/glamor_egl.c
+++ b/glamor/glamor_egl.c
@@ -403,6 +403,9 @@ glamor_egl_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
     struct gbm_bo *bo;
     int num_fds;
 #ifdef GBM_BO_WITH_MODIFIERS
+#ifndef GBM_BO_FD_FOR_PLANE
+    int32_t first_handle;
+#endif
     int i;
 #endif
 
@@ -416,7 +419,24 @@ glamor_egl_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
 #ifdef GBM_BO_WITH_MODIFIERS
     num_fds = gbm_bo_get_plane_count(bo);
     for (i = 0; i < num_fds; i++) {
-        fds[i] = gbm_bo_get_fd(bo);
+#ifdef GBM_BO_FD_FOR_PLANE
+        fds[i] = gbm_bo_get_fd_for_plane(bo, i);
+#else
+        union gbm_bo_handle plane_handle = gbm_bo_get_handle_for_plane(bo, i);
+
+        if (i == 0)
+            first_handle = plane_handle.s32;
+
+        /* If all planes point to the same object as the first plane, i.e. they
+         * all have the same handle, we can fall back to the non-planar
+         * gbm_bo_get_fd without losing information. If they point to different
+         * objects we are out of luck and need to give up.
+         */
+	if (first_handle == plane_handle.s32)
+            fds[i] = gbm_bo_get_fd(bo);
+        else
+            fds[i] = -1;
+#endif
         if (fds[i] == -1) {
             while (--i >= 0)
                 close(fds[i]);
commit 95944e2b990dacde81892406c8a0e2cc2afa7b3e
Author: Lucas Stach <l.stach at pengutronix.de>
Date:   Thu Jul 28 22:52:15 2022 +0200

    glamor_egl: handle fd export failure in glamor_egl_fds_from_pixmap
    
    Check the fd for validity before giving a success return code.
    
    Signed-off-by: Lucas Stach <l.stach at pengutronix.de>
    Reviewed-by: Simon Ser <contact at emersion.fr>
    Tested-by: Guido Günther <agx at sigxcpu.org>

diff --git a/glamor/glamor_egl.c b/glamor/glamor_egl.c
index 60d0df893..fa5fcbd04 100644
--- a/glamor/glamor_egl.c
+++ b/glamor/glamor_egl.c
@@ -417,6 +417,11 @@ glamor_egl_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
     num_fds = gbm_bo_get_plane_count(bo);
     for (i = 0; i < num_fds; i++) {
         fds[i] = gbm_bo_get_fd(bo);
+        if (fds[i] == -1) {
+            while (--i >= 0)
+                close(fds[i]);
+            return 0;
+        }
         strides[i] = gbm_bo_get_stride_for_plane(bo, i);
         offsets[i] = gbm_bo_get_offset(bo, i);
     }
@@ -424,6 +429,8 @@ glamor_egl_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
 #else
     num_fds = 1;
     fds[0] = gbm_bo_get_fd(bo);
+    if (fds[0] == -1)
+        return 0;
     strides[0] = gbm_bo_get_stride(bo);
     offsets[0] = 0;
     *modifier = DRM_FORMAT_MOD_INVALID;
commit 7d5ad2d372cc88648f6744c318a4bee18443689d
Author: Lucas Stach <l.stach at pengutronix.de>
Date:   Sun Jul 10 17:51:14 2022 +0200

    xwayland: properly get FDs from multiplanar GBM BOs
    
    Multiplanar GBM buffers can point to different objects from each plane.
    Use the _for_plane API when possible to retrieve the correct prime FD
    for each plane.
    
    Signed-off-by: Lucas Stach <l.stach at pengutronix.de>
    Reviewed-by: Simon Ser <contact at emersion.fr>
    Tested-by: Guido Günther <agx at sigxcpu.org>

diff --git a/hw/xwayland/xwayland-glamor-gbm.c b/hw/xwayland/xwayland-glamor-gbm.c
index adefc768b..ec5514fd2 100644
--- a/hw/xwayland/xwayland-glamor-gbm.c
+++ b/hw/xwayland/xwayland-glamor-gbm.c
@@ -354,12 +354,15 @@ xwl_glamor_gbm_get_wl_buffer_for_pixmap(PixmapPtr pixmap)
     unsigned short width = pixmap->drawable.width;
     unsigned short height = pixmap->drawable.height;
     uint32_t format;
-    int prime_fd;
     int num_planes;
+    int prime_fds[4];
     uint32_t strides[4];
     uint32_t offsets[4];
     uint64_t modifier;
     int i;
+#ifndef GBM_BO_FD_FOR_PLANE
+    int32_t first_handle;
+#endif
 
     if (xwl_pixmap == NULL)
        return NULL;
@@ -374,20 +377,43 @@ xwl_glamor_gbm_get_wl_buffer_for_pixmap(PixmapPtr pixmap)
 
     format = wl_drm_format_for_depth(pixmap->drawable.depth);
 
-    prime_fd = gbm_bo_get_fd(xwl_pixmap->bo);
-    if (prime_fd == -1)
-        return NULL;
-
 #ifdef GBM_BO_WITH_MODIFIERS
     num_planes = gbm_bo_get_plane_count(xwl_pixmap->bo);
     modifier = gbm_bo_get_modifier(xwl_pixmap->bo);
     for (i = 0; i < num_planes; i++) {
+#ifdef GBM_BO_FD_FOR_PLANE
+        prime_fds[i] = gbm_bo_get_fd_for_plane(xwl_pixmap->bo, i);
+#else
+        union gbm_bo_handle plane_handle;
+
+        plane_handle = gbm_bo_get_handle_for_plane(xwl_pixmap->bo, i);
+        if (i == 0)
+            first_handle = plane_handle.s32;
+
+        /* If all planes point to the same object as the first plane, i.e. they
+         * all have the same handle, we can fall back to the non-planar
+         * gbm_bo_get_fd without losing information. If they point to different
+         * objects we are out of luck and need to give up.
+         */
+        if (first_handle == plane_handle.s32)
+            prime_fds[i] = gbm_bo_get_fd(xwl_pixmap->bo);
+        else
+            prime_fds[i] = -1;
+#endif
+        if (prime_fds[i] == -1) {
+            while (--i >= 0)
+                close(prime_fds[i]);
+            return NULL;
+        }
         strides[i] = gbm_bo_get_stride_for_plane(xwl_pixmap->bo, i);
         offsets[i] = gbm_bo_get_offset(xwl_pixmap->bo, i);
     }
 #else
     num_planes = 1;
     modifier = DRM_FORMAT_MOD_INVALID;
+    prime_fds[0] = gbm_bo_get_fd(xwl_pixmap->bo);
+    if (prime_fds[0] == -1)
+        return NULL;
     strides[0] = gbm_bo_get_stride(xwl_pixmap->bo);
     offsets[0] = 0;
 #endif
@@ -398,7 +424,7 @@ xwl_glamor_gbm_get_wl_buffer_for_pixmap(PixmapPtr pixmap)
 
         params = zwp_linux_dmabuf_v1_create_params(xwl_screen->dmabuf);
         for (i = 0; i < num_planes; i++) {
-            zwp_linux_buffer_params_v1_add(params, prime_fd, i,
+            zwp_linux_buffer_params_v1_add(params, prime_fds[i], i,
                                            offsets[i], strides[i],
                                            modifier >> 32, modifier & 0xffffffff);
         }
@@ -409,14 +435,15 @@ xwl_glamor_gbm_get_wl_buffer_for_pixmap(PixmapPtr pixmap)
         zwp_linux_buffer_params_v1_destroy(params);
     } else if (num_planes == 1) {
         xwl_pixmap->buffer =
-            wl_drm_create_prime_buffer(xwl_gbm->drm, prime_fd, width, height,
+            wl_drm_create_prime_buffer(xwl_gbm->drm, prime_fds[0], width, height,
                                        format,
                                        0, gbm_bo_get_stride(xwl_pixmap->bo),
                                        0, 0,
                                        0, 0);
     }
 
-    close(prime_fd);
+    for (i = 0; i < num_planes; i++)
+        close(prime_fds[i]);
 
     /* Add our listener now */
     wl_buffer_add_listener(xwl_pixmap->buffer,
@@ -610,6 +637,9 @@ glamor_egl_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
 {
     struct xwl_pixmap *xwl_pixmap;
 #ifdef GBM_BO_WITH_MODIFIERS
+#ifndef GBM_BO_FD_FOR_PLANE
+    int32_t first_handle;
+#endif
     uint32_t num_fds;
     int i;
 #endif
@@ -627,7 +657,25 @@ glamor_egl_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
     *modifier = gbm_bo_get_modifier(xwl_pixmap->bo);
 
     for (i = 0; i < num_fds; i++) {
-        fds[i] = gbm_bo_get_fd(xwl_pixmap->bo);
+#ifdef GBM_BO_FD_FOR_PLANE
+        fds[i] = gbm_bo_get_fd_for_plane(xwl_pixmap->bo, i);
+#else
+        union gbm_bo_handle plane_handle;
+
+        plane_handle = gbm_bo_get_handle_for_plane(xwl_pixmap->bo, i);
+        if (i == 0)
+            first_handle = plane_handle.s32;
+
+        /* If all planes point to the same object as the first plane, i.e. they
+         * all have the same handle, we can fall back to the non-planar
+         * gbm_bo_get_fd without losing information. If they point to different
+         * objects we are out of luck and need to give up.
+         */
+        if (first_handle == plane_handle.s32)
+            fds[i] = gbm_bo_get_fd(xwl_pixmap->bo);
+        else
+            fds[i] = -1;
+#endif
         if (fds[i] == -1) {
             while (--i >= 0)
                 close(fds[i]);
commit 951502e49797ab4c5db047e9df32c93d050d64af
Author: Lucas Stach <l.stach at pengutronix.de>
Date:   Thu Jul 28 22:44:59 2022 +0200

    xwayland: handle fd export failure in glamor_egl_fds_from_pixmap
    
    Check the fd for validity before giving a success return code.
    
    Signed-off-by: Lucas Stach <l.stach at pengutronix.de>
    Reviewed-by: Simon Ser <contact at emersion.fr>
    Tested-by: Guido Günther <agx at sigxcpu.org>

diff --git a/hw/xwayland/xwayland-glamor-gbm.c b/hw/xwayland/xwayland-glamor-gbm.c
index 60c63ba99..adefc768b 100644
--- a/hw/xwayland/xwayland-glamor-gbm.c
+++ b/hw/xwayland/xwayland-glamor-gbm.c
@@ -628,6 +628,11 @@ glamor_egl_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
 
     for (i = 0; i < num_fds; i++) {
         fds[i] = gbm_bo_get_fd(xwl_pixmap->bo);
+        if (fds[i] == -1) {
+            while (--i >= 0)
+                close(fds[i]);
+            return 0;
+        }
         strides[i] = gbm_bo_get_stride_for_plane(xwl_pixmap->bo, i);
         offsets[i] = gbm_bo_get_offset(xwl_pixmap->bo, i);
     }
@@ -636,6 +641,8 @@ glamor_egl_fds_from_pixmap(ScreenPtr screen, PixmapPtr pixmap, int *fds,
 #else
     *modifier = DRM_FORMAT_MOD_INVALID;
     fds[0] = gbm_bo_get_fd(xwl_pixmap->bo);
+    if (fds[0] == -1)
+        return 0;
     strides[0] = gbm_bo_get_stride(xwl_pixmap->bo);
     offsets[0] = 0;
     return 1;


More information about the xorg-commit mailing list