xref: /llvm-project/flang/include/flang/Evaluate/integer.h (revision fc97d2e68b03bc2979395e84b645e5b3ba35aecd)
1 //===-- include/flang/Evaluate/integer.h ------------------------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #ifndef FORTRAN_EVALUATE_INTEGER_H_
10 #define FORTRAN_EVALUATE_INTEGER_H_
11 
12 // Emulates binary integers of an arbitrary (but fixed) bit size for use
13 // when the host C++ environment does not support that size or when the
14 // full suite of Fortran's integer intrinsic scalar functions are needed.
15 // The data model is typeless, so signed* and unsigned operations
16 // are distinguished from each other with distinct member function interfaces.
17 // (*"Signed" here means two's-complement, just to be clear.  Ones'-complement
18 // and signed-magnitude encodings appear to be extinct in 2018.)
19 
20 #include "flang/Common/bit-population-count.h"
21 #include "flang/Common/leading-zero-bit-count.h"
22 #include "flang/Evaluate/common.h"
23 #include <cinttypes>
24 #include <climits>
25 #include <cstddef>
26 #include <cstdint>
27 #include <string>
28 #include <type_traits>
29 
30 // Some environments, viz. glibc 2.17 and *BSD, allow the macro HUGE
31 // to leak out of <math.h>.
32 #undef HUGE
33 
34 namespace Fortran::evaluate::value {
35 
36 // Computes decimal range in the sense of SELECTED_INT_KIND
37 static constexpr int DecimalRange(int bits) {
38   // This magic value is LOG10(2.)*1E12.
39   return static_cast<int>((bits * 301029995664) / 1000000000000);
40 }
41 
42 // Implements an integer as an assembly of smaller host integer parts
43 // that constitute the digits of a large-radix fixed-point number.
44 // For best performance, the type of these parts should be half of the
45 // size of the largest efficient integer supported by the host processor.
46 // These parts are stored in either little- or big-endian order, which can
47 // match that of the host's endianness or not; but if the ordering matches
48 // that of the host, raw host data can be overlaid with a properly configured
49 // instance of this class and used in situ.
50 // To facilitate exhaustive testing of what would otherwise be more rare
51 // edge cases, this class template may be configured to use other part
52 // types &/or partial fields in the parts.  The radix (i.e., the number
53 // of possible values in a part), however, must be a power of two; this
54 // template class is not generalized to enable, say, decimal arithmetic.
55 // Member functions that correspond to Fortran intrinsic functions are
56 // named accordingly in ALL CAPS so that they can be referenced easily in
57 // the language standard.
58 template <int BITS, bool IS_LITTLE_ENDIAN = isHostLittleEndian,
59     int PARTBITS = BITS <= 32 ? BITS
60         : BITS % 32 == 0      ? 32
61         : BITS % 16 == 0      ? 16
62                               : 8,
63     typename PART = HostUnsignedInt<PARTBITS>,
64     typename BIGPART = HostUnsignedInt<PARTBITS * 2>, int ALIGNMENT = BITS>
65 class Integer {
66 public:
67   static constexpr int bits{BITS};
68   static constexpr int partBits{PARTBITS};
69   using Part = PART;
70   using BigPart = BIGPART;
71   static_assert(std::is_integral_v<Part>);
72   static_assert(std::is_unsigned_v<Part>);
73   static_assert(std::is_integral_v<BigPart>);
74   static_assert(std::is_unsigned_v<BigPart>);
75   static_assert(CHAR_BIT * sizeof(BigPart) >= 2 * partBits);
76   static constexpr bool littleEndian{IS_LITTLE_ENDIAN};
77 
78 private:
79   static constexpr int maxPartBits{CHAR_BIT * sizeof(Part)};
80   static_assert(partBits > 0 && partBits <= maxPartBits);
81   static constexpr int extraPartBits{maxPartBits - partBits};
82   static constexpr int parts{(bits + partBits - 1) / partBits};
83   static_assert(parts >= 1);
84   static constexpr int extraTopPartBits{
85       extraPartBits + (parts * partBits) - bits};
86   static constexpr int topPartBits{maxPartBits - extraTopPartBits};
87   static_assert(topPartBits > 0 && topPartBits <= partBits);
88   static_assert((parts - 1) * partBits + topPartBits == bits);
89   static constexpr Part partMask{static_cast<Part>(~0) >> extraPartBits};
90   static constexpr Part topPartMask{static_cast<Part>(~0) >> extraTopPartBits};
91   static constexpr int partsWithAlignment{
92       (ALIGNMENT + partBits - 1) / partBits};
93 
94 public:
95   // Some types used for member function results
96   struct ValueWithOverflow {
97     Integer value;
98     bool overflow;
99   };
100 
101   struct ValueWithCarry {
102     Integer value;
103     bool carry;
104   };
105 
106   struct Product {
107     bool SignedMultiplicationOverflowed() const {
108       return lower.IsNegative() ? (upper.POPCNT() != bits) : !upper.IsZero();
109     }
110     Integer upper, lower;
111   };
112 
113   struct QuotientWithRemainder {
114     Integer quotient, remainder;
115     bool divisionByZero, overflow;
116   };
117 
118   struct PowerWithErrors {
119     Integer power;
120     bool divisionByZero{false}, overflow{false}, zeroToZero{false};
121   };
122 
123   // Constructors and value-generating static functions
124   constexpr Integer() { Clear(); } // default constructor: zero
125   constexpr Integer(const Integer &) = default;
126   constexpr Integer(Integer &&) = default;
127 
128   // C++'s integral types can all be converted to Integer
129   // with silent truncation.
130   template <typename INT, typename = std::enable_if_t<std::is_integral_v<INT>>>
131   constexpr Integer(INT n) {
132     constexpr int nBits = CHAR_BIT * sizeof n;
133     if constexpr (nBits < partBits) {
134       if constexpr (std::is_unsigned_v<INT>) {
135         // Zero-extend an unsigned smaller value.
136         SetLEPart(0, n);
137         for (int j{1}; j < parts; ++j) {
138           SetLEPart(j, 0);
139         }
140       } else {
141         // n has a signed type smaller than the usable
142         // bits in a Part.
143         // Avoid conversions that change both size and sign.
144         using SignedPart = std::make_signed_t<Part>;
145         Part p = static_cast<SignedPart>(n);
146         SetLEPart(0, p);
147         if constexpr (parts > 1) {
148           Part signExtension = static_cast<SignedPart>(-(n < 0));
149           for (int j{1}; j < parts; ++j) {
150             SetLEPart(j, signExtension);
151           }
152         }
153       }
154     } else {
155       // n has some integral type no smaller than the usable
156       // bits in a Part.
157       // Ensure that all shifts are smaller than a whole word.
158       if constexpr (std::is_unsigned_v<INT>) {
159         for (int j{0}; j < parts; ++j) {
160           SetLEPart(j, static_cast<Part>(n));
161           if constexpr (nBits > partBits) {
162             n >>= partBits;
163           } else {
164             n = 0;
165           }
166         }
167       } else {
168         // Avoid left shifts of negative signed values (that's an undefined
169         // behavior in C++).
170         auto signExtension{std::make_unsigned_t<INT>(n < 0)};
171         signExtension = ~signExtension + 1;
172         static_assert(nBits >= partBits);
173         if constexpr (nBits > partBits) {
174           signExtension <<= nBits - partBits;
175           for (int j{0}; j < parts; ++j) {
176             SetLEPart(j, static_cast<Part>(n));
177             n >>= partBits;
178             n |= signExtension;
179           }
180         } else {
181           SetLEPart(0, static_cast<Part>(n));
182           for (int j{1}; j < parts; ++j) {
183             SetLEPart(j, static_cast<Part>(signExtension));
184           }
185         }
186       }
187     }
188   }
189 
190   constexpr Integer &operator=(const Integer &) = default;
191 
192   constexpr bool operator<(const Integer &that) const {
193     return CompareSigned(that) == Ordering::Less;
194   }
195   constexpr bool operator<=(const Integer &that) const {
196     return CompareSigned(that) != Ordering::Greater;
197   }
198   constexpr bool operator==(const Integer &that) const {
199     return CompareSigned(that) == Ordering::Equal;
200   }
201   constexpr bool operator!=(const Integer &that) const {
202     return !(*this == that);
203   }
204   constexpr bool operator>=(const Integer &that) const {
205     return CompareSigned(that) != Ordering::Less;
206   }
207   constexpr bool operator>(const Integer &that) const {
208     return CompareSigned(that) == Ordering::Greater;
209   }
210 
211   // Left-justified mask (e.g., MASKL(1) has only its sign bit set)
212   static constexpr Integer MASKL(int places) {
213     if (places <= 0) {
214       return {};
215     } else if (places >= bits) {
216       return MASKR(bits);
217     } else {
218       return MASKR(bits - places).NOT();
219     }
220   }
221 
222   // Right-justified mask (e.g., MASKR(1) == 1, MASKR(2) == 3, &c.)
223   static constexpr Integer MASKR(int places) {
224     Integer result{nullptr};
225     int j{0};
226     for (; j + 1 < parts && places >= partBits; ++j, places -= partBits) {
227       result.LEPart(j) = partMask;
228     }
229     if (places > 0) {
230       if (j + 1 < parts) {
231         result.LEPart(j++) = partMask >> (partBits - places);
232       } else if (j + 1 == parts) {
233         if (places >= topPartBits) {
234           result.LEPart(j++) = topPartMask;
235         } else {
236           result.LEPart(j++) = topPartMask >> (topPartBits - places);
237         }
238       }
239     }
240     for (; j < parts; ++j) {
241       result.LEPart(j) = 0;
242     }
243     return result;
244   }
245 
246   static constexpr ValueWithOverflow Read(
247       const char *&pp, std::uint64_t base = 10, bool isSigned = false) {
248     Integer result;
249     bool overflow{false};
250     const char *p{pp};
251     while (*p == ' ' || *p == '\t') {
252       ++p;
253     }
254     bool negate{*p == '-'};
255     if (negate || *p == '+') {
256       while (*++p == ' ' || *p == '\t') {
257       }
258     }
259     Integer radix{base};
260     // This code makes assumptions about local contiguity in regions of the
261     // character set and only works up to base 36.  These assumptions hold
262     // for all current combinations of surviving character sets (ASCII, UTF-8,
263     // EBCDIC) and the bases used in Fortran source and formatted I/O
264     // (viz., 2, 8, 10, & 16).  But: management thought that a disclaimer
265     // might be needed here to warn future users of this code about these
266     // assumptions, so here you go, future programmer in some postapocalyptic
267     // hellscape, and best of luck with the inexorable killer robots.
268     for (; std::uint64_t digit = *p; ++p) {
269       if (digit >= '0' && digit <= '9' && digit < '0' + base) {
270         digit -= '0';
271       } else if (base > 10 && digit >= 'A' && digit < 'A' + base - 10) {
272         digit -= 'A' - 10;
273       } else if (base > 10 && digit >= 'a' && digit < 'a' + base - 10) {
274         digit -= 'a' - 10;
275       } else {
276         break;
277       }
278       Product shifted{result.MultiplyUnsigned(radix)};
279       overflow |= !shifted.upper.IsZero();
280       ValueWithCarry next{shifted.lower.AddUnsigned(Integer{digit})};
281       overflow |= next.carry;
282       result = next.value;
283     }
284     pp = p;
285     if (negate) {
286       result = result.Negate().value;
287       overflow |= isSigned && !result.IsNegative() && !result.IsZero();
288     } else {
289       overflow |= isSigned && result.IsNegative();
290     }
291     return {result, overflow};
292   }
293 
294   template <typename FROM>
295   static constexpr ValueWithOverflow ConvertUnsigned(const FROM &that) {
296     std::uint64_t field{that.ToUInt64()};
297     ValueWithOverflow result{field, false};
298     if constexpr (bits < 64) {
299       result.overflow = (field >> bits) != 0;
300     }
301     for (int j{64}; j < that.bits && !result.overflow; j += 64) {
302       field = that.SHIFTR(j).ToUInt64();
303       if (bits <= j) {
304         result.overflow = field != 0;
305       } else {
306         result.value = result.value.IOR(Integer{field}.SHIFTL(j));
307         if (bits < j + 64) {
308           result.overflow = (field >> (bits - j)) != 0;
309         }
310       }
311     }
312     return result;
313   }
314 
315   template <typename FROM>
316   static constexpr ValueWithOverflow ConvertSigned(const FROM &that) {
317     ValueWithOverflow result{ConvertUnsigned(that)};
318     if constexpr (bits > FROM::bits) {
319       if (that.IsNegative()) {
320         result.value = result.value.IOR(MASKL(bits - FROM::bits));
321       }
322       result.overflow = false;
323     } else if constexpr (bits < FROM::bits) {
324       auto back{FROM::template ConvertSigned<Integer>(result.value)};
325       result.overflow = back.value.CompareUnsigned(that) != Ordering::Equal;
326     }
327     return result;
328   }
329 
330   std::string UnsignedDecimal() const {
331     if constexpr (bits < 4) {
332       char digit = '0' + ToUInt64();
333       return {digit};
334     } else if (IsZero()) {
335       return {'0'};
336     } else {
337       QuotientWithRemainder qr{DivideUnsigned(10)};
338       char digit = '0' + qr.remainder.ToUInt64();
339       if (qr.quotient.IsZero()) {
340         return {digit};
341       } else {
342         return qr.quotient.UnsignedDecimal() + digit;
343       }
344     }
345   }
346 
347   std::string SignedDecimal() const {
348     if (IsNegative()) {
349       return std::string{'-'} + Negate().value.UnsignedDecimal();
350     } else {
351       return UnsignedDecimal();
352     }
353   }
354 
355   // Omits a leading "0x".
356   std::string Hexadecimal() const {
357     std::string result;
358     int digits{(bits + 3) >> 2};
359     for (int j{0}; j < digits; ++j) {
360       int pos{(digits - 1 - j) * 4};
361       char nybble = IBITS(pos, 4).ToUInt64();
362       if (nybble != 0 || !result.empty() || j + 1 == digits) {
363         char digit = '0' + nybble;
364         if (digit > '9') {
365           digit += 'a' - ('9' + 1);
366         }
367         result += digit;
368       }
369     }
370     return result;
371   }
372 
373   static constexpr int DIGITS{bits - 1}; // don't count the sign bit
374   static constexpr Integer HUGE() { return MASKR(bits - 1); }
375   static constexpr Integer Least() { return MASKL(1); }
376   static constexpr int RANGE{DecimalRange(bits - 1)};
377   static constexpr int UnsignedRANGE{DecimalRange(bits)};
378 
379   constexpr bool IsZero() const {
380     for (int j{0}; j < parts; ++j) {
381       if (part_[j] != 0) {
382         return false;
383       }
384     }
385     return true;
386   }
387 
388   constexpr bool IsNegative() const {
389     return (LEPart(parts - 1) >> (topPartBits - 1)) & 1;
390   }
391 
392   constexpr Ordering CompareToZeroSigned() const {
393     if (IsNegative()) {
394       return Ordering::Less;
395     } else if (IsZero()) {
396       return Ordering::Equal;
397     } else {
398       return Ordering::Greater;
399     }
400   }
401 
402   // Count the number of contiguous most-significant bit positions
403   // that are clear.
404   constexpr int LEADZ() const {
405     if (LEPart(parts - 1) != 0) {
406       int lzbc{common::LeadingZeroBitCount(LEPart(parts - 1))};
407       return lzbc - extraTopPartBits;
408     }
409     int upperZeroes{topPartBits};
410     for (int j{1}; j < parts; ++j) {
411       if (Part p{LEPart(parts - 1 - j)}) {
412         int lzbc{common::LeadingZeroBitCount(p)};
413         return upperZeroes + lzbc - extraPartBits;
414       }
415       upperZeroes += partBits;
416     }
417     return bits;
418   }
419 
420   // Count the number of bit positions that are set.
421   constexpr int POPCNT() const {
422     int count{0};
423     for (int j{0}; j < parts; ++j) {
424       count += common::BitPopulationCount(part_[j]);
425     }
426     return count;
427   }
428 
429   // True when POPCNT is odd.
430   constexpr bool POPPAR() const { return POPCNT() & 1; }
431 
432   constexpr int TRAILZ() const {
433     auto minus1{AddUnsigned(MASKR(bits))}; // { x-1, carry = x > 0 }
434     if (!minus1.carry) {
435       return bits; // was zero
436     } else {
437       // x ^ (x-1) has all bits set at and below original least-order set bit.
438       return IEOR(minus1.value).POPCNT() - 1;
439     }
440   }
441 
442   constexpr bool BTEST(int pos) const {
443     if (pos < 0 || pos >= bits) {
444       return false;
445     } else {
446       return (LEPart(pos / partBits) >> (pos % partBits)) & 1;
447     }
448   }
449 
450   constexpr Ordering CompareUnsigned(const Integer &y) const {
451     for (int j{parts}; j-- > 0;) {
452       if (LEPart(j) > y.LEPart(j)) {
453         return Ordering::Greater;
454       }
455       if (LEPart(j) < y.LEPart(j)) {
456         return Ordering::Less;
457       }
458     }
459     return Ordering::Equal;
460   }
461 
462   constexpr bool BGE(const Integer &y) const {
463     return CompareUnsigned(y) != Ordering::Less;
464   }
465   constexpr bool BGT(const Integer &y) const {
466     return CompareUnsigned(y) == Ordering::Greater;
467   }
468   constexpr bool BLE(const Integer &y) const { return !BGT(y); }
469   constexpr bool BLT(const Integer &y) const { return !BGE(y); }
470 
471   constexpr Ordering CompareSigned(const Integer &y) const {
472     bool isNegative{IsNegative()};
473     if (isNegative != y.IsNegative()) {
474       return isNegative ? Ordering::Less : Ordering::Greater;
475     }
476     return CompareUnsigned(y);
477   }
478 
479   template <typename UINT = std::uint64_t> constexpr UINT ToUInt() const {
480     UINT n{LEPart(0)};
481     std::size_t filled{partBits};
482     constexpr std::size_t maxBits{CHAR_BIT * sizeof n};
483     for (int j{1}; filled < maxBits && j < parts; ++j, filled += partBits) {
484       n |= UINT{LEPart(j)} << filled;
485     }
486     return n;
487   }
488 
489   template <typename SINT = std::int64_t, typename UINT = std::uint64_t>
490   constexpr SINT ToSInt() const {
491     SINT n = ToUInt<UINT>();
492     constexpr std::size_t maxBits{CHAR_BIT * sizeof n};
493     if constexpr (bits < maxBits) {
494       // Avoid left shifts of negative signed values (that's an undefined
495       // behavior in C++).
496       auto u{std::make_unsigned_t<SINT>(ToUInt())};
497       u = (u >> (bits - 1)) << (bits - 1); // Get the sign bit only.
498       u = ~u + 1; // Negate top bits if not 0.
499       n |= static_cast<SINT>(u);
500     }
501     return n;
502   }
503 
504   constexpr std::uint64_t ToUInt64() const { return ToUInt<std::uint64_t>(); }
505 
506   constexpr std::int64_t ToInt64() const {
507     return ToSInt<std::int64_t, std::uint64_t>();
508   }
509 
510   // Ones'-complement (i.e., C's ~)
511   constexpr Integer NOT() const {
512     Integer result{nullptr};
513     for (int j{0}; j < parts; ++j) {
514       result.SetLEPart(j, ~LEPart(j));
515     }
516     return result;
517   }
518 
519   // Two's-complement negation (-x = ~x + 1).
520   // An overflow flag accompanies the result, and will be true when the
521   // operand is the most negative signed number (MASKL(1)).
522   constexpr ValueWithOverflow Negate() const {
523     Integer result{nullptr};
524     Part carry{1};
525     for (int j{0}; j + 1 < parts; ++j) {
526       Part newCarry{LEPart(j) == 0 && carry};
527       result.SetLEPart(j, ~LEPart(j) + carry);
528       carry = newCarry;
529     }
530     Part top{LEPart(parts - 1)};
531     result.SetLEPart(parts - 1, ~top + carry);
532     bool overflow{top != 0 && result.LEPart(parts - 1) == top};
533     return {result, overflow};
534   }
535 
536   constexpr ValueWithOverflow ABS() const {
537     if (IsNegative()) {
538       return Negate();
539     } else {
540       return {*this, false};
541     }
542   }
543 
544   // Shifts the operand left when the count is positive, right when negative.
545   // Vacated bit positions are filled with zeroes.
546   constexpr Integer ISHFT(int count) const {
547     if (count < 0) {
548       return SHIFTR(-count);
549     } else {
550       return SHIFTL(count);
551     }
552   }
553 
554   // Left shift with zero fill.
555   constexpr Integer SHIFTL(int count) const {
556     if (count <= 0) {
557       return *this;
558     } else {
559       Integer result{nullptr};
560       int shiftParts{count / partBits};
561       int bitShift{count - partBits * shiftParts};
562       int j{parts - 1};
563       if (bitShift == 0) {
564         for (; j >= shiftParts; --j) {
565           result.SetLEPart(j, LEPart(j - shiftParts));
566         }
567         for (; j >= 0; --j) {
568           result.LEPart(j) = 0;
569         }
570       } else {
571         for (; j > shiftParts; --j) {
572           result.SetLEPart(j,
573               ((LEPart(j - shiftParts) << bitShift) |
574                   (LEPart(j - shiftParts - 1) >> (partBits - bitShift))));
575         }
576         if (j == shiftParts) {
577           result.SetLEPart(j, LEPart(0) << bitShift);
578           --j;
579         }
580         for (; j >= 0; --j) {
581           result.LEPart(j) = 0;
582         }
583       }
584       return result;
585     }
586   }
587 
588   // Circular shift of a field of least-significant bits.  The least-order
589   // "size" bits are shifted circularly in place by "count" positions;
590   // the shift is leftward if count is nonnegative, rightward otherwise.
591   // Higher-order bits are unchanged.
592   constexpr Integer ISHFTC(int count, int size = bits) const {
593     if (count == 0 || size <= 0) {
594       return *this;
595     }
596     if (size > bits) {
597       size = bits;
598     }
599     count %= size;
600     if (count == 0) {
601       return *this;
602     }
603     int middleBits{size - count}, leastBits{count};
604     if (count < 0) {
605       middleBits = -count;
606       leastBits = size + count;
607     }
608     if (size == bits) {
609       return SHIFTL(leastBits).IOR(SHIFTR(middleBits));
610     }
611     Integer unchanged{IAND(MASKL(bits - size))};
612     Integer middle{IAND(MASKR(middleBits)).SHIFTL(leastBits)};
613     Integer least{SHIFTR(middleBits).IAND(MASKR(leastBits))};
614     return unchanged.IOR(middle).IOR(least);
615   }
616 
617   // Double shifts, aka shifts with specific fill.
618   constexpr Integer SHIFTLWithFill(const Integer &fill, int count) const {
619     if (count <= 0) {
620       return *this;
621     } else if (count >= 2 * bits) {
622       return {};
623     } else if (count > bits) {
624       return fill.SHIFTL(count - bits);
625     } else if (count == bits) {
626       return fill;
627     } else {
628       return SHIFTL(count).IOR(fill.SHIFTR(bits - count));
629     }
630   }
631 
632   constexpr Integer SHIFTRWithFill(const Integer &fill, int count) const {
633     if (count <= 0) {
634       return *this;
635     } else if (count >= 2 * bits) {
636       return {};
637     } else if (count > bits) {
638       return fill.SHIFTR(count - bits);
639     } else if (count == bits) {
640       return fill;
641     } else {
642       return SHIFTR(count).IOR(fill.SHIFTL(bits - count));
643     }
644   }
645 
646   constexpr Integer DSHIFTL(const Integer &fill, int count) const {
647     // DSHIFTL(I,J) shifts I:J left; the second argument is the right fill.
648     return SHIFTLWithFill(fill, count);
649   }
650 
651   constexpr Integer DSHIFTR(const Integer &value, int count) const {
652     // DSHIFTR(I,J) shifts I:J right; the *first* argument is the left fill.
653     return value.SHIFTRWithFill(*this, count);
654   }
655 
656   // Vacated upper bits are filled with zeroes.
657   constexpr Integer SHIFTR(int count) const {
658     if (count <= 0) {
659       return *this;
660     } else {
661       Integer result{nullptr};
662       int shiftParts{count / partBits};
663       int bitShift{count - partBits * shiftParts};
664       int j{0};
665       if (bitShift == 0) {
666         for (; j + shiftParts < parts; ++j) {
667           result.LEPart(j) = LEPart(j + shiftParts);
668         }
669         for (; j < parts; ++j) {
670           result.LEPart(j) = 0;
671         }
672       } else {
673         for (; j + shiftParts + 1 < parts; ++j) {
674           result.SetLEPart(j,
675               (LEPart(j + shiftParts) >> bitShift) |
676                   (LEPart(j + shiftParts + 1) << (partBits - bitShift)));
677         }
678         if (j + shiftParts + 1 == parts) {
679           result.LEPart(j++) = LEPart(parts - 1) >> bitShift;
680         }
681         for (; j < parts; ++j) {
682           result.LEPart(j) = 0;
683         }
684       }
685       return result;
686     }
687   }
688 
689   // Be advised, an arithmetic (sign-filling) right shift is not
690   // the same as a division by a power of two in all cases.
691   constexpr Integer SHIFTA(int count) const {
692     if (count <= 0) {
693       return *this;
694     } else if (IsNegative()) {
695       return SHIFTR(count).IOR(MASKL(count));
696     } else {
697       return SHIFTR(count);
698     }
699   }
700 
701   // Clears a single bit.
702   constexpr Integer IBCLR(int pos) const {
703     if (pos < 0 || pos >= bits) {
704       return *this;
705     } else {
706       Integer result{*this};
707       result.LEPart(pos / partBits) &= ~(Part{1} << (pos % partBits));
708       return result;
709     }
710   }
711 
712   // Sets a single bit.
713   constexpr Integer IBSET(int pos) const {
714     if (pos < 0 || pos >= bits) {
715       return *this;
716     } else {
717       Integer result{*this};
718       result.LEPart(pos / partBits) |= Part{1} << (pos % partBits);
719       return result;
720     }
721   }
722 
723   // Extracts a field.
724   constexpr Integer IBITS(int pos, int size) const {
725     return SHIFTR(pos).IAND(MASKR(size));
726   }
727 
728   constexpr Integer IAND(const Integer &y) const {
729     Integer result{nullptr};
730     for (int j{0}; j < parts; ++j) {
731       result.LEPart(j) = LEPart(j) & y.LEPart(j);
732     }
733     return result;
734   }
735 
736   constexpr Integer IOR(const Integer &y) const {
737     Integer result{nullptr};
738     for (int j{0}; j < parts; ++j) {
739       result.LEPart(j) = LEPart(j) | y.LEPart(j);
740     }
741     return result;
742   }
743 
744   constexpr Integer IEOR(const Integer &y) const {
745     Integer result{nullptr};
746     for (int j{0}; j < parts; ++j) {
747       result.LEPart(j) = LEPart(j) ^ y.LEPart(j);
748     }
749     return result;
750   }
751 
752   constexpr Integer MERGE_BITS(const Integer &y, const Integer &mask) const {
753     return IAND(mask).IOR(y.IAND(mask.NOT()));
754   }
755 
756   constexpr Integer MAX(const Integer &y) const {
757     if (CompareSigned(y) == Ordering::Less) {
758       return y;
759     } else {
760       return *this;
761     }
762   }
763 
764   constexpr Integer MIN(const Integer &y) const {
765     if (CompareSigned(y) == Ordering::Less) {
766       return *this;
767     } else {
768       return y;
769     }
770   }
771 
772   // Unsigned addition with carry.
773   constexpr ValueWithCarry AddUnsigned(
774       const Integer &y, bool carryIn = false) const {
775     Integer sum{nullptr};
776     BigPart carry{carryIn};
777     for (int j{0}; j + 1 < parts; ++j) {
778       carry += LEPart(j);
779       carry += y.LEPart(j);
780       sum.SetLEPart(j, carry);
781       carry >>= partBits;
782     }
783     carry += LEPart(parts - 1);
784     carry += y.LEPart(parts - 1);
785     sum.SetLEPart(parts - 1, carry);
786     return {sum, carry > topPartMask};
787   }
788 
789   constexpr ValueWithOverflow AddSigned(const Integer &y) const {
790     bool isNegative{IsNegative()};
791     bool sameSign{isNegative == y.IsNegative()};
792     ValueWithCarry sum{AddUnsigned(y)};
793     bool overflow{sameSign && sum.value.IsNegative() != isNegative};
794     return {sum.value, overflow};
795   }
796 
797   constexpr ValueWithOverflow SubtractSigned(const Integer &y) const {
798     bool isNegative{IsNegative()};
799     bool sameSign{isNegative == y.IsNegative()};
800     ValueWithCarry diff{AddUnsigned(y.Negate().value)};
801     bool overflow{!sameSign && diff.value.IsNegative() != isNegative};
802     return {diff.value, overflow};
803   }
804 
805   // DIM(X,Y)=MAX(X-Y, 0)
806   constexpr ValueWithOverflow DIM(const Integer &y) const {
807     if (CompareSigned(y) != Ordering::Greater) {
808       return {};
809     } else {
810       return SubtractSigned(y);
811     }
812   }
813 
814   constexpr ValueWithOverflow SIGN(bool toNegative) const {
815     if (toNegative == IsNegative()) {
816       return {*this, false};
817     } else if (toNegative) {
818       return Negate();
819     } else {
820       return ABS();
821     }
822   }
823 
824   constexpr ValueWithOverflow SIGN(const Integer &sign) const {
825     return SIGN(sign.IsNegative());
826   }
827 
828   constexpr Product MultiplyUnsigned(const Integer &y) const {
829     Part product[2 * parts]{}; // little-endian full product
830     for (int j{0}; j < parts; ++j) {
831       if (Part xpart{LEPart(j)}) {
832         for (int k{0}; k < parts; ++k) {
833           if (Part ypart{y.LEPart(k)}) {
834             BigPart xy{xpart};
835             xy *= ypart;
836 #if defined __GNUC__ && __GNUC__ < 8 || __GNUC__ >= 12
837             // && to < (2 * parts) was added to avoid GCC build failure on
838             // -Werror=array-bounds. This can be removed if -Werror is disabled.
839             for (int to{j + k}; xy != 0 && to < (2 * parts); ++to) {
840 #else
841             for (int to{j + k}; xy != 0; ++to) {
842 #endif
843               xy += product[to];
844               product[to] = xy & partMask;
845               xy >>= partBits;
846             }
847           }
848         }
849       }
850     }
851     Integer upper{nullptr}, lower{nullptr};
852     for (int j{0}; j < parts; ++j) {
853       lower.LEPart(j) = product[j];
854       upper.LEPart(j) = product[j + parts];
855     }
856     if constexpr (topPartBits < partBits) {
857       upper = upper.SHIFTL(partBits - topPartBits);
858       upper.LEPart(0) |= lower.LEPart(parts - 1) >> topPartBits;
859       lower.LEPart(parts - 1) &= topPartMask;
860     }
861     return {upper, lower};
862   }
863 
864   constexpr Product MultiplySigned(const Integer &y) const {
865     bool yIsNegative{y.IsNegative()};
866     Integer absy{y};
867     if (yIsNegative) {
868       absy = y.Negate().value;
869     }
870     bool isNegative{IsNegative()};
871     Integer absx{*this};
872     if (isNegative) {
873       absx = Negate().value;
874     }
875     Product product{absx.MultiplyUnsigned(absy)};
876     if (isNegative != yIsNegative) {
877       product.lower = product.lower.NOT();
878       product.upper = product.upper.NOT();
879       Integer one{1};
880       auto incremented{product.lower.AddUnsigned(one)};
881       product.lower = incremented.value;
882       if (incremented.carry) {
883         product.upper = product.upper.AddUnsigned(one).value;
884       }
885     }
886     return product;
887   }
888 
889   constexpr QuotientWithRemainder DivideUnsigned(const Integer &divisor) const {
890     if (divisor.IsZero()) {
891       return {MASKR(bits), Integer{}, true, false}; // overflow to max value
892     }
893     int bitsDone{LEADZ()};
894     Integer top{SHIFTL(bitsDone)};
895     Integer quotient, remainder;
896     for (; bitsDone < bits; ++bitsDone) {
897       auto doubledTop{top.AddUnsigned(top)};
898       top = doubledTop.value;
899       remainder = remainder.AddUnsigned(remainder, doubledTop.carry).value;
900       bool nextBit{remainder.CompareUnsigned(divisor) != Ordering::Less};
901       quotient = quotient.AddUnsigned(quotient, nextBit).value;
902       if (nextBit) {
903         remainder = remainder.SubtractSigned(divisor).value;
904       }
905     }
906     return {quotient, remainder, false, false};
907   }
908 
909   // A nonzero remainder has the sign of the dividend, i.e., it computes
910   // the MOD intrinsic (X-INT(X/Y)*Y), not MODULO (which is below).
911   // 8/5 = 1r3;  -8/5 = -1r-3;  8/-5 = -1r3;  -8/-5 = 1r-3
912   constexpr QuotientWithRemainder DivideSigned(Integer divisor) const {
913     bool dividendIsNegative{IsNegative()};
914     bool negateQuotient{dividendIsNegative};
915     Ordering divisorOrdering{divisor.CompareToZeroSigned()};
916     if (divisorOrdering == Ordering::Less) {
917       negateQuotient = !negateQuotient;
918       auto negated{divisor.Negate()};
919       if (negated.overflow) {
920         // divisor was (and is) the most negative number
921         if (CompareUnsigned(divisor) == Ordering::Equal) {
922           return {MASKR(1), Integer{}, false, bits <= 1};
923         } else {
924           return {Integer{}, *this, false, false};
925         }
926       }
927       divisor = negated.value;
928     } else if (divisorOrdering == Ordering::Equal) {
929       // division by zero
930       if (dividendIsNegative) {
931         return {MASKL(1), Integer{}, true, false};
932       } else {
933         return {MASKR(bits - 1), Integer{}, true, false};
934       }
935     }
936     Integer dividend{*this};
937     if (dividendIsNegative) {
938       auto negated{Negate()};
939       if (negated.overflow) {
940         // Dividend was (and remains) the most negative number.
941         // See whether the original divisor was -1 (if so, it's 1 now).
942         if (divisorOrdering == Ordering::Less &&
943             divisor.CompareUnsigned(Integer{1}) == Ordering::Equal) {
944           // most negative number / -1 is the sole overflow case
945           return {*this, Integer{}, false, true};
946         }
947       } else {
948         dividend = negated.value;
949       }
950     }
951     // Overflow is not possible, and both the dividend and divisor
952     // are now positive.
953     QuotientWithRemainder result{dividend.DivideUnsigned(divisor)};
954     if (negateQuotient) {
955       result.quotient = result.quotient.Negate().value;
956     }
957     if (dividendIsNegative) {
958       result.remainder = result.remainder.Negate().value;
959     }
960     return result;
961   }
962 
963   // Result has the sign of the divisor argument.
964   // 8 mod 5 = 3;  -8 mod 5 = 2;  8 mod -5 = -2;  -8 mod -5 = -3
965   constexpr ValueWithOverflow MODULO(const Integer &divisor) const {
966     bool negativeDivisor{divisor.IsNegative()};
967     bool distinctSigns{IsNegative() != negativeDivisor};
968     QuotientWithRemainder divided{DivideSigned(divisor)};
969     if (distinctSigns && !divided.remainder.IsZero()) {
970       return {divided.remainder.AddUnsigned(divisor).value, divided.overflow};
971     } else {
972       return {divided.remainder, divided.overflow};
973     }
974   }
975 
976   constexpr PowerWithErrors Power(const Integer &exponent) const {
977     PowerWithErrors result{1, false, false, false};
978     if (exponent.IsZero()) {
979       // x**0 -> 1, including the case 0**0, which is not defined specifically
980       // in F'18 afaict; however, other Fortrans tested all produce 1, not 0,
981       // apart from nagfor, which stops with an error at runtime.
982       // Ada, APL, C's pow(), Haskell, Julia, MATLAB, and R all produce 1 too.
983       // F'77 explicitly states that 0**0 is mathematically undefined and
984       // therefore prohibited.
985       result.zeroToZero = IsZero();
986     } else if (exponent.IsNegative()) {
987       if (IsZero()) {
988         result.divisionByZero = true;
989         result.power = MASKR(bits - 1);
990       } else if (CompareSigned(Integer{1}) == Ordering::Equal) {
991         result.power = *this; // 1**x -> 1
992       } else if (CompareSigned(Integer{-1}) == Ordering::Equal) {
993         if (exponent.BTEST(0)) {
994           result.power = *this; // (-1)**x -> -1 if x is odd
995         }
996       } else {
997         result.power.Clear(); // j**k -> 0 if |j| > 1 and k < 0
998       }
999     } else {
1000       Integer shifted{*this};
1001       Integer pow{exponent};
1002       int nbits{bits - pow.LEADZ()};
1003       for (int j{0}; j < nbits; ++j) {
1004         if (pow.BTEST(j)) {
1005           Product product{result.power.MultiplySigned(shifted)};
1006           result.power = product.lower;
1007           result.overflow |= product.SignedMultiplicationOverflowed();
1008         }
1009         if (j + 1 < nbits) {
1010           Product squared{shifted.MultiplySigned(shifted)};
1011           result.overflow |= squared.SignedMultiplicationOverflowed();
1012           shifted = squared.lower;
1013         }
1014       }
1015     }
1016     return result;
1017   }
1018 
1019 private:
1020   // A private constructor, selected by the use of nullptr,
1021   // that is used by member functions when it would be a waste
1022   // of time to initialize parts_[].
1023   constexpr Integer(std::nullptr_t) {}
1024 
1025   // Accesses parts in little-endian order.
1026   constexpr const Part &LEPart(int part) const {
1027     if constexpr (littleEndian) {
1028       return part_[part];
1029     } else {
1030       return part_[parts - 1 - part];
1031     }
1032   }
1033 
1034   constexpr Part &LEPart(int part) {
1035     if constexpr (littleEndian) {
1036       return part_[part];
1037     } else {
1038       return part_[parts - 1 - part];
1039     }
1040   }
1041 
1042   constexpr void SetLEPart(int part, Part x) {
1043     LEPart(part) = x & PartMask(part);
1044   }
1045 
1046   static constexpr Part PartMask(int part) {
1047     return part == parts - 1 ? topPartMask : partMask;
1048   }
1049 
1050   constexpr void Clear() {
1051     for (int j{0}; j < parts; ++j) {
1052       part_[j] = 0;
1053     }
1054   }
1055 
1056   Part part_[partsWithAlignment]{};
1057 };
1058 
1059 extern template class Integer<8>;
1060 extern template class Integer<16>;
1061 extern template class Integer<32>;
1062 extern template class Integer<64>;
1063 using X87IntegerContainer =
1064     Integer<80, isHostLittleEndian, 16, std::uint16_t, std::uint32_t, 128>;
1065 extern template class Integer<80, isHostLittleEndian, 16, std::uint16_t,
1066     std::uint32_t, 128>;
1067 extern template class Integer<128>;
1068 } // namespace Fortran::evaluate::value
1069 #endif // FORTRAN_EVALUATE_INTEGER_H_
1070