use core::{cell::UnsafeCell, mem::MaybeUninit, ptr::NonNull};
#[inline]
pub fn nonnull_slice_from_raw_parts<T>(ptr: NonNull<T>, len: usize) -> NonNull<[T]> {
unsafe { NonNull::new_unchecked(core::ptr::slice_from_raw_parts_mut(ptr.as_ptr(), len)) }
}
#[inline]
pub unsafe fn nonnull_slice_len<T>(ptr: NonNull<[T]>) -> usize {
(&*(ptr.as_ptr() as *const [MaybeUninit<UnsafeCell<T>>])).len()
}
#[inline]
pub fn nonnull_slice_start<T>(ptr: NonNull<[T]>) -> NonNull<T> {
unsafe { NonNull::new_unchecked(ptr.as_ptr() as *mut T) }
}
#[inline]
pub unsafe fn nonnull_slice_end<T>(ptr: NonNull<[T]>) -> *mut T {
(ptr.as_ptr() as *mut T).wrapping_add(nonnull_slice_len(ptr))
}
macro_rules! nn_field {
($ptr:expr, $($tt:tt)*) => {
core::ptr::addr_of_mut!((*$ptr.as_ptr()).$($tt)*)
};
}
#[inline]
#[rustversion::since(1.84)]
pub unsafe fn round_down(ptr: *mut u8, align: usize) -> *mut u8 {
debug_assert!(align.is_power_of_two());
ptr.map_addr(|addr| addr & !(align - 1))
}
#[inline]
#[rustversion::before(1.84)]
pub unsafe fn round_down(ptr: *mut u8, align: usize) -> *mut u8 {
debug_assert!(align.is_power_of_two());
(ptr as usize & !(align - 1)) as *mut u8
}
#[inline]
#[rustversion::since(1.84)]
pub unsafe fn round_up(ptr: *mut u8, align: usize) -> *mut u8 {
debug_assert!(align.is_power_of_two());
ptr.map_addr(|addr| addr.wrapping_add(align - 1) & !(align - 1))
}
#[inline]
#[rustversion::before(1.84)]
pub unsafe fn round_up(ptr: *mut u8, align: usize) -> *mut u8 {
debug_assert!(align.is_power_of_two());
((ptr as usize).wrapping_add(align - 1) & !(align - 1)) as *mut u8
}