Home | History | Annotate | Download | only in bits
      1 // unique_ptr implementation -*- C++ -*-
      2 
      3 // Copyright (C) 2008-2014 Free Software Foundation, Inc.
      4 //
      5 // This file is part of the GNU ISO C++ Library.  This library is free
      6 // software; you can redistribute it and/or modify it under the
      7 // terms of the GNU General Public License as published by the
      8 // Free Software Foundation; either version 3, or (at your option)
      9 // any later version.
     10 
     11 // This library is distributed in the hope that it will be useful,
     12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
     13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     14 // GNU General Public License for more details.
     15 
     16 // Under Section 7 of GPL version 3, you are granted additional
     17 // permissions described in the GCC Runtime Library Exception, version
     18 // 3.1, as published by the Free Software Foundation.
     19 
     20 // You should have received a copy of the GNU General Public License and
     21 // a copy of the GCC Runtime Library Exception along with this program;
     22 // see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
     23 // <http://www.gnu.org/licenses/>.
     24 
     25 /** @file bits/unique_ptr.h
     26  *  This is an internal header file, included by other library headers.
     27  *  Do not attempt to use it directly. @headername{memory}
     28  */
     29 
     30 #ifndef _UNIQUE_PTR_H
     31 #define _UNIQUE_PTR_H 1
     32 
     33 #include <bits/c++config.h>
     34 #include <debug/debug.h>
     35 #include <type_traits>
     36 #include <utility>
     37 #include <tuple>
     38 
     39 namespace std _GLIBCXX_VISIBILITY(default)
     40 {
     41 _GLIBCXX_BEGIN_NAMESPACE_VERSION
     42 
     43   /**
     44    * @addtogroup pointer_abstractions
     45    * @{
     46    */
     47 
     48 #if _GLIBCXX_USE_DEPRECATED
     49   template<typename> class auto_ptr;
     50 #endif
     51 
     52   /// Primary template of default_delete, used by unique_ptr
     53   template<typename _Tp>
     54     struct default_delete
     55     {
     56       /// Default constructor
     57       constexpr default_delete() noexcept = default;
     58 
     59       /** @brief Converting constructor.
     60        *
     61        * Allows conversion from a deleter for arrays of another type, @p _Up,
     62        * only if @p _Up* is convertible to @p _Tp*.
     63        */
     64       template<typename _Up, typename = typename
     65 	       enable_if<is_convertible<_Up*, _Tp*>::value>::type>
     66         default_delete(const default_delete<_Up>&) noexcept { }
     67 
     68       /// Calls @c delete @p __ptr
     69       void
     70       operator()(_Tp* __ptr) const
     71       {
     72 	static_assert(!is_void<_Tp>::value,
     73 		      "can't delete pointer to incomplete type");
     74 	static_assert(sizeof(_Tp)>0,
     75 		      "can't delete pointer to incomplete type");
     76 	delete __ptr;
     77       }
     78     };
     79 
     80   // _GLIBCXX_RESOLVE_LIB_DEFECTS
     81   // DR 740 - omit specialization for array objects with a compile time length
     82   /// Specialization for arrays, default_delete.
     83   template<typename _Tp>
     84     struct default_delete<_Tp[]>
     85     {
     86     private:
     87       template<typename _Up>
     88 	using __remove_cv = typename remove_cv<_Up>::type;
     89 
     90       // Like is_base_of<_Tp, _Up> but false if unqualified types are the same
     91       template<typename _Up>
     92 	using __is_derived_Tp
     93 	  = __and_< is_base_of<_Tp, _Up>,
     94 		    __not_<is_same<__remove_cv<_Tp>, __remove_cv<_Up>>> >;
     95 
     96     public:
     97       /// Default constructor
     98       constexpr default_delete() noexcept = default;
     99 
    100       /** @brief Converting constructor.
    101        *
    102        * Allows conversion from a deleter for arrays of another type, such as
    103        * a const-qualified version of @p _Tp.
    104        *
    105        * Conversions from types derived from @c _Tp are not allowed because
    106        * it is unsafe to @c delete[] an array of derived types through a
    107        * pointer to the base type.
    108        */
    109       template<typename _Up, typename = typename
    110 	       enable_if<!__is_derived_Tp<_Up>::value>::type>
    111         default_delete(const default_delete<_Up[]>&) noexcept { }
    112 
    113       /// Calls @c delete[] @p __ptr
    114       void
    115       operator()(_Tp* __ptr) const
    116       {
    117 	static_assert(sizeof(_Tp)>0,
    118 		      "can't delete pointer to incomplete type");
    119 	delete [] __ptr;
    120       }
    121 
    122       template<typename _Up>
    123 	typename enable_if<__is_derived_Tp<_Up>::value>::type
    124 	operator()(_Up*) const = delete;
    125     };
    126 
    127   /// 20.7.1.2 unique_ptr for single objects.
    128   template <typename _Tp, typename _Dp = default_delete<_Tp> >
    129     class unique_ptr
    130     {
    131       // use SFINAE to determine whether _Del::pointer exists
    132       class _Pointer
    133       {
    134 	template<typename _Up>
    135 	  static typename _Up::pointer __test(typename _Up::pointer*);
    136 
    137 	template<typename _Up>
    138 	  static _Tp* __test(...);
    139 
    140 	typedef typename remove_reference<_Dp>::type _Del;
    141 
    142       public:
    143 	typedef decltype(__test<_Del>(0)) type;
    144       };
    145 
    146       typedef std::tuple<typename _Pointer::type, _Dp>  __tuple_type;
    147       __tuple_type                                      _M_t;
    148 
    149     public:
    150       typedef typename _Pointer::type   pointer;
    151       typedef _Tp                       element_type;
    152       typedef _Dp                       deleter_type;
    153 
    154       // Constructors.
    155 
    156       /// Default constructor, creates a unique_ptr that owns nothing.
    157       constexpr unique_ptr() noexcept
    158       : _M_t()
    159       { static_assert(!is_pointer<deleter_type>::value,
    160 		     "constructed with null function pointer deleter"); }
    161 
    162       /** Takes ownership of a pointer.
    163        *
    164        * @param __p  A pointer to an object of @c element_type
    165        *
    166        * The deleter will be value-initialized.
    167        */
    168       explicit
    169       unique_ptr(pointer __p) noexcept
    170       : _M_t(__p, deleter_type())
    171       { static_assert(!is_pointer<deleter_type>::value,
    172 		     "constructed with null function pointer deleter"); }
    173 
    174       /** Takes ownership of a pointer.
    175        *
    176        * @param __p  A pointer to an object of @c element_type
    177        * @param __d  A reference to a deleter.
    178        *
    179        * The deleter will be initialized with @p __d
    180        */
    181       unique_ptr(pointer __p,
    182 	  typename conditional<is_reference<deleter_type>::value,
    183 	    deleter_type, const deleter_type&>::type __d) noexcept
    184       : _M_t(__p, __d) { }
    185 
    186       /** Takes ownership of a pointer.
    187        *
    188        * @param __p  A pointer to an object of @c element_type
    189        * @param __d  An rvalue reference to a deleter.
    190        *
    191        * The deleter will be initialized with @p std::move(__d)
    192        */
    193       unique_ptr(pointer __p,
    194 	  typename remove_reference<deleter_type>::type&& __d) noexcept
    195       : _M_t(std::move(__p), std::move(__d))
    196       { static_assert(!std::is_reference<deleter_type>::value,
    197 		      "rvalue deleter bound to reference"); }
    198 
    199       /// Creates a unique_ptr that owns nothing.
    200       constexpr unique_ptr(nullptr_t) noexcept : unique_ptr() { }
    201 
    202       // Move constructors.
    203 
    204       /// Move constructor.
    205       unique_ptr(unique_ptr&& __u) noexcept
    206       : _M_t(__u.release(), std::forward<deleter_type>(__u.get_deleter())) { }
    207 
    208       /** @brief Converting constructor from another type
    209        *
    210        * Requires that the pointer owned by @p __u is convertible to the
    211        * type of pointer owned by this object, @p __u does not own an array,
    212        * and @p __u has a compatible deleter type.
    213        */
    214       template<typename _Up, typename _Ep, typename = _Require<
    215 	       is_convertible<typename unique_ptr<_Up, _Ep>::pointer, pointer>,
    216 	       __not_<is_array<_Up>>,
    217 	       typename conditional<is_reference<_Dp>::value,
    218 				    is_same<_Ep, _Dp>,
    219 				    is_convertible<_Ep, _Dp>>::type>>
    220 	unique_ptr(unique_ptr<_Up, _Ep>&& __u) noexcept
    221 	: _M_t(__u.release(), std::forward<_Ep>(__u.get_deleter()))
    222 	{ }
    223 
    224 #if _GLIBCXX_USE_DEPRECATED
    225       /// Converting constructor from @c auto_ptr
    226       template<typename _Up, typename = _Require<
    227 	       is_convertible<_Up*, _Tp*>, is_same<_Dp, default_delete<_Tp>>>>
    228 	unique_ptr(auto_ptr<_Up>&& __u) noexcept;
    229 #endif
    230 
    231       /// Destructor, invokes the deleter if the stored pointer is not null.
    232       ~unique_ptr() noexcept
    233       {
    234 	auto& __ptr = std::get<0>(_M_t);
    235 	if (__ptr != nullptr)
    236 	  get_deleter()(__ptr);
    237 	__ptr = pointer();
    238       }
    239 
    240       // Assignment.
    241 
    242       /** @brief Move assignment operator.
    243        *
    244        * @param __u  The object to transfer ownership from.
    245        *
    246        * Invokes the deleter first if this object owns a pointer.
    247        */
    248       unique_ptr&
    249       operator=(unique_ptr&& __u) noexcept
    250       {
    251 	reset(__u.release());
    252 	get_deleter() = std::forward<deleter_type>(__u.get_deleter());
    253 	return *this;
    254       }
    255 
    256       /** @brief Assignment from another type.
    257        *
    258        * @param __u  The object to transfer ownership from, which owns a
    259        *             convertible pointer to a non-array object.
    260        *
    261        * Invokes the deleter first if this object owns a pointer.
    262        */
    263       template<typename _Up, typename _Ep>
    264 	typename enable_if< __and_<
    265 	  is_convertible<typename unique_ptr<_Up, _Ep>::pointer, pointer>,
    266 	  __not_<is_array<_Up>>
    267 	  >::value,
    268 	  unique_ptr&>::type
    269 	operator=(unique_ptr<_Up, _Ep>&& __u) noexcept
    270 	{
    271 	  reset(__u.release());
    272 	  get_deleter() = std::forward<_Ep>(__u.get_deleter());
    273 	  return *this;
    274 	}
    275 
    276       /// Reset the %unique_ptr to empty, invoking the deleter if necessary.
    277       unique_ptr&
    278       operator=(nullptr_t) noexcept
    279       {
    280 	reset();
    281 	return *this;
    282       }
    283 
    284       // Observers.
    285 
    286       /// Dereference the stored pointer.
    287       typename add_lvalue_reference<element_type>::type
    288       operator*() const
    289       {
    290 	_GLIBCXX_DEBUG_ASSERT(get() != pointer());
    291 	return *get();
    292       }
    293 
    294       /// Return the stored pointer.
    295       pointer
    296       operator->() const noexcept
    297       {
    298 	_GLIBCXX_DEBUG_ASSERT(get() != pointer());
    299 	return get();
    300       }
    301 
    302       /// Return the stored pointer.
    303       pointer
    304       get() const noexcept
    305       { return std::get<0>(_M_t); }
    306 
    307       /// Return a reference to the stored deleter.
    308       deleter_type&
    309       get_deleter() noexcept
    310       { return std::get<1>(_M_t); }
    311 
    312       /// Return a reference to the stored deleter.
    313       const deleter_type&
    314       get_deleter() const noexcept
    315       { return std::get<1>(_M_t); }
    316 
    317       /// Return @c true if the stored pointer is not null.
    318       explicit operator bool() const noexcept
    319       { return get() == pointer() ? false : true; }
    320 
    321       // Modifiers.
    322 
    323       /// Release ownership of any stored pointer.
    324       pointer
    325       release() noexcept
    326       {
    327 	pointer __p = get();
    328 	std::get<0>(_M_t) = pointer();
    329 	return __p;
    330       }
    331 
    332       /** @brief Replace the stored pointer.
    333        *
    334        * @param __p  The new pointer to store.
    335        *
    336        * The deleter will be invoked if a pointer is already owned.
    337        */
    338       void
    339       reset(pointer __p = pointer()) noexcept
    340       {
    341 	using std::swap;
    342 	swap(std::get<0>(_M_t), __p);
    343 	if (__p != pointer())
    344 	  get_deleter()(__p);
    345       }
    346 
    347       /// Exchange the pointer and deleter with another object.
    348       void
    349       swap(unique_ptr& __u) noexcept
    350       {
    351 	using std::swap;
    352 	swap(_M_t, __u._M_t);
    353       }
    354 
    355       // Disable copy from lvalue.
    356       unique_ptr(const unique_ptr&) = delete;
    357       unique_ptr& operator=(const unique_ptr&) = delete;
    358   };
    359 
    360   /// 20.7.1.3 unique_ptr for array objects with a runtime length
    361   // [unique.ptr.runtime]
    362   // _GLIBCXX_RESOLVE_LIB_DEFECTS
    363   // DR 740 - omit specialization for array objects with a compile time length
    364   template<typename _Tp, typename _Dp>
    365     class unique_ptr<_Tp[], _Dp>
    366     {
    367       // use SFINAE to determine whether _Del::pointer exists
    368       class _Pointer
    369       {
    370 	template<typename _Up>
    371 	  static typename _Up::pointer __test(typename _Up::pointer*);
    372 
    373 	template<typename _Up>
    374 	  static _Tp* __test(...);
    375 
    376 	typedef typename remove_reference<_Dp>::type _Del;
    377 
    378       public:
    379 	typedef decltype(__test<_Del>(0)) type;
    380       };
    381 
    382       typedef std::tuple<typename _Pointer::type, _Dp>  __tuple_type;
    383       __tuple_type                                      _M_t;
    384 
    385       template<typename _Up>
    386 	using __remove_cv = typename remove_cv<_Up>::type;
    387 
    388       // like is_base_of<_Tp, _Up> but false if unqualified types are the same
    389       template<typename _Up>
    390 	using __is_derived_Tp
    391 	  = __and_< is_base_of<_Tp, _Up>,
    392 		    __not_<is_same<__remove_cv<_Tp>, __remove_cv<_Up>>> >;
    393 
    394       template<typename _Up, typename _Ep,
    395 	       typename _Tp_pointer = typename _Pointer::type,
    396 	       typename _Up_pointer = typename unique_ptr<_Up, _Ep>::pointer>
    397 	using __safe_conversion = __and_<
    398 	    is_convertible<_Up_pointer, _Tp_pointer>,
    399 	    is_array<_Up>,
    400 	    __or_<__not_<is_pointer<_Up_pointer>>,
    401 		  __not_<is_pointer<_Tp_pointer>>,
    402 		  __not_<__is_derived_Tp<typename remove_extent<_Up>::type>>
    403 	    >
    404 	  >;
    405 
    406     public:
    407       typedef typename _Pointer::type	pointer;
    408       typedef _Tp		 	element_type;
    409       typedef _Dp                       deleter_type;
    410 
    411       // Constructors.
    412 
    413       /// Default constructor, creates a unique_ptr that owns nothing.
    414       constexpr unique_ptr() noexcept
    415       : _M_t()
    416       { static_assert(!std::is_pointer<deleter_type>::value,
    417 		      "constructed with null function pointer deleter"); }
    418 
    419       /** Takes ownership of a pointer.
    420        *
    421        * @param __p  A pointer to an array of @c element_type
    422        *
    423        * The deleter will be value-initialized.
    424        */
    425       explicit
    426       unique_ptr(pointer __p) noexcept
    427       : _M_t(__p, deleter_type())
    428       { static_assert(!is_pointer<deleter_type>::value,
    429 		      "constructed with null function pointer deleter"); }
    430 
    431       // Disable construction from convertible pointer types.
    432       template<typename _Up, typename = _Require<is_pointer<pointer>,
    433 	       is_convertible<_Up*, pointer>, __is_derived_Tp<_Up>>>
    434 	explicit
    435 	unique_ptr(_Up* __p) = delete;
    436 
    437       /** Takes ownership of a pointer.
    438        *
    439        * @param __p  A pointer to an array of @c element_type
    440        * @param __d  A reference to a deleter.
    441        *
    442        * The deleter will be initialized with @p __d
    443        */
    444       unique_ptr(pointer __p,
    445 	  typename conditional<is_reference<deleter_type>::value,
    446 	      deleter_type, const deleter_type&>::type __d) noexcept
    447       : _M_t(__p, __d) { }
    448 
    449       /** Takes ownership of a pointer.
    450        *
    451        * @param __p  A pointer to an array of @c element_type
    452        * @param __d  A reference to a deleter.
    453        *
    454        * The deleter will be initialized with @p std::move(__d)
    455        */
    456       unique_ptr(pointer __p, typename
    457 		 remove_reference<deleter_type>::type&& __d) noexcept
    458       : _M_t(std::move(__p), std::move(__d))
    459       { static_assert(!is_reference<deleter_type>::value,
    460 		      "rvalue deleter bound to reference"); }
    461 
    462       /// Move constructor.
    463       unique_ptr(unique_ptr&& __u) noexcept
    464       : _M_t(__u.release(), std::forward<deleter_type>(__u.get_deleter())) { }
    465 
    466       /// Creates a unique_ptr that owns nothing.
    467       constexpr unique_ptr(nullptr_t) noexcept : unique_ptr() { }
    468 
    469       template<typename _Up, typename _Ep,
    470 	       typename = _Require<__safe_conversion<_Up, _Ep>,
    471 		 typename conditional<is_reference<_Dp>::value,
    472 				      is_same<_Ep, _Dp>,
    473 				      is_convertible<_Ep, _Dp>>::type
    474 	       >>
    475 	unique_ptr(unique_ptr<_Up, _Ep>&& __u) noexcept
    476 	: _M_t(__u.release(), std::forward<_Ep>(__u.get_deleter()))
    477 	{ }
    478 
    479       /// Destructor, invokes the deleter if the stored pointer is not null.
    480       ~unique_ptr()
    481       {
    482 	auto& __ptr = std::get<0>(_M_t);
    483 	if (__ptr != nullptr)
    484 	  get_deleter()(__ptr);
    485 	__ptr = pointer();
    486       }
    487 
    488       // Assignment.
    489 
    490       /** @brief Move assignment operator.
    491        *
    492        * @param __u  The object to transfer ownership from.
    493        *
    494        * Invokes the deleter first if this object owns a pointer.
    495        */
    496       unique_ptr&
    497       operator=(unique_ptr&& __u) noexcept
    498       {
    499 	reset(__u.release());
    500 	get_deleter() = std::forward<deleter_type>(__u.get_deleter());
    501 	return *this;
    502       }
    503 
    504       /** @brief Assignment from another type.
    505        *
    506        * @param __u  The object to transfer ownership from, which owns a
    507        *             convertible pointer to an array object.
    508        *
    509        * Invokes the deleter first if this object owns a pointer.
    510        */
    511       template<typename _Up, typename _Ep>
    512 	typename
    513 	enable_if<__safe_conversion<_Up, _Ep>::value, unique_ptr&>::type
    514 	operator=(unique_ptr<_Up, _Ep>&& __u) noexcept
    515 	{
    516 	  reset(__u.release());
    517 	  get_deleter() = std::forward<_Ep>(__u.get_deleter());
    518 	  return *this;
    519 	}
    520 
    521       /// Reset the %unique_ptr to empty, invoking the deleter if necessary.
    522       unique_ptr&
    523       operator=(nullptr_t) noexcept
    524       {
    525 	reset();
    526 	return *this;
    527       }
    528 
    529       // Observers.
    530 
    531       /// Access an element of owned array.
    532       typename std::add_lvalue_reference<element_type>::type
    533       operator[](size_t __i) const
    534       {
    535 	_GLIBCXX_DEBUG_ASSERT(get() != pointer());
    536 	return get()[__i];
    537       }
    538 
    539       /// Return the stored pointer.
    540       pointer
    541       get() const noexcept
    542       { return std::get<0>(_M_t); }
    543 
    544       /// Return a reference to the stored deleter.
    545       deleter_type&
    546       get_deleter() noexcept
    547       { return std::get<1>(_M_t); }
    548 
    549       /// Return a reference to the stored deleter.
    550       const deleter_type&
    551       get_deleter() const noexcept
    552       { return std::get<1>(_M_t); }
    553 
    554       /// Return @c true if the stored pointer is not null.
    555       explicit operator bool() const noexcept
    556       { return get() == pointer() ? false : true; }
    557 
    558       // Modifiers.
    559 
    560       /// Release ownership of any stored pointer.
    561       pointer
    562       release() noexcept
    563       {
    564 	pointer __p = get();
    565 	std::get<0>(_M_t) = pointer();
    566 	return __p;
    567       }
    568 
    569       /** @brief Replace the stored pointer.
    570        *
    571        * @param __p  The new pointer to store.
    572        *
    573        * The deleter will be invoked if a pointer is already owned.
    574        */
    575       void
    576       reset(pointer __p = pointer()) noexcept
    577       {
    578 	using std::swap;
    579 	swap(std::get<0>(_M_t), __p);
    580 	if (__p != nullptr)
    581 	  get_deleter()(__p);
    582       }
    583 
    584       // Disable resetting from convertible pointer types.
    585       template<typename _Up, typename = _Require<is_pointer<pointer>,
    586 	       is_convertible<_Up*, pointer>, __is_derived_Tp<_Up>>>
    587 	void reset(_Up*) = delete;
    588 
    589       /// Exchange the pointer and deleter with another object.
    590       void
    591       swap(unique_ptr& __u) noexcept
    592       {
    593 	using std::swap;
    594 	swap(_M_t, __u._M_t);
    595       }
    596 
    597       // Disable copy from lvalue.
    598       unique_ptr(const unique_ptr&) = delete;
    599       unique_ptr& operator=(const unique_ptr&) = delete;
    600 
    601       // Disable construction from convertible pointer types.
    602       template<typename _Up, typename = _Require<is_pointer<pointer>,
    603 	       is_convertible<_Up*, pointer>, __is_derived_Tp<_Up>>>
    604 	unique_ptr(_Up*, typename
    605 		   conditional<is_reference<deleter_type>::value,
    606 		   deleter_type, const deleter_type&>::type) = delete;
    607 
    608       // Disable construction from convertible pointer types.
    609       template<typename _Up, typename = _Require<is_pointer<pointer>,
    610 	       is_convertible<_Up*, pointer>, __is_derived_Tp<_Up>>>
    611 	unique_ptr(_Up*, typename
    612 		   remove_reference<deleter_type>::type&&) = delete;
    613     };
    614 
    615   template<typename _Tp, typename _Dp>
    616     inline void
    617     swap(unique_ptr<_Tp, _Dp>& __x,
    618 	 unique_ptr<_Tp, _Dp>& __y) noexcept
    619     { __x.swap(__y); }
    620 
    621   template<typename _Tp, typename _Dp,
    622 	   typename _Up, typename _Ep>
    623     inline bool
    624     operator==(const unique_ptr<_Tp, _Dp>& __x,
    625 	       const unique_ptr<_Up, _Ep>& __y)
    626     { return __x.get() == __y.get(); }
    627 
    628   template<typename _Tp, typename _Dp>
    629     inline bool
    630     operator==(const unique_ptr<_Tp, _Dp>& __x, nullptr_t) noexcept
    631     { return !__x; }
    632 
    633   template<typename _Tp, typename _Dp>
    634     inline bool
    635     operator==(nullptr_t, const unique_ptr<_Tp, _Dp>& __x) noexcept
    636     { return !__x; }
    637 
    638   template<typename _Tp, typename _Dp,
    639 	   typename _Up, typename _Ep>
    640     inline bool
    641     operator!=(const unique_ptr<_Tp, _Dp>& __x,
    642 	       const unique_ptr<_Up, _Ep>& __y)
    643     { return __x.get() != __y.get(); }
    644 
    645   template<typename _Tp, typename _Dp>
    646     inline bool
    647     operator!=(const unique_ptr<_Tp, _Dp>& __x, nullptr_t) noexcept
    648     { return (bool)__x; }
    649 
    650   template<typename _Tp, typename _Dp>
    651     inline bool
    652     operator!=(nullptr_t, const unique_ptr<_Tp, _Dp>& __x) noexcept
    653     { return (bool)__x; }
    654 
    655   template<typename _Tp, typename _Dp,
    656 	   typename _Up, typename _Ep>
    657     inline bool
    658     operator<(const unique_ptr<_Tp, _Dp>& __x,
    659 	      const unique_ptr<_Up, _Ep>& __y)
    660     {
    661       typedef typename
    662 	std::common_type<typename unique_ptr<_Tp, _Dp>::pointer,
    663 	                 typename unique_ptr<_Up, _Ep>::pointer>::type _CT;
    664       return std::less<_CT>()(__x.get(), __y.get());
    665     }
    666 
    667   template<typename _Tp, typename _Dp>
    668     inline bool
    669     operator<(const unique_ptr<_Tp, _Dp>& __x, nullptr_t)
    670     { return std::less<typename unique_ptr<_Tp, _Dp>::pointer>()(__x.get(),
    671 								 nullptr); }
    672 
    673   template<typename _Tp, typename _Dp>
    674     inline bool
    675     operator<(nullptr_t, const unique_ptr<_Tp, _Dp>& __x)
    676     { return std::less<typename unique_ptr<_Tp, _Dp>::pointer>()(nullptr,
    677 								 __x.get()); }
    678 
    679   template<typename _Tp, typename _Dp,
    680 	   typename _Up, typename _Ep>
    681     inline bool
    682     operator<=(const unique_ptr<_Tp, _Dp>& __x,
    683 	       const unique_ptr<_Up, _Ep>& __y)
    684     { return !(__y < __x); }
    685 
    686   template<typename _Tp, typename _Dp>
    687     inline bool
    688     operator<=(const unique_ptr<_Tp, _Dp>& __x, nullptr_t)
    689     { return !(nullptr < __x); }
    690 
    691   template<typename _Tp, typename _Dp>
    692     inline bool
    693     operator<=(nullptr_t, const unique_ptr<_Tp, _Dp>& __x)
    694     { return !(__x < nullptr); }
    695 
    696   template<typename _Tp, typename _Dp,
    697 	   typename _Up, typename _Ep>
    698     inline bool
    699     operator>(const unique_ptr<_Tp, _Dp>& __x,
    700 	      const unique_ptr<_Up, _Ep>& __y)
    701     { return (__y < __x); }
    702 
    703   template<typename _Tp, typename _Dp>
    704     inline bool
    705     operator>(const unique_ptr<_Tp, _Dp>& __x, nullptr_t)
    706     { return std::less<typename unique_ptr<_Tp, _Dp>::pointer>()(nullptr,
    707 								 __x.get()); }
    708 
    709   template<typename _Tp, typename _Dp>
    710     inline bool
    711     operator>(nullptr_t, const unique_ptr<_Tp, _Dp>& __x)
    712     { return std::less<typename unique_ptr<_Tp, _Dp>::pointer>()(__x.get(),
    713 								 nullptr); }
    714 
    715   template<typename _Tp, typename _Dp,
    716 	   typename _Up, typename _Ep>
    717     inline bool
    718     operator>=(const unique_ptr<_Tp, _Dp>& __x,
    719 	       const unique_ptr<_Up, _Ep>& __y)
    720     { return !(__x < __y); }
    721 
    722   template<typename _Tp, typename _Dp>
    723     inline bool
    724     operator>=(const unique_ptr<_Tp, _Dp>& __x, nullptr_t)
    725     { return !(__x < nullptr); }
    726 
    727   template<typename _Tp, typename _Dp>
    728     inline bool
    729     operator>=(nullptr_t, const unique_ptr<_Tp, _Dp>& __x)
    730     { return !(nullptr < __x); }
    731 
    732   /// std::hash specialization for unique_ptr.
    733   template<typename _Tp, typename _Dp>
    734     struct hash<unique_ptr<_Tp, _Dp>>
    735     : public __hash_base<size_t, unique_ptr<_Tp, _Dp>>
    736     {
    737       size_t
    738       operator()(const unique_ptr<_Tp, _Dp>& __u) const noexcept
    739       {
    740 	typedef unique_ptr<_Tp, _Dp> _UP;
    741 	return std::hash<typename _UP::pointer>()(__u.get());
    742       }
    743     };
    744 
    745 #if __cplusplus > 201103L
    746   template<typename _Tp>
    747     struct _MakeUniq
    748     { typedef unique_ptr<_Tp> __single_object; };
    749 
    750   template<typename _Tp>
    751     struct _MakeUniq<_Tp[]>
    752     { typedef unique_ptr<_Tp[]> __array; };
    753 
    754   template<typename _Tp, size_t _Bound>
    755     struct _MakeUniq<_Tp[_Bound]>
    756     { struct __invalid_type { }; };
    757 
    758   /// std::make_unique for single objects
    759   template<typename _Tp, typename... _Args>
    760     inline typename _MakeUniq<_Tp>::__single_object
    761     make_unique(_Args&&... __args)
    762     { return unique_ptr<_Tp>(new _Tp(std::forward<_Args>(__args)...)); }
    763 
    764   /// std::make_unique for arrays of unknown bound
    765   template<typename _Tp>
    766     inline typename _MakeUniq<_Tp>::__array
    767     make_unique(size_t __num)
    768     { return unique_ptr<_Tp>(new typename remove_extent<_Tp>::type[__num]()); }
    769 
    770   /// Disable std::make_unique for arrays of known bound
    771   template<typename _Tp, typename... _Args>
    772     inline typename _MakeUniq<_Tp>::__invalid_type
    773     make_unique(_Args&&...) = delete;
    774 #endif
    775 
    776   // @} group pointer_abstractions
    777 
    778 _GLIBCXX_END_NAMESPACE_VERSION
    779 } // namespace
    780 
    781 #endif /* _UNIQUE_PTR_H */
    782