llvm.org GIT mirror
First step to fix PR2088. Implement routine to compute the multiplicative inverse of a given number. Modify udivrem to allow input and output pairs of arguments to overlap. Patch is based on the work by Chandler Carruth. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@52638 91177308-0d34-0410-b5e6-96231b3b80d8 Wojciech Matyjewicz 11 years ago
2 changed file(s) with 57 addition(s) and 11 deletion(s).
 667 667 return this->urem(RHS); 668 668 } 669 669 670 /// Sometimes it is convenient to divide two APInt values and obtain both 671 /// the quotient and remainder. This function does both operations in the 672 /// same computation making it a little more efficient.⏎ 670 /// Sometimes it is convenient to divide two APInt values and obtain both the⏎ 671 /// quotient and remainder. This function does both operations in the same 672 /// computation making it a little more efficient. The pair of input arguments 673 /// may overlap with the pair of output arguments. It is safe to call 674 /// udivrem(X, Y, X, Y), for example. 673 675 /// @brief Dual division/remainder interface. 674 676 static void udivrem(const APInt &LHS, const APInt &RHS, 675 677 APInt &Quotient, APInt &Remainder); 1106 1108 return *this; 1107 1109 } 1108 1110 1111 /// @returns the multiplicative inverse for a given modulo. 1112 APInt multiplicativeInverse(const APInt& modulo) const; 1113 1109 1114 /// @} 1110 1115 /// @name Building-block Operations for APInt and APFloat 1111 1116 /// @{ 1300 1305 } 1301 1306 1302 1307 /// GreatestCommonDivisor - This function returns the greatest common 1303 /// divisor of the two APInt values using Enclid's algorithm.⏎ 1308 /// divisor of the two APInt values using Euclid's algorithm.⏎ 1304 1309 /// @returns the greatest common divisor of Val1 and Val2 1305 1310 /// @brief Compute GCD of two APInt values. 1306 1311 APInt GreatestCommonDivisor(const APInt& Val1, const APInt& Val2);
 1423 1423 } else 1424 1424 assert(0 && "Error in APInt::sqrt computation"); 1425 1425 return x_old + 1; 1426 } 1427 1428 /// Computes the multiplicative inverse of this APInt for a given modulo. The 1429 /// iterative extended Euclidean algorithm is used to solve for this value, 1430 /// however we simplify it to speed up calculating only the inverse, and take 1431 /// advantage of div+rem calculations. We also use some tricks to avoid copying 1432 /// (potentially large) APInts around. 1433 APInt APInt::multiplicativeInverse(const APInt& modulo) const { 1434 assert(ult(modulo) && "This APInt must be smaller than the modulo"); 1435 1436 // Using the properties listed at the following web page (accessed 06/21/08): 1437 // http://www.numbertheory.org/php/euclid.html 1438 // (especially the properties numbered 3, 4 and 9) it can be proved that 1439 // BitWidth bits suffice for all the computations in the algorithm implemented 1440 // below. More precisely, this number of bits suffice if the multiplicative 1441 // inverse exists, but may not suffice for the general extended Euclidean 1442 // algorithm. 1443 1444 APInt r = { modulo, *this }; 1445 APInt t = { APInt(BitWidth, 0), APInt(BitWidth, 1) }; 1446 APInt q(BitWidth, 0); 1447 1448 unsigned i; 1449 for (i = 0; r[i^1] != 0; i ^= 1) { 1450 // An overview of the math without the confusing bit-flipping: 1451 // q = r[i-2] / r[i-1] 1452 // r[i] = r[i-2] % r[i-1] 1453 // t[i] = t[i-2] - t[i-1] * q 1454 udivrem(r[i], r[i^1], q, r[i]); 1455 t[i] -= t[i^1] * q; 1456 } 1457 1458 // If this APInt and the modulo are not coprime, there is no multiplicative 1459 // inverse, so return 0. We check this by looking at the next-to-last 1460 // remainder, which is the gcd(*this,modulo) as calculated by the Euclidean 1461 // algorithm. 1462 if (r[i] != 1) 1463 return APInt(BitWidth, 0); 1464 1465 // The next-to-last t is the multiplicative inverse. However, we are 1466 // interested in a positive inverse. Calcuate a positive one from a negative 1467 // one if necessary. A simple addition of the modulo suffices because 1468 // abs(t[i]) is known to less than *this/2 (see the link above). 1469 return t[i].isNegative() ? t[i] + modulo : t[i]; 1426 1470 } 1427 1471 1428 1472 /// Implementation of Knuth's Algorithm D (Division of nonnegative integers) 1881 1925 1882 1926 if (lhsWords == 1 && rhsWords == 1) { 1883 1927 // There is only one word to consider so use the native versions. 1884 if (LHS.isSingleWord()) { 1885 Quotient = APInt(LHS.getBitWidth(), LHS.VAL / RHS.VAL); 1886 Remainder = APInt(LHS.getBitWidth(), LHS.VAL % RHS.VAL); 1887 } else { 1888 Quotient = APInt(LHS.getBitWidth(), LHS.pVal / RHS.pVal); 1889 Remainder = APInt(LHS.getBitWidth(), LHS.pVal % RHS.pVal); 1890 }⏎ 1928 uint64_t lhsValue = LHS.isSingleWord() ? LHS.VAL : LHS.pVal;⏎ 1929 uint64_t rhsValue = RHS.isSingleWord() ? RHS.VAL : RHS.pVal; 1930 Quotient = APInt(LHS.getBitWidth(), lhsValue / rhsValue); 1931 Remainder = APInt(LHS.getBitWidth(), lhsValue % rhsValue); 1891 1932 return; 1892 1933 } 1893 1934