Module: Mesa
Branch: main
Commit: 88c03ddd345fe6b0cd16c11cb5c5309f8d7d16ff
URL:    
http://cgit.freedesktop.org/mesa/mesa/commit/?id=88c03ddd345fe6b0cd16c11cb5c5309f8d7d16ff

Author: Leandro Ribeiro <[email protected]>
Date:   Mon Sep  4 13:53:12 2023 -0300

egl/drm: get compatible render-only device fd for kms-only device

Things have been working by accident for split display/render SoCs when
using the GBM platform.

The device fd given to the GBM platform may be associated with a
KMS-only device, so _eglFindDevice() should find nothing (because the
global EGLDevice list only has render-capable devices). The only thing
making it work is that we don't error out when we go through the
EGLDevice list and can't find the device we are looking for. We simply
return the last EGLDevice from the list.

This patch fixes that. Now we look for a compatible render-only device
for the KMS-only in the GBM platform.

Signed-off-by: Leandro Ribeiro <[email protected]>
Reviewed-by: Simon Ser <[email protected]>
Reviewed-by: Daniel Stone <[email protected]>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/24825>

---

 src/egl/drivers/dri2/platform_drm.c | 33 +++++++++++++++++++++++++++------
 1 file changed, 27 insertions(+), 6 deletions(-)

diff --git a/src/egl/drivers/dri2/platform_drm.c 
b/src/egl/drivers/dri2/platform_drm.c
index 7b56a9a37ab..37623f7d7b3 100644
--- a/src/egl/drivers/dri2/platform_drm.c
+++ b/src/egl/drivers/dri2/platform_drm.c
@@ -562,6 +562,20 @@ static const struct dri2_egl_display_vtbl 
dri2_drm_display_vtbl = {
    .get_dri_drawable = dri2_surface_get_dri_drawable,
 };
 
+static int
+get_fd_render_gpu_drm(struct gbm_dri_device *gbm_dri, int fd_display_gpu)
+{
+   /* This doesn't make sense for the software case. */
+   assert(!gbm_dri->software);
+
+   /* Render-capable device, so just return the same fd. */
+   if (loader_is_device_render_capable(fd_display_gpu))
+      return fd_display_gpu;
+
+   /* Display-only device, so return a compatible render-only device. */
+   return gbm_dri->mesa->queryCompatibleRenderOnlyDeviceFd(fd_display_gpu);
+}
+
 EGLBoolean
 dri2_initialize_drm(_EGLDisplay *disp)
 {
@@ -593,30 +607,37 @@ dri2_initialize_drm(_EGLDisplay *disp)
             goto cleanup;
          }
 
-         dri2_dpy->fd_render_gpu =
+         dri2_dpy->fd_display_gpu =
             loader_open_device(drm->nodes[DRM_NODE_PRIMARY]);
       } else {
          char buf[64];
          int n = snprintf(buf, sizeof(buf), DRM_DEV_NAME, DRM_DIR_NAME, 0);
          if (n != -1 && n < sizeof(buf))
-            dri2_dpy->fd_render_gpu = loader_open_device(buf);
+            dri2_dpy->fd_display_gpu = loader_open_device(buf);
       }
 
-      gbm = gbm_create_device(dri2_dpy->fd_render_gpu);
+      gbm = gbm_create_device(dri2_dpy->fd_display_gpu);
       if (gbm == NULL) {
          err = "DRI2: failed to create gbm device";
          goto cleanup;
       }
       dri2_dpy->own_device = true;
    } else {
-      dri2_dpy->fd_render_gpu = os_dupfd_cloexec(gbm_device_get_fd(gbm));
-      if (dri2_dpy->fd_render_gpu < 0) {
+      dri2_dpy->fd_display_gpu = os_dupfd_cloexec(gbm_device_get_fd(gbm));
+      if (dri2_dpy->fd_display_gpu < 0) {
          err = "DRI2: failed to fcntl() existing gbm device";
          goto cleanup;
       }
    }
-   dri2_dpy->fd_display_gpu = dri2_dpy->fd_render_gpu;
    dri2_dpy->gbm_dri = gbm_dri_device(gbm);
+   if (!dri2_dpy->gbm_dri->software) {
+      dri2_dpy->fd_render_gpu =
+         get_fd_render_gpu_drm(dri2_dpy->gbm_dri, dri2_dpy->fd_display_gpu);
+      if (dri2_dpy->fd_render_gpu < 0) {
+         err = "DRI2: failed to get compatible render device";
+         goto cleanup;
+      }
+   }
 
    if (strcmp(gbm_device_get_backend_name(gbm), "drm") != 0) {
       err = "DRI2: gbm device using incorrect/incompatible backend";

Reply via email to