Exemplo n.º 1
0
/// GetIntegerValue - Convert this numeric literal value to an APInt that
/// matches Val's input width.  If there is an overflow, set Val to the low bits
/// of the result and return true.  Otherwise, return false.
bool NumericLiteralParser::GetIntegerValue(llvm::APInt &Val) {
	// Fast path: Compute a conservative bound on the maximum number of
	// bits per digit in this radix. If we can't possibly overflow a
	// uint64 based on that bound then do the simple conversion to
	// integer. This avoids the expensive overflow checking below, and
	// handles the common cases that matter (small decimal integers and
	// hex/octal values which don't overflow).
	const unsigned NumDigits = SuffixBegin - DigitsBegin;
	if (alwaysFitsInto64Bits(radix, NumDigits)) {
		uint64_t N = 0;
		for (const char *Ptr = DigitsBegin; Ptr != SuffixBegin; ++Ptr)
			if (!isDigitSeparator(*Ptr))
				N = N * radix + llvm::hexDigitValue(*Ptr);

		// This will truncate the value to Val's input width. Simply check
		// for overflow by comparing.
		Val = N;
		return Val.getZExtValue() != N;
	}

	Val = 0;
	const char *Ptr = DigitsBegin;

	llvm::APInt RadixVal(Val.getBitWidth(), radix);
	llvm::APInt CharVal(Val.getBitWidth(), 0);
	llvm::APInt OldVal = Val;

	bool OverflowOccurred = false;
	while (Ptr < SuffixBegin) {
		if (isDigitSeparator(*Ptr)) {
			++Ptr;
			continue;
		}

		unsigned C = llvm::hexDigitValue(*Ptr++);

		// If this letter is out of bound for this radix, reject it.
		assert(C < radix && "NumericLiteralParser ctor should have rejected this");

		CharVal = C;

		// Add the digit to the value in the appropriate radix.  If adding in digits
		// made the value smaller, then this overflowed.
		OldVal = Val;

		// Multiply by radix, did overflow occur on the multiply?
		Val *= RadixVal;
		OverflowOccurred |= Val.udiv(RadixVal) != OldVal;

		// Add value, did overflow occur on the value?
		//   (a + b) ult b  <=> overflow
		Val += CharVal;
		OverflowOccurred |= Val.ult(CharVal);
	}
	return OverflowOccurred;
}
bool MagicNumbersCheck::isIgnoredValue(const IntegerLiteral *Literal) const {
  const llvm::APInt IntValue = Literal->getValue();
  const int64_t Value = IntValue.getZExtValue();
  if (Value == 0)
    return true;

  if (IgnorePowersOf2IntegerValues && IntValue.isPowerOf2())
    return true;

  return std::binary_search(IgnoredIntegerValues.begin(),
                            IgnoredIntegerValues.end(), Value);
}