From b405582f81d798e55d63d18b79e0511351057651 Mon Sep 17 00:00:00 2001 From: Derek Foreman Date: Tue, 16 Feb 2016 10:34:39 -0600 Subject: egl/wayland: Try to use wl_surface.damage_buffer for SwapBuffersWithDamage Since commit d1314de293e9e4a63c35f094c3893aaaed8580b4 we ignore damage passed to SwapBuffersWithDamage. Wayland 1.10 now has functionality that allows us to properly process those damage rectangles, and a way to query if it's available. Now we can use wl_surface.damage_buffer and interpret the incoming damage as being in buffer co-ordinates. Cc: "11.1 11.2" Reviewed-by: Jason Ekstrand Reviewed-by: Pekka Paalanen Signed-off-by: Derek Foreman (cherry picked from commit d085a5dff5bf753b82228ef0827f2331aff7b35b) --- src/egl/drivers/dri2/platform_wayland.c | 39 ++++++++++++++++++++++++++++++--- 1 file changed, 36 insertions(+), 3 deletions(-) diff --git a/src/egl/drivers/dri2/platform_wayland.c b/src/egl/drivers/dri2/platform_wayland.c index c2438f7509b..341acb7ed1b 100644 --- a/src/egl/drivers/dri2/platform_wayland.c +++ b/src/egl/drivers/dri2/platform_wayland.c @@ -653,6 +653,37 @@ create_wl_buffer(struct dri2_egl_surface *dri2_surf) &wl_buffer_listener, dri2_surf); } +static EGLBoolean +try_damage_buffer(struct dri2_egl_surface *dri2_surf, + const EGLint *rects, + EGLint n_rects) +{ +/* The WL_SURFACE_DAMAGE_BUFFER_SINCE_VERSION macro and + * wl_proxy_get_version() were both introduced in wayland 1.10. + * Instead of bumping our wayland dependency we just make this + * function conditional on the required 1.10 features, falling + * back to old (correct but suboptimal) behaviour for older + * wayland. + */ +#ifdef WL_SURFACE_DAMAGE_BUFFER_SINCE_VERSION + int i; + + if (wl_proxy_get_version((struct wl_proxy *) dri2_surf->wl_win->surface) + < WL_SURFACE_DAMAGE_BUFFER_SINCE_VERSION) + return EGL_FALSE; + + for (i = 0; i < n_rects; i++) { + const int *rect = &rects[i * 4]; + + wl_surface_damage_buffer(dri2_surf->wl_win->surface, + rect[0], + dri2_surf->base.Height - rect[1] - rect[3], + rect[2], rect[3]); + } + return EGL_TRUE; +#endif + return EGL_FALSE; +} /** * Called via eglSwapBuffers(), drv->API.SwapBuffers(). */ @@ -703,10 +734,12 @@ dri2_wl_swap_buffers_with_damage(_EGLDriver *drv, dri2_surf->dx = 0; dri2_surf->dy = 0; - /* We deliberately ignore the damage region and post maximum damage, due to + /* If the compositor doesn't support damage_buffer, we deliberately + * ignore the damage region and post maximum damage, due to * https://bugs.freedesktop.org/78190 */ - wl_surface_damage(dri2_surf->wl_win->surface, - 0, 0, INT32_MAX, INT32_MAX); + if (!n_rects || !try_damage_buffer(dri2_surf, rects, n_rects)) + wl_surface_damage(dri2_surf->wl_win->surface, + 0, 0, INT32_MAX, INT32_MAX); if (dri2_dpy->is_different_gpu) { _EGLContext *ctx = _eglGetCurrentContext(); -- cgit v1.2.3