@@ -2249,7 +2249,9 @@ private:
22492249 // Allocate a buffer of __capacity size with __alloc and return it
22502250 _LIBCPP_HIDE_FROM_ABI static _LIBCPP_CONSTEXPR_SINCE_CXX20 __long
22512251 __allocate_long_buffer (_Allocator& __alloc, size_type __capacity) {
2252- auto __buffer = std::__allocate_at_least (__alloc, __recommend (__capacity) + 1 );
2252+ _LIBCPP_ASSERT_INTERNAL (!__fits_in_sso (__capacity),
2253+ " Trying to allocate long buffer for a capacity what would fit into the small buffer" );
2254+ auto __buffer = std::__allocate_at_least (__alloc, __align_allocation_size (__capacity));
22532255
22542256 if (__libcpp_is_constant_evaluated ()) {
22552257 for (size_type __i = 0 ; __i != __buffer.count ; ++__i)
@@ -2347,16 +2349,17 @@ private:
23472349 return (__s + (__a - 1 )) & ~(__a - 1 );
23482350 }
23492351 enum { __alignment = 8 };
2350- static _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 size_type __recommend (size_type __s) _NOEXCEPT {
2351- if (__s < __min_cap) {
2352- return static_cast <size_type>(__min_cap) - 1 ;
2353- }
2352+
2353+ _LIBCPP_HIDE_FROM_ABI static _LIBCPP_CONSTEXPR_SINCE_CXX20 size_type
2354+ __align_allocation_size (size_type __size) _NOEXCEPT {
2355+ _LIBCPP_ASSERT_INTERNAL (
2356+ !__fits_in_sso (__size), " Trying to align allocation of a size which would fit into the SSO" );
23542357 const size_type __boundary = sizeof (value_type) < __alignment ? __alignment / sizeof (value_type) : __endian_factor;
2355- size_type __guess = __align_it<__boundary>(__s + 1 ) - 1 ;
2356- if (__guess == __min_cap)
2358+ size_type __guess = __align_it<__boundary>(__size + 1 );
2359+ if (__guess == __min_cap + 1 )
23572360 __guess += __endian_factor;
23582361
2359- _LIBCPP_ASSERT_INTERNAL (__guess >= __s , " recommendation is below the requested size" );
2362+ _LIBCPP_ASSERT_INTERNAL (__guess >= __size , " aligned allocation size is below the requested size" );
23602363 return __guess;
23612364 }
23622365
@@ -2694,8 +2697,7 @@ _LIBCPP_CONSTEXPR_SINCE_CXX20 void basic_string<_CharT, _Traits, _Allocator>::__
26942697 if (__delta_cap > __ms - __old_cap)
26952698 __throw_length_error ();
26962699 pointer __old_p = __get_pointer ();
2697- size_type __cap =
2698- __old_cap < __ms / 2 - __alignment ? __recommend (std::max (__old_cap + __delta_cap, 2 * __old_cap)) : __ms;
2700+ size_type __cap = __old_cap < __ms / 2 - __alignment ? std::max (__old_cap + __delta_cap, 2 * __old_cap) : __ms;
26992701 __annotate_delete ();
27002702 auto __guard = std::__make_scope_guard (__annotate_new_size (*this ));
27012703 __long __buffer = __allocate_long_buffer (__alloc_, __cap);
@@ -2732,8 +2734,7 @@ _LIBCPP_DEPRECATED_("use __grow_by_without_replace") basic_string<_CharT, _Trait
27322734 if (__delta_cap > __ms - __old_cap)
27332735 this ->__throw_length_error ();
27342736 pointer __old_p = __get_pointer ();
2735- size_type __cap =
2736- __old_cap < __ms / 2 - __alignment ? __recommend (std::max (__old_cap + __delta_cap, 2 * __old_cap)) : __ms;
2737+ size_type __cap = __old_cap < __ms / 2 - __alignment ? std::max (__old_cap + __delta_cap, 2 * __old_cap) : __ms;
27372738 __long __buffer = __allocate_long_buffer (__alloc_, __cap);
27382739 if (__n_copy != 0 )
27392740 traits_type::copy (std::__to_address (__buffer.__data_ ), std::__to_address (__old_p), __n_copy);
@@ -3399,25 +3400,25 @@ _LIBCPP_CONSTEXPR_SINCE_CXX20 void basic_string<_CharT, _Traits, _Allocator>::re
33993400
34003401template <class _CharT , class _Traits , class _Allocator >
34013402inline _LIBCPP_CONSTEXPR_SINCE_CXX20 void basic_string<_CharT, _Traits, _Allocator>::shrink_to_fit() _NOEXCEPT {
3402- size_type __target_capacity = __recommend (size ());
3403- if (__target_capacity == capacity ())
3403+ if (!__is_long ())
34043404 return ;
34053405
3406- _LIBCPP_ASSERT_INTERNAL (__is_long (), " Trying to shrink small string" );
3407-
3408- // We're a long string and we're shrinking into the small buffer.
34093406 const auto __ptr = __get_long_pointer ();
34103407 const auto __size = __get_long_size ();
34113408 const auto __cap = __get_long_cap ();
34123409
3413- if (__fits_in_sso (__target_capacity)) {
3410+ // We're a long string and we're shrinking into the small buffer.
3411+ if (__fits_in_sso (__size)) {
34143412 __annotation_guard __g (*this );
34153413 __set_short_size (__size);
34163414 traits_type::copy (std::__to_address (__get_short_pointer ()), std::__to_address (__ptr), __size + 1 );
34173415 __alloc_traits::deallocate (__alloc_, __ptr, __cap);
34183416 return ;
34193417 }
34203418
3419+ if (__align_allocation_size (__size) == __cap)
3420+ return ;
3421+
34213422# if _LIBCPP_HAS_EXCEPTIONS
34223423 try {
34233424# endif // _LIBCPP_HAS_EXCEPTIONS
0 commit comments