Skip to content

Commit

Permalink
Add ensure_capacity and rename min to len
Browse files Browse the repository at this point in the history
  • Loading branch information
Zoxc committed Apr 1, 2019
1 parent e8b3aea commit 59ff059
Showing 1 changed file with 26 additions and 15 deletions.
41 changes: 26 additions & 15 deletions src/libarena/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -161,14 +161,21 @@ impl<T> TypedArena<T> {
available_capacity_bytes >= at_least_bytes
}

/// Ensures there's enough space in the current chunk to fit `len` objects.
#[inline]
fn ensure_capacity(&self, len: usize) {
if !self.can_allocate(len) {
self.grow(len);
debug_assert!(self.can_allocate(len));
}
}

#[inline]
unsafe fn alloc_raw_slice(&self, len: usize) -> *mut T {
assert!(mem::size_of::<T>() != 0);
assert!(len != 0);

if !self.can_allocate(len) {
self.grow(len);
}
self.ensure_capacity(len);

let start_ptr = self.ptr.get();
self.ptr.set(start_ptr.add(len));
Expand Down Expand Up @@ -203,19 +210,20 @@ impl<T> TypedArena<T> {

match size_hint {
(min, Some(max)) if min == max => {
if min == 0 {
// We know the exact number of elements the iterator will produce here
let len = min;

if len == 0 {
return &mut [];
}

if !self.can_allocate(min) {
self.grow(min);
}
self.ensure_capacity(len);

let slice = self.ptr.get();

unsafe {
let mut ptr = self.ptr.get();
for _ in 0..min {
for _ in 0..len {
// Write into uninitialized memory.
ptr::write(ptr, iter.next().unwrap());
// Advance the pointer.
Expand All @@ -224,7 +232,7 @@ impl<T> TypedArena<T> {
// we destroy the correct amount
self.ptr.set(ptr);
}
slice::from_raw_parts_mut(slice, min)
slice::from_raw_parts_mut(slice, len)
}
}
_ => {
Expand All @@ -239,7 +247,7 @@ impl<T> TypedArena<T> {
let len = vec.len();
let start_ptr = self.alloc_raw_slice(len);
vec.as_ptr().copy_to_nonoverlapping(start_ptr, len);
vev.set_len(0);
vec.set_len(0);
slice::from_raw_parts_mut(start_ptr, len)
}
})
Expand Down Expand Up @@ -488,16 +496,19 @@ impl DroplessArena {

match size_hint {
(min, Some(max)) if min == max => {
if min == 0 {
// We know the exact number of elements the iterator will produce here
let len = min;

if len == 0 {
return &mut []
}
let size = min.checked_mul(mem::size_of::<T>()).unwrap();
let size = len.checked_mul(mem::size_of::<T>()).unwrap();
let mem = self.alloc_raw(size, mem::align_of::<T>()) as *mut _ as *mut T;
unsafe {
for i in 0..min {
for i in 0..len {
ptr::write(mem.offset(i as isize), iter.next().unwrap())
}
slice::from_raw_parts_mut(mem, min)
slice::from_raw_parts_mut(mem, len)
}
}
(_, _) => {
Expand All @@ -515,7 +526,7 @@ impl DroplessArena {
mem::align_of::<T>()
) as *mut _ as *mut T;
vec.as_ptr().copy_to_nonoverlapping(start_ptr, len);
vev.set_len(0);
vec.set_len(0);
slice::from_raw_parts_mut(start_ptr, len)
}
})
Expand Down

0 comments on commit 59ff059

Please sign in to comment.