Skip to content

Commit 928e2e2

Browse files
committed
Auto merge of #23670 - cmr:vec-push-slowpath, r=pcwalton
Makes Vec::push considerably smaller: 25 instructions, rather than 42, on x86_64.
2 parents 593db00 + 0e838f7 commit 928e2e2

File tree

1 file changed

+16
-9
lines changed

1 file changed

+16
-9
lines changed

src/libcollections/vec.rs

+16-9
Original file line numberDiff line numberDiff line change
@@ -646,23 +646,30 @@ impl<T> Vec<T> {
646646
#[inline]
647647
#[stable(feature = "rust1", since = "1.0.0")]
648648
pub fn push(&mut self, value: T) {
649+
#[cold]
650+
#[inline(never)]
651+
fn resize<T>(vec: &mut Vec<T>) {
652+
let old_size = vec.cap * mem::size_of::<T>();
653+
let size = max(old_size, 2 * mem::size_of::<T>()) * 2;
654+
if old_size > size { panic!("capacity overflow") }
655+
unsafe {
656+
let ptr = alloc_or_realloc(*vec.ptr, old_size, size);
657+
if ptr.is_null() { ::alloc::oom() }
658+
vec.ptr = Unique::new(ptr);
659+
}
660+
vec.cap = max(vec.cap, 2) * 2;
661+
}
662+
649663
if mem::size_of::<T>() == 0 {
650664
// zero-size types consume no memory, so we can't rely on the
651665
// address space running out
652666
self.len = self.len.checked_add(1).expect("length overflow");
653667
unsafe { mem::forget(value); }
654668
return
655669
}
670+
656671
if self.len == self.cap {
657-
let old_size = self.cap * mem::size_of::<T>();
658-
let size = max(old_size, 2 * mem::size_of::<T>()) * 2;
659-
if old_size > size { panic!("capacity overflow") }
660-
unsafe {
661-
let ptr = alloc_or_realloc(*self.ptr, old_size, size);
662-
if ptr.is_null() { ::alloc::oom() }
663-
self.ptr = Unique::new(ptr);
664-
}
665-
self.cap = max(self.cap, 2) * 2;
672+
resize(self);
666673
}
667674

668675
unsafe {

0 commit comments

Comments
 (0)