[PATCH] input: Don't send leave events to destroyed views

Emilio Pozuelo Monfort pochu27 at gmail.com
Wed Nov 13 01:38:27 PST 2013


On 12/11/13 19:28, Emilio Pozuelo Monfort wrote:
> If a view which has focus is destroyed, we would send a leave
> event while changing focus, causing a segfault. Prevent this
> by listening to the view's destroy signal and removing it from
> the pointer focus.
> 
> Signed-off-by: Emilio Pozuelo Monfort <emilio.pozuelo at collabora.co.uk>
> ---
>  src/compositor.h |  1 +
>  src/input.c      | 22 ++++++++++++++++++++++
>  2 files changed, 23 insertions(+)
> 
> diff --git a/src/compositor.h b/src/compositor.h
> index 21d94d3..b69111f 100644
> --- a/src/compositor.h
> +++ b/src/compositor.h
> @@ -311,6 +311,7 @@ struct weston_pointer {
>  	struct wl_list focus_resource_list;
>  	struct weston_view *focus;
>  	uint32_t focus_serial;
> +	struct wl_listener focus_listener;
>  	struct wl_signal focus_signal;
>  
>  	struct weston_view *sprite;
> diff --git a/src/input.c b/src/input.c
> index ed3e06f..64f0606 100644
> --- a/src/input.c
> +++ b/src/input.c
> @@ -392,6 +392,7 @@ weston_pointer_create(void)
>  	pointer->default_grab.pointer = pointer;
>  	pointer->grab = &pointer->default_grab;
>  	wl_signal_init(&pointer->focus_signal);
> +	wl_list_init(&pointer->focus_listener.link);
>  
>  	pointer->sprite_destroy_listener.notify = pointer_handle_sprite_destroy;
>  
> @@ -487,6 +488,23 @@ seat_send_updated_caps(struct weston_seat *seat)
>  	}
>  }
>  
> +static void
> +destroy_pointer_focus(struct wl_listener *listener, void *data)
> +{
> +	struct weston_pointer *pointer;
> +
> +	pointer = container_of(listener, struct weston_pointer,
> +			       focus_listener);
> +
> +	pointer->focus = NULL;
> +	move_resources(&pointer->resource_list, &pointer->focus_resource_list);
> +
> +	wl_list_remove(&pointer->focus_listener.link);
> +	wl_list_init(&pointer->focus_listener.link);
> +
> +	wl_signal_emit(&pointer->focus_signal, pointer);
> +}
> +
>  WL_EXPORT void
>  weston_pointer_set_focus(struct weston_pointer *pointer,
>  			 struct weston_view *view,
> @@ -543,7 +561,11 @@ weston_pointer_set_focus(struct weston_pointer *pointer,
>  		pointer->focus_serial = serial;
>  	}
>  
> +	if (!wl_list_empty(&pointer->focus_listener.link))
> +		wl_list_remove(&pointer->focus_listener.link);
>  	pointer->focus = view;
> +	pointer->focus_listener.notify = destroy_pointer_focus;
> +	wl_signal_add(&view->destroy_signal, &pointer->focus_listener);

There's a bug here if view is NULL (e.g. when unsetting focus). I'll send an
updated patch.

Emilio

>  	wl_signal_emit(&pointer->focus_signal, pointer);
>  }
>  
> 



More information about the wayland-devel mailing list