1use std::{borrow::{Borrow, BorrowMut}, cell::UnsafeCell, future::Future, marker::PhantomData, mem::MaybeUninit, ops::{Deref, DerefMut}, pin::Pin, ptr::NonNull, sync::{atomic::{AtomicUsize, Ordering}, Mutex}, usize};
2
3use futures::{future::FusedFuture, FutureExt, Stream, StreamExt};
4
5mod graph;
6pub mod scope;
7pub mod slice;
8pub mod prelude;
9pub mod tuple;
10
11use graph::Graph;
12use scope::{Anchor, Spawner};
13
14struct BorrowInner<T> {
17 weak: AtomicUsize,
18 graph: Mutex<Graph>,
19 data: UnsafeCell<MaybeUninit<T>>
20}
21
22struct SharedPtr<T> {
25 inner: NonNull<BorrowInner<T>>
26}
27
28unsafe impl<T> Send for SharedPtr<T> {}
29
30unsafe impl<T> Sync for SharedPtr<T> {}
31
32impl<T> SharedPtr<T> {
33 pub fn new(data: T) -> Self {
34 SharedPtr {
35 inner: unsafe { NonNull::new_unchecked(Box::into_raw(Box::new(BorrowInner {
36 weak: 1.into(),
37 graph: Mutex::new(Graph::new()),
38 data: UnsafeCell::new(MaybeUninit::new(data)),
39 }))) }
40 }
41 }
42
43 pub fn inner(&self) -> &BorrowInner<T> {
44 unsafe { self.inner.as_ref() }
45 }
46
47 pub unsafe fn get_ref(&self) -> &T {
48 self.inner().data.get().as_ref().unwrap_unchecked().assume_init_ref()
49 }
50
51 pub unsafe fn get_mut(&mut self) -> &mut T {
52 self.inner().data.get().as_mut().unwrap_unchecked().assume_init_mut()
53 }
54
55 pub fn into_raw(self) -> *mut T {
56 let ptr = unsafe { self.inner.as_ptr().cast::<T>().byte_add(std::mem::offset_of!(BorrowInner<T>, data)) };
57 std::mem::forget(self);
58 ptr
59 }
60
61 pub unsafe fn from_raw(ptr: *mut T) -> Self {
62 SharedPtr {
63 inner: NonNull::new_unchecked(ptr.byte_sub(std::mem::offset_of!(BorrowInner<T>, data)).cast::<BorrowInner<T>>()),
64 }
65 }
66}
67
68impl<T> Clone for SharedPtr<T> {
69 fn clone(&self) -> Self {
70 self.inner().weak.fetch_add(1, Ordering::Relaxed);
71 SharedPtr { inner: self.inner }
72 }
73}
74
75impl<T> Drop for SharedPtr<T> {
76 fn drop(&mut self) {
77 if self.inner().weak.fetch_sub(1, Ordering::Release) == 1 {
78 drop(unsafe { Box::from_raw(self.inner.as_ptr()) })
79 }
80 }
81}
82
83struct BorrowPtr<T> {
84 shared: SharedPtr<T>,
85 index: usize,
86}
87
88impl<T> Deref for BorrowPtr<T> {
89 type Target = SharedPtr<T>;
90
91 fn deref(&self) -> &Self::Target {
92 &self.shared
93 }
94}
95
96impl<T> DerefMut for BorrowPtr<T> {
97 fn deref_mut(&mut self) -> &mut Self::Target {
98 &mut self.shared
99 }
100}
101
102impl<T> Clone for BorrowPtr<T> {
103 fn clone(&self) -> Self {
104 let mut graph = self.inner().graph.lock().unwrap();
105 unsafe { graph.track_borrow_unchecked(self.index) };
106 BorrowPtr {
107 shared: self.shared.clone(),
108 index: self.index
109 }
110 }
111}
112
113impl<T> Drop for BorrowPtr<T> {
114 fn drop(&mut self) {
115 let Ok(mut graph) = self.inner().graph.lock() else { return }; unsafe {
117 if graph.untrack_borrow_unchecked(self.index) {
118 self.inner().data.get().as_mut().unwrap_unchecked().assume_init_drop();
119 }
120 }
121 }
122}
123
124trait Index: Unpin {
125 fn get(&self) -> usize;
126}
127
128impl Index for usize {
129 fn get(&self) -> usize {
130 *self
131 }
132}
133
134struct First;
135
136impl Index for First {
137 fn get(&self) -> usize {
138 0
139 }
140}
141
142struct FuturePtr<T, I: Index> {
143 shared: Option<SharedPtr<T>>,
144 index: I
145}
146
147impl<T, I: Index> FuturePtr<T, I> {
148 pub fn generalise(mut self) -> FuturePtr<T, usize> {
149 FuturePtr { shared: self.shared.take(), index: self.index.get() }
150 }
151}
152
153impl<T> FuturePtr<T, First> {
154 pub fn poll_shared(&mut self, cx: &mut std::task::Context<'_>) -> std::task::Poll<SharedPtr<T>> {
155 Pin::new(self).poll(cx).map(|(_, shared)| shared)
156 }
157}
158
159impl<T> FuturePtr<T, usize> {
160 pub fn poll_borrow(&mut self, cx: &mut std::task::Context<'_>) -> std::task::Poll<BorrowPtr<T>> {
161 Pin::new(self).poll(cx).map(|(index, shared)|
162 BorrowPtr { shared, index }
163 )
164 }
165
166}
167
168impl<T, I: Index> Future for FuturePtr<T, I> {
169 type Output = (usize, SharedPtr<T>);
170
171 fn poll(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Self::Output> {
172 let mut graph = self.shared.as_ref().unwrap().inner().graph.lock().unwrap();
173 let poll = unsafe { graph.poll_unchecked(self.index.get(), cx) };
174 drop(graph); poll.map(|index| (index, unsafe { self.shared.take().unwrap_unchecked() }))
176 }
177}
178
179impl<T, I: Index> FusedFuture for FuturePtr<T, I> {
180 fn is_terminated(&self) -> bool {
181 self.shared.is_none()
182 }
183}
184
185impl<T, I: Index> Drop for FuturePtr<T, I> {
186 fn drop(&mut self) {
187 let Some(shared) = self.shared.take() else { return };
188 let mut graph = shared.inner().graph.lock().unwrap();
189 if unsafe { graph.close_future_unchecked(self.index.get()) } {
190 unsafe { shared.inner().data.get().as_mut().unwrap_unchecked().assume_init_drop() };
191 drop(graph); drop(shared)
193 }
194 }
195}
196
197pub struct Context<'a, T> {
200 ptr: BorrowPtr<T>,
201 _contextualise_ref: PhantomData<fn(&'a T) -> Ref<T>>,
202 _contextualise_mut: PhantomData<fn(&'a mut T) -> RefMut<T>>,
203}
204
205unsafe impl<'a, T: Send> Send for Context<'a, T> {}
206
207unsafe impl<'a, T: Send> Sync for Context<'a, T> {}
208
209impl<'a, T> Clone for Context<'a, T> {
210 fn clone(&self) -> Self {
211 Self {
212 ptr: self.ptr.clone(),
213 _contextualise_ref: PhantomData,
214 _contextualise_mut: PhantomData
215 }
216 }
217}
218
219impl<'a, T> Context<'a, T> {
220 pub fn contextualise_ref<B: ?Sized>(self, rf: &'a B) -> Ref<T, B> {
221 Ref {
222 ptr: self.ptr,
223 borrow: rf,
224 }
225 }
226
227 pub fn contextualise_mut<B: ?Sized>(self, rf: &'a mut B) -> RefMut<T, B> {
228 RefMut {
229 ptr: self.ptr,
230 borrow: rf,
231 }
232 }
233
234 pub fn lift_ref<B: ?Sized>(&self, rf: &'a B) -> Ref<T, B> {
235 self.clone().contextualise_ref(rf)
236 }
237
238 pub fn lift_mut<B: ?Sized>(&self, rf_mut: &'a mut B) -> RefMut<T, B> {
239 self.clone().contextualise_mut(rf_mut)
240 }
241}
242
243pub struct ShareBox<T> {
246 ptr: SharedPtr<T>,
247 _share: PhantomData<*const T>
248}
249
250unsafe impl<T: Send> Send for ShareBox<T> {}
251
252unsafe impl<T: Sync> Sync for ShareBox<T> {}
253
254impl<T> ShareBox<T> {
255 pub fn new(value: T) -> Self {
256 ShareBox {
257 ptr: SharedPtr::new(value),
258 _share: PhantomData
259 }
260 }
261
262 fn into_shared(self) -> SharedPtr<T> {
263 let ptr = SharedPtr { inner: self.ptr.inner };
264 std::mem::forget(self);
265 ptr
266 }
267
268 pub fn into_ref_share(self) -> RefShare<T> {
270 let mut graph = self.ptr.inner().graph.lock().unwrap();
271 debug_assert_eq!(graph.share(), 0, r#"
272 Graph should only have one root and it must be the last to be freed,
273 hence it should be at the start of the free list / stack
274 "#
275 );
276 let index = 0;
277 unsafe { graph.untrack_borrow_unchecked(index) };
278 drop(graph);
279 let ptr = self.into_shared();
280 RefShare {
281 ptr: FuturePtr { shared: Some(ptr), index: First },
282 _borrow: PhantomData,
283 }
284 }
285
286 pub fn into_mut_share(self) -> RefMutShare<T> {
288 let mut graph = self.ptr.inner().graph.lock().unwrap();
289 debug_assert_eq!(graph.share(), 0, r#"
290 Graph should only have one root and it must be the last to be freed,
291 hence it should be at the start of the free list / stack
292 "#
293 );
294 let index = 0;
295 unsafe { graph.untrack_borrow_unchecked(index) };
296 drop(graph);
297 let ptr = self.into_shared();
298 RefMutShare {
299 ptr: FuturePtr { shared: Some(ptr), index: First },
300 _borrow: PhantomData,
301 }
302 }
303
304 pub fn share_ref(self) -> (RefShare<T>, Ref<T>) {
305 let mut graph = self.ptr.inner().graph.lock().unwrap();
306 debug_assert_eq!(graph.share(), 0, r#"
307 Graph should only have one root and it must be the last to be freed,
308 hence it should be at the start of the free list / stack
309 "#
310 );
311 let index = 0;
312 drop(graph);
313 let shared = self.into_shared();
314 let borrow = shared.inner().data.get() as *mut T;
315 let ptr = shared.clone();
316 (
317 RefShare {
318 ptr: FuturePtr { shared: Some(ptr), index: First },
319 _borrow: PhantomData,
320 },
321 Ref {
322 ptr: BorrowPtr { shared, index },
323 borrow,
324 }
325 )
326 }
327
328 pub fn share_mut(self) -> (RefMutShare<T>, RefMut<T>) {
329 let mut graph = self.ptr.inner().graph.lock().unwrap();
330 debug_assert_eq!(graph.share(), 0, r#"
331 Graph should only have one root and it must be the last to be freed,
332 hence it should be at the start of the free list / stack
333 "#
334 );
335 let index = 0;
336 drop(graph);
337 let shared = self.into_shared();
338 let borrow = shared.inner().data.get() as *mut T;
339 let ptr = shared.clone();
340 (
341 RefMutShare {
342 ptr: FuturePtr { shared: Some(ptr), index: First },
343 _borrow: PhantomData,
344 },
345 RefMut {
346 ptr: BorrowPtr { shared, index },
347 borrow,
348 }
349 )
350 }
351
352 pub fn spawn_ref<U>(self, f: impl FnOnce(Ref<T>) -> U) -> RefShare<T> {
353 let (fut, rf) = self.share_ref();
354 f(rf);
355 fut
356 }
357
358 pub fn spawn_mut<U>(self, f: impl FnOnce(RefMut<T>) -> U) -> RefMutShare<T> {
359 let (fut, rf_mut) = self.share_mut();
360 f(rf_mut);
361 fut
362 }
363
364 pub fn into_ref(self) -> Ref<T> {
365 let index = 0;
366 let shared = self.into_shared();
367 let borrow = shared.inner().data.get() as *const T;
368 Ref {
369 ptr: BorrowPtr { shared, index },
370 borrow,
371 }
372
373 }
374
375 pub fn into_mut(self) -> RefMut<T> {
376 let index = 0;
377 let shared = self.into_shared();
378 let borrow = shared.inner().data.get() as *mut T;
379 RefMut {
380 ptr: BorrowPtr { shared, index },
381 borrow,
382 }
383 }
384
385 pub fn into_inner(self) -> T {
386 unsafe { self.into_shared().inner().data.get().as_mut().unwrap_unchecked().assume_init_read() }
387 }
388
389 pub fn into_raw(self) -> *const T {
390 self.into_shared().into_raw()
391 }
392
393 pub unsafe fn from_raw(ptr: *const T) -> ShareBox<T> {
394 ShareBox {
395 ptr: SharedPtr::from_raw(ptr as *mut T),
396 _share: PhantomData
397 }
398 }
399}
400
401impl<T> Deref for ShareBox<T> {
402 type Target = T;
403
404 fn deref(&self) -> &Self::Target {
405 unsafe { self.ptr.get_ref() }
406 }
407}
408
409impl<T> DerefMut for ShareBox<T> {
410 fn deref_mut(&mut self) -> &mut Self::Target {
411 unsafe { self.ptr.get_mut() }
412 }
413}
414
415impl<T: Clone> Clone for ShareBox<T> {
416 fn clone(&self) -> Self {
417 ShareBox::new(T::clone(&*self))
418 }
419}
420
421impl<T> Drop for ShareBox<T> {
422 fn drop(&mut self) {
423 unsafe { self.ptr.inner().data.get().as_mut().unwrap_unchecked().assume_init_drop() }
424 }
425}
426
427#[derive(Clone)]
428pub struct Weak<T, B: ?Sized = T> {
429 shared: SharedPtr<T>,
430 borrow: *const B,
431 index: usize,
432 version: u64,
433}
434
435unsafe impl<T: Send, B: ?Sized + Sync> Send for Weak<T, B> {}
436
437unsafe impl<T: Send, B: ?Sized + Sync> Sync for Weak<T, B> {}
438
439impl<T, B: ?Sized> Weak<T, B> {
440 pub fn upgrade(self) -> Option<Ref<T, B>> {
441 let mut graph = self.shared.inner().graph.lock().unwrap();
442 unsafe { graph.try_upgrade_weak_unchecked(self.index, self.version) }
443 .then_some(drop(graph))
444 .map(|_| Ref {
445 ptr: BorrowPtr { shared: self.shared, index: self.index, },
446 borrow: self.borrow,
447 })
448 }
449}
450
451pub struct Ref<T, B: ?Sized = T> {
452 ptr: BorrowPtr<T>,
453 borrow: *const B,
454}
455
456unsafe impl<T: Send, B: ?Sized + Sync> Send for Ref<T, B> {}
457
458unsafe impl<T: Send, B: ?Sized + Sync> Sync for Ref<T, B> {}
459
460impl<T, B: ?Sized> Ref<T, B> {
461 pub fn downgrade(&self) -> Weak<T, B> {
462 let mut graph = self.ptr.inner().graph.lock().unwrap();
463 let version = unsafe { graph.track_weak_unchecked(self.ptr.index) };
464 Weak {
465 shared: self.ptr.shared.clone(),
466 borrow: self.borrow,
467 index: self.ptr.index,
468 version,
469 }
470 }
471
472 pub fn map<C: ?Sized>(self, f: impl for<'a> FnOnce(&'a B) -> &'a C) -> Ref<T, C> {
483 Ref {
484 ptr: self.ptr,
485 borrow: f(unsafe { self.borrow.as_ref().unwrap_unchecked() }) as *const C
486 }
487 }
488
489 pub fn context<R>(self, f: impl for<'a> FnOnce(&'a B, Context<'a, T>) -> R) -> R {
502 let Ref {
503 ptr,
504 borrow
505 } = self;
506 let context = Context::<'_, T> {
507 ptr,
508 _contextualise_ref: PhantomData,
509 _contextualise_mut: PhantomData,
510 };
511 f(unsafe { borrow.as_ref().unwrap() }, context)
512 }
513
514 pub async fn scope<F: Future>(self, f: impl for<'a> FnOnce(&'a B, Context<'a, T>, Spawner<'a>) -> F) -> F::Output {
527 let Ref {
528 ptr,
529 borrow
530 } = self;
531 let context = Context::<'_, T> {
532 ptr,
533 _contextualise_ref: PhantomData,
534 _contextualise_mut: PhantomData,
535 };
536 let anchor = Anchor::new();
537 let fut = f(unsafe { borrow.as_ref().unwrap() }, context, anchor.spawner.clone());
538 let ((), output) = futures::join!(anchor.stream().collect::<()>(), fut);
539 output
540 }
541
542 pub fn into_deref(self) -> Ref<T, B::Target> where B: Deref {
552 self.map(B::deref)
553 }
554
555 pub fn into_borrow<C>(self) -> Ref<T, C> where B: Borrow<C> {
565 self.map(B::borrow)
566 }
567}
568
569impl<T, B: ?Sized> Deref for Ref<T, B> {
570 type Target = B;
571
572 fn deref(&self) -> &Self::Target {
573 unsafe { self.borrow.as_ref().unwrap_unchecked() }
574 }
575}
576
577impl<T, B: ?Sized> Clone for Ref<T, B> {
578 fn clone(&self) -> Self {
579 Ref {
580 ptr: self.ptr.clone(),
581 borrow: self.borrow
582 }
583 }
584}
585
586impl<T, B: ?Sized> From<RefMut<T, B>> for Ref<T, B> {
587 fn from(value: RefMut<T, B>) -> Self {
588 value.into_ref()
589 }
590}
591
592pub struct RefMut<T, B: ?Sized = T> {
593 ptr: BorrowPtr<T>,
594 borrow: *mut B,
595}
596
597unsafe impl<T: Send, B: ?Sized + Send> Send for RefMut<T, B> {}
598
599unsafe impl<T, B: ?Sized + Sync> Sync for RefMut<T, B> {}
600
601impl<T, B: ?Sized> RefMut<T, B> {
602 pub fn into_ref(self) -> Ref<T, B> {
603 let RefMut {
604 ptr,
605 borrow
606 } = self;
607 Ref {
608 ptr,
609 borrow,
610 }
611 }
612
613 pub fn into_ref_forward(self) -> RefForward<T, B> {
615 let mut graph = self.ptr.inner().graph.lock().unwrap();
616 let index = graph.forward(self.ptr.index);
617 unsafe { graph.untrack_borrow_unchecked(index) };
618 drop(graph);
619 let ptr = SharedPtr { inner: self.ptr.inner };
620 let borrow = self.borrow;
621 std::mem::forget(self.ptr);
622 RefForward {
623 ptr: FuturePtr { shared: Some(ptr), index },
624 borrow,
625 }
626 }
627
628 pub fn into_mut_forward(self) -> RefMutForward<T, B> {
630 let mut graph = self.ptr.inner().graph.lock().unwrap();
631 let index = graph.forward(self.ptr.index);
632 unsafe { graph.untrack_borrow_unchecked(index) };
633 drop(graph);
634 let ptr = SharedPtr { inner: self.ptr.inner };
635 let borrow = self.borrow;
636 std::mem::forget(self.ptr);
637 RefMutForward {
638 ptr: FuturePtr { shared: Some(ptr), index },
639 borrow,
640 }
641 }
642
643 pub fn forward_ref(self) -> (RefForward<T, B>, Ref<T, B>) {
644 let mut graph = self.ptr.inner().graph.lock().unwrap();
645 let index = graph.forward(self.ptr.index);
646 drop(graph);
647 let shared = SharedPtr { inner: self.ptr.inner };
648 let borrow = self.borrow;
649 let ptr = shared.clone();
650 std::mem::forget(self.ptr);
651 (
652 RefForward {
653 ptr: FuturePtr { shared: Some(ptr), index },
654 borrow,
655 },
656 Ref {
657 ptr: BorrowPtr { shared, index },
658 borrow,
659 }
660 )
661 }
662
663 pub fn forward_mut(self) -> (RefMutForward<T, B>, RefMut<T, B>) {
664 let mut graph = self.ptr.inner().graph.lock().unwrap();
665 let index = graph.forward(self.ptr.index);
666 drop(graph);
667 let shared = SharedPtr { inner: self.ptr.inner };
668 let borrow = self.borrow;
669 let ptr = shared.clone();
670 std::mem::forget(self.ptr);
671 (
672 RefMutForward {
673 ptr: FuturePtr { shared: Some(ptr), index },
674 borrow,
675 },
676 RefMut {
677 ptr: BorrowPtr { shared, index },
678 borrow,
679 }
680 )
681 }
682
683 pub fn cleave_ref<U>(self, f: impl FnOnce(Ref<T, B>) -> U) -> RefForward<T, B> {
684 let (fut, rf) = self.forward_ref();
685 f(rf);
686 fut
687 }
688
689 pub fn cleave_mut<U>(self, f: impl FnOnce(RefMut<T, B>) -> U) -> RefMutForward<T, B> {
690 let (fut, rf_mut) = self.forward_mut();
691 f(rf_mut);
692 fut
693 }
694
695 pub fn map<C: ?Sized>(self, f: impl for<'a> FnOnce(&'a mut B) -> &'a mut C) -> RefMut<T, C> {
706 RefMut {
707 ptr: self.ptr,
708 borrow: f(unsafe { self.borrow.as_mut().unwrap_unchecked() }) as *mut C
709 }
710 }
711
712 pub fn context<R>(self, f: impl for<'a> FnOnce(&'a mut B, Context<'a, T>) -> R) -> R {
725 let RefMut {
726 ptr,
727 borrow
728 } = self;
729 let context = Context::<'_, T> {
730 ptr,
731 _contextualise_ref: PhantomData,
732 _contextualise_mut: PhantomData,
733 };
734 f(unsafe { borrow.as_mut().unwrap() }, context)
735 }
736
737 pub async fn scope<F: Future>(self, f: impl for<'a> FnOnce(&'a mut B, Context<'a, T>, Spawner<'a>) -> F) -> F::Output {
750 let RefMut {
751 ptr,
752 borrow
753 } = self;
754 let context = Context::<'_, T> {
755 ptr,
756 _contextualise_ref: PhantomData,
757 _contextualise_mut: PhantomData,
758 };
759 let anchor = Anchor::new();
760 let fut = f(unsafe { borrow.as_mut().unwrap() }, context, anchor.spawner.clone());
761 let ((), output) = futures::join!(anchor.stream().collect::<()>(), fut);
762 output
763 }
764
765 pub fn into_deref_mut(self) -> RefMut<T, B::Target> where B: DerefMut {
775 self.map(B::deref_mut)
776 }
777
778 pub fn into_borrow_mut<C>(self) -> RefMut<T, C> where B: BorrowMut<C> {
788 self.map(B::borrow_mut)
789 }
790}
791
792impl<T, B: ?Sized> Deref for RefMut<T, B> {
793 type Target = B;
794
795 fn deref(&self) -> &Self::Target {
796 unsafe { self.borrow.as_ref().unwrap_unchecked() }
797 }
798}
799
800impl<T, B: ?Sized> DerefMut for RefMut<T, B> {
801 fn deref_mut(&mut self) -> &mut Self::Target {
802 unsafe { self.borrow.as_mut().unwrap_unchecked() }
803 }
804}
805
806pub struct RefShare<T> {
809 ptr: FuturePtr<T, First>,
810 _borrow: PhantomData<*const T>,
811}
812
813unsafe impl<T: Send + Sync> Send for RefShare<T> {}
814
815unsafe impl<T: Send + Sync> Sync for RefShare<T> {}
816
817impl<T> RefShare<T> {
818 pub fn spawn(&mut self) -> SpawnRef<'_, T> {
819 SpawnRef { fut: self }
820 }
821
822 pub fn spawn_while<F: Unpin + for<'a> FnMut(&'a mut T) -> bool>(&mut self, f: F) -> SpawnRefWhile<'_, T, F> {
823 SpawnRefWhile { fut: self, f }
824 }
825
826 pub fn get(&self) -> Option<&T> {
827 unsafe { self.ptr.shared.as_ref().map(|shared| shared.get_ref()) }
828 }
829
830 pub fn as_ref(&self) -> Ref<T> {
831 let shared = self.ptr.shared.as_ref().unwrap().clone();
832 let borrow = shared.inner().data.get() as *mut T;
833 let mut graph = shared.inner().graph.lock().unwrap();
834 let index = self.ptr.index.get();
835 unsafe { graph.track_borrow_unchecked(index) };
836 drop(graph);
837 Ref {
838 ptr: BorrowPtr { shared, index },
839 borrow,
840 }
841 }
842
843 pub fn generalise(self) -> RefForward<T> {
844 let borrow = self.ptr.shared.as_ref().unwrap().inner().data.get() as *mut T;
845 RefForward { ptr: self.ptr.generalise(), borrow }
846 }
847
848 pub fn into_raw(mut self) -> Option<*const T> {
849 self.ptr.shared.take().map(|shared| shared.into_raw() as *const T)
850 }
851
852 pub unsafe fn from_raw(ptr: *const T) -> RefShare<T> {
853 RefShare {
854 ptr: FuturePtr {
855 shared: Some(SharedPtr::from_raw(ptr as *mut T)),
856 index: First
857 },
858 _borrow: PhantomData,
859 }
860 }
861}
862
863impl<T> Future for RefShare<T> {
864 type Output = ShareBox<T>;
865
866 fn poll(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Self::Output> {
867 self.ptr.poll_shared(cx).map(|ptr| ShareBox { ptr, _share: PhantomData })
868 }
869}
870
871impl<T> FusedFuture for RefShare<T> {
872 fn is_terminated(&self) -> bool {
873 self.ptr.is_terminated()
874 }
875}
876
877pub struct RefMutShare<T> {
878 ptr: FuturePtr<T, First>,
879 _borrow: PhantomData<*const T>,
880}
881
882unsafe impl<T: Send> Send for RefMutShare<T> {}
883
884unsafe impl<T: Sync> Sync for RefMutShare<T> {}
885
886impl<T> RefMutShare<T> {
887 pub fn spawn_mut(&mut self) -> SpawnRefMut<'_, T> {
888 SpawnRefMut { fut: self }
889 }
890
891 pub fn spawn_mut_while<F: Unpin + for<'a> FnMut(&'a mut T) -> bool>(&mut self, f: F) -> SpawnRefMutWhile<'_, T, F> {
892 SpawnRefMutWhile { fut: self, f }
893 }
894
895 pub fn generalise(self) -> RefMutForward<T> {
896 let borrow = self.ptr.shared.as_ref().unwrap().inner().data.get() as *mut T;
897 RefMutForward { ptr: self.ptr.generalise(), borrow }
898 }
899
900 pub fn into_raw(mut self) -> Option<*const T> {
901 self.ptr.shared.take().map(|shared| shared.into_raw() as *const T)
902 }
903
904 pub unsafe fn from_raw(ptr: *const T) -> RefMutShare<T> {
905 RefMutShare {
906 ptr: FuturePtr {
907 shared: Some(SharedPtr::from_raw(ptr as *mut T)),
908 index: First
909 },
910 _borrow: PhantomData,
911 }
912 }
913}
914
915impl<T> Future for RefMutShare<T> {
916 type Output = ShareBox<T>;
917
918 fn poll(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Self::Output> {
919 self.ptr.poll_shared(cx).map(|ptr| ShareBox { ptr, _share: PhantomData })
920 }
921}
922
923impl<T> FusedFuture for RefMutShare<T> {
924 fn is_terminated(&self) -> bool {
925 self.ptr.is_terminated()
926 }
927}
928
929impl<T> From<RefShare<T>> for RefMutShare<T> {
930 fn from(value: RefShare<T>) -> Self {
931 RefMutShare { ptr: value.ptr, _borrow: value._borrow }
932 }
933}
934
935pub struct RefForward<T, B: ?Sized = T> {
936 ptr: FuturePtr<T, usize>,
937 borrow: *mut B,
938}
939
940unsafe impl<T: Send, B: ?Sized + Sync> Send for RefForward<T, B> {}
941
942unsafe impl<T: Send, B: ?Sized + Sync> Sync for RefForward<T, B> {}
943
944impl<T, B: ?Sized> RefForward<T, B> {
945 pub fn split(&mut self) -> SplitRef<'_, T, B> {
946 SplitRef { fut: self }
947 }
948
949 pub fn split_while<F: Unpin + for<'a> FnMut(&'a mut B) -> bool>(&mut self, f: F) -> SplitRefWhile<'_, T, B, F> {
950 SplitRefWhile { fut: self, f }
951 }
952
953 pub fn get(&self) -> Option<&T> {
954 unsafe { self.ptr.shared.as_ref().map(|shared| shared.get_ref()) }
955 }
956
957 pub fn as_ref(&self) -> Ref<T, B> {
958 let shared = self.ptr.shared.as_ref().unwrap().clone();
959 let borrow = self.borrow;
960 let mut graph = shared.inner().graph.lock().unwrap();
961 let index = self.ptr.index.get();
962 unsafe { graph.track_borrow_unchecked(index) };
963 drop(graph);
964 Ref {
965 ptr: BorrowPtr { shared, index },
966 borrow
967 }
968 }
969}
970
971impl<T, B: ?Sized> Future for RefForward<T, B> {
972 type Output = RefMut<T, B>;
973
974 fn poll(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Self::Output> {
975 self.ptr.poll_borrow(cx).map(|ptr| RefMut { ptr, borrow: self.borrow })
976 }
977}
978
979impl<T, B: ?Sized> FusedFuture for RefForward<T, B> {
980 fn is_terminated(&self) -> bool {
981 self.ptr.is_terminated()
982 }
983}
984
985pub struct RefMutForward<T, B: ?Sized = T> {
986 ptr: FuturePtr<T, usize>,
987 borrow: *mut B,
988}
989
990unsafe impl<T: Send, B: ?Sized + Send> Send for RefMutForward<T, B> {}
991
992unsafe impl<T, B: ?Sized + Sync> Sync for RefMutForward<T, B> {}
993
994impl<T, B: ?Sized> RefMutForward<T, B> {
995 pub fn split_mut(&mut self) -> SplitRefMut<'_, T, B> {
996 SplitRefMut { fut: self }
997 }
998
999 pub fn split_mut_while<F: Unpin + for<'a> FnMut(&'a mut B) -> bool>(&mut self, f: F) -> SplitRefMutWhile<'_, T, B, F> {
1000 SplitRefMutWhile { fut: self, f }
1001 }
1002}
1003
1004impl<T, B: ?Sized> Future for RefMutForward<T, B> {
1005 type Output = RefMut<T, B>;
1006
1007 fn poll(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Self::Output> {
1008 self.ptr.poll_borrow(cx).map(|ptr| RefMut { ptr, borrow: self.borrow })
1009 }
1010}
1011
1012impl<T, B: ?Sized> FusedFuture for RefMutForward<T, B> {
1013 fn is_terminated(&self) -> bool {
1014 self.ptr.is_terminated()
1015 }
1016}
1017
1018impl<T, B: ?Sized> From<RefForward<T, B>> for RefMutForward<T, B> {
1019 fn from(value: RefForward<T, B>) -> Self {
1020 RefMutForward { ptr: value.ptr, borrow: value.borrow }
1021 }
1022}
1023
1024pub struct SpawnRef<'f, T> {
1025 fut: &'f mut RefShare<T>
1026}
1027
1028impl<'f, T> Future for SpawnRef<'f, T> {
1029 type Output = Ref<T>;
1030
1031 fn poll(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Self::Output> {
1032 use std::task::Poll;
1033 match self.fut.poll_unpin(cx) {
1034 Poll::Ready(owner) => {
1035 let (fut, rf) = owner.share_ref();
1036 *self.fut = fut;
1037 Poll::Ready(rf)
1038 },
1039 Poll::Pending => Poll::Pending,
1040 }
1041 }
1042}
1043
1044impl<'f, T> Deref for SpawnRef<'f, T> {
1045 type Target = RefShare<T>;
1046
1047 fn deref(&self) -> &Self::Target {
1048 self.fut
1049 }
1050}
1051
1052impl<'f, T> DerefMut for SpawnRef<'f, T> {
1053 fn deref_mut(&mut self) -> &mut Self::Target {
1054 self.fut
1055 }
1056}
1057
1058pub struct SpawnRefMut<'f, T> {
1059 fut: &'f mut RefMutShare<T>
1060}
1061
1062impl<'f, T> Future for SpawnRefMut<'f, T> {
1063 type Output = RefMut<T>;
1064
1065 fn poll(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Self::Output> {
1066 use std::task::Poll;
1067 match self.fut.poll_unpin(cx) {
1068 Poll::Ready(owner) => {
1069 let (fut, rf_mut) = owner.share_mut();
1070 *self.fut = fut;
1071 Poll::Ready(rf_mut)
1072 },
1073 Poll::Pending => Poll::Pending,
1074 }
1075 }
1076}
1077
1078impl<'f, T> Deref for SpawnRefMut<'f, T> {
1079 type Target = RefMutShare<T>;
1080
1081 fn deref(&self) -> &Self::Target {
1082 self.fut
1083 }
1084}
1085
1086impl<'f, T> DerefMut for SpawnRefMut<'f, T> {
1087 fn deref_mut(&mut self) -> &mut Self::Target {
1088 self.fut
1089 }
1090}
1091
1092pub struct SplitRef<'f, T, B: ?Sized> {
1093 fut: &'f mut RefForward<T, B>
1094}
1095
1096impl<'f, T, B: ?Sized> Future for SplitRef<'f, T, B> {
1097 type Output = Ref<T, B>;
1098
1099 fn poll(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Self::Output> {
1100 use std::task::Poll;
1101 match self.fut.poll_unpin(cx) {
1102 Poll::Ready(rf_mut) => {
1103 let (fut, rf) = rf_mut.forward_ref();
1104 *self.fut = fut;
1105 Poll::Ready(rf)
1106 },
1107 Poll::Pending => Poll::Pending,
1108 }
1109 }
1110}
1111
1112impl<'f, T, B: ?Sized> Deref for SplitRef<'f, T, B> {
1113 type Target = RefForward<T, B>;
1114
1115 fn deref(&self) -> &Self::Target {
1116 self.fut
1117 }
1118}
1119
1120impl<'f, T, B: ?Sized> DerefMut for SplitRef<'f, T, B> {
1121 fn deref_mut(&mut self) -> &mut Self::Target {
1122 self.fut
1123 }
1124}
1125
1126pub struct SplitRefMut<'f, T, B: ?Sized> {
1127 fut: &'f mut RefMutForward<T, B>
1128}
1129
1130impl<'f, T, B: ?Sized> Future for SplitRefMut<'f, T, B> {
1131 type Output = RefMut<T, B>;
1132
1133 fn poll(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Self::Output> {
1134 use std::task::Poll;
1135 match self.fut.poll_unpin(cx) {
1136 Poll::Ready(rf_mut) => {
1137 let (fut, rf_mut) = rf_mut.forward_mut();
1138 *self.fut = fut;
1139 Poll::Ready(rf_mut)
1140 },
1141 Poll::Pending => Poll::Pending,
1142 }
1143 }
1144}
1145
1146impl<'f, T, B: ?Sized> Deref for SplitRefMut<'f, T, B> {
1147 type Target = RefMutForward<T, B>;
1148
1149 fn deref(&self) -> &Self::Target {
1150 self.fut
1151 }
1152}
1153
1154impl<'f, T, B: ?Sized> DerefMut for SplitRefMut<'f, T, B> {
1155 fn deref_mut(&mut self) -> &mut Self::Target {
1156 self.fut
1157 }
1158}
1159
1160pub struct SpawnRefWhile<'f, T, F: Unpin + for<'a> FnMut(&'a mut T) -> bool> {
1163 fut: &'f mut RefShare<T>,
1164 f: F
1165}
1166
1167impl<'f, T, F: Unpin + for<'a> FnMut(&'a mut T) -> bool> Stream for SpawnRefWhile<'f, T, F> {
1168 type Item = Ref<T>;
1169
1170 fn poll_next(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Option<Self::Item>> {
1171 use std::task::Poll;
1172 match self.fut.poll_unpin(cx) {
1173 Poll::Ready(mut owner) => {
1174 if (self.f)(&mut owner) {
1175 let (fut, rf) = owner.share_ref();
1176 *self.fut = fut;
1177 Poll::Ready(Some(rf))
1178 } else {
1179 *self.fut = owner.into_ref_share();
1180 Poll::Ready(None)
1181 }
1182 },
1183 Poll::Pending => Poll::Pending,
1184 }
1185 }
1186}
1187
1188impl<'f, T, F: Unpin + for<'a> FnMut(&'a mut T) -> bool> Deref for SpawnRefWhile<'f, T, F> {
1189 type Target = RefShare<T>;
1190
1191 fn deref(&self) -> &Self::Target {
1192 self.fut
1193 }
1194}
1195
1196impl<'f, T, F: Unpin + for<'a> FnMut(&'a mut T) -> bool> DerefMut for SpawnRefWhile<'f, T, F> {
1197 fn deref_mut(&mut self) -> &mut Self::Target {
1198 self.fut
1199 }
1200}
1201
1202pub struct SpawnRefMutWhile<'f, T, F: Unpin + for<'a> FnMut(&'a mut T) -> bool> {
1203 fut: &'f mut RefMutShare<T>,
1204 f: F
1205}
1206
1207impl<'f, T, F: Unpin + for<'a> FnMut(&'a mut T) -> bool> Stream for SpawnRefMutWhile<'f, T, F> {
1208 type Item = RefMut<T>;
1209
1210 fn poll_next(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Option<Self::Item>> {
1211 use std::task::Poll;
1212 match self.fut.poll_unpin(cx) {
1213 Poll::Ready(mut owner) => {
1214 if (self.f)(&mut owner) {
1215 let (fut, rf_mut) = owner.share_mut();
1216 *self.fut = fut;
1217 Poll::Ready(Some(rf_mut))
1218 } else {
1219 *self.fut = owner.into_mut_share();
1220 Poll::Ready(None)
1221 }
1222 },
1223 Poll::Pending => Poll::Pending,
1224 }
1225 }
1226}
1227
1228impl<'f, T, F: Unpin + for<'a> FnMut(&'a mut T) -> bool> Deref for SpawnRefMutWhile<'f, T, F> {
1229 type Target = RefMutShare<T>;
1230
1231 fn deref(&self) -> &Self::Target {
1232 self.fut
1233 }
1234}
1235
1236impl<'f, T, F: Unpin + for<'a> FnMut(&'a mut T) -> bool> DerefMut for SpawnRefMutWhile<'f, T, F> {
1237 fn deref_mut(&mut self) -> &mut Self::Target {
1238 self.fut
1239 }
1240}
1241
1242pub struct SplitRefWhile<'f, T, B: ?Sized, F: Unpin + for<'a> FnMut(&'a mut B) -> bool> {
1243 fut: &'f mut RefForward<T, B>,
1244 f: F
1245}
1246
1247impl<'f, T, B: ?Sized, F: Unpin + for<'a> FnMut(&'a mut B) -> bool> Stream for SplitRefWhile<'f, T, B, F> {
1248 type Item = Ref<T, B>;
1249
1250 fn poll_next(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Option<Self::Item>> {
1251 use std::task::Poll;
1252 match self.fut.poll_unpin(cx) {
1253 Poll::Ready(mut rf_mut) => {
1254 if (self.f)(&mut rf_mut) {
1255 let (fut, rf) = rf_mut.forward_ref();
1256 *self.fut = fut;
1257 Poll::Ready(Some(rf))
1258 } else {
1259 *self.fut = rf_mut.into_ref_forward();
1260 Poll::Ready(None)
1261 }
1262 },
1263 Poll::Pending => Poll::Pending,
1264 }
1265 }
1266}
1267
1268impl<'f, T, B: ?Sized, F: Unpin + for<'a> FnMut(&'a mut B) -> bool> Deref for SplitRefWhile<'f, T, B, F> {
1269 type Target = RefForward<T, B>;
1270
1271 fn deref(&self) -> &Self::Target {
1272 self.fut
1273 }
1274}
1275
1276impl<'f, T, B: ?Sized, F: Unpin + for<'a> FnMut(&'a mut B) -> bool> DerefMut for SplitRefWhile<'f, T, B, F> {
1277 fn deref_mut(&mut self) -> &mut Self::Target {
1278 self.fut
1279 }
1280}
1281
1282pub struct SplitRefMutWhile<'f, T, B: ?Sized, F: Unpin + for<'a> FnMut(&'a mut B) -> bool> {
1283 fut: &'f mut RefMutForward<T, B>,
1284 f: F
1285}
1286
1287impl<'f, T, B: ?Sized, F: Unpin + for<'a> FnMut(&'a mut B) -> bool> Stream for SplitRefMutWhile<'f, T, B, F> {
1288 type Item = RefMut<T, B>;
1289
1290 fn poll_next(mut self: Pin<&mut Self>, cx: &mut std::task::Context<'_>) -> std::task::Poll<Option<Self::Item>> {
1291 use std::task::Poll;
1292 match self.fut.poll_unpin(cx) {
1293 Poll::Ready(mut rf_mut) => {
1294 if (self.f)(&mut rf_mut) {
1295 let (fut, rf) = rf_mut.forward_mut();
1296 *self.fut = fut;
1297 Poll::Ready(Some(rf))
1298 } else {
1299 *self.fut = rf_mut.into_mut_forward();
1300 Poll::Ready(None)
1301 }
1302 },
1303 Poll::Pending => Poll::Pending,
1304 }
1305 }
1306}
1307
1308impl<'f, T, B: ?Sized, F: Unpin + for<'a> FnMut(&'a mut B) -> bool> Deref for SplitRefMutWhile<'f, T, B, F> {
1309 type Target = RefMutForward<T, B>;
1310
1311 fn deref(&self) -> &Self::Target {
1312 self.fut
1313 }
1314}
1315
1316impl<'f, T, B: ?Sized, F: Unpin + for<'a> FnMut(&'a mut B) -> bool> DerefMut for SplitRefMutWhile<'f, T, B, F> {
1317 fn deref_mut(&mut self) -> &mut Self::Target {
1318 self.fut
1319 }
1320}
1321
1322#[allow(type_alias_bounds)]
1325pub type WideShareBox<T: ?Sized> = ShareBox<Box<T>>;
1326
1327impl<T: ?Sized> WideShareBox<T> {
1328 pub fn share_wide_ref(self) -> (WideRefShare<T>, WideRef<T>) {
1329 let (fut, rf) = self.share_ref();
1330 (fut, rf.into_deref())
1331 }
1332
1333 pub fn share_wide_mut(self) -> (WideRefMutShare<T>, WideRefMut<T>) {
1334 let (fut, rf_mut) = self.share_mut();
1335 (fut, rf_mut.into_deref_mut())
1336 }
1337
1338 pub fn spawn_wide_ref<U>(self, f: impl FnOnce(WideRef<T>) -> U) -> WideRefShare<T> {
1339 self.spawn_ref(|rf| f(rf.into_deref()))
1340 }
1341
1342 pub fn spawn_wide_mut<U>(self, f: impl FnOnce(WideRefMut<T>) -> U) -> WideRefMutShare<T> {
1343 self.spawn_mut(|rf_mut| f(rf_mut.into_deref_mut()))
1344 }
1345}
1346
1347#[allow(type_alias_bounds)]
1348pub type WideWeak<T: ?Sized, B: ?Sized = T> = Weak<Box<T>, B>;
1349
1350#[allow(type_alias_bounds)]
1351pub type WideRef<T: ?Sized, B: ?Sized = T> = Ref<Box<T>, B>;
1352
1353#[allow(type_alias_bounds)]
1354pub type WideRefMut<T: ?Sized, B: ?Sized = T> = RefMut<Box<T>, B>;
1355
1356#[allow(type_alias_bounds)]
1357pub type WideRefShare<T: ?Sized> = RefShare<Box<T>>;
1358
1359impl<T: ?Sized> WideRefShare<T> {
1360 pub fn as_wide_ref(&self) -> WideRef<T> {
1361 self.as_ref().into_deref()
1362 }
1363}
1364
1365#[allow(type_alias_bounds)]
1366pub type WideRefMutShare<T: ?Sized> = RefMutShare<Box<T>>;
1367
1368#[allow(type_alias_bounds)]
1369pub type WideRefForward<T: ?Sized, B: ?Sized = T> = RefForward<Box<T>, B>;
1370
1371#[allow(type_alias_bounds)]
1372pub type WideRefMutForward<T: ?Sized, B: ?Sized = T> = RefMutForward<Box<T>, B>;
1373
1374#[cfg(test)]
1377mod test {
1378 use std::sync::Mutex;
1379
1380 use crate::ShareBox;
1381
1382 #[tokio::test]
1383 async fn vibe_check() {
1384 use tokio::{task::spawn, time::{sleep, Duration}};
1385 let mut example = ShareBox::new(Mutex::new(0));
1386 *example.get_mut().unwrap() += 1;
1387 let mut example = example
1388 .spawn_mut(|mut example| spawn(async move {
1390 *example.get_mut().unwrap() += 1;
1391 }))
1392 .await
1393 .spawn_mut(|example| spawn(async move {
1395 *example
1396 .cleave_mut(|mut example| spawn(async move {
1398 *example.get_mut().unwrap() += 1;
1399 }))
1400 .await
1401 .cleave_ref(|example| spawn(async move {
1403 let a = example.clone();
1404 let b = example.clone();
1405 let c = example;
1406 spawn(async move {
1407 sleep(Duration::from_millis(3)).await;
1408 *a.lock().unwrap() += 1;
1409 });
1410 spawn(async move {
1411 sleep(Duration::from_millis(2)).await;
1412 *b.lock().unwrap() += 1;
1413 });
1414 spawn(async move {
1415 sleep(Duration::from_millis(1)).await;
1416 *c.lock().unwrap() += 1;
1417 });
1418 }))
1419 .await
1420 .get_mut().unwrap() += 1;
1422 }))
1423 .await
1424 .spawn_ref(|example| spawn(async move {
1426 let a = example.clone();
1427 let b = example.clone();
1428 let c = example;
1429 spawn(async move {
1430 sleep(Duration::from_millis(3)).await;
1431 *a.lock().unwrap() += 1;
1432 });
1433 spawn(async move {
1434 sleep(Duration::from_millis(2)).await;
1435 *b.lock().unwrap() += 1;
1436 });
1437 spawn(async move {
1438 sleep(Duration::from_millis(1)).await;
1439 *c.lock().unwrap() += 1;
1440 });
1441 }))
1442 .await
1443 .spawn_mut(|mut example| spawn(async move {
1445 *example.get_mut().unwrap() += 1;
1446 }))
1447 .await;
1448 *example.get_mut().unwrap() += 1;
1450 assert_eq!(12, example.into_inner().into_inner().unwrap());
1451 }
1452
1453 #[test]
1454 fn new_drop() {
1455 let example = ShareBox::new(());
1456 drop(example);
1457 }
1458
1459 #[test]
1460 fn new_take() {
1461 let example = ShareBox::new(());
1462 example.into_inner();
1463 }
1464
1465 #[test]
1466 fn new_into_ref() {
1467 let example = ShareBox::new(());
1468 drop(example.into_ref());
1469 }
1470
1471 #[tokio::test]
1472 async fn lil_test() {
1473 let example = ShareBox::new(());
1474 let (fut, rm) = example.share_mut();
1475 drop(rm);
1476 let example = fut.await;
1477 example.into_inner();
1478 }
1479
1480 #[tokio::test]
1481 async fn context_test() {
1482 use futures::FutureExt;
1483 let x =
1484 ShareBox::new((0_i8, 0_i8))
1485 .spawn_mut(|rf_mut| tokio::spawn(async move {
1486 rf_mut
1487 .cleave_mut(|rf_mut| {
1488 let (mut rf_mut_left, mut rf_mut_right) = rf_mut.context(|(a, b), context| {
1489 (context.lift_mut(a), context.lift_mut(b))
1490 });
1491 tokio::spawn(async move {
1492 *rf_mut_left += 1
1493 });
1494 tokio::spawn(async move {
1495 *rf_mut_right -= 1
1496 });
1497 })
1498 .map(|mut rf_mut| {
1499 let ab = &mut* rf_mut;
1500 std::mem::swap(&mut ab.0, &mut ab.1)
1501 })
1502 .await
1503 }))
1504 .await
1505 .into_inner();
1506 assert_eq!(x, (-1_i8, 1_i8));
1507 }
1508
1509 #[tokio::test]
1510 async fn test_into_mut_share() {
1511 ShareBox::new(())
1512 .into_mut_share()
1513 .await
1514 .into_inner()
1515 }
1516
1517 #[tokio::test]
1518 async fn test_into_mut_forward() {
1519 ShareBox::new(())
1520 .spawn_mut(|rf_mut| tokio::spawn(async move {
1521 rf_mut
1522 .into_mut_forward()
1523 .await
1524 }))
1525 .await
1526 .into_inner()
1527 }
1528
1529 #[tokio::test]
1530 async fn test_drop_forward_then_drop_future() {
1531 ShareBox::new(())
1532 .spawn_mut(|rf_mut| tokio::spawn(async move {
1533 let (fut, rf_mut) = rf_mut
1534 .forward_mut();
1535 drop(rf_mut);
1536 drop(fut);
1537 }))
1538 .await
1539 .into_inner()
1540 }
1541
1542 #[tokio::test]
1543 async fn test_drop_future_then_drop_forward() {
1544 ShareBox::new(())
1545 .spawn_mut(|rf_mut| tokio::spawn(async move {
1546 let (fut, rf_mut) = rf_mut
1547 .forward_mut();
1548 drop(fut);
1549 drop(rf_mut);
1550 }))
1551 .await
1552 .into_inner()
1553 }
1554}