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