Struct Box

Source
pub struct Box<'a, T: ?Sized> { /* private fields */ }
Expand description

An allocated instance of a type.

§Example

The basic usage are allocated recursive data structures. Here is a standard example using a Bump with 'static storage duration as the allocator:

use without_alloc::{Box, alloc::LocalAllocLeakExt};
use static_alloc::Bump;

#[derive(Debug)]
enum List<T> {
    Nil,
    Cons(T, Box<'static, List<T>>),
}

static SLAB: Bump<[u8; 1024]> = Bump::uninit();

let base = SLAB.boxed(List::Nil).unwrap();
let one = SLAB.boxed(List::Cons(0, base)).unwrap();
let two = SLAB.boxed(List::Cons(1, one)).unwrap();

// We can destruct the value (not with `*` but comparable).
match Box::take(two).0 {
    List::Cons(val, _)  => assert_eq!(val, 1), // Got the value back.
    _ => unreachable!(),
}

§Downsides

Unfortunately, this Box does not yet support unsizing. This is very unfortunate as it means you can’t use it for type erasure.

§Design

You will likely notice quickly that this has different semantics than the std::boxed::Box. Its inner pointer may be larger and it does not allocate nor deallocate memory on its own. This only wraps a fully initialized Uninit in a RAII/Drop interface.

Of course, there is a reason for this choice. The standard Box, storing only the raw pointer (as a Unique), requires its underlying allocation to have the exact same size and align (Layout) as the value and the layout needs to be recalculated when deallocating. Without a dependency on an allocator it would seem that the underlying layout becomes less important and can be thrown away but the opposite is the case. Many converters for the std::boxed::Box rely on being able to reallocate into a suitably constructed new allocation on will. Not having this luxury at our disposal means there should be a mechanism to cope with mismatching allocations anyways. So we simply store the full Uninit provided, relying on the library user to manage other aspects of allocation for us.

Instead, this Box can offer additional ways to manipulate and massage the underlying allocation. It should be possible to restore the exact allocation Box semantics (albeit with one usize more space usage) via a wrapper when an allocator is available.

Implementations§

Source§

impl<'a, T> Box<'a, T>

Source

pub fn new(val: T, into: Uninit<'a, T>) -> Self

Place val into a provided allocation.

Source

pub fn take(b: Self) -> (T, Uninit<'a, T>)

Take out the value and return the allocation.

This function is the opposite of new.

Source§

impl<'a, T: ?Sized> Box<'a, T>

Source

pub unsafe fn from_raw(init: Uninit<'a, T>) -> Self

Create a box from an pointer to an already initialized value.

Ensures that an already initialized value is properly dropped at the end of the lifetime of the Box.

§Safety

The pointed-to location must have already been initialized via external means. This is as unsafe as init.as_mut().

Source

pub fn into_raw(b: Self) -> Uninit<'a, T>

Unwrap the contained Uninit.

The value stays initialized but that information is no longer statically available. If you simply want to avoid the Drop call, consider ManuallyDrop instead.

Source

pub fn leak(b: Self) -> &'a mut T

Consumes and leaks the Box, returning a mutable reference, &'a mut T.

Compared to a standard Box it should be noted that the reference alone is not enough to invoke Box::from_raw.

Trait Implementations§

Source§

impl<T> AsMut<T> for Box<'_, T>

Source§

fn as_mut(&mut self) -> &mut T

Converts this type into a mutable reference of the (usually inferred) input type.
Source§

impl<T> AsRef<T> for Box<'_, T>

Source§

fn as_ref(&self) -> &T

Converts this type into a shared reference of the (usually inferred) input type.
Source§

impl<T> Borrow<T> for Box<'_, T>

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for Box<'_, T>

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<'a, T, U: ?Sized> CoerciblePtr<U> for Box<'a, T>

Unsize a Box, for example into a dynamic trait object.

§Usage

use unsize::{Coercion, CoerceUnsize};
use without_alloc::Uninit;
use core::mem::MaybeUninit;

let mut memory: MaybeUninit<usize> = MaybeUninit::uninit();
let boxed = Box::new(0usize, Uninit::from(&mut memory));

let debug: Box<dyn core::fmt::Debug> = unsafe {
    boxed.unsize(Coercion::to_debug())
};
Source§

type Pointee = T

The type we point to. This influences which kinds of unsizing are possible.
Source§

type Output = Box<'a, U>

The output type when unsizing the pointee to U.
Source§

fn as_sized_ptr(&mut self) -> *mut T

Get the raw inner pointer.
Source§

unsafe fn replace_ptr(self, new: *mut U) -> Box<'a, U>

Replace the container inner pointer with an unsized version. Read more
Source§

impl<T: Debug> Debug for Box<'_, T>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl<T: ?Sized> Deref for Box<'_, T>

Source§

type Target = T

The resulting type after dereferencing.
Source§

fn deref(&self) -> &T

Dereferences the value.
Source§

impl<T: ?Sized> DerefMut for Box<'_, T>

Source§

fn deref_mut(&mut self) -> &mut T

Mutably dereferences the value.
Source§

impl<T: ?Sized> Drop for Box<'_, T>

Source§

fn drop(&mut self)

Executes the destructor for this type. Read more
Source§

impl<T: Hash> Hash for Box<'_, T>

Source§

fn hash<H: Hasher>(&self, state: &mut H)

Feeds this value into the given Hasher. Read more
1.3.0 · Source§

fn hash_slice<H>(data: &[Self], state: &mut H)
where H: Hasher, Self: Sized,

Feeds a slice of this type into the given Hasher. Read more
Source§

impl<T: Ord> Ord for Box<'_, T>

Source§

fn cmp(&self, other: &Box<'_, T>) -> Ordering

This method returns an Ordering between self and other. Read more
1.21.0 · Source§

fn max(self, other: Self) -> Self
where Self: Sized,

Compares and returns the maximum of two values. Read more
1.21.0 · Source§

fn min(self, other: Self) -> Self
where Self: Sized,

Compares and returns the minimum of two values. Read more
1.50.0 · Source§

fn clamp(self, min: Self, max: Self) -> Self
where Self: Sized,

Restrict a value to a certain interval. Read more
Source§

impl<'a, 'b, T: PartialEq> PartialEq<Box<'b, T>> for Box<'a, T>

Source§

fn eq(&self, other: &Box<'_, T>) -> bool

Tests for self and other values to be equal, and is used by ==.
Source§

fn ne(&self, other: &Box<'_, T>) -> bool

Tests for !=. The default implementation is almost always sufficient, and should not be overridden without very good reason.
Source§

impl<'a, 'b, T: PartialOrd> PartialOrd<Box<'b, T>> for Box<'a, T>

Source§

fn partial_cmp(&self, other: &Box<'_, T>) -> Option<Ordering>

This method returns an ordering between self and other values if one exists. Read more
Source§

fn lt(&self, other: &Box<'_, T>) -> bool

Tests less than (for self and other) and is used by the < operator. Read more
Source§

fn le(&self, other: &Box<'_, T>) -> bool

Tests less than or equal to (for self and other) and is used by the <= operator. Read more
Source§

fn ge(&self, other: &Box<'_, T>) -> bool

Tests greater than or equal to (for self and other) and is used by the >= operator. Read more
Source§

fn gt(&self, other: &Box<'_, T>) -> bool

Tests greater than (for self and other) and is used by the > operator. Read more
Source§

impl<T> Pointer for Box<'_, T>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl<T: Eq> Eq for Box<'_, T>

Auto Trait Implementations§

§

impl<'a, T> Freeze for Box<'a, T>
where T: ?Sized,

§

impl<'a, T> RefUnwindSafe for Box<'a, T>
where T: RefUnwindSafe + ?Sized,

§

impl<'a, T> !Send for Box<'a, T>

§

impl<'a, T> !Sync for Box<'a, T>

§

impl<'a, T> Unpin for Box<'a, T>
where T: ?Sized,

§

impl<'a, T> !UnwindSafe for Box<'a, T>

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T, U> CoerceUnsize<U> for T
where T: CoerciblePtr<U>, U: ?Sized,

Source§

fn unsize<F>(self, with: Coercion<Self::Pointee, U, F>) -> Self::Output
where F: FnOnce(*const Self::Pointee) -> *const U,

Convert a pointer, as if with unsize coercion. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<P, T> Receiver for P
where P: Deref<Target = T> + ?Sized, T: ?Sized,

Source§

type Target = T

🔬This is a nightly-only experimental API. (arbitrary_self_types)
The target type on which the method may be called.
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.