From e2e8746bb634a4b58fd6e424985b59b4f6aba089 Mon Sep 17 00:00:00 2001 From: Gray Olson Date: Wed, 27 Sep 2023 11:39:08 +0200 Subject: [PATCH] reword unpin auto impl section --- library/core/src/marker.rs | 14 +++++++------- library/core/src/pin.rs | 32 +++++++++++++------------------- 2 files changed, 20 insertions(+), 26 deletions(-) diff --git a/library/core/src/marker.rs b/library/core/src/marker.rs index bd19d3cc0e290..5b527dfc9e7e9 100644 --- a/library/core/src/marker.rs +++ b/library/core/src/marker.rs @@ -938,13 +938,13 @@ marker_impls! { /// mem::replace(&mut *pinned_string, "other".to_string()); /// ``` /// -/// This trait is automatically implemented for almost every type. The compiler (and you!) is free -/// to take the conservative stance of marking types as [`Unpin`] by default. This is because if a -/// type implements [`Unpin`], then it is unsound for [`unsafe`] code to assume that type is truly -/// pinned, *even* when viewed through a "pinning" pointer! It is the responsibility of the -/// implementor of [`unsafe`] code that relies upon pinning for soundness to ensure that all the -/// types it expects to be truly pinned do not implement [`Unpin`]. For more details, see the -/// [`pin` module] docs! +/// This trait is automatically implemented for almost every type. The compiler is free +/// to take the conservative stance of marking types as [`Unpin`] so long as all of the types that +/// compose its fields are also [`Unpin`]. This is because if a type implements [`Unpin`], then it +/// is unsound for that type's implementation to rely on pinning-related guarantees for soundness, +/// *even* when viewed through a "pinning" pointer! It is the responsibility of the implementor of +/// a type that relies upon pinning for soundness to ensure that type is *not* marked as [`Unpin`] +/// by adding [`PhantomPinned`] field. For more details, see the [`pin` module] docs. /// /// [`mem::replace`]: crate::mem::replace "mem replace" /// [`Pin`]: crate::pin::Pin "Pin" diff --git a/library/core/src/pin.rs b/library/core/src/pin.rs index 785044e689d88..eb9c0818f1767 100644 --- a/library/core/src/pin.rs +++ b/library/core/src/pin.rs @@ -205,7 +205,7 @@ //! value which does not actually satisfy the invariants that a pinned value must satisfy, and in //! this way lead undefined behavior even in (from that point) fully safe code. Similarly, using //! [`unsafe`], one may get access to a bare [`&mut T`] from a [`Pin`] and -//! juse that to invalidly *move* pinned the value out. It is the job of the user of the +//! use that to invalidly *move* pinned the value out. It is the job of the user of the //! [`unsafe`] parts of the [`Pin`] API to ensure these invariants are not violated. //! //! This differs from e.g. [`UnsafeCell`] which changes the semantics of a program's compiled @@ -336,24 +336,18 @@ //! unsound without being expressed through pinning, and they would then need to not //! implement [`Unpin`]. //! -//! The compiler (and users!) is free to take the conservative stance of marking types as [`Unpin`] -//! by default. This is because if a type implements [`Unpin`], then it is unsound for [`unsafe`] -//! code to assume that type is truly pinned, *even* when viewed through a "pinning" pointer! It is -//! the responsibility of *the implementor of [`unsafe`] code that relies upon pinning for -//! soundness* (you, in this case!) to ensure that all the types which that code expects to be truly -//! pinned do not implement [`Unpin`]. -//! -//! Like other auto-traits, the compiler will automatically determine that a type implements -//! [`Unpin`] if all its fields also implement [`Unpin`]. If you are building a type which consists -//! of only [`Unpin`] types but has an address-sensistive state and thus should not itself -//! implement [`Unpin`], you must opt out of [`Unpin`] via adding a field with the -//! [`PhantomPinned`] marker type, as we did with our latest `AddrTracker` example above. Without -//! doing this, you must not rely on the pinning guarantees to apply to your type! -//! -//! If you have reason to pin a value of a type that implements [`Unpin`] such that pinning-related -//! guarantees actually are respected, you'll need to create your own wrapper type which itself -//! opts out of implementing [`Unpin`] and contains a sub-field with the [`Unpin`] type that you -//! want to pin. +//! The compiler is free to take the conservative stance of marking types as [`Unpin`] so long as +//! all of the types that compose its fields are also [`Unpin`]. This is because if a type +//! implements [`Unpin`], then it is unsound for that type's implementation to rely on +//! pinning-related guarantees for soundness, *even* when viewed through a "pinning" pointer! It is +//! the responsibility of the implementor of a type that relies upon pinning for soundness to +//! ensure that type is *not* marked as [`Unpin`] by adding [`PhantomPinned`] field. This is +//! exactly what we did with our `AddrTracker` example above. Without doing this, you *must not* +//! rely on pinning-related guarantees to apply to your type! +//! +//! If need to truly pin a value of a foreign or built-in type that implements [`Unpin`], you'll +//! need to create your own wrapper type around the [`Unpin`] type you want to pin and then +//! opts-out of [`Unpin`] using [`PhantomPinned`]. //! //! Exposing access to the inner field which you want to remain pinned must then be carefully //! considered as well! Remember, exposing a method that gives access to a