1
0
forked from boostorg/move

Extracted default_delete into its own header.

Extracted meta utilities used only by unique_ptr and friends to its own "unique_ptr_meta_utils.hpp" header.
This commit is contained in:
Ion Gaztañaga
2014-09-02 16:28:17 +02:00
parent 19d35253cf
commit 90be9ebe22
8 changed files with 815 additions and 263 deletions

View File

@ -0,0 +1,173 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2014-2014. Distributed under the Boost
// Software License, Version 1.0. (See accompanying file
// LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
//
// See http://www.boost.org/libs/move for documentation.
//
//////////////////////////////////////////////////////////////////////////////
#ifndef BOOST_MOVE_DEFAULT_DELETE_HPP_INCLUDED
#define BOOST_MOVE_DEFAULT_DELETE_HPP_INCLUDED
#include <boost/move/detail/config_begin.hpp>
#include <boost/move/detail/workaround.hpp>
#include <boost/move/detail/unique_ptr_meta_utils.hpp>
#include <boost/move/utility_core.hpp>
#include <boost/static_assert.hpp>
#include <cstddef> //For std::size_t
//!\file
//! Describes the default deleter (destruction policy) of <tt>unique_ptr</tt>: <tt>default_delete</tt>.
namespace boost{
namespace move_upd {
namespace bmupmu = ::boost::move_upmu;
////////////////////////////////////////
//// enable_def_del
////////////////////////////////////////
//compatible with a pointer type T*:
//When either Y* is convertible to T*
//Y is U[N] and T is U cv []
template<class U, class T>
struct def_del_compatible_cond
: bmupmu::is_convertible<U*, T*>
{};
template<class U, class T, std::size_t N>
struct def_del_compatible_cond<U[N], T[]>
: def_del_compatible_cond<U[], T[]>
{};
template<class U, class T, class Type = bmupmu::nat>
struct enable_def_del
: bmupmu::enable_if_c<def_del_compatible_cond<U, T>::value, Type>
{};
////////////////////////////////////////
//// enable_defdel_call
////////////////////////////////////////
//When 2nd is T[N], 1st(*)[N] shall be convertible to T(*)[N];
//When 2nd is T[], 1st(*)[] shall be convertible to T(*)[];
//Otherwise, 1st* shall be convertible to 2nd*.
template<class U, class T, class Type = bmupmu::nat>
struct enable_defdel_call
: public enable_def_del<U, T, Type>
{};
template<class U, class T, class Type>
struct enable_defdel_call<U, T[], Type>
: public enable_def_del<U[], T[], Type>
{};
template<class U, class T, class Type, std::size_t N>
struct enable_defdel_call<U, T[N], Type>
: public enable_def_del<U[N], T[N], Type>
{};
////////////////////////////////////////
//// Some bool literal zero conversion utilities
////////////////////////////////////////
struct bool_conversion {int for_bool; int for_arg(); };
typedef int bool_conversion::* explicit_bool_arg;
#if !defined(BOOST_NO_CXX11_NULLPTR)
typedef std::nullptr_t nullptr_type;
#else
typedef int (bool_conversion::*nullptr_type)();
#endif
} //namespace move_upd {
namespace movelib {
namespace bmupd = boost::move_upd;
namespace bmupmu = boost::move_detail;
//!The class template <tt>default_delete</tt> serves as the default deleter
//!(destruction policy) for the class template <tt>unique_ptr</tt>.
//!
//! \tparam T The type to be deleted. It may be an incomplete type
template <class T>
struct default_delete
{
//! Default constructor.
//!
BOOST_CONSTEXPR default_delete()
//Avoid "defaulted on its first declaration must not have an exception-specification" error for GCC 4.6
#if !defined(BOOST_GCC) || (BOOST_GCC < 40600 && BOOST_GCC >= 40700) || defined(BOOST_MOVE_DOXYGEN_INVOKED)
BOOST_NOEXCEPT
#endif
#if !defined(BOOST_NO_CXX11_DEFAULTED_FUNCTIONS) || defined(BOOST_MOVE_DOXYGEN_INVOKED)
= default;
#else
{};
#endif
#if defined(BOOST_MOVE_DOXYGEN_INVOKED)
default_delete(const default_delete&) BOOST_NOEXCEPT = default;
default_delete &operator=(const default_delete&) BOOST_NOEXCEPT = default;
#else
typedef typename bmupmu::remove_extent<T>::type element_type;
#endif
//! <b>Effects</b>: Constructs a default_delete object from another <tt>default_delete<U></tt> object.
//!
//! <b>Remarks</b>: This constructor shall not participate in overload resolution unless:
//! - If T is not an array type and U* is implicitly convertible to T*.
//! - If T is an array type and U* is a more CV qualified pointer to remove_extent<T>::type.
template <class U>
default_delete(const default_delete<U>&
BOOST_MOVE_DOCIGN(BOOST_MOVE_I typename bmupd::enable_def_del<U BOOST_MOVE_I T>::type* =0)
) BOOST_NOEXCEPT
{}
//! <b>Effects</b>: Constructs a default_delete object from another <tt>default_delete<U></tt> object.
//!
//! <b>Remarks</b>: This constructor shall not participate in overload resolution unless:
//! - If T is not an array type and U* is implicitly convertible to T*.
//! - If T is an array type and U* is a more CV qualified pointer to remove_extent<T>::type.
template <class U>
BOOST_MOVE_DOC1ST(default_delete&,
typename bmupd::enable_def_del<U BOOST_MOVE_I T BOOST_MOVE_I default_delete &>::type)
operator=(const default_delete<U>&) BOOST_NOEXCEPT
{ return *this; }
//! <b>Effects</b>: if T is not an array type, calls <tt>delete</tt> on static_cast<T*>(ptr),
//! otherwise calls <tt>delete[]</tt> on static_cast<remove_extent<T>::type*>(ptr).
//!
//! <b>Remarks</b>: If U is an incomplete type, the program is ill-formed.
//! This operator shall not participate in overload resolution unless:
//! - T is not an array type and U* is convertible to T*, OR
//! - T is an array type, and remove_cv<U>::type is the same type as
//! remove_cv<remove_extent<T>::type>::type and U* is convertible to remove_extent<T>::type*.
template <class U>
BOOST_MOVE_DOC1ST(void, typename bmupd::enable_defdel_call<U BOOST_MOVE_I T BOOST_MOVE_I void>::type)
operator()(U* ptr) const BOOST_NOEXCEPT
{
//U must be a complete type
BOOST_STATIC_ASSERT(sizeof(U) > 0);
element_type * const p = static_cast<element_type*>(ptr);
bmupmu::is_array<T>::value ? delete [] p : delete p;
}
//! <b>Effects</b>: Same as <tt>(*this)(static_cast<element_type*>(nullptr))</tt>.
//!
void operator()(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type)) const BOOST_NOEXCEPT
{ BOOST_STATIC_ASSERT(sizeof(element_type) > 0); }
};
} //namespace movelib {
} //namespace boost{
#include <boost/move/detail/config_end.hpp>
#endif //#ifndef BOOST_MOVE_DEFAULT_DELETE_HPP_INCLUDED

View File

@ -0,0 +1,523 @@
//////////////////////////////////////////////////////////////////////////////
//
// (C) Copyright Ion Gaztanaga 2012-2012.
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
//
// See http://www.boost.org/libs/move for documentation.
//
//////////////////////////////////////////////////////////////////////////////
//! \file
#ifndef BOOST_MOVE_UNIQUE_PTR_DETAIL_META_UTILS_HPP
#define BOOST_MOVE_UNIQUE_PTR_DETAIL_META_UTILS_HPP
#include <cstddef> //for std::size_t
//Small meta-typetraits to support move
namespace boost {
#ifdef BOOST_NO_CXX11_RVALUE_REFERENCES
//Forward declare boost::rv
template <class T> class rv;
#endif
namespace move_upmu {
//////////////////////////////////////
// nat
//////////////////////////////////////
struct nat{};
//////////////////////////////////////
// natify
//////////////////////////////////////
template <class T> struct natify{};
//////////////////////////////////////
// if_c
//////////////////////////////////////
template<bool C, typename T1, typename T2>
struct if_c
{
typedef T1 type;
};
template<typename T1, typename T2>
struct if_c<false,T1,T2>
{
typedef T2 type;
};
//////////////////////////////////////
// if_
//////////////////////////////////////
template<typename T1, typename T2, typename T3>
struct if_ : if_c<0 != T1::value, T2, T3>
{};
//enable_if_
template <bool B, class T = nat>
struct enable_if_c
{
typedef T type;
};
//////////////////////////////////////
// enable_if_c
//////////////////////////////////////
template <class T>
struct enable_if_c<false, T> {};
//////////////////////////////////////
// enable_if
//////////////////////////////////////
template <class Cond, class T = nat>
struct enable_if : public enable_if_c<Cond::value, T> {};
//////////////////////////////////////
// remove_reference
//////////////////////////////////////
template<class T>
struct remove_reference
{
typedef T type;
};
template<class T>
struct remove_reference<T&>
{
typedef T type;
};
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
template<class T>
struct remove_reference<T&&>
{
typedef T type;
};
#else
template<class T>
struct remove_reference< rv<T> >
{
typedef T type;
};
template<class T>
struct remove_reference< rv<T> &>
{
typedef T type;
};
template<class T>
struct remove_reference< const rv<T> &>
{
typedef T type;
};
#endif
//////////////////////////////////////
// remove_const
//////////////////////////////////////
template< class T >
struct remove_const
{
typedef T type;
};
template< class T >
struct remove_const<const T>
{
typedef T type;
};
//////////////////////////////////////
// remove_volatile
//////////////////////////////////////
template< class T >
struct remove_volatile
{
typedef T type;
};
template< class T >
struct remove_volatile<volatile T>
{
typedef T type;
};
//////////////////////////////////////
// remove_cv
//////////////////////////////////////
template< class T >
struct remove_cv
{
typedef typename remove_volatile
<typename remove_const<T>::type>::type type;
};
//////////////////////////////////////
// remove_extent
//////////////////////////////////////
template<class T>
struct remove_extent
{
typedef T type;
};
template<class T>
struct remove_extent<T[]>
{
typedef T type;
};
template<class T, std::size_t N>
struct remove_extent<T[N]>
{
typedef T type;
};
//////////////////////////////////////
// extent
//////////////////////////////////////
template<class T, unsigned N = 0>
struct extent
{
static const std::size_t value = 0;
};
template<class T>
struct extent<T[], 0>
{
static const std::size_t value = 0;
};
template<class T, unsigned N>
struct extent<T[], N>
{
static const std::size_t value = extent<T, N-1>::value;
};
template<class T, std::size_t N>
struct extent<T[N], 0>
{
static const std::size_t value = N;
};
template<class T, std::size_t I, unsigned N>
struct extent<T[I], N>
{
static const std::size_t value = extent<T, N-1>::value;
};
//////////////////////////////////////
// add_lvalue_reference
//////////////////////////////////////
template<class T>
struct add_lvalue_reference
{
typedef T& type;
};
template<class T>
struct add_lvalue_reference<T&>
{
typedef T& type;
};
template<>
struct add_lvalue_reference<void>
{
typedef void type;
};
template<>
struct add_lvalue_reference<const void>
{
typedef const void type;
};
template<>
struct add_lvalue_reference<volatile void>
{
typedef volatile void type;
};
template<>
struct add_lvalue_reference<const volatile void>
{
typedef const volatile void type;
};
template<class T>
struct add_const_lvalue_reference
{
typedef typename remove_reference<T>::type t_unreferenced;
typedef const t_unreferenced t_unreferenced_const;
typedef typename add_lvalue_reference
<t_unreferenced_const>::type type;
};
//////////////////////////////////////
// is_same
//////////////////////////////////////
template<class T, class U>
struct is_same
{
static const bool value = false;
};
template<class T>
struct is_same<T, T>
{
static const bool value = true;
};
//////////////////////////////////////
// is_pointer
//////////////////////////////////////
template< class T >
struct is_pointer
{
static const bool value = false;
};
template< class T >
struct is_pointer<T*>
{
static const bool value = true;
};
//////////////////////////////////////
// is_reference
//////////////////////////////////////
template< class T >
struct is_reference
{
static const bool value = false;
};
template< class T >
struct is_reference<T&>
{
static const bool value = true;
};
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
template< class T >
struct is_reference<T&&>
{
static const bool value = true;
};
#endif
//////////////////////////////////////
// is_lvalue_reference
//////////////////////////////////////
template<class T>
struct is_lvalue_reference
{
static const bool value = false;
};
template<class T>
struct is_lvalue_reference<T&>
{
static const bool value = true;
};
//////////////////////////////////////
// is_array
//////////////////////////////////////
template<class T>
struct is_array
{
static const bool value = false;
};
template<class T>
struct is_array<T[]>
{
static const bool value = true;
};
template<class T, std::size_t N>
struct is_array<T[N]>
{
static const bool value = true;
};
//////////////////////////////////////
// has_pointer_type
//////////////////////////////////////
template <class T>
struct has_pointer_type
{
struct two { char c[2]; };
template <class U> static two test(...);
template <class U> static char test(typename U::pointer* = 0);
static const bool value = sizeof(test<T>(0)) == 1;
};
//////////////////////////////////////
// pointer_type
//////////////////////////////////////
template <class T, class D, bool = has_pointer_type<D>::value>
struct pointer_type_imp
{
typedef typename D::pointer type;
};
template <class T, class D>
struct pointer_type_imp<T, D, false>
{
typedef typename remove_extent<T>::type* type;
};
template <class T, class D>
struct pointer_type
{
typedef typename pointer_type_imp
<typename remove_extent<T>::type, typename remove_reference<D>::type>::type type;
};
//////////////////////////////////////
// is_convertible
//////////////////////////////////////
#if defined(_MSC_VER) && (_MSC_VER >= 1400)
//use intrinsic since in MSVC
//overaligned types can't go through ellipsis
template <class T, class U>
struct is_convertible
{
static const bool value = __is_convertible_to(T, U);
};
#else
template <class T, class U>
class is_convertible
{
typedef typename add_lvalue_reference<T>::type t_reference;
typedef char true_t;
class false_t { char dummy[2]; };
static false_t dispatch(...);
static true_t dispatch(U);
static t_reference trigger();
public:
static const bool value = sizeof(dispatch(trigger())) == sizeof(true_t);
};
#endif
//////////////////////////////////////
// is_unary_function
//////////////////////////////////////
#if defined(BOOST_MSVC) || defined(__BORLANDC_)
#define BOOST_MOVE_TT_DECL __cdecl
#else
#define BOOST_MOVE_TT_DECL
#endif
#if defined(_MSC_EXTENSIONS) && !defined(__BORLAND__) && !defined(_WIN64) && !defined(_M_ARM) && !defined(UNDER_CE)
#define BOOST_MOVE_TT_TEST_MSC_FUNC_SIGS
#endif
template <typename T>
struct is_unary_function_impl
{ static const bool value = false; };
// avoid duplicate definitions of is_unary_function_impl
#ifndef BOOST_MOVE_TT_TEST_MSC_FUNC_SIGS
template <typename R>
struct is_unary_function_impl<R (*)()>
{ static const bool value = true; };
template <typename R>
struct is_unary_function_impl<R (*)(...)>
{ static const bool value = true; };
#else // BOOST_MOVE_TT_TEST_MSC_FUNC_SIGS
template <typename R>
struct is_unary_function_impl<R (__stdcall*)()>
{ static const bool value = true; };
#ifndef _MANAGED
template <typename R>
struct is_unary_function_impl<R (__fastcall*)()>
{ static const bool value = true; };
#endif
template <typename R>
struct is_unary_function_impl<R (__cdecl*)()>
{ static const bool value = true; };
template <typename R>
struct is_unary_function_impl<R (__cdecl*)(...)>
{ static const bool value = true; };
#endif
// avoid duplicate definitions of is_unary_function_impl
#ifndef BOOST_MOVE_TT_TEST_MSC_FUNC_SIGS
template <typename R, class T0>
struct is_unary_function_impl<R (*)(T0)>
{ static const bool value = true; };
template <typename R, class T0>
struct is_unary_function_impl<R (*)(T0...)>
{ static const bool value = true; };
#else // BOOST_MOVE_TT_TEST_MSC_FUNC_SIGS
template <typename R, class T0>
struct is_unary_function_impl<R (__stdcall*)(T0)>
{ static const bool value = true; };
#ifndef _MANAGED
template <typename R, class T0>
struct is_unary_function_impl<R (__fastcall*)(T0)>
{ static const bool value = true; };
#endif
template <typename R, class T0>
struct is_unary_function_impl<R (__cdecl*)(T0)>
{ static const bool value = true; };
template <typename R, class T0>
struct is_unary_function_impl<R (__cdecl*)(T0...)>
{ static const bool value = true; };
#endif
template <typename T>
struct is_unary_function_impl<T&>
{ static const bool value = false; };
template<typename T>
struct is_unary_function
{ static const bool value = is_unary_function_impl<T>::value; };
} //namespace move_upmu {
} //namespace boost {
#endif //#ifndef BOOST_MOVE_UNIQUE_PTR_DETAIL_META_UTILS_HPP

View File

@ -13,8 +13,9 @@
#include <boost/move/detail/config_begin.hpp>
#include <boost/move/detail/workaround.hpp>
#include <boost/move/detail/unique_ptr_meta_utils.hpp>
#include <boost/move/default_delete.hpp>
#include <boost/move/utility_core.hpp>
#include <boost/move/detail/meta_utils.hpp>
#include <boost/static_assert.hpp>
#include <boost/assert.hpp>
@ -36,8 +37,7 @@
//! cv-less T and cv-less U are the same type and T is more CV qualified than U.
namespace boost{
namespace move_detail {
namespace move_upd {
////////////////////////////////////////////
// deleter types
@ -58,25 +58,25 @@ class is_noncopyable
template <class D>
struct deleter_types
{
typedef typename add_lvalue_reference<D>::type del_ref;
typedef typename add_const_lvalue_reference<D>::type del_cref;
typedef typename bmupmu::add_lvalue_reference<D>::type del_ref;
typedef typename bmupmu::add_const_lvalue_reference<D>::type del_cref;
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
typedef typename if_c
< is_lvalue_reference<D>::value, D, del_cref >::type deleter_arg_type1;
typedef typename remove_reference<D>::type && deleter_arg_type2;
typedef typename bmupmu::if_c
< bmupmu::is_lvalue_reference<D>::value, D, del_cref >::type deleter_arg_type1;
typedef typename bmupmu::remove_reference<D>::type && deleter_arg_type2;
#else
typedef typename if_c
< is_noncopyable<D>::value, nat, del_cref>::type non_ref_deleter_arg1;
typedef typename if_c< is_lvalue_reference<D>::value
, D, non_ref_deleter_arg1 >::type deleter_arg_type1;
typedef ::boost::rv<D> & deleter_arg_type2;
typedef typename bmupmu::if_c
< is_noncopyable<D>::value, bmupmu::nat, del_cref>::type non_ref_deleter_arg1;
typedef typename bmupmu::if_c< bmupmu::is_lvalue_reference<D>::value
, D, non_ref_deleter_arg1 >::type deleter_arg_type1;
typedef ::boost::rv<D> & deleter_arg_type2;
#endif
};
////////////////////////////////////////////
// unique_ptr_data
////////////////////////////////////////////
template <class P, class D, bool = is_unary_function<D>::value || is_reference<D>::value >
template <class P, class D, bool = bmupmu::is_unary_function<D>::value || bmupmu::is_reference<D>::value >
struct unique_ptr_data
{
typedef typename deleter_types<D>::deleter_arg_type1 deleter_arg_type1;
@ -155,11 +155,11 @@ struct unique_ptr_data<P, D, false>
template <typename T>
struct get_element_type
{
struct DefaultWrap { typedef natify<T> element_type; };
struct DefaultWrap { typedef bmupmu::natify<T> element_type; };
template <typename X> static char test(int, typename X::element_type*);
template <typename X> static int test(...);
static const bool value = (1 == sizeof(test<T>(0, 0)));
typedef typename if_c<value, T, DefaultWrap>::type::element_type type;
typedef typename bmupmu::if_c<value, T, DefaultWrap>::type::element_type type;
};
template<class T>
@ -170,18 +170,17 @@ struct get_element_type<T*>
template<class T>
struct get_cvelement
{
typedef typename remove_cv<typename get_element_type<T>::type>::type type;
};
: bmupmu::remove_cv<typename get_element_type<T>::type>
{};
template <class P1, class P2>
struct is_same_cvelement_and_convertible
{
typedef typename remove_reference<P1>::type arg1;
typedef typename remove_reference<P2>::type arg2;
typedef typename bmupmu::remove_reference<P1>::type arg1;
typedef typename bmupmu::remove_reference<P2>::type arg2;
static const bool same_cvless =
is_same<typename get_cvelement<arg1>::type,typename get_cvelement<arg2>::type>::value;
static const bool value = same_cvless && is_convertible<arg1, arg2>::value;
bmupmu::is_same<typename get_cvelement<arg1>::type,typename get_cvelement<arg2>::type>::value;
static const bool value = same_cvless && bmupmu::is_convertible<arg1, arg2>::value;
};
template<bool IsArray, class FromPointer, class ThisPointer>
@ -191,63 +190,17 @@ struct is_unique_ptr_convertible
template<class FromPointer, class ThisPointer>
struct is_unique_ptr_convertible<false, FromPointer, ThisPointer>
: is_convertible<FromPointer, ThisPointer>
{};
////////////////////////////////////////
//// enable_def_del
////////////////////////////////////////
//compatible with a pointer type T*:
//When either Y* is convertible to T*
//Y is U[N] and T is U cv []
template<class U, class T>
struct def_del_compatible_cond
{
static const bool value = is_convertible<U*, T*>::value;
};
template<class U, class T, std::size_t N>
struct def_del_compatible_cond<U[N], T[]>
{
static const bool value = def_del_compatible_cond<U[], T[]>::value;
};
template<class U, class T, class Type = nat>
struct enable_def_del
: enable_if_c<def_del_compatible_cond<U, T>::value, Type>
{};
////////////////////////////////////////
//// enable_defdel_call
////////////////////////////////////////
//When 2nd is T[N], 1st(*)[N] shall be convertible to T[N]*;
//When 2nd is T[], 1st(*)[] shall be convertible to T[]*;
//Otherwise, 1st* shall be convertible to 2nd*.
template<class U, class T, class Type = nat>
struct enable_defdel_call
: public enable_def_del<U, T, Type>
{};
template<class U, class T, class Type>
struct enable_defdel_call<U, T[], Type>
: public enable_def_del<U[], T[], Type>
{};
template<class U, class T, class Type, std::size_t N>
struct enable_defdel_call<U, T[N], Type>
: public enable_def_del<U[N], T[N], Type>
: bmupmu::is_convertible<FromPointer, ThisPointer>
{};
////////////////////////////////////////
//// enable_up_moveconv_assign
////////////////////////////////////////
template<class T, class FromPointer, class ThisPointer, class Type = nat>
template<class T, class FromPointer, class ThisPointer, class Type = bmupmu::nat>
struct enable_up_ptr
: enable_if_c< is_unique_ptr_convertible < is_array<T>::value, FromPointer, ThisPointer>::value, Type>
: bmupmu::enable_if_c< is_unique_ptr_convertible
< bmupmu::is_array<T>::value, FromPointer, ThisPointer>::value, Type>
{};
////////////////////////////////////////
@ -257,53 +210,40 @@ struct enable_up_ptr
template<class T, class D, class U, class E>
struct unique_moveconvert_assignable
{
static const bool value = (extent<T>::value == extent<U>::value)&& is_unique_ptr_convertible
<is_array<T>::value, typename pointer_type<U, E>::type, typename pointer_type<T, D>::type>::value;
static const bool value = (bmupmu::extent<T>::value == bmupmu::extent<U>::value) && is_unique_ptr_convertible
< bmupmu::is_array<T>::value
, typename bmupmu::pointer_type<U, E>::type, typename bmupmu::pointer_type<T, D>::type>::value;
};
template<class T, class D, class U, class E, std::size_t N>
struct unique_moveconvert_assignable<T[], D, U[N], E>
{
static const bool value = unique_moveconvert_assignable<T[], D, U[], E>::value;
};
/*
template<class T, class D, class U, class E, std::size_t N>
struct unique_moveconvert_assignable<T[N], D, U[], E>
{
static const bool value = unique_moveconvert_assignable<nat[], D, U[], E>::value;
};
: unique_moveconvert_assignable<T[], D, U[], E>
{};
template<class T, class D, class U, class E, std::size_t N, std::size_t M>
struct unique_moveconvert_assignable<T[N], D, U[M], E>
{
static const bool value = (M == N) && unique_moveconvert_assignable<T[], D, U[], E>::value;
};
*/
template<class T, class D, class U, class E, class Type = nat>
template<class T, class D, class U, class E, class Type = bmupmu::nat>
struct enable_up_moveconv_assign
: enable_if_c<unique_moveconvert_assignable<T, D, U, E>::value, Type>
: bmupmu::enable_if_c<unique_moveconvert_assignable<T, D, U, E>::value, Type>
{};
////////////////////////////////////////
//// enable_up_moveconv_constr
////////////////////////////////////////
template<class D, class E, bool IsReference = is_reference<D>::value>
template<class D, class E, bool IsReference = bmupmu::is_reference<D>::value>
struct unique_deleter_is_initializable
{
static const bool value = is_same<D, E>::value;
};
: bmupmu::is_same<D, E>
{};
template <class T, class U>
class is_rvalue_convertible
{
#ifndef BOOST_NO_CXX11_RVALUE_REFERENCES
typedef typename remove_reference<T>::type&& t_from;
typedef typename bmupmu::remove_reference<T>::type&& t_from;
#else
typedef typename if_c
< has_move_emulation_enabled<T>::value && !is_reference<T>::value
, boost::rv<T>&
, typename add_lvalue_reference<T>::type
typedef typename bmupmu::if_c
< ::boost::has_move_emulation_enabled<T>::value && !bmupmu::is_reference<T>::value
, ::boost::rv<T>&
, typename bmupmu::add_lvalue_reference<T>::type
>::type t_from;
#endif
@ -339,103 +279,16 @@ struct unique_deleter_is_initializable<D, E, false>
#endif
};
template<class T, class D, class U, class E, class Type = nat>
template<class T, class D, class U, class E, class Type = bmupmu::nat>
struct enable_up_moveconv_constr
: enable_if_c<unique_moveconvert_assignable<T, D, U, E>::value &&
unique_deleter_is_initializable<D, E>::value, Type>
: bmupmu::enable_if_c<unique_moveconvert_assignable<T, D, U, E>::value &&
unique_deleter_is_initializable<D, E>::value, Type>
{};
////////////////////////////////////////
//// Some bool literal zero conversion utilities
////////////////////////////////////////
struct bool_conversion {int for_bool; int for_arg(); };
typedef int bool_conversion::* explicit_bool_arg;
#if !defined(BOOST_NO_CXX11_NULLPTR)
typedef std::nullptr_t nullptr_type;
#else
typedef int (bool_conversion::*nullptr_type)();
#endif
} //namespace move_detail {
} //namespace move_upd {
namespace movelib {
namespace bmd = boost::move_detail;
//!The class template <tt>default_delete</tt> serves as the default deleter
//!(destruction policy) for the class template <tt>unique_ptr</tt>.
template <class T>
struct default_delete
{
//! Default constructor.
//!
BOOST_CONSTEXPR default_delete()
//Avoid "defaulted on its first declaration must not have an exception-specification" error for GCC 4.6
#if !defined(BOOST_GCC) || (BOOST_GCC < 40600 && BOOST_GCC >= 40700) || defined(BOOST_MOVE_DOXYGEN_INVOKED)
BOOST_NOEXCEPT
#endif
#if !defined(BOOST_NO_CXX11_DEFAULTED_FUNCTIONS) || defined(BOOST_MOVE_DOXYGEN_INVOKED)
= default;
#else
{};
#endif
#if defined(BOOST_MOVE_DOXYGEN_INVOKED)
default_delete(const default_delete&) BOOST_NOEXCEPT = default;
default_delete &operator=(const default_delete&) BOOST_NOEXCEPT = default;
#else
typedef typename bmd::remove_extent<T>::type element_type;
#endif
//! <b>Effects</b>: Constructs a default_delete object from another <tt>default_delete<U></tt> object.
//!
//! <b>Remarks</b>: This constructor shall not participate in overload resolution unless:
//! - If T is not an array type and U* is implicitly convertible to T*.
//! - If T is an array type and U* is a more CV qualified pointer to remove_extent<T>::type.
template <class U>
default_delete(const default_delete<U>&
BOOST_MOVE_DOCIGN(BOOST_MOVE_I typename bmd::enable_def_del<U BOOST_MOVE_I T>::type* =0)
) BOOST_NOEXCEPT
{}
//! <b>Effects</b>: Constructs a default_delete object from another <tt>default_delete<U></tt> object.
//!
//! <b>Remarks</b>: This constructor shall not participate in overload resolution unless:
//! - If T is not an array type and U* is implicitly convertible to T*.
//! - If T is an array type and U* is a more CV qualified pointer to remove_extent<T>::type.
template <class U>
BOOST_MOVE_DOC1ST(default_delete&,
typename bmd::enable_def_del<U BOOST_MOVE_I T BOOST_MOVE_I default_delete &>::type)
operator=(const default_delete<U>&) BOOST_NOEXCEPT
{ return *this; }
//! <b>Effects</b>: if T is not an array type, calls <tt>delete</tt> on static_cast<T*>(ptr),
//! otherwise calls <tt>delete[]</tt> on static_cast<remove_extent<T>::type*>(ptr).
//!
//! <b>Remarks</b>: If U is an incomplete type, the program is ill-formed.
//! This operator shall not participate in overload resolution unless:
//! - T is not an array type and U* is convertible to T*, OR
//! - T is an array type, and remove_cv<U>::type is the same type as
//! remove_cv<remove_extent<T>::type>::type and U* is convertible to remove_extent<T>::type*.
template <class U>
BOOST_MOVE_DOC1ST(void, typename bmd::enable_defdel_call<U BOOST_MOVE_I T BOOST_MOVE_I void>::type)
operator()(U* ptr) const BOOST_NOEXCEPT
{
//U must be a complete type
BOOST_STATIC_ASSERT(sizeof(U) > 0);
element_type * const p = static_cast<element_type*>(ptr);
bmd::is_array<T>::value ? delete [] p : delete p;
}
//! <b>Effects</b>: Same as <tt>(*this)(static_cast<element_type*>(nullptr))</tt>.
//!
void operator()(BOOST_MOVE_DOC0PTR(bmd::nullptr_type)) const BOOST_NOEXCEPT
{ BOOST_STATIC_ASSERT(sizeof(element_type) > 0); }
};
//! A unique pointer is an object that owns another object and
//! manages that other object through a pointer.
//!
@ -491,11 +344,11 @@ class unique_ptr
#else
BOOST_MOVABLE_BUT_NOT_COPYABLE(unique_ptr)
typedef move_detail::pointer_type<T, D > pointer_type_obtainer;
typedef bmd::unique_ptr_data
typedef bmupmu::pointer_type<T, D > pointer_type_obtainer;
typedef bmupd::unique_ptr_data
<typename pointer_type_obtainer::type, D> data_type;
typedef typename bmd::deleter_types<D>::deleter_arg_type1 deleter_arg_type1;
typedef typename bmd::deleter_types<D>::deleter_arg_type2 deleter_arg_type2;
typedef typename bmupd::deleter_types<D>::deleter_arg_type1 deleter_arg_type1;
typedef typename bmupd::deleter_types<D>::deleter_arg_type2 deleter_arg_type2;
data_type m_data;
#endif
@ -506,7 +359,7 @@ class unique_ptr
typedef typename BOOST_MOVE_SEEDOC(pointer_type_obtainer::type) pointer;
//! If T is an array type, then element_type is equal to T. Otherwise, if T is a type
//! in the form U[], element_type is equal to U.
typedef typename BOOST_MOVE_SEEDOC(bmd::remove_extent<T>::type) element_type;
typedef typename BOOST_MOVE_SEEDOC(bmupmu::remove_extent<T>::type) element_type;
typedef D deleter_type;
//! <b>Requires</b>: D shall satisfy the requirements of DefaultConstructible, and
@ -524,19 +377,19 @@ class unique_ptr
{
//If this constructor is instantiated with a pointer type or reference type
//for the template argument D, the program is ill-formed.
BOOST_STATIC_ASSERT(!bmd::is_pointer<D>::value);
BOOST_STATIC_ASSERT(!bmd::is_reference<D>::value);
BOOST_STATIC_ASSERT(!bmupmu::is_pointer<D>::value);
BOOST_STATIC_ASSERT(!bmupmu::is_reference<D>::value);
}
//! <b>Effects</b>: Same as <tt>unique_ptr()</tt> (default constructor).
//!
BOOST_CONSTEXPR unique_ptr(BOOST_MOVE_DOC0PTR(bmd::nullptr_type)) BOOST_NOEXCEPT
BOOST_CONSTEXPR unique_ptr(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type)) BOOST_NOEXCEPT
: m_data()
{
//If this constructor is instantiated with a pointer type or reference type
//for the template argument D, the program is ill-formed.
BOOST_STATIC_ASSERT(!bmd::is_pointer<D>::value);
BOOST_STATIC_ASSERT(!bmd::is_reference<D>::value);
BOOST_STATIC_ASSERT(!bmupmu::is_pointer<D>::value);
BOOST_STATIC_ASSERT(!bmupmu::is_reference<D>::value);
}
//! <b>Requires</b>: D shall satisfy the requirements of DefaultConstructible, and
@ -554,14 +407,14 @@ class unique_ptr
//! - If T is an array type and Pointer is a more CV qualified pointer to element_type.
template<class Pointer>
explicit unique_ptr(Pointer p
BOOST_MOVE_DOCIGN(BOOST_MOVE_I typename bmd::enable_up_ptr<T BOOST_MOVE_I Pointer BOOST_MOVE_I pointer>::type* =0)
BOOST_MOVE_DOCIGN(BOOST_MOVE_I typename bmupd::enable_up_ptr<T BOOST_MOVE_I Pointer BOOST_MOVE_I pointer>::type* =0)
) BOOST_NOEXCEPT
: m_data(p)
{
//If this constructor is instantiated with a pointer type or reference type
//for the template argument D, the program is ill-formed.
BOOST_STATIC_ASSERT(!bmd::is_pointer<D>::value);
BOOST_STATIC_ASSERT(!bmd::is_reference<D>::value);
BOOST_STATIC_ASSERT(!bmupmu::is_pointer<D>::value);
BOOST_STATIC_ASSERT(!bmupmu::is_reference<D>::value);
}
//!The signature of this constructor depends upon whether D is a reference type.
@ -588,14 +441,14 @@ class unique_ptr
//! - If T is an array type and Pointer is a more CV qualified pointer to element_type.
template<class Pointer>
unique_ptr(Pointer p, BOOST_MOVE_SEEDOC(deleter_arg_type1) d1
BOOST_MOVE_DOCIGN(BOOST_MOVE_I typename bmd::enable_up_ptr<T BOOST_MOVE_I Pointer BOOST_MOVE_I pointer>::type* =0)
BOOST_MOVE_DOCIGN(BOOST_MOVE_I typename bmupd::enable_up_ptr<T BOOST_MOVE_I Pointer BOOST_MOVE_I pointer>::type* =0)
) BOOST_NOEXCEPT
: m_data(p, d1)
{}
//! <b>Effects</b>: Same effects as <tt>template<class Pointer> unique_ptr(Pointer p, deleter_arg_type1 d1)</tt>
//! and additionally <tt>get() == nullptr</tt>
unique_ptr(BOOST_MOVE_DOC0PTR(bmd::nullptr_type), BOOST_MOVE_SEEDOC(deleter_arg_type1) d1) BOOST_NOEXCEPT
unique_ptr(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type), BOOST_MOVE_SEEDOC(deleter_arg_type1) d1) BOOST_NOEXCEPT
: m_data(pointer(), d1)
{}
@ -621,14 +474,14 @@ class unique_ptr
//! - If T is an array type and Pointer is a more CV qualified pointer to element_type.
template<class Pointer>
unique_ptr(Pointer p, BOOST_MOVE_SEEDOC(deleter_arg_type2) d2
BOOST_MOVE_DOCIGN(BOOST_MOVE_I typename bmd::enable_up_ptr<T BOOST_MOVE_I Pointer BOOST_MOVE_I pointer>::type* =0)
BOOST_MOVE_DOCIGN(BOOST_MOVE_I typename bmupd::enable_up_ptr<T BOOST_MOVE_I Pointer BOOST_MOVE_I pointer>::type* =0)
) BOOST_NOEXCEPT
: m_data(p, ::boost::move(d2))
{}
//! <b>Effects</b>: Same effects as <tt>template<class Pointer> unique_ptr(Pointer p, deleter_arg_type2 d2)</tt>
//! and additionally <tt>get() == nullptr</tt>
unique_ptr(BOOST_MOVE_DOC0PTR(bmd::nullptr_type), BOOST_MOVE_SEEDOC(deleter_arg_type2) d2) BOOST_NOEXCEPT
unique_ptr(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type), BOOST_MOVE_SEEDOC(deleter_arg_type2) d2) BOOST_NOEXCEPT
: m_data(pointer(), ::boost::move(d2))
{}
@ -663,7 +516,7 @@ class unique_ptr
//! returns a reference to the stored deleter that was constructed from <tt>u.get_deleter()</tt>.
template <class U, class E>
unique_ptr( BOOST_RV_REF_BEG unique_ptr<U, E> BOOST_RV_REF_END u
BOOST_MOVE_DOCIGN(BOOST_MOVE_I typename bmd::enable_up_moveconv_constr<T BOOST_MOVE_I D BOOST_MOVE_I U BOOST_MOVE_I E>::type* =0)
BOOST_MOVE_DOCIGN(BOOST_MOVE_I typename bmupd::enable_up_moveconv_constr<T BOOST_MOVE_I D BOOST_MOVE_I U BOOST_MOVE_I E>::type* =0)
) BOOST_NOEXCEPT
: m_data(u.release(), ::boost::move_if_not_lvalue_reference<E>(u.get_deleter()))
{}
@ -706,7 +559,7 @@ class unique_ptr
//!
//! <b>Returns</b>: *this.
template <class U, class E>
BOOST_MOVE_DOC1ST(unique_ptr&, typename bmd::enable_up_moveconv_assign
BOOST_MOVE_DOC1ST(unique_ptr&, typename bmupd::enable_up_moveconv_assign
<T BOOST_MOVE_I D BOOST_MOVE_I U BOOST_MOVE_I E BOOST_MOVE_I unique_ptr &>::type)
operator=(BOOST_RV_REF_BEG unique_ptr<U, E> BOOST_RV_REF_END u) BOOST_NOEXCEPT
{
@ -720,7 +573,7 @@ class unique_ptr
//! <b>Postcondition</b>: <tt>get() == nullptr</tt>
//!
//! <b>Returns</b>: *this.
unique_ptr& operator=(BOOST_MOVE_DOC0PTR(bmd::nullptr_type)) BOOST_NOEXCEPT
unique_ptr& operator=(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type)) BOOST_NOEXCEPT
{ this->reset(); return *this; }
//! <b>Requires</b>: <tt>get() != nullptr</tt>.
@ -728,10 +581,10 @@ class unique_ptr
//! <b>Returns</b>: <tt>*get()</tt>.
//!
//! <b>Remarks</b: If T is an array type, the program is ill-formed.
BOOST_MOVE_DOC1ST(element_type&, typename bmd::add_lvalue_reference<element_type>::type)
BOOST_MOVE_DOC1ST(element_type&, typename bmupmu::add_lvalue_reference<element_type>::type)
operator*() const BOOST_NOEXCEPT
{
BOOST_STATIC_ASSERT((!bmd::is_array<T>::value));
BOOST_STATIC_ASSERT((!bmupmu::is_array<T>::value));
return *m_data.m_p;
}
@ -740,10 +593,10 @@ class unique_ptr
//! <b>Returns</b>: <tt>get()[i]</tt>.
//!
//! <b>Remarks</b: If T is not an array type, the program is ill-formed.
BOOST_MOVE_DOC1ST(element_type&, typename bmd::add_lvalue_reference<element_type>::type)
BOOST_MOVE_DOC1ST(element_type&, typename bmupmu::add_lvalue_reference<element_type>::type)
operator[](std::size_t i) const BOOST_NOEXCEPT
{
BOOST_ASSERT( bmd::extent<T>::value == 0 || i < bmd::extent<T>::value );
BOOST_ASSERT( bmupmu::extent<T>::value == 0 || i < bmupmu::extent<T>::value );
BOOST_ASSERT(m_data.m_p);
return m_data.m_p[i];
}
@ -757,7 +610,7 @@ class unique_ptr
//! <b>Remarks</b: If T is an array type, the program is ill-formed.
pointer operator->() const BOOST_NOEXCEPT
{
BOOST_STATIC_ASSERT((!bmd::is_array<T>::value));
BOOST_STATIC_ASSERT((!bmupmu::is_array<T>::value));
BOOST_ASSERT(m_data.m_p);
return m_data.m_p;
}
@ -769,13 +622,13 @@ class unique_ptr
//! <b>Returns</b>: A reference to the stored deleter.
//!
BOOST_MOVE_DOC1ST(D&, typename bmd::add_lvalue_reference<D>::type)
BOOST_MOVE_DOC1ST(D&, typename bmupmu::add_lvalue_reference<D>::type)
get_deleter() BOOST_NOEXCEPT
{ return m_data.deleter(); }
//! <b>Returns</b>: A reference to the stored deleter.
//!
BOOST_MOVE_DOC1ST(const D&, typename bmd::add_const_lvalue_reference<D>::type)
BOOST_MOVE_DOC1ST(const D&, typename bmupmu::add_const_lvalue_reference<D>::type)
get_deleter() const BOOST_NOEXCEPT
{ return m_data.deleter(); }
@ -784,13 +637,13 @@ class unique_ptr
//!
explicit operator bool
#else
operator bmd::explicit_bool_arg
operator bmupd::explicit_bool_arg
#endif
()const BOOST_NOEXCEPT
{
return m_data.m_p
? &bmd::bool_conversion::for_bool
: bmd::explicit_bool_arg(0);
? &bmupd::bool_conversion::for_bool
: bmupd::explicit_bool_arg(0);
}
//! <b>Postcondition</b>: <tt>get() == nullptr</tt>.
@ -817,7 +670,7 @@ class unique_ptr
//! - If T is not an array type and Pointer is implicitly convertible to pointer.
//! - If T is an array type and Pointer is a more CV qualified pointer to element_type.
template<class Pointer>
BOOST_MOVE_DOC1ST(void, typename bmd::enable_up_ptr<T BOOST_MOVE_I Pointer BOOST_MOVE_I pointer BOOST_MOVE_I void>::type)
BOOST_MOVE_DOC1ST(void, typename bmupd::enable_up_ptr<T BOOST_MOVE_I Pointer BOOST_MOVE_I pointer BOOST_MOVE_I void>::type)
reset(Pointer p) BOOST_NOEXCEPT
{
pointer tmp = m_data.m_p;
@ -839,7 +692,7 @@ class unique_ptr
//! <b>Effects</b>: Same as <tt>reset()</tt>
//!
void reset(BOOST_MOVE_DOC0PTR(bmd::nullptr_type)) BOOST_NOEXCEPT
void reset(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type)) BOOST_NOEXCEPT
{ this->reset(); }
//! <b>Requires</b>: <tt>get_deleter()</tt> shall be swappable and shall not throw an exception under swap.
@ -847,7 +700,7 @@ class unique_ptr
//! <b>Effects</b>: Invokes swap on the stored pointers and on the stored deleters of *this and u.
void swap(unique_ptr& u) BOOST_NOEXCEPT
{
using bmd::swap;
using bmupmu::swap;
swap(m_data.m_p, u.m_data.m_p);
swap(m_data.deleter(), u.m_data.deleter());
}
@ -900,76 +753,76 @@ inline bool operator>=(const unique_ptr<T1, D1> &x, const unique_ptr<T2, D2> &y)
//! <b>Returns</b>:!x.
//!
template <class T, class D>
inline bool operator==(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmd::nullptr_type)) BOOST_NOEXCEPT
inline bool operator==(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmupd::nullptr_type)) BOOST_NOEXCEPT
{ return !x; }
//! <b>Returns</b>:!x.
//!
template <class T, class D>
inline bool operator==(BOOST_MOVE_DOC0PTR(bmd::nullptr_type), const unique_ptr<T, D> &x) BOOST_NOEXCEPT
inline bool operator==(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type), const unique_ptr<T, D> &x) BOOST_NOEXCEPT
{ return !x; }
//! <b>Returns</b>: (bool)x.
//!
template <class T, class D>
inline bool operator!=(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmd::nullptr_type)) BOOST_NOEXCEPT
inline bool operator!=(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmupd::nullptr_type)) BOOST_NOEXCEPT
{ return !!x; }
//! <b>Returns</b>: (bool)x.
//!
template <class T, class D>
inline bool operator!=(BOOST_MOVE_DOC0PTR(bmd::nullptr_type), const unique_ptr<T, D> &x) BOOST_NOEXCEPT
inline bool operator!=(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type), const unique_ptr<T, D> &x) BOOST_NOEXCEPT
{ return !!x; }
//! <b>Requires</b>: <tt>operator </tt> shall induce a strict weak ordering on unique_ptr<T, D>::pointer values.
//!
//! <b>Returns</b>: Returns <tt>x.get() < pointer()</tt>.
template <class T, class D>
inline bool operator<(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmd::nullptr_type))
inline bool operator<(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmupd::nullptr_type))
{ return x.get() < typename unique_ptr<T, D>::pointer(); }
//! <b>Requires</b>: <tt>operator </tt> shall induce a strict weak ordering on unique_ptr<T, D>::pointer values.
//!
//! <b>Returns</b>: Returns <tt>pointer() < x.get()</tt>.
template <class T, class D>
inline bool operator<(BOOST_MOVE_DOC0PTR(bmd::nullptr_type), const unique_ptr<T, D> &x)
inline bool operator<(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type), const unique_ptr<T, D> &x)
{ return typename unique_ptr<T, D>::pointer() < x.get(); }
//! <b>Returns</b>: <tt>nullptr < x</tt>.
//!
template <class T, class D>
inline bool operator>(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmd::nullptr_type))
inline bool operator>(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmupd::nullptr_type))
{ return x.get() > typename unique_ptr<T, D>::pointer(); }
//! <b>Returns</b>: <tt>x < nullptr</tt>.
//!
template <class T, class D>
inline bool operator>(BOOST_MOVE_DOC0PTR(bmd::nullptr_type), const unique_ptr<T, D> &x)
inline bool operator>(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type), const unique_ptr<T, D> &x)
{ return typename unique_ptr<T, D>::pointer() > x.get(); }
//! <b>Returns</b>: <tt>!(nullptr < x)</tt>.
//!
template <class T, class D>
inline bool operator<=(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmd::nullptr_type))
{ return !(bmd::nullptr_type() < x); }
inline bool operator<=(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmupd::nullptr_type))
{ return !(bmupd::nullptr_type() < x); }
//! <b>Returns</b>: <tt>!(x < nullptr)</tt>.
//!
template <class T, class D>
inline bool operator<=(BOOST_MOVE_DOC0PTR(bmd::nullptr_type), const unique_ptr<T, D> &x)
{ return !(x < bmd::nullptr_type()); }
inline bool operator<=(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type), const unique_ptr<T, D> &x)
{ return !(x < bmupd::nullptr_type()); }
//! <b>Returns</b>: <tt>!(x < nullptr)</tt>.
//!
template <class T, class D>
inline bool operator>=(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmd::nullptr_type))
{ return !(x < bmd::nullptr_type()); }
inline bool operator>=(const unique_ptr<T, D> &x, BOOST_MOVE_DOC0PTR(bmupd::nullptr_type))
{ return !(x < bmupd::nullptr_type()); }
//! <b>Returns</b>: <tt>!(nullptr < x)</tt>.
//!
template <class T, class D>
inline bool operator>=(BOOST_MOVE_DOC0PTR(bmd::nullptr_type), const unique_ptr<T, D> &x)
{ return !(bmd::nullptr_type() < x); }
inline bool operator>=(BOOST_MOVE_DOC0PTR(bmupd::nullptr_type), const unique_ptr<T, D> &x)
{ return !(bmupd::nullptr_type() < x); }
} //namespace movelib {
} //namespace boost{

View File

@ -95,7 +95,7 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "unique_ptr_nullptr_test", "
ProjectSection(ProjectDependencies) = postProject
EndProjectSection
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "unique_ptr_test", "unique_ptr_observers_test.vcproj", "{C57C28A3-4FE0-6208-BF87-B2B61D3A7670}"
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "unique_ptr_observers_test", "unique_ptr_observers_test.vcproj", "{C57C28A3-4FE0-6208-BF87-B2B61D3A7670}"
ProjectSection(ProjectDependencies) = postProject
EndProjectSection
EndProject
@ -221,6 +221,7 @@ Global
..\..\..\..\boost\move\detail\config_begin.hpp = ..\..\..\..\boost\move\detail\config_begin.hpp
..\..\..\..\boost\move\detail\config_end.hpp = ..\..\..\..\boost\move\detail\config_end.hpp
..\..\..\..\boost\move\core.hpp = ..\..\..\..\boost\move\core.hpp
..\..\..\..\boost\move\default_delete.hpp = ..\..\..\..\boost\move\default_delete.hpp
..\..\..\..\boost\move\iterator.hpp = ..\..\..\..\boost\move\iterator.hpp
..\..\doc\Jamfile.v2 = ..\..\doc\Jamfile.v2
..\..\..\..\boost\move\make_unique.hpp = ..\..\..\..\boost\move\make_unique.hpp

View File

@ -10,7 +10,7 @@
// See http://www.boost.org/libs/move for documentation.
//
//////////////////////////////////////////////////////////////////////////////
#include <boost/move/unique_ptr.hpp>
#include <boost/move/default_delete.hpp>
#include <boost/core/lightweight_test.hpp>
//////////////////////////////////////////////

View File

@ -32,6 +32,7 @@
#include "unique_ptr_test_utils_beg.hpp"
namespace bml = ::boost::movelib;
namespace bmupmu = ::boost::move_upmu;
////////////////////////////////
// unique_ptr_ctor_move_defdel
@ -266,7 +267,7 @@ void test()
{
//Single unique_ptr
reset_counters();
BOOST_STATIC_ASSERT((boost::move_detail::is_convertible<B, A>::value));
BOOST_STATIC_ASSERT((bmupmu::is_convertible<B, A>::value));
{
bml::unique_ptr<B, move_constr_deleter<B> > s(new B);
A* p = s.get();

View File

@ -71,13 +71,13 @@ class copy_constr_deleter
template<class U>
copy_constr_deleter(const copy_constr_deleter<U>&
, typename boost::move_detail::enable_def_del<U, T>::type* =0)
, typename boost::move_upd::enable_def_del<U, T>::type* =0)
{ state_ = 5; }
explicit copy_constr_deleter(int s) : state_(s) {}
template <class U>
typename boost::move_detail::enable_def_del<U, T, copy_constr_deleter&>::type
typename boost::move_upd::enable_def_del<U, T, copy_constr_deleter&>::type
operator=(const copy_constr_deleter<U> &d)
{
state_ = d.state();
@ -117,7 +117,7 @@ class move_constr_deleter
template <class U>
move_constr_deleter(BOOST_RV_REF(move_constr_deleter<U>) d
, typename boost::move_detail::enable_def_del<U, T>::type* =0)
, typename boost::move_upd::enable_def_del<U, T>::type* =0)
: state_(d.state())
{ d.set_state(0); }
@ -129,7 +129,7 @@ class move_constr_deleter
}
template <class U>
typename boost::move_detail::enable_def_del<U, T, move_constr_deleter&>::type
typename boost::move_upd::enable_def_del<U, T, move_constr_deleter&>::type
operator=(BOOST_RV_REF(move_constr_deleter<U>) d)
{
state_ = d.state();

View File

@ -32,6 +32,7 @@
#include "unique_ptr_test_utils_beg.hpp"
namespace bml = ::boost::movelib;
namespace bmupmu = ::boost::move_upmu;
////////////////////////////////
// unique_ptr_pointer_type
@ -49,29 +50,29 @@ void test()
//Single unique_ptr
{
typedef bml::unique_ptr<int> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::pointer, int*>::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::pointer, int*>::value));
}
{
typedef bml::unique_ptr<int, Deleter> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::pointer, Deleter::pointer>::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::pointer, Deleter::pointer>::value));
}
//Unbounded array unique_ptr
{
typedef bml::unique_ptr<int[]> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::pointer, int*>::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::pointer, int*>::value));
}
{
typedef bml::unique_ptr<int[], Deleter> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::pointer, Deleter::pointer>::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::pointer, Deleter::pointer>::value));
}
//Bounded array unique_ptr
{
typedef bml::unique_ptr<int[5]> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::pointer, int*>::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::pointer, int*>::value));
}
{
typedef bml::unique_ptr<int[5], Deleter> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::pointer, Deleter::pointer>::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::pointer, Deleter::pointer>::value));
}
}
@ -91,29 +92,29 @@ void test()
//Single unique_ptr
{
typedef bml::unique_ptr<int> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::deleter_type, bml::default_delete<int> >::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::deleter_type, bml::default_delete<int> >::value));
}
{
typedef bml::unique_ptr<int, Deleter> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::deleter_type, Deleter >::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::deleter_type, Deleter >::value));
}
//Unbounded array unique_ptr
{
typedef bml::unique_ptr<int[]> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::deleter_type, bml::default_delete<int[]> >::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::deleter_type, bml::default_delete<int[]> >::value));
}
{
typedef bml::unique_ptr<int[], Deleter> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::deleter_type, Deleter >::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::deleter_type, Deleter >::value));
}
//Bounded array unique_ptr
{
typedef bml::unique_ptr<int[2]> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::deleter_type, bml::default_delete<int[2]> >::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::deleter_type, bml::default_delete<int[2]> >::value));
}
{
typedef bml::unique_ptr<int[2], Deleter> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::deleter_type, Deleter >::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::deleter_type, Deleter >::value));
}
}
@ -130,17 +131,17 @@ void test()
//Single unique_ptr
{
typedef bml::unique_ptr<const int> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::element_type, const int>::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::element_type, const int>::value));
}
//Unbounded array unique_ptr
{
typedef bml::unique_ptr<const int[]> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::element_type, const int>::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::element_type, const int>::value));
}
//Bounded array unique_ptr
{
typedef bml::unique_ptr<const int[2]> P;
BOOST_STATIC_ASSERT((boost::move_detail::is_same<P::element_type, const int>::value));
BOOST_STATIC_ASSERT((bmupmu::is_same<P::element_type, const int>::value));
}
}