From a01f2c0f7d9dcfa3c6160bef80e5d67cc5bf5487 Mon Sep 17 00:00:00 2001 From: Pablo Saavedra Date: Wed, 5 May 2021 09:41:38 +0000 Subject: [PATCH] Remove view backend bridge association on connection drops Arrange for calling ViewBackend::unregisterSurface() also when a Surface is destroyed. This is a no-op if the nested compositor had the chance to receive and handle a FdoIPC::UnregisterSurface message before the surface is destroyed; but allows undoing the bridge association when the Wayland client connection is closed beforehand. The destruction callback for the surface is guaranteed to always be called by libwayland, even on dropped connections, to allow cleaning up reagardless of the fate of its clients. Among others, this covers the case in which a WPEWebProcess is abruptly exited, for example due to a crash or a top-level resource load being blocked by a content filter. Co-authored-by: Adrian Perez de Castro Acked-by: Adrian Perez de Castro Signed-off-by: Pablo Saavedra (cherry picked from commit 4e64c8d378b0512a97b06466602dadaf1acc3394) --- src/view-backend-private.h | 6 ++++++ src/ws.cpp | 5 ++++- src/ws.h | 6 ++++++ 3 files changed, 16 insertions(+), 1 deletion(-) diff --git a/src/view-backend-private.h b/src/view-backend-private.h index a86399a..3e8b6ab 100644 --- a/src/view-backend-private.h +++ b/src/view-backend-private.h @@ -68,6 +68,12 @@ class ViewBackend final : public WS::APIClient, public FdoIPC::MessageReceiver { void exportLinuxDmabuf(const struct linux_dmabuf_buffer *dmabuf_buffer) override; void exportShmBuffer(struct wl_resource* bufferResource, struct wl_shm_buffer* shmBuffer) override; void exportEGLStreamProducer(struct wl_resource*) override; + + void bridgeConnectionLost(uint32_t id) override + { + unregisterSurface(id); + } + void dispatchFrameCallbacks(); void releaseBuffer(struct wl_resource* buffer_resource); diff --git a/src/ws.cpp b/src/ws.cpp index 379a97b..5c5731b 100644 --- a/src/ws.cpp +++ b/src/ws.cpp @@ -545,8 +545,11 @@ void Instance::unregisterSurface(Surface* surface) [surface](const std::pair& value) -> bool { return value.second == surface; }); - if (it != m_viewBackendMap.end()) + if (it != m_viewBackendMap.end()) { m_viewBackendMap.erase(it); + if (surface->apiClient) + surface->apiClient->bridgeConnectionLost(it->first); + } } void Instance::dispatchFrameCallbacks(uint32_t bridgeId) diff --git a/src/ws.h b/src/ws.h index fbc8250..4371c0e 100644 --- a/src/ws.h +++ b/src/ws.h @@ -45,6 +45,12 @@ struct APIClient { virtual void exportLinuxDmabuf(const struct linux_dmabuf_buffer *dmabuf_buffer) = 0; virtual void exportShmBuffer(struct wl_resource*, struct wl_shm_buffer*) = 0; virtual void exportEGLStreamProducer(struct wl_resource*) = 0; + + // Invoked when the association with the surface associated with a given + // wpe_bridge identifier is no longer valid, typically due to the nested + // compositor client being disconnected before having the chance to read + // and process a FdoIPC::UnregisterSurface message. + virtual void bridgeConnectionLost(uint32_t bridgeId) = 0; }; struct Surface {