LLVM  10.0.0svn
APSInt.h
Go to the documentation of this file.
1 //===-- llvm/ADT/APSInt.h - Arbitrary Precision Signed Int -----*- 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 // This file implements the APSInt class, which is a simple class that
10 // represents an arbitrary sized integer that knows its signedness.
11 //
12 //===----------------------------------------------------------------------===//
13 
14 #ifndef LLVM_ADT_APSINT_H
15 #define LLVM_ADT_APSINT_H
16 
17 #include "llvm/ADT/APInt.h"
18 
19 namespace llvm {
20 
21 class LLVM_NODISCARD APSInt : public APInt {
22  bool IsUnsigned;
23 
24 public:
25  /// Default constructor that creates an uninitialized APInt.
26  explicit APSInt() : IsUnsigned(false) {}
27 
28  /// APSInt ctor - Create an APSInt with the specified width, default to
29  /// unsigned.
30  explicit APSInt(uint32_t BitWidth, bool isUnsigned = true)
31  : APInt(BitWidth, 0), IsUnsigned(isUnsigned) {}
32 
33  explicit APSInt(APInt I, bool isUnsigned = true)
34  : APInt(std::move(I)), IsUnsigned(isUnsigned) {}
35 
36  /// Construct an APSInt from a string representation.
37  ///
38  /// This constructor interprets the string \p Str using the radix of 10.
39  /// The interpretation stops at the end of the string. The bit width of the
40  /// constructed APSInt is determined automatically.
41  ///
42  /// \param Str the string to be interpreted.
43  explicit APSInt(StringRef Str);
44 
45  /// Determine sign of this APSInt.
46  ///
47  /// \returns true if this APSInt is negative, false otherwise
48  bool isNegative() const { return isSigned() && APInt::isNegative(); }
49 
50  /// Determine if this APSInt Value is non-negative (>= 0)
51  ///
52  /// \returns true if this APSInt is non-negative, false otherwise
53  bool isNonNegative() const { return !isNegative(); }
54 
55  /// Determine if this APSInt Value is positive.
56  ///
57  /// This tests if the value of this APSInt is positive (> 0). Note
58  /// that 0 is not a positive value.
59  ///
60  /// \returns true if this APSInt is positive.
61  bool isStrictlyPositive() const { return isNonNegative() && !isNullValue(); }
62 
64  // Retain our current sign.
65  APInt::operator=(std::move(RHS));
66  return *this;
67  }
68 
69  APSInt &operator=(uint64_t RHS) {
70  // Retain our current sign.
71  APInt::operator=(RHS);
72  return *this;
73  }
74 
75  // Query sign information.
76  bool isSigned() const { return !IsUnsigned; }
77  bool isUnsigned() const { return IsUnsigned; }
78  void setIsUnsigned(bool Val) { IsUnsigned = Val; }
79  void setIsSigned(bool Val) { IsUnsigned = !Val; }
80 
81  /// toString - Append this APSInt to the specified SmallString.
82  void toString(SmallVectorImpl<char> &Str, unsigned Radix = 10) const {
83  APInt::toString(Str, Radix, isSigned());
84  }
85  /// toString - Converts an APInt to a std::string. This is an inefficient
86  /// method; you should prefer passing in a SmallString instead.
87  std::string toString(unsigned Radix) const {
88  return APInt::toString(Radix, isSigned());
89  }
90  using APInt::toString;
91 
92  /// Get the correctly-extended \c int64_t value.
93  int64_t getExtValue() const {
94  assert(getMinSignedBits() <= 64 && "Too many bits for int64_t");
95  return isSigned() ? getSExtValue() : getZExtValue();
96  }
97 
98  APSInt trunc(uint32_t width) const {
99  return APSInt(APInt::trunc(width), IsUnsigned);
100  }
101 
102  APSInt extend(uint32_t width) const {
103  if (IsUnsigned)
104  return APSInt(zext(width), IsUnsigned);
105  else
106  return APSInt(sext(width), IsUnsigned);
107  }
108 
109  APSInt extOrTrunc(uint32_t width) const {
110  if (IsUnsigned)
111  return APSInt(zextOrTrunc(width), IsUnsigned);
112  else
113  return APSInt(sextOrTrunc(width), IsUnsigned);
114  }
115 
116  const APSInt &operator%=(const APSInt &RHS) {
117  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
118  if (IsUnsigned)
119  *this = urem(RHS);
120  else
121  *this = srem(RHS);
122  return *this;
123  }
124  const APSInt &operator/=(const APSInt &RHS) {
125  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
126  if (IsUnsigned)
127  *this = udiv(RHS);
128  else
129  *this = sdiv(RHS);
130  return *this;
131  }
132  APSInt operator%(const APSInt &RHS) const {
133  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
134  return IsUnsigned ? APSInt(urem(RHS), true) : APSInt(srem(RHS), false);
135  }
136  APSInt operator/(const APSInt &RHS) const {
137  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
138  return IsUnsigned ? APSInt(udiv(RHS), true) : APSInt(sdiv(RHS), false);
139  }
140 
141  APSInt operator>>(unsigned Amt) const {
142  return IsUnsigned ? APSInt(lshr(Amt), true) : APSInt(ashr(Amt), false);
143  }
144  APSInt& operator>>=(unsigned Amt) {
145  if (IsUnsigned)
146  lshrInPlace(Amt);
147  else
148  ashrInPlace(Amt);
149  return *this;
150  }
151 
152  inline bool operator<(const APSInt& RHS) const {
153  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
154  return IsUnsigned ? ult(RHS) : slt(RHS);
155  }
156  inline bool operator>(const APSInt& RHS) const {
157  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
158  return IsUnsigned ? ugt(RHS) : sgt(RHS);
159  }
160  inline bool operator<=(const APSInt& RHS) const {
161  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
162  return IsUnsigned ? ule(RHS) : sle(RHS);
163  }
164  inline bool operator>=(const APSInt& RHS) const {
165  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
166  return IsUnsigned ? uge(RHS) : sge(RHS);
167  }
168  inline bool operator==(const APSInt& RHS) const {
169  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
170  return eq(RHS);
171  }
172  inline bool operator!=(const APSInt& RHS) const {
173  return !((*this) == RHS);
174  }
175 
176  bool operator==(int64_t RHS) const {
177  return compareValues(*this, get(RHS)) == 0;
178  }
179  bool operator!=(int64_t RHS) const {
180  return compareValues(*this, get(RHS)) != 0;
181  }
182  bool operator<=(int64_t RHS) const {
183  return compareValues(*this, get(RHS)) <= 0;
184  }
185  bool operator>=(int64_t RHS) const {
186  return compareValues(*this, get(RHS)) >= 0;
187  }
188  bool operator<(int64_t RHS) const {
189  return compareValues(*this, get(RHS)) < 0;
190  }
191  bool operator>(int64_t RHS) const {
192  return compareValues(*this, get(RHS)) > 0;
193  }
194 
195  // The remaining operators just wrap the logic of APInt, but retain the
196  // signedness information.
197 
198  APSInt operator<<(unsigned Bits) const {
199  return APSInt(static_cast<const APInt&>(*this) << Bits, IsUnsigned);
200  }
201  APSInt& operator<<=(unsigned Amt) {
202  static_cast<APInt&>(*this) <<= Amt;
203  return *this;
204  }
205 
207  ++(static_cast<APInt&>(*this));
208  return *this;
209  }
211  --(static_cast<APInt&>(*this));
212  return *this;
213  }
215  return APSInt(++static_cast<APInt&>(*this), IsUnsigned);
216  }
218  return APSInt(--static_cast<APInt&>(*this), IsUnsigned);
219  }
220  APSInt operator-() const {
221  return APSInt(-static_cast<const APInt&>(*this), IsUnsigned);
222  }
223  APSInt& operator+=(const APSInt& RHS) {
224  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
225  static_cast<APInt&>(*this) += RHS;
226  return *this;
227  }
228  APSInt& operator-=(const APSInt& RHS) {
229  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
230  static_cast<APInt&>(*this) -= RHS;
231  return *this;
232  }
233  APSInt& operator*=(const APSInt& RHS) {
234  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
235  static_cast<APInt&>(*this) *= RHS;
236  return *this;
237  }
238  APSInt& operator&=(const APSInt& RHS) {
239  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
240  static_cast<APInt&>(*this) &= RHS;
241  return *this;
242  }
243  APSInt& operator|=(const APSInt& RHS) {
244  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
245  static_cast<APInt&>(*this) |= RHS;
246  return *this;
247  }
248  APSInt& operator^=(const APSInt& RHS) {
249  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
250  static_cast<APInt&>(*this) ^= RHS;
251  return *this;
252  }
253 
254  APSInt operator&(const APSInt& RHS) const {
255  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
256  return APSInt(static_cast<const APInt&>(*this) & RHS, IsUnsigned);
257  }
258 
259  APSInt operator|(const APSInt& RHS) const {
260  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
261  return APSInt(static_cast<const APInt&>(*this) | RHS, IsUnsigned);
262  }
263 
264  APSInt operator^(const APSInt &RHS) const {
265  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
266  return APSInt(static_cast<const APInt&>(*this) ^ RHS, IsUnsigned);
267  }
268 
269  APSInt operator*(const APSInt& RHS) const {
270  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
271  return APSInt(static_cast<const APInt&>(*this) * RHS, IsUnsigned);
272  }
273  APSInt operator+(const APSInt& RHS) const {
274  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
275  return APSInt(static_cast<const APInt&>(*this) + RHS, IsUnsigned);
276  }
277  APSInt operator-(const APSInt& RHS) const {
278  assert(IsUnsigned == RHS.IsUnsigned && "Signedness mismatch!");
279  return APSInt(static_cast<const APInt&>(*this) - RHS, IsUnsigned);
280  }
281  APSInt operator~() const {
282  return APSInt(~static_cast<const APInt&>(*this), IsUnsigned);
283  }
284 
285  /// getMaxValue - Return the APSInt representing the maximum integer value
286  /// with the given bit width and signedness.
287  static APSInt getMaxValue(uint32_t numBits, bool Unsigned) {
288  return APSInt(Unsigned ? APInt::getMaxValue(numBits)
289  : APInt::getSignedMaxValue(numBits), Unsigned);
290  }
291 
292  /// getMinValue - Return the APSInt representing the minimum integer value
293  /// with the given bit width and signedness.
294  static APSInt getMinValue(uint32_t numBits, bool Unsigned) {
295  return APSInt(Unsigned ? APInt::getMinValue(numBits)
296  : APInt::getSignedMinValue(numBits), Unsigned);
297  }
298 
299  /// Determine if two APSInts have the same value, zero- or
300  /// sign-extending as needed.
301  static bool isSameValue(const APSInt &I1, const APSInt &I2) {
302  return !compareValues(I1, I2);
303  }
304 
305  /// Compare underlying values of two numbers.
306  static int compareValues(const APSInt &I1, const APSInt &I2) {
307  if (I1.getBitWidth() == I2.getBitWidth() && I1.isSigned() == I2.isSigned())
308  return I1.IsUnsigned ? I1.compare(I2) : I1.compareSigned(I2);
309 
310  // Check for a bit-width mismatch.
311  if (I1.getBitWidth() > I2.getBitWidth())
312  return compareValues(I1, I2.extend(I1.getBitWidth()));
313  if (I2.getBitWidth() > I1.getBitWidth())
314  return compareValues(I1.extend(I2.getBitWidth()), I2);
315 
316  // We have a signedness mismatch. Check for negative values and do an
317  // unsigned compare if both are positive.
318  if (I1.isSigned()) {
319  assert(!I2.isSigned() && "Expected signed mismatch");
320  if (I1.isNegative())
321  return -1;
322  } else {
323  assert(I2.isSigned() && "Expected signed mismatch");
324  if (I2.isNegative())
325  return 1;
326  }
327 
328  return I1.compare(I2);
329  }
330 
331  static APSInt get(int64_t X) { return APSInt(APInt(64, X), false); }
332  static APSInt getUnsigned(uint64_t X) { return APSInt(APInt(64, X), true); }
333 
334  /// Profile - Used to insert APSInt objects, or objects that contain APSInt
335  /// objects, into FoldingSets.
336  void Profile(FoldingSetNodeID& ID) const;
337 };
338 
339 inline bool operator==(int64_t V1, const APSInt &V2) { return V2 == V1; }
340 inline bool operator!=(int64_t V1, const APSInt &V2) { return V2 != V1; }
341 inline bool operator<=(int64_t V1, const APSInt &V2) { return V2 >= V1; }
342 inline bool operator>=(int64_t V1, const APSInt &V2) { return V2 <= V1; }
343 inline bool operator<(int64_t V1, const APSInt &V2) { return V2 > V1; }
344 inline bool operator>(int64_t V1, const APSInt &V2) { return V2 < V1; }
345 
346 inline raw_ostream &operator<<(raw_ostream &OS, const APSInt &I) {
347  I.print(OS, I.isSigned());
348  return OS;
349 }
350 
351 } // end namespace llvm
352 
353 #endif
APSInt operator-() const
Definition: APSInt.h:220
static GCMetadataPrinterRegistry::Add< ErlangGCPrinter > X("erlang", "erlang-compatible garbage collector")
const APSInt & operator/=(const APSInt &RHS)
Definition: APSInt.h:124
bool isNonNegative() const
Determine if this APSInt Value is non-negative (>= 0)
Definition: APSInt.h:53
APSInt & operator-=(const APSInt &RHS)
Definition: APSInt.h:228
This class represents lattice values for constants.
Definition: AllocatorList.h:23
APSInt operator/(const APSInt &RHS) const
Definition: APSInt.h:136
bool operator>(int64_t V1, const APSInt &V2)
Definition: APSInt.h:344
bool operator!=(int64_t RHS) const
Definition: APSInt.h:179
APSInt()
Default constructor that creates an uninitialized APInt.
Definition: APSInt.h:26
bool operator<=(int64_t RHS) const
Definition: APSInt.h:182
APSInt(uint32_t BitWidth, bool isUnsigned=true)
APSInt ctor - Create an APSInt with the specified width, default to unsigned.
Definition: APSInt.h:30
void setIsSigned(bool Val)
Definition: APSInt.h:79
APInt trunc(unsigned width) const
Truncate to new width.
Definition: APInt.cpp:865
APInt operator &(APInt a, const APInt &b)
Definition: APInt.h:1987
APSInt & operator^=(const APSInt &RHS)
Definition: APSInt.h:248
static APInt getSignedMaxValue(unsigned numBits)
Gets maximum signed value of APInt for a specific bit width.
Definition: APInt.h:534
void setIsUnsigned(bool Val)
Definition: APSInt.h:78
unsigned getBitWidth() const
Return the number of bits in the APInt.
Definition: APInt.h:1517
bool operator<=(int64_t V1, const APSInt &V2)
Definition: APSInt.h:341
Definition: BitVector.h:937
bool operator>=(int64_t V1, const APSInt &V2)
Definition: APSInt.h:342
APSInt & operator--()
Definition: APSInt.h:210
APSInt extend(uint32_t width) const
Definition: APSInt.h:102
APSInt extOrTrunc(uint32_t width) const
Definition: APSInt.h:109
This file implements a class to represent arbitrary precision integral constant values and operations...
APSInt & operator<<=(unsigned Amt)
Definition: APSInt.h:201
bool operator<=(const APSInt &RHS) const
Definition: APSInt.h:160
APSInt operator^(const APSInt &RHS) const
Definition: APSInt.h:264
APSInt & operator*=(const APSInt &RHS)
Definition: APSInt.h:233
bool operator<(const APSInt &RHS) const
Definition: APSInt.h:152
APSInt operator*(const APSInt &RHS) const
Definition: APSInt.h:269
bool operator!=(const APSInt &RHS) const
Definition: APSInt.h:172
static bool isSameValue(const APSInt &I1, const APSInt &I2)
Determine if two APSInts have the same value, zero- or sign-extending as needed.
Definition: APSInt.h:301
FoldingSetNodeID - This class is used to gather all the unique data bits of a node.
Definition: FoldingSet.h:305
bool isNegative() const
Determine sign of this APInt.
Definition: APInt.h:363
APSInt operator--(int)
Definition: APSInt.h:217
bool isSigned() const
Definition: APSInt.h:76
APSInt trunc(uint32_t width) const
Definition: APSInt.h:98
APInt & operator=(const APInt &RHS)
Copy assignment operator.
Definition: APInt.h:734
APSInt operator++(int)
Definition: APSInt.h:214
APSInt & operator++()
Definition: APSInt.h:206
APSInt operator|(const APSInt &RHS) const
Definition: APSInt.h:259
APSInt & operator=(uint64_t RHS)
Definition: APSInt.h:69
int64_t getExtValue() const
Get the correctly-extended int64_t value.
Definition: APSInt.h:93
bool operator>(const APSInt &RHS) const
Definition: APSInt.h:156
static APSInt getMaxValue(uint32_t numBits, bool Unsigned)
getMaxValue - Return the APSInt representing the maximum integer value with the given bit width and s...
Definition: APSInt.h:287
bool isStrictlyPositive() const
Determine if this APSInt Value is positive.
Definition: APSInt.h:61
static APSInt getMinValue(uint32_t numBits, bool Unsigned)
getMinValue - Return the APSInt representing the minimum integer value with the given bit width and s...
Definition: APSInt.h:294
APSInt & operator|=(const APSInt &RHS)
Definition: APSInt.h:243
bool operator==(const APSInt &RHS) const
Definition: APSInt.h:168
APSInt operator>>(unsigned Amt) const
Definition: APSInt.h:141
static APInt getMinValue(unsigned numBits)
Gets minimum unsigned value of APInt for a specific bit width.
Definition: APInt.h:541
void print(raw_ostream &OS, bool isSigned) const
Definition: APInt.cpp:2234
bool isUnsigned() const
Definition: APSInt.h:77
std::string toString(unsigned Radix) const
toString - Converts an APInt to a std::string.
Definition: APSInt.h:87
APSInt operator%(const APSInt &RHS) const
Definition: APSInt.h:132
Class for arbitrary precision integers.
Definition: APInt.h:69
static APInt getMaxValue(unsigned numBits)
Gets maximum unsigned value of APInt for specific bit width.
Definition: APInt.h:529
bool operator>(int64_t RHS) const
Definition: APSInt.h:191
const APSInt & operator%=(const APSInt &RHS)
Definition: APSInt.h:116
bool operator!=(uint64_t V1, const APInt &V2)
Definition: APInt.h:1977
APSInt operator<<(unsigned Bits) const
Definition: APSInt.h:198
bool isNegative() const
Determine sign of this APSInt.
Definition: APSInt.h:48
bool operator>=(int64_t RHS) const
Definition: APSInt.h:185
bool operator>=(const APSInt &RHS) const
Definition: APSInt.h:164
APSInt(APInt I, bool isUnsigned=true)
Definition: APSInt.h:33
#define I(x, y, z)
Definition: MD5.cpp:58
raw_ostream & operator<<(raw_ostream &OS, const APInt &I)
Definition: APInt.h:2047
APSInt & operator+=(const APSInt &RHS)
Definition: APSInt.h:223
#define LLVM_NODISCARD
LLVM_NODISCARD - Warn if a type or return value is discarded.
Definition: Compiler.h:145
bool operator==(int64_t RHS) const
Definition: APSInt.h:176
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
static APSInt getUnsigned(uint64_t X)
Definition: APSInt.h:332
static APInt getSignedMinValue(unsigned numBits)
Gets minimum signed value of APInt for a specific bit width.
Definition: APInt.h:544
bool operator<(int64_t V1, const APSInt &V2)
Definition: APSInt.h:343
E & operator &=(E &LHS, E RHS)
Definition: BitmaskEnum.h:133
APSInt operator+(const APSInt &RHS) const
Definition: APSInt.h:273
void toString(SmallVectorImpl< char > &Str, unsigned Radix=10) const
toString - Append this APSInt to the specified SmallString.
Definition: APSInt.h:82
static int compareValues(const APSInt &I1, const APSInt &I2)
Compare underlying values of two numbers.
Definition: APSInt.h:306
This class implements an extremely fast bulk output stream that can only output to a stream...
Definition: raw_ostream.h:45
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:48
APSInt & operator>>=(unsigned Amt)
Definition: APSInt.h:144
bool operator==(uint64_t V1, const APInt &V2)
Definition: APInt.h:1975
APSInt operator-(const APSInt &RHS) const
Definition: APSInt.h:277
APSInt operator~() const
Definition: APSInt.h:281
void toString(SmallVectorImpl< char > &Str, unsigned Radix, bool Signed, bool formatAsCLiteral=false) const
Converts an APInt to a string and append it to Str.
Definition: APInt.cpp:2103
bool operator<(int64_t RHS) const
Definition: APSInt.h:188
APSInt & operator=(APInt RHS)
Definition: APSInt.h:63