Use eglGetPlatformDisplay{,EXT} if available

Calling eglGetDisplay forces libEGL to guess what kind of pointer you
passed it. Different EGL libraries will do different things here, and in
particular glvnd will do something different than Mesa. Since we do have
an API that allows us to explicitly type the display, use it.

The explicit call to eglGetProcAddress is working around a bug in
libepoxy 1.3, which does not understand the EGL concept of client
extensions. Since it does not, the normal epoxy resolver for
eglGetPlatformDisplayEXT would not find any provider for that entry
point, and crash when you attempted to call it.

Signed-off-by: Adam Jackson <ajax@redhat.com>

https://bugzilla.gnome.org/show_bug.cgi?id=772415
This commit is contained in:
Adam Jackson 2016-10-10 14:12:40 -04:00 committed by Matthias Clasen
parent 0757914aba
commit 19aa3a4fca
2 changed files with 71 additions and 2 deletions

View File

@ -274,6 +274,40 @@ gdk_wayland_gl_context_init (GdkWaylandGLContext *self)
{
}
static EGLDisplay
gdk_wayland_get_display (GdkWaylandDisplay *display_wayland)
{
EGLDisplay dpy = NULL;
if (epoxy_has_egl_extension (NULL, "EGL_KHR_platform_base"))
{
PFNEGLGETPLATFORMDISPLAYPROC getPlatformDisplay =
(void *) eglGetProcAddress ("eglGetPlatformDisplay");
if (getPlatformDisplay)
dpy = getPlatformDisplay (EGL_PLATFORM_WAYLAND_EXT,
display_wayland->wl_display,
NULL);
if (dpy)
return dpy;
}
if (epoxy_has_egl_extension (NULL, "EGL_EXT_platform_base"))
{
PFNEGLGETPLATFORMDISPLAYEXTPROC getPlatformDisplay =
(void *) eglGetProcAddress ("eglGetPlatformDisplayEXT");
if (getPlatformDisplay)
dpy = getPlatformDisplay (EGL_PLATFORM_WAYLAND_EXT,
display_wayland->wl_display,
NULL);
if (dpy)
return dpy;
}
return eglGetDisplay ((EGLNativeDisplayType) display_wayland->wl_display);
}
gboolean
gdk_wayland_display_init_gl (GdkDisplay *display)
{
@ -284,7 +318,8 @@ gdk_wayland_display_init_gl (GdkDisplay *display)
if (display_wayland->have_egl)
return TRUE;
dpy = eglGetDisplay ((EGLNativeDisplayType)display_wayland->wl_display);
dpy = gdk_wayland_get_display (display_wayland);
if (dpy == NULL)
return FALSE;

View File

@ -214,6 +214,40 @@ append_egl_extension_row (GtkInspectorGeneral *gen,
{
add_check_row (gen, GTK_LIST_BOX (gen->priv->gl_box), ext, epoxy_has_egl_extension (dpy, ext), 0);
}
static EGLDisplay
wayland_get_display (struct wl_display *wl_display)
{
EGLDisplay dpy = NULL;
if (epoxy_has_egl_extension (NULL, "EGL_KHR_platform_base"))
{
PFNEGLGETPLATFORMDISPLAYPROC getPlatformDisplay =
(void *) eglGetProcAddress ("eglGetPlatformDisplay");
if (getPlatformDisplay)
dpy = getPlatformDisplay (EGL_PLATFORM_WAYLAND_EXT,
wl_display,
NULL);
if (dpy)
return dpy;
}
if (epoxy_has_egl_extension (NULL, "EGL_EXT_platform_base"))
{
PFNEGLGETPLATFORMDISPLAYEXTPROC getPlatformDisplay =
(void *) eglGetProcAddress ("eglGetPlatformDisplayEXT");
if (getPlatformDisplay)
dpy = getPlatformDisplay (EGL_PLATFORM_WAYLAND_EXT,
wl_display,
NULL);
if (dpy)
return dpy;
}
return eglGetDisplay ((EGLNativeDisplayType)wl_display);
}
#endif
@ -254,7 +288,7 @@ init_gl (GtkInspectorGeneral *gen)
EGLint major, minor;
gchar *version;
dpy = eglGetDisplay ((EGLNativeDisplayType)gdk_wayland_display_get_wl_display (display));
dpy = wayland_get_display (gdk_wayland_display_get_wl_display (display));
if (!eglInitialize (dpy, &major, &minor))
return;