[llvm-commits] CVS: llvm/lib/Support/APInt.cpp

Zhou Sheng zhousheng00 at gmail.com
Mon Feb 5 22:05:09 PST 2007



Changes in directory llvm/lib/Support:

APInt.cpp updated: 1.2 -> 1.3
---
Log message:

As Reid suggested, fixed some problems.


---
Diffs of the changes:  (+143 -150)

 APInt.cpp |  293 ++++++++++++++++++++++++++++++--------------------------------
 1 files changed, 143 insertions(+), 150 deletions(-)


Index: llvm/lib/Support/APInt.cpp
diff -u llvm/lib/Support/APInt.cpp:1.2 llvm/lib/Support/APInt.cpp:1.3
--- llvm/lib/Support/APInt.cpp:1.2	Mon Feb  5 23:38:37 2007
+++ llvm/lib/Support/APInt.cpp	Tue Feb  6 00:04:53 2007
@@ -24,147 +24,10 @@
 #include <cstdlib>
 using namespace llvm;
 
-APInt::APInt(uint64_t val, unsigned numBits, bool sign)
-  : bitsnum(numBits), isSigned(sign) {
-  assert(bitsnum >= IntegerType::MIN_INT_BITS && "bitwidth too small");
-  assert(bitsnum <= IntegerType::MAX_INT_BITS && "bitwidth too large");
-  if (isSingleWord()) 
-    VAL = val & (~uint64_t(0ULL) >> (APINT_BITS_PER_WORD - bitsnum));
-  else {
-    // Memory allocation and check if successful.
-    assert((pVal = new uint64_t[numWords()]) && 
-            "APInt memory allocation fails!");
-    bzero(pVal, numWords() * 8);
-    pVal[0] = val;
-  }
-}
-
-APInt::APInt(unsigned numBits, uint64_t bigVal[], bool sign)
-  : bitsnum(numBits), isSigned(sign) {
-  assert(bitsnum >= IntegerType::MIN_INT_BITS && "bitwidth too small");
-  assert(bitsnum <= IntegerType::MAX_INT_BITS && "bitwidth too large");
-  assert(bigVal && "Null pointer detected!");
-  if (isSingleWord())
-    VAL = bigVal[0] & (~uint64_t(0ULL) >> (APINT_BITS_PER_WORD - bitsnum));
-  else {
-    // Memory allocation and check if successful.
-    assert((pVal = new uint64_t[numWords()]) && 
-           "APInt memory allocation fails!");
-    // Calculate the actual length of bigVal[].
-    unsigned n = sizeof(*bigVal) / sizeof(bigVal[0]);
-    unsigned maxN = std::max<unsigned>(n, numWords());
-    unsigned minN = std::min<unsigned>(n, numWords());
-    memcpy(pVal, bigVal, (minN - 1) * 8);
-    pVal[minN-1] = bigVal[minN-1] & (~uint64_t(0ULL) >> (64 - bitsnum % 64));
-    if (maxN == numWords())
-      bzero(pVal+n, (numWords() - n) * 8);
-  }
-}
-
-APInt::APInt(std::string& Val, uint8_t radix, bool sign)
-  : isSigned(sign) {
-  assert((radix == 10 || radix == 8 || radix == 16 || radix == 2) &&
-         "Radix should be 2, 8, 10, or 16!");
-  assert(!Val.empty() && "String empty?");
-  unsigned slen = Val.size();
-  unsigned size = 0;
-  // If the radix is a power of 2, read the input
-  // from most significant to least significant.
-  if ((radix & (radix - 1)) == 0) {
-    unsigned nextBitPos = 0, bits_per_digit = radix / 8 + 2;
-    uint64_t resDigit = 0;
-    bitsnum = slen * bits_per_digit;
-    if (numWords() > 1)
-      assert((pVal = new uint64_t[numWords()]) && 
-             "APInt memory allocation fails!");
-    for (int i = slen - 1; i >= 0; --i) {
-      uint64_t digit = Val[i] - 48;             // '0' == 48.
-      resDigit |= digit << nextBitPos;
-      nextBitPos += bits_per_digit;
-      if (nextBitPos >= 64) {
-        if (isSingleWord()) {
-          VAL = resDigit;
-           break;
-        }
-        pVal[size++] = resDigit;
-        nextBitPos -= 64;
-        resDigit = digit >> (bits_per_digit - nextBitPos);
-      }
-    }
-    if (!isSingleWord() && size <= numWords()) 
-      pVal[size] = resDigit;
-  } else {   // General case.  The radix is not a power of 2.
-    // For 10-radix, the max value of 64-bit integer is 18446744073709551615,
-    // and its digits number is 14.
-    const unsigned chars_per_word = 20;
-    if (slen < chars_per_word || 
-        (Val <= "18446744073709551615" && 
-         slen == chars_per_word)) { // In case Val <= 2^64 - 1
-      bitsnum = 64;
-      VAL = strtoull(Val.c_str(), 0, 10);
-    } else { // In case Val > 2^64 - 1
-      bitsnum = (slen / chars_per_word + 1) * 64;
-      assert((pVal = new uint64_t[numWords()]) && 
-             "APInt memory allocation fails!");
-      bzero(pVal, numWords() * 8);
-      unsigned str_pos = 0;
-      while (str_pos < slen) {
-        unsigned chunk = slen - str_pos;
-        if (chunk > chars_per_word - 1)
-          chunk = chars_per_word - 1;
-        uint64_t resDigit = Val[str_pos++] - 48;  // 48 == '0'.
-        uint64_t big_base = radix;
-        while (--chunk > 0) {
-          resDigit = resDigit * radix + Val[str_pos++] - 48;
-          big_base *= radix;
-        }
-       
-        uint64_t carry;
-        if (!size)
-          carry = resDigit;
-        else {
-          carry = mul_1(pVal, pVal, size, big_base);
-          carry += add_1(pVal, pVal, size, resDigit);
-        }
-        
-        if (carry) pVal[size++] = carry;
-      }
-    }
-  }
-}
-
-APInt::APInt(const APInt& APIVal)
-  : bitsnum(APIVal.bitsnum), isSigned(APIVal.isSigned) {
-  if (isSingleWord()) VAL = APIVal.VAL;
-  else {
-    // Memory allocation and check if successful.
-    assert((pVal = new uint64_t[numWords()]) && 
-           "APInt memory allocation fails!");
-    memcpy(pVal, APIVal.pVal, numWords() * 8);
-  }
-}
-
-APInt::~APInt() {
-  if (!isSingleWord() && pVal) delete[] pVal;
-}
-
-/// whichByte - This function returns the word position 
-/// for the specified bit position.
-inline unsigned APInt::whichByte(unsigned bitPosition)
-{ return (bitPosition % APINT_BITS_PER_WORD) / 8; }
-
-/// getWord - returns the corresponding word for the specified bit position.
-inline uint64_t& APInt::getWord(unsigned bitPosition)
-{ return isSingleWord() ? VAL : pVal[whichWord(bitPosition)]; }
-
-/// getWord - returns the corresponding word for the specified bit position.
-/// This is a constant version.
-inline uint64_t APInt::getWord(unsigned bitPosition) const
-{ return isSingleWord() ? VAL : pVal[whichWord(bitPosition)]; }
-
-/// mul_1 - This function multiplies the integer array x[] by a integer y and 
-/// returns the carry.
-uint64_t APInt::mul_1(uint64_t dest[], uint64_t x[],
+/// mul_1 - This function performs the multiplication operation on a
+/// large integer (represented as an integer array) and a uint64_t integer.
+/// @returns the carry of the multiplication.
+static uint64_t mul_1(uint64_t dest[], uint64_t x[],
                      unsigned len, uint64_t y) {
   // Split y into high 32-bit part and low 32-bit part.
   uint64_t ly = y & 0xffffffffULL, hy = y >> 32;
@@ -197,7 +60,7 @@
 /// mul - This function multiplies integer array x[] by integer array y[] and
 /// stores the result into integer array dest[].
 /// Note the array dest[]'s size should no less than xlen + ylen.
-void APInt::mul(uint64_t dest[], uint64_t x[], unsigned xlen,
+static void mul(uint64_t dest[], uint64_t x[], unsigned xlen,
                uint64_t y[], unsigned ylen) {
   dest[xlen] = mul_1(dest, x, xlen, y[0]);
 
@@ -230,7 +93,8 @@
 
 /// add_1 - This function adds the integer array x[] by integer y and
 /// returns the carry.
-uint64_t APInt::add_1(uint64_t dest[], uint64_t x[],
+/// @returns the carry of the addition.
+static uint64_t add_1(uint64_t dest[], uint64_t x[],
                       unsigned len, uint64_t y) {
   uint64_t carry = y;
 
@@ -243,7 +107,7 @@
 
 /// add - This function adds the integer array x[] by integer array
 /// y[] and returns the carry.
-uint64_t APInt::add(uint64_t dest[], uint64_t x[],
+static uint64_t add(uint64_t dest[], uint64_t x[],
                     uint64_t y[], unsigned len) {
   unsigned carry = 0;
   
@@ -257,7 +121,7 @@
 
 /// sub_1 - This function subtracts the integer array x[] by
 /// integer y and returns the borrow-out carry.
-uint64_t APInt::sub_1(uint64_t x[], unsigned len, uint64_t y) {
+static uint64_t sub_1(uint64_t x[], unsigned len, uint64_t y) {
   uint64_t cy = y;
 
   for (unsigned i = 0; i < len; ++i) {
@@ -276,7 +140,7 @@
 
 /// sub - This function subtracts the integer array x[] by
 /// integer array y[], and returns the borrow-out carry.
-uint64_t APInt::sub(uint64_t dest[], uint64_t x[],
+static uint64_t sub(uint64_t dest[], uint64_t x[],
                     uint64_t y[], unsigned len) {
   // Carry indicator.
   uint64_t cy = 0;
@@ -296,7 +160,7 @@
 /// UnitDiv - This function divides N by D, 
 /// and returns (remainder << 32) | quotient.
 /// Assumes (N >> 32) < D.
-uint64_t APInt::unitDiv(uint64_t N, unsigned D) {
+static uint64_t unitDiv(uint64_t N, unsigned D) {
   uint64_t q, r;                   // q: quotient, r: remainder.
   uint64_t a1 = N >> 32;           // a1: high 32-bit part of N.
   uint64_t a0 = N & 0xffffffffL;   // a0: low 32-bit part of N
@@ -320,7 +184,7 @@
 /// subMul - This function substracts x[len-1:0] * y from 
 /// dest[offset+len-1:offset], and returns the most significant 
 /// word of the product, minus the borrow-out from the subtraction.
-unsigned APInt::subMul(unsigned dest[], unsigned offset, 
+static unsigned subMul(unsigned dest[], unsigned offset, 
                         unsigned x[], unsigned len, unsigned y) {
   uint64_t yl = (uint64_t) y & 0xffffffffL;
   unsigned carry = 0;
@@ -348,7 +212,7 @@
 /// Our nx == Knuth's m+n.
 /// Could be re-implemented using gmp's mpn_divrem:
 /// zds[nx] = mpn_divrem (&zds[ny], 0, zds, nx, y, ny).
-void APInt::div(unsigned zds[], unsigned nx, unsigned y[], unsigned ny) {
+static void div(unsigned zds[], unsigned nx, unsigned y[], unsigned ny) {
   unsigned j = nx;
   do {                          // loop over digits of quotient
     // Knuth's j == our nx-j.
@@ -386,7 +250,7 @@
 /// store the len least significant words of the result in 
 /// dest[d_offset:d_offset+len-1]. It returns the bits shifted out from 
 /// the most significant digit.
-uint64_t APInt::lshift(uint64_t dest[], unsigned d_offset,
+static uint64_t lshift(uint64_t dest[], unsigned d_offset,
                        uint64_t x[], unsigned len, unsigned shiftAmt) {
   unsigned count = 64 - shiftAmt;
   int i = len - 1;
@@ -401,6 +265,135 @@
   return retVal;
 }
 
+APInt::APInt(uint64_t val, unsigned numBits, bool sign)
+  : bitsnum(numBits), isSigned(sign) {
+  assert(bitsnum >= IntegerType::MIN_INT_BITS && "bitwidth too small");
+  assert(bitsnum <= IntegerType::MAX_INT_BITS && "bitwidth too large");
+  if (isSingleWord()) 
+    VAL = val & (~uint64_t(0ULL) >> (APINT_BITS_PER_WORD - bitsnum));
+  else {
+    // Memory allocation and check if successful.
+    assert((pVal = new uint64_t[numWords()]) && 
+            "APInt memory allocation fails!");
+    bzero(pVal, numWords() * 8);
+    pVal[0] = val;
+  }
+}
+
+APInt::APInt(unsigned numBits, uint64_t bigVal[], bool sign)
+  : bitsnum(numBits), isSigned(sign) {
+  assert(bitsnum >= IntegerType::MIN_INT_BITS && "bitwidth too small");
+  assert(bitsnum <= IntegerType::MAX_INT_BITS && "bitwidth too large");
+  assert(bigVal && "Null pointer detected!");
+  if (isSingleWord())
+    VAL = bigVal[0] & (~uint64_t(0ULL) >> (APINT_BITS_PER_WORD - bitsnum));
+  else {
+    // Memory allocation and check if successful.
+    assert((pVal = new uint64_t[numWords()]) && 
+           "APInt memory allocation fails!");
+    // Calculate the actual length of bigVal[].
+    unsigned n = sizeof(*bigVal) / sizeof(bigVal[0]);
+    unsigned maxN = std::max<unsigned>(n, numWords());
+    unsigned minN = std::min<unsigned>(n, numWords());
+    memcpy(pVal, bigVal, (minN - 1) * 8);
+    pVal[minN-1] = bigVal[minN-1] & (~uint64_t(0ULL) >> (64 - bitsnum % 64));
+    if (maxN == numWords())
+      bzero(pVal+n, (numWords() - n) * 8);
+  }
+}
+
+APInt::APInt(std::string& Val, uint8_t radix, bool sign)
+  : isSigned(sign) {
+  assert((radix == 10 || radix == 8 || radix == 16 || radix == 2) &&
+         "Radix should be 2, 8, 10, or 16!");
+  assert(!Val.empty() && "String empty?");
+  unsigned slen = Val.size();
+  unsigned size = 0;
+  // If the radix is a power of 2, read the input
+  // from most significant to least significant.
+  if ((radix & (radix - 1)) == 0) {
+    unsigned nextBitPos = 0, bits_per_digit = radix / 8 + 2;
+    uint64_t resDigit = 0;
+    bitsnum = slen * bits_per_digit;
+    if (numWords() > 1)
+      assert((pVal = new uint64_t[numWords()]) && 
+             "APInt memory allocation fails!");
+    for (int i = slen - 1; i >= 0; --i) {
+      uint64_t digit = Val[i] - 48;             // '0' == 48.
+      resDigit |= digit << nextBitPos;
+      nextBitPos += bits_per_digit;
+      if (nextBitPos >= 64) {
+        if (isSingleWord()) {
+          VAL = resDigit;
+           break;
+        }
+        pVal[size++] = resDigit;
+        nextBitPos -= 64;
+        resDigit = digit >> (bits_per_digit - nextBitPos);
+      }
+    }
+    if (!isSingleWord() && size <= numWords()) 
+      pVal[size] = resDigit;
+  } else {   // General case.  The radix is not a power of 2.
+    // For 10-radix, the max value of 64-bit integer is 18446744073709551615,
+    // and its digits number is 14.
+    const unsigned chars_per_word = 20;
+    if (slen < chars_per_word || 
+        (Val <= "18446744073709551615" && 
+         slen == chars_per_word)) { // In case Val <= 2^64 - 1
+      bitsnum = 64;
+      VAL = strtoull(Val.c_str(), 0, 10);
+    } else { // In case Val > 2^64 - 1
+      bitsnum = (slen / chars_per_word + 1) * 64;
+      assert((pVal = new uint64_t[numWords()]) && 
+             "APInt memory allocation fails!");
+      bzero(pVal, numWords() * 8);
+      unsigned str_pos = 0;
+      while (str_pos < slen) {
+        unsigned chunk = slen - str_pos;
+        if (chunk > chars_per_word - 1)
+          chunk = chars_per_word - 1;
+        uint64_t resDigit = Val[str_pos++] - 48;  // 48 == '0'.
+        uint64_t big_base = radix;
+        while (--chunk > 0) {
+          resDigit = resDigit * radix + Val[str_pos++] - 48;
+          big_base *= radix;
+        }
+       
+        uint64_t carry;
+        if (!size)
+          carry = resDigit;
+        else {
+          carry = mul_1(pVal, pVal, size, big_base);
+          carry += add_1(pVal, pVal, size, resDigit);
+        }
+        
+        if (carry) pVal[size++] = carry;
+      }
+    }
+  }
+}
+
+APInt::APInt(const APInt& APIVal)
+  : bitsnum(APIVal.bitsnum), isSigned(APIVal.isSigned) {
+  if (isSingleWord()) VAL = APIVal.VAL;
+  else {
+    // Memory allocation and check if successful.
+    assert((pVal = new uint64_t[numWords()]) && 
+           "APInt memory allocation fails!");
+    memcpy(pVal, APIVal.pVal, numWords() * 8);
+  }
+}
+
+APInt::~APInt() {
+  if (!isSingleWord() && pVal) delete[] pVal;
+}
+
+/// whichByte - This function returns the word position 
+/// for the specified bit position.
+inline unsigned APInt::whichByte(unsigned bitPosition)
+{ return (bitPosition % APINT_BITS_PER_WORD) / 8; }
+
 /// @brief Copy assignment operator. Create a new object from the given
 /// APInt one by initialization.
 APInt& APInt::operator=(const APInt& RHS) {






More information about the llvm-commits mailing list