From dcadf208c9b66976516c34bccf1eb89c52972502 Mon Sep 17 00:00:00 2001 From: Christian Meissl Date: Sat, 14 Dec 2024 21:14:52 +0100 Subject: [PATCH 1/4] backend/rs: delay client cleanup delay client cleanup until the state lock is dropped to prevent potential deadlocks in drop impls of the client state. --- wayland-backend/CHANGELOG.md | 4 ++++ wayland-backend/src/rs/server_impl/client.rs | 4 ++-- wayland-backend/src/rs/server_impl/handle.rs | 1 + wayland-backend/src/rs/server_impl/registry.rs | 2 +- 4 files changed, 8 insertions(+), 3 deletions(-) diff --git a/wayland-backend/CHANGELOG.md b/wayland-backend/CHANGELOG.md index b5990046e13..d334f5ce381 100644 --- a/wayland-backend/CHANGELOG.md +++ b/wayland-backend/CHANGELOG.md @@ -2,6 +2,10 @@ ## Unreleased +### Bugfixes + +- backend/rs: Prevent a potential deadlock during client cleanup + ## 0.3.7 -- 2024-09-04 ### Bugfixes diff --git a/wayland-backend/src/rs/server_impl/client.rs b/wayland-backend/src/rs/server_impl/client.rs index 3ef1a652aec..8777899e894 100644 --- a/wayland-backend/src/rs/server_impl/client.rs +++ b/wayland-backend/src/rs/server_impl/client.rs @@ -720,7 +720,7 @@ impl ClientStore { pub(crate) fn cleanup( &mut self, pending_destructors: &mut Vec>, - ) -> SmallVec<[ClientId; 1]> { + ) -> SmallVec<[Client; 1]> { let mut cleaned = SmallVec::new(); for place in &mut self.clients { if place.as_ref().map(|client| client.killed).unwrap_or(false) { @@ -728,7 +728,7 @@ impl ClientStore { let mut client = place.take().unwrap(); client.queue_all_destructors(pending_destructors); let _ = client.flush(); - cleaned.push(ClientId { id: client.id }); + cleaned.push(client); } } cleaned diff --git a/wayland-backend/src/rs/server_impl/handle.rs b/wayland-backend/src/rs/server_impl/handle.rs index 7d1cff1ce08..ec33f037b73 100644 --- a/wayland-backend/src/rs/server_impl/handle.rs +++ b/wayland-backend/src/rs/server_impl/handle.rs @@ -53,6 +53,7 @@ impl State { ObjectId { id: object_id }, ); } + std::mem::drop(dead_clients); } } diff --git a/wayland-backend/src/rs/server_impl/registry.rs b/wayland-backend/src/rs/server_impl/registry.rs index adfb6f27317..e125a944458 100644 --- a/wayland-backend/src/rs/server_impl/registry.rs +++ b/wayland-backend/src/rs/server_impl/registry.rs @@ -127,7 +127,7 @@ impl Registry { Some((target_global.interface, target_global.id.clone(), target_global.handler.clone())) } - pub(crate) fn cleanup(&mut self, dead_clients: &[ClientId]) { + pub(crate) fn cleanup(&mut self, dead_clients: &[Client]) { self.known_registries .retain(|obj_id| !dead_clients.iter().any(|cid| cid.id == obj_id.client_id)) } From 0690d178d56420ee8923cdcf5d338319246606d8 Mon Sep 17 00:00:00 2001 From: Christian Meissl Date: Sat, 14 Dec 2024 22:09:28 +0100 Subject: [PATCH 2/4] fix lifetime clippy lints --- wayland-backend/src/debug.rs | 2 +- wayland-client/src/event_queue.rs | 2 +- wayland-server/src/dispatch.rs | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/wayland-backend/src/debug.rs b/wayland-backend/src/debug.rs index 322961c2b50..24c2fc3f4c3 100644 --- a/wayland-backend/src/debug.rs +++ b/wayland-backend/src/debug.rs @@ -58,7 +58,7 @@ pub fn print_send_message( pub(crate) struct DisplaySlice<'a, D>(pub &'a [D]); -impl<'a, D: Display> Display for DisplaySlice<'a, D> { +impl Display for DisplaySlice<'_, D> { #[cfg_attr(coverage, coverage(off))] fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { let mut it = self.0.iter(); diff --git a/wayland-client/src/event_queue.rs b/wayland-client/src/event_queue.rs index ba46db8e195..0850163c6b2 100644 --- a/wayland-client/src/event_queue.rs +++ b/wayland-client/src/event_queue.rs @@ -632,7 +632,7 @@ impl QueueHandle { } } -impl<'a, State> Drop for QueueFreezeGuard<'a, State> { +impl Drop for QueueFreezeGuard<'_, State> { fn drop(&mut self) { let mut lock = self.qh.inner.lock().unwrap(); lock.freeze_count -= 1; diff --git a/wayland-server/src/dispatch.rs b/wayland-server/src/dispatch.rs index ea99edc6750..ea73fbfd5d4 100644 --- a/wayland-server/src/dispatch.rs +++ b/wayland-server/src/dispatch.rs @@ -158,7 +158,7 @@ pub struct DataInit<'a, D: 'static> { pub(crate) error: &'a mut Option<(u32, String)>, } -impl<'a, D> DataInit<'a, D> { +impl DataInit<'_, D> { /// Initialize an object by assigning it its user-data pub fn init( &mut self, From b07d3f36494e638c9dfe4ed8a593d02a5161a6d9 Mon Sep 17 00:00:00 2001 From: Christian Meissl Date: Sat, 14 Dec 2024 22:13:12 +0100 Subject: [PATCH 3/4] deny: allow Unicode-3.0 licenses --- deny.toml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/deny.toml b/deny.toml index 8d235dbd6e9..c2d7970a02a 100644 --- a/deny.toml +++ b/deny.toml @@ -33,4 +33,6 @@ allow = [ # Google categorizes the license under "notice" which means it can be used (with some exceptions like # notices or advertising clauses): https://opensource.google/documentation/reference/thirdparty/licenses#notice "Unicode-DFS-2016", + # Unicode-DFS-2016 has been superseded by Unicode V3 + "Unicode-3.0", ] From 50bb66216e6bb86b2feba3ec31430d068cc20307 Mon Sep 17 00:00:00 2001 From: Christian Meissl Date: Sat, 14 Dec 2024 23:19:41 +0100 Subject: [PATCH 4/4] sys: disable function ptr lint --- wayland-sys/src/server.rs | 3 +++ 1 file changed, 3 insertions(+) diff --git a/wayland-sys/src/server.rs b/wayland-sys/src/server.rs index b11e8ed7060..0acee4f8873 100644 --- a/wayland-sys/src/server.rs +++ b/wayland-sys/src/server.rs @@ -251,6 +251,9 @@ pub mod signal { // Safety: the signal pointer is valid unsafe { list_for_each!(l, &mut (*signal).listener_list as *mut wl_list, wl_listener, link, { + // nightly only lint + #[allow(unknown_lints)] + #[allow(unpredictable_function_pointer_comparisons)] if (*l).notify == notify { return l; }