APInt.h revision 66ed1099ff3591c61e008198bb5a30862e778fc0
1d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//===-- llvm/Support/APInt.h - For Arbitrary Precision Integer -*- C++ -*--===//
2d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//
3d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//                     The LLVM Compiler Infrastructure
4d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//
5d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng// This file was developed by Sheng Zhou and is distributed under the
6d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng// University of Illinois Open Source License. See LICENSE.TXT for details.
7d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//
8d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//===----------------------------------------------------------------------===//
9d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//
10d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng// This file implements a class to represent arbitrary precision integral
11d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng// constant values.
12d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//
13d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//===----------------------------------------------------------------------===//
14d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
15d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng#ifndef LLVM_APINT_H
16d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng#define LLVM_APINT_H
17d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
18d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng#include "llvm/Support/DataTypes.h"
1958a0d64fae7ace05b27dad94fd427991d853619bLauro Ramos Venancio#include <cassert>
20d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng#include <string>
21d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
22d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Shengnamespace llvm {
23d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
240b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Forward declaration.
250b706b18bd0a7760d971727460a1f26bff8289b0Zhou Shengclass APInt;
260b706b18bd0a7760d971727460a1f26bff8289b0Zhou Shengnamespace APIntOps {
27e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  APInt udiv(const APInt& LHS, const APInt& RHS);
28e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  APInt urem(const APInt& LHS, const APInt& RHS);
290b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng}
300b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
31d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//===----------------------------------------------------------------------===//
32d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//                              APInt Class
33d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng//===----------------------------------------------------------------------===//
34d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
35d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// APInt - This class represents arbitrary precision constant integral values.
36d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// It is a functional replacement for common case unsigned integer type like
37d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// "unsigned", "unsigned long" or "uint64_t", but also allows non-byte-width
38e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer/// integer sizes and large integer value types such as 3-bits, 15-bits, or more
39d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// than 64-bits of precision. APInt provides a variety of arithmetic operators
40e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer/// and methods to manipulate integer values of any bit-width. It supports both
41e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer/// the typical integer arithmetic and comparison operations as well as bitwise
42e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer/// manipulation.
43d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng///
44e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer/// The class has several invariants worth noting:
45e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///   * All bit, byte, and word positions are zero-based.
46e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///   * Once the bit width is set, it doesn't change except by the Truncate,
47e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///     SignExtend, or ZeroExtend operations.
48e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///   * All binary operators must be on APInt instances of the same bit width.
49e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///     Attempting to use these operators on instances with different bit
50e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///     widths will yield an assertion.
51e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///   * The value is stored canonically as an unsigned value. For operations
52e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///     where it makes a difference, there are both signed and unsigned variants
53e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///     of the operation. For example, sdiv and udiv. However, because the bit
54e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///     widths must be the same, operations such as Mul and Add produce the same
55e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///     results regardless of whether the values are interpreted as signed or
56e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///     not.
57e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///   * In general, the class tries to follow the style of computation that LLVM
58e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer///     uses in its IR. This simplifies its use for LLVM.
597406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng///
60e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer/// @brief Class for arbitrary precision integers.
61d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Shengclass APInt {
6220b1f5db1e93d28debc6449dcd56da6ca7aa6b67Reid Spencer
63a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  uint32_t BitWidth;      ///< The number of bits in this APInt.
64d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
65d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// This union is used to store the integer value. When the
667406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// integer bit-width <= 64, it uses VAL;
677406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// otherwise it uses the pVal.
68d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  union {
69d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng    uint64_t VAL;    ///< Used to store the <= 64 bits integer value.
70d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng    uint64_t *pVal;  ///< Used to store the >64 bits integer value.
71d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  };
72d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
737406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// This enum is just used to hold a constant we needed for APInt.
74d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  enum {
75d81b0659501c66b2fec2009e8a999c3db6a1f95cReid Spencer    APINT_BITS_PER_WORD = sizeof(uint64_t) * 8,
76d81b0659501c66b2fec2009e8a999c3db6a1f95cReid Spencer    APINT_WORD_SIZE = sizeof(uint64_t)
77d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  };
78d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
7920b1f5db1e93d28debc6449dcd56da6ca7aa6b67Reid Spencer  // Fast internal constructor
8020b1f5db1e93d28debc6449dcd56da6ca7aa6b67Reid Spencer  APInt(uint64_t* val, uint32_t bits) : BitWidth(bits), pVal(val) { }
8120b1f5db1e93d28debc6449dcd56da6ca7aa6b67Reid Spencer
82d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// Here one word's bitwidth equals to that of uint64_t.
837406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @returns the number of words to hold the integer value of this APInt.
847406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Get the number of words.
85a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  inline uint32_t getNumWords() const {
86e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return (BitWidth + APINT_BITS_PER_WORD - 1) / APINT_BITS_PER_WORD;
87d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  }
88d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
89d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns true if the number of bits <= 64, false otherwise.
90d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @brief Determine if this APInt just has one word to store value.
91e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  inline bool isSingleWord() const {
92e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return BitWidth <= APINT_BITS_PER_WORD;
93e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
94d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
95d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns the word position for the specified bit position.
96a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  static inline uint32_t whichWord(uint32_t bitPosition) {
97e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return bitPosition / APINT_BITS_PER_WORD;
98e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
99d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
100d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns the bit position in a word for the specified bit position
101d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// in APInt.
102a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  static inline uint32_t whichBit(uint32_t bitPosition) {
103e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return bitPosition % APINT_BITS_PER_WORD;
104e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
105d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
106d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns a uint64_t type integer with just bit position at
107d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// "whichBit(bitPosition)" setting, others zero.
108a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  static inline uint64_t maskBit(uint32_t bitPosition) {
109e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return (static_cast<uint64_t>(1)) << whichBit(bitPosition);
110e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
111d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
112e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// This method is used internally to clear the to "N" bits that are not used
113d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// by the APInt. This is needed after the most significant word is assigned
114d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// a value to ensure that those bits are zero'd out.
115e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Clear high order bits
116c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  inline APInt& clearUnusedBits() {
117c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer    // Compute how many bits are used in the final word
118c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer    uint32_t wordBits = BitWidth % APINT_BITS_PER_WORD;
119c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer    if (wordBits == 0)
120c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer      // If all bits are used, we want to leave the value alone. This also
121c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer      // avoids the undefined behavior of >> when the shfit is the same size as
122c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer      // the word size (64).
123c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer      return *this;
124c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer
125c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer    // Mask out the hight bits.
126c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer    uint64_t mask = ~uint64_t(0ULL) >> (APINT_BITS_PER_WORD - wordBits);
127d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng    if (isSingleWord())
128c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer      VAL &= mask;
129d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng    else
130c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer      pVal[getNumWords() - 1] &= mask;
131c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer    return *this;
132d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  }
133d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
134d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns the corresponding word for the specified bit position.
135d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// @brief Get the word corresponding to a bit position
136a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  inline uint64_t getWord(uint32_t bitPosition) const {
137e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return isSingleWord() ? VAL : pVal[whichWord(bitPosition)];
138e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
139d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
140d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// This is used by the constructors that take string arguments.
141d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// @brief Converts a char array into an APInt
142a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  void fromString(uint32_t numBits, const char *StrStart, uint32_t slen,
143e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer                  uint8_t radix);
144f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng
145d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// This is used by the toString method to divide by the radix. It simply
146c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// provides a more convenient form of divide for internal use since KnuthDiv
147c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// has specific constraints on its inputs. If those constraints are not met
148c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// then it provides a simpler form of divide.
149d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// @brief An internal division function for dividing APInts.
150d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  static void divide(const APInt LHS, uint32_t lhsWords,
151d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer                     const APInt &RHS, uint32_t rhsWords,
152d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer                     APInt *Quotient, APInt *Remainder);
153d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer
154f31c784f2774311d1f7194ac4ca86262197a8099Reid Spencer#ifndef NDEBUG
155f31c784f2774311d1f7194ac4ca86262197a8099Reid Spencer  /// @brief debug method
156f31c784f2774311d1f7194ac4ca86262197a8099Reid Spencer  void dump() const;
157f31c784f2774311d1f7194ac4ca86262197a8099Reid Spencer#endif
158f31c784f2774311d1f7194ac4ca86262197a8099Reid Spencer
159f31c784f2774311d1f7194ac4ca86262197a8099Reid Spencerpublic:
160d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// @brief Create a new APInt of numBits width, initialized as val.
161a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt(uint32_t numBits, uint64_t val);
162d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
163d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// Note that numWords can be smaller or larger than the corresponding bit
164d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// width but any extraneous bits will be dropped.
165d03d012ad97fad9f91b107d206dadad4c34bebefReid Spencer  /// @brief Create a new APInt of numBits width, initialized as bigVal[].
166a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt(uint32_t numBits, uint32_t numWords, uint64_t bigVal[]);
167d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
1687406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Create a new APInt by translating the string represented
1697406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// integer value.
170a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt(uint32_t numBits, const std::string& Val, uint8_t radix);
171f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng
172f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  /// @brief Create a new APInt by translating the char array represented
173f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  /// integer value.
174a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt(uint32_t numBits, const char StrStart[], uint32_t slen, uint8_t radix);
175d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
1767406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Copy Constructor.
177d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt(const APInt& API);
178d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
1797406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Destructor.
180d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  ~APInt();
181d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
1827406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Copy assignment operator.
183d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt& operator=(const APInt& RHS);
184d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
1857406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Assigns an integer value to the APInt.
1867406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Assignment operator.
187d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt& operator=(uint64_t RHS);
188d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
1897406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Increments the APInt by one.
1907406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Postfix increment operator.
191f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  inline const APInt operator++(int) {
192f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng    APInt API(*this);
193b04973edfaffb12905f58379d632f0d7e4bb5d9bZhou Sheng    ++(*this);
194b04973edfaffb12905f58379d632f0d7e4bb5d9bZhou Sheng    return API;
195f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  }
196d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
1977406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Increments the APInt by one.
1987406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Prefix increment operator.
199d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt& operator++();
200d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2017406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Decrements the APInt by one.
2027406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Postfix decrement operator.
203f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  inline const APInt operator--(int) {
204f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng    APInt API(*this);
205b04973edfaffb12905f58379d632f0d7e4bb5d9bZhou Sheng    --(*this);
206b04973edfaffb12905f58379d632f0d7e4bb5d9bZhou Sheng    return API;
207f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  }
208d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2097406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Decrements the APInt by one.
2107406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Prefix decrement operator.
211d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt& operator--();
212d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2137406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Performs bitwise AND operation on this APInt and the given APInt& RHS,
2147406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// assigns the result to this APInt.
2157406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Bitwise AND assignment operator.
216d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt& operator&=(const APInt& RHS);
217d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2187406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Performs bitwise OR operation on this APInt and the given APInt& RHS,
2197406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// assigns the result to this APInt.
2207406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Bitwise OR assignment operator.
221d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt& operator|=(const APInt& RHS);
222d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2237406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Performs bitwise XOR operation on this APInt and the given APInt& RHS,
2247406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// assigns the result to this APInt.
2257406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Bitwise XOR assignment operator.
226d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt& operator^=(const APInt& RHS);
227d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2287406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Performs a bitwise complement operation on this APInt.
2297406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Bitwise complement operator.
230d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt operator~() const;
231d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2327406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Multiplies this APInt by the  given APInt& RHS and
2337406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// assigns the result to this APInt.
2347406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Multiplication assignment operator.
235d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt& operator*=(const APInt& RHS);
236d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2377406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Adds this APInt by the given APInt& RHS and
2387406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// assigns the result to this APInt.
2397406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Addition assignment operator.
240d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt& operator+=(const APInt& RHS);
241d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2427406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Subtracts this APInt by the given APInt &RHS and
2437406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// assigns the result to this APInt.
2447406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Subtraction assignment operator.
245d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt& operator-=(const APInt& RHS);
246d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2477406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Performs bitwise AND operation on this APInt and
2487406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// the given APInt& RHS.
2497406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Bitwise AND operator.
250d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt operator&(const APInt& RHS) const;
251d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2527406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Performs bitwise OR operation on this APInt and the given APInt& RHS.
2537406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Bitwise OR operator.
254d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt operator|(const APInt& RHS) const;
255d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2567406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Performs bitwise XOR operation on this APInt and the given APInt& RHS.
2577406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Bitwise XOR operator.
258d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt operator^(const APInt& RHS) const;
259d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2607406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Performs logical negation operation on this APInt.
2617406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Logical negation operator.
262d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  bool operator !() const;
263d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2647406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Multiplies this APInt by the given APInt& RHS.
2657406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Multiplication operator.
266d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt operator*(const APInt& RHS) const;
267d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2687406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Adds this APInt by the given APInt& RHS.
2697406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Addition operator.
270d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt operator+(const APInt& RHS) const;
271d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2727406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Subtracts this APInt by the given APInt& RHS
2737406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Subtraction operator.
274d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  APInt operator-(const APInt& RHS) const;
275d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
276e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Unary negation operator
2770b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng  inline APInt operator-() const {
278cd6f2bfc268add3dd54cbdf98b2a2c4862fe4ba5Reid Spencer    return APInt(BitWidth, 0) - (*this);
2790b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng  }
280d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
281d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @brief Array-indexing support.
282a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  bool operator[](uint32_t bitPosition) const;
283d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
2847406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Compare this APInt with the given APInt& RHS
285d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// for the validity of the equality relationship.
2867406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Equality operator.
287d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  bool operator==(const APInt& RHS) const;
288d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
289f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  /// Compare this APInt with the given uint64_t value
290f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  /// for the validity of the equality relationship.
291f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  /// @brief Equality operator.
292f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  bool operator==(uint64_t Val) const;
293f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng
2947406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// Compare this APInt with the given APInt& RHS
295d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// for the validity of the inequality relationship.
2967406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// @brief Inequality operator.
297f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  inline bool operator!=(const APInt& RHS) const {
298f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng    return !((*this) == RHS);
299f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  }
300d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
301f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  /// Compare this APInt with the given uint64_t value
302f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  /// for the validity of the inequality relationship.
303f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  /// @brief Inequality operator.
304f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  inline bool operator!=(uint64_t Val) const {
305f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng    return !((*this) == Val);
306f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng  }
307f29a09d6272265e90362d5dfba201c4ed6dcf6d5Zhou Sheng
308e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Equality comparison
309e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  bool eq(const APInt &RHS) const {
310e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return (*this) == RHS;
311e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
312e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
313e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Inequality comparison
314e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  bool ne(const APInt &RHS) const {
315e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return !((*this) == RHS);
316e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
317e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
318e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Unsigned less than comparison
319e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  bool ult(const APInt& RHS) const;
320e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
321e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Signed less than comparison
322e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  bool slt(const APInt& RHS) const;
323e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
324e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Unsigned less or equal comparison
325e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  bool ule(const APInt& RHS) const {
326e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return ult(RHS) || eq(RHS);
327e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
328e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
329e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Signed less or equal comparison
330e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  bool sle(const APInt& RHS) const {
331e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return slt(RHS) || eq(RHS);
332e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
333e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
334e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Unsigned greather than comparison
335e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  bool ugt(const APInt& RHS) const {
336e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return !ult(RHS) && !eq(RHS);
337e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
338e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
339e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Signed greather than comparison
340e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  bool sgt(const APInt& RHS) const {
341e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return !slt(RHS) && !eq(RHS);
342e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
343e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
344e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Unsigned greater or equal comparison
345e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  bool uge(const APInt& RHS) const {
346e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return !ult(RHS);
347e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
348e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
349e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Signed greather or equal comparison
350e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  bool sge(const APInt& RHS) const {
351e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return !slt(RHS);
352e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
353e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
354dcffd5c3d90f295c90bc211a9c402e1fc18f8b12Reid Spencer  /// This just tests the high bit of this APInt to determine if it is negative.
355dcffd5c3d90f295c90bc211a9c402e1fc18f8b12Reid Spencer  /// @returns true if this APInt is negative, false otherwise
356dcffd5c3d90f295c90bc211a9c402e1fc18f8b12Reid Spencer  /// @brief Determine sign of this APInt.
357ebf4ebd69155ea46c7937aec25df1f50dd61c136Reid Spencer  bool isNegative() const {
358dcffd5c3d90f295c90bc211a9c402e1fc18f8b12Reid Spencer    return (*this)[BitWidth - 1];
359dcffd5c3d90f295c90bc211a9c402e1fc18f8b12Reid Spencer  }
360dcffd5c3d90f295c90bc211a9c402e1fc18f8b12Reid Spencer
361e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Arithmetic right-shift this APInt by shiftAmt.
362e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Arithmetic right-shift function.
363a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt ashr(uint32_t shiftAmt) const;
364e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
365e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Logical right-shift this APInt by shiftAmt.
366e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Logical right-shift function.
367a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt lshr(uint32_t shiftAmt) const;
368e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
369e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Left-shift this APInt by shiftAmt.
370e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Left-shift function.
371a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt shl(uint32_t shiftAmt) const;
372e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
373e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Signed divide this APInt by APInt RHS.
374e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Signed division function for APInt.
375e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  inline APInt sdiv(const APInt& RHS) const {
37666ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    bool isNegativeLHS = isNegative();
37766ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    bool isNegativeRHS = RHS.isNegative();
378a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer    APInt Result = APIntOps::udiv(
379e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer        isNegativeLHS ? -(*this) : (*this), isNegativeRHS ? -RHS : RHS);
380a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer    return isNegativeLHS != isNegativeRHS ? -Result : Result;
381e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
382e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
383e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Unsigned divide this APInt by APInt RHS.
384e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Unsigned division function for APInt.
385e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  APInt udiv(const APInt& RHS) const;
386e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
387e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Signed remainder operation on APInt.
388e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Function for signed remainder operation.
389e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  inline APInt srem(const APInt& RHS) const {
39066ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    bool isNegativeLHS = isNegative();
39166ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    bool isNegativeRHS = RHS.isNegative();
392a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer    APInt Result = APIntOps::urem(
393e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer        isNegativeLHS ? -(*this) : (*this), isNegativeRHS ? -RHS : RHS);
394a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer    return isNegativeLHS ? -Result : Result;
395e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
396e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
397e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Unsigned remainder operation on APInt.
398e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Function for unsigned remainder operation.
399e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  APInt urem(const APInt& RHS) const;
400e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
401e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Truncate the APInt to a specified width. It is an error to specify a width
402e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// that is greater than or equal to the current width.
403e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Truncate to new width.
404a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  void trunc(uint32_t width);
405e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
406e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// This operation sign extends the APInt to a new width. If the high order
407e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// bit is set, the fill on the left will be done with 1 bits, otherwise zero.
408e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// It is an error to specify a width that is less than or equal to the
409e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// current width.
410e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Sign extend to a new width.
411a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  void sext(uint32_t width);
412e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
413e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// This operation zero extends the APInt to a new width. Thie high order bits
414e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// are filled with 0 bits.  It is an error to specify a width that is less
415e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// than or equal to the current width.
416e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Zero extend to a new width.
417a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  void zext(uint32_t width);
418e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
419e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Set every bit to 1.
420e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  APInt& set();
421e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
422e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Set the given bit to 1 whose position is given as "bitPosition".
423e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Set a given bit to 1.
424a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt& set(uint32_t bitPosition);
425e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
426e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Set every bit to 0.
427e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  APInt& clear();
428e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
429e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Set the given bit to 0 whose position is given as "bitPosition".
430e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Set a given bit to 0.
431a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt& clear(uint32_t bitPosition);
432e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
433e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Toggle every bit to its opposite value.
434e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  APInt& flip();
435e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
436e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Toggle a given bit to its opposite value whose position is given
437e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// as "bitPosition".
438e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Toggles a given bit to its opposite value.
439a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt& flip(uint32_t bitPosition);
440e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer
441e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// This function returns the number of active bits which is defined as the
442e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// bit width minus the number of leading zeros. This is used in several
443e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// computations to see how "wide" the value is.
444e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Compute the number of active bits in the value
445a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  inline uint32_t getActiveBits() const {
446f31c784f2774311d1f7194ac4ca86262197a8099Reid Spencer    return BitWidth - countLeadingZeros();
447e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
448d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
44931a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// This method attempts to return the value of this APInt as a zero extended
45031a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// uint64_t. The bitwidth must be <= 64 or the value must fit within a
45131a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// uint64_t. Otherwise an assertion will result.
45231a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// @brief Get zero extended value
45331a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  inline uint64_t getZExtValue() const {
454d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng    if (isSingleWord())
45531a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer      return VAL;
45631a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer    assert(getActiveBits() <= 64 && "Too many bits for uint64_t");
45731a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer    return pVal[0];
45831a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  }
45931a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer
46031a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// This method attempts to return the value of this APInt as a sign extended
46131a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// int64_t. The bit width must be <= 64 or the value must fit within an
46231a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// int64_t. Otherwise an assertion will result.
46331a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// @brief Get sign extended value
46431a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  inline int64_t getSExtValue() const {
46531a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer    if (isSingleWord())
46631a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer      return int64_t(VAL << (APINT_BITS_PER_WORD - BitWidth)) >>
46731a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer                     (APINT_BITS_PER_WORD - BitWidth);
46831a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer    assert(getActiveBits() <= 64 && "Too many bits for int64_t");
469946bca5bae2539ca55f8fb4700bff8b5e3f5a7ebReid Spencer    return int64_t(pVal[0]);
470d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  }
471d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
47266ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @brief Gets maximum unsigned value of APInt for specific bit width.
47366ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  static APInt getMaxValue(uint32_t numBits) {
47466ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    return APInt(numBits, 0).set();
47566ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  }
47666ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer
47766ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @brief Gets maximum signed value of APInt for a specific bit width.
47866ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  static APInt getSignedMaxValue(uint32_t numBits) {
47966ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    return APInt(numBits, 0).set().clear(numBits - 1);
48066ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  }
48166ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer
48266ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @brief Gets minimum unsigned value of APInt for a specific bit width.
48366ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  static APInt getMinValue(uint32_t numBits) {
48466ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    return APInt(numBits, 0);
48566ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  }
486d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
48766ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @brief Gets minimum signed value of APInt for a specific bit width.
48866ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  static APInt getSignedMinValue(uint32_t numBits) {
48966ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    return APInt(numBits, 0).set(numBits - 1);
49066ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  }
491d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
492d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns the all-ones value for an APInt of the specified bit-width.
493d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @brief Get the all-ones value.
49466ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  static APInt getAllOnesValue(uint32_t numBits) {
49566ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    return APInt(numBits, 0).set();
49666ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  }
497d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
498db3faa64ee89d537ca1b1410dd841ef51e957540Reid Spencer  /// @returns the '0' value for an APInt of the specified bit-width.
499db3faa64ee89d537ca1b1410dd841ef51e957540Reid Spencer  /// @brief Get the '0' value.
50066ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  static APInt getNullValue(uint32_t numBits) {
50166ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    return APInt(numBits, 0);
50266ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  }
503db3faa64ee89d537ca1b1410dd841ef51e957540Reid Spencer
50431a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// The hash value is computed as the sum of the words and the bit width.
50531a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// @returns A hash value computed from the sum of the APInt words.
50631a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  /// @brief Get a hash value based on this APInt
50731a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer  uint64_t getHashValue() const;
50831a81f0190179b19dc72302dfea05cd1c2f0d22eReid Spencer
509e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// This converts the APInt to a boolean valy as a test against zero.
510e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// @brief Boolean conversion function.
511e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  inline bool getBoolValue() const {
512e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return countLeadingZeros() != BitWidth;
513e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
514d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
515f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// This checks to see if the value has all bits of the APInt are set or not.
516f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// @brief Determine if all bits are set
517f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  inline bool isAllOnesValue() const {
518f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer    return countPopulation() == BitWidth;
519f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  }
520f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer
521f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// This checks to see if the value of this APInt is the maximum unsigned
522f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// value for the APInt's bit width.
523f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// @brief Determine if this is the largest unsigned value.
524f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  bool isMaxValue() const {
525f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer    return countPopulation() == BitWidth;
526f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  }
527f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer
528f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// This checks to see if the value of this APInt is the maximum signed
529f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// value for the APInt's bit width.
530f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// @brief Determine if this is the largest signed value.
531f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  bool isMaxSignedValue() const {
532f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer    return BitWidth == 1 ? VAL == 0 :
533f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer                          !isNegative() && countPopulation() == BitWidth - 1;
534f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  }
535f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer
536f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// This checks to see if the value of this APInt is the minimum signed
537f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// value for the APInt's bit width.
538f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// @brief Determine if this is the smallest unsigned value.
539f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  bool isMinValue() const {
540f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer    return countPopulation() == 0;
541f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  }
542f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer
543f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// This checks to see if the value of this APInt is the minimum signed
544f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// value for the APInt's bit width.
545f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  /// @brief Determine if this is the smallest signed value.
546f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  bool isMinSignedValue() const {
547f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer    return BitWidth == 1 ? VAL == 1 :
548f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer                           isNegative() && countPopulation() == 1;
549f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer  }
550f99705e8985bbd4ff5786f5fc9d843d5de38a3d4Reid Spencer
55166ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// This is used internally to convert an APInt to a string.
55266ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @brief Converts an APInt to a std::string
55366ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  std::string toString(uint8_t radix, bool wantSigned) const;
55466ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer
55566ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// Considers the APInt to be unsigned and converts it into a string in the
55666ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// radix given. The radix can be 2, 8, 10 or 16.
55766ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @returns a character interpretation of the APInt
55866ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @brief Convert unsigned APInt to string representation.
55966ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  inline std::string toString(uint8_t radix = 10) const {
56066ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    return toString(radix, false);
56166ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  }
56266ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer
56366ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// Considers the APInt to be unsigned and converts it into a string in the
56466ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// radix given. The radix can be 2, 8, 10 or 16.
56566ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @returns a character interpretation of the APInt
56666ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @brief Convert unsigned APInt to string representation.
56766ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  inline std::string toStringSigned(uint8_t radix = 10) const {
56866ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    return toString(radix, true);
56966ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  }
570d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
571e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Get an APInt with the same BitWidth as this APInt, just zero mask
5727406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// the low bits and right shift to the least significant bit.
573d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns the high "numBits" bits of this APInt.
574a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt getHiBits(uint32_t numBits) const;
575d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
576e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  /// Get an APInt with the same BitWidth as this APInt, just zero mask
5777406dcdc2981ae864a22ba34f96d1db5e3a4cf87Zhou Sheng  /// the high bits.
578d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns the low "numBits" bits of this APInt.
579a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  APInt getLoBits(uint32_t numBits) const;
580d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
581d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns true if the argument APInt value is a power of two > 0.
582cd6f2bfc268add3dd54cbdf98b2a2c4862fe4ba5Reid Spencer  bool isPowerOf2() const;
583d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
584c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// countLeadingZeros - This function is an APInt version of the
585c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// countLeadingZeros_{32,64} functions in MathExtras.h. It counts the number
586c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// of zeros from the most significant bit to the first one bit.
587c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// @returns getNumWords() * APINT_BITS_PER_WORD if the value is zero.
588d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns the number of zeros from the most significant bit to the first
589d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// one bits.
590c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// @brief Count the number of trailing one bits.
591a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  uint32_t countLeadingZeros() const;
592d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
593c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// countTrailingZeros - This function is an APInt version of the
594c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// countTrailingZoers_{32,64} functions in MathExtras.h. It counts
595c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// the number of zeros from the least significant bit to the first one bit.
596c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// @returns getNumWords() * APINT_BITS_PER_WORD if the value is zero.
597d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns the number of zeros from the least significant bit to the first
598d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// one bit.
599c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// @brief Count the number of trailing zero bits.
600a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  uint32_t countTrailingZeros() const;
601d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
602c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// countPopulation - This function is an APInt version of the
603c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// countPopulation_{32,64} functions in MathExtras.h. It counts the number
604c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// of 1 bits in the APInt value.
605c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// @returns 0 if the value is zero.
606d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns the number of set bits.
607c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer  /// @brief Count the number of bits set.
608a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  uint32_t countPopulation() const;
609d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
610d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng  /// @returns the total number of bits.
611a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  inline uint32_t getBitWidth() const {
612e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return BitWidth;
613e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  }
614d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
615ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng  /// @brief Check if this APInt has a N-bits integer value.
616a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  inline bool isIntN(uint32_t N) const {
617b04973edfaffb12905f58379d632f0d7e4bb5d9bZhou Sheng    assert(N && "N == 0 ???");
618ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng    if (isSingleWord()) {
619b04973edfaffb12905f58379d632f0d7e4bb5d9bZhou Sheng      return VAL == (VAL & (~0ULL >> (64 - N)));
620ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng    } else {
621e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer      APInt Tmp(N, getNumWords(), pVal);
622ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng      return Tmp == (*this);
623ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng    }
624ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng  }
625ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng
626ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng  /// @returns a byte-swapped representation of this APInt Value.
627e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  APInt byteSwap() const;
628ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng
629ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng  /// @returns the floor log base 2 of this APInt.
630a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencer  inline uint32_t logBase2() const {
631e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer    return getNumWords() * APINT_BITS_PER_WORD - 1 - countLeadingZeros();
632ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng  }
633ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng
634d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng  /// @brief Converts this APInt to a double value.
63566ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  double roundToDouble(bool isSigned) const;
63666ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer
63766ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @brief Converts this unsigned APInt to a double value.
63866ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  double roundToDouble() const {
63966ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    return roundToDouble(false);
64066ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  }
641ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng
64266ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  /// @brief Converts this signed APInt to a double value.
64366ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  double signedRoundToDouble() const {
64466ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer    return roundToDouble(true);
64566ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  }
646d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng};
647d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
6480b706b18bd0a7760d971727460a1f26bff8289b0Zhou Shengnamespace APIntOps {
6490b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
650d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// @brief Check if the specified APInt has a N-bits integer value.
651a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencerinline bool isIntN(uint32_t N, const APInt& APIVal) {
652e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return APIVal.isIntN(N);
653d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng}
654d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
655d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// @returns true if the argument APInt value is a sequence of ones
656d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// starting at the least significant bit with the remainder zero.
657a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencerinline const bool isMask(uint32_t numBits, const APInt& APIVal) {
658e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return APIVal.getBoolValue() && ((APIVal + APInt(numBits,1)) & APIVal) == 0;
659d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng}
660d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
661d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// @returns true if the argument APInt value contains a sequence of ones
662d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// with the remainder zero.
663a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencerinline const bool isShiftedMask(uint32_t numBits, const APInt& APIVal) {
664e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return isMask(numBits, (APIVal - APInt(numBits,1)) | APIVal);
665d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng}
666d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
667d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// @returns a byte-swapped representation of the specified APInt Value.
668e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencerinline APInt byteSwap(const APInt& APIVal) {
669e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return APIVal.byteSwap();
670ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng}
671d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
672d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng/// @returns the floor log base 2 of the specified APInt value.
673a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencerinline uint32_t logBase2(const APInt& APIVal) {
674e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return APIVal.logBase2();
675d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng}
676d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
677c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer/// GreatestCommonDivisor - This function returns the greatest common
678c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer/// divisor of the two APInt values using Enclid's algorithm.
679c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer/// @returns the greatest common divisor of Val1 and Val2
680c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer/// @brief Compute GCD of two APInt values.
681c68c2243dcb716bc117f41aa543ca8a41046df41Reid SpencerAPInt GreatestCommonDivisor(const APInt& Val1, const APInt& Val2);
682d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
68366ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer/// Treats the APInt as an unsigned value for conversion purposes.
68466ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer/// @brief Converts the given APInt to a double value.
68566ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencerinline double RoundAPIntToDouble(const APInt& APIVal) {
68666ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  return APIVal.roundToDouble();
68766ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer}
68866ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer
68966ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer/// Treats the APInt as a signed value for conversion purposes.
690d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng/// @brief Converts the given APInt to a double value.
69166ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencerinline double RoundSignedAPIntToDouble(const APInt& APIVal) {
69266ed1099ff3591c61e008198bb5a30862e778fc0Reid Spencer  return APIVal.signedRoundToDouble();
693d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng}
694d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng
695d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng/// @brief Converts the given APInt to a float vlalue.
696e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencerinline float RoundAPIntToFloat(const APInt& APIVal) {
697e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return float(RoundAPIntToDouble(APIVal));
698d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng}
699d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng
700c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer/// RoundDoubleToAPInt - This function convert a double value to an APInt value.
701d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng/// @brief Converts the given double value into a APInt.
702409f092766e61ab317e46aec37b4a9234ead9b5aReid SpencerAPInt RoundDoubleToAPInt(double Double, uint32_t width = 64);
703d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng
704c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer/// RoundFloatToAPInt - Converts a float value into an APInt value.
705c68c2243dcb716bc117f41aa543ca8a41046df41Reid Spencer/// @brief Converts a float value into a APInt.
706e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencerinline APInt RoundFloatToAPInt(float Float) {
707e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return RoundDoubleToAPInt(double(Float));
708d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng}
709d93f00c35dbd1ea415bb2b39435253aef9428d71Zhou Sheng
7100b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Arithmetic right-shift the APInt by shiftAmt.
7110b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// @brief Arithmetic right-shift function.
712a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencerinline APInt ashr(const APInt& LHS, uint32_t shiftAmt) {
713e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return LHS.ashr(shiftAmt);
714ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng}
7150b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
7160b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Logical right-shift the APInt by shiftAmt.
7170b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// @brief Logical right-shift function.
718a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencerinline APInt lshr(const APInt& LHS, uint32_t shiftAmt) {
719e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return LHS.lshr(shiftAmt);
720ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng}
7210b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
7220b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Left-shift the APInt by shiftAmt.
7230b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// @brief Left-shift function.
724a932e3f799cbf2f689e4987fea543d3f8661e7a8Reid Spencerinline APInt shl(const APInt& LHS, uint32_t shiftAmt) {
725e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return LHS.shl(shiftAmt);
726ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng}
7270b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
7280b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Signed divide APInt LHS by APInt RHS.
7290b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// @brief Signed division function for APInt.
730e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencerinline APInt sdiv(const APInt& LHS, const APInt& RHS) {
731e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return LHS.sdiv(RHS);
7320b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng}
7330b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
7340b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Unsigned divide APInt LHS by APInt RHS.
7350b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// @brief Unsigned division function for APInt.
736e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencerinline APInt udiv(const APInt& LHS, const APInt& RHS) {
737e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return LHS.udiv(RHS);
738ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng}
7390b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
7400b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Signed remainder operation on APInt.
7410b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// @brief Function for signed remainder operation.
742e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencerinline APInt srem(const APInt& LHS, const APInt& RHS) {
743e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return LHS.srem(RHS);
7440b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng}
7450b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
7460b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Unsigned remainder operation on APInt.
7470b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// @brief Function for unsigned remainder operation.
748e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencerinline APInt urem(const APInt& LHS, const APInt& RHS) {
749e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencer  return LHS.urem(RHS);
750ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng}
7510b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
7520b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Performs multiplication on APInt values.
7530b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// @brief Function for multiplication operation.
754e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencerinline APInt mul(const APInt& LHS, const APInt& RHS) {
7550b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng  return LHS * RHS;
7560b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng}
7570b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
7580b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Performs addition on APInt values.
7590b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// @brief Function for addition operation.
760e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencerinline APInt add(const APInt& LHS, const APInt& RHS) {
7610b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng  return LHS + RHS;
7620b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng}
7630b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
7640b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// Performs subtraction on APInt values.
7650b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng/// @brief Function for subtraction operation.
766e81d2dad2c54014d36c73573307db5852c5caf8eReid Spencerinline APInt sub(const APInt& LHS, const APInt& RHS) {
7670b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng  return LHS - RHS;
7680b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng}
7690b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
770ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng/// Performs bitwise AND operation on APInt LHS and
771ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng/// APInt RHS.
772ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng/// @brief Bitwise AND function for APInt.
773ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Shenginline APInt And(const APInt& LHS, const APInt& RHS) {
774ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng  return LHS & RHS;
775ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng}
776ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng
777ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng/// Performs bitwise OR operation on APInt LHS and APInt RHS.
778ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng/// @brief Bitwise OR function for APInt.
779ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Shenginline APInt Or(const APInt& LHS, const APInt& RHS) {
780ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng  return LHS | RHS;
781ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng}
782ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng
783ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng/// Performs bitwise XOR operation on APInt.
784ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng/// @brief Bitwise XOR function for APInt.
785ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Shenginline APInt Xor(const APInt& LHS, const APInt& RHS) {
786ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng  return LHS ^ RHS;
787ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng}
788ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng
789ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng/// Performs a bitwise complement operation on APInt.
790ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng/// @brief Bitwise complement function.
791ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Shenginline APInt Not(const APInt& APIVal) {
792ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng  return ~APIVal;
793ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng}
794ff4304f8243f55e2e5c63bc95517cd38ff9295e1Zhou Sheng
7950b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng} // End of APIntOps namespace
7960b706b18bd0a7760d971727460a1f26bff8289b0Zhou Sheng
797d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng} // End of llvm namespace
798d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng
799d0f285e212c47ac71af842bb39ea5364f1e556b4Zhou Sheng#endif
800