1// -*- C++ -*-
2//===----------------------------------------------------------------------===//
3//
4// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
5// See https://llvm.org/LICENSE.txt for license information.
6// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7//
8//===----------------------------------------------------------------------===//
9
10#ifndef _LIBCPP___MEMORY_UNIQUE_PTR_H
11#define _LIBCPP___MEMORY_UNIQUE_PTR_H
12
13#include <__compare/compare_three_way.h>
14#include <__compare/compare_three_way_result.h>
15#include <__compare/three_way_comparable.h>
16#include <__config>
17#include <__functional/hash.h>
18#include <__functional/operations.h>
19#include <__memory/allocator_traits.h> // __pointer
20#include <__memory/auto_ptr.h>
21#include <__memory/compressed_pair.h>
22#include <__type_traits/add_lvalue_reference.h>
23#include <__type_traits/common_type.h>
24#include <__type_traits/dependent_type.h>
25#include <__type_traits/integral_constant.h>
26#include <__type_traits/is_array.h>
27#include <__type_traits/is_assignable.h>
28#include <__type_traits/is_constructible.h>
29#include <__type_traits/is_convertible.h>
30#include <__type_traits/is_default_constructible.h>
31#include <__type_traits/is_function.h>
32#include <__type_traits/is_pointer.h>
33#include <__type_traits/is_reference.h>
34#include <__type_traits/is_same.h>
35#include <__type_traits/is_swappable.h>
36#include <__type_traits/is_void.h>
37#include <__type_traits/remove_extent.h>
38#include <__type_traits/type_identity.h>
39#include <__utility/forward.h>
40#include <__utility/move.h>
41#include <cstddef>
42
43#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
44#  pragma GCC system_header
45#endif
46
47_LIBCPP_PUSH_MACROS
48#include <__undef_macros>
49
50_LIBCPP_BEGIN_NAMESPACE_STD
51
52template <class _Tp>
53struct _LIBCPP_TEMPLATE_VIS default_delete {
54  static_assert(!is_function<_Tp>::value, "default_delete cannot be instantiated for function types");
55#ifndef _LIBCPP_CXX03_LANG
56  _LIBCPP_HIDE_FROM_ABI constexpr default_delete() _NOEXCEPT = default;
57#else
58  _LIBCPP_HIDE_FROM_ABI default_delete() {}
59#endif
60  template <class _Up, __enable_if_t<is_convertible<_Up*, _Tp*>::value, int> = 0>
61  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 default_delete(const default_delete<_Up>&) _NOEXCEPT {}
62
63  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 void operator()(_Tp* __ptr) const _NOEXCEPT {
64    static_assert(sizeof(_Tp) >= 0, "cannot delete an incomplete type");
65    static_assert(!is_void<_Tp>::value, "cannot delete an incomplete type");
66    delete __ptr;
67  }
68};
69
70template <class _Tp>
71struct _LIBCPP_TEMPLATE_VIS default_delete<_Tp[]> {
72private:
73  template <class _Up>
74  struct _EnableIfConvertible : enable_if<is_convertible<_Up (*)[], _Tp (*)[]>::value> {};
75
76public:
77#ifndef _LIBCPP_CXX03_LANG
78  _LIBCPP_HIDE_FROM_ABI constexpr default_delete() _NOEXCEPT = default;
79#else
80  _LIBCPP_HIDE_FROM_ABI default_delete() {}
81#endif
82
83  template <class _Up>
84  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23
85  default_delete(const default_delete<_Up[]>&, typename _EnableIfConvertible<_Up>::type* = 0) _NOEXCEPT {}
86
87  template <class _Up>
88  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 typename _EnableIfConvertible<_Up>::type
89  operator()(_Up* __ptr) const _NOEXCEPT {
90    static_assert(sizeof(_Up) >= 0, "cannot delete an incomplete type");
91    delete[] __ptr;
92  }
93};
94
95template <class _Deleter>
96struct __unique_ptr_deleter_sfinae {
97  static_assert(!is_reference<_Deleter>::value, "incorrect specialization");
98  typedef const _Deleter& __lval_ref_type;
99  typedef _Deleter&& __good_rval_ref_type;
100  typedef true_type __enable_rval_overload;
101};
102
103template <class _Deleter>
104struct __unique_ptr_deleter_sfinae<_Deleter const&> {
105  typedef const _Deleter& __lval_ref_type;
106  typedef const _Deleter&& __bad_rval_ref_type;
107  typedef false_type __enable_rval_overload;
108};
109
110template <class _Deleter>
111struct __unique_ptr_deleter_sfinae<_Deleter&> {
112  typedef _Deleter& __lval_ref_type;
113  typedef _Deleter&& __bad_rval_ref_type;
114  typedef false_type __enable_rval_overload;
115};
116
117#if defined(_LIBCPP_ABI_ENABLE_UNIQUE_PTR_TRIVIAL_ABI)
118#  define _LIBCPP_UNIQUE_PTR_TRIVIAL_ABI __attribute__((__trivial_abi__))
119#else
120#  define _LIBCPP_UNIQUE_PTR_TRIVIAL_ABI
121#endif
122
123template <class _Tp, class _Dp = default_delete<_Tp> >
124class _LIBCPP_UNIQUE_PTR_TRIVIAL_ABI _LIBCPP_TEMPLATE_VIS unique_ptr {
125public:
126  typedef _Tp element_type;
127  typedef _Dp deleter_type;
128  typedef _LIBCPP_NODEBUG typename __pointer<_Tp, deleter_type>::type pointer;
129
130  static_assert(!is_rvalue_reference<deleter_type>::value, "the specified deleter type cannot be an rvalue reference");
131
132private:
133  __compressed_pair<pointer, deleter_type> __ptr_;
134
135  typedef _LIBCPP_NODEBUG __unique_ptr_deleter_sfinae<_Dp> _DeleterSFINAE;
136
137  template <bool _Dummy>
138  using _LValRefType _LIBCPP_NODEBUG = typename __dependent_type<_DeleterSFINAE, _Dummy>::__lval_ref_type;
139
140  template <bool _Dummy>
141  using _GoodRValRefType _LIBCPP_NODEBUG = typename __dependent_type<_DeleterSFINAE, _Dummy>::__good_rval_ref_type;
142
143  template <bool _Dummy>
144  using _BadRValRefType _LIBCPP_NODEBUG = typename __dependent_type<_DeleterSFINAE, _Dummy>::__bad_rval_ref_type;
145
146  template <bool _Dummy, class _Deleter = typename __dependent_type< __type_identity<deleter_type>, _Dummy>::type>
147  using _EnableIfDeleterDefaultConstructible _LIBCPP_NODEBUG =
148      __enable_if_t<is_default_constructible<_Deleter>::value && !is_pointer<_Deleter>::value>;
149
150  template <class _ArgType>
151  using _EnableIfDeleterConstructible _LIBCPP_NODEBUG = __enable_if_t<is_constructible<deleter_type, _ArgType>::value>;
152
153  template <class _UPtr, class _Up>
154  using _EnableIfMoveConvertible _LIBCPP_NODEBUG =
155      __enable_if_t< is_convertible<typename _UPtr::pointer, pointer>::value && !is_array<_Up>::value >;
156
157  template <class _UDel>
158  using _EnableIfDeleterConvertible _LIBCPP_NODEBUG =
159      __enable_if_t< (is_reference<_Dp>::value && is_same<_Dp, _UDel>::value) ||
160                     (!is_reference<_Dp>::value && is_convertible<_UDel, _Dp>::value) >;
161
162  template <class _UDel>
163  using _EnableIfDeleterAssignable = __enable_if_t< is_assignable<_Dp&, _UDel&&>::value >;
164
165public:
166  template <bool _Dummy = true, class = _EnableIfDeleterDefaultConstructible<_Dummy> >
167  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR unique_ptr() _NOEXCEPT : __ptr_(__value_init_tag(), __value_init_tag()) {}
168
169  template <bool _Dummy = true, class = _EnableIfDeleterDefaultConstructible<_Dummy> >
170  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR unique_ptr(nullptr_t) _NOEXCEPT
171      : __ptr_(__value_init_tag(), __value_init_tag()) {}
172
173  template <bool _Dummy = true, class = _EnableIfDeleterDefaultConstructible<_Dummy> >
174  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 explicit unique_ptr(pointer __p) _NOEXCEPT
175      : __ptr_(__p, __value_init_tag()) {}
176
177  template <bool _Dummy = true, class = _EnableIfDeleterConstructible<_LValRefType<_Dummy> > >
178  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr(pointer __p, _LValRefType<_Dummy> __d) _NOEXCEPT
179      : __ptr_(__p, __d) {}
180
181  template <bool _Dummy = true, class = _EnableIfDeleterConstructible<_GoodRValRefType<_Dummy> > >
182  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr(pointer __p, _GoodRValRefType<_Dummy> __d) _NOEXCEPT
183      : __ptr_(__p, std::move(__d)) {
184    static_assert(!is_reference<deleter_type>::value, "rvalue deleter bound to reference");
185  }
186
187  template <bool _Dummy = true, class = _EnableIfDeleterConstructible<_BadRValRefType<_Dummy> > >
188  _LIBCPP_HIDE_FROM_ABI unique_ptr(pointer __p, _BadRValRefType<_Dummy> __d) = delete;
189
190  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr(unique_ptr&& __u) _NOEXCEPT
191      : __ptr_(__u.release(), std::forward<deleter_type>(__u.get_deleter())) {}
192
193  template <class _Up,
194            class _Ep,
195            class = _EnableIfMoveConvertible<unique_ptr<_Up, _Ep>, _Up>,
196            class = _EnableIfDeleterConvertible<_Ep> >
197  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr(unique_ptr<_Up, _Ep>&& __u) _NOEXCEPT
198      : __ptr_(__u.release(), std::forward<_Ep>(__u.get_deleter())) {}
199
200#if _LIBCPP_STD_VER <= 14 || defined(_LIBCPP_ENABLE_CXX17_REMOVED_AUTO_PTR)
201  template <class _Up,
202            __enable_if_t<is_convertible<_Up*, _Tp*>::value && is_same<_Dp, default_delete<_Tp> >::value, int> = 0>
203  _LIBCPP_HIDE_FROM_ABI unique_ptr(auto_ptr<_Up>&& __p) _NOEXCEPT : __ptr_(__p.release(), __value_init_tag()) {}
204#endif
205
206  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr& operator=(unique_ptr&& __u) _NOEXCEPT {
207    reset(__u.release());
208    __ptr_.second() = std::forward<deleter_type>(__u.get_deleter());
209    return *this;
210  }
211
212  template <class _Up,
213            class _Ep,
214            class = _EnableIfMoveConvertible<unique_ptr<_Up, _Ep>, _Up>,
215            class = _EnableIfDeleterAssignable<_Ep> >
216  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr& operator=(unique_ptr<_Up, _Ep>&& __u) _NOEXCEPT {
217    reset(__u.release());
218    __ptr_.second() = std::forward<_Ep>(__u.get_deleter());
219    return *this;
220  }
221
222#if _LIBCPP_STD_VER <= 14 || defined(_LIBCPP_ENABLE_CXX17_REMOVED_AUTO_PTR)
223  template <class _Up,
224            __enable_if_t<is_convertible<_Up*, _Tp*>::value && is_same<_Dp, default_delete<_Tp> >::value, int> = 0>
225  _LIBCPP_HIDE_FROM_ABI unique_ptr& operator=(auto_ptr<_Up> __p) {
226    reset(__p.release());
227    return *this;
228  }
229#endif
230
231#ifdef _LIBCPP_CXX03_LANG
232  unique_ptr(unique_ptr const&)            = delete;
233  unique_ptr& operator=(unique_ptr const&) = delete;
234#endif
235
236  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 ~unique_ptr() { reset(); }
237
238  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr& operator=(nullptr_t) _NOEXCEPT {
239    reset();
240    return *this;
241  }
242
243  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 __add_lvalue_reference_t<_Tp> operator*() const {
244    return *__ptr_.first();
245  }
246  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 pointer operator->() const _NOEXCEPT { return __ptr_.first(); }
247  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 pointer get() const _NOEXCEPT { return __ptr_.first(); }
248  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 deleter_type& get_deleter() _NOEXCEPT { return __ptr_.second(); }
249  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 const deleter_type& get_deleter() const _NOEXCEPT {
250    return __ptr_.second();
251  }
252  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 explicit operator bool() const _NOEXCEPT {
253    return __ptr_.first() != nullptr;
254  }
255
256  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 pointer release() _NOEXCEPT {
257    pointer __t    = __ptr_.first();
258    __ptr_.first() = pointer();
259    return __t;
260  }
261
262  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 void reset(pointer __p = pointer()) _NOEXCEPT {
263    pointer __tmp  = __ptr_.first();
264    __ptr_.first() = __p;
265    if (__tmp)
266      __ptr_.second()(__tmp);
267  }
268
269  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 void swap(unique_ptr& __u) _NOEXCEPT { __ptr_.swap(__u.__ptr_); }
270};
271
272template <class _Tp, class _Dp>
273class _LIBCPP_UNIQUE_PTR_TRIVIAL_ABI _LIBCPP_TEMPLATE_VIS unique_ptr<_Tp[], _Dp> {
274public:
275  typedef _Tp element_type;
276  typedef _Dp deleter_type;
277  typedef typename __pointer<_Tp, deleter_type>::type pointer;
278
279private:
280  __compressed_pair<pointer, deleter_type> __ptr_;
281
282  template <class _From>
283  struct _CheckArrayPointerConversion : is_same<_From, pointer> {};
284
285  template <class _FromElem>
286  struct _CheckArrayPointerConversion<_FromElem*>
287      : integral_constant<bool,
288                          is_same<_FromElem*, pointer>::value ||
289                              (is_same<pointer, element_type*>::value &&
290                               is_convertible<_FromElem (*)[], element_type (*)[]>::value) > {};
291
292  typedef __unique_ptr_deleter_sfinae<_Dp> _DeleterSFINAE;
293
294  template <bool _Dummy>
295  using _LValRefType _LIBCPP_NODEBUG = typename __dependent_type<_DeleterSFINAE, _Dummy>::__lval_ref_type;
296
297  template <bool _Dummy>
298  using _GoodRValRefType _LIBCPP_NODEBUG = typename __dependent_type<_DeleterSFINAE, _Dummy>::__good_rval_ref_type;
299
300  template <bool _Dummy>
301  using _BadRValRefType _LIBCPP_NODEBUG = typename __dependent_type<_DeleterSFINAE, _Dummy>::__bad_rval_ref_type;
302
303  template <bool _Dummy, class _Deleter = typename __dependent_type< __type_identity<deleter_type>, _Dummy>::type>
304  using _EnableIfDeleterDefaultConstructible _LIBCPP_NODEBUG =
305      __enable_if_t<is_default_constructible<_Deleter>::value && !is_pointer<_Deleter>::value>;
306
307  template <class _ArgType>
308  using _EnableIfDeleterConstructible _LIBCPP_NODEBUG = __enable_if_t<is_constructible<deleter_type, _ArgType>::value>;
309
310  template <class _Pp>
311  using _EnableIfPointerConvertible _LIBCPP_NODEBUG = __enable_if_t< _CheckArrayPointerConversion<_Pp>::value >;
312
313  template <class _UPtr, class _Up, class _ElemT = typename _UPtr::element_type>
314  using _EnableIfMoveConvertible _LIBCPP_NODEBUG =
315      __enable_if_t< is_array<_Up>::value && is_same<pointer, element_type*>::value &&
316                     is_same<typename _UPtr::pointer, _ElemT*>::value &&
317                     is_convertible<_ElemT (*)[], element_type (*)[]>::value >;
318
319  template <class _UDel>
320  using _EnableIfDeleterConvertible _LIBCPP_NODEBUG =
321      __enable_if_t< (is_reference<_Dp>::value && is_same<_Dp, _UDel>::value) ||
322                     (!is_reference<_Dp>::value && is_convertible<_UDel, _Dp>::value) >;
323
324  template <class _UDel>
325  using _EnableIfDeleterAssignable _LIBCPP_NODEBUG = __enable_if_t< is_assignable<_Dp&, _UDel&&>::value >;
326
327public:
328  template <bool _Dummy = true, class = _EnableIfDeleterDefaultConstructible<_Dummy> >
329  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR unique_ptr() _NOEXCEPT : __ptr_(__value_init_tag(), __value_init_tag()) {}
330
331  template <bool _Dummy = true, class = _EnableIfDeleterDefaultConstructible<_Dummy> >
332  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR unique_ptr(nullptr_t) _NOEXCEPT
333      : __ptr_(__value_init_tag(), __value_init_tag()) {}
334
335  template <class _Pp,
336            bool _Dummy = true,
337            class       = _EnableIfDeleterDefaultConstructible<_Dummy>,
338            class       = _EnableIfPointerConvertible<_Pp> >
339  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 explicit unique_ptr(_Pp __p) _NOEXCEPT
340      : __ptr_(__p, __value_init_tag()) {}
341
342  template <class _Pp,
343            bool _Dummy = true,
344            class       = _EnableIfDeleterConstructible<_LValRefType<_Dummy> >,
345            class       = _EnableIfPointerConvertible<_Pp> >
346  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr(_Pp __p, _LValRefType<_Dummy> __d) _NOEXCEPT
347      : __ptr_(__p, __d) {}
348
349  template <bool _Dummy = true, class = _EnableIfDeleterConstructible<_LValRefType<_Dummy> > >
350  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr(nullptr_t, _LValRefType<_Dummy> __d) _NOEXCEPT
351      : __ptr_(nullptr, __d) {}
352
353  template <class _Pp,
354            bool _Dummy = true,
355            class       = _EnableIfDeleterConstructible<_GoodRValRefType<_Dummy> >,
356            class       = _EnableIfPointerConvertible<_Pp> >
357  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr(_Pp __p, _GoodRValRefType<_Dummy> __d) _NOEXCEPT
358      : __ptr_(__p, std::move(__d)) {
359    static_assert(!is_reference<deleter_type>::value, "rvalue deleter bound to reference");
360  }
361
362  template <bool _Dummy = true, class = _EnableIfDeleterConstructible<_GoodRValRefType<_Dummy> > >
363  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr(nullptr_t, _GoodRValRefType<_Dummy> __d) _NOEXCEPT
364      : __ptr_(nullptr, std::move(__d)) {
365    static_assert(!is_reference<deleter_type>::value, "rvalue deleter bound to reference");
366  }
367
368  template <class _Pp,
369            bool _Dummy = true,
370            class       = _EnableIfDeleterConstructible<_BadRValRefType<_Dummy> >,
371            class       = _EnableIfPointerConvertible<_Pp> >
372  _LIBCPP_HIDE_FROM_ABI unique_ptr(_Pp __p, _BadRValRefType<_Dummy> __d) = delete;
373
374  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr(unique_ptr&& __u) _NOEXCEPT
375      : __ptr_(__u.release(), std::forward<deleter_type>(__u.get_deleter())) {}
376
377  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr& operator=(unique_ptr&& __u) _NOEXCEPT {
378    reset(__u.release());
379    __ptr_.second() = std::forward<deleter_type>(__u.get_deleter());
380    return *this;
381  }
382
383  template <class _Up,
384            class _Ep,
385            class = _EnableIfMoveConvertible<unique_ptr<_Up, _Ep>, _Up>,
386            class = _EnableIfDeleterConvertible<_Ep> >
387  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr(unique_ptr<_Up, _Ep>&& __u) _NOEXCEPT
388      : __ptr_(__u.release(), std::forward<_Ep>(__u.get_deleter())) {}
389
390  template <class _Up,
391            class _Ep,
392            class = _EnableIfMoveConvertible<unique_ptr<_Up, _Ep>, _Up>,
393            class = _EnableIfDeleterAssignable<_Ep> >
394  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr& operator=(unique_ptr<_Up, _Ep>&& __u) _NOEXCEPT {
395    reset(__u.release());
396    __ptr_.second() = std::forward<_Ep>(__u.get_deleter());
397    return *this;
398  }
399
400#ifdef _LIBCPP_CXX03_LANG
401  unique_ptr(unique_ptr const&)            = delete;
402  unique_ptr& operator=(unique_ptr const&) = delete;
403#endif
404
405public:
406  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 ~unique_ptr() { reset(); }
407
408  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 unique_ptr& operator=(nullptr_t) _NOEXCEPT {
409    reset();
410    return *this;
411  }
412
413  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 __add_lvalue_reference_t<_Tp> operator[](size_t __i) const {
414    return __ptr_.first()[__i];
415  }
416  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 pointer get() const _NOEXCEPT { return __ptr_.first(); }
417
418  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 deleter_type& get_deleter() _NOEXCEPT { return __ptr_.second(); }
419
420  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 const deleter_type& get_deleter() const _NOEXCEPT {
421    return __ptr_.second();
422  }
423  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 explicit operator bool() const _NOEXCEPT {
424    return __ptr_.first() != nullptr;
425  }
426
427  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 pointer release() _NOEXCEPT {
428    pointer __t    = __ptr_.first();
429    __ptr_.first() = pointer();
430    return __t;
431  }
432
433  template <class _Pp, __enable_if_t<_CheckArrayPointerConversion<_Pp>::value, int> = 0>
434  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 void reset(_Pp __p) _NOEXCEPT {
435    pointer __tmp  = __ptr_.first();
436    __ptr_.first() = __p;
437    if (__tmp)
438      __ptr_.second()(__tmp);
439  }
440
441  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 void reset(nullptr_t = nullptr) _NOEXCEPT {
442    pointer __tmp  = __ptr_.first();
443    __ptr_.first() = nullptr;
444    if (__tmp)
445      __ptr_.second()(__tmp);
446  }
447
448  _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 void swap(unique_ptr& __u) _NOEXCEPT { __ptr_.swap(__u.__ptr_); }
449};
450
451template <class _Tp, class _Dp, __enable_if_t<__is_swappable<_Dp>::value, int> = 0>
452inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 void
453swap(unique_ptr<_Tp, _Dp>& __x, unique_ptr<_Tp, _Dp>& __y) _NOEXCEPT {
454  __x.swap(__y);
455}
456
457template <class _T1, class _D1, class _T2, class _D2>
458inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 bool
459operator==(const unique_ptr<_T1, _D1>& __x, const unique_ptr<_T2, _D2>& __y) {
460  return __x.get() == __y.get();
461}
462
463#if _LIBCPP_STD_VER <= 17
464template <class _T1, class _D1, class _T2, class _D2>
465inline _LIBCPP_HIDE_FROM_ABI bool operator!=(const unique_ptr<_T1, _D1>& __x, const unique_ptr<_T2, _D2>& __y) {
466  return !(__x == __y);
467}
468#endif
469
470template <class _T1, class _D1, class _T2, class _D2>
471inline _LIBCPP_HIDE_FROM_ABI bool operator<(const unique_ptr<_T1, _D1>& __x, const unique_ptr<_T2, _D2>& __y) {
472  typedef typename unique_ptr<_T1, _D1>::pointer _P1;
473  typedef typename unique_ptr<_T2, _D2>::pointer _P2;
474  typedef typename common_type<_P1, _P2>::type _Vp;
475  return less<_Vp>()(__x.get(), __y.get());
476}
477
478template <class _T1, class _D1, class _T2, class _D2>
479inline _LIBCPP_HIDE_FROM_ABI bool operator>(const unique_ptr<_T1, _D1>& __x, const unique_ptr<_T2, _D2>& __y) {
480  return __y < __x;
481}
482
483template <class _T1, class _D1, class _T2, class _D2>
484inline _LIBCPP_HIDE_FROM_ABI bool operator<=(const unique_ptr<_T1, _D1>& __x, const unique_ptr<_T2, _D2>& __y) {
485  return !(__y < __x);
486}
487
488template <class _T1, class _D1, class _T2, class _D2>
489inline _LIBCPP_HIDE_FROM_ABI bool operator>=(const unique_ptr<_T1, _D1>& __x, const unique_ptr<_T2, _D2>& __y) {
490  return !(__x < __y);
491}
492
493#if _LIBCPP_STD_VER >= 20
494template <class _T1, class _D1, class _T2, class _D2>
495  requires three_way_comparable_with<typename unique_ptr<_T1, _D1>::pointer, typename unique_ptr<_T2, _D2>::pointer>
496_LIBCPP_HIDE_FROM_ABI
497    compare_three_way_result_t<typename unique_ptr<_T1, _D1>::pointer, typename unique_ptr<_T2, _D2>::pointer>
498    operator<=>(const unique_ptr<_T1, _D1>& __x, const unique_ptr<_T2, _D2>& __y) {
499  return compare_three_way()(__x.get(), __y.get());
500}
501#endif
502
503template <class _T1, class _D1>
504inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 bool
505operator==(const unique_ptr<_T1, _D1>& __x, nullptr_t) _NOEXCEPT {
506  return !__x;
507}
508
509#if _LIBCPP_STD_VER <= 17
510template <class _T1, class _D1>
511inline _LIBCPP_HIDE_FROM_ABI bool operator==(nullptr_t, const unique_ptr<_T1, _D1>& __x) _NOEXCEPT {
512  return !__x;
513}
514
515template <class _T1, class _D1>
516inline _LIBCPP_HIDE_FROM_ABI bool operator!=(const unique_ptr<_T1, _D1>& __x, nullptr_t) _NOEXCEPT {
517  return static_cast<bool>(__x);
518}
519
520template <class _T1, class _D1>
521inline _LIBCPP_HIDE_FROM_ABI bool operator!=(nullptr_t, const unique_ptr<_T1, _D1>& __x) _NOEXCEPT {
522  return static_cast<bool>(__x);
523}
524#endif // _LIBCPP_STD_VER <= 17
525
526template <class _T1, class _D1>
527inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 bool operator<(const unique_ptr<_T1, _D1>& __x, nullptr_t) {
528  typedef typename unique_ptr<_T1, _D1>::pointer _P1;
529  return less<_P1>()(__x.get(), nullptr);
530}
531
532template <class _T1, class _D1>
533inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 bool operator<(nullptr_t, const unique_ptr<_T1, _D1>& __x) {
534  typedef typename unique_ptr<_T1, _D1>::pointer _P1;
535  return less<_P1>()(nullptr, __x.get());
536}
537
538template <class _T1, class _D1>
539inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 bool operator>(const unique_ptr<_T1, _D1>& __x, nullptr_t) {
540  return nullptr < __x;
541}
542
543template <class _T1, class _D1>
544inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 bool operator>(nullptr_t, const unique_ptr<_T1, _D1>& __x) {
545  return __x < nullptr;
546}
547
548template <class _T1, class _D1>
549inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 bool operator<=(const unique_ptr<_T1, _D1>& __x, nullptr_t) {
550  return !(nullptr < __x);
551}
552
553template <class _T1, class _D1>
554inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 bool operator<=(nullptr_t, const unique_ptr<_T1, _D1>& __x) {
555  return !(__x < nullptr);
556}
557
558template <class _T1, class _D1>
559inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 bool operator>=(const unique_ptr<_T1, _D1>& __x, nullptr_t) {
560  return !(__x < nullptr);
561}
562
563template <class _T1, class _D1>
564inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 bool operator>=(nullptr_t, const unique_ptr<_T1, _D1>& __x) {
565  return !(nullptr < __x);
566}
567
568#if _LIBCPP_STD_VER >= 20
569template <class _T1, class _D1>
570  requires three_way_comparable< typename unique_ptr<_T1, _D1>::pointer>
571_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 compare_three_way_result_t<typename unique_ptr<_T1, _D1>::pointer>
572operator<=>(const unique_ptr<_T1, _D1>& __x, nullptr_t) {
573  return compare_three_way()(__x.get(), static_cast<typename unique_ptr<_T1, _D1>::pointer>(nullptr));
574}
575#endif
576
577#if _LIBCPP_STD_VER >= 14
578
579template <class _Tp>
580struct __unique_if {
581  typedef unique_ptr<_Tp> __unique_single;
582};
583
584template <class _Tp>
585struct __unique_if<_Tp[]> {
586  typedef unique_ptr<_Tp[]> __unique_array_unknown_bound;
587};
588
589template <class _Tp, size_t _Np>
590struct __unique_if<_Tp[_Np]> {
591  typedef void __unique_array_known_bound;
592};
593
594template <class _Tp, class... _Args>
595inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 typename __unique_if<_Tp>::__unique_single
596make_unique(_Args&&... __args) {
597  return unique_ptr<_Tp>(new _Tp(std::forward<_Args>(__args)...));
598}
599
600template <class _Tp>
601inline _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 typename __unique_if<_Tp>::__unique_array_unknown_bound
602make_unique(size_t __n) {
603  typedef __remove_extent_t<_Tp> _Up;
604  return unique_ptr<_Tp>(new _Up[__n]());
605}
606
607template <class _Tp, class... _Args>
608typename __unique_if<_Tp>::__unique_array_known_bound make_unique(_Args&&...) = delete;
609
610#endif // _LIBCPP_STD_VER >= 14
611
612#if _LIBCPP_STD_VER >= 20
613
614template <class _Tp>
615_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 typename __unique_if<_Tp>::__unique_single
616make_unique_for_overwrite() {
617  return unique_ptr<_Tp>(new _Tp);
618}
619
620template <class _Tp>
621_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX23 typename __unique_if<_Tp>::__unique_array_unknown_bound
622make_unique_for_overwrite(size_t __n) {
623  return unique_ptr<_Tp>(new __remove_extent_t<_Tp>[__n]);
624}
625
626template <class _Tp, class... _Args>
627typename __unique_if<_Tp>::__unique_array_known_bound make_unique_for_overwrite(_Args&&...) = delete;
628
629#endif // _LIBCPP_STD_VER >= 20
630
631template <class _Tp>
632struct _LIBCPP_TEMPLATE_VIS hash;
633
634template <class _Tp, class _Dp>
635#ifdef _LIBCPP_CXX03_LANG
636struct _LIBCPP_TEMPLATE_VIS hash<unique_ptr<_Tp, _Dp> >
637#else
638struct _LIBCPP_TEMPLATE_VIS hash<__enable_hash_helper< unique_ptr<_Tp, _Dp>, typename unique_ptr<_Tp, _Dp>::pointer> >
639#endif
640{
641#if _LIBCPP_STD_VER <= 17 || defined(_LIBCPP_ENABLE_CXX20_REMOVED_BINDER_TYPEDEFS)
642  _LIBCPP_DEPRECATED_IN_CXX17 typedef unique_ptr<_Tp, _Dp> argument_type;
643  _LIBCPP_DEPRECATED_IN_CXX17 typedef size_t result_type;
644#endif
645
646  _LIBCPP_HIDE_FROM_ABI size_t operator()(const unique_ptr<_Tp, _Dp>& __ptr) const {
647    typedef typename unique_ptr<_Tp, _Dp>::pointer pointer;
648    return hash<pointer>()(__ptr.get());
649  }
650};
651
652_LIBCPP_END_NAMESPACE_STD
653
654_LIBCPP_POP_MACROS
655
656#endif // _LIBCPP___MEMORY_UNIQUE_PTR_H
657