Skip to content

core::ptr: deduplicate more method docs #142101

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
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
64 changes: 2 additions & 62 deletions library/core/src/ptr/const_ptr.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,24 +5,7 @@ use crate::mem::{self, SizedTypeProperties};
use crate::slice::{self, SliceIndex};

impl<T: ?Sized> *const T {
/// Returns `true` if the pointer is null.
///
/// Note that unsized types have many possible null pointers, as only the
/// raw data pointer is considered, not their length, vtable, etc.
/// Therefore, two pointers that are null may still not compare equal to
/// each other.
///
/// # Panics during const evaluation
///
/// If this method is used during const evaluation, and `self` is a pointer
/// that is offset beyond the bounds of the memory it initially pointed to,
/// then there might not be enough information to determine whether the
/// pointer is null. This is because the absolute address in memory is not
/// known at compile time. If the nullness of the pointer cannot be
/// determined, this method will panic.
///
/// In-bounds pointers are never null, so the method will never panic for
/// such pointers.
#[doc = include_str!("docs/is_null.md")]
///
/// # Examples
///
Expand Down Expand Up @@ -1550,50 +1533,7 @@ impl<T> *const [T] {
unsafe { index.get_unchecked(self) }
}

/// Returns `None` if the pointer is null, or else returns a shared slice to
/// the value wrapped in `Some`. In contrast to [`as_ref`], this does not require
/// that the value has to be initialized.
///
/// [`as_ref`]: #method.as_ref
///
/// # Safety
///
/// When calling this method, you have to ensure that *either* the pointer is null *or*
/// all of the following is true:
///
/// * The pointer must be [valid] for reads for `ptr.len() * size_of::<T>()` many bytes,
/// and it must be properly aligned. This means in particular:
///
/// * The entire memory range of this slice must be contained within a single [allocation]!
/// Slices can never span across multiple allocations.
///
/// * The pointer must be aligned even for zero-length slices. One
/// reason for this is that enum layout optimizations may rely on references
/// (including slices of any length) being aligned and non-null to distinguish
/// them from other data. You can obtain a pointer that is usable as `data`
/// for zero-length slices using [`NonNull::dangling()`].
///
/// * The total size `ptr.len() * size_of::<T>()` of the slice must be no larger than `isize::MAX`.
/// See the safety documentation of [`pointer::offset`].
///
/// * You must enforce Rust's aliasing rules, since the returned lifetime `'a` is
/// arbitrarily chosen and does not necessarily reflect the actual lifetime of the data.
/// In particular, while this reference exists, the memory the pointer points to must
/// not get mutated (except inside `UnsafeCell`).
///
/// This applies even if the result of this method is unused!
///
/// See also [`slice::from_raw_parts`][].
///
/// [valid]: crate::ptr#safety
/// [allocation]: crate::ptr#allocation
///
/// # Panics during const evaluation
///
/// This method will panic during const evaluation if the pointer cannot be
/// determined to be null or not. See [`is_null`] for more information.
///
/// [`is_null`]: #method.is_null
#[doc = include_str!("docs/as_uninit_slice.md")]
#[inline]
#[unstable(feature = "ptr_as_uninit", issue = "75402")]
pub const unsafe fn as_uninit_slice<'a>(self) -> Option<&'a [MaybeUninit<T>]> {
Expand Down
44 changes: 44 additions & 0 deletions library/core/src/ptr/docs/as_uninit_slice.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
Returns `None` if the pointer is null, or else returns a shared slice to
the value wrapped in `Some`. In contrast to [`as_ref`], this does not require
that the value has to be initialized.

[`as_ref`]: #method.as_ref

# Safety

When calling this method, you have to ensure that *either* the pointer is null *or*
all of the following is true:

* The pointer must be [valid] for reads for `ptr.len() * size_of::<T>()` many bytes,
and it must be properly aligned. This means in particular:

* The entire memory range of this slice must be contained within a single [allocation]!
Slices can never span across multiple allocations.

* The pointer must be aligned even for zero-length slices. One
reason for this is that enum layout optimizations may rely on references
(including slices of any length) being aligned and non-null to distinguish
them from other data. You can obtain a pointer that is usable as `data`
for zero-length slices using [`NonNull::dangling()`].

* The total size `ptr.len() * size_of::<T>()` of the slice must be no larger than `isize::MAX`.
See the safety documentation of [`pointer::offset`].

* You must enforce Rust's aliasing rules, since the returned lifetime `'a` is
arbitrarily chosen and does not necessarily reflect the actual lifetime of the data.
In particular, while this reference exists, the memory the pointer points to must
not get mutated (except inside `UnsafeCell`).

This applies even if the result of this method is unused!

See also [`slice::from_raw_parts`][].

[valid]: crate::ptr#safety
[allocation]: crate::ptr#allocation

# Panics during const evaluation

This method will panic during const evaluation if the pointer cannot be
determined to be null or not. See [`is_null`] for more information.

[`is_null`]: #method.is_null
18 changes: 18 additions & 0 deletions library/core/src/ptr/docs/is_null.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
Returns `true` if the pointer is null.

Note that unsized types have many possible null pointers, as only the
raw data pointer is considered, not their length, vtable, etc.
Therefore, two pointers that are null may still not compare equal to
each other.

# Panics during const evaluation

If this method is used during const evaluation, and `self` is a pointer
that is offset beyond the bounds of the memory it initially pointed to,
then there might not be enough information to determine whether the
pointer is null. This is because the absolute address in memory is not
known at compile time. If the nullness of the pointer cannot be
determined, this method will panic.

In-bounds pointers are never null, so the method will never panic for
such pointers.
66 changes: 3 additions & 63 deletions library/core/src/ptr/mut_ptr.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,24 +5,7 @@ use crate::mem::{self, SizedTypeProperties};
use crate::slice::{self, SliceIndex};

impl<T: ?Sized> *mut T {
/// Returns `true` if the pointer is null.
///
/// Note that unsized types have many possible null pointers, as only the
/// raw data pointer is considered, not their length, vtable, etc.
/// Therefore, two pointers that are null may still not compare equal to
/// each other.
///
/// # Panics during const evaluation
///
/// If this method is used during const evaluation, and `self` is a pointer
/// that is offset beyond the bounds of the memory it initially pointed to,
/// then there might not be enough information to determine whether the
/// pointer is null. This is because the absolute address in memory is not
/// known at compile time. If the nullness of the pointer cannot be
/// determined, this method will panic.
///
/// In-bounds pointers are never null, so the method will never panic for
/// such pointers.
#[doc = include_str!("docs/is_null.md")]
///
/// # Examples
///
Expand Down Expand Up @@ -1906,53 +1889,10 @@ impl<T> *mut [T] {
unsafe { index.get_unchecked_mut(self) }
}

/// Returns `None` if the pointer is null, or else returns a shared slice to
/// the value wrapped in `Some`. In contrast to [`as_ref`], this does not require
/// that the value has to be initialized.
#[doc = include_str!("docs/as_uninit_slice.md")]
///
/// # See Also
/// For the mutable counterpart see [`as_uninit_slice_mut`].
///
/// [`as_ref`]: pointer#method.as_ref-1
/// [`as_uninit_slice_mut`]: #method.as_uninit_slice_mut
///
/// # Safety
///
/// When calling this method, you have to ensure that *either* the pointer is null *or*
/// all of the following is true:
///
/// * The pointer must be [valid] for reads for `ptr.len() * size_of::<T>()` many bytes,
/// and it must be properly aligned. This means in particular:
///
/// * The entire memory range of this slice must be contained within a single [allocation]!
/// Slices can never span across multiple allocations.
///
/// * The pointer must be aligned even for zero-length slices. One
/// reason for this is that enum layout optimizations may rely on references
/// (including slices of any length) being aligned and non-null to distinguish
/// them from other data. You can obtain a pointer that is usable as `data`
/// for zero-length slices using [`NonNull::dangling()`].
///
/// * The total size `ptr.len() * size_of::<T>()` of the slice must be no larger than `isize::MAX`.
/// See the safety documentation of [`pointer::offset`].
///
/// * You must enforce Rust's aliasing rules, since the returned lifetime `'a` is
/// arbitrarily chosen and does not necessarily reflect the actual lifetime of the data.
/// In particular, while this reference exists, the memory the pointer points to must
/// not get mutated (except inside `UnsafeCell`).
///
/// This applies even if the result of this method is unused!
///
/// See also [`slice::from_raw_parts`][].
///
/// [valid]: crate::ptr#safety
/// [allocation]: crate::ptr#allocation
///
/// # Panics during const evaluation
///
/// This method will panic during const evaluation if the pointer cannot be
/// determined to be null or not. See [`is_null`] for more information.
///
/// [`is_null`]: #method.is_null-1
#[inline]
#[unstable(feature = "ptr_as_uninit", issue = "75402")]
pub const unsafe fn as_uninit_slice<'a>(self) -> Option<&'a [MaybeUninit<T>]> {
Expand Down
Loading