1233f1875SNick Fitzgerald use super::TryNew; 2*8325e1ecSAlex Crichton use crate::error::OutOfMemory; 3233f1875SNick Fitzgerald use std_alloc::sync::Arc; 4233f1875SNick Fitzgerald 5233f1875SNick Fitzgerald /// XXX: Stable Rust doesn't actually give us any method to build fallible 6233f1875SNick Fitzgerald /// allocation for `Arc<T>`, so this is only actually fallible when using 7233f1875SNick Fitzgerald /// nightly Rust and setting `RUSTFLAGS="--cfg arc_try_new"`. 8233f1875SNick Fitzgerald impl<T> TryNew for Arc<T> { 9233f1875SNick Fitzgerald type Value = T; 10233f1875SNick Fitzgerald 11233f1875SNick Fitzgerald #[inline] try_new(value: T) -> Result<Self, OutOfMemory> where Self: Sized,12233f1875SNick Fitzgerald fn try_new(value: T) -> Result<Self, OutOfMemory> 13233f1875SNick Fitzgerald where 14233f1875SNick Fitzgerald Self: Sized, 15233f1875SNick Fitzgerald { 16233f1875SNick Fitzgerald #[cfg(arc_try_new)] 17233f1875SNick Fitzgerald return Arc::try_new(value).map_err(|_| { 18233f1875SNick Fitzgerald // We don't have access to the exact size of the inner `Arc` 19233f1875SNick Fitzgerald // allocation, but (at least at one point) it was made up of a 20233f1875SNick Fitzgerald // strong ref count, a weak ref count, and the inner value. 21233f1875SNick Fitzgerald let bytes = core::mem::size_of::<(usize, usize, T)>(); 22233f1875SNick Fitzgerald OutOfMemory::new(bytes) 23233f1875SNick Fitzgerald }); 24233f1875SNick Fitzgerald 25233f1875SNick Fitzgerald #[cfg(not(arc_try_new))] 26233f1875SNick Fitzgerald return Ok(Arc::new(value)); 27233f1875SNick Fitzgerald } 28233f1875SNick Fitzgerald } 299acefdfeSAlex Crichton 309acefdfeSAlex Crichton #[cfg(test)] 319acefdfeSAlex Crichton mod test { 329acefdfeSAlex Crichton use super::{Arc, TryNew}; 339acefdfeSAlex Crichton 349acefdfeSAlex Crichton #[test] try_new()359acefdfeSAlex Crichton fn try_new() { 369acefdfeSAlex Crichton <Arc<_> as TryNew>::try_new(4).unwrap(); 379acefdfeSAlex Crichton } 389acefdfeSAlex Crichton } 39