Skip to content

Commit 1906c6f

Browse files
SimonSapinCentril
authored andcommitted
Add MaybeUninit methods uninit_array, slice_get_ref, slice_get_mut
1 parent 7a76fe7 commit 1906c6f

File tree

1 file changed

+57
-0
lines changed

1 file changed

+57
-0
lines changed

src/libcore/mem/maybe_uninit.rs

+57
Original file line numberDiff line numberDiff line change
@@ -258,6 +258,37 @@ impl<T> MaybeUninit<T> {
258258
MaybeUninit { uninit: () }
259259
}
260260

261+
/// Create a new array of `MaybeUninit<T>` items, in an uninitialized state.
262+
///
263+
/// # Examples
264+
///
265+
/// ```
266+
/// #![feature(maybe_uninit_uninit_array, maybe_uninit_extra, maybe_uninit_slice_assume_init)]
267+
/// use std::mem::MaybeUninit;
268+
///
269+
/// let input = b"Foo";
270+
/// let f = u8::to_ascii_uppercase;
271+
///
272+
/// let mut buffer: [MaybeUninit<u8>; 32] = MaybeUninit::uninit_array();
273+
/// let vec;
274+
/// let output = if let Some(buffer) = buffer.get_mut(..input.len()) {
275+
/// buffer.iter_mut().zip(input).for_each(|(a, b)| { a.write(f(b)); });
276+
/// unsafe { MaybeUninit::slice_get_ref(buffer) }
277+
/// } else {
278+
/// vec = input.iter().map(f).collect::<Vec<u8>>();
279+
/// &vec
280+
/// };
281+
///
282+
/// assert_eq!(output, b"FOO");
283+
/// ```
284+
#[unstable(feature = "maybe_uninit_uninit_array", issue = "0")]
285+
#[inline(always)]
286+
pub fn uninit_array<const LEN: usize>() -> [Self; LEN] {
287+
unsafe {
288+
MaybeUninit::<[MaybeUninit<T>; LEN]>::uninit().assume_init()
289+
}
290+
}
291+
261292
/// A promotable constant, equivalent to `uninit()`.
262293
#[unstable(feature = "internal_uninit_const", issue = "0",
263294
reason = "hack to work around promotability")]
@@ -690,6 +721,32 @@ impl<T> MaybeUninit<T> {
690721
&mut *self.value
691722
}
692723

724+
/// Get a slice of assume-initialized items.
725+
///
726+
/// # Safety
727+
///
728+
/// It is up to the caller to guarantee that the `MaybeUninit<T>` items
729+
/// really are in an initialized state.
730+
/// Calling this when the content is not yet fully initialized causes undefined behavior.
731+
#[unstable(feature = "maybe_uninit_slice_assume_init", issue = "0")]
732+
#[inline(always)]
733+
pub unsafe fn slice_get_ref(slice: &[Self]) -> &[T] {
734+
&*(slice as *const [Self] as *const [T])
735+
}
736+
737+
/// Get a mutable slice of assume-initialized items.
738+
///
739+
/// # Safety
740+
///
741+
/// It is up to the caller to guarantee that the `MaybeUninit<T>` items
742+
/// really are in an initialized state.
743+
/// Calling this when the content is not yet fully initialized causes undefined behavior.
744+
#[unstable(feature = "maybe_uninit_slice_assume_init", issue = "0")]
745+
#[inline(always)]
746+
pub unsafe fn slice_get_mut(slice: &mut [Self]) -> &mut [T] {
747+
&mut *(slice as *mut [Self] as *mut [T])
748+
}
749+
693750
/// Gets a pointer to the first element of the array.
694751
#[unstable(feature = "maybe_uninit_slice", issue = "63569")]
695752
#[inline(always)]

0 commit comments

Comments
 (0)