[PATCH weston v4] libweston-desktop: fix stale ping when a wl_shell_surface is destroyed
Quentin Glidic
sardemff7+wayland at sardemff7.net
Thu Dec 8 15:46:20 UTC 2016
On 08/12/2016 16:20, Giulio Camuffo wrote:
> When sending a ping event to a surface using the wl_shell interface,
> if that surface is destroyed before we receive the pong we will never
> receive it, even if the client is actually responsive, since the
> interface does not exist anymore. So when the surface if destroyed
> pretend it's a pong and reset the ping state.
>
> Signed-off-by: Giulio Camuffo <giuliocamuffo at gmail.com>
I made a few renames to match the current code.
I was going to push it, but I found a last issue, see below.
> ---
>
> v3: store the ping serial in the surface instead of the client wrapper
> v4: removed leftover change
>
> libweston-desktop/wl-shell.c | 22 +++++++++++++++++++++-
> 1 file changed, 21 insertions(+), 1 deletion(-)
>
> diff --git a/libweston-desktop/wl-shell.c b/libweston-desktop/wl-shell.c
> index 399139c..f75b022 100644
> --- a/libweston-desktop/wl-shell.c
> +++ b/libweston-desktop/wl-shell.c
> @@ -57,6 +57,7 @@ struct weston_desktop_wl_shell_surface {
> struct weston_desktop_seat *popup_seat;
> enum weston_desktop_wl_shell_surface_state state;
> struct wl_listener wl_surface_resource_destroy_listener;
> + uint32_t ping_serial;
> };
>
> static void
> @@ -112,6 +113,7 @@ weston_desktop_wl_shell_surface_ping(struct weston_desktop_surface *dsurface,
> {
> struct weston_desktop_wl_shell_surface *surface = user_data;
>
> + surface->ping_serial = serial;
> wl_shell_surface_send_ping(surface->resource, serial);
> }
>
> @@ -181,11 +183,27 @@ weston_desktop_wl_shell_change_state(struct weston_desktop_wl_shell_surface *sur
> }
>
> static void
> +pong_client(struct weston_desktop_wl_shell_surface *surface)
weston_desktop_wl_shell_surface_pong_client
> +{
> + struct weston_desktop_client *client =
> + weston_desktop_surface_get_client(surface->surface);
> +
> + weston_desktop_client_pong(client, surface->ping_serial);
> + surface->ping_serial = 0;
> +}
> +
> +static void
> weston_desktop_wl_shell_surface_destroy(struct weston_desktop_surface *dsurface,
> void *user_data)
> {
> struct weston_desktop_wl_shell_surface *surface = user_data;
>
> + /* If the surface being destroyed was the one that was pinged before
> + * we need to fake a pong here, because it cannot answer the ping anymore,
> + * even if the client is responsive. */
> + if (surface->ping_serial != 0)
> + pong_client(surface);
> +
> wl_list_remove(&surface->wl_surface_resource_destroy_listener.link);
>
> weston_desktop_wl_shell_surface_maybe_ungrab(surface);
> @@ -203,8 +221,10 @@ weston_desktop_wl_shell_surface_protocol_pong(struct wl_client *wl_client,
> uint32_t serial)
> {
> struct weston_desktop_surface *surface = wl_resource_get_user_data(resource);
dsurface
> + struct weston_desktop_wl_shell_surface *wls =
> + weston_desktop_surface_get_implementation_data(surface);
surface
> - weston_desktop_client_pong(weston_desktop_surface_get_client(surface), serial);
> + pong_client(wls);
We should check that surface->ping_serial == serial somehow.
Maybe it is safe to ignore serial for now, as it fixes something, then
add a check in a follow-up commit.
Thoughts? Pekka (aka assertman)?
Cheers,
> }
>
> static void
>
--
Quentin “Sardem FF7” Glidic
More information about the wayland-devel
mailing list