drop_tracker/
itemtraits.rs1use crate::DropItem;
2use crate::DroppedError;
3use crate::State;
4use std::borrow::Borrow;
5use std::borrow::BorrowMut;
6use std::cmp::Ordering;
7use std::fmt;
8use std::hash;
9use std::ops::Deref;
10use std::ops::DerefMut;
11
12impl<V> DropItem<V> {
13 fn inner_ref(&self) -> &V {
14 self.try_inner_ref().expect("cannot borrow value")
15 }
16
17 fn try_inner_ref(&self) -> Result<&V, DroppedError> {
18 match self.state {
19 Some(ref state) if state.is_alive() => {
20 Ok(unsafe { self.value.assume_init_ref() })
24 }
25 _ => Err(DroppedError),
26 }
27 }
28
29 fn inner_mut(&mut self) -> &mut V {
30 self.try_inner_mut().expect("cannot borrow mutable value")
31 }
32
33 fn try_inner_mut(&mut self) -> Result<&mut V, DroppedError> {
34 match self.state {
35 Some(ref state) if state.is_alive() => {
36 Ok(unsafe { self.value.assume_init_mut() })
40 }
41 _ => Err(DroppedError),
42 }
43 }
44}
45
46impl<V> Deref for DropItem<V> {
47 type Target = V;
48
49 fn deref(&self) -> &Self::Target {
50 self.inner_ref()
51 }
52}
53
54impl<V> DerefMut for DropItem<V> {
55 fn deref_mut(&mut self) -> &mut Self::Target {
56 self.inner_mut()
57 }
58}
59
60macro_rules! impl_ref_trait {
61 () => {};
62 ( impl <{ $( $params:tt )* }> Borrow < $target:ty > for DropItem < $type_bound:ty > ; $( $rest:tt )* ) => {
63 impl<$($params)*> Borrow<$target> for DropItem<$type_bound> {
64 #[inline(always)]
65 fn borrow(&self) -> &$target {
66 self.inner_ref().borrow()
67 }
68 }
69
70 impl_ref_trait! { $($rest)* }
71 };
72 ( impl <{ $( $params:tt )* }> BorrowMut < $target:ty > for DropItem < $type_bound:ty > ; $( $rest:tt )* ) => {
73 impl<$($params)*> BorrowMut<$target> for DropItem<$type_bound> {
74 #[inline(always)]
75 fn borrow_mut(&mut self) -> &mut $target {
76 self.inner_mut().borrow_mut()
77 }
78 }
79
80 impl_ref_trait! { $($rest)* }
81 };
82 ( impl <{ $( $params:tt )* }> AsRef < $target:ty > for DropItem < $type_bound:ty > ; $( $rest:tt )* ) => {
83 impl<$($params)*> AsRef<$target> for DropItem<$type_bound> {
84 #[inline(always)]
85 fn as_ref(&self) -> &$target {
86 self.inner_ref().as_ref()
87 }
88 }
89
90 impl_ref_trait! { $($rest)* }
91 };
92 ( impl <{ $( $params:tt )* }> AsMut < $target:ty > for DropItem < $type_bound:ty > ; $( $rest:tt )* ) => {
93 impl<$($params)*> AsMut<$target> for DropItem<$type_bound> {
94 #[inline(always)]
95 fn as_mut(&mut self) -> &mut $target {
96 self.inner_mut().as_mut()
97 }
98 }
99
100 impl_ref_trait! { $($rest)* }
101 };
102}
103
104impl_ref_trait! {
105 impl<{V}> Borrow<V> for DropItem<V>;
106 impl<{V: Borrow<str>}> Borrow<str> for DropItem<V>;
107 impl<{V: Borrow<[T]>, T}> Borrow<[T]> for DropItem<V>;
108
109 impl<{V}> BorrowMut<V> for DropItem<V>;
110 impl<{V: BorrowMut<str>}> BorrowMut<str> for DropItem<V>;
111 impl<{V: BorrowMut<[T]>, T}> BorrowMut<[T]> for DropItem<V>;
112
113 impl<{V: AsRef<T>, T}> AsRef<T> for DropItem<V>;
114 impl<{V: AsMut<T>, T}> AsMut<T> for DropItem<V>;
115}
116
117impl<V: Eq> Eq for DropItem<V> {}
118
119impl<V: PartialEq<W>, W> PartialEq<DropItem<W>> for DropItem<V> {
120 fn eq(&self, other: &DropItem<W>) -> bool {
121 self.inner_ref().eq(other.inner_ref())
122 }
123}
124
125impl<V: PartialOrd<W>, W> PartialOrd<DropItem<W>> for DropItem<V> {
126 fn partial_cmp(&self, other: &DropItem<W>) -> Option<Ordering> {
127 self.inner_ref().partial_cmp(other.inner_ref())
128 }
129}
130
131macro_rules! impl_cmp_trait {
132 () => {};
133 (
134 impl < $( $lifetime:lifetime , )? $param:ident $( , $extra_param:ident )? >
135 PartialEq + PartialOrd < $other_type:ty >
136 for DropItem < $item_bound:ty > ; $( $rest:tt )*
137 ) => {
138 impl<$($lifetime,)? $param $(, $extra_param)?> PartialEq<$other_type> for DropItem<$item_bound>
139 where $param: PartialEq<$other_type>
140 {
141 fn eq(&self, other: &$other_type) -> bool {
142 self.inner_ref().eq(other)
143 }
144 }
145
146 impl<$($lifetime,)? $param $(, $extra_param)?> PartialOrd<$other_type> for DropItem<$item_bound>
147 where $param: PartialOrd<$other_type>
148 {
149 fn partial_cmp(&self, other: &$other_type) -> Option<Ordering> {
150 self.inner_ref().partial_cmp(other)
151 }
152 }
153
154 impl_cmp_trait! { $($rest)* }
155 };
156}
157
158impl_cmp_trait! {
159 impl<V> PartialEq+PartialOrd<i8> for DropItem<V>;
160 impl<V> PartialEq+PartialOrd<i16> for DropItem<V>;
161 impl<V> PartialEq+PartialOrd<i32> for DropItem<V>;
162 impl<V> PartialEq+PartialOrd<i64> for DropItem<V>;
163 impl<V> PartialEq+PartialOrd<i128> for DropItem<V>;
164
165 impl<V> PartialEq+PartialOrd<u8> for DropItem<V>;
166 impl<V> PartialEq+PartialOrd<u16> for DropItem<V>;
167 impl<V> PartialEq+PartialOrd<u32> for DropItem<V>;
168 impl<V> PartialEq+PartialOrd<u64> for DropItem<V>;
169 impl<V> PartialEq+PartialOrd<u128> for DropItem<V>;
170
171 impl<V> PartialEq+PartialOrd<f32> for DropItem<V>;
172 impl<V> PartialEq+PartialOrd<f64> for DropItem<V>;
173
174 impl<V> PartialEq+PartialOrd<char> for DropItem<V>;
175 impl<V> PartialEq+PartialOrd<bool> for DropItem<V>;
176 impl<V> PartialEq+PartialOrd<()> for DropItem<V>;
177 impl<V> PartialEq+PartialOrd<str> for DropItem<V>;
178 impl<'a, V> PartialEq+PartialOrd<&'a str> for DropItem<V>;
179 impl<V, T> PartialEq+PartialOrd<[T]> for DropItem<V>;
180 impl<'a, V, T> PartialEq+PartialOrd<&'a [T]> for DropItem<V>;
181}
182
183impl<V: hash::Hash> hash::Hash for DropItem<V> {
184 fn hash<H: hash::Hasher>(&self, state: &mut H) {
185 self.inner_ref().hash(state)
186 }
187}
188
189impl<V: fmt::Display> fmt::Display for DropItem<V> {
190 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
191 self.inner_ref().fmt(f)
192 }
193}
194
195impl<V: fmt::Debug> fmt::Debug for DropItem<V> {
196 fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
197 match self.try_inner_ref() {
198 Ok(value) => f
199 .debug_struct("DropItem")
200 .field("value", value)
201 .field("state", &State::Alive)
202 .finish(),
203 Err(_) => f
204 .debug_struct("DropItem")
205 .field("value", &"<dropped>")
206 .field("state", &State::Dropped)
207 .finish(),
208 }
209 }
210}