@@ -12,7 +12,7 @@ use core::sync::atomic;
1212use  core:: sync:: atomic:: Ordering :: { Acquire ,  Relaxed ,  Release ,  SeqCst } ; 
1313use  core:: borrow; 
1414use  core:: fmt; 
15- use  core:: cmp:: { self ,   Ordering } ; 
15+ use  core:: cmp:: Ordering ; 
1616use  core:: iter; 
1717use  core:: intrinsics:: abort; 
1818use  core:: mem:: { self ,  align_of,  align_of_val,  size_of_val} ; 
@@ -1529,7 +1529,7 @@ impl<T: ?Sized> Weak<T> {
15291529/// If `self` was created using [`Weak::new`], this will return 0. 
15301530/// 
15311531/// [`Weak::new`]: #method.new 
1532- #[ unstable ( feature = "weak_counts" ,  issue  = "57977 " ) ]  
1532+ #[ stable ( feature = "weak_counts" ,  since  = "1.41.0 " ) ]  
15331533    pub  fn  strong_count ( & self )  -> usize  { 
15341534        if  let  Some ( inner)  = self . inner ( )  { 
15351535            inner. strong . load ( SeqCst ) 
@@ -1541,9 +1541,8 @@ impl<T: ?Sized> Weak<T> {
15411541    /// Gets an approximation of the number of `Weak` pointers pointing to this 
15421542/// allocation. 
15431543/// 
1544- /// If `self` was created using [`Weak::new`], this will return 0. If not, 
1545- /// the returned value is at least 1, since `self` still points to the 
1546- /// allocation. 
1544+ /// If `self` was created using [`Weak::new`], or if there are no remaining 
1545+ /// strong pointers, this will return 0. 
15471546/// 
15481547/// # Accuracy 
15491548/// 
@@ -1552,31 +1551,22 @@ impl<T: ?Sized> Weak<T> {
15521551/// `Weak`s pointing to the same allocation. 
15531552/// 
15541553/// [`Weak::new`]: #method.new 
1555- #[ unstable( feature = "weak_counts" ,  issue = "57977" ) ]  
1556-     pub  fn  weak_count ( & self )  -> Option < usize >  { 
1557-         // Due to the implicit weak pointer added when any strong pointers are 
1558-         // around, we cannot implement `weak_count` correctly since it 
1559-         // necessarily requires accessing the strong count and weak count in an 
1560-         // unsynchronized fashion. So this version is a bit racy. 
1554+ #[ stable( feature = "weak_counts" ,  since = "1.41.0" ) ]  
1555+     pub  fn  weak_count ( & self )  -> usize  { 
15611556        self . inner ( ) . map ( |inner| { 
1562-             let  strong = inner. strong . load ( SeqCst ) ; 
15631557            let  weak = inner. weak . load ( SeqCst ) ; 
1558+             let  strong = inner. strong . load ( SeqCst ) ; 
15641559            if  strong == 0  { 
1565-                 // If the last `Arc` has *just* been dropped, it might not yet 
1566-                 // have removed the implicit weak count, so the value we get 
1567-                 // here might be 1 too high. 
1568-                 weak
1560+                 0 
15691561            }  else  { 
1570-                 // As long as there's still at least 1 `Arc` around, subtract 
1571-                 // the implicit weak pointer. 
1572-                 // Note that the last `Arc` might get dropped between the 2 
1573-                 // loads we do above, removing the implicit weak pointer. This 
1574-                 // means that the value might be 1 too low here. In order to not 
1575-                 // return 0 here (which would happen if we're the only weak 
1576-                 // pointer), we guard against that specifically. 
1577-                 cmp:: max ( 1 ,  weak - 1 ) 
1562+                 // Since we observed that there was at least one strong pointer 
1563+                 // after reading the weak count, we know that the implicit weak 
1564+                 // reference (present whenever any strong references are alive) 
1565+                 // was still around when we observed the weak count, and can 
1566+                 // therefore safely subtract it. 
1567+                 weak - 1 
15781568            } 
1579-         } ) 
1569+         } ) . unwrap_or ( 0 ) 
15801570    } 
15811571
15821572    /// Returns `None` when the pointer is dangling and there is no allocated `ArcInner`, 
0 commit comments