gl-renderer: fuzzy EGLConfig matching for non-GBM
authorPekka Paalanen <pekka.paalanen@collabora.com>
Mon, 30 Sep 2019 11:57:25 +0000 (14:57 +0300)
committerPekka Paalanen <pekka.paalanen@collabora.com>
Fri, 4 Oct 2019 09:17:18 +0000 (12:17 +0300)
Implement fuzzy EGLConfig pixel format matching, where we ensure that R, G, B
and A channels have the expected number of bits exactly. This is used on EGL
platforms where the EGLConfig native visual ID is not a DRM format code. On EGL
GBM platform, the old exact matching of native visual ID is kept.

As only the DRM backend uses a DRM format list for picking a config, this patch
should not change any behaviour.

Signed-off-by: Pekka Paalanen <pekka.paalanen@collabora.com>
libweston/renderer-gl/egl-glue.c
libweston/renderer-gl/gl-renderer-internal.h
libweston/renderer-gl/gl-renderer.c

index 87a84863d81a31fa318416cb43719fad5b1aed33..918523e5c8ed300e3f5e45149e0627d32b6dd52c 100644 (file)
@@ -99,27 +99,37 @@ log_egl_config_info(EGLDisplay egldpy, EGLConfig eglconfig)
                weston_log_continue(" unknown\n");
 }
 
-static int
-match_config_to_visual(EGLDisplay egl_display,
-                      EGLint visual_id,
-                      EGLConfig *configs,
-                      int count)
+static bool
+egl_config_pixel_format_matches(struct gl_renderer *gr,
+                               EGLConfig config,
+                               const struct pixel_format_info *pinfo)
 {
-       int i;
+       static const EGLint attribs[4] = {
+               EGL_ALPHA_SIZE, EGL_RED_SIZE, EGL_GREEN_SIZE, EGL_BLUE_SIZE
+       };
+       const int *argb[4] = {
+               &pinfo->bits.a, &pinfo->bits.r, &pinfo->bits.g, &pinfo->bits.b
+       };
+       unsigned i;
+       EGLint value;
 
-       for (i = 0; i < count; ++i) {
-               EGLint id;
+       if (gr->platform == EGL_PLATFORM_GBM_KHR) {
+               if (!eglGetConfigAttrib(gr->egl_display, config,
+                                       EGL_NATIVE_VISUAL_ID, &value))
+                       return false;
 
-               if (!eglGetConfigAttrib(egl_display,
-                               configs[i], EGL_NATIVE_VISUAL_ID,
-                               &id))
-                       continue;
+               return ((uint32_t)value) == pinfo->format;
+       }
 
-               if (id == visual_id)
-                       return i;
+       for (i = 0; i < 4; i++) {
+               if (!eglGetConfigAttrib(gr->egl_display, config,
+                                       attribs[i], &value))
+                       return false;
+               if (value != *argb[i])
+                       return false;
        }
 
-       return -1;
+       return true;
 }
 
 int
@@ -133,6 +143,7 @@ egl_choose_config(struct gl_renderer *gr,
        EGLint matched = 0;
        EGLConfig *configs;
        unsigned i;
+       EGLint j;
        int config_index = -1;
 
        if (!eglGetConfigs(gr->egl_display, NULL, 0, &count) || count < 1) {
@@ -153,10 +164,10 @@ egl_choose_config(struct gl_renderer *gr,
                config_index = 0;
 
        for (i = 0; config_index == -1 && i < pinfo_count; i++)
-               config_index = match_config_to_visual(gr->egl_display,
-                                                     pinfo[i]->format,
-                                                     configs,
-                                                     matched);
+               for (j = 0; config_index == -1 && j < matched; j++)
+                       if (egl_config_pixel_format_matches(gr, configs[j],
+                                                           pinfo[i]))
+                               config_index = j;
 
        if (config_index != -1)
                *config_out = configs[config_index];
index 0c4536162ae1cd5c3b10a99be11d7eb82170a579..07e29144c84590c9188689f81ddd87ed8a3013f0 100644 (file)
@@ -46,6 +46,7 @@ struct gl_renderer {
        struct weston_binding *fragment_binding;
        struct weston_binding *fan_binding;
 
+       EGLenum platform;
        EGLDisplay egl_display;
        EGLContext egl_context;
        EGLConfig egl_config;
index 6b5520f9e0733cb2433acd94064f2a0d50173fb8..0d55c9302caccd9a5d7c9d4109cdd64da1cabf3c 100644 (file)
@@ -3415,6 +3415,7 @@ gl_renderer_display_create(struct weston_compositor *ec,
        gr->base.surface_get_content_size =
                gl_renderer_surface_get_content_size;
        gr->base.surface_copy_content = gl_renderer_surface_copy_content;
+       gr->platform = platform;
        gr->egl_display = NULL;
 
        /* extension_suffix is supported */