This implements that changes from P1132R8, including optimized paths for
std::shared_ptr and std::unique_ptr.
For std::shared_ptr we pre-allocate a new control block in the
std::out_ptr_t constructor so that the destructor is non-throwing. This
requires some care because unlike the shared_ptr(Y*, D, A) constructor,
we don't want to invoke the deleter if allocating the control block
throws, because we don't own any pointer yet. In order to avoid the
unwanted deleter invocation, we create the control block manually. We
also want to avoid invoking the deleter on a null pointer on
destruction, so we destroy the control block manually if there is no
pointer to take ownership of.
For std::unique_ptr and for raw pointers, the out_ptr_t object hands out
direct access to the pointer, so that we don't have anything to do
(except possibly assign a new deleter) in the ~out_ptr_t destructor.
These optimizations avoid requiring additional temporary storage for the
pointer (and optional arguments), and avoid additional instructions to
copy that pointer into the smart pointer at the end.
libstdc++-v3/ChangeLog:
PR libstdc++/111667
* include/Makefile.am: Add new header.
* include/Makefile.in: Regenerate.
* include/bits/out_ptr.h: New file.
* include/bits/shared_ptr.h (__is_shared_ptr): Move definition
to here ...
* include/bits/shared_ptr_atomic.h (__is_shared_ptr): ... from
here.
* include/bits/shared_ptr_base.h (__shared_count): Declare
out_ptr_t as a friend.
(_Sp_counted_deleter, __shared_ptr): Likewise.
* include/bits/unique_ptr.h (unique_ptr, unique_ptr<T[], D>):
Declare out_ptr_t and inout_ptr_t as friends.
(__is_unique_ptr): Define new variable template.
* include/bits/version.def (out_ptr): Define.
* include/bits/version.h: Regenerate.
* include/std/memory: Include new header.
* testsuite/20_util/smartptr.adapt/inout_ptr/1.cc: New test.
* testsuite/20_util/smartptr.adapt/inout_ptr/2.cc: New test.
* testsuite/20_util/smartptr.adapt/inout_ptr/shared_ptr_neg.cc:
New test.
* testsuite/20_util/smartptr.adapt/inout_ptr/void_ptr.cc: New
test.
* testsuite/20_util/smartptr.adapt/out_ptr/1.cc: New test.
* testsuite/20_util/smartptr.adapt/out_ptr/2.cc: New test.
* testsuite/20_util/smartptr.adapt/out_ptr/shared_ptr_neg.cc:
New test.
* testsuite/20_util/smartptr.adapt/out_ptr/void_ptr.cc: New
test.
This change moves the definitions of feature test macros (or strictly
speaking, the requests for <bits/version.h> to define them) so that only
standard headers define them. For example, <bits/shared_ptr.h> will no
longer define macros related to std::shared_ptr, only <memory> and
<version> will define them. This means that __cpp_lib_shared_ptr_arrays
will not be defined by <future> or by other headers that include
<bits/shared_ptr.h>. It will only be defined when <memory> has been
included. This will discourage users from relying on transitive
includes.
As a result, internal headers that need to query the macros should use
the internal macros like __glibcxx_shared_ptr_arrays instead of
__cpp_lib_shared_ptr_arrays, as those internal macros are defined by the
internal headers after icluding <bits/version.h>. There are some
exceptions to this rule, because __cpp_lib_is_constant_evaluated is
defined by bits/c++config.h and so is available everywhere, and
__cpp_lib_three_way_comparison is defined by <compare> which several
headers are explicitly specified to include, so its macro is guaranteed
to be usable too.
N.B. not many internal headers actually need an explicit include of
<bits/version.h>, because most of them include <type_traits> and so get
all the __glibcxx_foo internal macros from there.
libstdc++-v3/ChangeLog:
* include/bits/algorithmfwd.h: Do not define standard feature
test macro here.
* include/bits/align.h: Likewise. Test internal macros instead
of standard macros.
* include/bits/alloc_traits.h: Likewise.
* include/bits/allocator.h: Likewise.
* include/bits/atomic_base.h: Likewise.
* include/bits/atomic_timed_wait.h: Likewise.
* include/bits/atomic_wait.h: Likewise.
* include/bits/basic_string.h: Likewise.
* include/bits/basic_string.tcc: Likewise.
* include/bits/char_traits.h: Likewise.
* include/bits/chrono.h: Likewise.
* include/bits/cow_string.h: Likewise.
* include/bits/forward_list.h: Likewise.
* include/bits/hashtable.h: Likewise.
* include/bits/ios_base.h: Likewise.
* include/bits/memory_resource.h: Likewise.
* include/bits/move.h: Likewise.
* include/bits/move_only_function.h: Likewise.
* include/bits/node_handle.h: Likewise.
* include/bits/ptr_traits.h: Likewise.
* include/bits/range_access.h: Likewise.
* include/bits/ranges_algo.h: Likewise.
* include/bits/ranges_cmp.h: Likewise.
* include/bits/ranges_util.h: Likewise.
* include/bits/semaphore_base.h: Likewise.
* include/bits/shared_ptr.h: Likewise.
* include/bits/shared_ptr_atomic.h: Likewise.
* include/bits/shared_ptr_base.h: Likewise.
* include/bits/stl_algo.h: Likewise.
* include/bits/stl_algobase.h: Likewise.
* include/bits/stl_function.h: Likewise.
* include/bits/stl_iterator.h: Likewise.
* include/bits/stl_list.h: Likewise.
* include/bits/stl_map.h: Likewise.
* include/bits/stl_pair.h: Likewise.
* include/bits/stl_queue.h: Likewise.
* include/bits/stl_stack.h: Likewise.
* include/bits/stl_tree.h: Likewise.
* include/bits/stl_uninitialized.h: Likewise.
* include/bits/stl_vector.h: Likewise.
* include/bits/unique_ptr.h: Likewise.
* include/bits/unordered_map.h: Likewise.
* include/bits/uses_allocator_args.h: Likewise.
* include/bits/utility.h: Likewise.
* include/bits/erase_if.h: Add comment.
* include/std/algorithm: Define standard feature test macros
here.
* include/std/atomic: Likewise.
* include/std/array: Likewise.
* include/std/chrono: Likewise.
* include/std/condition_variable: Likewise.
* include/std/deque: Likewise.
* include/std/format: Likewise.
* include/std/functional: Likewise.
* include/std/forward_list: Likewise.
* include/std/ios: Likewise.
* include/std/iterator: Likewise.
* include/std/list: Likewise.
* include/std/map: Likewise.
* include/std/memory: Likewise.
* include/std/numeric: Likewise.
* include/std/queue: Likewise.
* include/std/ranges: Likewise.
* include/std/regex: Likewise.
* include/std/set: Likewise.
* include/std/stack: Likewise.
* include/std/stop_token: Likewise.
* include/std/string: Likewise.
* include/std/string_view:
* include/std/tuple: Likewise.
* include/std/unordered_map:
* include/std/unordered_set:
* include/std/utility: Likewise.
* include/std/vector: Likewise.
* include/std/scoped_allocator: Query internal macros instead of
standard macros.
Due to recent, large changes in libstdc++, the feature test macros
declared in <version> got out of sync with the other headers that
possibly declare them.
libstdc++-v3/ChangeLog:
* include/bits/unique_ptr.h (__cpp_lib_constexpr_memory):
Synchronize the definition block with...
* include/bits/ptr_traits.h (__cpp_lib_constexpr_memory):
... this one here. Also define the 202202L value, rather than
leaving it up to purely unique_ptr.h, so that the value is
synchronized across all headers.
(__gnu_debug::_Safe_iterator_base): Move into new conditional
block.
* include/std/memory (__cpp_lib_atomic_value_initialization):
Define on freestanding under the same conditions as in
atomic_base.h.
* include/std/version (__cpp_lib_robust_nonmodifying_seq_ops):
Also define on freestanding.
(__cpp_lib_to_chars): Ditto.
(__cpp_lib_gcd): Ditto.
(__cpp_lib_gcd_lcm): Ditto.
(__cpp_lib_raw_memory_algorithms): Ditto.
(__cpp_lib_array_constexpr): Ditto.
(__cpp_lib_nonmember_container_access): Ditto.
(__cpp_lib_clamp): Ditto.
(__cpp_lib_constexpr_char_traits): Ditto.
(__cpp_lib_constexpr_string): Ditto.
(__cpp_lib_sample): Ditto.
(__cpp_lib_lcm): Ditto.
(__cpp_lib_constexpr_iterator): Ditto.
(__cpp_lib_constexpr_char_traits): Ditto.
(__cpp_lib_interpolate): Ditto.
(__cpp_lib_constexpr_utility): Ditto.
(__cpp_lib_shift): Ditto.
(__cpp_lib_ranges): Ditto.
(__cpp_lib_move_iterator_concept): Ditto.
(__cpp_lib_constexpr_numeric): Ditto.
(__cpp_lib_constexpr_functional): Ditto.
(__cpp_lib_constexpr_algorithms): Ditto.
(__cpp_lib_constexpr_tuple): Ditto.
(__cpp_lib_constexpr_memory): Ditto.
This adds checks for _GLIBCXX_HOSTED to a number of headers which are
not currently installed for freestanding, but need to be for P1642R11
support. For example, <iterator> needs to be installed for C++23
freestanding mode, but without stream iterators and streambuf iterators.
Similarly, <memory> needs to be installed, but without std::allocator
and std::shared_ptr. This change disables the non-freestanding parts of
those headers.
libstdc++-v3/ChangeLog:
PR libstdc++/106953
* include/backward/auto_ptr.h [!_GLIBCXX_HOSTED]: Do not define
shared_ptr members.
* include/bits/alloc_traits.h [!_GLIBCXX_HOSTED]: Do not declare
std::allocator_traits<std::allocator<T>> specializations for
freestanding.
* include/bits/memoryfwd.h [!_GLIBCXX_HOSTED] (allocator): Do
not declare for freestanding.
* include/bits/stl_algo.h [!_GLIBCXX_HOSTED] (stable_partition):
Do not define for freestanding.
[!_GLIBCXX_HOSTED] (merge, stable_sort): Do not use temporary
buffers for freestanding.
* include/bits/stl_algobase.h [!_GLIBCXX_HOSTED]: Do not declare
streambuf iterators and overloaded algorithms using them.
* include/bits/stl_uninitialized.h [!_GLIBCXX_HOSTED]: Do not
define specialized overloads for std::allocator.
* include/bits/unique_ptr.h [!_GLIBCXX_HOSTED] (make_unique)
(make_unique_for_overwrite, operator<<): Do not define for
freestanding.
* include/c_global/cstdlib [!_GLIBCXX_HOSTED] (_Exit): Declare.
Use _GLIBCXX_NOTHROW instead of throw().
* include/debug/assertions.h [!_GLIBCXX_HOSTED]: Ignore
_GLIBCXX_DEBUG for freestanding.
* include/debug/debug.h [!_GLIBCXX_DEBUG]: Likewise.
* include/std/bit [!_GLIBCXX_HOSTED]: Do not use the custom
__int_traits if <ext/numeric_traits.h> is available.
* include/std/functional [!_GLIBCXX_HOSTED]: Do not include
headers that aren't valid for freestanding.
(boyer_moore_searcher, boyer_moore_horspool_searcher): Do not
define for freestanding.
* include/std/iterator [!_GLIBCXX_HOSTED]: Do not include
headers that aren't valid for freestanding.
* include/std/memory [!_GLIBCXX_HOSTED]: Likewise.
* include/std/ranges [!_GLIBCXX_HOSTED] (istream_view): Do not
define for freestanding.
(views::__detail::__is_basic_string_view) [!_GLIBCXX_HOSTED]:
Do not define partial specialization for freestanding.
libstdc++-v3/ChangeLog:
* include/bits/ptr_traits.h (__cpp_lib_constexpr_memory): Define
conditionally.
* include/bits/unique_ptr.h (__cpp_lib_constexpr_memory):
Define for C++23.
(default_delete, default_delete<T[]>, __uniq_ptr_impl)
(unique_ptr, unique_ptr<T[], D>): Add constexpr to all member
functions.
* include/std/version (__cpp_lib_constexpr_memory): Define new
value for C++23.
* testsuite/20_util/unique_ptr/assign/constexpr.cc: New test.
* testsuite/20_util/unique_ptr/comparison/constexpr.cc: New test.
* testsuite/20_util/unique_ptr/cons/constexpr_c++20.cc: New test.
* testsuite/20_util/unique_ptr/creation/constexpr.cc: New test.
* testsuite/20_util/unique_ptr/modifiers/constexpr.cc: New test.
* testsuite/20_util/unique_ptr/specialized_algorithms/constexpr.cc:
New test.
This change is inspired by the suggestion in
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2019/p1715r0.html
The new std::__conditional_t alias template is functionally equivalent
to std::conditional_t but should be more efficient to compile, due to
only ever instantiating two specializations (std::__conditional<true>
and std::__conditional<false>) rather than a new specialization for
every use of std::conditional.
The new alias template is also available in C++11, unlike the C++14
std::conditional_t alias.
Signed-off-by: Jonathan Wakely <jwakely@redhat.com>
libstdc++-v3/ChangeLog:
* include/std/type_traits (__conditional): New class template
for internal uses of std::conditional.
(__conditional_t): New alias template to replace conditional_t.
(__and_, __or_, __result_of_memfun, __result_of_memobj): Use
__conditional_t instead of conditional::type.
* include/bits/atomic_base.h (__atomic_impl::_Diff): Likewise.
* include/bits/hashtable.h (_Hashtable): Likewise.
* include/bits/hashtable_policy.h (_Node_iterator, _Insert_base)
(_Local_iterator): Likewise. Replace typedefs with
using-declarations.
* include/bits/move.h (move_if_noexcept): Use __conditional_t.
* include/bits/parse_numbers.h (_Select_int_base): Likewise.
* include/bits/ptr_traits.h (__make_not_void): Likewise.
* include/bits/ranges_algobase.h (__copy_or_move_backward)
(__copy_or_move): Likewise.
* include/bits/ranges_base.h (borrowed_iterator_t): Likewise.
* include/bits/ranges_util.h (borrowed_subrange_t): Likewise.
* include/bits/regex_compiler.h (_BracketMatcher): Use
__conditional_t. Replace typedefs with using-declarations.
* include/bits/shared_ptr_base.h (__shared_count): Use
__conditional_t.
* include/bits/stl_algobase.h (__copy_move, __copy_move_backward):
Likewise.
* include/bits/stl_iterator.h (__detail::__clamp_iter_cat)
(reverse_iterator::iterator_concept)
(__make_move_if_noexcept_iterator)
(iterator_traits<common_iterator<_It, _Sent>>)
(iterator_traits<counted_iterator<_It>>): Likewise.
* include/bits/stl_pair.h (_PCC, pair::operator=): Likewise.
* include/bits/stl_tree.h (_Rb_tree::insert_return_type)
(_Rb_tree::_M_clone_node): Likewise.
* include/bits/unique_ptr.h (unique_ptr(unique_ptr<U,E>&&)):
Likewise.
* include/bits/uses_allocator.h (__uses_alloc): Likewise.
(__is_uses_allocator_predicate): Likewise.
* include/debug/functions.h (__foreign_iterator_aux2): Likewise.
* include/experimental/any (any::_Manager, __any_caster):
Likewise.
* include/experimental/executor (async_completion): Likewise.
* include/experimental/functional (__boyer_moore_base_t):
Likewise.
* include/std/any (any::_Manager): Likewise.
* include/std/functional (__boyer_moore_base_t): Likewise.
* include/std/ranges (borrowed_iterator_t)
(borrowed_subrange_t, __detail::__maybe_present_t)
(__detail::__maybe_const_t, split_view): Likewise.
* include/std/tuple (__empty_not_final, tuple::operator=):
Likewise.
* include/std/variant (__detail::__variant::__get_t): Likewise.
Add more detailed documentation for unique_ptr and related components.
The new alias templates for the _MakeUniq SFINAE helper make the
generated docs look better too.
Signed-off-by: Jonathan Wakely <jwakely@redhat.com>
libstdc++-v3/ChangeLog:
* include/bits/unique_ptr.h (default_delete): Add @since tag.
(unique_ptr, unique_ptr<T[]>): Likewise. Improve @brief.
(make_unique, make_unique_for_overwrite): Likewise. Add @tparam,
@param, and @returns.
(_MakeUniq): Move to __detail namespace. Add alias template
helpers.
The <algorithm> header includes <utility>, with a comment referring to
UK-300, a National Body comment on the C++11 draft. That comment
proposed to move std::swap to <utility> and then require <algorithm> to
include <utility>. The comment was rejected, so we do not need to
implement the suggestion. For backwards compatibility with C++03 we do
want <algorithm> to define std::swap, but it does so anyway via
<bits/move.h>. We don't need the whole of <utility> to do that.
A few other headers that need std::swap can include <bits/move.h> to
get it, instead of <utility>.
There are several headers that include <utility> to get std::pair, but
they can use <bits/stl_pair.h> to get it without also including the
rel_ops namespace and other contents of <utility>.
Signed-off-by: Jonathan Wakely <jwakely@redhat.com>
libstdc++-v3/ChangeLog:
* include/std/algorithm: Do not include <utility>.
* include/std/functional: Likewise.
* include/std/regex: Include <bits/stl_pair.h> instead of
<utility>.
* include/debug/map.h: Likewise.
* include/debug/multimap.h: Likewise.
* include/debug/multiset.h: Likewise.
* include/debug/set.h: Likewise.
* include/debug/vector: Likewise.
* include/bits/fs_path.h: Likewise.
* include/bits/unique_ptr.h: Do not include <utility>.
* include/experimental/any: Likewise.
* include/experimental/executor: Likewise.
* include/experimental/memory: Likewise.
* include/experimental/optional: Likewise.
* include/experimental/socket: Use __exchange instead
of std::exchange.
* src/filesystem/ops-common.h: Likewise.
* testsuite/20_util/default_delete/48631_neg.cc: Adjust expected
errors to not use a hardcoded line number.
* testsuite/20_util/default_delete/void_neg.cc: Likewise.
* testsuite/20_util/specialized_algorithms/uninitialized_copy/constrained.cc:
Include <utility> for std::as_const.
* testsuite/20_util/specialized_algorithms/uninitialized_default_construct/constrained.cc:
Likewise.
* testsuite/20_util/specialized_algorithms/uninitialized_move/constrained.cc:
Likewise.
* testsuite/20_util/specialized_algorithms/uninitialized_value_construct/constrained.cc:
Likewise.
* testsuite/23_containers/vector/cons/destructible_debug_neg.cc:
Adjust dg-error line number.
This reorders the @{ and @relates tags, and moves the definition of the
__cpp_lib_make_unique macro out of the group, as it seems to confuse
doxygen.
libstdc++-v3/ChangeLog:
* include/bits/unique_ptr.h: Adjust doxygen markup.
This reverts the changes in r12-1778 which added a noexcept-specifier to
std::unique_ptr<T[]>::operator[], and the changes in r12-1844 which
tried to make it work with incomplete types (for PR 101236).
The noexcept-specifier is not required by the standard, and is causing
regressions, so just remove it.
Signed-off-by: Jonathan Wakely <jwakely@redhat.com>
libstdc++-v3/ChangeLog:
PR libstdc++/101271
* include/bits/unique_ptr.h (unique_ptr<T[],D>::operator[]):
Remove noexcept-specifier.
(unique_ptr<T[],D>::_S_nothrow_deref): Remove.
* testsuite/20_util/unique_ptr/lwg2762.cc: Remove checks for
operator[].
PR libstdc++/101236 shows that LLVM depends on being able to use
unique_ptr<T[]>::operator[] when T is incomplete. This is undefined, but
previously worked with libstdc++. When I added the conditional noexcept
to that operator we started to diagnose the incomplete type.
This change restores support for that case, by making the noexcept
condition check that the type is complete before checking whether
indexing on the pointer can throw. A workaround for PR c++/101239 is
needed to avoid a bogus error where G++ fails to do SFINAE on the
ill-formed p[n] expression and gets an ICE. Instead of checking that the
p[n] expression is valid in the trailing-return-type, we only check that
the element_type is complete.
libstdc++-v3/ChangeLog:
PR libstdc++/101236
* include/bits/unique_ptr.h (unique_ptr<T[], D>::operator[]):
Fail gracefully if element_type is incomplete.
* testsuite/20_util/unique_ptr/cons/incomplete.cc: Clarify that
the standard doesn't require this test to work for array types.
* testsuite/20_util/unique_ptr/lwg2762.cc: Check that incomplete
types can be used with array specialization.
* testsuite/20_util/unique_ptr/101236.cc: New test.
The LWG issue proposes to add a conditional noexcept-specifier to
std::unique_ptr's dereference operator. The issue is currently in
Tentatively Ready status, but even if it isn't voted into the draft, we
can do it as a conforming extensions. This commit also adds a similar
noexcept-specifier to operator[] for the unique_ptr<T[], D> partial
specialization.
Also ensure that all dereference operators for shared_ptr are noexcept,
and adds tests for the std::optional accessors modified by the issue,
which were already noexcept in our implementation.
Signed-off-by: Jonathan Wakely <jwakely@redhat.com>
libstdc++-v3/ChangeLog:
* include/bits/shared_ptr_base.h (__shared_ptr_access::operator[]):
Add noexcept.
* include/bits/unique_ptr.h (unique_ptr::operator*): Add
conditional noexcept as per LWG 2762.
* testsuite/20_util/shared_ptr/observers/array.cc: Check that
dereferencing cannot throw.
* testsuite/20_util/shared_ptr/observers/get.cc: Likewise.
* testsuite/20_util/optional/observers/lwg2762.cc: New test.
* testsuite/20_util/unique_ptr/lwg2762.cc: New test.
This is the std::unique_ptr part of P1020R1 (as amended by P1973R1) for
C++20. The std::shared_ptr part still needs to be done.
libstdc++-v3/ChangeLog:
* include/bits/unique_ptr.h (make_unique_for_overwrite): Define
for C++20.
* testsuite/20_util/unique_ptr/creation/array_neg.cc: Remove
unused header. Adjust standard reference.
* testsuite/20_util/unique_ptr/creation/for_overwrite.cc: New test.
* testsuite/20_util/unique_ptr/creation/for_overwrite__neg.cc: New test.
This also implements the proposed resolution to LWG issue 3247, so that
the ill-formed <=> expression with nullptr is not used.
PR libstdc++/94562
* include/bits/shared_ptr.h (operator<=>): Define for C++20.
* include/bits/shared_ptr_base.h (operator<=>): Likewise.
* include/bits/unique_ptr.h (operator<=>): Add inline specifier.
* testsuite/20_util/shared_ptr/comparison/cmp_c++20.cc: New test.
* testsuite/20_util/shared_ptr/comparison/less.cc: Do not expect
std::less<A*> to be used when comparing std::shared_ptr<A> objects in
C++20.
Some more C++20 changes from P1614R2, "The Mothership has Landed".
This includes the proposed resolution for LWG 3426 to fix the three-way
comparison with nullptr_t.
The existing tests for unique_ptr comparisons don't actually check the
results, only that the expressions compile and are convertible to bool.
This also adds a test for the results of those comparisons for C++11 and
up.
* include/bits/unique_ptr.h (operator<=>): Define for C++20.
* testsuite/20_util/default_delete/48631_neg.cc: Adjust dg-error line.
* testsuite/20_util/default_delete/void_neg.cc: Likewise.
* testsuite/20_util/unique_ptr/comparison/compare.cc: New test.
* testsuite/20_util/unique_ptr/comparison/compare_c++20.cc: New test.
The requirements for this function are only that the deleter is
swappable, but we incorrectly require that the element type is complete
and that the deleter can be swapped using std::swap (which requires it
to be move cosntructible and move assignable).
The fix is to add __uniq_ptr_impl::swap which swaps the pointer and
deleter individually, instead of using the generic std::swap on the
tuple containing them.
PR libstdc++/93562
* include/bits/unique_ptr.h (__uniq_ptr_impl::swap): Define.
(unique_ptr::swap, unique_ptr<T[], D>::swap): Call it.
* testsuite/20_util/unique_ptr/modifiers/93562.cc: New test.
PR libstdc++/91308
* include/bits/unique_ptr.h (unique_ptr::__safe_conversion_up): Remove
constraints on deleter that should only apply to the constructor.
(unique_ptr<T[], D>::__safe_conversion_up): Likewise.
(unique_ptr<T[], D>::unique_ptr(unique_ptr<U, D>&&)): Restore
constraints on deleter here.
* testsuite/20_util/unique_ptr/assign/91308.cc: New test.
From-SVN: r273937
* include/bits/unique_ptr.h (__uniq_ptr_impl): Add move constructor,
move assignment operator.
(__uniq_ptr_impl::release(), __uniq_ptr_impl::reset(pointer)): Add.
(__uniq_ptr_data): New class template with conditionally deleted
special members.
(unique_ptr, unique_ptr<T[], D>): Change type of data member from
__uniq_ptr_impl<T, D> to __uniq_ptr_data<T, D>. Define move
constructor and move assignment operator as defaulted.
(unique_ptr::release(), unique_ptr<T[], D>::release()): Forward to
__uniq_ptr_impl::release().
(unique_ptr::reset(pointer), unique_ptr<T[], D>::reset<U>(U)): Forward
to __uniq_ptr_impl::reset(pointer).
* python/libstdcxx/v6/printers.py (UniquePointerPrinter.__init__):
Check for new __uniq_ptr_data type.
* testsuite/20_util/unique_ptr/dr2899.cc: New test.
From-SVN: r271158
A disabled specialization should not be callable, so move the function
call operator into a new base class which correctly implements the
disabled hash semantics. For the versioned namespace configuration do
not derive from __poison_hash in the enabled case, as the empty base
class serves no purpose but potentially increases the object size. For
the default configuration that base class must be kept, to preserve
layout.
An enabled specialization should not be unconditionally noexcept,
because the underlying hash object might throw.
PR libstdc++/90388
* include/bits/unique_ptr.h (default_delete, default_delete<T[]>):
Use _Require for constraints.
(operator>(nullptr_t, const unique_ptr<T,D>&)): Implement exactly as
per the standard.
(__uniq_ptr_hash): New base class with conditionally-disabled call
operator.
(hash<unique_ptr<T,D>>): Derive from __uniq_ptr_hash.
* testsuite/20_util/default_delete/48631_neg.cc: Adjust dg-error line.
* testsuite/20_util/unique_ptr/hash/90388.cc: New test.
From-SVN: r271078
Avoid creating arbitrarily large objects on the stack when emplacing
trivially copyable objects into a variant. Currently we provide the
strong exception-safety guarantee for all trivially copyable types, by
constructing a second variant and then doing a non-throwing move
assignment from the temporary. This patch restricts that behaviour to
trivially copyable types that are no larger than 256 bytes. For larger
types the object will be emplaced directly into the variant, and if its
initialization throws then the variant becomes valueless.
Also implement Antony Polukhin's suggestion to whitelist specific types
that are not trivially copyable but can be efficiently move-assigned.
Emplacing those types will never cause a variant to become valueless.
The whitelisted types are: std::shared_ptr, std::weak_ptr,
std::unique_ptr, std::function, and std::any. Additionally,
std::basic_string, std::vector, and __gnu_debug::vector are whitelisted
if their allocator traits give them a non-throwing move assignment
operator. Specifically, this means std::string is whitelisted, but
std::pmr::string is not.
As part of this patch, additional if-constexpr branches are added for
the cases where the initialization is known to be non-throwing (so the
overhead of the try-catch block can be avoided) and where a scalar is
being produced by a potentially-throwing conversion operator (so that
the overhead of constructing and move-assigning a variant is avoided).
These changes should have no semantic effect, just better codegen.
PR libstdc++/87431 (again)
* include/bits/basic_string.h (__variant::_Never_valueless_alt):
Define partial specialization for basic_string.
* include/bits/shared_ptr.h (_Never_valueless_alt): Likewise for
shared_ptr and weak_ptr.
* include/bits/std_function.h (_Never_valueless_alt): Likewise for
function.
* include/bits/stl_vector.h (_Never_valueless_alt): Likewise for
vector.
* include/bits/unique_ptr.h (_Never_valueless_alt): Likewise for
unique_ptr.
* include/debug/vector (_Never_valueless_alt): Likewise for debug
vector.
* include/std/any (_Never_valueless_alt): Define explicit
specialization for any.
* include/std/variant (_Never_valueless_alt): Define primary template.
(__never_valueless): Use _Never_valueless_alt instead of
is_trivially_copyable.
(variant::emplace<N>(Args&&...)): Add special case for non-throwing
initializations to avoid try-catch overhead. Add special case for
scalars produced by potentially-throwing conversions. Use
_Never_valueless_alt instead of is_trivially_copyable for the
remaining strong exception-safety cases.
(variant::emplace<N>(initializer_list<U>, Args&&...)): Likewise.
* testsuite/20_util/variant/87431.cc: Run both test functions.
* testsuite/20_util/variant/exception_safety.cc: New test.
* testsuite/20_util/variant/run.cc: Use pmr::string instead of string,
so the variant becomes valueless.
From-SVN: r270170
PR libstdc++/88738
Warn about unused comparisons of shared_ptr/unique_ptr
* include/bits/c++config [_GLIBCXX_NODISCARD]: Define.
* include/bits/shared_ptr.h: Use it for operator ==, !=,
<, <=, >, >= for shared_ptr.
* include/bits/unique_ptr.h: Likewise for unique_ptr.
From-SVN: r267964
Using a delegating constructor to implement these constructors means
that they instantiate the destructor, which requires the element_type to
be complete. In C++11 and C++14 they were specified to be delegating,
but that was changed as part of LWG 2801 so in C++17 they don't require
a complete type (as was intended all along).
PR libstdc++/87704
* include/bits/unique_ptr.h (unique_ptr::unique_ptr(nullptr_t)): Do
not delegate to default constructor.
(unique_ptr<T[], D>::unique_ptr(nullptr_t)): Likewise.
* testsuite/20_util/unique_ptr/cons/incomplete.cc: New test.
From-SVN: r265423
The deleter only needs to be invocable when the unique_ptr destructor
and reset member function are instantiated. In other contexts it might
not be possible to pass unique_ptr<T, D>::pointer to the deleter, if
that requires a derived-to-base conversion from T* and T is incomplete.
* include/bits/unique_ptr.h (__uniq_ptr_impl): Remove static assertion
checking invocable condition.
(unique_ptr::~unique_ptr, unique_ptr::reset): Restore static assertion
here, where types must be complete. Pass pointer to deleter as an
rvalue.
* testsuite/20_util/unique_ptr/requirements/incomplete.cc: New test.
From-SVN: r264399
LWG DR 2905 says that is_constructible_v<unique_ptr<P, D>, P, D const &>
should be false when D is not copy constructible. This commit implements
the changes from the DR and simplifies the signatures as per
https://github.com/cplusplus/draft/issues/1530
* include/bits/unique_ptr.h (__uniq_ptr_impl): Add assertions to
check deleter type.
(unique_ptr::unique_ptr(pointer, const deleter_type&)): Add copy
constructible constraint.
(unique_ptr::unique_ptr(pointer, deleter_type&&)): Disable for
deleters of reference type and add move constructible constraint.
(unique_ptr::unique_ptr(pointer, remove_reference_t<deleter_type>&&)):
Disable for deleters of non-reference type. Define as deleted.
(unique_ptr<T[], D>): Likewise.
* testsuite/20_util/unique_ptr/assign/48635_neg.cc: Replace dg-error
directives with unstable line numbers with dg-prune-output.
* testsuite/20_util/unique_ptr/cons/cv_qual_neg.cc: Likewise.
* testsuite/20_util/unique_ptr/cons/lwg2905.cc: New test.
* testsuite/20_util/unique_ptr/specialized_algorithms/swap_cxx17.cc:
Make deleter types invocable.
From-SVN: r264206