mirror of
https://github.com/boostorg/multiprecision.git
synced 2026-02-19 02:22:17 +00:00
Test and allow MSVC compiled code to be used with /RTC1 /RTCc etc.
This commit is contained in:
@@ -774,10 +774,10 @@ public:
|
||||
//
|
||||
template <class SI>
|
||||
BOOST_MP_FORCEINLINE BOOST_CONSTEXPR cpp_int_base(SI i, typename boost::enable_if_c<is_signed<SI>::value && (Checked == unchecked) >::type const* = 0) BOOST_MP_NOEXCEPT_IF(noexcept(std::declval<cpp_int_base>().check_in_range(std::declval<SI>())))
|
||||
: m_data(i < 0 ? static_cast<local_limb_type>(static_cast<typename make_unsigned<SI>::type>(boost::multiprecision::detail::unsigned_abs(i)) & limb_mask) : static_cast<local_limb_type>(i)& limb_mask), m_sign(i < 0) {}
|
||||
: m_data(i < 0 ? static_cast<local_limb_type>(static_cast<typename make_unsigned<SI>::type>(boost::multiprecision::detail::unsigned_abs(i)) & limb_mask) : static_cast<local_limb_type>(i & limb_mask)), m_sign(i < 0) {}
|
||||
template <class SI>
|
||||
BOOST_MP_FORCEINLINE cpp_int_base(SI i, typename boost::enable_if_c<is_signed<SI>::value && (Checked == checked) >::type const* = 0) BOOST_MP_NOEXCEPT_IF(noexcept(std::declval<cpp_int_base>().check_in_range(std::declval<SI>())))
|
||||
: m_data(i < 0 ? (static_cast<local_limb_type>(static_cast<typename make_unsigned<SI>::type>(boost::multiprecision::detail::unsigned_abs(i)) & limb_mask)) : static_cast<local_limb_type>(i)& limb_mask), m_sign(i < 0)
|
||||
: m_data(i < 0 ? (static_cast<local_limb_type>(static_cast<typename make_unsigned<SI>::type>(boost::multiprecision::detail::unsigned_abs(i)) & limb_mask)) : static_cast<local_limb_type>(i & limb_mask)), m_sign(i < 0)
|
||||
{ check_in_range(i); }
|
||||
template <class UI>
|
||||
BOOST_MP_FORCEINLINE BOOST_CONSTEXPR cpp_int_base(UI i, typename boost::enable_if_c<is_unsigned<UI>::value && (Checked == unchecked)>::type const* = 0) BOOST_NOEXCEPT
|
||||
@@ -915,6 +915,20 @@ public:
|
||||
//
|
||||
// Direct construction:
|
||||
//
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
template <class SI>
|
||||
BOOST_MP_FORCEINLINE BOOST_CONSTEXPR cpp_int_base(SI i, typename boost::enable_if_c<is_signed<SI>::value && (Checked == unchecked) >::type const* = 0) BOOST_NOEXCEPT
|
||||
: m_data(i < 0 ? (1 + ~static_cast<local_limb_type>(-i & limb_mask)) & limb_mask : static_cast<local_limb_type>(i & limb_mask)) {}
|
||||
template <class SI>
|
||||
BOOST_MP_FORCEINLINE cpp_int_base(SI i, typename boost::enable_if_c<is_signed<SI>::value && (Checked == checked) >::type const* = 0) BOOST_MP_NOEXCEPT_IF(noexcept(std::declval<cpp_int_base>().check_in_range(std::declval<SI>())))
|
||||
: m_data(i < 0 ? 1 + ~static_cast<local_limb_type>(-i & limb_mask) : static_cast<local_limb_type>(i & limb_mask)) { check_in_range(i); }
|
||||
template <class UI>
|
||||
BOOST_MP_FORCEINLINE BOOST_CONSTEXPR cpp_int_base(UI i, typename boost::enable_if_c<is_unsigned<UI>::value && (Checked == unchecked) >::type const* = 0) BOOST_NOEXCEPT
|
||||
: m_data(static_cast<local_limb_type>(i & limb_mask)) {}
|
||||
template <class UI>
|
||||
BOOST_MP_FORCEINLINE cpp_int_base(UI i, typename boost::enable_if_c<is_unsigned<UI>::value && (Checked == checked) >::type const* = 0) BOOST_MP_NOEXCEPT_IF(noexcept(std::declval<cpp_int_base>().check_in_range(std::declval<UI>())))
|
||||
: m_data(static_cast<local_limb_type>(i & limb_mask)) { check_in_range(i); }
|
||||
#else
|
||||
template <class SI>
|
||||
BOOST_MP_FORCEINLINE BOOST_CONSTEXPR cpp_int_base(SI i, typename boost::enable_if_c<is_signed<SI>::value && (Checked == unchecked) >::type const* = 0) BOOST_NOEXCEPT
|
||||
: m_data(i < 0 ? (1 + ~static_cast<local_limb_type>(-i)) & limb_mask : static_cast<local_limb_type>(i) & limb_mask) {}
|
||||
@@ -927,6 +941,7 @@ public:
|
||||
template <class UI>
|
||||
BOOST_MP_FORCEINLINE cpp_int_base(UI i, typename boost::enable_if_c<is_unsigned<UI>::value && (Checked == checked) >::type const* = 0) BOOST_MP_NOEXCEPT_IF(noexcept(std::declval<cpp_int_base>().check_in_range(std::declval<UI>())))
|
||||
: m_data(static_cast<local_limb_type>(i)) { check_in_range(i); }
|
||||
#endif
|
||||
template <class F>
|
||||
BOOST_MP_FORCEINLINE cpp_int_base(F i, typename boost::enable_if<is_floating_point<F> >::type const* = 0) BOOST_MP_NOEXCEPT_IF((Checked == unchecked))
|
||||
: m_data(static_cast<local_limb_type>(std::fabs(i)) & limb_mask)
|
||||
@@ -1208,7 +1223,11 @@ private:
|
||||
BOOST_STATIC_ASSERT(sizeof(i) == 2 * sizeof(limb_type));
|
||||
BOOST_STATIC_ASSERT(base_type::internal_limb_count >= 2);
|
||||
typename base_type::limb_pointer p = this->limbs();
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
*p = static_cast<limb_type>(i & ~static_cast<limb_type>(0));
|
||||
#else
|
||||
*p = static_cast<limb_type>(i);
|
||||
#endif
|
||||
p[1] = static_cast<limb_type>(i >> base_type::limb_bits);
|
||||
this->resize(p[1] ? 2 : 1, p[1] ? 2 : 1);
|
||||
this->sign(false);
|
||||
@@ -1223,7 +1242,11 @@ private:
|
||||
s = true;
|
||||
ui = static_cast<double_limb_type>(boost::multiprecision::detail::unsigned_abs(i));
|
||||
typename base_type::limb_pointer p = this->limbs();
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
*p = static_cast<limb_type>(ui & ~static_cast<limb_type>(0));
|
||||
#else
|
||||
*p = static_cast<limb_type>(ui);
|
||||
#endif
|
||||
p[1] = static_cast<limb_type>(ui >> base_type::limb_bits);
|
||||
this->resize(p[1] ? 2 : 1, p[1] ? 2 : 1);
|
||||
this->sign(s);
|
||||
|
||||
@@ -49,7 +49,11 @@ inline void add_unsigned(CppInt1& result, const CppInt2& a, const CppInt3& b) BO
|
||||
while(pr != pr_end)
|
||||
{
|
||||
carry += static_cast<double_limb_type>(*pa) + static_cast<double_limb_type>(*pb);
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
*pr = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
#else
|
||||
*pr = static_cast<limb_type>(carry);
|
||||
#endif
|
||||
carry >>= CppInt1::limb_bits;
|
||||
++pr, ++pa, ++pb;
|
||||
}
|
||||
@@ -68,7 +72,11 @@ inline void add_unsigned(CppInt1& result, const CppInt2& a, const CppInt3& b) BO
|
||||
break;
|
||||
}
|
||||
carry += static_cast<double_limb_type>(*pa);
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
*pr = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
#else
|
||||
*pr = static_cast<limb_type>(carry);
|
||||
#endif
|
||||
carry >>= CppInt1::limb_bits;
|
||||
++pr, ++pa;
|
||||
}
|
||||
@@ -100,7 +108,11 @@ inline void add_unsigned(CppInt1& result, const CppInt2& a, const limb_type& o)
|
||||
for(; carry && (i < result.size()); ++i)
|
||||
{
|
||||
carry += static_cast<double_limb_type>(pa[i]);
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
pr[i] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
#else
|
||||
pr[i] = static_cast<limb_type>(carry);
|
||||
#endif
|
||||
carry >>= CppInt1::limb_bits;
|
||||
}
|
||||
// Just copy any remaining digits:
|
||||
|
||||
@@ -227,12 +227,20 @@ void divide_unsigned_helper(
|
||||
for(unsigned i = 0; i < y.size(); ++i)
|
||||
{
|
||||
carry += static_cast<double_limb_type>(py[i]) * static_cast<double_limb_type>(guess);
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
pt[i + shift] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
#else
|
||||
pt[i + shift] = static_cast<limb_type>(carry);
|
||||
#endif
|
||||
carry >>= CppInt1::limb_bits;
|
||||
}
|
||||
if(carry && !truncated_t)
|
||||
{
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
pt[t.size() - 1] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
#else
|
||||
pt[t.size() - 1] = static_cast<limb_type>(carry);
|
||||
#endif
|
||||
}
|
||||
else if(!truncated_t)
|
||||
{
|
||||
|
||||
@@ -20,7 +20,7 @@ namespace boost {
|
||||
|
||||
limb_type mask = chunk_bits >= sizeof(limb_type) * CHAR_BIT ? ~static_cast<limb_type>(0u) : (static_cast<limb_type>(1u) << chunk_bits) - 1;
|
||||
|
||||
limb_type value = (static_cast<limb_type>(bits) & mask) << shift;
|
||||
limb_type value = static_cast<limb_type>(bits & mask) << shift;
|
||||
if(value)
|
||||
{
|
||||
if(val.size() == limb)
|
||||
@@ -132,7 +132,7 @@ namespace boost {
|
||||
if(byte_len % sizeof(limb_type))
|
||||
++limb_len;
|
||||
cpp_int_backend<MinBits, MaxBits, SignType, Checked, Allocator>& result = val.backend();
|
||||
result.resize(limb_len, limb_len); // checked types may throw here if they're not large enough to hold the data!
|
||||
result.resize(static_cast<unsigned>(limb_len), static_cast<unsigned>(limb_len)); // checked types may throw here if they're not large enough to hold the data!
|
||||
result.limbs()[result.size() - 1] = 0u;
|
||||
std::memcpy(result.limbs(), i, std::min(byte_len, result.size() * sizeof(limb_type)));
|
||||
result.normalize(); // In case data has leading zeros.
|
||||
@@ -149,7 +149,7 @@ namespace boost {
|
||||
if(byte_len % sizeof(result.limbs()[0]))
|
||||
++limb_len;
|
||||
result.limbs()[0] = 0u;
|
||||
result.resize(limb_len, limb_len); // checked types may throw here if they're not large enough to hold the data!
|
||||
result.resize(static_cast<unsigned>(limb_len), static_cast<unsigned>(limb_len)); // checked types may throw here if they're not large enough to hold the data!
|
||||
std::memcpy(result.limbs(), i, std::min(byte_len, result.size() * sizeof(result.limbs()[0])));
|
||||
result.normalize(); // In case data has leading zeros.
|
||||
return val;
|
||||
|
||||
@@ -326,7 +326,11 @@ inline double_limb_type integer_gcd_reduce(double_limb_type u, double_limb_type
|
||||
break;
|
||||
}
|
||||
v -= u;
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
while((v & 1u) == 0)
|
||||
#else
|
||||
while((static_cast<unsigned>(v) & 1u) == 0)
|
||||
#endif
|
||||
v >>= 1;
|
||||
} while(true);
|
||||
return u;
|
||||
|
||||
@@ -36,7 +36,11 @@ inline typename enable_if_c<!is_trivial_cpp_int<cpp_int_backend<MinBits1, MaxBit
|
||||
while(p != pe)
|
||||
{
|
||||
carry += static_cast<double_limb_type>(*pa) * static_cast<double_limb_type>(val);
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
*p = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
#else
|
||||
*p = static_cast<limb_type>(carry);
|
||||
#endif
|
||||
carry >>= cpp_int_backend<MinBits1, MaxBits1, SignType1, Checked1, Allocator1>::limb_bits;
|
||||
++p, ++pa;
|
||||
}
|
||||
@@ -144,7 +148,11 @@ inline typename enable_if_c<!is_trivial_cpp_int<cpp_int_backend<MinBits1, MaxBit
|
||||
carry += static_cast<double_limb_type>(pa[i]) * static_cast<double_limb_type>(pb[j]);
|
||||
BOOST_ASSERT(!std::numeric_limits<double_limb_type>::is_specialized || ((std::numeric_limits<double_limb_type>::max)() - carry >= pr[i+j]));
|
||||
carry += pr[i + j];
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
pr[i + j] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
#else
|
||||
pr[i + j] = static_cast<limb_type>(carry);
|
||||
#endif
|
||||
carry >>= cpp_int_backend<MinBits1, MaxBits1, SignType1, Checked1, Allocator1>::limb_bits;
|
||||
BOOST_ASSERT(carry <= (cpp_int_backend<MinBits1, MaxBits1, SignType1, Checked1, Allocator1>::max_limb_value));
|
||||
}
|
||||
@@ -353,6 +361,16 @@ BOOST_MP_FORCEINLINE typename enable_if_c<
|
||||
limb_type* pr = result.limbs();
|
||||
|
||||
double_limb_type carry = w * y;
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
pr[0] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
carry >>= limb_bits;
|
||||
carry += w * z + x * y;
|
||||
pr[1] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
carry >>= limb_bits;
|
||||
carry += x * z;
|
||||
pr[2] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
pr[3] = static_cast<limb_type>(carry >> limb_bits);
|
||||
#else
|
||||
pr[0] = static_cast<limb_type>(carry);
|
||||
carry >>= limb_bits;
|
||||
carry += w * z + x * y;
|
||||
@@ -361,7 +379,7 @@ BOOST_MP_FORCEINLINE typename enable_if_c<
|
||||
carry += x * z;
|
||||
pr[2] = static_cast<limb_type>(carry);
|
||||
pr[3] = static_cast<limb_type>(carry >> limb_bits);
|
||||
|
||||
#endif
|
||||
result.sign(s);
|
||||
result.normalize();
|
||||
}
|
||||
@@ -387,6 +405,20 @@ BOOST_MP_FORCEINLINE typename enable_if_c<
|
||||
limb_type* pr = result.limbs();
|
||||
|
||||
double_limb_type carry = w * y;
|
||||
#ifdef __MSVC_RUNTIME_CHECKS
|
||||
pr[0] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
carry >>= limb_bits;
|
||||
carry += w * z;
|
||||
pr[1] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
carry >>= limb_bits;
|
||||
pr[2] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
carry = x * y + pr[1];
|
||||
pr[1] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
carry >>= limb_bits;
|
||||
carry += pr[2] + x * z;
|
||||
pr[2] = static_cast<limb_type>(carry & ~static_cast<limb_type>(0));
|
||||
pr[3] = static_cast<limb_type>(carry >> limb_bits);
|
||||
#else
|
||||
pr[0] = static_cast<limb_type>(carry);
|
||||
carry >>= limb_bits;
|
||||
carry += w * z;
|
||||
@@ -399,7 +431,7 @@ BOOST_MP_FORCEINLINE typename enable_if_c<
|
||||
carry += pr[2] + x * z;
|
||||
pr[2] = static_cast<limb_type>(carry);
|
||||
pr[3] = static_cast<limb_type>(carry >> limb_bits);
|
||||
|
||||
#endif
|
||||
result.sign(false);
|
||||
result.normalize();
|
||||
}
|
||||
|
||||
@@ -36,6 +36,9 @@ project : requirements
|
||||
<toolset>gcc:<cxxflags>-Wall
|
||||
<toolset>gcc:<cxxflags>-Wextra
|
||||
<toolset>intel:<define>SLOW_COMPILER
|
||||
<toolset>msvc,<optimization>off:<cxxflags>-RTC1
|
||||
<toolset>msvc,<optimization>off:<cxxflags>-RTCc
|
||||
<toolset>msvc,<optimization>off:<define>_ALLOW_RTCc_IN_STL
|
||||
;
|
||||
|
||||
local enable-specfun = [ MATCH (--enable-specfun) : [ modules.peek : ARGV ] ] ;
|
||||
|
||||
Reference in New Issue
Block a user