diff --git a/include/boost/unordered/detail/allocate.hpp b/include/boost/unordered/detail/allocate.hpp index 319c9cd5..73cff77c 100644 --- a/include/boost/unordered/detail/allocate.hpp +++ b/include/boost/unordered/detail/allocate.hpp @@ -412,11 +412,69 @@ namespace boost { namespace unordered { namespace detail { namespace boost { namespace unordered { namespace detail { - // TODO: Does this match std::allocator_traits::rebind_alloc? + template + struct rebind_alloc; + +#if !defined(BOOST_NO_CXX11_VARIADIC_TEMPLATES) + + template class Alloc, + typename U, typename T, typename... Args> + struct rebind_alloc, T> + { + typedef Alloc type; + }; + +#else + + template < + template class Alloc, + typename U, typename T> + struct rebind_alloc, T> + { + typedef Alloc type; + }; + + template < + template class Alloc, + typename U, typename T, + typename A0> + struct rebind_alloc, T> + { + typedef Alloc type; + }; + + template < + template class Alloc, + typename U, typename T, + typename A0, typename A1> + struct rebind_alloc, T> + { + typedef Alloc type; + }; + +#endif + template struct rebind_wrap { - typedef typename Alloc::BOOST_NESTED_TEMPLATE rebind::other type; + template + static choice1::type test(choice1, + typename X::BOOST_NESTED_TEMPLATE rebind::other* = 0); + template + static choice2::type test(choice2, void* = 0); + + enum { value = (1 == sizeof(test(choose()))) }; + + struct fallback { + template + struct rebind { + typedef typename rebind_alloc::type other; + }; + }; + + typedef typename boost::detail::if_true:: + BOOST_NESTED_TEMPLATE then + ::type::BOOST_NESTED_TEMPLATE rebind::other type; }; # if defined(BOOST_MSVC) && BOOST_MSVC <= 1400 @@ -606,7 +664,14 @@ namespace boost { namespace unordered { namespace detail { typedef BOOST_UNORDERED_DEFAULT_TYPE(Alloc, size_type, std::size_t) size_type; - // TODO: rebind_alloc and rebind_traits +#if !defined(BOOST_NO_CXX11_TEMPLATE_ALIASES) + template + using rebind_alloc = typename rebind_wrap::type; + + template + using rebind_traits = + boost::unordered::detail::allocator_traits >; +#endif static pointer allocate(Alloc& a, size_type n) { return a.allocate(n); } diff --git a/test/objects/cxx11_allocator.hpp b/test/objects/cxx11_allocator.hpp index 11f67808..1c638be2 100644 --- a/test/objects/cxx11_allocator.hpp +++ b/test/objects/cxx11_allocator.hpp @@ -201,9 +201,9 @@ namespace test public move_allocator_base, Flags { - template struct rebind { - typedef cxx11_allocator other; - }; + //template struct rebind { + // typedef cxx11_allocator other; + //}; explicit cxx11_allocator(int t = 0) : cxx11_allocator_base(t) diff --git a/test/objects/minimal.hpp b/test/objects/minimal.hpp index b876aa20..d8e8a7eb 100644 --- a/test/objects/minimal.hpp +++ b/test/objects/minimal.hpp @@ -447,7 +447,7 @@ namespace minimal { public: typedef T value_type; - template struct rebind { typedef cxx11_allocator other; }; + //template struct rebind { typedef cxx11_allocator other; }; cxx11_allocator() {} template cxx11_allocator(cxx11_allocator const&) {}