Rollup merge of #135394 - clarfonthey:uninit-slices-part-2, r=tgross35
`MaybeUninit` inherent slice methods part 2 These were moved out of #129259 since they require additional libs-api approval. Tracking issue: #117428. New API surface: ```rust impl<T> [MaybeUninit<T>] { // replacing fill; renamed to avoid conflict pub fn write_filled(&mut self, value: T) -> &mut [T] where T: Clone; // replacing fill_with; renamed to avoid conflict pub fn write_with<F>(&mut self, value: F) -> &mut [T] where F: FnMut() -> T; // renamed to remove "fill" terminology, since this is closer to the write_*_of_slice methods pub fn write_iter<I>(&mut self, iter: I) -> (&mut [T], &mut Self) where I: Iterator<Item = T>; } ``` Relevant motivation for these methods; see #129259 for earlier methods' motiviations. * I chose `write_filled` since `filled` is being used as an object here, whereas it's being used as an action in `fill`. * I chose `write_with` instead of `write_filled_with` since it's shorter and still matches well. * I chose `write_iter` because it feels completely different from the fill methods, and still has the intent clear. In all of the methods, it felt appropriate to ensure that they contained `write` to clarify that they are effectively just special ways of doing `MaybeUninit::write` for each element of a slice. Tracking issue: https://github.com/rust-lang/rust/issues/117428 r? libs-api
This commit is contained in:
commit
d46cc71f54
3 changed files with 209 additions and 168 deletions
|
@ -1065,161 +1065,46 @@ impl<T> MaybeUninit<T> {
|
|||
this.write_clone_of_slice(src)
|
||||
}
|
||||
|
||||
/// Fills a slice with elements by cloning `value`, returning a mutable reference to the now
|
||||
/// initialized contents of the slice.
|
||||
/// Any previously initialized elements will not be dropped.
|
||||
///
|
||||
/// This is similar to [`slice::fill`].
|
||||
///
|
||||
/// # Panics
|
||||
///
|
||||
/// This function will panic if any call to `Clone` panics.
|
||||
///
|
||||
/// If such a panic occurs, any elements previously initialized during this operation will be
|
||||
/// dropped.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// ```
|
||||
/// #![feature(maybe_uninit_fill)]
|
||||
/// use std::mem::MaybeUninit;
|
||||
///
|
||||
/// let mut buf = [const { MaybeUninit::uninit() }; 10];
|
||||
/// let initialized = MaybeUninit::fill(&mut buf, 1);
|
||||
/// assert_eq!(initialized, &mut [1; 10]);
|
||||
/// ```
|
||||
#[doc(alias = "memset")]
|
||||
/// Deprecated version of [`slice::write_filled`].
|
||||
#[unstable(feature = "maybe_uninit_fill", issue = "117428")]
|
||||
pub fn fill(this: &mut [MaybeUninit<T>], value: T) -> &mut [T]
|
||||
#[deprecated(
|
||||
note = "replaced by inherent write_filled method; will eventually be removed",
|
||||
since = "1.83.0"
|
||||
)]
|
||||
pub fn fill<'a>(this: &'a mut [MaybeUninit<T>], value: T) -> &'a mut [T]
|
||||
where
|
||||
T: Clone,
|
||||
{
|
||||
SpecFill::spec_fill(this, value);
|
||||
// SAFETY: Valid elements have just been filled into `this` so it is initialized
|
||||
unsafe { this.assume_init_mut() }
|
||||
this.write_filled(value)
|
||||
}
|
||||
|
||||
/// Fills a slice with elements returned by calling a closure repeatedly.
|
||||
///
|
||||
/// This method uses a closure to create new values. If you'd rather `Clone` a given value, use
|
||||
/// [`MaybeUninit::fill`]. If you want to use the `Default` trait to generate values, you can
|
||||
/// pass [`Default::default`] as the argument.
|
||||
///
|
||||
/// # Panics
|
||||
///
|
||||
/// This function will panic if any call to the provided closure panics.
|
||||
///
|
||||
/// If such a panic occurs, any elements previously initialized during this operation will be
|
||||
/// dropped.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// ```
|
||||
/// #![feature(maybe_uninit_fill)]
|
||||
/// use std::mem::MaybeUninit;
|
||||
///
|
||||
/// let mut buf = [const { MaybeUninit::<i32>::uninit() }; 10];
|
||||
/// let initialized = MaybeUninit::fill_with(&mut buf, Default::default);
|
||||
/// assert_eq!(initialized, &mut [0; 10]);
|
||||
/// ```
|
||||
/// Deprecated version of [`slice::write_with`].
|
||||
#[unstable(feature = "maybe_uninit_fill", issue = "117428")]
|
||||
pub fn fill_with<F>(this: &mut [MaybeUninit<T>], mut f: F) -> &mut [T]
|
||||
#[deprecated(
|
||||
note = "replaced by inherent write_with method; will eventually be removed",
|
||||
since = "1.83.0"
|
||||
)]
|
||||
pub fn fill_with<'a, F>(this: &'a mut [MaybeUninit<T>], mut f: F) -> &'a mut [T]
|
||||
where
|
||||
F: FnMut() -> T,
|
||||
{
|
||||
let mut guard = Guard { slice: this, initialized: 0 };
|
||||
|
||||
for element in guard.slice.iter_mut() {
|
||||
element.write(f());
|
||||
guard.initialized += 1;
|
||||
}
|
||||
|
||||
super::forget(guard);
|
||||
|
||||
// SAFETY: Valid elements have just been written into `this` so it is initialized
|
||||
unsafe { this.assume_init_mut() }
|
||||
this.write_with(|_| f())
|
||||
}
|
||||
|
||||
/// Fills a slice with elements yielded by an iterator until either all elements have been
|
||||
/// initialized or the iterator is empty.
|
||||
///
|
||||
/// Returns two slices. The first slice contains the initialized portion of the original slice.
|
||||
/// The second slice is the still-uninitialized remainder of the original slice.
|
||||
///
|
||||
/// # Panics
|
||||
///
|
||||
/// This function panics if the iterator's `next` function panics.
|
||||
///
|
||||
/// If such a panic occurs, any elements previously initialized during this operation will be
|
||||
/// dropped.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// Completely filling the slice:
|
||||
///
|
||||
/// ```
|
||||
/// #![feature(maybe_uninit_fill)]
|
||||
/// use std::mem::MaybeUninit;
|
||||
///
|
||||
/// let mut buf = [const { MaybeUninit::uninit() }; 5];
|
||||
///
|
||||
/// let iter = [1, 2, 3].into_iter().cycle();
|
||||
/// let (initialized, remainder) = MaybeUninit::fill_from(&mut buf, iter);
|
||||
///
|
||||
/// assert_eq!(initialized, &mut [1, 2, 3, 1, 2]);
|
||||
/// assert_eq!(remainder.len(), 0);
|
||||
/// ```
|
||||
///
|
||||
/// Partially filling the slice:
|
||||
///
|
||||
/// ```
|
||||
/// #![feature(maybe_uninit_fill)]
|
||||
/// use std::mem::MaybeUninit;
|
||||
///
|
||||
/// let mut buf = [const { MaybeUninit::uninit() }; 5];
|
||||
/// let iter = [1, 2];
|
||||
/// let (initialized, remainder) = MaybeUninit::fill_from(&mut buf, iter);
|
||||
///
|
||||
/// assert_eq!(initialized, &mut [1, 2]);
|
||||
/// assert_eq!(remainder.len(), 3);
|
||||
/// ```
|
||||
///
|
||||
/// Checking an iterator after filling a slice:
|
||||
///
|
||||
/// ```
|
||||
/// #![feature(maybe_uninit_fill)]
|
||||
/// use std::mem::MaybeUninit;
|
||||
///
|
||||
/// let mut buf = [const { MaybeUninit::uninit() }; 3];
|
||||
/// let mut iter = [1, 2, 3, 4, 5].into_iter();
|
||||
/// let (initialized, remainder) = MaybeUninit::fill_from(&mut buf, iter.by_ref());
|
||||
///
|
||||
/// assert_eq!(initialized, &mut [1, 2, 3]);
|
||||
/// assert_eq!(remainder.len(), 0);
|
||||
/// assert_eq!(iter.as_slice(), &[4, 5]);
|
||||
/// ```
|
||||
/// Deprecated version of [`slice::write_iter`].
|
||||
#[unstable(feature = "maybe_uninit_fill", issue = "117428")]
|
||||
pub fn fill_from<I>(this: &mut [MaybeUninit<T>], it: I) -> (&mut [T], &mut [MaybeUninit<T>])
|
||||
#[deprecated(
|
||||
note = "replaced by inherent write_iter method; will eventually be removed",
|
||||
since = "1.83.0"
|
||||
)]
|
||||
pub fn fill_from<'a, I>(
|
||||
this: &'a mut [MaybeUninit<T>],
|
||||
it: I,
|
||||
) -> (&'a mut [T], &'a mut [MaybeUninit<T>])
|
||||
where
|
||||
I: IntoIterator<Item = T>,
|
||||
{
|
||||
let iter = it.into_iter();
|
||||
let mut guard = Guard { slice: this, initialized: 0 };
|
||||
|
||||
for (element, val) in guard.slice.iter_mut().zip(iter) {
|
||||
element.write(val);
|
||||
guard.initialized += 1;
|
||||
}
|
||||
|
||||
let initialized_len = guard.initialized;
|
||||
super::forget(guard);
|
||||
|
||||
// SAFETY: guard.initialized <= this.len()
|
||||
let (initted, remainder) = unsafe { this.split_at_mut_unchecked(initialized_len) };
|
||||
|
||||
// SAFETY: Valid elements have just been written into `init`, so that portion
|
||||
// of `this` is initialized.
|
||||
(unsafe { initted.assume_init_mut() }, remainder)
|
||||
this.write_iter(it)
|
||||
}
|
||||
|
||||
/// Deprecated version of [`slice::as_bytes`].
|
||||
|
@ -1380,6 +1265,163 @@ impl<T> [MaybeUninit<T>] {
|
|||
unsafe { self.assume_init_mut() }
|
||||
}
|
||||
|
||||
/// Fills a slice with elements by cloning `value`, returning a mutable reference to the now
|
||||
/// initialized contents of the slice.
|
||||
/// Any previously initialized elements will not be dropped.
|
||||
///
|
||||
/// This is similar to [`slice::fill`].
|
||||
///
|
||||
/// # Panics
|
||||
///
|
||||
/// This function will panic if any call to `Clone` panics.
|
||||
///
|
||||
/// If such a panic occurs, any elements previously initialized during this operation will be
|
||||
/// dropped.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// ```
|
||||
/// #![feature(maybe_uninit_fill)]
|
||||
/// use std::mem::MaybeUninit;
|
||||
///
|
||||
/// let mut buf = [const { MaybeUninit::uninit() }; 10];
|
||||
/// let initialized = buf.write_filled(1);
|
||||
/// assert_eq!(initialized, &mut [1; 10]);
|
||||
/// ```
|
||||
#[doc(alias = "memset")]
|
||||
#[unstable(feature = "maybe_uninit_fill", issue = "117428")]
|
||||
pub fn write_filled(&mut self, value: T) -> &mut [T]
|
||||
where
|
||||
T: Clone,
|
||||
{
|
||||
SpecFill::spec_fill(self, value);
|
||||
// SAFETY: Valid elements have just been filled into `self` so it is initialized
|
||||
unsafe { self.assume_init_mut() }
|
||||
}
|
||||
|
||||
/// Fills a slice with elements returned by calling a closure for each index.
|
||||
///
|
||||
/// This method uses a closure to create new values. If you'd rather `Clone` a given value, use
|
||||
/// [`MaybeUninit::fill`]. If you want to use the `Default` trait to generate values, you can
|
||||
/// pass [`|_| Default::default()`][Default::default] as the argument.
|
||||
///
|
||||
/// # Panics
|
||||
///
|
||||
/// This function will panic if any call to the provided closure panics.
|
||||
///
|
||||
/// If such a panic occurs, any elements previously initialized during this operation will be
|
||||
/// dropped.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// ```
|
||||
/// #![feature(maybe_uninit_fill)]
|
||||
/// use std::mem::MaybeUninit;
|
||||
///
|
||||
/// let mut buf = [const { MaybeUninit::<usize>::uninit() }; 5];
|
||||
/// let initialized = buf.write_with(|idx| idx + 1);
|
||||
/// assert_eq!(initialized, &mut [1, 2, 3, 4, 5]);
|
||||
/// ```
|
||||
#[unstable(feature = "maybe_uninit_fill", issue = "117428")]
|
||||
pub fn write_with<F>(&mut self, mut f: F) -> &mut [T]
|
||||
where
|
||||
F: FnMut(usize) -> T,
|
||||
{
|
||||
let mut guard = Guard { slice: self, initialized: 0 };
|
||||
|
||||
for (idx, element) in guard.slice.iter_mut().enumerate() {
|
||||
element.write(f(idx));
|
||||
guard.initialized += 1;
|
||||
}
|
||||
|
||||
super::forget(guard);
|
||||
|
||||
// SAFETY: Valid elements have just been written into `this` so it is initialized
|
||||
unsafe { self.assume_init_mut() }
|
||||
}
|
||||
|
||||
/// Fills a slice with elements yielded by an iterator until either all elements have been
|
||||
/// initialized or the iterator is empty.
|
||||
///
|
||||
/// Returns two slices. The first slice contains the initialized portion of the original slice.
|
||||
/// The second slice is the still-uninitialized remainder of the original slice.
|
||||
///
|
||||
/// # Panics
|
||||
///
|
||||
/// This function panics if the iterator's `next` function panics.
|
||||
///
|
||||
/// If such a panic occurs, any elements previously initialized during this operation will be
|
||||
/// dropped.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// Completely filling the slice:
|
||||
///
|
||||
/// ```
|
||||
/// #![feature(maybe_uninit_fill)]
|
||||
/// use std::mem::MaybeUninit;
|
||||
///
|
||||
/// let mut buf = [const { MaybeUninit::uninit() }; 5];
|
||||
///
|
||||
/// let iter = [1, 2, 3].into_iter().cycle();
|
||||
/// let (initialized, remainder) = buf.write_iter(iter);
|
||||
///
|
||||
/// assert_eq!(initialized, &mut [1, 2, 3, 1, 2]);
|
||||
/// assert_eq!(remainder.len(), 0);
|
||||
/// ```
|
||||
///
|
||||
/// Partially filling the slice:
|
||||
///
|
||||
/// ```
|
||||
/// #![feature(maybe_uninit_fill)]
|
||||
/// use std::mem::MaybeUninit;
|
||||
///
|
||||
/// let mut buf = [const { MaybeUninit::uninit() }; 5];
|
||||
/// let iter = [1, 2];
|
||||
/// let (initialized, remainder) = buf.write_iter(iter);
|
||||
///
|
||||
/// assert_eq!(initialized, &mut [1, 2]);
|
||||
/// assert_eq!(remainder.len(), 3);
|
||||
/// ```
|
||||
///
|
||||
/// Checking an iterator after filling a slice:
|
||||
///
|
||||
/// ```
|
||||
/// #![feature(maybe_uninit_fill)]
|
||||
/// use std::mem::MaybeUninit;
|
||||
///
|
||||
/// let mut buf = [const { MaybeUninit::uninit() }; 3];
|
||||
/// let mut iter = [1, 2, 3, 4, 5].into_iter();
|
||||
/// let (initialized, remainder) = buf.write_iter(iter.by_ref());
|
||||
///
|
||||
/// assert_eq!(initialized, &mut [1, 2, 3]);
|
||||
/// assert_eq!(remainder.len(), 0);
|
||||
/// assert_eq!(iter.as_slice(), &[4, 5]);
|
||||
/// ```
|
||||
#[unstable(feature = "maybe_uninit_fill", issue = "117428")]
|
||||
pub fn write_iter<I>(&mut self, it: I) -> (&mut [T], &mut [MaybeUninit<T>])
|
||||
where
|
||||
I: IntoIterator<Item = T>,
|
||||
{
|
||||
let iter = it.into_iter();
|
||||
let mut guard = Guard { slice: self, initialized: 0 };
|
||||
|
||||
for (element, val) in guard.slice.iter_mut().zip(iter) {
|
||||
element.write(val);
|
||||
guard.initialized += 1;
|
||||
}
|
||||
|
||||
let initialized_len = guard.initialized;
|
||||
super::forget(guard);
|
||||
|
||||
// SAFETY: guard.initialized <= self.len()
|
||||
let (initted, remainder) = unsafe { self.split_at_mut_unchecked(initialized_len) };
|
||||
|
||||
// SAFETY: Valid elements have just been written into `init`, so that portion
|
||||
// of `this` is initialized.
|
||||
(unsafe { initted.assume_init_mut() }, remainder)
|
||||
}
|
||||
|
||||
/// Returns the contents of this `MaybeUninit` as a slice of potentially uninitialized bytes.
|
||||
///
|
||||
/// Note that even if the contents of a `MaybeUninit` have been initialized, the value may still
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
use core::mem::*;
|
||||
use core::ptr;
|
||||
use core::{array, ptr};
|
||||
#[cfg(panic = "unwind")]
|
||||
use std::rc::Rc;
|
||||
|
||||
|
@ -327,11 +327,11 @@ fn uninit_write_clone_of_slice_no_drop() {
|
|||
}
|
||||
|
||||
#[test]
|
||||
fn uninit_fill() {
|
||||
fn uninit_write_filled() {
|
||||
let mut dst = [MaybeUninit::new(255); 64];
|
||||
let expect = [0; 64];
|
||||
|
||||
assert_eq!(MaybeUninit::fill(&mut dst, 0), &expect);
|
||||
assert_eq!(dst.write_filled(0), &expect);
|
||||
}
|
||||
|
||||
#[cfg(panic = "unwind")]
|
||||
|
@ -352,7 +352,7 @@ impl Clone for CloneUntilPanic {
|
|||
|
||||
#[test]
|
||||
#[cfg(panic = "unwind")]
|
||||
fn uninit_fill_clone_panic_drop() {
|
||||
fn uninit_write_filled_panic_drop() {
|
||||
use std::panic;
|
||||
|
||||
let rc = Rc::new(());
|
||||
|
@ -361,7 +361,7 @@ fn uninit_fill_clone_panic_drop() {
|
|||
|
||||
let src = CloneUntilPanic { limit: 3, rc: rc.clone() };
|
||||
let err = panic::catch_unwind(panic::AssertUnwindSafe(|| {
|
||||
MaybeUninit::fill(&mut dst, src);
|
||||
dst.write_filled(src);
|
||||
}));
|
||||
|
||||
match err {
|
||||
|
@ -378,23 +378,23 @@ fn uninit_fill_clone_panic_drop() {
|
|||
|
||||
#[test]
|
||||
#[cfg(panic = "unwind")]
|
||||
fn uninit_fill_clone_no_drop_clones() {
|
||||
fn uninit_write_filled_no_drop_clones() {
|
||||
let mut dst = [MaybeUninit::uninit(), MaybeUninit::uninit(), MaybeUninit::uninit()];
|
||||
|
||||
MaybeUninit::fill(&mut dst, Bomb);
|
||||
dst.write_filled(Bomb);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn uninit_fill_with() {
|
||||
let mut dst = [MaybeUninit::new(255); 64];
|
||||
let expect = [0; 64];
|
||||
fn uninit_write_with() {
|
||||
let mut dst = [MaybeUninit::new(255usize); 64];
|
||||
let expect = array::from_fn::<usize, 64, _>(|idx| idx);
|
||||
|
||||
assert_eq!(MaybeUninit::fill_with(&mut dst, || 0), &expect);
|
||||
assert_eq!(dst.write_with(|idx| idx), &expect);
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[cfg(panic = "unwind")]
|
||||
fn uninit_fill_with_mid_panic() {
|
||||
fn uninit_write_with_mid_panic() {
|
||||
use std::panic;
|
||||
|
||||
let rc = Rc::new(());
|
||||
|
@ -403,7 +403,7 @@ fn uninit_fill_with_mid_panic() {
|
|||
|
||||
let src = CloneUntilPanic { limit: 3, rc: rc.clone() };
|
||||
let err = panic::catch_unwind(panic::AssertUnwindSafe(|| {
|
||||
MaybeUninit::fill_with(&mut dst, || src.clone());
|
||||
dst.write_with(|_| src.clone());
|
||||
}));
|
||||
|
||||
drop(src);
|
||||
|
@ -423,58 +423,58 @@ fn uninit_fill_with_mid_panic() {
|
|||
|
||||
#[test]
|
||||
#[cfg(panic = "unwind")]
|
||||
fn uninit_fill_with_no_drop() {
|
||||
fn uninit_write_with_no_drop() {
|
||||
let mut dst = [MaybeUninit::uninit()];
|
||||
let src = Bomb;
|
||||
|
||||
MaybeUninit::fill_with(&mut dst, || src.clone());
|
||||
dst.write_with(|_| src.clone());
|
||||
|
||||
forget(src);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn uninit_fill_from() {
|
||||
fn uninit_write_iter() {
|
||||
let mut dst = [MaybeUninit::new(255); 64];
|
||||
let src = [0; 64];
|
||||
|
||||
let (initted, remainder) = MaybeUninit::fill_from(&mut dst, src.into_iter());
|
||||
let (initted, remainder) = dst.write_iter(src.into_iter());
|
||||
assert_eq!(initted, &src);
|
||||
assert_eq!(remainder.len(), 0);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn uninit_fill_from_partial() {
|
||||
fn uninit_write_iter_partial() {
|
||||
let mut dst = [MaybeUninit::new(255); 64];
|
||||
let src = [0; 48];
|
||||
|
||||
let (initted, remainder) = MaybeUninit::fill_from(&mut dst, src.into_iter());
|
||||
let (initted, remainder) = dst.write_iter(src.into_iter());
|
||||
assert_eq!(initted, &src);
|
||||
assert_eq!(remainder.len(), 16);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn uninit_over_fill() {
|
||||
fn uninit_write_iter_overfill() {
|
||||
let mut dst = [MaybeUninit::new(255); 64];
|
||||
let src = [0; 72];
|
||||
|
||||
let (initted, remainder) = MaybeUninit::fill_from(&mut dst, src.into_iter());
|
||||
let (initted, remainder) = dst.write_iter(src.into_iter());
|
||||
assert_eq!(initted, &src[0..64]);
|
||||
assert_eq!(remainder.len(), 0);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn uninit_empty_fill() {
|
||||
fn uninit_write_iter_empty() {
|
||||
let mut dst = [MaybeUninit::new(255); 64];
|
||||
let src = [0; 0];
|
||||
|
||||
let (initted, remainder) = MaybeUninit::fill_from(&mut dst, src.into_iter());
|
||||
let (initted, remainder) = dst.write_iter(src.into_iter());
|
||||
assert_eq!(initted, &src[0..0]);
|
||||
assert_eq!(remainder.len(), 64);
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[cfg(panic = "unwind")]
|
||||
fn uninit_fill_from_mid_panic() {
|
||||
fn uninit_write_iter_mid_panic() {
|
||||
use std::panic;
|
||||
|
||||
struct IterUntilPanic {
|
||||
|
@ -504,7 +504,7 @@ fn uninit_fill_from_mid_panic() {
|
|||
let src = IterUntilPanic { limit: 3, rc: rc.clone() };
|
||||
|
||||
let err = panic::catch_unwind(panic::AssertUnwindSafe(|| {
|
||||
MaybeUninit::fill_from(&mut dst, src);
|
||||
dst.write_iter(src);
|
||||
}));
|
||||
|
||||
match err {
|
||||
|
@ -522,11 +522,11 @@ fn uninit_fill_from_mid_panic() {
|
|||
|
||||
#[test]
|
||||
#[cfg(panic = "unwind")]
|
||||
fn uninit_fill_from_no_drop() {
|
||||
fn uninit_write_iter_no_drop() {
|
||||
let mut dst = [MaybeUninit::uninit()];
|
||||
let src = [Bomb];
|
||||
|
||||
MaybeUninit::fill_from(&mut dst, src.iter());
|
||||
dst.write_iter(src.iter());
|
||||
|
||||
forget(src);
|
||||
}
|
||||
|
|
|
@ -7,7 +7,6 @@ use crate::fmt;
|
|||
use crate::io::{
|
||||
self, BorrowedCursor, BufRead, IoSlice, IoSliceMut, Read, Seek, SeekFrom, SizeHint, Write,
|
||||
};
|
||||
use crate::mem::MaybeUninit;
|
||||
|
||||
/// `Empty` ignores any data written via [`Write`], and will always be empty
|
||||
/// (returning zero bytes) when read via [`Read`].
|
||||
|
@ -196,7 +195,7 @@ impl Read for Repeat {
|
|||
#[inline]
|
||||
fn read_buf(&mut self, mut buf: BorrowedCursor<'_>) -> io::Result<()> {
|
||||
// SAFETY: No uninit bytes are being written.
|
||||
MaybeUninit::fill(unsafe { buf.as_mut() }, self.byte);
|
||||
unsafe { buf.as_mut() }.write_filled(self.byte);
|
||||
// SAFETY: the entire unfilled portion of buf has been initialized.
|
||||
unsafe { buf.advance_unchecked(buf.capacity()) };
|
||||
Ok(())
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue