classicube_helpers/
shared.rs1use std::{
2 cell::RefCell,
3 ops::DerefMut,
4 rc::Rc,
5 sync::{Arc, Mutex},
6};
7
8use futures::lock::Mutex as FutureMutex;
9
10pub struct SyncShared<T: ?Sized> {
11 inner: Rc<RefCell<T>>,
12}
13
14impl<T> SyncShared<T> {
15 pub fn new(value: T) -> Self {
16 Self {
17 inner: Rc::new(RefCell::new(value)),
18 }
19 }
20}
21
22impl<T: ?Sized> SyncShared<T> {
23 pub fn lock(&mut self) -> impl DerefMut<Target = T> + '_ {
24 self.inner.borrow_mut()
25 }
26
27 pub fn with<F, R>(&mut self, f: F) -> R
28 where
29 F: FnOnce(&mut T) -> R,
30 {
31 let mut guard = self.lock();
32 f(&mut guard)
33 }
34}
35
36impl<T: ?Sized> Clone for SyncShared<T> {
37 fn clone(&self) -> SyncShared<T> {
38 Self {
39 inner: self.inner.clone(),
40 }
41 }
42}
43
44pub struct ThreadShared<T: ?Sized> {
45 inner: Arc<Mutex<T>>,
46}
47
48impl<T> ThreadShared<T> {
49 pub fn new(value: T) -> Self {
50 Self {
51 inner: Arc::new(Mutex::new(value)),
52 }
53 }
54
55 pub fn lock(&mut self) -> impl DerefMut<Target = T> + '_ {
56 self.inner.lock().unwrap()
57 }
58
59 pub fn with<F, R>(&mut self, f: F) -> R
60 where
61 F: FnOnce(&mut T) -> R,
62 {
63 let mut guard = self.lock();
64 f(&mut guard)
65 }
66}
67
68impl<T: ?Sized> Clone for ThreadShared<T> {
69 fn clone(&self) -> ThreadShared<T> {
70 Self {
71 inner: self.inner.clone(),
72 }
73 }
74}
75
76pub struct FutureShared<T: ?Sized> {
77 inner: Arc<FutureMutex<T>>,
78}
79
80impl<T> FutureShared<T> {
81 pub fn new(value: T) -> Self {
82 Self {
83 inner: Arc::new(FutureMutex::new(value)),
84 }
85 }
86
87 pub async fn lock(&mut self) -> impl DerefMut<Target = T> + '_ {
88 self.inner.lock().await
89 }
90
91 pub async fn with<F, R>(&mut self, f: F) -> R
92 where
93 F: FnOnce(&mut T) -> R,
94 {
95 let mut guard = self.lock().await;
96 f(&mut guard)
97 }
98
99 pub async fn with_async<F, FUT, R>(&mut self, f: F) -> R
100 where
101 F: FnOnce(&mut T) -> FUT,
102 FUT: futures::Future<Output = R>,
103 {
104 let mut guard = self.lock().await;
105 f(&mut guard).await
106 }
107}
108
109impl<T: ?Sized> Clone for FutureShared<T> {
110 fn clone(&self) -> FutureShared<T> {
111 Self {
112 inner: self.inner.clone(),
113 }
114 }
115}
116
117#[test]
118fn test_shared() {
119 {
120 let mut shared = SyncShared::new(1);
121 shared.with(|v| {
122 println!("{v}");
123 });
124 let v = shared.lock();
125 println!("{}", {
126 let a: &u8 = &v;
127 a
128 });
129 }
130
131 {
132 #[derive(Debug)]
133 struct NotClone {}
134
135 let mut shared = ThreadShared::new(NotClone {});
136
137 {
138 let mut shared = shared.clone();
139 std::thread::spawn(move || {
140 shared.with(|v| {
141 println!("{v:?}");
142 });
143 let v = shared.lock();
144 println!("{:?}", {
145 let a: &NotClone = &v;
146 a
147 });
148 });
149 }
150
151 shared.with(|v| {
152 println!("{v:?}");
153 });
154 let v = shared.lock();
155 println!("{:?}", {
156 let a: &NotClone = &v;
157 a
158 });
159 }
160
161 futures::executor::block_on(async {
162 let mut shared = FutureShared::new(3);
163 shared
164 .with(|v| {
165 println!("{v}");
166 })
167 .await;
168 let v = shared.lock().await;
169 println!("{}", {
170 let a: &u8 = &v;
171 a
172 });
173 });
174
175 {
176 trait Module {
177 fn load(&mut self);
178 fn unload(&mut self);
179 }
180
181 struct ModuleThing {}
182 impl Module for ModuleThing {
183 fn load(&mut self) {}
184
185 fn unload(&mut self) {}
186 }
187
188 let mut list_of_sync_shareds: Vec<Rc<Box<dyn Module>>> = Vec::new();
189 let mod_thing: Rc<Box<dyn Module>> = Rc::new(Box::new(ModuleThing {}));
190 list_of_sync_shareds.push(mod_thing);
191
192 let mut list_of_sync_shareds: Vec<SyncShared<Box<dyn Module>>> = Vec::new();
193 let mod_thing: SyncShared<Box<dyn Module>> = SyncShared::new(Box::new(ModuleThing {}));
194 list_of_sync_shareds.push(mod_thing);
195
196 for module in &mut list_of_sync_shareds {
197 module.lock().load();
198 }
199 }
200}