rstsr_core/storage/
data.rs

1extern crate alloc;
2
3use alloc::sync::Arc;
4use alloc::vec::Vec;
5use core::mem::{transmute, ManuallyDrop};
6use duplicate::duplicate_item;
7
8/* #region definitions */
9
10#[derive(Debug)]
11pub struct DataOwned<C> {
12    pub(crate) raw: C,
13}
14
15#[derive(Debug)]
16pub enum DataRef<'a, C> {
17    TrueRef(&'a C),
18    ManuallyDropOwned(ManuallyDrop<C>),
19}
20
21#[derive(Debug)]
22pub enum DataMut<'a, C> {
23    TrueRef(&'a mut C),
24    ManuallyDropOwned(ManuallyDrop<C>),
25}
26
27#[derive(Debug)]
28pub enum DataCow<'a, C> {
29    Owned(DataOwned<C>),
30    Ref(DataRef<'a, C>),
31}
32
33#[derive(Debug)]
34pub struct DataArc<C> {
35    pub(crate) raw: Arc<C>,
36}
37
38#[derive(Debug)]
39pub enum DataReference<'a, C> {
40    Ref(DataRef<'a, C>),
41    Mut(DataMut<'a, C>),
42}
43
44unsafe impl<C> Send for DataOwned<C> where C: Send {}
45unsafe impl<C> Send for DataRef<'_, C> where C: Send {}
46unsafe impl<C> Sync for DataRef<'_, C> where C: Sync {}
47unsafe impl<C> Send for DataMut<'_, C> where C: Send {}
48unsafe impl<C> Sync for DataCow<'_, C> where C: Sync {}
49unsafe impl<C> Send for DataCow<'_, C> where C: Send {}
50unsafe impl<C> Send for DataArc<C> where C: Send {}
51unsafe impl<C> Sync for DataArc<C> where C: Sync {}
52unsafe impl<C> Send for DataReference<'_, C> where C: Send {}
53unsafe impl<C> Sync for DataReference<'_, C> where C: Sync {}
54
55/* #endregion */
56
57/* #region specific implementations */
58
59impl<C> From<C> for DataOwned<C> {
60    #[inline]
61    fn from(data: C) -> Self {
62        Self { raw: data }
63    }
64}
65
66impl<C> DataOwned<C> {
67    #[inline]
68    pub fn into_raw(self) -> C {
69        self.raw
70    }
71}
72
73impl<'a, C> From<&'a C> for DataRef<'a, C> {
74    #[inline]
75    fn from(data: &'a C) -> Self {
76        DataRef::TrueRef(data)
77    }
78}
79
80impl<C> DataRef<'_, C> {
81    #[inline]
82    pub fn from_manually_drop(data: ManuallyDrop<C>) -> Self {
83        DataRef::ManuallyDropOwned(data)
84    }
85
86    #[inline]
87    pub fn is_true_ref(&self) -> bool {
88        matches!(self, DataRef::TrueRef(_))
89    }
90
91    #[inline]
92    pub fn is_manually_drop_owned(&self) -> bool {
93        matches!(self, DataRef::ManuallyDropOwned(_))
94    }
95}
96
97impl<'a, C> From<&'a mut C> for DataMut<'a, C> {
98    #[inline]
99    fn from(data: &'a mut C) -> Self {
100        DataMut::TrueRef(data)
101    }
102}
103
104impl<C> DataMut<'_, C> {
105    #[inline]
106    pub fn from_manually_drop(data: ManuallyDrop<C>) -> Self {
107        DataMut::ManuallyDropOwned(data)
108    }
109
110    #[inline]
111    pub fn is_true_ref(&self) -> bool {
112        matches!(self, DataMut::TrueRef(_))
113    }
114
115    #[inline]
116    pub fn is_manually_drop_owned(&self) -> bool {
117        matches!(self, DataMut::ManuallyDropOwned(_))
118    }
119}
120
121impl<C> DataCow<'_, C> {
122    #[inline]
123    pub fn is_owned(&self) -> bool {
124        matches!(self, DataCow::Owned(_))
125    }
126
127    #[inline]
128    pub fn is_ref(&self) -> bool {
129        matches!(self, DataCow::Ref(_))
130    }
131}
132
133impl<C> From<Arc<C>> for DataArc<C> {
134    #[inline]
135    fn from(data: Arc<C>) -> Self {
136        Self { raw: data }
137    }
138}
139
140impl<C> From<C> for DataArc<C> {
141    #[inline]
142    fn from(data: C) -> Self {
143        Self { raw: Arc::new(data) }
144    }
145}
146
147impl<C> DataArc<C> {
148    #[inline]
149    pub fn strong_count(&self) -> usize {
150        Arc::strong_count(&self.raw)
151    }
152
153    #[inline]
154    pub fn weak_count(&self) -> usize {
155        Arc::weak_count(&self.raw)
156    }
157}
158
159impl<C> DataReference<'_, C> {
160    #[inline]
161    pub fn is_ref(&self) -> bool {
162        matches!(self, DataReference::Ref(_))
163    }
164
165    #[inline]
166    pub fn is_mut(&self) -> bool {
167        matches!(self, DataReference::Mut(_))
168    }
169}
170
171/* #endregion */
172
173/* #region data traits */
174
175pub trait DataAPI {
176    type Data;
177    fn raw(&self) -> &Self::Data;
178    fn as_ref(&'_ self) -> DataRef<'_, Self::Data> {
179        DataRef::from(self.raw())
180    }
181}
182
183pub trait DataCloneAPI
184where
185    Self: DataAPI,
186    Self::Data: Clone,
187{
188    fn into_owned(self) -> DataOwned<Self::Data>;
189    fn into_shared(self) -> DataArc<Self::Data>;
190}
191
192pub trait DataMutAPI: DataAPI {
193    fn raw_mut(&mut self) -> &mut Self::Data;
194    fn as_mut(&'_ mut self) -> DataMut<'_, Self::Data> {
195        DataMut::TrueRef(self.raw_mut())
196    }
197}
198
199pub trait DataOwnedAPI: DataMutAPI {}
200
201pub trait DataForceMutAPI<C>: DataAPI<Data = C> {
202    /// # Safety
203    ///
204    /// This function is highly unsafe, as it entirely bypasses Rust's lifetime
205    /// and borrowing rules.
206    unsafe fn force_mut(&self) -> DataMut<'_, C>;
207}
208
209/* #endregion */
210
211/* #region impl DataCloneAPI */
212
213impl<C> DataAPI for DataOwned<C> {
214    type Data = C;
215
216    #[inline]
217    fn raw(&self) -> &Self::Data {
218        &self.raw
219    }
220}
221
222impl<C> DataCloneAPI for DataOwned<C>
223where
224    C: Clone,
225{
226    #[inline]
227    fn into_owned(self) -> DataOwned<Self::Data> {
228        self
229    }
230
231    #[inline]
232    fn into_shared(self) -> DataArc<Self::Data> {
233        DataArc::from(self.raw)
234    }
235}
236
237impl<C> DataAPI for DataRef<'_, C> {
238    type Data = C;
239
240    #[inline]
241    fn raw(&self) -> &Self::Data {
242        match self {
243            DataRef::TrueRef(raw) => raw,
244            DataRef::ManuallyDropOwned(raw) => raw,
245        }
246    }
247}
248
249impl<C> DataCloneAPI for DataRef<'_, C>
250where
251    C: Clone,
252{
253    #[inline]
254    fn into_owned(self) -> DataOwned<Self::Data> {
255        match self {
256            DataRef::TrueRef(raw) => DataOwned::from(raw.clone()),
257            DataRef::ManuallyDropOwned(raw) => DataOwned::from(ManuallyDrop::into_inner(raw.clone())),
258        }
259    }
260
261    #[inline]
262    fn into_shared(self) -> DataArc<Self::Data> {
263        match self {
264            DataRef::TrueRef(raw) => DataArc::from(raw.clone()),
265            DataRef::ManuallyDropOwned(raw) => DataArc::from(ManuallyDrop::into_inner(raw.clone())),
266        }
267    }
268}
269
270impl<C> DataAPI for DataMut<'_, C> {
271    type Data = C;
272
273    #[inline]
274    fn raw(&self) -> &Self::Data {
275        match self {
276            DataMut::TrueRef(raw) => raw,
277            DataMut::ManuallyDropOwned(raw) => raw,
278        }
279    }
280}
281
282impl<C> DataCloneAPI for DataMut<'_, C>
283where
284    C: Clone,
285{
286    #[inline]
287    fn into_owned(self) -> DataOwned<Self::Data> {
288        match self {
289            DataMut::TrueRef(raw) => DataOwned::from(raw.clone()),
290            DataMut::ManuallyDropOwned(raw) => DataOwned::from(ManuallyDrop::into_inner(raw.clone())),
291        }
292    }
293
294    #[inline]
295    fn into_shared(self) -> DataArc<Self::Data> {
296        match self {
297            DataMut::TrueRef(raw) => DataArc::from(raw.clone()),
298            DataMut::ManuallyDropOwned(raw) => DataArc::from(ManuallyDrop::into_inner(raw.clone())),
299        }
300    }
301}
302
303impl<C> DataAPI for DataCow<'_, C> {
304    type Data = C;
305
306    #[inline]
307    fn raw(&self) -> &Self::Data {
308        match self {
309            DataCow::Owned(data) => data.raw(),
310            DataCow::Ref(data) => data.raw(),
311        }
312    }
313}
314
315impl<C> DataCloneAPI for DataCow<'_, C>
316where
317    C: Clone,
318{
319    #[inline]
320    fn into_owned(self) -> DataOwned<Self::Data> {
321        match self {
322            DataCow::Owned(data) => data,
323            DataCow::Ref(data) => data.into_owned(),
324        }
325    }
326
327    #[inline]
328    fn into_shared(self) -> DataArc<Self::Data> {
329        match self {
330            DataCow::Owned(data) => DataArc::from(data.into_raw()),
331            DataCow::Ref(data) => data.into_shared(),
332        }
333    }
334}
335
336impl<C> DataAPI for DataArc<C> {
337    type Data = C;
338
339    #[inline]
340    fn raw(&self) -> &Self::Data {
341        &self.raw
342    }
343}
344
345impl<C> DataCloneAPI for DataArc<C>
346where
347    C: Clone,
348{
349    #[inline]
350    fn into_owned(self) -> DataOwned<Self::Data> {
351        DataOwned::from(Arc::try_unwrap(self.raw).ok().unwrap())
352    }
353
354    #[inline]
355    fn into_shared(self) -> DataArc<Self::Data> {
356        self
357    }
358}
359
360impl<C> DataAPI for DataReference<'_, C> {
361    type Data = C;
362
363    #[inline]
364    fn raw(&self) -> &Self::Data {
365        match self {
366            DataReference::Ref(data) => data.raw(),
367            DataReference::Mut(data) => data.raw(),
368        }
369    }
370}
371
372impl<C> DataCloneAPI for DataReference<'_, C>
373where
374    C: Clone,
375{
376    #[inline]
377    fn into_owned(self) -> DataOwned<Self::Data> {
378        match self {
379            DataReference::Ref(data) => data.into_owned(),
380            DataReference::Mut(data) => data.into_owned(),
381        }
382    }
383
384    #[inline]
385    fn into_shared(self) -> DataArc<Self::Data> {
386        match self {
387            DataReference::Ref(data) => data.into_shared(),
388            DataReference::Mut(data) => data.into_shared(),
389        }
390    }
391}
392
393/* #endregion */
394
395/* #region impl DataMutAPI */
396
397impl<C> DataMutAPI for DataOwned<C> {
398    #[inline]
399    fn raw_mut(&mut self) -> &mut Self::Data {
400        &mut self.raw
401    }
402}
403
404impl<C> DataMutAPI for DataMut<'_, C> {
405    #[inline]
406    fn raw_mut(&mut self) -> &mut Self::Data {
407        match self {
408            DataMut::TrueRef(raw) => raw,
409            DataMut::ManuallyDropOwned(raw) => raw,
410        }
411    }
412}
413
414impl<C> DataMutAPI for DataArc<C>
415where
416    C: Clone,
417{
418    #[inline]
419    fn raw_mut(&mut self) -> &mut Self::Data {
420        Arc::make_mut(&mut self.raw)
421    }
422}
423
424/* #endregion */
425
426/* #region impl DataForceMutAPI */
427
428impl<T> DataForceMutAPI<Vec<T>> for DataRef<'_, Vec<T>> {
429    unsafe fn force_mut(&self) -> DataMut<'_, Vec<T>> {
430        let (ptr, len) = match self {
431            DataRef::TrueRef(raw) => (raw.as_ptr(), raw.len()),
432            DataRef::ManuallyDropOwned(raw) => (raw.as_ptr(), raw.len()),
433        };
434        let vec = unsafe { Vec::from_raw_parts(ptr as *mut T, len, len) };
435        let vec = ManuallyDrop::new(vec);
436        DataMut::ManuallyDropOwned(vec)
437    }
438}
439
440#[duplicate_item(
441    Data;
442    [DataOwned<Vec<T>>];
443    [DataMut<'_, Vec<T>>];
444    [DataCow<'_, Vec<T>>];
445    [DataArc<Vec<T>>];
446    [DataReference<'_, Vec<T>>];
447)]
448impl<T> DataForceMutAPI<Vec<T>> for Data {
449    unsafe fn force_mut(&self) -> DataMut<'_, Vec<T>> {
450        transmute(self.as_ref().force_mut())
451    }
452}
453
454/* #endregion */
455
456/* #region DataCow */
457
458pub trait DataIntoCowAPI<'a>
459where
460    Self: DataAPI,
461{
462    fn into_cow(self) -> DataCow<'a, Self::Data>;
463}
464
465impl<'a, C> DataIntoCowAPI<'a> for DataOwned<C> {
466    #[inline]
467    fn into_cow(self) -> DataCow<'a, C> {
468        DataCow::Owned(self)
469    }
470}
471
472impl<'a, C> DataIntoCowAPI<'a> for DataRef<'a, C> {
473    #[inline]
474    fn into_cow(self) -> DataCow<'a, C> {
475        DataCow::Ref(self)
476    }
477}
478
479impl<'a, C> DataIntoCowAPI<'a> for DataMut<'a, C> {
480    #[inline]
481    fn into_cow(self) -> DataCow<'a, C> {
482        match self {
483            DataMut::TrueRef(data) => DataRef::from(&*data).into_cow(),
484            DataMut::ManuallyDropOwned(data) => DataRef::from_manually_drop(data).into_cow(),
485        }
486    }
487}
488
489impl<'a, C> DataIntoCowAPI<'a> for DataCow<'a, C> {
490    #[inline]
491    fn into_cow(self) -> DataCow<'a, C> {
492        self
493    }
494}
495
496impl<'a, C> DataIntoCowAPI<'a> for DataArc<C>
497where
498    C: Clone,
499{
500    #[inline]
501    fn into_cow(self) -> DataCow<'a, C> {
502        DataCow::Owned(self.into_owned())
503    }
504}
505
506impl<'a, C> DataIntoCowAPI<'a> for DataReference<'a, C> {
507    #[inline]
508    fn into_cow(self) -> DataCow<'a, C> {
509        match self {
510            DataReference::Ref(data) => data.into_cow(),
511            DataReference::Mut(data) => data.into_cow(),
512        }
513    }
514}
515
516/* #endregion */
517
518#[cfg(test)]
519mod test {
520    use super::*;
521
522    #[test]
523    fn test_trait_data() {
524        let vec = vec![10, 20, 30];
525        println!("===");
526        println!("{:?}", vec.as_ptr());
527        let data = DataOwned { raw: vec.clone() };
528        let data_ref = data.as_ref();
529        let data_ref_ref = data_ref.as_ref();
530        println!("{:?}", data_ref.raw().as_ptr());
531        println!("{:?}", data_ref_ref.raw().as_ptr());
532        let data_ref2 = data_ref.into_owned();
533        println!("{:?}", data_ref2.raw().as_ptr());
534
535        println!("===");
536        let data_ref = DataRef::from_manually_drop(ManuallyDrop::new(vec.clone()));
537        let data_ref_ref = data_ref.as_ref();
538        println!("{:?}", data_ref.raw().as_ptr());
539        println!("{:?}", data_ref_ref.raw().as_ptr());
540        let mut data_ref2 = data_ref.into_owned();
541        println!("{:?}", data_ref2.raw().as_ptr());
542        data_ref2.raw_mut()[1] = 10;
543    }
544}