]> git.proxmox.com Git - rustc.git/blob - src/test/ui/union/union-nodrop.rs
New upstream version 1.55.0+dfsg1
[rustc.git] / src / test / ui / union / union-nodrop.rs
1 // run-pass
2 // revisions: mirunsafeck thirunsafeck
3 // [thirunsafeck]compile-flags: -Z thir-unsafeck
4
5 #![allow(dead_code)]
6
7 use std::mem::needs_drop;
8 use std::mem::ManuallyDrop;
9
10 struct NeedDrop;
11
12 impl Drop for NeedDrop {
13 fn drop(&mut self) {}
14 }
15
16 // Constant expressios allow `NoDrop` to go out of scope,
17 // unlike a value of the interior type implementing `Drop`.
18 static X: () = (NoDrop { inner: ManuallyDrop::new(NeedDrop) }, ()).1;
19
20 const Y: () = (NoDrop { inner: ManuallyDrop::new(NeedDrop) }, ()).1;
21
22 const fn _f() { (NoDrop { inner: ManuallyDrop::new(NeedDrop) }, ()).1 }
23
24 // A union that scrubs the drop glue from its inner type
25 union NoDrop<T> { inner: ManuallyDrop<T> }
26
27 // Copy currently can't be implemented on drop-containing unions,
28 // this may change later
29 // https://github.com/rust-lang/rust/pull/38934#issuecomment-271219289
30
31 // // We should be able to implement Copy for NoDrop
32 // impl<T> Copy for NoDrop<T> {}
33 // impl<T> Clone for NoDrop<T> {fn clone(&self) -> Self { *self }}
34
35 // // We should be able to implement Copy for things using NoDrop
36 // #[derive(Copy, Clone)]
37 struct Foo {
38 x: NoDrop<Box<u8>>
39 }
40
41 struct Baz {
42 x: NoDrop<Box<u8>>,
43 y: Box<u8>,
44 }
45
46 union ActuallyDrop<T> { inner: ManuallyDrop<T> }
47
48 impl<T> Drop for ActuallyDrop<T> {
49 fn drop(&mut self) {}
50 }
51
52 fn main() {
53 // NoDrop should not make needs_drop true
54 assert!(!needs_drop::<Foo>());
55 assert!(!needs_drop::<NoDrop<u8>>());
56 assert!(!needs_drop::<NoDrop<Box<u8>>>());
57 // presence of other drop types should still work
58 assert!(needs_drop::<Baz>());
59 // drop impl on union itself should work
60 assert!(needs_drop::<ActuallyDrop<u8>>());
61 assert!(needs_drop::<ActuallyDrop<Box<u8>>>());
62 }