Avoid regression in consteval#2286
Conversation
| // &[u8] and &[T::ULE] are the same slice with different length metadata. | ||
| let (data, mut metadata): (usize, usize) = core::mem::transmute(bytes); | ||
| // n.b. be careful here, this might hit https://github.com/rust-lang/rust/issues/99923 | ||
| let data = bytes.as_ptr(); | ||
| let mut metadata = bytes.len(); | ||
| metadata /= core::mem::size_of::<T::ULE>(); | ||
| Self::Borrowed(core::mem::transmute((data, metadata))) |
There was a problem hiding this comment.
NB: the proper way to do this will be stable in 1.64:
| /// `bytes` need to be an output from [`ZeroSlice::as_bytes()`]. | ||
| pub const unsafe fn from_bytes_unchecked(bytes: &'a [u8]) -> Self { | ||
| // &[u8] and &[T::ULE] are the same slice with different length metadata. | ||
| let (data, mut metadata): (usize, usize) = core::mem::transmute(bytes); |
There was a problem hiding this comment.
FWIW the old code most likely has UB. Quoting from the transmute docs:
Transmuting pointers to integers in a const context is undefined behavior. Any attempt to use the resulting value for integer operations will abort const-evaluation.
So, if from_bytes_unchecked is ever called with a non-zero-sized slice (or a zero-sized slice that actually uses a pointer to some allocated memory), then this is definitely UB. This PR is a UB-fix, not a rustc-regression-workaround.
There was a problem hiding this comment.
Yeah I'm aware it's UB.
As I've stated in rust-lang/rust#99923, I still consider things like this a regression as long as the docs on undefined behavior are incomplete, scattered, and in flux, and avoiding UB is not practically possible for unsafe Rust programmers.
Avoids rust-lang/rust#99923