@@ -45,10 +45,6 @@ extern crate serde;
45
45
extern crate unreachable;
46
46
use unreachable:: UncheckedOptionExt ;
47
47
48
- #[ cfg( not( feature = "union" ) ) ]
49
- #[ macro_use]
50
- extern crate debug_unreachable;
51
-
52
48
#[ cfg( not( feature = "std" ) ) ]
53
49
mod std {
54
50
pub use core:: * ;
@@ -123,6 +119,19 @@ macro_rules! smallvec {
123
119
} ) ;
124
120
}
125
121
122
+ /// `panic!()` in debug builds, optimization hint in release.
123
+ #[ cfg( not( feature = "union" ) ) ]
124
+ macro_rules! debug_unreachable {
125
+ ( ) => { debug_unreachable!( "entered unreachable code" ) } ;
126
+ ( $e: expr) => {
127
+ if cfg!( not( debug_assertions) ) {
128
+ unreachable:: unreachable( ) ;
129
+ } else {
130
+ panic!( $e) ;
131
+ }
132
+ }
133
+ }
134
+
126
135
/// Common operations implemented by both `Vec` and `SmallVec`.
127
136
///
128
137
/// This can be used to write generic code that works with both `Vec` and `SmallVec`.
@@ -370,6 +379,9 @@ unsafe impl<A: Array + Sync> Sync for SmallVecData<A> {}
370
379
/// assert!(v.spilled());
371
380
/// ```
372
381
pub struct SmallVec < A : Array > {
382
+ // The capacity field is used to determine which of the storage variants is active:
383
+ // If capacity <= A::size() then the inline variant is used and capacity holds the current length of the vector (number of elements actually in use).
384
+ // If capacity > A::size() then the heap variant is used and capacity holds the size of the memory allocation.
373
385
capacity : usize ,
374
386
data : SmallVecData < A > ,
375
387
}
@@ -406,8 +418,9 @@ impl<A: Array> SmallVec<A> {
406
418
v
407
419
}
408
420
409
- /// Construct a new `SmallVec` from a `Vec<A::Item>` without copying
410
- /// elements.
421
+ /// Construct a new `SmallVec` from a `Vec<A::Item>`.
422
+ ///
423
+ /// Elements will be copied to the inline buffer if vec.capacity() <= A::size().
411
424
///
412
425
/// ```rust
413
426
/// use smallvec::SmallVec;
@@ -495,6 +508,8 @@ impl<A: Array> SmallVec<A> {
495
508
self . triple ( ) . 2
496
509
}
497
510
511
+ /// Returns a tuple with (data ptr, len, capacity)
512
+ /// Useful to get all SmallVec properties with a single check of the current storage variant.
498
513
#[ inline]
499
514
fn triple ( & self ) -> ( * const A :: Item , usize , usize ) {
500
515
unsafe {
@@ -507,6 +522,7 @@ impl<A: Array> SmallVec<A> {
507
522
}
508
523
}
509
524
525
+ /// Returns a tuple with (data ptr, len ptr, capacity)
510
526
#[ inline]
511
527
fn triple_mut ( & mut self ) -> ( * mut A :: Item , & mut usize , usize ) {
512
528
unsafe {
@@ -666,7 +682,7 @@ impl<A: Array> SmallVec<A> {
666
682
while len < * len_ptr {
667
683
let last_index = * len_ptr - 1 ;
668
684
* len_ptr = last_index;
669
- ptr:: read ( ptr. offset ( last_index as isize ) ) ;
685
+ ptr:: drop_in_place ( ptr. offset ( last_index as isize ) ) ;
670
686
}
671
687
}
672
688
}
@@ -1168,9 +1184,9 @@ impl<A: Array> Drop for SmallVec<A> {
1168
1184
let ( ptr, len) = self . data . heap ( ) ;
1169
1185
Vec :: from_raw_parts ( ptr, len, self . capacity ) ;
1170
1186
} else {
1171
- let ptr = self . as_ptr ( ) ;
1187
+ let ptr = self . as_mut_ptr ( ) ;
1172
1188
for i in 0 ..self . len ( ) {
1173
- ptr:: read ( ptr. offset ( i as isize ) ) ;
1189
+ ptr:: drop_in_place ( ptr. offset ( i as isize ) ) ;
1174
1190
}
1175
1191
}
1176
1192
}
0 commit comments