Skip to content

Commit 9e9858c

Browse files
committed
Improve int128::operator+
1 parent ac932f1 commit 9e9858c

File tree

1 file changed

+20
-8
lines changed

1 file changed

+20
-8
lines changed

include/boost/decimal/detail/emulated128.hpp

Lines changed: 20 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -645,8 +645,8 @@ struct int128
645645
constexpr auto operator==(int rhs) const noexcept -> bool;
646646
constexpr auto operator>(int rhs) const noexcept -> bool;
647647

648-
friend constexpr auto operator+(int128 lhs, int128 rhs) noexcept -> int128;
649-
friend constexpr auto operator-(int128 lhs, int128 rhs) noexcept -> int128;
648+
friend constexpr auto operator+(const int128& lhs, const int128& rhs) noexcept -> int128;
649+
friend constexpr auto operator-(const int128& lhs, const int128& rhs) noexcept -> int128;
650650

651651
#if !defined(BOOST_DECIMAL_DISABLE_IOSTREAM)
652652
template <typename charT, typename traits>
@@ -764,8 +764,8 @@ constexpr auto operator+(uint128 lhs, uint128 rhs) noexcept -> uint128
764764
unsigned long long low {};
765765
unsigned long long high {};
766766

767-
const auto carry {_addcarry_u64(0, lhs.low, rhs.low, &low)};
768-
_addcarry_u64(carry, lhs.high, rhs.high, &high);
767+
const auto carry {_addcarryx_u64(0, lhs.low, rhs.low, &low)};
768+
_addcarryx_u64(carry, lhs.high, rhs.high, &high);
769769

770770
return uint128{high, low};
771771
}
@@ -1326,17 +1326,29 @@ constexpr auto int128::operator>(int rhs) const noexcept -> bool
13261326
return *this > static_cast<std::int64_t>(rhs);
13271327
}
13281328

1329-
constexpr auto operator+(int128 lhs, int128 rhs) noexcept -> int128
1329+
constexpr auto operator+(const int128& lhs, const int128& rhs) noexcept -> int128
13301330
{
1331+
#ifdef BOOST_DECIMAL_HAS_INT128
1332+
1333+
const auto lhs_full {(static_cast<__uint128_t>(lhs.high) << 64) | lhs.low};
1334+
const auto rhs_full {(static_cast<__uint128_t>(rhs.high) << 64) | rhs.low};
1335+
const auto result {lhs_full + rhs_full};
1336+
1337+
return {static_cast<std::int64_t>(result >> 64), static_cast<std::uint64_t>(result)};
1338+
1339+
#else
1340+
13311341
const auto new_low {lhs.low + rhs.low};
1332-
const auto new_high {lhs.high + rhs.high + (new_low < lhs.low)};
1342+
const auto new_high {lhs.high + rhs.high + static_cast<std::int64_t>(new_low < lhs.low)};
13331343
return int128{new_high, new_low};
1344+
1345+
#endif
13341346
}
13351347

1336-
constexpr auto operator-(int128 lhs, int128 rhs) noexcept -> int128
1348+
constexpr auto operator-(const int128& lhs, int128& rhs) noexcept -> int128
13371349
{
13381350
const auto new_low {lhs.low - rhs.low};
1339-
const auto new_high {lhs.high - rhs.high - (lhs.low < rhs.low ? 1 : 0)};
1351+
const auto new_high {lhs.high - rhs.high - static_cast<std::int64_t>(lhs.low < rhs.low)};
13401352
return int128{new_high, new_low};
13411353
}
13421354

0 commit comments

Comments
 (0)