diff --git a/include/boost/intrusive/detail/utilities.hpp b/include/boost/intrusive/detail/utilities.hpp index c121c2c..6b4ef26 100644 --- a/include/boost/intrusive/detail/utilities.hpp +++ b/include/boost/intrusive/detail/utilities.hpp @@ -366,22 +366,45 @@ void destructor_impl(Hook &, detail::link_dispatch) // floor_log2 Dispatcher //////////////////////////// -#if defined(_MSC_VER) && (_MSC_VER >= 1400) +#if defined(_MSC_VER) && (_MSC_VER >= 1300) }}} //namespace boost::intrusive::detail - #include + //Use _BitScanReverseXX intrinsics + + #if defined(_M_X64) || defined(_M_AMD64) || defined(_M_IA64) //64 bit target + #define BOOST_INTRUSIVE_BSR_INTRINSIC_64_BIT + #endif + + #ifndef __INTRIN_H_ // Avoid including any windows system header + #ifdef __cplusplus + extern "C" { + #endif // __cplusplus + + #if defined(BOOST_INTRUSIVE_BSR_INTRINSIC_64_BIT) //64 bit target + unsigned char _BitScanReverse64(unsigned long *index, unsigned __int64 mask); + #pragma intrinsic(_BitScanReverse64) + #else //32 bit target + unsigned char _BitScanReverse(unsigned long *index, unsigned long mask); + #pragma intrinsic(_BitScanReverse) + #endif + + #ifdef __cplusplus + } + #endif // __cplusplus + #endif // __INTRIN_H_ + + #ifdef BOOST_INTRUSIVE_BSR_INTRINSIC_64_BIT + #define BOOST_INTRUSIVE_BSR_INTRINSIC _BitScanReverse64 + #undef BOOST_INTRUSIVE_BSR_INTRINSIC_64_BIT + #else + #define BOOST_INTRUSIVE_BSR_INTRINSIC _BitScanReverse + #endif namespace boost { namespace intrusive { namespace detail { - #if defined(_M_X64) || defined(_M_AMD64) || defined(_M_IA64) //64 bit target - #define BOOST_INTRUSIVE_BSR_INTRINSIC _BitScanReverse64 - #else //32 bit target - #define BOOST_INTRUSIVE_BSR_INTRINSIC _BitScanReverse - #endif - inline std::size_t floor_log2 (std::size_t x) { unsigned long log2; @@ -391,19 +414,6 @@ void destructor_impl(Hook &, detail::link_dispatch) #undef BOOST_INTRUSIVE_BSR_INTRINSIC -#elif defined(_MSC_VER) //visual 2003 - - inline std::size_t floor_log2 (std::size_t x) - { - unsigned long log2; - __asm - { - bsr eax, x - mov log2, eax - } - return static_cast(log2); - } - #elif defined(__GNUC__) && ((__GNUC__ >= 4) || (__GNUC__ == 3 && __GNUC_MINOR__ >= 4)) //GCC >=3.4 #if SIZE_MAX > UINT_MAX