Skip to content

Commit 2f648bc

Browse files
committed
add support for zero length HeaderVec
Having a HeaderVec being zero length is mostly useless because it has to reallocated instanly when anything becomes pushed. This clearly should be avoided! Nevertheless supporting zero length takes out a corner-case and a potential panic and removes the burden for users explicitly ensuring zero length HeaderVecs don't happen in practice. Generally improving software reliability.
1 parent caafac5 commit 2f648bc

File tree

2 files changed

+15
-4
lines changed

2 files changed

+15
-4
lines changed

src/lib.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,6 @@ impl<H, T> HeaderVec<H, T> {
6161
}
6262

6363
pub fn with_capacity(capacity: usize, head: H) -> Self {
64-
assert!(capacity > 0, "HeaderVec capacity cannot be 0");
6564
// Allocate the initial memory, which is uninitialized.
6665
let layout = Self::layout(capacity);
6766
let ptr = unsafe { alloc::alloc::alloc(layout) } as *mut AlignedHeader<H, T>;
@@ -276,8 +275,6 @@ impl<H, T> HeaderVec<H, T> {
276275
"requested capacity is less than current length"
277276
);
278277
let old_capacity = self.capacity();
279-
debug_assert_ne!(old_capacity, 0, "capacity of 0 not yet supported");
280-
debug_assert_ne!(requested_capacity, 0, "capacity of 0 not yet supported");
281278

282279
let new_capacity = if requested_capacity > old_capacity {
283280
if exact {
@@ -286,11 +283,14 @@ impl<H, T> HeaderVec<H, T> {
286283
} else if requested_capacity <= old_capacity * 2 {
287284
// doubling the capacity is sufficient
288285
old_capacity * 2
289-
} else {
286+
} else if old_capacity > 0 {
290287
// requested more than twice as much space, reserve the next multiple of
291288
// old_capacity that is greater than the requested capacity. This gives headroom
292289
// for new inserts while not doubling the memory requirement with bulk requests
293290
(requested_capacity / old_capacity + 1).saturating_mul(old_capacity)
291+
} else {
292+
// special case when we start at capacity 0
293+
requested_capacity
294294
}
295295
} else if exact {
296296
// exact shrinking

tests/simple.rs

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,17 @@ fn test_sizeof() {
2525
);
2626
}
2727

28+
#[test]
29+
fn test_empty() {
30+
let mut v_empty = HeaderVec::with_capacity(0, TestA { a: 4, b: !0, c: 66 });
31+
32+
assert_eq!(0, v_empty.len());
33+
assert_eq!(0, v_empty.capacity());
34+
assert_eq!(0, v_empty.as_slice().len());
35+
36+
v_empty.extend_from_slice("the quick brown fox jumps over the lazy dog".as_bytes());
37+
}
38+
2839
#[test]
2940
fn test_head_array() {
3041
let mut v_orig = HeaderVec::new(TestA { a: 4, b: !0, c: 66 });

0 commit comments

Comments
 (0)