diff --git a/include/boost/type_traits/intrinsics.hpp b/include/boost/type_traits/intrinsics.hpp index b1f553c..1799240 100644 --- a/include/boost/type_traits/intrinsics.hpp +++ b/include/boost/type_traits/intrinsics.hpp @@ -82,6 +82,7 @@ #if (defined(BOOST_MSVC) && defined(BOOST_MSVC_FULL_VER) && (BOOST_MSVC_FULL_VER >=140050215))\ || (defined(BOOST_INTEL) && defined(_MSC_VER) && (_MSC_VER >= 1500)) # include +# include # define BOOST_IS_UNION(T) __is_union(T) # define BOOST_IS_POD(T) (__is_pod(T) && __has_trivial_constructor(T)) @@ -98,7 +99,7 @@ # define BOOST_IS_ABSTRACT(T) __is_abstract(T) # define BOOST_IS_BASE_OF(T,U) (__is_base_of(T,U) && !is_same::value) # define BOOST_IS_CLASS(T) __is_class(T) -# define BOOST_IS_CONVERTIBLE(T,U) ((__is_convertible_to(T,U) || is_same::value) && !__is_abstract(U)) +# define BOOST_IS_CONVERTIBLE(T,U) ((__is_convertible_to(T,U) || (is_same::value && !is_function::value)) && !__is_abstract(U)) # define BOOST_IS_ENUM(T) __is_enum(T) // This one doesn't quite always do the right thing: // # define BOOST_IS_POLYMORPHIC(T) __is_polymorphic(T) @@ -222,11 +223,6 @@ # define BOOST_ALIGNMENT_OF(T) __alignof__(T) # endif -#ifdef __GXX_EXPERIMENTAL_CXX0X__ -# include -# define BOOST_IS_CONVERTIBLE(T,U) (std::is_convertible::value) -#endif - # define BOOST_HAS_TYPE_TRAITS_INTRINSICS #endif @@ -293,3 +289,4 @@ + diff --git a/include/boost/type_traits/is_convertible.hpp b/include/boost/type_traits/is_convertible.hpp index 72df747..ca56c85 100644 --- a/include/boost/type_traits/is_convertible.hpp +++ b/include/boost/type_traits/is_convertible.hpp @@ -17,13 +17,13 @@ #include #include #include -#include #include #include #include #ifndef BOOST_NO_IS_ABSTRACT #include #endif +#include #include #include @@ -69,7 +69,7 @@ struct does_conversion_exist { static no_type BOOST_TT_DECL _m_check(...); static yes_type BOOST_TT_DECL _m_check(To); - static typename add_rvalue_reference::type _m_from; + static typename add_lvalue_reference::type _m_from; enum { value = sizeof( _m_check(_m_from) ) == sizeof(yes_type) }; }; }; @@ -107,7 +107,7 @@ struct is_convertible_impl static ::boost::type_traits::yes_type BOOST_TT_DECL _m_check(T); }; - static typename add_rvalue_reference::type _m_from; + static typename add_lvalue_reference::type _m_from; static bool const value = sizeof( checker::_m_check(_m_from) ) == sizeof(::boost::type_traits::yes_type); #pragma option pop @@ -134,10 +134,17 @@ template struct checker template struct is_convertible_basic_impl { + typedef typename add_lvalue_reference::type lvalue_type; typedef typename add_rvalue_reference::type rvalue_type; - static From _m_from; - static bool const value = sizeof( boost::detail::checker::_m_check(static_cast(_m_from), 0) ) + static lvalue_type _m_from; + static bool const value = +#if !defined(BOOST_NO_RVALUE_REFERENCES) && ((__GNUC__ > 4) || ((__GNUC__ == 4) && (__GNUC_MINOR__ > 6))) + sizeof( boost::detail::checker::_m_check(static_cast(_m_from), 0) ) == sizeof(::boost::type_traits::yes_type); +#else + sizeof( boost::detail::checker::_m_check(_m_from, 0) ) + == sizeof(::boost::type_traits::yes_type); +#endif }; #elif (defined(__EDG_VERSION__) && (__EDG_VERSION__ >= 245) && !defined(__ICL)) \ @@ -167,11 +174,16 @@ struct is_convertible_basic_impl { static ::boost::type_traits::no_type BOOST_TT_DECL _m_check(any_conversion ...); static ::boost::type_traits::yes_type BOOST_TT_DECL _m_check(To, int); + typedef typename add_lvalue_reference::type lvalue_type; typedef typename add_rvalue_reference::type rvalue_type; - static From _m_from; + static lvalue_type _m_from; BOOST_STATIC_CONSTANT(bool, value = +#ifndef BOOST_NO_RVALUE_REFERENCES sizeof( _m_check(static_cast(_m_from), 0) ) == sizeof(::boost::type_traits::yes_type) +#else + sizeof( _m_check(_m_from, 0) ) == sizeof(::boost::type_traits::yes_type) +#endif ); }; @@ -194,13 +206,18 @@ struct is_convertible_basic_impl template static ::boost::type_traits::no_type BOOST_TT_DECL _m_check(any_conversion, float, T); static ::boost::type_traits::yes_type BOOST_TT_DECL _m_check(To, int, int); - typedef typename add_rvalue_reference::type rvalue_type; - static From _m_from; + typedef typename add_lvalue_reference::type lvalue_type; + typedef typename add_rvalue_reference::type rvalue_type; + static lvalue_type _m_from; // Static constants sometime cause the conversion of _m_from to To to be // called. This doesn't happen with an enum. enum { value = +#ifndef BOOST_NO_RVALUE_REFERENCES sizeof( _m_check(static_cast(_m_from), 0, 0) ) == sizeof(::boost::type_traits::yes_type) +#else + sizeof( _m_check(_m_from, 0, 0) ) == sizeof(::boost::type_traits::yes_type) +#endif }; }; @@ -228,11 +245,16 @@ struct is_convertible_basic_impl_aux { static ::boost::type_traits::no_type BOOST_TT_DECL _m_check(any_conversion ...); static ::boost::type_traits::yes_type BOOST_TT_DECL _m_check(To, int); + typedef typename add_lvalue_reference::type lvalue_type; typedef typename add_rvalue_reference::type rvalue_type; - static From _m_from; + static lvalue_type _m_from; BOOST_STATIC_CONSTANT(bool, value = +#ifndef BOOST_NO_RVALUE_REFERENCES sizeof( _m_check(static_cast(_m_from), 0) ) == sizeof(::boost::type_traits::yes_type) +#else + sizeof( _m_check(_m_from, 0) ) == sizeof(::boost::type_traits::yes_type) +#endif ); }; @@ -241,10 +263,15 @@ struct is_convertible_basic_impl_aux { static ::boost::type_traits::no_type BOOST_TT_DECL _m_check(...); static ::boost::type_traits::yes_type BOOST_TT_DECL _m_check(To); - typedef typename add_rvalue_reference::type rvalue_type; - static From _m_from; + typedef typename add_lvalue_reference::type lvalue_type; + typedef typename add_rvalue_reference::type rvalue_type; + static lvalue_type _m_from; BOOST_STATIC_CONSTANT(bool, value = +#ifndef BOOST_NO_RVALUE_REFERENCES sizeof( _m_check(static_cast(_m_from)) ) == sizeof(::boost::type_traits::yes_type) +#else + sizeof( _m_check(_m_from) ) == sizeof(::boost::type_traits::yes_type) +#endif ); }; @@ -266,8 +293,9 @@ struct is_convertible_basic_impl { static ::boost::type_traits::no_type BOOST_TT_DECL _m_check(...); static ::boost::type_traits::yes_type BOOST_TT_DECL _m_check(To); + typedef typename add_lvalue_reference::type lvalue_type; typedef typename add_rvalue_reference::type rvalue_type; - static From _m_from; + static lvalue_type _m_from; #ifdef BOOST_MSVC #pragma warning(push) #pragma warning(disable:4244) @@ -276,7 +304,11 @@ struct is_convertible_basic_impl #endif #endif BOOST_STATIC_CONSTANT(bool, value = +#ifndef BOOST_NO_RVALUE_REFERENCES sizeof( _m_check(static_cast(_m_from)) ) == sizeof(::boost::type_traits::yes_type) +#else + sizeof( _m_check(_m_from) ) == sizeof(::boost::type_traits::yes_type) +#endif ); #ifdef BOOST_MSVC #pragma warning(pop) @@ -290,11 +322,10 @@ struct is_convertible_basic_impl template struct is_convertible_impl { - typedef typename add_reference::type ref_type; enum { value = (::boost::type_traits::ice_and< ::boost::type_traits::ice_or< - ::boost::detail::is_convertible_basic_impl::value, + ::boost::detail::is_convertible_basic_impl::value, ::boost::is_void::value >::value, ::boost::type_traits::ice_not< @@ -309,11 +340,10 @@ struct is_convertible_impl template struct is_convertible_impl { - typedef typename add_reference::type ref_type; BOOST_STATIC_CONSTANT(bool, value = (::boost::type_traits::ice_and< ::boost::type_traits::ice_or< - ::boost::detail::is_convertible_basic_impl::value, + ::boost::detail::is_convertible_basic_impl::value, ::boost::is_void::value >::value, ::boost::type_traits::ice_not< diff --git a/include/boost/type_traits/is_function.hpp b/include/boost/type_traits/is_function.hpp index 2cb1bb9..1e837ce 100644 --- a/include/boost/type_traits/is_function.hpp +++ b/include/boost/type_traits/is_function.hpp @@ -83,6 +83,11 @@ struct is_function_impl template struct is_function_impl : public false_type {}; +#ifndef BOOST_NO_RVALUE_REFERENCES +template +struct is_function_impl : public false_type +{}; +#endif #endif #endif diff --git a/test/is_convertible_test.cpp b/test/is_convertible_test.cpp index fd05b4b..ce309e7 100644 --- a/test/is_convertible_test.cpp +++ b/test/is_convertible_test.cpp @@ -103,8 +103,11 @@ BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), tr #ifndef BOOST_NO_RVALUE_REFERENCES BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); +#if !defined(__GNUC__) || ((__GNUC__ > 4) || ((__GNUC__ == 4) && (__GNUC_MINOR__ > 6))) +// Machinary required to support this, not available prior to gcc-4.7.0: BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), false); #endif +#endif BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); @@ -115,16 +118,6 @@ BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), false); BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); -BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), false); -BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); -BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); -BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); -BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); -BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); -#ifndef BOOST_NO_RVALUE_REFERENCES -BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); -#endif - BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), false); BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); diff --git a/test/tricky_function_type_test.cpp b/test/tricky_function_type_test.cpp index 30ba24c..5c339d1 100644 --- a/test/tricky_function_type_test.cpp +++ b/test/tricky_function_type_test.cpp @@ -97,6 +97,13 @@ BOOST_CHECK_INTEGRAL_CONSTANT(::tt::is_member_function_pointer::value, t typedef void (test_abc1::*vproc3)(int, char, long, long, ...)const; BOOST_CHECK_INTEGRAL_CONSTANT(::tt::is_member_function_pointer::value, true); +BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), false); +BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); +BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); +BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); +BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); +BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); + TT_TEST_END diff --git a/test/tricky_rvalue_test.cpp b/test/tricky_rvalue_test.cpp index a768f10..1659f1f 100644 --- a/test/tricky_rvalue_test.cpp +++ b/test/tricky_rvalue_test.cpp @@ -13,6 +13,7 @@ # include # include # include +# include #endif TT_TEST_BEGIN(rvalue_reference_test) @@ -22,6 +23,7 @@ BOOST_CHECK_INTEGRAL_CONSTANT(::tt::is_reference::value, true); BOOST_CHECK_INTEGRAL_CONSTANT(::tt::is_rvalue_reference::value, false); BOOST_CHECK_INTEGRAL_CONSTANT(::tt::is_rvalue_reference::value, true); BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), false); +BOOST_CHECK_INTEGRAL_CONSTANT((::tt::is_convertible::value), true); #endif TT_TEST_END