From 62affbb44b771931a8895fc7428df23afb888750 Mon Sep 17 00:00:00 2001 From: Philipp Kerling Date: Wed, 16 Aug 2017 12:37:27 +0200 Subject: wayland: Implement registry remove handler Wayland event handlers are never optional. libwayland-client will abort the program if events for unbound handlers are to be dispatched. Although the event queue is only dispatched a few times during initialization for getting the wl_drm global and authenticating the DRM device, in rare circumstances it can happen that another global such as a wl_output - or even wl_drm itself - is removed during that time, which would crash the program. Implement the handler to fix this. Fixes: #99 Signed-off-by: Philipp Kerling --- va/wayland/va_wayland_drm.c | 23 ++++++++++++++++++++--- 1 file changed, 20 insertions(+), 3 deletions(-) (limited to 'va/wayland') diff --git a/va/wayland/va_wayland_drm.c b/va/wayland/va_wayland_drm.c index a4d3ebb..552f243 100644 --- a/va/wayland/va_wayland_drm.c +++ b/va/wayland/va_wayland_drm.c @@ -41,6 +41,7 @@ typedef struct va_wayland_drm_context { struct va_wayland_context base; struct wl_event_queue *queue; struct wl_drm *drm; + uint32_t drm_name; struct wl_registry *registry; unsigned int is_authenticated : 1; } VADisplayContextWaylandDRM; @@ -148,7 +149,7 @@ static void registry_handle_global( void *data, struct wl_registry *registry, - uint32_t id, + uint32_t name, const char *interface, uint32_t version ) @@ -159,15 +160,31 @@ registry_handle_global( /* bind to at most version 2, but also support version 1 if * compositor does not have v2 */ + wl_drm_ctx->drm_name = name; wl_drm_ctx->drm = - wl_registry_bind(wl_drm_ctx->registry, id, &wl_drm_interface, + wl_registry_bind(wl_drm_ctx->registry, name, &wl_drm_interface, (version < 2) ? version : 2); } } +static void +registry_handle_global_remove( + void *data, + struct wl_registry *registry, + uint32_t name +) +{ + struct va_wayland_drm_context *wl_drm_ctx = data; + + if (wl_drm_ctx->drm && name == wl_drm_ctx->drm_name) { + wl_drm_destroy(wl_drm_ctx->drm); + wl_drm_ctx->drm = NULL; + } +} + static const struct wl_registry_listener registry_listener = { registry_handle_global, - NULL, + registry_handle_global_remove }; static bool -- cgit v1.2.1