From 7c9fa279f4b6649785aa9487c802cad2d4ce24e7 Mon Sep 17 00:00:00 2001 From: Matt Borland Date: Sun, 21 Mar 2021 10:05:56 +0300 Subject: [PATCH 1/3] Remove boost.predef dependency --- .../special_functions/detail/fp_traits.hpp | 118 ++++++++++-------- include/boost/math/tools/config.hpp | 1 - 2 files changed, 69 insertions(+), 50 deletions(-) diff --git a/include/boost/math/special_functions/detail/fp_traits.hpp b/include/boost/math/special_functions/detail/fp_traits.hpp index 3a69492c1..2eb67215a 100644 --- a/include/boost/math/special_functions/detail/fp_traits.hpp +++ b/include/boost/math/special_functions/detail/fp_traits.hpp @@ -25,8 +25,28 @@ With these techniques, the code could be simplified. #include #include #include + +// Determine endinaness +#ifndef BOOST_MATH_STANDALONE + #include -#include +#define BOOST_MATH_ENDIAN_BIG_BYTE BOOST_ENDIAN_BIG_BYTE +#define BOOST_MATH_ENDIAN_LITTLE_BYTE BOOST_ENDIAN_LITTLE_BYTE + +#else // Using standalone mode +#if (__cplusplus > 202000L || _MSVC_LANG > 202000L) && __has_include() + +#include +#define BOOST_MATH_ENDIAN_BIG_BYTE (std::endian::native == std::endian::big) +#define BOOST_MATH_ENDIAN_LITTLE_BYTE (std::endian::native == std::endian::little) + +#else // Does not have compliant C++20 + +#define BOOST_MATH_ENDIAN_BIG_BYTE (__BYTE_ORDER__ == __ORDER_BIG_ENDIAN__) +#define BOOST_MATH_ENDIAN_LITTLE_BYTE (__BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__) + +#endif // Standalone mode +#endif // Endian #ifdef BOOST_NO_STDC_NAMESPACE namespace std{ using ::memcpy; } @@ -178,10 +198,10 @@ template<> struct fp_traits_non_native { typedef ieee_copy_all_bits_tag method; - BOOST_STATIC_CONSTANT(uint32_t, sign = 0x80000000u); - BOOST_STATIC_CONSTANT(uint32_t, exponent = 0x7f800000); - BOOST_STATIC_CONSTANT(uint32_t, flag = 0x00000000); - BOOST_STATIC_CONSTANT(uint32_t, significand = 0x007fffff); + static constexpr uint32_t sign = 0x80000000u; + static constexpr uint32_t exponent = 0x7f800000; + static constexpr uint32_t flag = 0x00000000; + static constexpr uint32_t significand = 0x007fffff; typedef uint32_t bits; static void get_bits(float x, uint32_t& a) { std::memcpy(&a, &x, 4); } @@ -197,10 +217,10 @@ template<> struct fp_traits_non_native { typedef ieee_copy_leading_bits_tag method; - BOOST_STATIC_CONSTANT(uint32_t, sign = 0x80000000u); - BOOST_STATIC_CONSTANT(uint32_t, exponent = 0x7ff00000); - BOOST_STATIC_CONSTANT(uint32_t, flag = 0); - BOOST_STATIC_CONSTANT(uint32_t, significand = 0x000fffff); + static constexpr uint32_t sign = 0x80000000u; + static constexpr uint32_t exponent = 0x7ff00000; + static constexpr uint32_t flag = 0; + static constexpr uint32_t significand = 0x000fffff; typedef uint32_t bits; @@ -216,10 +236,10 @@ template<> struct fp_traits_non_native private: -#if BOOST_ENDIAN_BIG_BYTE - BOOST_STATIC_CONSTANT(int, offset_ = 0); -#elif BOOST_ENDIAN_LITTLE_BYTE - BOOST_STATIC_CONSTANT(int, offset_ = 4); +#if BOOST_MATH_ENDIAN_BIG_BYTE + static constexpr int offset_ = 0; +#elif BOOST_MATH_ENDIAN_LITTLE_BYTE + static constexpr int offset_ = 4; #else static_assert(false, "Endian type could not be identified"); #endif @@ -233,10 +253,10 @@ template<> struct fp_traits_non_native { typedef ieee_copy_all_bits_tag method; - static const uint64_t sign = ((uint64_t)0x80000000u) << 32; - static const uint64_t exponent = ((uint64_t)0x7ff00000) << 32; - static const uint64_t flag = 0; - static const uint64_t significand + static constexpr uint64_t sign = ((uint64_t)0x80000000u) << 32; + static constexpr uint64_t exponent = ((uint64_t)0x7ff00000) << 32; + static constexpr uint64_t flag = 0; + static constexpr uint64_t significand = (((uint64_t)0x000fffff) << 32) + ((uint64_t)0xffffffffu); typedef uint64_t bits; @@ -257,10 +277,10 @@ template<> struct fp_traits_non_native { typedef ieee_copy_leading_bits_tag method; - BOOST_STATIC_CONSTANT(uint32_t, sign = 0x80000000u); - BOOST_STATIC_CONSTANT(uint32_t, exponent = 0x7ff00000); - BOOST_STATIC_CONSTANT(uint32_t, flag = 0); - BOOST_STATIC_CONSTANT(uint32_t, significand = 0x000fffff); + static constexpr uint32_t sign = 0x80000000u; + static constexpr uint32_t exponent = 0x7ff00000; + static constexpr uint32_t flag = 0; + static constexpr uint32_t significand = 0x000fffff; typedef uint32_t bits; @@ -276,10 +296,10 @@ template<> struct fp_traits_non_native private: -#if BOOST_ENDIAN_BIG_BYTE - BOOST_STATIC_CONSTANT(int, offset_ = 0); -#elif BOOST_ENDIAN_LITTLE_BYTE - BOOST_STATIC_CONSTANT(int, offset_ = 4); +#if BOOST_MATH_ENDIAN_BIG_BYTE + static constexpr int offset_ = 0; +#elif BOOST_MATH_ENDIAN_LITTLE_BYTE + static constexpr int offset_ = 4; #else static_assert(false, "Endian type could not be identified"); #endif @@ -320,10 +340,10 @@ struct fp_traits_non_native { typedef ieee_copy_leading_bits_tag method; - BOOST_STATIC_CONSTANT(uint32_t, sign = 0x80000000u); - BOOST_STATIC_CONSTANT(uint32_t, exponent = 0x7fff0000); - BOOST_STATIC_CONSTANT(uint32_t, flag = 0x00008000); - BOOST_STATIC_CONSTANT(uint32_t, significand = 0x00007fff); + static constexpr uint32_t sign = 0x80000000u; + static constexpr uint32_t exponent = 0x7fff0000; + static constexpr uint32_t flag = 0x00008000; + static constexpr uint32_t significand = 0x00007fff; typedef uint32_t bits; @@ -371,10 +391,10 @@ struct fp_traits_non_native { typedef ieee_copy_leading_bits_tag method; - BOOST_STATIC_CONSTANT(uint32_t, sign = 0x80000000u); - BOOST_STATIC_CONSTANT(uint32_t, exponent = 0x7ff00000); - BOOST_STATIC_CONSTANT(uint32_t, flag = 0x00000000); - BOOST_STATIC_CONSTANT(uint32_t, significand = 0x000fffff); + static constexpr uint32_t sign = 0x80000000u; + static constexpr uint32_t exponent = 0x7ff00000; + static constexpr uint32_t flag = 0x00000000; + static constexpr uint32_t significand = 0x000fffff; typedef uint32_t bits; @@ -390,10 +410,10 @@ struct fp_traits_non_native private: -#if BOOST_ENDIAN_BIG_BYTE - BOOST_STATIC_CONSTANT(int, offset_ = 0); -#elif BOOST_ENDIAN_LITTLE_BYTE - BOOST_STATIC_CONSTANT(int, offset_ = 12); +#if BOOST_MATH_ENDIAN_BIG_BYTE + static constexpr int offset_ = 0; +#elif BOOST_MATH_ENDIAN_LITTLE_BYTE + static constexpr int offset_ = 12; #else static_assert(false, "Endian type could not be identified"); #endif @@ -416,10 +436,10 @@ struct fp_traits_non_native { typedef ieee_copy_leading_bits_tag method; - BOOST_STATIC_CONSTANT(uint32_t, sign = 0x80000000u); - BOOST_STATIC_CONSTANT(uint32_t, exponent = 0x7fff0000); - BOOST_STATIC_CONSTANT(uint32_t, flag = 0x00008000); - BOOST_STATIC_CONSTANT(uint32_t, significand = 0x00007fff); + static constexpr uint32_t sign = 0x80000000u; + static constexpr uint32_t exponent = 0x7fff0000; + static constexpr uint32_t flag = 0x00008000; + static constexpr uint32_t significand = 0x00007fff; // copy 1st, 2nd, 5th and 6th byte. 3rd and 4th byte are padding. @@ -452,10 +472,10 @@ struct fp_traits_non_native { typedef ieee_copy_leading_bits_tag method; - BOOST_STATIC_CONSTANT(uint32_t, sign = 0x80000000u); - BOOST_STATIC_CONSTANT(uint32_t, exponent = 0x7fff0000); - BOOST_STATIC_CONSTANT(uint32_t, flag = 0x00000000); - BOOST_STATIC_CONSTANT(uint32_t, significand = 0x0000ffff); + static constexpr uint32_t sign = 0x80000000u; + static constexpr uint32_t exponent = 0x7fff0000; + static constexpr uint32_t flag = 0x00000000; + static constexpr uint32_t significand = 0x0000ffff; typedef uint32_t bits; @@ -471,10 +491,10 @@ struct fp_traits_non_native private: -#if BOOST_ENDIAN_BIG_BYTE - BOOST_STATIC_CONSTANT(int, offset_ = 0); -#elif BOOST_ENDIAN_LITTLE_BYTE - BOOST_STATIC_CONSTANT(int, offset_ = 12); +#if BOOST_MATH_ENDIAN_BIG_BYTE + static constexpr int offset_ = 0; +#elif BOOST_MATH_ENDIAN_LITTLE_BYTE + static constexpr int offset_ = 12; #else static_assert(false, "Endian type could not be identified"); #endif diff --git a/include/boost/math/tools/config.hpp b/include/boost/math/tools/config.hpp index 6dc6bc110..2f8c16be1 100644 --- a/include/boost/math/tools/config.hpp +++ b/include/boost/math/tools/config.hpp @@ -11,7 +11,6 @@ #endif #include -#include #include #include // for min and max #include From 004805e21becd5662863c7a857c418fa2f574b5f Mon Sep 17 00:00:00 2001 From: Matt Borland Date: Thu, 25 Mar 2021 19:04:20 +0300 Subject: [PATCH 2/3] Add _WIN32 --- include/boost/math/special_functions/detail/fp_traits.hpp | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/include/boost/math/special_functions/detail/fp_traits.hpp b/include/boost/math/special_functions/detail/fp_traits.hpp index 2eb67215a..80b3f692e 100644 --- a/include/boost/math/special_functions/detail/fp_traits.hpp +++ b/include/boost/math/special_functions/detail/fp_traits.hpp @@ -42,9 +42,17 @@ With these techniques, the code could be simplified. #else // Does not have compliant C++20 +#ifdef _WIN32 + +#define BOOST_MATH_ENDIAN_BIG_BYTE 1 +#define BOOST_MATH_ENDIAN_LITTLE_BYTE 0 + +#else + #define BOOST_MATH_ENDIAN_BIG_BYTE (__BYTE_ORDER__ == __ORDER_BIG_ENDIAN__) #define BOOST_MATH_ENDIAN_LITTLE_BYTE (__BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__) +#endif // Windows or POSIX #endif // Standalone mode #endif // Endian From 4703138b5e28e2d1bdfde7174627af752cac0347 Mon Sep 17 00:00:00 2001 From: Matt Borland Date: Fri, 26 Mar 2021 22:19:40 +0300 Subject: [PATCH 3/3] Refactor and add error message --- .../math/special_functions/detail/fp_traits.hpp | 15 ++++++--------- 1 file changed, 6 insertions(+), 9 deletions(-) diff --git a/include/boost/math/special_functions/detail/fp_traits.hpp b/include/boost/math/special_functions/detail/fp_traits.hpp index 80b3f692e..8d922c2c2 100644 --- a/include/boost/math/special_functions/detail/fp_traits.hpp +++ b/include/boost/math/special_functions/detail/fp_traits.hpp @@ -33,28 +33,25 @@ With these techniques, the code could be simplified. #define BOOST_MATH_ENDIAN_BIG_BYTE BOOST_ENDIAN_BIG_BYTE #define BOOST_MATH_ENDIAN_LITTLE_BYTE BOOST_ENDIAN_LITTLE_BYTE -#else // Using standalone mode -#if (__cplusplus > 202000L || _MSVC_LANG > 202000L) && __has_include() +#elif (__cplusplus > 202000L || _MSVC_LANG > 202000L) && __has_include() #include #define BOOST_MATH_ENDIAN_BIG_BYTE (std::endian::native == std::endian::big) #define BOOST_MATH_ENDIAN_LITTLE_BYTE (std::endian::native == std::endian::little) -#else // Does not have compliant C++20 - -#ifdef _WIN32 +#elif defined(_WIN32) #define BOOST_MATH_ENDIAN_BIG_BYTE 1 #define BOOST_MATH_ENDIAN_LITTLE_BYTE 0 -#else +#elif defined(__BYTE_ORDER__) #define BOOST_MATH_ENDIAN_BIG_BYTE (__BYTE_ORDER__ == __ORDER_BIG_ENDIAN__) #define BOOST_MATH_ENDIAN_LITTLE_BYTE (__BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__) -#endif // Windows or POSIX -#endif // Standalone mode -#endif // Endian +#else +#error Could not determine endian type. Please disable standalone mode, and file an issue at https://github.com/boostorg/math +#endif // Determine endinaness #ifdef BOOST_NO_STDC_NAMESPACE namespace std{ using ::memcpy; }