@@ -20,7 +20,6 @@ struct FragmentData {
20
20
pub struct ConcurrentSplitVec < T , G : GrowthWithConstantTimeAccess = Doubling > {
21
21
growth : G ,
22
22
data : Vec < UnsafeCell < * mut T > > ,
23
- num_fragments : AtomicUsize ,
24
23
capacity : AtomicUsize ,
25
24
maximum_capacity : usize ,
26
25
max_num_fragments : usize ,
@@ -30,7 +29,7 @@ pub struct ConcurrentSplitVec<T, G: GrowthWithConstantTimeAccess = Doubling> {
30
29
impl < T , G : GrowthWithConstantTimeAccess > Drop for ConcurrentSplitVec < T , G > {
31
30
fn drop ( & mut self ) {
32
31
let mut take_fragment = |_fragment : Fragment < T > | { } ;
33
- unsafe { self . into_fragments ( self . pinned_vec_len , & mut take_fragment) } ;
32
+ unsafe { self . process_into_fragments ( self . pinned_vec_len , & mut take_fragment) } ;
34
33
self . zero ( ) ;
35
34
}
36
35
}
@@ -51,15 +50,15 @@ impl<T, G: GrowthWithConstantTimeAccess> ConcurrentSplitVec<T, G> {
51
50
}
52
51
53
52
fn layout ( len : usize ) -> std:: alloc:: Layout {
54
- std:: alloc:: Layout :: array :: < T > ( len) . unwrap ( )
53
+ std:: alloc:: Layout :: array :: < T > ( len) . expect ( "len must not overflow" )
55
54
}
56
55
57
56
unsafe fn to_fragment ( & self , data : FragmentData ) -> Fragment < T > {
58
57
let ptr = * self . data [ data. f ] . get ( ) ;
59
58
fragment_from_raw ( ptr, data. len , data. capacity )
60
59
}
61
60
62
- unsafe fn into_fragments < F > ( & mut self , len : usize , take_fragment : & mut F )
61
+ unsafe fn process_into_fragments < F > ( & mut self , len : usize , take_fragment : & mut F )
63
62
where
64
63
F : FnMut ( Fragment < T > ) ,
65
64
{
@@ -116,12 +115,23 @@ impl<T, G: GrowthWithConstantTimeAccess> ConcurrentSplitVec<T, G> {
116
115
}
117
116
118
117
fn zero ( & mut self ) {
119
- self . num_fragments = 0 . into ( ) ;
120
118
self . capacity = 0 . into ( ) ;
121
119
self . maximum_capacity = 0 ;
122
120
self . max_num_fragments = 0 ;
123
121
self . pinned_vec_len = 0 ;
124
122
}
123
+
124
+ fn num_fragments_for_capacity ( & self , capacity : usize ) -> usize {
125
+ match capacity {
126
+ 0 => 0 ,
127
+ _ => {
128
+ self . growth
129
+ . get_fragment_and_inner_indices_unchecked ( capacity - 1 )
130
+ . 0
131
+ + 1
132
+ }
133
+ }
134
+ }
125
135
}
126
136
127
137
impl < T , G : GrowthWithConstantTimeAccess > From < SplitVec < T , G > > for ConcurrentSplitVec < T , G > {
@@ -144,7 +154,7 @@ impl<T, G: GrowthWithConstantTimeAccess> From<SplitVec<T, G>> for ConcurrentSpli
144
154
total_len += len;
145
155
maximum_capacity += cap;
146
156
147
- data. push ( UnsafeCell :: new ( p as * mut T ) ) ;
157
+ data. push ( UnsafeCell :: new ( p) ) ;
148
158
}
149
159
assert_eq ! ( total_len, pinned_vec_len) ;
150
160
let capacity = maximum_capacity;
@@ -159,7 +169,6 @@ impl<T, G: GrowthWithConstantTimeAccess> From<SplitVec<T, G>> for ConcurrentSpli
159
169
Self {
160
170
growth,
161
171
data,
162
- num_fragments : num_fragments. into ( ) ,
163
172
capacity : capacity. into ( ) ,
164
173
maximum_capacity,
165
174
max_num_fragments,
@@ -174,7 +183,7 @@ impl<T, G: GrowthWithConstantTimeAccess> ConcurrentPinnedVec<T> for ConcurrentSp
174
183
unsafe fn into_inner ( mut self , len : usize ) -> Self :: P {
175
184
let mut fragments = Vec :: with_capacity ( self . max_num_fragments ) ;
176
185
let mut take_fragment = |fragment| fragments. push ( fragment) ;
177
- self . into_fragments ( len, & mut take_fragment) ;
186
+ self . process_into_fragments ( len, & mut take_fragment) ;
178
187
179
188
self . zero ( ) ;
180
189
SplitVec :: from_raw_parts ( len, fragments, self . growth . clone ( ) )
@@ -355,8 +364,7 @@ impl<T, G: GrowthWithConstantTimeAccess> ConcurrentPinnedVec<T> for ConcurrentSp
355
364
match new_capacity <= capacity {
356
365
true => Ok ( capacity) ,
357
366
false => {
358
- let mut f = self . num_fragments . load ( Ordering :: Relaxed ) ;
359
-
367
+ let mut f = self . num_fragments_for_capacity ( capacity) ;
360
368
let mut current_capacity = capacity;
361
369
362
370
while new_capacity > current_capacity {
@@ -369,7 +377,6 @@ impl<T, G: GrowthWithConstantTimeAccess> ConcurrentPinnedVec<T> for ConcurrentSp
369
377
current_capacity += new_fragment_capacity;
370
378
}
371
379
372
- self . num_fragments . store ( f, Ordering :: SeqCst ) ;
373
380
self . capacity . store ( current_capacity, Ordering :: Release ) ;
374
381
375
382
Ok ( current_capacity)
@@ -389,7 +396,7 @@ impl<T, G: GrowthWithConstantTimeAccess> ConcurrentPinnedVec<T> for ConcurrentSp
389
396
match new_capacity <= capacity {
390
397
true => Ok ( capacity) ,
391
398
false => {
392
- let mut f = self . num_fragments . load ( Ordering :: Relaxed ) ;
399
+ let mut f = self . num_fragments_for_capacity ( capacity ) ;
393
400
394
401
let mut current_capacity = capacity;
395
402
@@ -408,7 +415,6 @@ impl<T, G: GrowthWithConstantTimeAccess> ConcurrentPinnedVec<T> for ConcurrentSp
408
415
current_capacity += new_fragment_capacity;
409
416
}
410
417
411
- self . num_fragments . store ( f, Ordering :: SeqCst ) ;
412
418
self . capacity . store ( current_capacity, Ordering :: Release ) ;
413
419
414
420
Ok ( current_capacity)
@@ -468,13 +474,25 @@ impl<T, G: GrowthWithConstantTimeAccess> ConcurrentPinnedVec<T> for ConcurrentSp
468
474
self . maximum_capacity
469
475
}
470
476
477
+ unsafe fn reserve_maximum_concurrent_capacity_fill_with < F > (
478
+ & mut self ,
479
+ current_len : usize ,
480
+ new_maximum_capacity : usize ,
481
+ _fill_with : F ,
482
+ ) -> usize
483
+ where
484
+ F : Fn ( ) -> T ,
485
+ {
486
+ self . reserve_maximum_concurrent_capacity ( current_len, new_maximum_capacity)
487
+ }
488
+
471
489
unsafe fn set_pinned_vec_len ( & mut self , len : usize ) {
472
490
self . pinned_vec_len = len;
473
491
}
474
492
475
493
unsafe fn clear ( & mut self , len : usize ) {
476
494
let mut take_fragment = |_fragment : Fragment < T > | { } ;
477
- unsafe { self . into_fragments ( len, & mut take_fragment) } ;
495
+ unsafe { self . process_into_fragments ( len, & mut take_fragment) } ;
478
496
self . zero ( ) ;
479
497
480
498
let max_num_fragments = self . data . len ( ) ;
0 commit comments