diff --git a/libcxx/include/CMakeLists.txt b/libcxx/include/CMakeLists.txt --- a/libcxx/include/CMakeLists.txt +++ b/libcxx/include/CMakeLists.txt @@ -496,6 +496,7 @@ __memory/temp_value.h __memory/temporary_buffer.h __memory/uninitialized_algorithms.h + __memory/uninitialized_buffer.h __memory/unique_ptr.h __memory/uses_allocator.h __memory/uses_allocator_construction.h diff --git a/libcxx/include/__algorithm/inplace_merge.h b/libcxx/include/__algorithm/inplace_merge.h --- a/libcxx/include/__algorithm/inplace_merge.h +++ b/libcxx/include/__algorithm/inplace_merge.h @@ -24,7 +24,7 @@ #include <__iterator/iterator_traits.h> #include <__iterator/reverse_iterator.h> #include <__memory/destruct_n.h> -#include <__memory/temporary_buffer.h> +#include <__memory/uninitialized_buffer.h> #include <__memory/unique_ptr.h> #include <__utility/pair.h> #include @@ -225,13 +225,9 @@ difference_type __len1 = _IterOps<_AlgPolicy>::distance(__first, __middle); difference_type __len2 = _IterOps<_AlgPolicy>::distance(__middle, __last); difference_type __buf_size = _VSTD::min(__len1, __len2); -// TODO: Remove the use of std::get_temporary_buffer -_LIBCPP_SUPPRESS_DEPRECATED_PUSH - pair __buf = _VSTD::get_temporary_buffer(__buf_size); -_LIBCPP_SUPPRESS_DEPRECATED_POP - unique_ptr __h(__buf.first); + __uninitialized_buffer __buf(__buf_size); return std::__inplace_merge<_AlgPolicy>( - std::move(__first), std::move(__middle), std::move(__last), __comp, __len1, __len2, __buf.first, __buf.second); + std::move(__first), std::move(__middle), std::move(__last), __comp, __len1, __len2, __buf.get(), __buf_size); } template diff --git a/libcxx/include/__algorithm/stable_partition.h b/libcxx/include/__algorithm/stable_partition.h --- a/libcxx/include/__algorithm/stable_partition.h +++ b/libcxx/include/__algorithm/stable_partition.h @@ -17,6 +17,7 @@ #include <__iterator/iterator_traits.h> #include <__memory/destruct_n.h> #include <__memory/temporary_buffer.h> +#include <__memory/uninitialized_buffer.h> #include <__memory/unique_ptr.h> #include <__utility/move.h> #include <__utility/pair.h> @@ -137,18 +138,25 @@ typedef typename iterator_traits<_ForwardIterator>::difference_type difference_type; typedef typename iterator_traits<_ForwardIterator>::value_type value_type; difference_type __len = _IterOps<_AlgPolicy>::distance(__first, __last); - pair __p(0, 0); - unique_ptr __h; if (__len >= __alloc_limit) { -// TODO: Remove the use of std::get_temporary_buffer -_LIBCPP_SUPPRESS_DEPRECATED_PUSH - __p = _VSTD::get_temporary_buffer(__len); -_LIBCPP_SUPPRESS_DEPRECATED_POP - __h.reset(__p.first); + __uninitialized_buffer __buf(__len); + return std::__stable_partition_impl<_AlgPolicy, _Predicate&>( + std::move(__first), + std::move(__last), + __pred, + __len, + std::make_pair(__buf.get(), __len), + forward_iterator_tag()); + } else { + return std::__stable_partition_impl<_AlgPolicy, _Predicate&>( + std::move(__first), + std::move(__last), + __pred, + __len, + std::make_pair(static_cast(nullptr), 0), + forward_iterator_tag()); } - return std::__stable_partition_impl<_AlgPolicy, _Predicate&>( - std::move(__first), std::move(__last), __pred, __len, __p, forward_iterator_tag()); } template @@ -291,18 +299,25 @@ // *__last is known to be true // __len >= 2 difference_type __len = _IterOps<_AlgPolicy>::distance(__first, __last) + 1; - pair __p(0, 0); - unique_ptr __h; if (__len >= __alloc_limit) { -// TODO: Remove the use of std::get_temporary_buffer -_LIBCPP_SUPPRESS_DEPRECATED_PUSH - __p = _VSTD::get_temporary_buffer(__len); -_LIBCPP_SUPPRESS_DEPRECATED_POP - __h.reset(__p.first); + __uninitialized_buffer __buf(__len); + return std::__stable_partition_impl<_AlgPolicy, _Predicate&>( + std::move(__first), + std::move(__last), + __pred, + __len, + std::make_pair(__buf.get(), __len), + bidirectional_iterator_tag()); + } else { + return std::__stable_partition_impl<_AlgPolicy, _Predicate&>( + std::move(__first), + std::move(__last), + __pred, + __len, + std::make_pair(static_cast(nullptr), 0), + bidirectional_iterator_tag()); } - return std::__stable_partition_impl<_AlgPolicy, _Predicate&>( - std::move(__first), std::move(__last), __pred, __len, __p, bidirectional_iterator_tag()); } template diff --git a/libcxx/include/__algorithm/stable_sort.h b/libcxx/include/__algorithm/stable_sort.h --- a/libcxx/include/__algorithm/stable_sort.h +++ b/libcxx/include/__algorithm/stable_sort.h @@ -248,17 +248,13 @@ using difference_type = typename iterator_traits<_RandomAccessIterator>::difference_type; difference_type __len = __last - __first; - pair __buf(0, 0); - unique_ptr __h; if (__len > static_cast(__stable_sort_switch::value)) { -// TODO: Remove the use of std::get_temporary_buffer -_LIBCPP_SUPPRESS_DEPRECATED_PUSH - __buf = std::get_temporary_buffer(__len); -_LIBCPP_SUPPRESS_DEPRECATED_POP - __h.reset(__buf.first); + __uninitialized_buffer __buf(__len); + std::__stable_sort<_AlgPolicy, __comp_ref_type<_Compare> >(__first, __last, __comp, __len, __buf.get(), __len); + } else { + std::__stable_sort<_AlgPolicy, __comp_ref_type<_Compare> >( + __first, __last, __comp, __len, static_cast(nullptr), 0); } - - std::__stable_sort<_AlgPolicy, __comp_ref_type<_Compare> >(__first, __last, __comp, __len, __buf.first, __buf.second); } template diff --git a/libcxx/include/__memory/construct_at.h b/libcxx/include/__memory/construct_at.h --- a/libcxx/include/__memory/construct_at.h +++ b/libcxx/include/__memory/construct_at.h @@ -93,6 +93,13 @@ return __last; } +template +_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 +_ForwardIterator __destroy_n(_ForwardIterator __first, _Size __n) { + for (; __n > 0; (void)++__first, --__n) + std::__destroy_at(std::addressof(*__first)); + return __first; +} #if _LIBCPP_STD_VER >= 17 template , int> = 0> @@ -118,9 +125,7 @@ template _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 _ForwardIterator destroy_n(_ForwardIterator __first, _Size __n) { - for (; __n > 0; (void)++__first, --__n) - std::__destroy_at(std::addressof(*__first)); - return __first; + return std::__destroy_n(__first, __n); } #endif // _LIBCPP_STD_VER >= 17 diff --git a/libcxx/include/__memory/uninitialized_buffer.h b/libcxx/include/__memory/uninitialized_buffer.h new file mode 100644 --- /dev/null +++ b/libcxx/include/__memory/uninitialized_buffer.h @@ -0,0 +1,65 @@ +//===----------------------------------------------------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#ifndef _LIBCPP___MEMORY_UNINITIALIZED_BUFFER_H +#define _LIBCPP___MEMORY_UNINITIALIZED_BUFFER_H + +#include <__config> +#include <__memory/construct_at.h> +#include +#include + +#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) +# pragma GCC system_header +#endif + +_LIBCPP_BEGIN_NAMESPACE_STD + +enum class __destruct { + __never, + __always, +}; + +template +class __uninitialized_buffer { +public: + using value_type = _Tp; + +#ifdef _LIBCPP_HAS_NO_ALIGNED_ALLOCATION + _LIBCPP_HIDE_FROM_ABI __uninitialized_buffer(size_type __count) + : __data_(static_cast<_Tp*>(::operator new(sizeof(_Tp) * __count))), __count_(__count) {} +#else + _LIBCPP_HIDE_FROM_ABI __uninitialized_buffer(size_t __count) + : __data_(static_cast<_Tp*>(::operator new(sizeof(_Tp) * __count, align_val_t(_LIBCPP_ALIGNOF(_Tp))))), + __count_(__count) {} +#endif + __uninitialized_buffer(const __uninitialized_buffer&) = delete; + __uninitialized_buffer(__uninitialized_buffer&&) = delete; + __uninitialized_buffer& operator=(const __uninitialized_buffer&) = delete; + __uninitialized_buffer& operator=(__uninitialized_buffer&&) = delete; + + _LIBCPP_NODISCARD _LIBCPP_HIDE_FROM_ABI _Tp* get() { return __data_; } + + _LIBCPP_HIDE_FROM_ABI ~__uninitialized_buffer() { + if (__run_destructors == __destruct::__always) + std::__destroy_n(get(), __count_); +#ifdef _LIBCPP_HAS_NO_ALIGNED_ALLOCATION + ::operator delete(get(), __count_ * sizeof(_Tp)); +#else + ::operator delete(get(), __count_ * sizeof(_Tp), align_val_t(_LIBCPP_ALIGNOF(_Tp))); +#endif + } + +private: + _Tp* __data_; + size_t __count_; +}; + +_LIBCPP_END_NAMESPACE_STD + +#endif // _LIBCPP___MEMORY_UNINITIALIZED_BUFFER_H