Skip to content

Commit cb14a4c

Browse files
committed
Add RawUniqueRc methods for sized values
1 parent 2918ce1 commit cb14a4c

File tree

2 files changed

+66
-0
lines changed

2 files changed

+66
-0
lines changed

library/alloc/src/raw_rc/raw_rc.rs

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,8 @@ use crate::boxed::Box;
2929
use crate::raw_rc::MakeMutStrategy;
3030
use crate::raw_rc::RefCounter;
3131
#[cfg(not(no_global_oom_handling))]
32+
use crate::raw_rc::raw_unique_rc::RawUniqueRc;
33+
#[cfg(not(no_global_oom_handling))]
3234
use crate::raw_rc::raw_weak;
3335
use crate::raw_rc::raw_weak::RawWeak;
3436
#[cfg(not(no_global_oom_handling))]
@@ -430,6 +432,45 @@ impl<T, A> RawRc<T, A> {
430432
unsafe { Self::from_raw_parts(ptr.as_ptr().cast(), alloc) }
431433
}
432434

435+
#[cfg(not(no_global_oom_handling))]
436+
unsafe fn new_cyclic_impl<F, R>(mut weak: RawWeak<T, A>, data_fn: F) -> Self
437+
where
438+
A: Allocator,
439+
F: FnOnce(&RawWeak<T, A>) -> T,
440+
R: RefCounter,
441+
{
442+
let guard = unsafe { raw_weak::new_weak_guard::<T, A, R>(&mut weak) };
443+
let data = data_fn(&guard);
444+
445+
mem::forget(guard);
446+
447+
unsafe { RawUniqueRc::from_weak_with_value(weak, data).into_rc::<R>() }
448+
}
449+
450+
#[cfg(not(no_global_oom_handling))]
451+
pub(crate) unsafe fn new_cyclic<F, R>(data_fn: F) -> Self
452+
where
453+
A: Allocator + Default,
454+
F: FnOnce(&RawWeak<T, A>) -> T,
455+
R: RefCounter,
456+
{
457+
let weak = RawWeak::new_uninit::<0>();
458+
459+
unsafe { Self::new_cyclic_impl::<F, R>(weak, data_fn) }
460+
}
461+
462+
#[cfg(not(no_global_oom_handling))]
463+
pub(crate) unsafe fn new_cyclic_in<F, R>(data_fn: F, alloc: A) -> Self
464+
where
465+
A: Allocator,
466+
F: FnOnce(&RawWeak<T, A>) -> T,
467+
R: RefCounter,
468+
{
469+
let weak = RawWeak::new_uninit_in::<0>(alloc);
470+
471+
unsafe { Self::new_cyclic_impl::<F, R>(weak, data_fn) }
472+
}
473+
433474
/// # Safety
434475
///
435476
/// All accesses to `self` must use the same `RefCounter` implementation for `R`.

library/alloc/src/raw_rc/raw_unique_rc.rs

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -73,3 +73,28 @@ where
7373
}
7474
}
7575
}
76+
77+
impl<T, A> RawUniqueRc<T, A> {
78+
#[cfg(not(no_global_oom_handling))]
79+
pub(super) unsafe fn from_weak_with_value(weak: RawWeak<T, A>, value: T) -> Self {
80+
unsafe { weak.as_ptr().write(value) };
81+
82+
Self { weak, _marker: PhantomData, _marker2: PhantomData }
83+
}
84+
85+
#[cfg(not(no_global_oom_handling))]
86+
pub(crate) fn new(value: T) -> Self
87+
where
88+
A: Allocator + Default,
89+
{
90+
unsafe { Self::from_weak_with_value(RawWeak::new_uninit::<0>(), value) }
91+
}
92+
93+
#[cfg(not(no_global_oom_handling))]
94+
pub(crate) fn new_in(value: T, alloc: A) -> Self
95+
where
96+
A: Allocator,
97+
{
98+
unsafe { Self::from_weak_with_value(RawWeak::new_uninit_in::<0>(alloc), value) }
99+
}
100+
}

0 commit comments

Comments
 (0)