Rollup merge of #90958 - WaffleLapkin:const_align_offset, r=oli-obk

Mark `<*const _>::align_offset` and `<*mut _>::align_offset` as `const fn`

This PR marks the following APIs as `const`:
```rust
impl<T> *const T {
    pub const fn align_offset(self, align: usize) -> usize;
}

impl<T> *mut T {
    pub const fn align_offset(self, align: usize) -> usize;
}
```

`const` implementation simply returns `usize::MAX`.

---

Previous discussion: https://github.com/rust-lang/rust/pull/90607#discussion_r743638164

---

r? `@oli-obk`
This commit is contained in:
Matthias Krüger 2021-11-16 23:58:27 +01:00 committed by GitHub
commit 0c3a662ba9
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 36 additions and 6 deletions

View file

@ -879,15 +879,30 @@ impl<T: ?Sized> *const T {
/// # } }
/// ```
#[stable(feature = "align_offset", since = "1.36.0")]
pub fn align_offset(self, align: usize) -> usize
#[rustc_const_unstable(feature = "const_align_offset", issue = "90962")]
pub const fn align_offset(self, align: usize) -> usize
where
T: Sized,
{
if !align.is_power_of_two() {
panic!("align_offset: align is not a power-of-two");
}
// SAFETY: `align` has been checked to be a power of 2 above
unsafe { align_offset(self, align) }
fn rt_impl<T>(p: *const T, align: usize) -> usize {
// SAFETY: `align` has been checked to be a power of 2 above
unsafe { align_offset(p, align) }
}
const fn ctfe_impl<T>(_: *const T, _: usize) -> usize {
usize::MAX
}
// SAFETY:
// It is permisseble for `align_offset` to always return `usize::MAX`,
// algorithm correctness can not depend on `align_offset` returning non-max values.
//
// As such the behaviour can't change after replacing `align_offset` with `usize::MAX`, only performance can.
unsafe { intrinsics::const_eval_select((self, align), ctfe_impl, rt_impl) }
}
}

View file

@ -1142,15 +1142,30 @@ impl<T: ?Sized> *mut T {
/// # } }
/// ```
#[stable(feature = "align_offset", since = "1.36.0")]
pub fn align_offset(self, align: usize) -> usize
#[rustc_const_unstable(feature = "const_align_offset", issue = "90962")]
pub const fn align_offset(self, align: usize) -> usize
where
T: Sized,
{
if !align.is_power_of_two() {
panic!("align_offset: align is not a power-of-two");
}
// SAFETY: `align` has been checked to be a power of 2 above
unsafe { align_offset(self, align) }
fn rt_impl<T>(p: *mut T, align: usize) -> usize {
// SAFETY: `align` has been checked to be a power of 2 above
unsafe { align_offset(p, align) }
}
const fn ctfe_impl<T>(_: *mut T, _: usize) -> usize {
usize::MAX
}
// SAFETY:
// It is permisseble for `align_offset` to always return `usize::MAX`,
// algorithm correctness can not depend on `align_offset` returning non-max values.
//
// As such the behaviour can't change after replacing `align_offset` with `usize::MAX`, only performance can.
unsafe { intrinsics::const_eval_select((self, align), ctfe_impl, rt_impl) }
}
}