//! Types which pin data to its location in memory //! //! See the [standard library module] for more information. //! //! [standard library module]: ../../std/pin/index.html #![unstable(feature = "pin", issue = "49150")] use fmt; use future::{Future, UnsafeFutureObj}; use marker::{Sized, Unpin, Unsize}; use task::{Context, Poll}; use ops::{Deref, DerefMut, CoerceUnsized}; /// A pinned reference. /// /// This type is similar to a mutable reference, except that it pins its value, /// which prevents it from moving out of the reference, unless it implements [`Unpin`]. /// /// See the [`pin` module] documentation for furthur explanation on pinning. /// /// [`Unpin`]: ../../std/marker/trait.Unpin.html /// [`pin` module]: ../../std/pin/index.html #[unstable(feature = "pin", issue = "49150")] #[fundamental] pub struct PinMut<'a, T: ?Sized + 'a> { inner: &'a mut T, } #[unstable(feature = "pin", issue = "49150")] impl<'a, T: ?Sized + Unpin> PinMut<'a, T> { /// Construct a new `PinMut` around a reference to some data of a type that /// implements `Unpin`. #[unstable(feature = "pin", issue = "49150")] pub fn new(reference: &'a mut T) -> PinMut<'a, T> { PinMut { inner: reference } } /// Get a mutable reference to the data inside of this `PinMut`. #[unstable(feature = "pin", issue = "49150")] pub fn get_mut(this: PinMut<'a, T>) -> &'a mut T { this.inner } } #[unstable(feature = "pin", issue = "49150")] impl<'a, T: ?Sized> PinMut<'a, T> { /// Construct a new `PinMut` around a reference to some data of a type that /// may or may not implement `Unpin`. /// /// This constructor is unsafe because we do not know what will happen with /// that data after the lifetime of the reference ends. If you cannot guarantee that the /// data will never move again, calling this constructor is invalid. #[unstable(feature = "pin", issue = "49150")] pub unsafe fn new_unchecked(reference: &'a mut T) -> PinMut<'a, T> { PinMut { inner: reference } } /// Reborrow a `PinMut` for a shorter lifetime. /// /// For example, `PinMut::get_mut(x.reborrow())` (unsafely) returns a /// short-lived mutable reference reborrowing from `x`. #[unstable(feature = "pin", issue = "49150")] pub fn reborrow<'b>(&'b mut self) -> PinMut<'b, T> { PinMut { inner: self.inner } } /// Get a mutable reference to the data inside of this `PinMut`. /// /// This function is unsafe. You must guarantee that you will never move /// the data out of the mutable reference you receive when you call this /// function. #[unstable(feature = "pin", issue = "49150")] pub unsafe fn get_mut_unchecked(this: PinMut<'a, T>) -> &'a mut T { this.inner } /// Construct a new pin by mapping the interior value. /// /// For example, if you wanted to get a `PinMut` of a field of something, /// you could use this to get access to that field in one line of code. /// /// This function is unsafe. You must guarantee that the data you return /// will not move so long as the argument value does not move (for example, /// because it is one of the fields of that value), and also that you do /// not move out of the argument you receive to the interior function. #[unstable(feature = "pin", issue = "49150")] pub unsafe fn map_unchecked(this: PinMut<'a, T>, f: F) -> PinMut<'a, U> where F: FnOnce(&mut T) -> &mut U { PinMut { inner: f(this.inner) } } /// Assign a new value to the memory behind the pinned reference. #[unstable(feature = "pin", issue = "49150")] pub fn set(this: PinMut<'a, T>, value: T) where T: Sized, { *this.inner = value; } } #[unstable(feature = "pin", issue = "49150")] impl<'a, T: ?Sized> Deref for PinMut<'a, T> { type Target = T; fn deref(&self) -> &T { &*self.inner } } #[unstable(feature = "pin", issue = "49150")] impl<'a, T: ?Sized + Unpin> DerefMut for PinMut<'a, T> { fn deref_mut(&mut self) -> &mut T { self.inner } } #[unstable(feature = "pin", issue = "49150")] impl<'a, T: fmt::Debug + ?Sized> fmt::Debug for PinMut<'a, T> { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { fmt::Debug::fmt(&**self, f) } } #[unstable(feature = "pin", issue = "49150")] impl<'a, T: fmt::Display + ?Sized> fmt::Display for PinMut<'a, T> { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { fmt::Display::fmt(&**self, f) } } #[unstable(feature = "pin", issue = "49150")] impl<'a, T: ?Sized> fmt::Pointer for PinMut<'a, T> { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { fmt::Pointer::fmt(&(&*self.inner as *const T), f) } } #[unstable(feature = "pin", issue = "49150")] impl<'a, T: ?Sized + Unsize, U: ?Sized> CoerceUnsized> for PinMut<'a, T> {} #[unstable(feature = "pin", issue = "49150")] impl<'a, T: ?Sized> Unpin for PinMut<'a, T> {} #[unstable(feature = "futures_api", issue = "50547")] unsafe impl<'a, T, F> UnsafeFutureObj<'a, T> for PinMut<'a, F> where F: Future + 'a { fn into_raw(self) -> *mut () { unsafe { PinMut::get_mut_unchecked(self) as *mut F as *mut () } } unsafe fn poll(ptr: *mut (), cx: &mut Context) -> Poll { PinMut::new_unchecked(&mut *(ptr as *mut F)).poll(cx) } unsafe fn drop(_ptr: *mut ()) {} }