@@ -668,8 +668,7 @@ impl<A: Allocator> RawVecInner<A> {
668668/// - `elem_layout` must be valid for `self`, i.e. it must be the same `elem_layout` used to 
669669///   initially construct `self` 
670670/// - `elem_layout`'s size must be a multiple of its alignment 
671- /// - The sum of `len` and `additional` must be greater than or equal to 
672- ///   `self.capacity(elem_layout.size())` 
671+ /// - The sum of `len` and `additional` must be greater than the current capacity 
673672unsafe  fn  grow_amortized ( 
674673        & mut  self , 
675674        len :  usize , 
@@ -693,16 +692,12 @@ impl<A: Allocator> RawVecInner<A> {
693692        let  cap = cmp:: max ( self . cap . as_inner ( )  *  2 ,  required_cap) ; 
694693        let  cap = cmp:: max ( min_non_zero_cap ( elem_layout. size ( ) ) ,  cap) ; 
695694
696-         let  new_layout = layout_array ( cap,  elem_layout) ?; 
697- 
698695        // SAFETY: 
699-         // - For the `current_memory` call: Precondition passed to caller 
700-         // - For the `finish_grow` call: Precondition passed to caller 
701-         //   + `current_memory` does the right thing 
702-         let  ptr =
703-             unsafe  {  finish_grow ( new_layout,  self . current_memory ( elem_layout) ,  & mut  self . alloc ) ? } ; 
696+         // - cap >= len + additional 
697+         // - other preconditions passed to caller 
698+         let  ptr = unsafe  {  self . finish_grow ( cap,  elem_layout) ? } ; 
704699
705-         // SAFETY: layout_array  would have resulted in a capacity overflow  if we tried to allocate more than ` isize::MAX` items  
700+         // SAFETY: `finish_grow`  would have failed  if `cap >  isize::MAX` 
706701        unsafe  {  self . set_ptr_and_cap ( ptr,  cap)  } ; 
707702        Ok ( ( ) ) 
708703    } 
@@ -711,8 +706,7 @@ impl<A: Allocator> RawVecInner<A> {
711706/// - `elem_layout` must be valid for `self`, i.e. it must be the same `elem_layout` used to 
712707///   initially construct `self` 
713708/// - `elem_layout`'s size must be a multiple of its alignment 
714- /// - The sum of `len` and `additional` must be greater than or equal to 
715- ///   `self.capacity(elem_layout.size())` 
709+ /// - The sum of `len` and `additional` must be greater than the current capacity 
716710unsafe  fn  grow_exact ( 
717711        & mut  self , 
718712        len :  usize , 
@@ -726,21 +720,44 @@ impl<A: Allocator> RawVecInner<A> {
726720        } 
727721
728722        let  cap = len. checked_add ( additional) . ok_or ( CapacityOverflow ) ?; 
729-         let  new_layout = layout_array ( cap,  elem_layout) ?; 
730723
731-         // SAFETY: 
732-         // - For the `current_memory` call: Precondition passed to caller 
733-         // - For the `finish_grow` call: Precondition passed to caller 
734-         //   + `current_memory` does the right thing 
735-         let  ptr =
736-             unsafe  {  finish_grow ( new_layout,  self . current_memory ( elem_layout) ,  & mut  self . alloc ) ? } ; 
737-         // SAFETY: layout_array would have resulted in a capacity overflow if we tried to allocate more than `isize::MAX` items 
738-         unsafe  { 
739-             self . set_ptr_and_cap ( ptr,  cap) ; 
740-         } 
724+         // SAFETY: preconditions passed to caller 
725+         let  ptr = unsafe  {  self . finish_grow ( cap,  elem_layout) ? } ; 
726+ 
727+         // SAFETY: `finish_grow` would have failed if `cap > isize::MAX` 
728+         unsafe  {  self . set_ptr_and_cap ( ptr,  cap)  } ; 
741729        Ok ( ( ) ) 
742730    } 
743731
732+     /// # Safety 
733+ /// - `elem_layout` must be valid for `self`, i.e. it must be the same `elem_layout` used to 
734+ ///   initially construct `self` 
735+ /// - `elem_layout`'s size must be a multiple of its alignment 
736+ /// - `cap` must be greater than the current capacity 
737+ // not marked inline(never) since we want optimizers to be able to observe the specifics of this 
738+     // function, see tests/codegen-llvm/vec-reserve-extend.rs. 
739+     #[ cold]  
740+     unsafe  fn  finish_grow ( 
741+         & self , 
742+         cap :  usize , 
743+         elem_layout :  Layout , 
744+     )  -> Result < NonNull < [ u8 ] > ,  TryReserveError >  { 
745+         let  new_layout = layout_array ( cap,  elem_layout) ?; 
746+ 
747+         let  memory = if  let  Some ( ( ptr,  old_layout) )  = unsafe  {  self . current_memory ( elem_layout)  }  { 
748+             debug_assert_eq ! ( old_layout. align( ) ,  new_layout. align( ) ) ; 
749+             unsafe  { 
750+                 // The allocator checks for alignment equality 
751+                 hint:: assert_unchecked ( old_layout. align ( )  == new_layout. align ( ) ) ; 
752+                 self . alloc . grow ( ptr,  old_layout,  new_layout) 
753+             } 
754+         }  else  { 
755+             self . alloc . allocate ( new_layout) 
756+         } ; 
757+ 
758+         memory. map_err ( |_| AllocError  {  layout :  new_layout,  non_exhaustive :  ( )  } . into ( ) ) 
759+     } 
760+ 
744761    /// # Safety 
745762/// - `elem_layout` must be valid for `self`, i.e. it must be the same `elem_layout` used to 
746763///   initially construct `self` 
@@ -820,38 +837,6 @@ impl<A: Allocator> RawVecInner<A> {
820837    } 
821838} 
822839
823- /// # Safety 
824- /// If `current_memory` matches `Some((ptr, old_layout))`: 
825- /// - `ptr` must denote a block of memory *currently allocated* via `alloc` 
826- /// - `old_layout` must *fit* that block of memory 
827- /// - `new_layout` must have the same alignment as `old_layout` 
828- /// - `new_layout.size()` must be greater than or equal to `old_layout.size()` 
829- /// If `current_memory` is `None`, this function is safe. 
830- // not marked inline(never) since we want optimizers to be able to observe the specifics of this 
831- // function, see tests/codegen-llvm/vec-reserve-extend.rs. 
832- #[ cold]  
833- unsafe  fn  finish_grow < A > ( 
834-     new_layout :  Layout , 
835-     current_memory :  Option < ( NonNull < u8 > ,  Layout ) > , 
836-     alloc :  & mut  A , 
837- )  -> Result < NonNull < [ u8 ] > ,  TryReserveError > 
838- where 
839-     A :  Allocator , 
840- { 
841-     let  memory = if  let  Some ( ( ptr,  old_layout) )  = current_memory { 
842-         debug_assert_eq ! ( old_layout. align( ) ,  new_layout. align( ) ) ; 
843-         unsafe  { 
844-             // The allocator checks for alignment equality 
845-             hint:: assert_unchecked ( old_layout. align ( )  == new_layout. align ( ) ) ; 
846-             alloc. grow ( ptr,  old_layout,  new_layout) 
847-         } 
848-     }  else  { 
849-         alloc. allocate ( new_layout) 
850-     } ; 
851- 
852-     memory. map_err ( |_| AllocError  {  layout :  new_layout,  non_exhaustive :  ( )  } . into ( ) ) 
853- } 
854- 
855840// Central function for reserve error handling. 
856841#[ cfg( not( no_global_oom_handling) ) ]  
857842#[ cold]  
0 commit comments