Struct bump_scope::BumpBox
source · pub struct BumpBox<'a, T: ?Sized> { /* private fields */ }
Expand description
A pointer type that uniquely owns a bump allocation of type T
. This type is returned whenever a bump allocation is made.
You can turn a BumpBox
into a reference with into_ref
and into_mut
and into a Box
with into_box
.
Unlike Box
, BumpBox
can not implement Clone
or free the allocated space as it does not store its allocator.
It’s essentially just an owned reference.
§BumpBox
has a lot of methods
BumpBox<[T]>
provides methods fromVec<T>
likepop
,clear
,truncate
,remove
,swap_remove
,retain
,drain
,extract_if
,dedup
, slice methods but with owned semantics likesplit_at
,split_first
,split_last
and new methods likepartition
.BumpBox<str>
andBumpBox<[u8]>
provide methods to convert between the two likeinto_boxed_bytes
,into_boxed_str
andinto_boxed_str_unchecked
.BumpBox<MaybeUninit<T>>
andBumpBox<[MaybeUninit<T>]>
provide methods likeinit
,assume_init
,init_fill
,init_fill_with
,init_fill_iter
,init_copy
,init_clone
andinit_zeroed
.
§No pinning
There is no way to safely pin a BumpBox
in the general case.
The drop guarantee of Pin
requires the value to be dropped before its memory is reused.
Preventing reuse of memory is not an option as that’s what this crate is all about.
So we need to drop the pinned value.
But there is no way to ensure that a value is dropped in an async context.
Example of an unsound pin macro implementation.
We define a bump_box_pin
macro that turns a BumpBox<T>
into a Pin<&mut T>
. This is only sound in synchronous code.
Here the memory Foo(1)
is allocated at is reused by Foo(2)
without dropping Foo(1)
first which violates the drop guarantee.
macro_rules! bump_box_pin {
($name:ident) => {
let mut boxed: BumpBox<_> = $name;
let $name = unsafe { Pin::new_unchecked(&mut *boxed) };
};
}
struct Foo(i32);
impl Drop for Foo {
fn drop(&mut self) {
println!("dropped Foo({}) at {:?}", self.0, self as *const Foo);
}
}
fn use_pinned(_foo: Pin<&mut Foo>) {}
fn violate_drop_guarantee(cx: &mut Context) {
let mut bump: Bump = Bump::new();
let mut future = Box::pin(async {
let foo = bump.alloc(Foo(1));
println!("created Foo({}) at {:?}", foo.0, &*foo as *const Foo);
bump_box_pin!(foo);
println!("pinned Foo({}) at {:?}", foo.0, &*foo as *const Foo);
yield_now().await;
use_pinned(foo);
});
assert_eq!(future.as_mut().poll(cx), Poll::Pending);
mem::forget(future);
bump.reset();
let foo = bump.alloc(Foo(2));
println!("created Foo({}) at {:?}", foo.0, &*foo as *const Foo);
}
This will print something like:
created Foo(1) at 0x78a4f4000d30
pinned Foo(1) at 0x78a4f4000d30
created Foo(2) at 0x78a4f4000d30
dropped Foo(2) at 0x78a4f4000d30
Implementations§
source§impl<'a, T: ?Sized> BumpBox<'a, T>
impl<'a, T: ?Sized> BumpBox<'a, T>
sourcepub fn into_box<A: BumpAllocator>(self, bump: A) -> Box<T, WithLifetime<'a, A>>
Available on crate feature alloc
only.
pub fn into_box<A: BumpAllocator>(self, bump: A) -> Box<T, WithLifetime<'a, A>>
alloc
only.Turns this BumpBox<T>
into Box<T>
. The bump
allocator is not required to be
the allocator this box was allocated in.
Unlike BumpBox
, Box
implements Clone
and frees space iff it is the last allocation:
let a = bump.alloc(3i32).into_box(&bump);
let b = a.clone();
assert_eq!(a, b);
drop(b);
drop(a);
assert_eq!(bump.stats().allocated(), 0);
sourcepub fn deallocate_in<A: BumpAllocator>(self, bump: A)
pub fn deallocate_in<A: BumpAllocator>(self, bump: A)
Drops this box and frees its memory iff it is the last allocation:
let boxed = bump.alloc(3i32);
assert_eq!(bump.stats().allocated(), 4);
boxed.deallocate_in(&bump);
assert_eq!(bump.stats().allocated(), 0);
source§impl<'a, T> BumpBox<'a, T>
impl<'a, T> BumpBox<'a, T>
sourcepub fn into_inner(self) -> T
pub fn into_inner(self) -> T
Consumes the BumpBox
, returning the wrapped value.
§Examples
let c = bump.alloc(5);
assert_eq!(c.into_inner(), 5);
sourcepub fn into_boxed_slice(self) -> BumpBox<'a, [T]> ⓘ
pub fn into_boxed_slice(self) -> BumpBox<'a, [T]> ⓘ
Converts a BumpBox<T>
into a BumpBox<[T]>
This conversion happens in place.
source§impl<'a> BumpBox<'a, [u8]>
impl<'a> BumpBox<'a, [u8]>
sourcepub const fn into_boxed_str(
self,
) -> Result<BumpBox<'a, str>, FromUtf8Error<Self>>
pub const fn into_boxed_str( self, ) -> Result<BumpBox<'a, str>, FromUtf8Error<Self>>
sourcepub const unsafe fn into_boxed_str_unchecked(self) -> BumpBox<'a, str> ⓘ
pub const unsafe fn into_boxed_str_unchecked(self) -> BumpBox<'a, str> ⓘ
Converts a slice of bytes to a string slice without checking that the string contains valid UTF-8.
See the safe version, into_boxed_str
, for more information.
§Safety
The bytes passed in must be valid UTF-8.
source§impl<'a, T: Sized> BumpBox<'a, MaybeUninit<T>>
impl<'a, T: Sized> BumpBox<'a, MaybeUninit<T>>
sourcepub fn init(self, value: T) -> BumpBox<'a, T> ⓘ
pub fn init(self, value: T) -> BumpBox<'a, T> ⓘ
Initializes self
with value
.
§Examples
let uninit = bump.alloc_uninit();
let init = uninit.init(1);
assert_eq!(*init, 1);
sourcepub unsafe fn assume_init(self) -> BumpBox<'a, T> ⓘ
pub unsafe fn assume_init(self) -> BumpBox<'a, T> ⓘ
§Safety
It is up to the caller to guarantee that the MaybeUninit<T>
really is in an initialized state. Calling this when the content is not yet fully initialized causes immediate undefined behavior.
source§impl<'a, T: Sized> BumpBox<'a, [MaybeUninit<T>]>
impl<'a, T: Sized> BumpBox<'a, [MaybeUninit<T>]>
sourcepub fn init_fill(self, value: T) -> BumpBox<'a, [T]> ⓘwhere
T: Clone,
pub fn init_fill(self, value: T) -> BumpBox<'a, [T]> ⓘwhere
T: Clone,
Initializes self
by filling it with elements by cloning value
.
§Examples
let buf = bump.alloc_uninit_slice(10);
let buf = buf.init_fill(1);
assert_eq!(buf, [1; 10]);
sourcepub fn init_fill_with(self, f: impl FnMut() -> T) -> BumpBox<'a, [T]> ⓘ
pub fn init_fill_with(self, f: impl FnMut() -> T) -> BumpBox<'a, [T]> ⓘ
Initializes self
by filling it with elements returned by calling a closure repeatedly.
This method uses a closure to create new values. If you’d rather
Clone
a given value, use init_fill
. If you want to use the Default
trait to generate values, you can pass Default::default
as the
argument.
§Examples
let buf = bump.alloc_uninit_slice(10);
let buf = buf.init_fill_with(Default::default);
assert_eq!(buf, [0; 10]);
sourcepub fn init_fill_iter(self, iter: impl Iterator<Item = T>) -> BumpBox<'a, [T]> ⓘ
pub fn init_fill_iter(self, iter: impl Iterator<Item = T>) -> BumpBox<'a, [T]> ⓘ
Initializes self
by filling it with elements returned from an iterator.
§Panics
This function will panic if the iterator runs out of items before the slice is filled.
§Examples
let buf = bump.alloc_uninit_slice(5);
let buf = buf.init_fill_iter(['a', 'b'].iter().copied().cycle());
assert_eq!(buf, ['a', 'b', 'a', 'b', 'a']);
sourcepub fn init_copy(self, slice: &[T]) -> BumpBox<'a, [T]> ⓘwhere
T: Copy,
pub fn init_copy(self, slice: &[T]) -> BumpBox<'a, [T]> ⓘwhere
T: Copy,
Initializes self
by copying the elements from slice
into self
.
The length of slice
must be the same as self
.
§Panics
This function will panic if the two slices have different lengths.
sourcepub fn init_clone(self, slice: &[T]) -> BumpBox<'a, [T]> ⓘwhere
T: Clone,
pub fn init_clone(self, slice: &[T]) -> BumpBox<'a, [T]> ⓘwhere
T: Clone,
Initializes self
by cloning the elements from slice
into self
.
The length of slice
must be the same as self
.
§Panics
This function will panic if the two slices have different lengths.
source§impl<'a, T> BumpBox<'a, [T]>
impl<'a, T> BumpBox<'a, [T]>
sourcepub const fn len(&self) -> usize
pub const fn len(&self) -> usize
Returns the number of elements in the slice, also referred to as its ‘length’.
sourcepub fn pop(&mut self) -> Option<T>
pub fn pop(&mut self) -> Option<T>
Removes the last element from a slice and returns it, or None
if it
is empty.
sourcepub fn clear(&mut self)
pub fn clear(&mut self)
Clears the slice, removing all values.
§Examples
let mut slice = bump.alloc_slice_copy(&[1, 2, 3]);
slice.clear();
assert!(slice.is_empty());
sourcepub fn truncate(&mut self, len: usize)
pub fn truncate(&mut self, len: usize)
Shortens the slice, keeping the first len
elements and dropping
the rest.
If len
is greater than the slice’s current length, this has no
effect.
The drain
method can emulate truncate
, but causes the excess
elements to be returned instead of dropped.
Note that this method has no effect on the allocated capacity of the vector.
§Examples
Truncating a five element vector to two elements:
let mut slice = bump.alloc_slice_copy(&[1, 2, 3, 4, 5]);
slice.truncate(2);
assert_eq!(slice, [1, 2]);
No truncation occurs when len
is greater than the slice’s current
length:
let mut slice = bump.alloc_slice_copy(&[1, 2, 3]);
slice.truncate(8);
assert_eq!(slice, [1, 2, 3]);
Truncating when len == 0
is equivalent to calling the clear
method.
let mut slice = bump.alloc_slice_copy(&[1, 2, 3]);
slice.truncate(0);
assert_eq!(slice, []);
sourcepub const fn as_slice(&self) -> &[T]
pub const fn as_slice(&self) -> &[T]
Extracts a slice containing the entire boxed slice.
Equivalent to &s[..]
.
sourcepub fn as_mut_slice(&mut self) -> &mut [T]
pub fn as_mut_slice(&mut self) -> &mut [T]
Extracts a mutable slice containing the entire boxed slice.
Equivalent to &mut s[..]
.
sourcepub fn as_ptr(&self) -> *const T
pub fn as_ptr(&self) -> *const T
Returns a raw pointer to the slice, or a dangling raw pointer valid for zero sized reads.
sourcepub fn as_mut_ptr(&mut self) -> *mut T
pub fn as_mut_ptr(&mut self) -> *mut T
Returns an unsafe mutable pointer to slice, or a dangling raw pointer valid for zero sized reads.
sourcepub fn as_non_null_ptr(&self) -> NonNull<T>
pub fn as_non_null_ptr(&self) -> NonNull<T>
Returns a raw nonnull pointer to the slice, or a dangling raw pointer valid for zero sized reads.
sourcepub fn as_non_null_slice(&self) -> NonNull<[T]>
pub fn as_non_null_slice(&self) -> NonNull<[T]>
Returns a raw nonnull pointer to the slice, or a dangling raw pointer valid for zero sized reads.
sourcepub unsafe fn set_len(&mut self, new_len: usize)
pub unsafe fn set_len(&mut self, new_len: usize)
Forces the length of the slice to new_len
.
This is a low-level operation that maintains none of the normal
invariants of the type. Normally changing the length of a boxed slice
is done using one of the safe operations instead, such as
truncate
or clear
.
§Safety
new_len
must be less than or equal to thecapacity
(capacity is not tracked by this type).- The elements at
old_len..new_len
must be initialized.
sourcepub fn remove(&mut self, index: usize) -> T
pub fn remove(&mut self, index: usize) -> T
Removes and returns the element at position index
within the vector,
shifting all elements after it to the left.
Note: Because this shifts over the remaining elements, it has a
worst-case performance of O(n). If you don’t need the order of elements
to be preserved, use swap_remove
instead.
§Panics
Panics if index
is out of bounds.
§Examples
let mut v = bump.alloc_slice_copy(&[1, 2, 3]);
assert_eq!(v.remove(1), 2);
assert_eq!(v, [1, 3]);
sourcepub fn swap_remove(&mut self, index: usize) -> T
pub fn swap_remove(&mut self, index: usize) -> T
Removes an element from the vector and returns it.
The removed element is replaced by the last element of the vector.
This does not preserve ordering, but is O(1).
If you need to preserve the element order, use remove
instead.
§Panics
Panics if index
is out of bounds.
§Examples
let mut v = bump.alloc_slice_copy(&["foo", "bar", "baz", "qux"]);
assert_eq!(v.swap_remove(1), "bar");
assert_eq!(v, ["foo", "qux", "baz"]);
assert_eq!(v.swap_remove(0), "foo");
assert_eq!(v, ["baz", "qux"]);
sourcepub fn split_at(self, mid: usize) -> (Self, Self)
pub fn split_at(self, mid: usize) -> (Self, Self)
Divides one slice into two at an index.
The first will contain all indices from [0, mid)
(excluding
the index mid
itself) and the second will contain all
indices from [mid, len)
(excluding the index len
itself).
§Panics
Panics if mid > len
.
§Examples
let v = bump.alloc_slice_copy(&[1, 2, 3, 4, 5, 6]);
{
let (left, right) = v.split_at(0);
assert_eq!(left, []);
assert_eq!(right, [1, 2, 3, 4, 5, 6]);
}
let v = bump.alloc_slice_copy(&[1, 2, 3, 4, 5, 6]);
{
let (left, right) = v.split_at(2);
assert_eq!(left, [1, 2]);
assert_eq!(right, [3, 4, 5, 6]);
}
let v = bump.alloc_slice_copy(&[1, 2, 3, 4, 5, 6]);
{
let (left, right) = v.split_at(6);
assert_eq!(left, [1, 2, 3, 4, 5, 6]);
assert_eq!(right, []);
}
sourcepub unsafe fn split_at_unchecked(self, mid: usize) -> (Self, Self)
pub unsafe fn split_at_unchecked(self, mid: usize) -> (Self, Self)
Divides one slice into two at an index, without doing bounds checking.
The first will contain all indices from [0, mid)
(excluding
the index mid
itself) and the second will contain all
indices from [mid, len)
(excluding the index len
itself).
For a safe alternative see split_at
.
§Safety
Calling this method with an out-of-bounds index is undefined behavior
even if the resulting reference is not used. The caller has to ensure that
0 <= mid <= self.len()
.
§Examples
let v = bump.alloc_slice_copy(&[1, 2, 3, 4, 5, 6]);
unsafe {
let (left, right) = v.split_at_unchecked(0);
assert_eq!(left, []);
assert_eq!(right, [1, 2, 3, 4, 5, 6]);
}
let v = bump.alloc_slice_copy(&[1, 2, 3, 4, 5, 6]);
unsafe {
let (left, right) = v.split_at_unchecked(2);
assert_eq!(left, [1, 2]);
assert_eq!(right, [3, 4, 5, 6]);
}
let v = bump.alloc_slice_copy(&[1, 2, 3, 4, 5, 6]);
unsafe {
let (left, right) = v.split_at_unchecked(6);
assert_eq!(left, [1, 2, 3, 4, 5, 6]);
assert_eq!(right, []);
}
sourcepub fn split_first(self) -> Option<(BumpBox<'a, T>, BumpBox<'a, [T]>)>
pub fn split_first(self) -> Option<(BumpBox<'a, T>, BumpBox<'a, [T]>)>
Returns the first and all the rest of the elements of the slice, or None
if it is empty.
This does consume the BumpBox
. You can create a new empty one with BumpBox::default
.
§Examples
let x = bump.alloc_slice_copy(&[0, 1, 2]);
if let Some((first, elements)) = x.split_first() {
assert_eq!(&*first, &0);
assert_eq!(&*elements, &[1, 2]);
}
sourcepub fn split_last(self) -> Option<(BumpBox<'a, T>, BumpBox<'a, [T]>)>
pub fn split_last(self) -> Option<(BumpBox<'a, T>, BumpBox<'a, [T]>)>
Returns the last and all the rest of the elements of the slice, or None
if it is empty.
This does consume the BumpBox
. You can create a new empty one with BumpBox::default
.
§Examples
let x = bump.alloc_slice_copy(&[0, 1, 2]);
if let Some((last, elements)) = x.split_last() {
assert_eq!(&*last, &2);
assert_eq!(&*elements, &[0, 1]);
}
sourcepub fn merge(self, other: Self) -> Self
pub fn merge(self, other: Self) -> Self
Merges two contiguous slices into one.
§Panics
Panics if self
and other
are not contiguous.
Panics if T
is a zero-sized type and adding the lengths overflows.
§Examples
Split and merge back together.
let v = bump.alloc_slice_copy(&[1, 2, 3, 4, 5, 6]);
let (left, right) = v.split_at(3);
assert_eq!(left, [1, 2, 3]);
assert_eq!(right, [4, 5, 6]);
let merged = left.merge(right);
assert_eq!(merged, [1, 2, 3, 4, 5, 6]);
sourcepub fn retain<F>(&mut self, f: F)
pub fn retain<F>(&mut self, f: F)
Retains only the elements specified by the predicate, passing a mutable reference to it.
In other words, remove all elements e
such that f(&mut e)
returns false
.
This method operates in place, visiting each element exactly once in the
original order, and preserves the order of the retained elements.
§Examples
let mut slice = bump.alloc_slice_copy(&[1, 2, 3, 4]);
slice.retain(|x| if *x <= 3 {
*x += 1;
true
} else {
false
});
assert_eq!(slice, [2, 3, 4]);
sourcepub fn drain<R>(&mut self, range: R) -> Drain<'_, T> ⓘwhere
R: RangeBounds<usize>,
pub fn drain<R>(&mut self, range: R) -> Drain<'_, T> ⓘwhere
R: RangeBounds<usize>,
Removes the specified range from the slice in bulk, returning all removed elements as an iterator. If the iterator is dropped before being fully consumed, it drops the remaining removed elements.
The returned iterator keeps a mutable borrow on the slice to optimize its implementation.
§Panics
Panics if the starting point is greater than the end point or if the end point is greater than the length of the vector.
§Leaking
If the returned iterator goes out of scope without being dropped (due to
mem::forget
, for example), the vector may have lost and leaked
elements arbitrarily, including elements outside the range.
§Examples
let mut v = bump.alloc_slice_copy(&[1, 2, 3]);
let u = bump.alloc_iter(v.drain(1..));
assert_eq!(v, [1]);
assert_eq!(u, [2, 3]);
// A full range clears the slice, like `clear()` does
v.drain(..);
assert_eq!(v, []);
sourcepub fn extract_if<F>(&mut self, filter: F) -> ExtractIf<'_, T, F> ⓘ
pub fn extract_if<F>(&mut self, filter: F) -> ExtractIf<'_, T, F> ⓘ
Creates an iterator which uses a closure to determine if an element should be removed.
If the closure returns true, then the element is removed and yielded. If the closure returns false, the element will remain in the slice and will not be yielded by the iterator.
If the returned ExtractIf
is not exhausted, e.g. because it is dropped without iterating
or the iteration short-circuits, then the remaining elements will be retained.
Use retain
with a negated predicate if you do not need the returned iterator.
Using this method is equivalent to the following code:
let mut i = 0;
while i < slice.len() {
if some_predicate(&mut slice[i]) {
let val = slice.remove(i);
// your code here
} else {
i += 1;
}
}
But extract_if
is easier to use. extract_if
is also more efficient,
because it can backshift the elements of the array in bulk.
Note that extract_if
also lets you mutate every element in the filter closure,
regardless of whether you choose to keep or remove it.
§Examples
Splitting an array into evens and odds, reusing the original allocation:
let mut numbers = bump.alloc_slice_copy(&[1, 2, 3, 4, 5, 6, 8, 9, 11, 13, 14, 15]);
let evens = bump.alloc_iter(numbers.extract_if(|x| *x % 2 == 0));
let odds = numbers;
assert_eq!(evens, [2, 4, 6, 8, 14]);
assert_eq!(odds, [1, 3, 5, 9, 11, 13, 15]);
sourcepub fn dedup_by_key<F, K>(&mut self, key: F)
pub fn dedup_by_key<F, K>(&mut self, key: F)
Removes all but the first of consecutive elements in the slice that resolve to the same key.
If the slice is sorted, this removes all duplicates.
§Examples
let mut slice = bump.alloc_slice_copy(&[10, 20, 21, 30, 20]);
slice.dedup_by_key(|i| *i / 10);
assert_eq!(slice, [10, 20, 30, 20]);
sourcepub fn dedup_by<F>(&mut self, same_bucket: F)
pub fn dedup_by<F>(&mut self, same_bucket: F)
Removes all but the first of consecutive elements in the vector satisfying a given equality relation.
The same_bucket
function is passed references to two elements from the vector and
must determine if the elements compare equal. The elements are passed in opposite order
from their order in the slice, so if same_bucket(a, b)
returns true
, a
is removed.
If the vector is sorted, this removes all duplicates.
§Examples
let mut slice = bump.alloc_slice_copy(&["foo", "bar", "Bar", "baz", "bar"]);
slice.dedup_by(|a, b| a.eq_ignore_ascii_case(b));
assert_eq!(slice, ["foo", "bar", "baz", "bar"]);
sourcepub fn partition<F>(self, f: F) -> (Self, Self)
pub fn partition<F>(self, f: F) -> (Self, Self)
Consumes self
, creating two boxed slices from it.
The predicate passed to partition()
can return true
, or false
.
partition()
returns a pair, all of the elements for which it returned
true
, and all of the elements for which it returned false
.
See also is_partitioned()
and partition_in_place()
.
§Examples
Basic usage:
let slice = bump.alloc_slice_copy(&[1, 2, 3, 4, 5, 6, 7]);
let (even, odd) = slice.partition(|n| n % 2 == 0);
assert!(even.iter().all(|n| n % 2 == 0));
assert!(odd.iter().all(|n| n % 2 != 0));
source§impl<'a, T, const N: usize> BumpBox<'a, [[T; N]]>
impl<'a, T, const N: usize> BumpBox<'a, [[T; N]]>
sourcepub fn into_flattened(self) -> BumpBox<'a, [T]> ⓘ
pub fn into_flattened(self) -> BumpBox<'a, [T]> ⓘ
Takes a BumpBox<[[T; N]]>
and flattens it into a BumpBox<[T]>
.
§Panics
Panics if the length of the resulting slice would overflow a usize
.
This is only possible when flattening a slice of arrays of zero-sized
types, and thus tends to be irrelevant in practice. If
size_of::<T>() > 0
, this will never panic.
§Examples
let mut slice = bump.alloc_slice_copy(&[[1, 2, 3], [4, 5, 6], [7, 8, 9]]);
assert_eq!(slice.pop(), Some([7, 8, 9]));
let mut flattened = slice.into_flattened();
assert_eq!(flattened.pop(), Some(6));
source§impl<'a, T: ?Sized> BumpBox<'a, T>
impl<'a, T: ?Sized> BumpBox<'a, T>
sourcepub fn into_raw(self) -> NonNull<T>
pub fn into_raw(self) -> NonNull<T>
Consumes the BumpBox
, returning a wrapped raw pointer.
The pointer will be properly aligned and non-null. It is only valid for the lifetime 'a
.
After calling this function, the caller is responsible for dropping the
value previously managed by the BumpBox
. The easiest way to do this is to p.drop_in_place()
.
You can turn this pointer back into a BumpBox
with BumpBox::from_raw
.
§Examples
Manually dropping T
:
use bump_scope::{ Bump, BumpBox };
let bump: Bump = Bump::new();
let x = bump.alloc(String::from("Hello"));
let p = BumpBox::into_raw(x);
unsafe { p.as_ptr().drop_in_place() }
sourcepub unsafe fn from_raw(ptr: NonNull<T>) -> Self
pub unsafe fn from_raw(ptr: NonNull<T>) -> Self
Constructs a BumpBox
from a raw pointer.
After calling this function, the pointed to value is owned by the resulting BumpBox
.
Specifically, the BumpBox
destructor will call the destructor of T
.
For this to be safe, the pointer must point to a valid T
for the lifetime of 'a
.
§Safety
ptr
must point to a valid value for the lifetime'a
§Examples
Recreate a BumpBox
which was previously converted to a raw pointer
using BumpBox::into_raw
:
use bump_scope::{ Bump, BumpBox };
use core::ptr::NonNull;
unsafe fn from_raw_in<'a, T>(ptr: NonNull<T>, bump: &'a Bump) -> BumpBox<'a, T> {
BumpBox::from_raw(ptr)
}
let bump: Bump = Bump::new();
let x = bump.alloc(String::from("Hello"));
let ptr = BumpBox::into_raw(x);
let x = unsafe { from_raw_in(ptr, &bump) };
assert_eq!(x.as_str(), "Hello");
drop(x);
Manually create a BumpBox
from scratch by using the bump allocator:
use bump_scope::{ Bump, BumpBox };
use core::alloc::Layout;
use core::ptr::NonNull;
unsafe fn from_raw_in<'a, T>(ptr: NonNull<T>, bump: &'a Bump) -> BumpBox<'a, T> {
BumpBox::from_raw(ptr)
}
let bump: Bump = Bump::new();
let five = unsafe {
let ptr = bump.alloc_layout(Layout::new::<i32>());
// In general .write is required to avoid attempting to destruct
// the (uninitialized) previous contents of `ptr`, though for this
// simple example `*ptr = 5` would have worked as well.
ptr.as_ptr().write(5);
from_raw_in(ptr, &bump)
};
assert_eq!(*five, 5);
source§impl<'a> BumpBox<'a, dyn Any>
impl<'a> BumpBox<'a, dyn Any>
source§impl<'a> BumpBox<'a, dyn Any + Send>
impl<'a> BumpBox<'a, dyn Any + Send>
source§impl<'a> BumpBox<'a, dyn Any + Send + Sync>
impl<'a> BumpBox<'a, dyn Any + Send + Sync>
source§impl<'a, T> BumpBox<'a, MaybeUninit<T>>where
T: FromZeroes,
impl<'a, T> BumpBox<'a, MaybeUninit<T>>where
T: FromZeroes,
sourcepub fn init_zeroed(self) -> BumpBox<'a, T> ⓘ
Available on crate feature zerocopy
only.
pub fn init_zeroed(self) -> BumpBox<'a, T> ⓘ
zerocopy
only.Initializes self
by filling it with zero.
§Examples
let uninit = bump.alloc_uninit::<i32>();
let init = uninit.init_zeroed();
assert_eq!(*init, 0);
source§impl<'a, T> BumpBox<'a, [MaybeUninit<T>]>where
T: FromZeroes,
impl<'a, T> BumpBox<'a, [MaybeUninit<T>]>where
T: FromZeroes,
Trait Implementations§
source§impl<T: ?Sized> BorrowMut<T> for BumpBox<'_, T>
impl<T: ?Sized> BorrowMut<T> for BumpBox<'_, T>
source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
source§impl<T: ?Sized + BufRead> BufRead for BumpBox<'_, T>
Available on crate feature std
only.
impl<T: ?Sized + BufRead> BufRead for BumpBox<'_, T>
std
only.source§fn fill_buf(&mut self) -> Result<&[u8]>
fn fill_buf(&mut self) -> Result<&[u8]>
source§fn consume(&mut self, amt: usize)
fn consume(&mut self, amt: usize)
amt
bytes have been consumed from the buffer,
so they should no longer be returned in calls to read
. Read moresource§fn read_line(&mut self, buf: &mut String) -> Result<usize>
fn read_line(&mut self, buf: &mut String) -> Result<usize>
0xA
byte) is reached, and append
them to the provided String
buffer. Read moresource§fn has_data_left(&mut self) -> Result<bool, Error>
fn has_data_left(&mut self) -> Result<bool, Error>
buf_read_has_data_left
)Read
has any data left to be read. Read moresource§fn skip_until(&mut self, byte: u8) -> Result<usize, Error>
fn skip_until(&mut self, byte: u8) -> Result<usize, Error>
bufread_skip_until
)byte
or EOF is reached. Read moresource§impl<'a> Extend<BumpBox<'a, str>> for String
Available on crate feature alloc
only.
impl<'a> Extend<BumpBox<'a, str>> for String
alloc
only.source§fn extend<T: IntoIterator<Item = BumpBox<'a, str>>>(&mut self, iter: T)
fn extend<T: IntoIterator<Item = BumpBox<'a, str>>>(&mut self, iter: T)
source§fn extend_one(&mut self, item: A)
fn extend_one(&mut self, item: A)
extend_one
)source§fn extend_reserve(&mut self, additional: usize)
fn extend_reserve(&mut self, additional: usize)
extend_one
)source§impl<'a, T: ?Sized + Hasher> Hasher for BumpBox<'a, T>
impl<'a, T: ?Sized + Hasher> Hasher for BumpBox<'a, T>
source§fn write_u128(&mut self, i: u128)
fn write_u128(&mut self, i: u128)
u128
into this hasher.source§fn write_usize(&mut self, i: usize)
fn write_usize(&mut self, i: usize)
usize
into this hasher.source§fn write_i128(&mut self, i: i128)
fn write_i128(&mut self, i: i128)
i128
into this hasher.source§fn write_isize(&mut self, i: isize)
fn write_isize(&mut self, i: isize)
isize
into this hasher.source§fn write_length_prefix(&mut self, len: usize)
fn write_length_prefix(&mut self, len: usize)
hasher_prefixfree_extras
)source§impl<'b, 'a, T> IntoIterator for &'b BumpBox<'a, [T]>
impl<'b, 'a, T> IntoIterator for &'b BumpBox<'a, [T]>
source§impl<'b, 'a, T> IntoIterator for &'b mut BumpBox<'a, [T]>
impl<'b, 'a, T> IntoIterator for &'b mut BumpBox<'a, [T]>
source§impl<'a, T> IntoIterator for BumpBox<'a, [T]>
impl<'a, T> IntoIterator for BumpBox<'a, [T]>
source§impl<'a, T: ?Sized + Ord> Ord for BumpBox<'a, T>
impl<'a, T: ?Sized + Ord> Ord for BumpBox<'a, T>
1.21.0 · source§fn max(self, other: Self) -> Selfwhere
Self: Sized,
fn max(self, other: Self) -> Selfwhere
Self: Sized,
source§impl<'b, 'a, T: ?Sized + PartialOrd> PartialOrd<BumpBox<'b, T>> for BumpBox<'a, T>
impl<'b, 'a, T: ?Sized + PartialOrd> PartialOrd<BumpBox<'b, T>> for BumpBox<'a, T>
source§impl<T: ?Sized + Read> Read for BumpBox<'_, T>
Available on crate feature std
only.
impl<T: ?Sized + Read> Read for BumpBox<'_, T>
std
only.source§fn read(&mut self, buf: &mut [u8]) -> Result<usize>
fn read(&mut self, buf: &mut [u8]) -> Result<usize>
source§fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result<usize>
fn read_vectored(&mut self, bufs: &mut [IoSliceMut<'_>]) -> Result<usize>
read
, except that it reads into a slice of buffers. Read moresource§fn read_to_end(&mut self, buf: &mut Vec<u8>) -> Result<usize>
fn read_to_end(&mut self, buf: &mut Vec<u8>) -> Result<usize>
buf
. Read moresource§fn read_to_string(&mut self, buf: &mut String) -> Result<usize>
fn read_to_string(&mut self, buf: &mut String) -> Result<usize>
buf
. Read moresource§fn read_exact(&mut self, buf: &mut [u8]) -> Result<()>
fn read_exact(&mut self, buf: &mut [u8]) -> Result<()>
buf
. Read moresource§fn is_read_vectored(&self) -> bool
fn is_read_vectored(&self) -> bool
can_vector
)source§fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> Result<(), Error>
fn read_buf(&mut self, buf: BorrowedCursor<'_>) -> Result<(), Error>
read_buf
)source§fn read_buf_exact(&mut self, cursor: BorrowedCursor<'_>) -> Result<(), Error>
fn read_buf_exact(&mut self, cursor: BorrowedCursor<'_>) -> Result<(), Error>
read_buf
)cursor
. Read more1.0.0 · source§fn by_ref(&mut self) -> &mut Selfwhere
Self: Sized,
fn by_ref(&mut self) -> &mut Selfwhere
Self: Sized,
Read
. Read moresource§impl<T: ?Sized + Seek> Seek for BumpBox<'_, T>
Available on crate feature std
only.
impl<T: ?Sized + Seek> Seek for BumpBox<'_, T>
std
only.source§fn seek(&mut self, pos: SeekFrom) -> Result<u64>
fn seek(&mut self, pos: SeekFrom) -> Result<u64>
source§fn stream_position(&mut self) -> Result<u64>
fn stream_position(&mut self) -> Result<u64>
1.55.0 · source§fn rewind(&mut self) -> Result<(), Error>
fn rewind(&mut self) -> Result<(), Error>
source§impl<T: ?Sized + Write> Write for BumpBox<'_, T>
Available on crate feature std
only.
impl<T: ?Sized + Write> Write for BumpBox<'_, T>
std
only.source§fn write(&mut self, buf: &[u8]) -> Result<usize>
fn write(&mut self, buf: &[u8]) -> Result<usize>
source§fn flush(&mut self) -> Result<()>
fn flush(&mut self) -> Result<()>
source§fn write_all(&mut self, buf: &[u8]) -> Result<()>
fn write_all(&mut self, buf: &[u8]) -> Result<()>
source§fn write_fmt(&mut self, fmt: Arguments<'_>) -> Result<()>
fn write_fmt(&mut self, fmt: Arguments<'_>) -> Result<()>
source§fn is_write_vectored(&self) -> bool
fn is_write_vectored(&self) -> bool
can_vector
)impl<'a, T, U> CoerceUnsized<BumpBox<'a, U>> for BumpBox<'a, T>
nightly-coerce-unsized
only.