Skip to content
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.

Commit 507583a

Browse files
committedMar 8, 2024
align_offset, align_to: no longer allow implementations to spuriously fail to align
1 parent d2e8ecd commit 507583a

File tree

3 files changed

+24
-16
lines changed

3 files changed

+24
-16
lines changed
 

‎library/core/src/ptr/const_ptr.rs

+10-3
Original file line numberDiff line numberDiff line change
@@ -1322,9 +1322,7 @@ impl<T: ?Sized> *const T {
13221322
/// `align`.
13231323
///
13241324
/// If it is not possible to align the pointer, the implementation returns
1325-
/// `usize::MAX`. It is permissible for the implementation to *always*
1326-
/// return `usize::MAX`. Only your algorithm's performance can depend
1327-
/// on getting a usable offset here, not its correctness.
1325+
/// `usize::MAX`.
13281326
///
13291327
/// The offset is expressed in number of `T` elements, and not bytes. The value returned can be
13301328
/// used with the `wrapping_add` method.
@@ -1333,6 +1331,15 @@ impl<T: ?Sized> *const T {
13331331
/// beyond the allocation that the pointer points into. It is up to the caller to ensure that
13341332
/// the returned offset is correct in all terms other than alignment.
13351333
///
1334+
/// When this is called during compile-time evaluation (which is unstable), the implementation
1335+
/// may return `usize::MAX` in cases where that can never happen at runtime. This is because the
1336+
/// actual alignment of pointers is not known yet during compile-time, so an offset with
1337+
/// guaranteed alignment can sometimes not be computed. For example, a buffer declared as `[u8;
1338+
/// N]` might be allocated at an odd or an even address, but at compile-time this is not yet
1339+
/// known, so the execution has to be correct for either choice. It is therefore impossible to
1340+
/// find an offset that is guaranteed to be 2-aligned. (This behavior is subject to change, as usual
1341+
/// for unstable APIs.)
1342+
///
13361343
/// # Panics
13371344
///
13381345
/// The function panics if `align` is not a power-of-two.

‎library/core/src/ptr/mut_ptr.rs

+10-3
Original file line numberDiff line numberDiff line change
@@ -1585,9 +1585,7 @@ impl<T: ?Sized> *mut T {
15851585
/// `align`.
15861586
///
15871587
/// If it is not possible to align the pointer, the implementation returns
1588-
/// `usize::MAX`. It is permissible for the implementation to *always*
1589-
/// return `usize::MAX`. Only your algorithm's performance can depend
1590-
/// on getting a usable offset here, not its correctness.
1588+
/// `usize::MAX`.
15911589
///
15921590
/// The offset is expressed in number of `T` elements, and not bytes. The value returned can be
15931591
/// used with the `wrapping_add` method.
@@ -1596,6 +1594,15 @@ impl<T: ?Sized> *mut T {
15961594
/// beyond the allocation that the pointer points into. It is up to the caller to ensure that
15971595
/// the returned offset is correct in all terms other than alignment.
15981596
///
1597+
/// When this is called during compile-time evaluation (which is unstable), the implementation
1598+
/// may return `usize::MAX` in cases where that can never happen at runtime. This is because the
1599+
/// actual alignment of pointers is not known yet during compile-time, so an offset with
1600+
/// guaranteed alignment can sometimes not be computed. For example, a buffer declared as `[u8;
1601+
/// N]` might be allocated at an odd or an even address, but at compile-time this is not yet
1602+
/// known, so the execution has to be correct for either choice. It is therefore impossible to
1603+
/// find an offset that is guaranteed to be 2-aligned. (This behavior is subject to change, as usual
1604+
/// for unstable APIs.)
1605+
///
15991606
/// # Panics
16001607
///
16011608
/// The function panics if `align` is not a power-of-two.

‎library/core/src/slice/mod.rs

+4-10
Original file line numberDiff line numberDiff line change
@@ -3756,11 +3756,8 @@ impl<T> [T] {
37563756
/// maintained.
37573757
///
37583758
/// This method splits the slice into three distinct slices: prefix, correctly aligned middle
3759-
/// slice of a new type, and the suffix slice. How exactly the slice is split up is not
3760-
/// specified; the middle part may be smaller than necessary. However, if this fails to return a
3761-
/// maximal middle part, that is because code is running in a context where performance does not
3762-
/// matter, such as a sanitizer attempting to find alignment bugs. Regular code running
3763-
/// in a default (debug or release) execution *will* return a maximal middle part.
3759+
/// slice of a new type, and the suffix slice. The middle part will be as big as possible under
3760+
/// the given alignment constraint and element size.
37643761
///
37653762
/// This method has no purpose when either input element `T` or output element `U` are
37663763
/// zero-sized and will return the original slice without splitting anything.
@@ -3824,11 +3821,8 @@ impl<T> [T] {
38243821
/// types is maintained.
38253822
///
38263823
/// This method splits the slice into three distinct slices: prefix, correctly aligned middle
3827-
/// slice of a new type, and the suffix slice. How exactly the slice is split up is not
3828-
/// specified; the middle part may be smaller than necessary. However, if this fails to return a
3829-
/// maximal middle part, that is because code is running in a context where performance does not
3830-
/// matter, such as a sanitizer attempting to find alignment bugs. Regular code running
3831-
/// in a default (debug or release) execution *will* return a maximal middle part.
3824+
/// slice of a new type, and the suffix slice. The middle part will be as big as possible under
3825+
/// the given alignment constraint and element size.
38323826
///
38333827
/// This method has no purpose when either input element `T` or output element `U` are
38343828
/// zero-sized and will return the original slice without splitting anything.

0 commit comments

Comments
 (0)
Failed to load comments.