int128.h 39 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192
  1. //
  2. // Copyright 2017 The Abseil Authors.
  3. //
  4. // Licensed under the Apache License, Version 2.0 (the "License");
  5. // you may not use this file except in compliance with the License.
  6. // You may obtain a copy of the License at
  7. //
  8. // https://www.apache.org/licenses/LICENSE-2.0
  9. //
  10. // Unless required by applicable law or agreed to in writing, software
  11. // distributed under the License is distributed on an "AS IS" BASIS,
  12. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. // See the License for the specific language governing permissions and
  14. // limitations under the License.
  15. //
  16. // -----------------------------------------------------------------------------
  17. // File: int128.h
  18. // -----------------------------------------------------------------------------
  19. //
  20. // This header file defines 128-bit integer types, `uint128` and `int128`.
  21. //
  22. // TODO(absl-team): This module is inconsistent as many inline `uint128` methods
  23. // are defined in this file, while many inline `int128` methods are defined in
  24. // the `int128_*_intrinsic.inc` files.
  25. #ifndef ABSL_NUMERIC_INT128_H_
  26. #define ABSL_NUMERIC_INT128_H_
  27. #include <cassert>
  28. #include <cmath>
  29. #include <cstdint>
  30. #include <cstring>
  31. #include <iosfwd>
  32. #include <limits>
  33. #include <string>
  34. #include <utility>
  35. #include "absl/base/config.h"
  36. #include "absl/base/macros.h"
  37. #include "absl/base/port.h"
  38. #include "absl/types/compare.h"
  39. #if defined(_MSC_VER)
  40. // In very old versions of MSVC and when the /Zc:wchar_t flag is off, wchar_t is
  41. // a typedef for unsigned short. Otherwise wchar_t is mapped to the __wchar_t
  42. // builtin type. We need to make sure not to define operator wchar_t()
  43. // alongside operator unsigned short() in these instances.
  44. #define ABSL_INTERNAL_WCHAR_T __wchar_t
  45. #if defined(_M_X64) && !defined(_M_ARM64EC)
  46. #include <intrin.h>
  47. #pragma intrinsic(_umul128)
  48. #endif // defined(_M_X64)
  49. #else // defined(_MSC_VER)
  50. #define ABSL_INTERNAL_WCHAR_T wchar_t
  51. #endif // defined(_MSC_VER)
  52. namespace absl {
  53. ABSL_NAMESPACE_BEGIN
  54. class int128;
  55. // uint128
  56. //
  57. // An unsigned 128-bit integer type. The API is meant to mimic an intrinsic type
  58. // as closely as is practical, including exhibiting undefined behavior in
  59. // analogous cases (e.g. division by zero). This type is intended to be a
  60. // drop-in replacement once C++ supports an intrinsic `uint128_t` type; when
  61. // that occurs, existing well-behaved uses of `uint128` will continue to work
  62. // using that new type.
  63. //
  64. // Note: code written with this type will continue to compile once `uint128_t`
  65. // is introduced, provided the replacement helper functions
  66. // `Uint128(Low|High)64()` and `MakeUint128()` are made.
  67. //
  68. // A `uint128` supports the following:
  69. //
  70. // * Implicit construction from integral types
  71. // * Explicit conversion to integral types
  72. //
  73. // Additionally, if your compiler supports `__int128`, `uint128` is
  74. // interoperable with that type. (Abseil checks for this compatibility through
  75. // the `ABSL_HAVE_INTRINSIC_INT128` macro.)
  76. //
  77. // However, a `uint128` differs from intrinsic integral types in the following
  78. // ways:
  79. //
  80. // * Errors on implicit conversions that do not preserve value (such as
  81. // loss of precision when converting to float values).
  82. // * Requires explicit construction from and conversion to floating point
  83. // types.
  84. // * Conversion to integral types requires an explicit static_cast() to
  85. // mimic use of the `-Wnarrowing` compiler flag.
  86. // * The alignment requirement of `uint128` may differ from that of an
  87. // intrinsic 128-bit integer type depending on platform and build
  88. // configuration.
  89. //
  90. // Example:
  91. //
  92. // float y = absl::Uint128Max(); // Error. uint128 cannot be implicitly
  93. // // converted to float.
  94. //
  95. // absl::uint128 v;
  96. // uint64_t i = v; // Error
  97. // uint64_t i = static_cast<uint64_t>(v); // OK
  98. //
  99. class
  100. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  101. alignas(unsigned __int128)
  102. #endif // ABSL_HAVE_INTRINSIC_INT128
  103. uint128 {
  104. public:
  105. uint128() = default;
  106. // Constructors from arithmetic types
  107. constexpr uint128(int v); // NOLINT(runtime/explicit)
  108. constexpr uint128(unsigned int v); // NOLINT(runtime/explicit)
  109. constexpr uint128(long v); // NOLINT(runtime/int)
  110. constexpr uint128(unsigned long v); // NOLINT(runtime/int)
  111. constexpr uint128(long long v); // NOLINT(runtime/int)
  112. constexpr uint128(unsigned long long v); // NOLINT(runtime/int)
  113. #ifdef ABSL_HAVE_INTRINSIC_INT128
  114. constexpr uint128(__int128 v); // NOLINT(runtime/explicit)
  115. constexpr uint128(unsigned __int128 v); // NOLINT(runtime/explicit)
  116. #endif // ABSL_HAVE_INTRINSIC_INT128
  117. constexpr uint128(int128 v); // NOLINT(runtime/explicit)
  118. explicit uint128(float v);
  119. explicit uint128(double v);
  120. explicit uint128(long double v);
  121. // Assignment operators from arithmetic types
  122. uint128& operator=(int v);
  123. uint128& operator=(unsigned int v);
  124. uint128& operator=(long v); // NOLINT(runtime/int)
  125. uint128& operator=(unsigned long v); // NOLINT(runtime/int)
  126. uint128& operator=(long long v); // NOLINT(runtime/int)
  127. uint128& operator=(unsigned long long v); // NOLINT(runtime/int)
  128. #ifdef ABSL_HAVE_INTRINSIC_INT128
  129. uint128& operator=(__int128 v);
  130. uint128& operator=(unsigned __int128 v);
  131. #endif // ABSL_HAVE_INTRINSIC_INT128
  132. uint128& operator=(int128 v);
  133. // Conversion operators to other arithmetic types
  134. constexpr explicit operator bool() const;
  135. constexpr explicit operator char() const;
  136. constexpr explicit operator signed char() const;
  137. constexpr explicit operator unsigned char() const;
  138. constexpr explicit operator char16_t() const;
  139. constexpr explicit operator char32_t() const;
  140. constexpr explicit operator ABSL_INTERNAL_WCHAR_T() const;
  141. constexpr explicit operator short() const; // NOLINT(runtime/int)
  142. // NOLINTNEXTLINE(runtime/int)
  143. constexpr explicit operator unsigned short() const;
  144. constexpr explicit operator int() const;
  145. constexpr explicit operator unsigned int() const;
  146. constexpr explicit operator long() const; // NOLINT(runtime/int)
  147. // NOLINTNEXTLINE(runtime/int)
  148. constexpr explicit operator unsigned long() const;
  149. // NOLINTNEXTLINE(runtime/int)
  150. constexpr explicit operator long long() const;
  151. // NOLINTNEXTLINE(runtime/int)
  152. constexpr explicit operator unsigned long long() const;
  153. #ifdef ABSL_HAVE_INTRINSIC_INT128
  154. constexpr explicit operator __int128() const;
  155. constexpr explicit operator unsigned __int128() const;
  156. #endif // ABSL_HAVE_INTRINSIC_INT128
  157. explicit operator float() const;
  158. explicit operator double() const;
  159. explicit operator long double() const;
  160. // Trivial copy constructor, assignment operator and destructor.
  161. // Arithmetic operators.
  162. uint128& operator+=(uint128 other);
  163. uint128& operator-=(uint128 other);
  164. uint128& operator*=(uint128 other);
  165. // Long division/modulo for uint128.
  166. uint128& operator/=(uint128 other);
  167. uint128& operator%=(uint128 other);
  168. uint128 operator++(int);
  169. uint128 operator--(int);
  170. uint128& operator<<=(int);
  171. uint128& operator>>=(int);
  172. uint128& operator&=(uint128 other);
  173. uint128& operator|=(uint128 other);
  174. uint128& operator^=(uint128 other);
  175. uint128& operator++();
  176. uint128& operator--();
  177. // Uint128Low64()
  178. //
  179. // Returns the lower 64-bit value of a `uint128` value.
  180. friend constexpr uint64_t Uint128Low64(uint128 v);
  181. // Uint128High64()
  182. //
  183. // Returns the higher 64-bit value of a `uint128` value.
  184. friend constexpr uint64_t Uint128High64(uint128 v);
  185. // MakeUInt128()
  186. //
  187. // Constructs a `uint128` numeric value from two 64-bit unsigned integers.
  188. // Note that this factory function is the only way to construct a `uint128`
  189. // from integer values greater than 2^64.
  190. //
  191. // Example:
  192. //
  193. // absl::uint128 big = absl::MakeUint128(1, 0);
  194. friend constexpr uint128 MakeUint128(uint64_t high, uint64_t low);
  195. // Uint128Max()
  196. //
  197. // Returns the highest value for a 128-bit unsigned integer.
  198. friend constexpr uint128 Uint128Max();
  199. // Support for absl::Hash.
  200. template <typename H>
  201. friend H AbslHashValue(H h, uint128 v) {
  202. return H::combine(std::move(h), Uint128High64(v), Uint128Low64(v));
  203. }
  204. // Support for absl::StrCat() etc.
  205. template <typename Sink>
  206. friend void AbslStringify(Sink& sink, uint128 v) {
  207. sink.Append(v.ToString());
  208. }
  209. private:
  210. constexpr uint128(uint64_t high, uint64_t low);
  211. std::string ToString() const;
  212. // TODO(strel) Update implementation to use __int128 once all users of
  213. // uint128 are fixed to not depend on alignof(uint128) == 8. Also add
  214. // alignas(16) to class definition to keep alignment consistent across
  215. // platforms.
  216. #if defined(ABSL_IS_LITTLE_ENDIAN)
  217. uint64_t lo_;
  218. uint64_t hi_;
  219. #elif defined(ABSL_IS_BIG_ENDIAN)
  220. uint64_t hi_;
  221. uint64_t lo_;
  222. #else // byte order
  223. #error "Unsupported byte order: must be little-endian or big-endian."
  224. #endif // byte order
  225. };
  226. // allow uint128 to be logged
  227. std::ostream& operator<<(std::ostream& os, uint128 v);
  228. // TODO(strel) add operator>>(std::istream&, uint128)
  229. constexpr uint128 Uint128Max() {
  230. return uint128((std::numeric_limits<uint64_t>::max)(),
  231. (std::numeric_limits<uint64_t>::max)());
  232. }
  233. ABSL_NAMESPACE_END
  234. } // namespace absl
  235. // Specialized numeric_limits for uint128.
  236. namespace std {
  237. template <>
  238. class numeric_limits<absl::uint128> {
  239. public:
  240. static constexpr bool is_specialized = true;
  241. static constexpr bool is_signed = false;
  242. static constexpr bool is_integer = true;
  243. static constexpr bool is_exact = true;
  244. static constexpr bool has_infinity = false;
  245. static constexpr bool has_quiet_NaN = false;
  246. static constexpr bool has_signaling_NaN = false;
  247. ABSL_INTERNAL_DISABLE_DEPRECATED_DECLARATION_WARNING
  248. static constexpr float_denorm_style has_denorm = denorm_absent;
  249. ABSL_INTERNAL_RESTORE_DEPRECATED_DECLARATION_WARNING
  250. static constexpr bool has_denorm_loss = false;
  251. static constexpr float_round_style round_style = round_toward_zero;
  252. static constexpr bool is_iec559 = false;
  253. static constexpr bool is_bounded = true;
  254. static constexpr bool is_modulo = true;
  255. static constexpr int digits = 128;
  256. static constexpr int digits10 = 38;
  257. static constexpr int max_digits10 = 0;
  258. static constexpr int radix = 2;
  259. static constexpr int min_exponent = 0;
  260. static constexpr int min_exponent10 = 0;
  261. static constexpr int max_exponent = 0;
  262. static constexpr int max_exponent10 = 0;
  263. #ifdef ABSL_HAVE_INTRINSIC_INT128
  264. static constexpr bool traps = numeric_limits<unsigned __int128>::traps;
  265. #else // ABSL_HAVE_INTRINSIC_INT128
  266. static constexpr bool traps = numeric_limits<uint64_t>::traps;
  267. #endif // ABSL_HAVE_INTRINSIC_INT128
  268. static constexpr bool tinyness_before = false;
  269. static constexpr absl::uint128(min)() { return 0; }
  270. static constexpr absl::uint128 lowest() { return 0; }
  271. static constexpr absl::uint128(max)() { return absl::Uint128Max(); }
  272. static constexpr absl::uint128 epsilon() { return 0; }
  273. static constexpr absl::uint128 round_error() { return 0; }
  274. static constexpr absl::uint128 infinity() { return 0; }
  275. static constexpr absl::uint128 quiet_NaN() { return 0; }
  276. static constexpr absl::uint128 signaling_NaN() { return 0; }
  277. static constexpr absl::uint128 denorm_min() { return 0; }
  278. };
  279. } // namespace std
  280. namespace absl {
  281. ABSL_NAMESPACE_BEGIN
  282. // int128
  283. //
  284. // A signed 128-bit integer type. The API is meant to mimic an intrinsic
  285. // integral type as closely as is practical, including exhibiting undefined
  286. // behavior in analogous cases (e.g. division by zero).
  287. //
  288. // An `int128` supports the following:
  289. //
  290. // * Implicit construction from integral types
  291. // * Explicit conversion to integral types
  292. //
  293. // However, an `int128` differs from intrinsic integral types in the following
  294. // ways:
  295. //
  296. // * It is not implicitly convertible to other integral types.
  297. // * Requires explicit construction from and conversion to floating point
  298. // types.
  299. // Additionally, if your compiler supports `__int128`, `int128` is
  300. // interoperable with that type. (Abseil checks for this compatibility through
  301. // the `ABSL_HAVE_INTRINSIC_INT128` macro.)
  302. //
  303. // The design goal for `int128` is that it will be compatible with a future
  304. // `int128_t`, if that type becomes a part of the standard.
  305. //
  306. // Example:
  307. //
  308. // float y = absl::int128(17); // Error. int128 cannot be implicitly
  309. // // converted to float.
  310. //
  311. // absl::int128 v;
  312. // int64_t i = v; // Error
  313. // int64_t i = static_cast<int64_t>(v); // OK
  314. //
  315. class int128 {
  316. public:
  317. int128() = default;
  318. // Constructors from arithmetic types
  319. constexpr int128(int v); // NOLINT(runtime/explicit)
  320. constexpr int128(unsigned int v); // NOLINT(runtime/explicit)
  321. constexpr int128(long v); // NOLINT(runtime/int)
  322. constexpr int128(unsigned long v); // NOLINT(runtime/int)
  323. constexpr int128(long long v); // NOLINT(runtime/int)
  324. constexpr int128(unsigned long long v); // NOLINT(runtime/int)
  325. #ifdef ABSL_HAVE_INTRINSIC_INT128
  326. constexpr int128(__int128 v); // NOLINT(runtime/explicit)
  327. constexpr explicit int128(unsigned __int128 v);
  328. #endif // ABSL_HAVE_INTRINSIC_INT128
  329. constexpr explicit int128(uint128 v);
  330. explicit int128(float v);
  331. explicit int128(double v);
  332. explicit int128(long double v);
  333. // Assignment operators from arithmetic types
  334. int128& operator=(int v);
  335. int128& operator=(unsigned int v);
  336. int128& operator=(long v); // NOLINT(runtime/int)
  337. int128& operator=(unsigned long v); // NOLINT(runtime/int)
  338. int128& operator=(long long v); // NOLINT(runtime/int)
  339. int128& operator=(unsigned long long v); // NOLINT(runtime/int)
  340. #ifdef ABSL_HAVE_INTRINSIC_INT128
  341. int128& operator=(__int128 v);
  342. #endif // ABSL_HAVE_INTRINSIC_INT128
  343. // Conversion operators to other arithmetic types
  344. constexpr explicit operator bool() const;
  345. constexpr explicit operator char() const;
  346. constexpr explicit operator signed char() const;
  347. constexpr explicit operator unsigned char() const;
  348. constexpr explicit operator char16_t() const;
  349. constexpr explicit operator char32_t() const;
  350. constexpr explicit operator ABSL_INTERNAL_WCHAR_T() const;
  351. constexpr explicit operator short() const; // NOLINT(runtime/int)
  352. // NOLINTNEXTLINE(runtime/int)
  353. constexpr explicit operator unsigned short() const;
  354. constexpr explicit operator int() const;
  355. constexpr explicit operator unsigned int() const;
  356. constexpr explicit operator long() const; // NOLINT(runtime/int)
  357. // NOLINTNEXTLINE(runtime/int)
  358. constexpr explicit operator unsigned long() const;
  359. // NOLINTNEXTLINE(runtime/int)
  360. constexpr explicit operator long long() const;
  361. // NOLINTNEXTLINE(runtime/int)
  362. constexpr explicit operator unsigned long long() const;
  363. #ifdef ABSL_HAVE_INTRINSIC_INT128
  364. constexpr explicit operator __int128() const;
  365. constexpr explicit operator unsigned __int128() const;
  366. #endif // ABSL_HAVE_INTRINSIC_INT128
  367. explicit operator float() const;
  368. explicit operator double() const;
  369. explicit operator long double() const;
  370. // Trivial copy constructor, assignment operator and destructor.
  371. // Arithmetic operators
  372. int128& operator+=(int128 other);
  373. int128& operator-=(int128 other);
  374. int128& operator*=(int128 other);
  375. int128& operator/=(int128 other);
  376. int128& operator%=(int128 other);
  377. int128 operator++(int); // postfix increment: i++
  378. int128 operator--(int); // postfix decrement: i--
  379. int128& operator++(); // prefix increment: ++i
  380. int128& operator--(); // prefix decrement: --i
  381. int128& operator&=(int128 other);
  382. int128& operator|=(int128 other);
  383. int128& operator^=(int128 other);
  384. int128& operator<<=(int amount);
  385. int128& operator>>=(int amount);
  386. // Int128Low64()
  387. //
  388. // Returns the lower 64-bit value of a `int128` value.
  389. friend constexpr uint64_t Int128Low64(int128 v);
  390. // Int128High64()
  391. //
  392. // Returns the higher 64-bit value of a `int128` value.
  393. friend constexpr int64_t Int128High64(int128 v);
  394. // MakeInt128()
  395. //
  396. // Constructs a `int128` numeric value from two 64-bit integers. Note that
  397. // signedness is conveyed in the upper `high` value.
  398. //
  399. // (absl::int128(1) << 64) * high + low
  400. //
  401. // Note that this factory function is the only way to construct a `int128`
  402. // from integer values greater than 2^64 or less than -2^64.
  403. //
  404. // Example:
  405. //
  406. // absl::int128 big = absl::MakeInt128(1, 0);
  407. // absl::int128 big_n = absl::MakeInt128(-1, 0);
  408. friend constexpr int128 MakeInt128(int64_t high, uint64_t low);
  409. // Int128Max()
  410. //
  411. // Returns the maximum value for a 128-bit signed integer.
  412. friend constexpr int128 Int128Max();
  413. // Int128Min()
  414. //
  415. // Returns the minimum value for a 128-bit signed integer.
  416. friend constexpr int128 Int128Min();
  417. // Support for absl::Hash.
  418. template <typename H>
  419. friend H AbslHashValue(H h, int128 v) {
  420. return H::combine(std::move(h), Int128High64(v), Int128Low64(v));
  421. }
  422. // Support for absl::StrCat() etc.
  423. template <typename Sink>
  424. friend void AbslStringify(Sink& sink, int128 v) {
  425. sink.Append(v.ToString());
  426. }
  427. private:
  428. constexpr int128(int64_t high, uint64_t low);
  429. std::string ToString() const;
  430. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  431. __int128 v_;
  432. #else // ABSL_HAVE_INTRINSIC_INT128
  433. #if defined(ABSL_IS_LITTLE_ENDIAN)
  434. uint64_t lo_;
  435. int64_t hi_;
  436. #elif defined(ABSL_IS_BIG_ENDIAN)
  437. int64_t hi_;
  438. uint64_t lo_;
  439. #else // byte order
  440. #error "Unsupported byte order: must be little-endian or big-endian."
  441. #endif // byte order
  442. #endif // ABSL_HAVE_INTRINSIC_INT128
  443. };
  444. std::ostream& operator<<(std::ostream& os, int128 v);
  445. // TODO(absl-team) add operator>>(std::istream&, int128)
  446. constexpr int128 Int128Max() {
  447. return int128((std::numeric_limits<int64_t>::max)(),
  448. (std::numeric_limits<uint64_t>::max)());
  449. }
  450. constexpr int128 Int128Min() {
  451. return int128((std::numeric_limits<int64_t>::min)(), 0);
  452. }
  453. ABSL_NAMESPACE_END
  454. } // namespace absl
  455. // Specialized numeric_limits for int128.
  456. namespace std {
  457. template <>
  458. class numeric_limits<absl::int128> {
  459. public:
  460. static constexpr bool is_specialized = true;
  461. static constexpr bool is_signed = true;
  462. static constexpr bool is_integer = true;
  463. static constexpr bool is_exact = true;
  464. static constexpr bool has_infinity = false;
  465. static constexpr bool has_quiet_NaN = false;
  466. static constexpr bool has_signaling_NaN = false;
  467. ABSL_INTERNAL_DISABLE_DEPRECATED_DECLARATION_WARNING
  468. static constexpr float_denorm_style has_denorm = denorm_absent;
  469. ABSL_INTERNAL_RESTORE_DEPRECATED_DECLARATION_WARNING
  470. static constexpr bool has_denorm_loss = false;
  471. static constexpr float_round_style round_style = round_toward_zero;
  472. static constexpr bool is_iec559 = false;
  473. static constexpr bool is_bounded = true;
  474. static constexpr bool is_modulo = false;
  475. static constexpr int digits = 127;
  476. static constexpr int digits10 = 38;
  477. static constexpr int max_digits10 = 0;
  478. static constexpr int radix = 2;
  479. static constexpr int min_exponent = 0;
  480. static constexpr int min_exponent10 = 0;
  481. static constexpr int max_exponent = 0;
  482. static constexpr int max_exponent10 = 0;
  483. #ifdef ABSL_HAVE_INTRINSIC_INT128
  484. static constexpr bool traps = numeric_limits<__int128>::traps;
  485. #else // ABSL_HAVE_INTRINSIC_INT128
  486. static constexpr bool traps = numeric_limits<uint64_t>::traps;
  487. #endif // ABSL_HAVE_INTRINSIC_INT128
  488. static constexpr bool tinyness_before = false;
  489. static constexpr absl::int128(min)() { return absl::Int128Min(); }
  490. static constexpr absl::int128 lowest() { return absl::Int128Min(); }
  491. static constexpr absl::int128(max)() { return absl::Int128Max(); }
  492. static constexpr absl::int128 epsilon() { return 0; }
  493. static constexpr absl::int128 round_error() { return 0; }
  494. static constexpr absl::int128 infinity() { return 0; }
  495. static constexpr absl::int128 quiet_NaN() { return 0; }
  496. static constexpr absl::int128 signaling_NaN() { return 0; }
  497. static constexpr absl::int128 denorm_min() { return 0; }
  498. };
  499. } // namespace std
  500. // --------------------------------------------------------------------------
  501. // Implementation details follow
  502. // --------------------------------------------------------------------------
  503. namespace absl {
  504. ABSL_NAMESPACE_BEGIN
  505. constexpr uint128 MakeUint128(uint64_t high, uint64_t low) {
  506. return uint128(high, low);
  507. }
  508. // Assignment from integer types.
  509. inline uint128& uint128::operator=(int v) { return *this = uint128(v); }
  510. inline uint128& uint128::operator=(unsigned int v) {
  511. return *this = uint128(v);
  512. }
  513. inline uint128& uint128::operator=(long v) { // NOLINT(runtime/int)
  514. return *this = uint128(v);
  515. }
  516. // NOLINTNEXTLINE(runtime/int)
  517. inline uint128& uint128::operator=(unsigned long v) {
  518. return *this = uint128(v);
  519. }
  520. // NOLINTNEXTLINE(runtime/int)
  521. inline uint128& uint128::operator=(long long v) { return *this = uint128(v); }
  522. // NOLINTNEXTLINE(runtime/int)
  523. inline uint128& uint128::operator=(unsigned long long v) {
  524. return *this = uint128(v);
  525. }
  526. #ifdef ABSL_HAVE_INTRINSIC_INT128
  527. inline uint128& uint128::operator=(__int128 v) { return *this = uint128(v); }
  528. inline uint128& uint128::operator=(unsigned __int128 v) {
  529. return *this = uint128(v);
  530. }
  531. #endif // ABSL_HAVE_INTRINSIC_INT128
  532. inline uint128& uint128::operator=(int128 v) { return *this = uint128(v); }
  533. // Arithmetic operators.
  534. constexpr uint128 operator<<(uint128 lhs, int amount);
  535. constexpr uint128 operator>>(uint128 lhs, int amount);
  536. constexpr uint128 operator+(uint128 lhs, uint128 rhs);
  537. constexpr uint128 operator-(uint128 lhs, uint128 rhs);
  538. uint128 operator*(uint128 lhs, uint128 rhs);
  539. uint128 operator/(uint128 lhs, uint128 rhs);
  540. uint128 operator%(uint128 lhs, uint128 rhs);
  541. inline uint128& uint128::operator<<=(int amount) {
  542. *this = *this << amount;
  543. return *this;
  544. }
  545. inline uint128& uint128::operator>>=(int amount) {
  546. *this = *this >> amount;
  547. return *this;
  548. }
  549. inline uint128& uint128::operator+=(uint128 other) {
  550. *this = *this + other;
  551. return *this;
  552. }
  553. inline uint128& uint128::operator-=(uint128 other) {
  554. *this = *this - other;
  555. return *this;
  556. }
  557. inline uint128& uint128::operator*=(uint128 other) {
  558. *this = *this * other;
  559. return *this;
  560. }
  561. inline uint128& uint128::operator/=(uint128 other) {
  562. *this = *this / other;
  563. return *this;
  564. }
  565. inline uint128& uint128::operator%=(uint128 other) {
  566. *this = *this % other;
  567. return *this;
  568. }
  569. constexpr uint64_t Uint128Low64(uint128 v) { return v.lo_; }
  570. constexpr uint64_t Uint128High64(uint128 v) { return v.hi_; }
  571. // Constructors from integer types.
  572. #if defined(ABSL_IS_LITTLE_ENDIAN)
  573. constexpr uint128::uint128(uint64_t high, uint64_t low) : lo_{low}, hi_{high} {}
  574. constexpr uint128::uint128(int v)
  575. : lo_{static_cast<uint64_t>(v)},
  576. hi_{v < 0 ? (std::numeric_limits<uint64_t>::max)() : 0} {}
  577. constexpr uint128::uint128(long v) // NOLINT(runtime/int)
  578. : lo_{static_cast<uint64_t>(v)},
  579. hi_{v < 0 ? (std::numeric_limits<uint64_t>::max)() : 0} {}
  580. constexpr uint128::uint128(long long v) // NOLINT(runtime/int)
  581. : lo_{static_cast<uint64_t>(v)},
  582. hi_{v < 0 ? (std::numeric_limits<uint64_t>::max)() : 0} {}
  583. constexpr uint128::uint128(unsigned int v) : lo_{v}, hi_{0} {}
  584. // NOLINTNEXTLINE(runtime/int)
  585. constexpr uint128::uint128(unsigned long v) : lo_{v}, hi_{0} {}
  586. // NOLINTNEXTLINE(runtime/int)
  587. constexpr uint128::uint128(unsigned long long v) : lo_{v}, hi_{0} {}
  588. #ifdef ABSL_HAVE_INTRINSIC_INT128
  589. constexpr uint128::uint128(__int128 v)
  590. : lo_{static_cast<uint64_t>(v & ~uint64_t{0})},
  591. hi_{static_cast<uint64_t>(static_cast<unsigned __int128>(v) >> 64)} {}
  592. constexpr uint128::uint128(unsigned __int128 v)
  593. : lo_{static_cast<uint64_t>(v & ~uint64_t{0})},
  594. hi_{static_cast<uint64_t>(v >> 64)} {}
  595. #endif // ABSL_HAVE_INTRINSIC_INT128
  596. constexpr uint128::uint128(int128 v)
  597. : lo_{Int128Low64(v)}, hi_{static_cast<uint64_t>(Int128High64(v))} {}
  598. #elif defined(ABSL_IS_BIG_ENDIAN)
  599. constexpr uint128::uint128(uint64_t high, uint64_t low) : hi_{high}, lo_{low} {}
  600. constexpr uint128::uint128(int v)
  601. : hi_{v < 0 ? (std::numeric_limits<uint64_t>::max)() : 0},
  602. lo_{static_cast<uint64_t>(v)} {}
  603. constexpr uint128::uint128(long v) // NOLINT(runtime/int)
  604. : hi_{v < 0 ? (std::numeric_limits<uint64_t>::max)() : 0},
  605. lo_{static_cast<uint64_t>(v)} {}
  606. constexpr uint128::uint128(long long v) // NOLINT(runtime/int)
  607. : hi_{v < 0 ? (std::numeric_limits<uint64_t>::max)() : 0},
  608. lo_{static_cast<uint64_t>(v)} {}
  609. constexpr uint128::uint128(unsigned int v) : hi_{0}, lo_{v} {}
  610. // NOLINTNEXTLINE(runtime/int)
  611. constexpr uint128::uint128(unsigned long v) : hi_{0}, lo_{v} {}
  612. // NOLINTNEXTLINE(runtime/int)
  613. constexpr uint128::uint128(unsigned long long v) : hi_{0}, lo_{v} {}
  614. #ifdef ABSL_HAVE_INTRINSIC_INT128
  615. constexpr uint128::uint128(__int128 v)
  616. : hi_{static_cast<uint64_t>(static_cast<unsigned __int128>(v) >> 64)},
  617. lo_{static_cast<uint64_t>(v & ~uint64_t{0})} {}
  618. constexpr uint128::uint128(unsigned __int128 v)
  619. : hi_{static_cast<uint64_t>(v >> 64)},
  620. lo_{static_cast<uint64_t>(v & ~uint64_t{0})} {}
  621. #endif // ABSL_HAVE_INTRINSIC_INT128
  622. constexpr uint128::uint128(int128 v)
  623. : hi_{static_cast<uint64_t>(Int128High64(v))}, lo_{Int128Low64(v)} {}
  624. #else // byte order
  625. #error "Unsupported byte order: must be little-endian or big-endian."
  626. #endif // byte order
  627. // Conversion operators to integer types.
  628. constexpr uint128::operator bool() const { return lo_ || hi_; }
  629. constexpr uint128::operator char() const { return static_cast<char>(lo_); }
  630. constexpr uint128::operator signed char() const {
  631. return static_cast<signed char>(lo_);
  632. }
  633. constexpr uint128::operator unsigned char() const {
  634. return static_cast<unsigned char>(lo_);
  635. }
  636. constexpr uint128::operator char16_t() const {
  637. return static_cast<char16_t>(lo_);
  638. }
  639. constexpr uint128::operator char32_t() const {
  640. return static_cast<char32_t>(lo_);
  641. }
  642. constexpr uint128::operator ABSL_INTERNAL_WCHAR_T() const {
  643. return static_cast<ABSL_INTERNAL_WCHAR_T>(lo_);
  644. }
  645. // NOLINTNEXTLINE(runtime/int)
  646. constexpr uint128::operator short() const { return static_cast<short>(lo_); }
  647. constexpr uint128::operator unsigned short() const { // NOLINT(runtime/int)
  648. return static_cast<unsigned short>(lo_); // NOLINT(runtime/int)
  649. }
  650. constexpr uint128::operator int() const { return static_cast<int>(lo_); }
  651. constexpr uint128::operator unsigned int() const {
  652. return static_cast<unsigned int>(lo_);
  653. }
  654. // NOLINTNEXTLINE(runtime/int)
  655. constexpr uint128::operator long() const { return static_cast<long>(lo_); }
  656. constexpr uint128::operator unsigned long() const { // NOLINT(runtime/int)
  657. return static_cast<unsigned long>(lo_); // NOLINT(runtime/int)
  658. }
  659. constexpr uint128::operator long long() const { // NOLINT(runtime/int)
  660. return static_cast<long long>(lo_); // NOLINT(runtime/int)
  661. }
  662. constexpr uint128::operator unsigned long long() const { // NOLINT(runtime/int)
  663. return static_cast<unsigned long long>(lo_); // NOLINT(runtime/int)
  664. }
  665. #ifdef ABSL_HAVE_INTRINSIC_INT128
  666. constexpr uint128::operator __int128() const {
  667. return (static_cast<__int128>(hi_) << 64) + lo_;
  668. }
  669. constexpr uint128::operator unsigned __int128() const {
  670. return (static_cast<unsigned __int128>(hi_) << 64) + lo_;
  671. }
  672. #endif // ABSL_HAVE_INTRINSIC_INT128
  673. // Conversion operators to floating point types.
  674. inline uint128::operator float() const {
  675. return static_cast<float>(lo_) + std::ldexp(static_cast<float>(hi_), 64);
  676. }
  677. inline uint128::operator double() const {
  678. return static_cast<double>(lo_) + std::ldexp(static_cast<double>(hi_), 64);
  679. }
  680. inline uint128::operator long double() const {
  681. return static_cast<long double>(lo_) +
  682. std::ldexp(static_cast<long double>(hi_), 64);
  683. }
  684. // Comparison operators.
  685. constexpr bool operator==(uint128 lhs, uint128 rhs) {
  686. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  687. return static_cast<unsigned __int128>(lhs) ==
  688. static_cast<unsigned __int128>(rhs);
  689. #else
  690. return (Uint128Low64(lhs) == Uint128Low64(rhs) &&
  691. Uint128High64(lhs) == Uint128High64(rhs));
  692. #endif
  693. }
  694. constexpr bool operator!=(uint128 lhs, uint128 rhs) { return !(lhs == rhs); }
  695. constexpr bool operator<(uint128 lhs, uint128 rhs) {
  696. #ifdef ABSL_HAVE_INTRINSIC_INT128
  697. return static_cast<unsigned __int128>(lhs) <
  698. static_cast<unsigned __int128>(rhs);
  699. #else
  700. return (Uint128High64(lhs) == Uint128High64(rhs))
  701. ? (Uint128Low64(lhs) < Uint128Low64(rhs))
  702. : (Uint128High64(lhs) < Uint128High64(rhs));
  703. #endif
  704. }
  705. constexpr bool operator>(uint128 lhs, uint128 rhs) { return rhs < lhs; }
  706. constexpr bool operator<=(uint128 lhs, uint128 rhs) { return !(rhs < lhs); }
  707. constexpr bool operator>=(uint128 lhs, uint128 rhs) { return !(lhs < rhs); }
  708. #ifdef __cpp_impl_three_way_comparison
  709. constexpr absl::strong_ordering operator<=>(uint128 lhs, uint128 rhs) {
  710. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  711. if (auto lhs_128 = static_cast<unsigned __int128>(lhs),
  712. rhs_128 = static_cast<unsigned __int128>(rhs);
  713. lhs_128 < rhs_128) {
  714. return absl::strong_ordering::less;
  715. } else if (lhs_128 > rhs_128) {
  716. return absl::strong_ordering::greater;
  717. } else {
  718. return absl::strong_ordering::equal;
  719. }
  720. #else
  721. if (uint64_t lhs_high = Uint128High64(lhs), rhs_high = Uint128High64(rhs);
  722. lhs_high < rhs_high) {
  723. return absl::strong_ordering::less;
  724. } else if (lhs_high > rhs_high) {
  725. return absl::strong_ordering::greater;
  726. } else if (uint64_t lhs_low = Uint128Low64(lhs), rhs_low = Uint128Low64(rhs);
  727. lhs_low < rhs_low) {
  728. return absl::strong_ordering::less;
  729. } else if (lhs_low > rhs_low) {
  730. return absl::strong_ordering::greater;
  731. } else {
  732. return absl::strong_ordering::equal;
  733. }
  734. #endif
  735. }
  736. #endif
  737. // Unary operators.
  738. constexpr inline uint128 operator+(uint128 val) { return val; }
  739. constexpr inline int128 operator+(int128 val) { return val; }
  740. constexpr uint128 operator-(uint128 val) {
  741. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  742. return -static_cast<unsigned __int128>(val);
  743. #else
  744. return MakeUint128(
  745. ~Uint128High64(val) + static_cast<unsigned long>(Uint128Low64(val) == 0),
  746. ~Uint128Low64(val) + 1);
  747. #endif
  748. }
  749. constexpr inline bool operator!(uint128 val) {
  750. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  751. return !static_cast<unsigned __int128>(val);
  752. #else
  753. return !Uint128High64(val) && !Uint128Low64(val);
  754. #endif
  755. }
  756. // Logical operators.
  757. constexpr inline uint128 operator~(uint128 val) {
  758. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  759. return ~static_cast<unsigned __int128>(val);
  760. #else
  761. return MakeUint128(~Uint128High64(val), ~Uint128Low64(val));
  762. #endif
  763. }
  764. constexpr inline uint128 operator|(uint128 lhs, uint128 rhs) {
  765. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  766. return static_cast<unsigned __int128>(lhs) |
  767. static_cast<unsigned __int128>(rhs);
  768. #else
  769. return MakeUint128(Uint128High64(lhs) | Uint128High64(rhs),
  770. Uint128Low64(lhs) | Uint128Low64(rhs));
  771. #endif
  772. }
  773. constexpr inline uint128 operator&(uint128 lhs, uint128 rhs) {
  774. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  775. return static_cast<unsigned __int128>(lhs) &
  776. static_cast<unsigned __int128>(rhs);
  777. #else
  778. return MakeUint128(Uint128High64(lhs) & Uint128High64(rhs),
  779. Uint128Low64(lhs) & Uint128Low64(rhs));
  780. #endif
  781. }
  782. constexpr inline uint128 operator^(uint128 lhs, uint128 rhs) {
  783. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  784. return static_cast<unsigned __int128>(lhs) ^
  785. static_cast<unsigned __int128>(rhs);
  786. #else
  787. return MakeUint128(Uint128High64(lhs) ^ Uint128High64(rhs),
  788. Uint128Low64(lhs) ^ Uint128Low64(rhs));
  789. #endif
  790. }
  791. inline uint128& uint128::operator|=(uint128 other) {
  792. *this = *this | other;
  793. return *this;
  794. }
  795. inline uint128& uint128::operator&=(uint128 other) {
  796. *this = *this & other;
  797. return *this;
  798. }
  799. inline uint128& uint128::operator^=(uint128 other) {
  800. *this = *this ^ other;
  801. return *this;
  802. }
  803. // Arithmetic operators.
  804. constexpr uint128 operator<<(uint128 lhs, int amount) {
  805. #ifdef ABSL_HAVE_INTRINSIC_INT128
  806. return static_cast<unsigned __int128>(lhs) << amount;
  807. #else
  808. // uint64_t shifts of >= 64 are undefined, so we will need some
  809. // special-casing.
  810. return amount >= 64 ? MakeUint128(Uint128Low64(lhs) << (amount - 64), 0)
  811. : amount == 0 ? lhs
  812. : MakeUint128((Uint128High64(lhs) << amount) |
  813. (Uint128Low64(lhs) >> (64 - amount)),
  814. Uint128Low64(lhs) << amount);
  815. #endif
  816. }
  817. constexpr uint128 operator>>(uint128 lhs, int amount) {
  818. #ifdef ABSL_HAVE_INTRINSIC_INT128
  819. return static_cast<unsigned __int128>(lhs) >> amount;
  820. #else
  821. // uint64_t shifts of >= 64 are undefined, so we will need some
  822. // special-casing.
  823. return amount >= 64 ? MakeUint128(0, Uint128High64(lhs) >> (amount - 64))
  824. : amount == 0 ? lhs
  825. : MakeUint128(Uint128High64(lhs) >> amount,
  826. (Uint128Low64(lhs) >> amount) |
  827. (Uint128High64(lhs) << (64 - amount)));
  828. #endif
  829. }
  830. #if !defined(ABSL_HAVE_INTRINSIC_INT128)
  831. namespace int128_internal {
  832. constexpr uint128 AddResult(uint128 result, uint128 lhs) {
  833. // check for carry
  834. return (Uint128Low64(result) < Uint128Low64(lhs))
  835. ? MakeUint128(Uint128High64(result) + 1, Uint128Low64(result))
  836. : result;
  837. }
  838. } // namespace int128_internal
  839. #endif
  840. constexpr uint128 operator+(uint128 lhs, uint128 rhs) {
  841. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  842. return static_cast<unsigned __int128>(lhs) +
  843. static_cast<unsigned __int128>(rhs);
  844. #else
  845. return int128_internal::AddResult(
  846. MakeUint128(Uint128High64(lhs) + Uint128High64(rhs),
  847. Uint128Low64(lhs) + Uint128Low64(rhs)),
  848. lhs);
  849. #endif
  850. }
  851. #if !defined(ABSL_HAVE_INTRINSIC_INT128)
  852. namespace int128_internal {
  853. constexpr uint128 SubstructResult(uint128 result, uint128 lhs, uint128 rhs) {
  854. // check for carry
  855. return (Uint128Low64(lhs) < Uint128Low64(rhs))
  856. ? MakeUint128(Uint128High64(result) - 1, Uint128Low64(result))
  857. : result;
  858. }
  859. } // namespace int128_internal
  860. #endif
  861. constexpr uint128 operator-(uint128 lhs, uint128 rhs) {
  862. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  863. return static_cast<unsigned __int128>(lhs) -
  864. static_cast<unsigned __int128>(rhs);
  865. #else
  866. return int128_internal::SubstructResult(
  867. MakeUint128(Uint128High64(lhs) - Uint128High64(rhs),
  868. Uint128Low64(lhs) - Uint128Low64(rhs)),
  869. lhs, rhs);
  870. #endif
  871. }
  872. inline uint128 operator*(uint128 lhs, uint128 rhs) {
  873. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  874. // TODO(strel) Remove once alignment issues are resolved and unsigned __int128
  875. // can be used for uint128 storage.
  876. return static_cast<unsigned __int128>(lhs) *
  877. static_cast<unsigned __int128>(rhs);
  878. #elif defined(_MSC_VER) && defined(_M_X64) && !defined(_M_ARM64EC)
  879. uint64_t carry;
  880. uint64_t low = _umul128(Uint128Low64(lhs), Uint128Low64(rhs), &carry);
  881. return MakeUint128(Uint128Low64(lhs) * Uint128High64(rhs) +
  882. Uint128High64(lhs) * Uint128Low64(rhs) + carry,
  883. low);
  884. #else // ABSL_HAVE_INTRINSIC128
  885. uint64_t a32 = Uint128Low64(lhs) >> 32;
  886. uint64_t a00 = Uint128Low64(lhs) & 0xffffffff;
  887. uint64_t b32 = Uint128Low64(rhs) >> 32;
  888. uint64_t b00 = Uint128Low64(rhs) & 0xffffffff;
  889. uint128 result =
  890. MakeUint128(Uint128High64(lhs) * Uint128Low64(rhs) +
  891. Uint128Low64(lhs) * Uint128High64(rhs) + a32 * b32,
  892. a00 * b00);
  893. result += uint128(a32 * b00) << 32;
  894. result += uint128(a00 * b32) << 32;
  895. return result;
  896. #endif // ABSL_HAVE_INTRINSIC128
  897. }
  898. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  899. inline uint128 operator/(uint128 lhs, uint128 rhs) {
  900. return static_cast<unsigned __int128>(lhs) /
  901. static_cast<unsigned __int128>(rhs);
  902. }
  903. inline uint128 operator%(uint128 lhs, uint128 rhs) {
  904. return static_cast<unsigned __int128>(lhs) %
  905. static_cast<unsigned __int128>(rhs);
  906. }
  907. #endif
  908. // Increment/decrement operators.
  909. inline uint128 uint128::operator++(int) {
  910. uint128 tmp(*this);
  911. *this += 1;
  912. return tmp;
  913. }
  914. inline uint128 uint128::operator--(int) {
  915. uint128 tmp(*this);
  916. *this -= 1;
  917. return tmp;
  918. }
  919. inline uint128& uint128::operator++() {
  920. *this += 1;
  921. return *this;
  922. }
  923. inline uint128& uint128::operator--() {
  924. *this -= 1;
  925. return *this;
  926. }
  927. constexpr int128 MakeInt128(int64_t high, uint64_t low) {
  928. return int128(high, low);
  929. }
  930. // Assignment from integer types.
  931. inline int128& int128::operator=(int v) { return *this = int128(v); }
  932. inline int128& int128::operator=(unsigned int v) { return *this = int128(v); }
  933. inline int128& int128::operator=(long v) { // NOLINT(runtime/int)
  934. return *this = int128(v);
  935. }
  936. // NOLINTNEXTLINE(runtime/int)
  937. inline int128& int128::operator=(unsigned long v) { return *this = int128(v); }
  938. // NOLINTNEXTLINE(runtime/int)
  939. inline int128& int128::operator=(long long v) { return *this = int128(v); }
  940. // NOLINTNEXTLINE(runtime/int)
  941. inline int128& int128::operator=(unsigned long long v) {
  942. return *this = int128(v);
  943. }
  944. // Arithmetic operators.
  945. constexpr int128 operator-(int128 v);
  946. constexpr int128 operator+(int128 lhs, int128 rhs);
  947. constexpr int128 operator-(int128 lhs, int128 rhs);
  948. int128 operator*(int128 lhs, int128 rhs);
  949. int128 operator/(int128 lhs, int128 rhs);
  950. int128 operator%(int128 lhs, int128 rhs);
  951. constexpr int128 operator|(int128 lhs, int128 rhs);
  952. constexpr int128 operator&(int128 lhs, int128 rhs);
  953. constexpr int128 operator^(int128 lhs, int128 rhs);
  954. constexpr int128 operator<<(int128 lhs, int amount);
  955. constexpr int128 operator>>(int128 lhs, int amount);
  956. inline int128& int128::operator+=(int128 other) {
  957. *this = *this + other;
  958. return *this;
  959. }
  960. inline int128& int128::operator-=(int128 other) {
  961. *this = *this - other;
  962. return *this;
  963. }
  964. inline int128& int128::operator*=(int128 other) {
  965. *this = *this * other;
  966. return *this;
  967. }
  968. inline int128& int128::operator/=(int128 other) {
  969. *this = *this / other;
  970. return *this;
  971. }
  972. inline int128& int128::operator%=(int128 other) {
  973. *this = *this % other;
  974. return *this;
  975. }
  976. inline int128& int128::operator|=(int128 other) {
  977. *this = *this | other;
  978. return *this;
  979. }
  980. inline int128& int128::operator&=(int128 other) {
  981. *this = *this & other;
  982. return *this;
  983. }
  984. inline int128& int128::operator^=(int128 other) {
  985. *this = *this ^ other;
  986. return *this;
  987. }
  988. inline int128& int128::operator<<=(int amount) {
  989. *this = *this << amount;
  990. return *this;
  991. }
  992. inline int128& int128::operator>>=(int amount) {
  993. *this = *this >> amount;
  994. return *this;
  995. }
  996. // Forward declaration for comparison operators.
  997. constexpr bool operator!=(int128 lhs, int128 rhs);
  998. namespace int128_internal {
  999. // Casts from unsigned to signed while preserving the underlying binary
  1000. // representation.
  1001. constexpr int64_t BitCastToSigned(uint64_t v) {
  1002. // Casting an unsigned integer to a signed integer of the same
  1003. // width is implementation defined behavior if the source value would not fit
  1004. // in the destination type. We step around it with a roundtrip bitwise not
  1005. // operation to make sure this function remains constexpr. Clang, GCC, and
  1006. // MSVC optimize this to a no-op on x86-64.
  1007. return v & (uint64_t{1} << 63) ? ~static_cast<int64_t>(~v)
  1008. : static_cast<int64_t>(v);
  1009. }
  1010. } // namespace int128_internal
  1011. #if defined(ABSL_HAVE_INTRINSIC_INT128)
  1012. #include "absl/numeric/int128_have_intrinsic.inc" // IWYU pragma: export
  1013. #else // ABSL_HAVE_INTRINSIC_INT128
  1014. #include "absl/numeric/int128_no_intrinsic.inc" // IWYU pragma: export
  1015. #endif // ABSL_HAVE_INTRINSIC_INT128
  1016. ABSL_NAMESPACE_END
  1017. } // namespace absl
  1018. #undef ABSL_INTERNAL_WCHAR_T
  1019. #endif // ABSL_NUMERIC_INT128_H_