@@ -2226,9 +2226,9 @@ where
22262226 return SpecFromNested :: from_iter ( iterator) ;
22272227 }
22282228
2229- let ( src_buf, src_end) = {
2229+ let ( src_buf, src_end, cap ) = {
22302230 let inner = unsafe { iterator. as_inner ( ) . as_into_iter ( ) } ;
2231- ( inner. buf . as_ptr ( ) , inner. end )
2231+ ( inner. buf . as_ptr ( ) , inner. end , inner . cap )
22322232 } ;
22332233 let dst = src_buf;
22342234
@@ -2278,23 +2278,15 @@ where
22782278 debug_assert_eq ! ( src_buf, src. buf. as_ptr( ) ) ;
22792279 debug_assert ! ( dst as * const _ <= src. ptr, "InPlaceIterable contract violation" ) ;
22802280
2281- if mem:: needs_drop :: < T > ( ) {
2282- // drop tail if iterator was only partially exhausted
2283- unsafe {
2284- ptr:: drop_in_place ( src. as_mut_slice ( ) ) ;
2285- }
2286- }
2281+ // drop any remaining values at the tail of the source
2282+ src. drop_in_place ( ) ;
2283+ // but prevent drop of the allocation itself once IntoIter goes out of scope
2284+ src. forget_in_place ( ) ;
22872285
22882286 let vec = unsafe {
22892287 let len = dst. offset_from ( src_buf) as usize ;
2290- Vec :: from_raw_parts ( src . buf . as_ptr ( ) , len, src . cap )
2288+ Vec :: from_raw_parts ( src_buf , len, cap)
22912289 } ;
2292- // prevent drop of the underlying storage by turning the IntoIter into
2293- // the equivalent of Vec::new().into_iter()
2294- src. cap = 0 ;
2295- src. buf = unsafe { NonNull :: new_unchecked ( RawVec :: NEW . ptr ( ) ) } ;
2296- src. ptr = src. buf . as_ptr ( ) ;
2297- src. end = src. buf . as_ptr ( ) ;
22982290
22992291 vec
23002292 }
@@ -2839,6 +2831,24 @@ impl<T> IntoIter<T> {
28392831 fn as_raw_mut_slice ( & mut self ) -> * mut [ T ] {
28402832 ptr:: slice_from_raw_parts_mut ( self . ptr as * mut T , self . len ( ) )
28412833 }
2834+
2835+ fn drop_in_place ( & mut self ) {
2836+ if mem:: needs_drop :: < T > ( ) {
2837+ unsafe {
2838+ ptr:: drop_in_place ( self . as_mut_slice ( ) ) ;
2839+ }
2840+ }
2841+ self . ptr = self . end ;
2842+ }
2843+
2844+ /// Relinquishes the backing allocation, equivalent to
2845+ /// `ptr::write(&mut self, Vec::new().into_iter())`
2846+ fn forget_in_place ( & mut self ) {
2847+ self . cap = 0 ;
2848+ self . buf = unsafe { NonNull :: new_unchecked ( RawVec :: NEW . ptr ( ) ) } ;
2849+ self . ptr = self . buf . as_ptr ( ) ;
2850+ self . end = self . buf . as_ptr ( ) ;
2851+ }
28422852}
28432853
28442854#[ stable( feature = "vec_intoiter_as_ref" , since = "1.46.0" ) ]
0 commit comments