From: Marcelo Moreira <marcelomoreira1905@gmail.com>
To: aliceryhl@google.com, lossin@kernel.org, dakr@kernel.org,
ojeda@kernel.org, rust-for-linux@vger.kernel.org,
skhan@linuxfoundation.org,
linux-kernel-mentees@lists.linuxfoundation.org,
~lkcamp/patches@lists.sr.ht
Subject: [PATCH v7 2/3] rust: revocable: Refactor revocation mechanism to remove generic revoke_internal
Date: Sun, 20 Jul 2025 22:01:54 -0300 [thread overview]
Message-ID: <20250721010258.70567-3-marcelomoreira1905@gmail.com> (raw)
In-Reply-To: <20250721010258.70567-1-marcelomoreira1905@gmail.com>
The revocation mechanism is refactored by removing the generic
`revoke_internal` function. Its logic is now directly integrated into
two distinct public functions: `revoke()` and `revoke_nosync()`.
`revoke_nosync()` is an `unsafe` function that requires the caller to
guarantee no concurrent users, thus avoiding an RCU grace period.
`revoke()` is a safe function that internally waits for the RCU grace
period to ensure all concurrent accesses have completed before dropping
the wrapped object.
This change improves API clarity and simplifies associated `SAFETY`
comments by making the synchronization behavior explicit in the function
signatures.
Suggested-by: Benno Lossin <lossin@kernel.org>
Suggested-by: Danilo Krummrich <dakr@kernel.org>
Reviewed-by: Benno Lossin <lossin@kernel.org>
Signed-off-by: Marcelo Moreira <marcelomoreira1905@gmail.com>
---
rust/kernel/revocable.rs | 48 ++++++++++++++++++----------------------
1 file changed, 21 insertions(+), 27 deletions(-)
diff --git a/rust/kernel/revocable.rs b/rust/kernel/revocable.rs
index 2dfee25240a0..6d8e9237dbdf 100644
--- a/rust/kernel/revocable.rs
+++ b/rust/kernel/revocable.rs
@@ -160,26 +160,6 @@ pub unsafe fn access(&self) -> &T {
unsafe { &*self.data.get() }
}
- /// # Safety
- ///
- /// Callers must ensure that there are no more concurrent users of the revocable object.
- unsafe fn revoke_internal<const SYNC: bool>(&self) -> bool {
- let revoke = self.is_available.swap(false, Ordering::Relaxed);
-
- if revoke {
- if SYNC {
- // SAFETY: Just an FFI call, there are no further requirements.
- unsafe { bindings::synchronize_rcu() };
- }
-
- // SAFETY: We know `self.data` is valid because only one CPU can succeed the
- // `compare_exchange` above that takes `is_available` from `true` to `false`.
- unsafe { drop_in_place(self.data.get()) };
- }
-
- revoke
- }
-
/// Revokes access to and drops the wrapped object.
///
/// Access to the object is revoked immediately to new callers of [`Revocable::try_access`],
@@ -192,10 +172,15 @@ unsafe fn revoke_internal<const SYNC: bool>(&self) -> bool {
///
/// Callers must ensure that there are no more concurrent users of the revocable object.
pub unsafe fn revoke_nosync(&self) -> bool {
- // SAFETY: By the safety requirement of this function, the caller ensures that nobody is
- // accessing the data anymore and hence we don't have to wait for the grace period to
- // finish.
- unsafe { self.revoke_internal::<false>() }
+ let revoke = self.is_available.swap(false, Ordering::Relaxed);
+
+ if revoke {
+ // SAFETY: `self.data` is valid for writes because of `Self`'s type invariants,
+ // as `self.is_available` is false due to the atomic swap, and by the safety
+ // requirements of this function, no thread is accessing `data` anymore.
+ unsafe { drop_in_place(self.data.get()) };
+ }
+ revoke
}
/// Revokes access to and drops the wrapped object.
@@ -209,9 +194,18 @@ pub unsafe fn revoke_nosync(&self) -> bool {
/// Returns `true` if `&self` has been revoked with this call, `false` if it was revoked
/// already.
pub fn revoke(&self) -> bool {
- // SAFETY: By passing `true` we ask `revoke_internal` to wait for the grace period to
- // finish.
- unsafe { self.revoke_internal::<true>() }
+ let revoke = self.is_available.swap(false, Ordering::Relaxed);
+
+ if revoke {
+ // SAFETY: Just an FFI call, there are no further requirements.
+ unsafe { bindings::synchronize_rcu() };
+
+ // SAFETY: `self.data` is valid for writes because of `Self`'s type invariants,
+ // as `self.is_available` is false due to the atomic swap, and `synchronize_rcu`
+ // ensures all prior RCU read-side critical sections have completed.
+ unsafe { drop_in_place(self.data.get()) };
+ }
+ revoke
}
}
--
2.50.1
next prev parent reply other threads:[~2025-07-21 1:03 UTC|newest]
Thread overview: 11+ messages / expand[flat|nested] mbox.gz Atom feed top
2025-07-21 1:01 [PATCH v7 0/3] rust: revocable: Documentation and safety refinements Marcelo Moreira
2025-07-21 1:01 ` [PATCH v7 1/3] rust: revocable: Clarify write invariant and update safety comments Marcelo Moreira
2025-07-21 1:01 ` Marcelo Moreira [this message]
2025-07-21 1:01 ` [PATCH v7 3/3] rust: revocable: Document RevocableGuard invariants/safety and refine Deref safety Marcelo Moreira
2025-07-21 14:20 ` Benno Lossin
2025-07-21 23:01 ` Marcelo Moreira
2025-07-22 10:51 ` Benno Lossin
2025-07-22 21:23 ` Marcelo Moreira
2025-07-23 14:22 ` Benno Lossin
2025-07-23 23:49 ` Marcelo Moreira
2025-07-24 10:30 ` Benno Lossin
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20250721010258.70567-3-marcelomoreira1905@gmail.com \
--to=marcelomoreira1905@gmail.com \
--cc=aliceryhl@google.com \
--cc=dakr@kernel.org \
--cc=linux-kernel-mentees@lists.linuxfoundation.org \
--cc=lossin@kernel.org \
--cc=ojeda@kernel.org \
--cc=rust-for-linux@vger.kernel.org \
--cc=skhan@linuxfoundation.org \
--cc=~lkcamp/patches@lists.sr.ht \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).