forked from OSchip/llvm-project
Eliminates friend function declaration inside APInt, instead, adds public
methods as those global function's internal implementation. llvm-svn: 34083
This commit is contained in:
parent
133ae0b2a6
commit
e93db8fba2
|
@ -24,15 +24,7 @@ namespace llvm {
|
||||||
/// Forward declaration.
|
/// Forward declaration.
|
||||||
class APInt;
|
class APInt;
|
||||||
namespace APIntOps {
|
namespace APIntOps {
|
||||||
bool isIntN(unsigned N, const APInt& APIVal);
|
|
||||||
APInt ByteSwap(const APInt& APIVal);
|
|
||||||
APInt LogBase2(const APInt& APIVal);
|
|
||||||
APInt ashr(const APInt& LHS, unsigned shiftAmt);
|
|
||||||
APInt lshr(const APInt& LHS, unsigned shiftAmt);
|
|
||||||
APInt shl(const APInt& LHS, unsigned shiftAmt);
|
|
||||||
APInt sdiv(const APInt& LHS, const APInt& RHS);
|
|
||||||
APInt udiv(const APInt& LHS, const APInt& RHS);
|
APInt udiv(const APInt& LHS, const APInt& RHS);
|
||||||
APInt srem(const APInt& LHS, const APInt& RHS);
|
|
||||||
APInt urem(const APInt& LHS, const APInt& RHS);
|
APInt urem(const APInt& LHS, const APInt& RHS);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -53,19 +45,6 @@ namespace APIntOps {
|
||||||
/// Note: In this class, all bit/byte/word positions are zero-based.
|
/// Note: In this class, all bit/byte/word positions are zero-based.
|
||||||
///
|
///
|
||||||
class APInt {
|
class APInt {
|
||||||
/// Friend Functions of APInt declared here. For detailed comments,
|
|
||||||
/// see bottom of this file.
|
|
||||||
friend bool APIntOps::isIntN(unsigned N, const APInt& APIVal);
|
|
||||||
friend APInt APIntOps::ByteSwap(const APInt& APIVal);
|
|
||||||
friend APInt APIntOps::LogBase2(const APInt& APIVal);
|
|
||||||
friend APInt APIntOps::ashr(const APInt& LHS, unsigned shiftAmt);
|
|
||||||
friend APInt APIntOps::lshr(const APInt& LHS, unsigned shiftAmt);
|
|
||||||
friend APInt APIntOps::shl(const APInt& LHS, unsigned shiftAmt);
|
|
||||||
friend APInt APIntOps::sdiv(const APInt& LHS, const APInt& RHS);
|
|
||||||
friend APInt APIntOps::udiv(const APInt& LHS, const APInt& RHS);
|
|
||||||
friend APInt APIntOps::srem(const APInt& LHS, const APInt& RHS);
|
|
||||||
friend APInt APIntOps::urem(const APInt& LHS, const APInt& RHS);
|
|
||||||
|
|
||||||
unsigned BitsNum; ///< The number of bits.
|
unsigned BitsNum; ///< The number of bits.
|
||||||
|
|
||||||
/// This union is used to store the integer value. When the
|
/// This union is used to store the integer value. When the
|
||||||
|
@ -387,19 +366,68 @@ public:
|
||||||
inline unsigned getNumBits() const
|
inline unsigned getNumBits() const
|
||||||
{ return BitsNum; }
|
{ return BitsNum; }
|
||||||
|
|
||||||
|
/// @brief Check if this APInt has a N-bits integer value.
|
||||||
|
inline bool isIntN(unsigned N) const {
|
||||||
|
if (isSingleWord()) {
|
||||||
|
return VAL == VAL & (~uint64_t(0ULL) >> (64 - N));
|
||||||
|
} else {
|
||||||
|
APInt Tmp(N, pVal);
|
||||||
|
return Tmp == (*this);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// @returns a byte-swapped representation of this APInt Value.
|
||||||
|
APInt ByteSwap() const;
|
||||||
|
|
||||||
|
/// @returns the floor log base 2 of this APInt.
|
||||||
|
inline unsigned LogBase2() const {
|
||||||
|
return getNumWords() * APINT_BITS_PER_WORD -
|
||||||
|
CountLeadingZeros();
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Arithmetic right-shift this APInt by shiftAmt.
|
||||||
|
/// @brief Arithmetic right-shift function.
|
||||||
|
APInt ashr(unsigned shiftAmt) const;
|
||||||
|
|
||||||
|
/// Logical right-shift this APInt by shiftAmt.
|
||||||
|
/// @brief Logical right-shift function.
|
||||||
|
APInt lshr(unsigned shiftAmt) const;
|
||||||
|
|
||||||
|
/// Left-shift this APInt by shiftAmt.
|
||||||
|
/// @brief Left-shift function.
|
||||||
|
APInt shl(unsigned shiftAmt) const;
|
||||||
|
|
||||||
|
/// Signed divide this APInt by APInt RHS.
|
||||||
|
/// @brief Signed division function for APInt.
|
||||||
|
inline APInt sdiv(const APInt& RHS) const {
|
||||||
|
bool isSignedLHS = (*this)[BitsNum - 1], isSignedRHS = RHS[RHS.BitsNum - 1];
|
||||||
|
APInt API = APIntOps::udiv(isSignedLHS ? -(*this) : (*this), isSignedRHS ? -RHS : RHS);
|
||||||
|
return isSignedLHS != isSignedRHS ? -API : API;;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Unsigned divide this APInt by APInt RHS.
|
||||||
|
/// @brief Unsigned division function for APInt.
|
||||||
|
APInt udiv(const APInt& RHS) const;
|
||||||
|
|
||||||
|
/// Signed remainder operation on APInt.
|
||||||
|
/// @brief Function for signed remainder operation.
|
||||||
|
inline APInt srem(const APInt& RHS) const {
|
||||||
|
bool isSignedLHS = (*this)[BitsNum - 1], isSignedRHS = RHS[RHS.BitsNum - 1];
|
||||||
|
APInt API = APIntOps::urem(isSignedLHS ? -(*this) : (*this), isSignedRHS ? -RHS : RHS);
|
||||||
|
return isSignedLHS ? -API : API;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Unsigned remainder operation on APInt.
|
||||||
|
/// @brief Function for unsigned remainder operation.
|
||||||
|
APInt urem(const APInt& RHS) const;
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
namespace APIntOps {
|
namespace APIntOps {
|
||||||
|
|
||||||
/// @brief Check if the specified APInt has a N-bits integer value.
|
/// @brief Check if the specified APInt has a N-bits integer value.
|
||||||
inline bool isIntN(unsigned N, const APInt& APIVal) {
|
inline bool isIntN(unsigned N, const APInt& APIVal) {
|
||||||
if (APIVal.isSingleWord()) {
|
return APIVal.isIntN(N);
|
||||||
APInt Tmp(N, APIVal.VAL);
|
|
||||||
return Tmp == APIVal;
|
|
||||||
} else {
|
|
||||||
APInt Tmp(N, APIVal.pVal);
|
|
||||||
return Tmp == APIVal;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// @returns true if the argument APInt value is a sequence of ones
|
/// @returns true if the argument APInt value is a sequence of ones
|
||||||
|
@ -415,12 +443,13 @@ inline const bool isShiftedMask(unsigned numBits, const APInt& APIVal) {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// @returns a byte-swapped representation of the specified APInt Value.
|
/// @returns a byte-swapped representation of the specified APInt Value.
|
||||||
APInt ByteSwap(const APInt& APIVal);
|
inline APInt ByteSwap(const APInt& APIVal) {
|
||||||
|
return APIVal.ByteSwap();
|
||||||
|
}
|
||||||
|
|
||||||
/// @returns the floor log base 2 of the specified APInt value.
|
/// @returns the floor log base 2 of the specified APInt value.
|
||||||
inline APInt LogBase2(const APInt& APIVal) {
|
inline unsigned LogBase2(const APInt& APIVal) {
|
||||||
return APIVal.getNumWords() * APInt::APINT_BITS_PER_WORD -
|
return APIVal.LogBase2();
|
||||||
APIVal.CountLeadingZeros();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// @returns the greatest common divisor of the two values
|
/// @returns the greatest common divisor of the two values
|
||||||
|
@ -429,39 +458,45 @@ APInt GreatestCommonDivisor(const APInt& API1, const APInt& API2);
|
||||||
|
|
||||||
/// Arithmetic right-shift the APInt by shiftAmt.
|
/// Arithmetic right-shift the APInt by shiftAmt.
|
||||||
/// @brief Arithmetic right-shift function.
|
/// @brief Arithmetic right-shift function.
|
||||||
APInt ashr(const APInt& LHS, unsigned shiftAmt);
|
inline APInt ashr(const APInt& LHS, unsigned shiftAmt) {
|
||||||
|
return LHS.ashr(shiftAmt);
|
||||||
|
}
|
||||||
|
|
||||||
/// Logical right-shift the APInt by shiftAmt.
|
/// Logical right-shift the APInt by shiftAmt.
|
||||||
/// @brief Logical right-shift function.
|
/// @brief Logical right-shift function.
|
||||||
APInt lshr(const APInt& LHS, unsigned shiftAmt);
|
inline APInt lshr(const APInt& LHS, unsigned shiftAmt) {
|
||||||
|
return LHS.lshr(shiftAmt);
|
||||||
|
}
|
||||||
|
|
||||||
/// Left-shift the APInt by shiftAmt.
|
/// Left-shift the APInt by shiftAmt.
|
||||||
/// @brief Left-shift function.
|
/// @brief Left-shift function.
|
||||||
APInt shl(const APInt& LHS, unsigned shiftAmt);
|
inline APInt shl(const APInt& LHS, unsigned shiftAmt) {
|
||||||
|
return LHS.shl(shiftAmt);
|
||||||
|
}
|
||||||
|
|
||||||
/// Signed divide APInt LHS by APInt RHS.
|
/// Signed divide APInt LHS by APInt RHS.
|
||||||
/// @brief Signed division function for APInt.
|
/// @brief Signed division function for APInt.
|
||||||
inline APInt sdiv(const APInt& LHS, const APInt& RHS) {
|
inline APInt sdiv(const APInt& LHS, const APInt& RHS) {
|
||||||
bool isSignedLHS = LHS[LHS.BitsNum - 1], isSignedRHS = RHS[RHS.BitsNum - 1];
|
return LHS.sdiv(RHS);
|
||||||
APInt API = udiv(isSignedLHS ? -LHS : LHS, isSignedRHS ? -RHS : RHS);
|
|
||||||
return isSignedLHS != isSignedRHS ? -API : API;;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Unsigned divide APInt LHS by APInt RHS.
|
/// Unsigned divide APInt LHS by APInt RHS.
|
||||||
/// @brief Unsigned division function for APInt.
|
/// @brief Unsigned division function for APInt.
|
||||||
APInt udiv(const APInt& LHS, const APInt& RHS);
|
inline APInt udiv(const APInt& LHS, const APInt& RHS) {
|
||||||
|
return LHS.udiv(RHS);
|
||||||
|
}
|
||||||
|
|
||||||
/// Signed remainder operation on APInt.
|
/// Signed remainder operation on APInt.
|
||||||
/// @brief Function for signed remainder operation.
|
/// @brief Function for signed remainder operation.
|
||||||
inline APInt srem(const APInt& LHS, const APInt& RHS) {
|
inline APInt srem(const APInt& LHS, const APInt& RHS) {
|
||||||
bool isSignedLHS = LHS[LHS.BitsNum - 1], isSignedRHS = RHS[RHS.BitsNum - 1];
|
return LHS.srem(RHS);
|
||||||
APInt API = urem(isSignedLHS ? -LHS : LHS, isSignedRHS ? -RHS : RHS);
|
|
||||||
return isSignedLHS ? -API : API;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Unsigned remainder operation on APInt.
|
/// Unsigned remainder operation on APInt.
|
||||||
/// @brief Function for unsigned remainder operation.
|
/// @brief Function for unsigned remainder operation.
|
||||||
APInt urem(const APInt& LHS, const APInt& RHS);
|
inline APInt urem(const APInt& LHS, const APInt& RHS) {
|
||||||
|
return LHS.urem(RHS);
|
||||||
|
}
|
||||||
|
|
||||||
/// Performs multiplication on APInt values.
|
/// Performs multiplication on APInt values.
|
||||||
/// @brief Function for multiplication operation.
|
/// @brief Function for multiplication operation.
|
||||||
|
@ -481,6 +516,31 @@ inline APInt sub(const APInt& LHS, const APInt& RHS) {
|
||||||
return LHS - RHS;
|
return LHS - RHS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Performs bitwise AND operation on APInt LHS and
|
||||||
|
/// APInt RHS.
|
||||||
|
/// @brief Bitwise AND function for APInt.
|
||||||
|
inline APInt And(const APInt& LHS, const APInt& RHS) {
|
||||||
|
return LHS & RHS;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Performs bitwise OR operation on APInt LHS and APInt RHS.
|
||||||
|
/// @brief Bitwise OR function for APInt.
|
||||||
|
inline APInt Or(const APInt& LHS, const APInt& RHS) {
|
||||||
|
return LHS | RHS;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Performs bitwise XOR operation on APInt.
|
||||||
|
/// @brief Bitwise XOR function for APInt.
|
||||||
|
inline APInt Xor(const APInt& LHS, const APInt& RHS) {
|
||||||
|
return LHS ^ RHS;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Performs a bitwise complement operation on APInt.
|
||||||
|
/// @brief Bitwise complement function.
|
||||||
|
inline APInt Not(const APInt& APIVal) {
|
||||||
|
return ~APIVal;
|
||||||
|
}
|
||||||
|
|
||||||
} // End of APIntOps namespace
|
} // End of APIntOps namespace
|
||||||
|
|
||||||
} // End of llvm namespace
|
} // End of llvm namespace
|
||||||
|
|
|
@ -674,8 +674,8 @@ APInt APInt::operator-(const APInt& RHS) const {
|
||||||
|
|
||||||
/// @brief Array-indexing support.
|
/// @brief Array-indexing support.
|
||||||
bool APInt::operator[](unsigned bitPosition) const {
|
bool APInt::operator[](unsigned bitPosition) const {
|
||||||
return maskBit(bitPosition) & (isSingleWord() ?
|
return (maskBit(bitPosition) & (isSingleWord() ?
|
||||||
VAL : pVal[whichWord(bitPosition)]) != 0;
|
VAL : pVal[whichWord(bitPosition)])) != 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// @brief Equality operator. Compare this APInt with the given APInt& RHS
|
/// @brief Equality operator. Compare this APInt with the given APInt& RHS
|
||||||
|
@ -932,14 +932,14 @@ unsigned APInt::CountPopulation() const {
|
||||||
|
|
||||||
|
|
||||||
/// ByteSwap - This function returns a byte-swapped representation of the
|
/// ByteSwap - This function returns a byte-swapped representation of the
|
||||||
/// APInt argument, APIVal.
|
/// this APInt.
|
||||||
APInt llvm::APIntOps::ByteSwap(const APInt& APIVal) {
|
APInt APInt::ByteSwap() const {
|
||||||
if (APIVal.BitsNum <= 32)
|
if (BitsNum <= 32)
|
||||||
return APInt(APIVal.BitsNum, ByteSwap_32(unsigned(APIVal.VAL)));
|
return APInt(BitsNum, ByteSwap_32(unsigned(VAL)));
|
||||||
else if (APIVal.BitsNum <= 64)
|
else if (BitsNum <= 64)
|
||||||
return APInt(APIVal.BitsNum, ByteSwap_64(APIVal.VAL));
|
return APInt(BitsNum, ByteSwap_64(VAL));
|
||||||
else
|
else
|
||||||
return APIVal;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// GreatestCommonDivisor - This function returns the greatest common
|
/// GreatestCommonDivisor - This function returns the greatest common
|
||||||
|
@ -955,10 +955,10 @@ APInt llvm::APIntOps::GreatestCommonDivisor(const APInt& API1,
|
||||||
return A;
|
return A;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Arithmetic right-shift the APInt by shiftAmt.
|
/// Arithmetic right-shift this APInt by shiftAmt.
|
||||||
/// @brief Arithmetic right-shift function.
|
/// @brief Arithmetic right-shift function.
|
||||||
APInt llvm::APIntOps::ashr(const APInt& LHS, unsigned shiftAmt) {
|
APInt APInt::ashr(unsigned shiftAmt) const {
|
||||||
APInt API(LHS);
|
APInt API(*this);
|
||||||
if (API.isSingleWord())
|
if (API.isSingleWord())
|
||||||
API.VAL = (((int64_t(API.VAL) << (64 - API.BitsNum)) >> (64 - API.BitsNum))
|
API.VAL = (((int64_t(API.VAL) << (64 - API.BitsNum)) >> (64 - API.BitsNum))
|
||||||
>> shiftAmt) & (~uint64_t(0UL) >> (64 - API.BitsNum));
|
>> shiftAmt) & (~uint64_t(0UL) >> (64 - API.BitsNum));
|
||||||
|
@ -981,10 +981,10 @@ APInt llvm::APIntOps::ashr(const APInt& LHS, unsigned shiftAmt) {
|
||||||
return API;
|
return API;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Logical right-shift the APInt by shiftAmt.
|
/// Logical right-shift this APInt by shiftAmt.
|
||||||
/// @brief Logical right-shift function.
|
/// @brief Logical right-shift function.
|
||||||
APInt llvm::APIntOps::lshr(const APInt& RHS, unsigned shiftAmt) {
|
APInt APInt::lshr(unsigned shiftAmt) const {
|
||||||
APInt API(RHS);
|
APInt API(*this);
|
||||||
if (API.isSingleWord())
|
if (API.isSingleWord())
|
||||||
API.VAL >>= shiftAmt;
|
API.VAL >>= shiftAmt;
|
||||||
else {
|
else {
|
||||||
|
@ -1000,10 +1000,10 @@ APInt llvm::APIntOps::lshr(const APInt& RHS, unsigned shiftAmt) {
|
||||||
return API;
|
return API;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Left-shift the APInt by shiftAmt.
|
/// Left-shift this APInt by shiftAmt.
|
||||||
/// @brief Left-shift function.
|
/// @brief Left-shift function.
|
||||||
APInt llvm::APIntOps::shl(const APInt& RHS, unsigned shiftAmt) {
|
APInt APInt::shl(unsigned shiftAmt) const {
|
||||||
APInt API(RHS);
|
APInt API(*this);
|
||||||
if (shiftAmt >= API.BitsNum) {
|
if (shiftAmt >= API.BitsNum) {
|
||||||
if (API.isSingleWord())
|
if (API.isSingleWord())
|
||||||
API.VAL = 0;
|
API.VAL = 0;
|
||||||
|
@ -1019,10 +1019,10 @@ APInt llvm::APIntOps::shl(const APInt& RHS, unsigned shiftAmt) {
|
||||||
return API;
|
return API;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Unsigned divide APInt LHS by APInt RHS.
|
/// Unsigned divide this APInt by APInt RHS.
|
||||||
/// @brief Unsigned division function for APInt.
|
/// @brief Unsigned division function for APInt.
|
||||||
APInt llvm::APIntOps::udiv(const APInt& LHS, const APInt& RHS) {
|
APInt APInt::udiv(const APInt& RHS) const {
|
||||||
APInt API(LHS);
|
APInt API(*this);
|
||||||
unsigned first = RHS.getNumWords() * APInt::APINT_BITS_PER_WORD -
|
unsigned first = RHS.getNumWords() * APInt::APINT_BITS_PER_WORD -
|
||||||
RHS.CountLeadingZeros();
|
RHS.CountLeadingZeros();
|
||||||
unsigned ylen = !first ? 0 : APInt::whichWord(first - 1) + 1;
|
unsigned ylen = !first ? 0 : APInt::whichWord(first - 1) + 1;
|
||||||
|
@ -1066,8 +1066,8 @@ APInt llvm::APIntOps::udiv(const APInt& LHS, const APInt& RHS) {
|
||||||
|
|
||||||
/// Unsigned remainder operation on APInt.
|
/// Unsigned remainder operation on APInt.
|
||||||
/// @brief Function for unsigned remainder operation.
|
/// @brief Function for unsigned remainder operation.
|
||||||
APInt llvm::APIntOps::urem(const APInt& LHS, const APInt& RHS) {
|
APInt APInt::urem(const APInt& RHS) const {
|
||||||
APInt API(LHS);
|
APInt API(*this);
|
||||||
unsigned first = RHS.getNumWords() * APInt::APINT_BITS_PER_WORD -
|
unsigned first = RHS.getNumWords() * APInt::APINT_BITS_PER_WORD -
|
||||||
RHS.CountLeadingZeros();
|
RHS.CountLeadingZeros();
|
||||||
unsigned ylen = !first ? 0 : APInt::whichWord(first - 1) + 1;
|
unsigned ylen = !first ? 0 : APInt::whichWord(first - 1) + 1;
|
||||||
|
|
Loading…
Reference in New Issue