@@ -258,12 +258,12 @@ use core::iter;
258
258
use core:: marker:: { PhantomData , Unsize } ;
259
259
#[ cfg( not( no_global_oom_handling) ) ]
260
260
use core:: mem:: size_of_val;
261
- use core:: mem:: { self , align_of_val_raw, forget} ;
262
- use core:: ops:: { CoerceUnsized , Deref , DispatchFromDyn , Receiver } ;
261
+ use core:: mem:: { self , align_of_val_raw, forget, ManuallyDrop } ;
262
+ use core:: ops:: { CoerceUnsized , Deref , DerefMut , DispatchFromDyn , Receiver } ;
263
263
use core:: panic:: { RefUnwindSafe , UnwindSafe } ;
264
264
#[ cfg( not( no_global_oom_handling) ) ]
265
265
use core:: pin:: Pin ;
266
- use core:: ptr:: { self , NonNull } ;
266
+ use core:: ptr:: { self , drop_in_place , NonNull } ;
267
267
#[ cfg( not( no_global_oom_handling) ) ]
268
268
use core:: slice:: from_raw_parts_mut;
269
269
@@ -2744,3 +2744,139 @@ fn data_offset_align(align: usize) -> usize {
2744
2744
let layout = Layout :: new :: < RcBox < ( ) > > ( ) ;
2745
2745
layout. size ( ) + layout. padding_needed_for ( align)
2746
2746
}
2747
+
2748
+ /// A uniquely owned `Rc`
2749
+ ///
2750
+ /// This represents an `Rc` that is known to be uniquely owned -- that is, have exactly one strong
2751
+ /// reference. Multiple weak pointers can be created, but attempts to upgrade those to strong
2752
+ /// references will fail unless the `UniqueRc` they point to has been converted into a regular `Rc`.
2753
+ ///
2754
+ /// Because they are uniquely owned, the contents of a `UniqueRc` can be freely mutated. A common
2755
+ /// use case is to have an object be mutable during its initialization phase but then have it become
2756
+ /// immutable and converted to a normal `Rc`.
2757
+ ///
2758
+ /// This can be used as a flexible way to create cyclic data structures, as in the example below.
2759
+ ///
2760
+ /// ```
2761
+ /// #![feature(unique_rc_arc)]
2762
+ /// use std::rc::{Rc, Weak, UniqueRc};
2763
+ ///
2764
+ /// struct Gadget {
2765
+ /// #[allow(dead_code)]
2766
+ /// me: Weak<Gadget>,
2767
+ /// }
2768
+ ///
2769
+ /// fn create_gadget() -> Option<Rc<Gadget>> {
2770
+ /// let mut rc = UniqueRc::new(Gadget {
2771
+ /// me: Weak::new(),
2772
+ /// });
2773
+ /// rc.me = UniqueRc::downgrade(&rc);
2774
+ /// Some(UniqueRc::into_rc(rc))
2775
+ /// }
2776
+ ///
2777
+ /// create_gadget().unwrap();
2778
+ /// ```
2779
+ ///
2780
+ /// An advantage of using `UniqueRc` over [`Rc::new_cyclic`] to build cyclic data structures is that
2781
+ /// [`Rc::new_cyclic`]'s `data_fn` parameter cannot be async or return a [`Result`]. As shown in the
2782
+ /// previous example, `UniqueRc` allows for more flexibility in the construction of cyclic data,
2783
+ /// including fallible or async constructors.
2784
+ #[ unstable( feature = "unique_rc_arc" , issue = "112566" ) ]
2785
+ #[ derive( Debug ) ]
2786
+ pub struct UniqueRc < T > {
2787
+ ptr : NonNull < RcBox < T > > ,
2788
+ phantom : PhantomData < RcBox < T > > ,
2789
+ }
2790
+
2791
+ impl < T > UniqueRc < T > {
2792
+ /// Creates a new `UniqueRc`
2793
+ ///
2794
+ /// Weak references to this `UniqueRc` can be created with [`UniqueRc::downgrade`]. Upgrading
2795
+ /// these weak references will fail before the `UniqueRc` has been converted into an [`Rc`].
2796
+ /// After converting the `UniqueRc` into an [`Rc`], any weak references created beforehand will
2797
+ /// point to the new [`Rc`].
2798
+ #[ cfg( not( no_global_oom_handling) ) ]
2799
+ #[ unstable( feature = "unique_rc_arc" , issue = "112566" ) ]
2800
+ pub fn new ( value : T ) -> Self {
2801
+ Self {
2802
+ ptr : Box :: leak ( Box :: new ( RcBox {
2803
+ strong : Cell :: new ( 0 ) ,
2804
+ // keep one weak reference so if all the weak pointers that are created are dropped
2805
+ // the UniqueRc still stays valid.
2806
+ weak : Cell :: new ( 1 ) ,
2807
+ value,
2808
+ } ) )
2809
+ . into ( ) ,
2810
+ phantom : PhantomData ,
2811
+ }
2812
+ }
2813
+
2814
+ /// Creates a new weak reference to the `UniqueRc`
2815
+ ///
2816
+ /// Attempting to upgrade this weak reference will fail before the `UniqueRc` has been converted
2817
+ /// to a [`Rc`] using [`UniqueRc::into_rc`].
2818
+ #[ unstable( feature = "unique_rc_arc" , issue = "112566" ) ]
2819
+ pub fn downgrade ( this : & Self ) -> Weak < T > {
2820
+ // SAFETY: This pointer was allocated at creation time and we guarantee that we only have
2821
+ // one strong reference before converting to a regular Rc.
2822
+ unsafe {
2823
+ this. ptr . as_ref ( ) . inc_weak ( ) ;
2824
+ }
2825
+ Weak { ptr : this. ptr }
2826
+ }
2827
+
2828
+ /// Converts the `UniqueRc` into a regular [`Rc`]
2829
+ ///
2830
+ /// This consumes the `UniqueRc` and returns a regular [`Rc`] that contains the `value` that
2831
+ /// is passed to `into_rc`.
2832
+ ///
2833
+ /// Any weak references created before this method is called can now be upgraded to strong
2834
+ /// references.
2835
+ #[ unstable( feature = "unique_rc_arc" , issue = "112566" ) ]
2836
+ pub fn into_rc ( this : Self ) -> Rc < T > {
2837
+ let mut this = ManuallyDrop :: new ( this) ;
2838
+ // SAFETY: This pointer was allocated at creation time so we know it is valid.
2839
+ unsafe {
2840
+ // Convert our weak reference into a strong reference
2841
+ this. ptr . as_mut ( ) . strong . set ( 1 ) ;
2842
+ Rc :: from_inner ( this. ptr )
2843
+ }
2844
+ }
2845
+ }
2846
+
2847
+ #[ unstable( feature = "unique_rc_arc" , issue = "112566" ) ]
2848
+ impl < T > Deref for UniqueRc < T > {
2849
+ type Target = T ;
2850
+
2851
+ fn deref ( & self ) -> & T {
2852
+ // SAFETY: This pointer was allocated at creation time so we know it is valid.
2853
+ unsafe { & self . ptr . as_ref ( ) . value }
2854
+ }
2855
+ }
2856
+
2857
+ #[ unstable( feature = "unique_rc_arc" , issue = "112566" ) ]
2858
+ impl < T > DerefMut for UniqueRc < T > {
2859
+ fn deref_mut ( & mut self ) -> & mut T {
2860
+ // SAFETY: This pointer was allocated at creation time so we know it is valid. We know we
2861
+ // have unique ownership and therefore it's safe to make a mutable reference because
2862
+ // `UniqueRc` owns the only strong reference to itself.
2863
+ unsafe { & mut ( * self . ptr . as_ptr ( ) ) . value }
2864
+ }
2865
+ }
2866
+
2867
+ #[ unstable( feature = "unique_rc_arc" , issue = "112566" ) ]
2868
+ unsafe impl < #[ may_dangle] T > Drop for UniqueRc < T > {
2869
+ fn drop ( & mut self ) {
2870
+ unsafe {
2871
+ // destroy the contained object
2872
+ drop_in_place ( DerefMut :: deref_mut ( self ) ) ;
2873
+
2874
+ // remove the implicit "strong weak" pointer now that we've destroyed the contents.
2875
+ self . ptr . as_ref ( ) . dec_weak ( ) ;
2876
+
2877
+ if self . ptr . as_ref ( ) . weak ( ) == 0 {
2878
+ Global . deallocate ( self . ptr . cast ( ) , Layout :: for_value ( self . ptr . as_ref ( ) ) ) ;
2879
+ }
2880
+ }
2881
+ }
2882
+ }
0 commit comments