I have this wrapper around [T]::align_to::<U>()
which is used strictly in contexts where the input slice is supposed to be aligned correctly for U already. If it isn't, I'd like to print out the actual alignment of the slice for diagnostics. There doesn't seem to be a good way to do that. I found a clunky way, shown below. Have I missed something? It seems like this ought to be an intrinsic method of slices and/or raw pointers... (note: mem::align_of_val
does something different)
use core::any::type_name;
use core::mem::{align_of, size_of};
pub fn view_head_as<S>(slice: &[u8]) -> &S {
// SAFETY: In the full program S is constrained to be a type for which
// the transmutation performed by `align_to` is safe.
let (prefix, s_slice, _) = unsafe { slice.align_to::<S>() };
if !prefix.is_empty() {
// There appears to be no better way to query the actual
// alignment of a pointer than this. I may have missed
// something.
let p = slice.as_ptr();
let mut alignment = align_of::<S>() >> 1;
while alignment > 1 {
if p.align_offset(alignment) == 0 {
break;
}
alignment >>= 1;
}
panic!(
"slice not properly aligned for {}: {} < {}",
type_name::<S>(),
alignment,
align_of::<S>()
);
}
s_slice.get(0).unwrap_or_else(|| {
panic!(
"slice too small to view as {}: {} < {}",
type_name::<S>(),
slice.len(),
size_of::<S>()
)
})
}