diff options
Diffstat (limited to 'contrib/src/boost/intrusive/pointer_rebind.hpp')
-rw-r--r-- | contrib/src/boost/intrusive/pointer_rebind.hpp | 188 |
1 files changed, 188 insertions, 0 deletions
diff --git a/contrib/src/boost/intrusive/pointer_rebind.hpp b/contrib/src/boost/intrusive/pointer_rebind.hpp new file mode 100644 index 0000000..9592e06 --- /dev/null +++ b/contrib/src/boost/intrusive/pointer_rebind.hpp @@ -0,0 +1,188 @@ +////////////////////////////////////////////////////////////////////////////// +// +// (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/intrusive for documentation. +// +////////////////////////////////////////////////////////////////////////////// + +#ifndef BOOST_INTRUSIVE_POINTER_REBIND_HPP +#define BOOST_INTRUSIVE_POINTER_REBIND_HPP + +#ifndef BOOST_INTRUSIVE_DETAIL_WORKAROUND_HPP +#include <boost/intrusive/detail/workaround.hpp> +#endif //BOOST_INTRUSIVE_DETAIL_WORKAROUND_HPP + +#ifndef BOOST_CONFIG_HPP +# include <boost/config.hpp> +#endif + +#if defined(BOOST_HAS_PRAGMA_ONCE) +# pragma once +#endif + +namespace boost { +namespace intrusive { + +/////////////////////////// +//struct pointer_rebind_mode +/////////////////////////// +template <typename Ptr, typename U> +struct pointer_has_rebind +{ + template <typename V> struct any + { any(const V&) { } }; + + template <typename X> + static char test(int, typename X::template rebind<U>*); + + template <typename X> + static int test(any<int>, void*); + + static const bool value = (1 == sizeof(test<Ptr>(0, 0))); +}; + +template <typename Ptr, typename U> +struct pointer_has_rebind_other +{ + template <typename V> struct any + { any(const V&) { } }; + + template <typename X> + static char test(int, typename X::template rebind<U>::other*); + + template <typename X> + static int test(any<int>, void*); + + static const bool value = (1 == sizeof(test<Ptr>(0, 0))); +}; + +template <typename Ptr, typename U> +struct pointer_rebind_mode +{ + static const unsigned int rebind = (unsigned int)pointer_has_rebind<Ptr, U>::value; + static const unsigned int rebind_other = (unsigned int)pointer_has_rebind_other<Ptr, U>::value; + static const unsigned int mode = rebind + rebind*rebind_other; +}; + +//////////////////////// +//struct pointer_rebinder +//////////////////////// +template <typename Ptr, typename U, unsigned int RebindMode> +struct pointer_rebinder; + +// Implementation of pointer_rebinder<U>::type if Ptr has +// its own rebind<U>::other type (C++03) +template <typename Ptr, typename U> +struct pointer_rebinder< Ptr, U, 2u > +{ + typedef typename Ptr::template rebind<U>::other type; +}; + +// Implementation of pointer_rebinder<U>::type if Ptr has +// its own rebind template. +template <typename Ptr, typename U> +struct pointer_rebinder< Ptr, U, 1u > +{ + typedef typename Ptr::template rebind<U> type; +}; + +// Specialization of pointer_rebinder if Ptr does not +// have its own rebind template but has a the form Ptr<A, An...>, +// where An... comprises zero or more type parameters. +// Many types fit this form, hence many pointers will get a +// reasonable default for rebind. +#if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) + +template <template <class, class...> class Ptr, typename A, class... An, class U> +struct pointer_rebinder<Ptr<A, An...>, U, 0u > +{ + typedef Ptr<U, An...> type; +}; + +//Needed for non-conforming compilers like GCC 4.3 +template <template <class> class Ptr, typename A, class U> +struct pointer_rebinder<Ptr<A>, U, 0u > +{ + typedef Ptr<U> type; +}; + +#else //C++03 compilers + +template <template <class> class Ptr //0arg + , typename A + , class U> +struct pointer_rebinder<Ptr<A>, U, 0u> +{ typedef Ptr<U> type; }; + +template <template <class, class> class Ptr //1arg + , typename A, class P0 + , class U> +struct pointer_rebinder<Ptr<A, P0>, U, 0u> +{ typedef Ptr<U, P0> type; }; + +template <template <class, class, class> class Ptr //2arg + , typename A, class P0, class P1 + , class U> +struct pointer_rebinder<Ptr<A, P0, P1>, U, 0u> +{ typedef Ptr<U, P0, P1> type; }; + +template <template <class, class, class, class> class Ptr //3arg + , typename A, class P0, class P1, class P2 + , class U> +struct pointer_rebinder<Ptr<A, P0, P1, P2>, U, 0u> +{ typedef Ptr<U, P0, P1, P2> type; }; + +template <template <class, class, class, class, class> class Ptr //4arg + , typename A, class P0, class P1, class P2, class P3 + , class U> +struct pointer_rebinder<Ptr<A, P0, P1, P2, P3>, U, 0u> +{ typedef Ptr<U, P0, P1, P2, P3> type; }; + +template <template <class, class, class, class, class, class> class Ptr //5arg + , typename A, class P0, class P1, class P2, class P3, class P4 + , class U> +struct pointer_rebinder<Ptr<A, P0, P1, P2, P3, P4>, U, 0u> +{ typedef Ptr<U, P0, P1, P2, P3, P4> type; }; + +template <template <class, class, class, class, class, class, class> class Ptr //6arg + , typename A, class P0, class P1, class P2, class P3, class P4, class P5 + , class U> +struct pointer_rebinder<Ptr<A, P0, P1, P2, P3, P4, P5>, U, 0u> +{ typedef Ptr<U, P0, P1, P2, P3, P4, P5> type; }; + +template <template <class, class, class, class, class, class, class, class> class Ptr //7arg + , typename A, class P0, class P1, class P2, class P3, class P4, class P5, class P6 + , class U> +struct pointer_rebinder<Ptr<A, P0, P1, P2, P3, P4, P5, P6>, U, 0u> +{ typedef Ptr<U, P0, P1, P2, P3, P4, P5, P6> type; }; + +template <template <class, class, class, class, class, class, class, class, class> class Ptr //8arg + , typename A, class P0, class P1, class P2, class P3, class P4, class P5, class P6, class P7 + , class U> +struct pointer_rebinder<Ptr<A, P0, P1, P2, P3, P4, P5, P6, P7>, U, 0u> +{ typedef Ptr<U, P0, P1, P2, P3, P4, P5, P6, P7> type; }; + +template <template <class, class, class, class, class, class, class, class, class, class> class Ptr //9arg + , typename A, class P0, class P1, class P2, class P3, class P4, class P5, class P6, class P7, class P8 + , class U> +struct pointer_rebinder<Ptr<A, P0, P1, P2, P3, P4, P5, P6, P7, P8>, U, 0u> +{ typedef Ptr<U, P0, P1, P2, P3, P4, P5, P6, P7, P8> type; }; + +#endif //!defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) + +template <typename Ptr, typename U> +struct pointer_rebind + : public pointer_rebinder<Ptr, U, pointer_rebind_mode<Ptr, U>::mode> +{}; + +template <typename T, typename U> +struct pointer_rebind<T*, U> +{ typedef U* type; }; + +} //namespace container { +} //namespace boost { + +#endif // defined(BOOST_INTRUSIVE_POINTER_REBIND_HPP) |