Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 14 additions & 8 deletions library/alloc/src/rcs/arc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2864,14 +2864,16 @@ impl<T: ?Sized, A: Allocator> Arc<T, A> {
/// Returns `true` if there are no other `Arc` or [`Weak`] pointers to the same allocation;
/// returns `false` otherwise.
///
/// If this function returns `true`, then is guaranteed to be safe to call [`get_mut_unchecked`]
/// on this `Arc`, so long as no clones occur in between.
/// If this function returns `true`, then it is guaranteed to be safe to call [`get_mut_unchecked`]
/// on this `Arc`, as long as no clones occur in between.
///
/// The result can become stale if another thread can call `clone` or
/// `downgrade` through a shared reference. Make sure you have exclusive
/// access to the `Arc`.
///
/// # Examples
///
/// ```
/// #![feature(arc_is_unique)]
///
/// use std::sync::Arc;
///
/// let x = Arc::new(3);
Expand All @@ -2891,11 +2893,9 @@ impl<T: ?Sized, A: Allocator> Arc<T, A> {
/// This function will always return the same value as `Arc::get_mut(arc).is_some()`. However,
/// unlike that operation it does not produce any mutable references to the underlying data,
/// meaning no pointers to the data inside the `Arc` are invalidated by the call. Thus, the
/// following code is valid, even though it would be UB if it used `Arc::get_mut`:
/// following code is valid:
///
/// ```
/// #![feature(arc_is_unique)]
///
/// use std::sync::Arc;
///
/// let arc = Arc::new(5);
Expand All @@ -2904,6 +2904,12 @@ impl<T: ?Sized, A: Allocator> Arc<T, A> {
/// assert_eq!(unsafe { *pointer }, 5);
/// ```
///
/// The following changes would make the example unsound:
///
/// - Using `Arc::get_mut` to create a mutable reference while also accessing the value
/// through `pointer`.
/// - Dropping `arc` before dereferencing `pointer`, leaving it dangling.
///
/// # Atomic orderings
///
/// Concurrent drops to other `Arc` pointers to the same allocation will synchronize with this
Expand All @@ -2915,7 +2921,7 @@ impl<T: ?Sized, A: Allocator> Arc<T, A> {
///
/// [`get_mut_unchecked`]: Self::get_mut_unchecked
#[inline]
#[unstable(feature = "arc_is_unique", issue = "138938")]
#[stable(feature = "arc_is_unique", since = "CURRENT_RUSTC_VERSION")]
pub fn is_unique(this: &Self) -> bool {
// lock the weak pointer count if we appear to be the sole weak pointer
// holder.
Expand Down
22 changes: 14 additions & 8 deletions library/alloc/src/rcs/rc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1990,14 +1990,16 @@ impl<T: ?Sized, A: Allocator> Rc<T, A> {
/// Returns `true` if there are no other `Rc` or [`Weak`] pointers to the same allocation;
/// returns `false` otherwise.
///
/// If this function returns `true`, it is safe to call [`get_mut_unchecked`]
/// immediately afterward.
/// If this function returns `true`, then it is guaranteed to be safe to call
/// [`get_mut_unchecked`] on this `Rc`, as long as no clones occur in between.
///
/// The result can become stale if the `Rc` is cloned or downgraded between
/// the check and its use. Make sure no new `Rc` or `Weak` pointers are created
/// in between.
///
/// # Examples
///
/// ```
/// #![feature(arc_is_unique)]
///
/// use std::rc::Rc;
///
/// let x = Rc::new(3);
Expand All @@ -2017,11 +2019,9 @@ impl<T: ?Sized, A: Allocator> Rc<T, A> {
/// This function will always return the same value as `Rc::get_mut(rc).is_some()`. However,
/// unlike that operation it does not produce any mutable references to the underlying data,
/// meaning no pointers to the data inside the `Rc` are invalidated by the call. Thus, the
/// following code is valid, even though it would be UB if it used `Rc::get_mut`:
/// following code is valid:
///
/// ```
/// #![feature(arc_is_unique)]
///
/// use std::rc::Rc;
///
/// let rc = Rc::new(5);
Expand All @@ -2030,9 +2030,15 @@ impl<T: ?Sized, A: Allocator> Rc<T, A> {
/// assert_eq!(unsafe { *pointer }, 5);
/// ```
///
/// The following changes would make the example unsound:
///
/// - Using `Rc::get_mut` to create a mutable reference while also accessing the value
/// through `pointer`.
/// - Dropping `rc` before dereferencing `pointer`, leaving it dangling.
///
/// [`get_mut_unchecked`]: Self::get_mut_unchecked
#[inline]
#[unstable(feature = "arc_is_unique", issue = "138938")]
#[stable(feature = "arc_is_unique", since = "CURRENT_RUSTC_VERSION")]
pub fn is_unique(this: &Self) -> bool {
Rc::weak_count(this) == 0 && Rc::strong_count(this) == 1
}
Expand Down
Loading