diff options
| author | Laurențiu Nicola <lnicola@dend.ro> | 2024-08-13 17:58:52 +0300 |
|---|---|---|
| committer | Laurențiu Nicola <lnicola@dend.ro> | 2024-08-13 17:58:52 +0300 |
| commit | 28af7e09581c3b39cdbf2850df2f157690ab7e56 (patch) | |
| tree | 76c5e72c0570998ece04f11ac90e09b5d2613abc /library/core/src/ptr | |
| parent | ddb8551e03a1310a841da05b0418b49fd6287482 (diff) | |
| parent | 80eb5a8e910e5185d47cdefe3732d839c78a5e7e (diff) | |
Merge from rust-lang/rust
Diffstat (limited to 'library/core/src/ptr')
| -rw-r--r-- | library/core/src/ptr/const_ptr.rs | 2 | ||||
| -rw-r--r-- | library/core/src/ptr/metadata.rs | 5 | ||||
| -rw-r--r-- | library/core/src/ptr/mod.rs | 48 | ||||
| -rw-r--r-- | library/core/src/ptr/mut_ptr.rs | 2 | ||||
| -rw-r--r-- | library/core/src/ptr/non_null.rs | 22 | ||||
| -rw-r--r-- | library/core/src/ptr/unique.rs | 4 |
6 files changed, 44 insertions, 39 deletions
diff --git a/library/core/src/ptr/const_ptr.rs b/library/core/src/ptr/const_ptr.rs index 3e7933e9eec..93bbd92593f 100644 --- a/library/core/src/ptr/const_ptr.rs +++ b/library/core/src/ptr/const_ptr.rs @@ -61,7 +61,7 @@ impl<T: ?Sized> *const T { self as _ } - /// Use the pointer value in a new pointer of another type. + /// Uses the pointer value in a new pointer of another type. /// /// In case `meta` is a (fat) pointer to an unsized type, this operation /// will ignore the pointer part, whereas for (thin) pointers to sized diff --git a/library/core/src/ptr/metadata.rs b/library/core/src/ptr/metadata.rs index 06f205c0f26..ccc9f8754f0 100644 --- a/library/core/src/ptr/metadata.rs +++ b/library/core/src/ptr/metadata.rs @@ -2,8 +2,7 @@ use crate::fmt; use crate::hash::{Hash, Hasher}; -use crate::intrinsics::aggregate_raw_ptr; -use crate::intrinsics::ptr_metadata; +use crate::intrinsics::{aggregate_raw_ptr, ptr_metadata}; use crate::marker::Freeze; use crate::ptr::NonNull; @@ -81,7 +80,7 @@ pub trait Pointee { // NOTE: don’t stabilize this before trait aliases are stable in the language? pub trait Thin = Pointee<Metadata = ()>; -/// Extract the metadata component of a pointer. +/// Extracts the metadata component of a pointer. /// /// Values of type `*mut T`, `&T`, or `&mut T` can be passed directly to this function /// as they implicitly coerce to `*const T`. diff --git a/library/core/src/ptr/mod.rs b/library/core/src/ptr/mod.rs index 9b0aa2e7bfe..25d8f4a0adb 100644 --- a/library/core/src/ptr/mod.rs +++ b/library/core/src/ptr/mod.rs @@ -196,9 +196,9 @@ //! * The **provenance** it has, defining the memory it has permission to access. //! Provenance can be absent, in which case the pointer does not have permission to access any memory. //! -//! Under Strict Provenance, a usize *cannot* accurately represent a pointer, and converting from -//! a pointer to a usize is generally an operation which *only* extracts the address. It is -//! therefore *impossible* to construct a valid pointer from a usize because there is no way +//! Under Strict Provenance, a `usize` *cannot* accurately represent a pointer, and converting from +//! a pointer to a `usize` is generally an operation which *only* extracts the address. It is +//! therefore *impossible* to construct a valid pointer from a `usize` because there is no way //! to restore the address-space and provenance. In other words, pointer-integer-pointer //! roundtrips are not possible (in the sense that the resulting pointer is not dereferenceable). //! @@ -234,16 +234,16 @@ //! //! Most code needs no changes to conform to strict provenance, as the only really concerning //! operation that *wasn't* obviously already Undefined Behaviour is casts from usize to a -//! pointer. For code which *does* cast a usize to a pointer, the scope of the change depends +//! pointer. For code which *does* cast a `usize` to a pointer, the scope of the change depends //! on exactly what you're doing. //! -//! In general, you just need to make sure that if you want to convert a usize address to a +//! In general, you just need to make sure that if you want to convert a `usize` address to a //! pointer and then use that pointer to read/write memory, you need to keep around a pointer //! that has sufficient provenance to perform that read/write itself. In this way all of your //! casts from an address to a pointer are essentially just applying offsets/indexing. //! //! This is generally trivial to do for simple cases like tagged pointers *as long as you -//! represent the tagged pointer as an actual pointer and not a usize*. For instance: +//! represent the tagged pointer as an actual pointer and not a `usize`*. For instance: //! //! ``` //! #![feature(strict_provenance)] @@ -409,13 +409,9 @@ #![allow(clippy::not_unsafe_ptr_arg_deref)] use crate::cmp::Ordering; -use crate::fmt; -use crate::hash; -use crate::intrinsics; use crate::marker::FnPtr; -use crate::ub_checks; - use crate::mem::{self, MaybeUninit}; +use crate::{fmt, hash, intrinsics, ub_checks}; mod alignment; #[unstable(feature = "ptr_alignment_type", issue = "102070")] @@ -423,12 +419,10 @@ pub use alignment::Alignment; #[stable(feature = "rust1", since = "1.0.0")] #[doc(inline)] -pub use crate::intrinsics::copy_nonoverlapping; - +pub use crate::intrinsics::copy; #[stable(feature = "rust1", since = "1.0.0")] #[doc(inline)] -pub use crate::intrinsics::copy; - +pub use crate::intrinsics::copy_nonoverlapping; #[stable(feature = "rust1", since = "1.0.0")] #[doc(inline)] pub use crate::intrinsics::write_bytes; @@ -606,7 +600,7 @@ pub const fn null_mut<T: ?Sized + Thin>() -> *mut T { /// Without provenance, this pointer is not associated with any actual allocation. Such a /// no-provenance pointer may be used for zero-sized memory accesses (if suitably aligned), but /// non-zero-sized memory accesses with a no-provenance pointer are UB. No-provenance pointers are -/// little more than a usize address in disguise. +/// little more than a `usize` address in disguise. /// /// This is different from `addr as *const T`, which creates a pointer that picks up a previously /// exposed provenance. See [`with_exposed_provenance`] for more details on that operation. @@ -650,7 +644,7 @@ pub const fn dangling<T>() -> *const T { /// Without provenance, this pointer is not associated with any actual allocation. Such a /// no-provenance pointer may be used for zero-sized memory accesses (if suitably aligned), but /// non-zero-sized memory accesses with a no-provenance pointer are UB. No-provenance pointers are -/// little more than a usize address in disguise. +/// little more than a `usize` address in disguise. /// /// This is different from `addr as *mut T`, which creates a pointer that picks up a previously /// exposed provenance. See [`with_exposed_provenance_mut`] for more details on that operation. @@ -687,7 +681,7 @@ pub const fn dangling_mut<T>() -> *mut T { without_provenance_mut(mem::align_of::<T>()) } -/// Convert an address back to a pointer, picking up a previously 'exposed' provenance. +/// Converts an address back to a pointer, picking up a previously 'exposed' provenance. /// /// This is a more rigorously specified alternative to `addr as *const T`. The provenance of the /// returned pointer is that of *any* pointer that was previously exposed by passing it to @@ -735,7 +729,7 @@ where addr as *const T } -/// Convert an address back to a mutable pointer, picking up a previously 'exposed' provenance. +/// Converts an address back to a mutable pointer, picking up a previously 'exposed' provenance. /// /// This is a more rigorously specified alternative to `addr as *mut T`. The provenance of the /// returned pointer is that of *any* pointer that was previously passed to @@ -775,7 +769,7 @@ where addr as *mut T } -/// Convert a reference to a raw pointer. +/// Converts a reference to a raw pointer. /// /// For `r: &T`, `from_ref(r)` is equivalent to `r as *const T` (except for the caveat noted below), /// but is a bit safer since it will never silently change type or mutability, in particular if the @@ -786,7 +780,7 @@ where /// /// The caller must also ensure that the memory the pointer (non-transitively) points to is never /// written to (except inside an `UnsafeCell`) using this pointer or any pointer derived from it. If -/// you need to mutate the pointee, use [`from_mut`]`. Specifically, to turn a mutable reference `m: +/// you need to mutate the pointee, use [`from_mut`]. Specifically, to turn a mutable reference `m: /// &mut T` into `*const T`, prefer `from_mut(m).cast_const()` to obtain a pointer that can later be /// used for mutation. /// @@ -832,7 +826,7 @@ pub const fn from_ref<T: ?Sized>(r: &T) -> *const T { r } -/// Convert a mutable reference to a raw pointer. +/// Converts a mutable reference to a raw pointer. /// /// For `r: &mut T`, `from_mut(r)` is equivalent to `r as *mut T` (except for the caveat noted /// below), but is a bit safer since it will never silently change type or mutability, in particular @@ -1468,7 +1462,7 @@ pub const unsafe fn read<T>(src: *const T) -> T { /// /// # Examples /// -/// Read a usize value from a byte buffer: +/// Read a `usize` value from a byte buffer: /// /// ``` /// use std::mem; @@ -1679,7 +1673,7 @@ pub const unsafe fn write<T>(dst: *mut T, src: T) { /// /// # Examples /// -/// Write a usize value to a byte buffer: +/// Write a `usize` value to a byte buffer: /// /// ``` /// use std::mem; @@ -2014,7 +2008,7 @@ pub(crate) const unsafe fn align_offset<T: Sized>(p: *const T, a: usize) -> usiz let y = cttz_nonzero(a); if x < y { x } else { y } }; - // SAFETY: gcdpow has an upper-bound that’s at most the number of bits in a usize. + // SAFETY: gcdpow has an upper-bound that’s at most the number of bits in a `usize`. let gcd = unsafe { unchecked_shl(1usize, gcdpow) }; // SAFETY: gcd is always greater or equal to 1. if addr & unsafe { unchecked_sub(gcd, 1) } == 0 { @@ -2213,7 +2207,7 @@ impl<F: FnPtr> fmt::Debug for F { } } -/// Create a `const` raw pointer to a place, without creating an intermediate reference. +/// Creates a `const` raw pointer to a place, without creating an intermediate reference. /// /// Creating a reference with `&`/`&mut` is only allowed if the pointer is properly aligned /// and points to initialized data. For cases where those requirements do not hold, @@ -2287,7 +2281,7 @@ pub macro addr_of($place:expr) { &raw const $place } -/// Create a `mut` raw pointer to a place, without creating an intermediate reference. +/// Creates a `mut` raw pointer to a place, without creating an intermediate reference. /// /// Creating a reference with `&`/`&mut` is only allowed if the pointer is properly aligned /// and points to initialized data. For cases where those requirements do not hold, diff --git a/library/core/src/ptr/mut_ptr.rs b/library/core/src/ptr/mut_ptr.rs index 904d6c62dcf..bcf9b889182 100644 --- a/library/core/src/ptr/mut_ptr.rs +++ b/library/core/src/ptr/mut_ptr.rs @@ -60,7 +60,7 @@ impl<T: ?Sized> *mut T { self as _ } - /// Use the pointer value in a new pointer of another type. + /// Uses the pointer value in a new pointer of another type. /// /// In case `meta` is a (fat) pointer to an unsized type, this operation /// will ignore the pointer part, whereas for (thin) pointers to sized diff --git a/library/core/src/ptr/non_null.rs b/library/core/src/ptr/non_null.rs index 796c85d0cac..d6be37a76bb 100644 --- a/library/core/src/ptr/non_null.rs +++ b/library/core/src/ptr/non_null.rs @@ -1,15 +1,13 @@ use crate::cmp::Ordering; -use crate::fmt; -use crate::hash; -use crate::intrinsics; use crate::marker::Unsize; use crate::mem::{MaybeUninit, SizedTypeProperties}; use crate::num::NonZero; use crate::ops::{CoerceUnsized, DispatchFromDyn}; -use crate::ptr; +use crate::pin::PinCoerceUnsized; use crate::ptr::Unique; use crate::slice::{self, SliceIndex}; use crate::ub_checks::assert_unsafe_precondition; +use crate::{fmt, hash, intrinsics, ptr}; /// `*mut T` but non-zero and [covariant]. /// @@ -1171,9 +1169,7 @@ impl<T: ?Sized> NonNull<T> { /// `align`. /// /// If it is not possible to align the pointer, the implementation returns - /// `usize::MAX`. It is permissible for the implementation to *always* - /// return `usize::MAX`. Only your algorithm's performance can depend - /// on getting a usable offset here, not its correctness. + /// `usize::MAX`. /// /// The offset is expressed in number of `T` elements, and not bytes. /// @@ -1181,6 +1177,15 @@ impl<T: ?Sized> NonNull<T> { /// beyond the allocation that the pointer points into. It is up to the caller to ensure that /// the returned offset is correct in all terms other than alignment. /// + /// When this is called during compile-time evaluation (which is unstable), the implementation + /// may return `usize::MAX` in cases where that can never happen at runtime. This is because the + /// actual alignment of pointers is not known yet during compile-time, so an offset with + /// guaranteed alignment can sometimes not be computed. For example, a buffer declared as `[u8; + /// N]` might be allocated at an odd or an even address, but at compile-time this is not yet + /// known, so the execution has to be correct for either choice. It is therefore impossible to + /// find an offset that is guaranteed to be 2-aligned. (This behavior is subject to change, as usual + /// for unstable APIs.) + /// /// # Panics /// /// The function panics if `align` is not a power-of-two. @@ -1727,6 +1732,9 @@ impl<T: ?Sized, U: ?Sized> CoerceUnsized<NonNull<U>> for NonNull<T> where T: Uns #[unstable(feature = "dispatch_from_dyn", issue = "none")] impl<T: ?Sized, U: ?Sized> DispatchFromDyn<NonNull<U>> for NonNull<T> where T: Unsize<U> {} +#[stable(feature = "pin", since = "1.33.0")] +unsafe impl<T: ?Sized> PinCoerceUnsized for NonNull<T> {} + #[stable(feature = "nonnull", since = "1.25.0")] impl<T: ?Sized> fmt::Debug for NonNull<T> { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { diff --git a/library/core/src/ptr/unique.rs b/library/core/src/ptr/unique.rs index b74d691e454..4810ebe01f9 100644 --- a/library/core/src/ptr/unique.rs +++ b/library/core/src/ptr/unique.rs @@ -1,6 +1,7 @@ use crate::fmt; use crate::marker::{PhantomData, Unsize}; use crate::ops::{CoerceUnsized, DispatchFromDyn}; +use crate::pin::PinCoerceUnsized; use crate::ptr::NonNull; /// A wrapper around a raw non-null `*mut T` that indicates that the possessor @@ -166,6 +167,9 @@ impl<T: ?Sized, U: ?Sized> CoerceUnsized<Unique<U>> for Unique<T> where T: Unsiz #[unstable(feature = "ptr_internals", issue = "none")] impl<T: ?Sized, U: ?Sized> DispatchFromDyn<Unique<U>> for Unique<T> where T: Unsize<U> {} +#[unstable(feature = "pin_coerce_unsized_trait", issue = "123430")] +unsafe impl<T: ?Sized> PinCoerceUnsized for Unique<T> {} + #[unstable(feature = "ptr_internals", issue = "none")] impl<T: ?Sized> fmt::Debug for Unique<T> { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { |
