Skip to content

Commit 8e3e270

Browse files
committed
Add drop check test & MaybeUninit::first_ptr_mut
1 parent 92ac60d commit 8e3e270

File tree

2 files changed

+30
-1
lines changed

2 files changed

+30
-1
lines changed

library/core/src/array/mod.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -413,7 +413,8 @@ impl<T, const N: usize> [T; N] {
413413
}
414414
}
415415
let mut dst = MaybeUninit::uninit_array::<N>();
416-
let mut guard: Guard<U, N> = Guard { dst: &mut dst as *mut _ as *mut U, initialized: 0 };
416+
let mut guard: Guard<U, N> =
417+
Guard { dst: MaybeUninit::first_ptr_mut(&mut dst), initialized: 0 };
417418
for (src, dst) in IntoIter::new(self).zip(&mut dst) {
418419
dst.write(f(src));
419420
guard.initialized += 1;

library/core/tests/array.rs

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -301,3 +301,31 @@ fn array_map() {
301301
let b = a.map(|v| v as u64);
302302
assert_eq!(b, [1, 2, 3]);
303303
}
304+
305+
#[test]
306+
fn array_map_drop_safety() {
307+
use core::sync::atomic::AtomicUsize;
308+
use core::sync::atomic::Ordering;
309+
static DROPPED: AtomicUsize = AtomicUsize::new(0);
310+
struct DropCounter;
311+
impl Drop for DropCounter {
312+
fn drop(&mut self) {
313+
DROPPED.fetch_add(1, Ordering::SeqCst);
314+
}
315+
}
316+
317+
let num_to_create = 5;
318+
let success = std::panic::catch_unwind(|| {
319+
let items = [0; 10];
320+
let mut nth = 0;
321+
items.map(|_| {
322+
if nth == num_to_create {
323+
panic!("Oh no!");
324+
}
325+
nth += 1;
326+
DropCounter
327+
});
328+
});
329+
assert!(success.is_err());
330+
assert_eq!(DROPPED.load(Ordering::SeqCst), num_to_create);
331+
}

0 commit comments

Comments
 (0)