1 /*
2  * This is a copy of the sync_wrapper crate.
3  */
4 
5 /// A mutual exclusion primitive that relies on static type information only
6 ///
7 /// In some cases synchronization can be proven statically: whenever you hold an exclusive `&mut`
8 /// reference, the Rust type system ensures that no other part of the program can hold another
9 /// reference to the data. Therefore it is safe to access it even if the current thread obtained
10 /// this reference via a channel. Whenever this is the case, the overhead of allocating and locking
11 /// a [`Mutex`] can be avoided by using this static version.
12 ///
13 /// One example where this is often applicable is [`Future`], which requires an exclusive reference
14 /// for its [`poll`] method: While a given `Future` implementation may not be safe to access by
15 /// multiple threads concurrently, the executor can only run the `Future` on one thread at any
16 /// given time, making it [`Sync`] in practice as long as the implementation is `Send`. You can
17 /// therefore use the sync wrapper to prove that your data structure is `Sync` even though it
18 /// contains such a `Future`.
19 ///
20 /// # Example
21 ///
22 /// ```ignore
23 /// use hyper::common::sync_wrapper::SyncWrapper;
24 /// use std::future::Future;
25 ///
26 /// struct MyThing {
27 ///     future: SyncWrapper<Box<dyn Future<Output = String> + Send>>,
28 /// }
29 ///
30 /// impl MyThing {
31 ///     // all accesses to `self.future` now require an exclusive reference or ownership
32 /// }
33 ///
34 /// fn assert_sync<T: Sync>() {}
35 ///
36 /// assert_sync::<MyThing>();
37 /// ```
38 ///
39 /// [`Mutex`]: https://doc.rust-lang.org/std/sync/struct.Mutex.html
40 /// [`Future`]: https://doc.rust-lang.org/std/future/trait.Future.html
41 /// [`poll`]: https://doc.rust-lang.org/std/future/trait.Future.html#method.poll
42 /// [`Sync`]: https://doc.rust-lang.org/std/marker/trait.Sync.html
43 #[repr(transparent)]
44 pub(crate) struct SyncWrapper<T>(T);
45 
46 impl<T> SyncWrapper<T> {
47     /// Creates a new SyncWrapper containing the given value.
48     ///
49     /// # Examples
50     ///
51     /// ```ignore
52     /// use hyper::common::sync_wrapper::SyncWrapper;
53     ///
54     /// let wrapped = SyncWrapper::new(42);
55     /// ```
new(value: T) -> Self56     pub(crate) fn new(value: T) -> Self {
57         Self(value)
58     }
59 
60     /// Acquires a reference to the protected value.
61     ///
62     /// This is safe because it requires an exclusive reference to the wrapper. Therefore this method
63     /// neither panics nor does it return an error. This is in contrast to [`Mutex::get_mut`] which
64     /// returns an error if another thread panicked while holding the lock. It is not recommended
65     /// to send an exclusive reference to a potentially damaged value to another thread for further
66     /// processing.
67     ///
68     /// [`Mutex::get_mut`]: https://doc.rust-lang.org/std/sync/struct.Mutex.html#method.get_mut
69     ///
70     /// # Examples
71     ///
72     /// ```ignore
73     /// use hyper::common::sync_wrapper::SyncWrapper;
74     ///
75     /// let mut wrapped = SyncWrapper::new(42);
76     /// let value = wrapped.get_mut();
77     /// *value = 0;
78     /// assert_eq!(*wrapped.get_mut(), 0);
79     /// ```
get_mut(&mut self) -> &mut T80     pub(crate) fn get_mut(&mut self) -> &mut T {
81         &mut self.0
82     }
83 
84     /// Consumes this wrapper, returning the underlying data.
85     ///
86     /// This is safe because it requires ownership of the wrapper, aherefore this method will neither
87     /// panic nor does it return an error. This is in contrast to [`Mutex::into_inner`] which
88     /// returns an error if another thread panicked while holding the lock. It is not recommended
89     /// to send an exclusive reference to a potentially damaged value to another thread for further
90     /// processing.
91     ///
92     /// [`Mutex::into_inner`]: https://doc.rust-lang.org/std/sync/struct.Mutex.html#method.into_inner
93     ///
94     /// # Examples
95     ///
96     /// ```ignore
97     /// use hyper::common::sync_wrapper::SyncWrapper;
98     ///
99     /// let mut wrapped = SyncWrapper::new(42);
100     /// assert_eq!(wrapped.into_inner(), 42);
101     /// ```
102     #[allow(dead_code)]
into_inner(self) -> T103     pub(crate) fn into_inner(self) -> T {
104         self.0
105     }
106 }
107 
108 // this is safe because the only operations permitted on this data structure require exclusive
109 // access or ownership
110 unsafe impl<T: Send> Sync for SyncWrapper<T> {}
111