diff options
author | Hans Wennborg <hans@hanshq.net> | 2018-11-27 14:01:40 +0000 |
---|---|---|
committer | Hans Wennborg <hans@hanshq.net> | 2018-11-27 14:01:40 +0000 |
commit | e44c638ccfb9c020561219a3bfc76ce41a99cf4b (patch) | |
tree | 1c2a925b80306bd7ce2c14d3ef737ff3a190e671 /lib/Sema/SemaChecking.cpp | |
parent | 58828cc308e0a6030d0418573376624d01baa7d3 (diff) | |
download | clang-e44c638ccfb9c020561219a3bfc76ce41a99cf4b.tar.gz |
Revert r347417 "Re-Reinstate 347294 with a fix for the failures."
This caused a miscompile in Chrome (see crbug.com/908372) that's
illustrated by this small reduction:
static bool f(int *a, int *b) {
return !__builtin_constant_p(b - a) || (!(b - a));
}
int arr[] = {1,2,3};
bool g() {
return f(arr, arr + 3);
}
$ clang -O2 -S -emit-llvm a.cc -o -
g() should return true, but after r347417 it became false for some reason.
This also reverts the follow-up commits.
r347417:
> Re-Reinstate 347294 with a fix for the failures.
>
> Don't try to emit a scalar expression for a non-scalar argument to
> __builtin_constant_p().
>
> Third time's a charm!
r347446:
> The result of is.constant() is unsigned.
r347480:
> A __builtin_constant_p() returns 0 with a function type.
r347512:
> isEvaluatable() implies a constant context.
>
> Assume that we're in a constant context if we're asking if the expression can
> be compiled into a constant initializer. This fixes the issue where a
> __builtin_constant_p() in a compound literal was diagnosed as not being
> constant, even though it's always possible to convert the builtin into a
> constant.
r347531:
> A "constexpr" is evaluated in a constant context. Make sure this is reflected
> if a __builtin_constant_p() is a part of a constexpr.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@347656 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema/SemaChecking.cpp')
-rw-r--r-- | lib/Sema/SemaChecking.cpp | 47 |
1 files changed, 18 insertions, 29 deletions
diff --git a/lib/Sema/SemaChecking.cpp b/lib/Sema/SemaChecking.cpp index 4b77ac6197..a45d4fdfd7 100644 --- a/lib/Sema/SemaChecking.cpp +++ b/lib/Sema/SemaChecking.cpp @@ -247,16 +247,13 @@ static void SemaBuiltinMemChkCall(Sema &S, FunctionDecl *FDecl, const Expr *SizeArg = TheCall->getArg(SizeIdx); const Expr *DstSizeArg = TheCall->getArg(DstSizeIdx); - Expr::EvalResult SizeResult, DstSizeResult; + llvm::APSInt Size, DstSize; // find out if both sizes are known at compile time - if (!SizeArg->EvaluateAsInt(SizeResult, S.Context) || - !DstSizeArg->EvaluateAsInt(DstSizeResult, S.Context)) + if (!SizeArg->EvaluateAsInt(Size, S.Context) || + !DstSizeArg->EvaluateAsInt(DstSize, S.Context)) return; - llvm::APSInt Size = SizeResult.Val.getInt(); - llvm::APSInt DstSize = DstSizeResult.Val.getInt(); - if (Size.ule(DstSize)) return; @@ -6486,12 +6483,13 @@ checkFormatStringExpr(Sema &S, const Expr *E, ArrayRef<const Expr *> Args, return SLCT_NotALiteral; } case Stmt::BinaryOperatorClass: { + llvm::APSInt LResult; + llvm::APSInt RResult; + const BinaryOperator *BinOp = cast<BinaryOperator>(E); // A string literal + an int offset is still a string literal. if (BinOp->isAdditiveOp()) { - Expr::EvalResult LResult, RResult; - bool LIsInt = BinOp->getLHS()->EvaluateAsInt(LResult, S.Context); bool RIsInt = BinOp->getRHS()->EvaluateAsInt(RResult, S.Context); @@ -6500,12 +6498,12 @@ checkFormatStringExpr(Sema &S, const Expr *E, ArrayRef<const Expr *> Args, if (LIsInt) { if (BinOpKind == BO_Add) { - sumOffsets(Offset, LResult.Val.getInt(), BinOpKind, RIsInt); + sumOffsets(Offset, LResult, BinOpKind, RIsInt); E = BinOp->getRHS(); goto tryAgain; } } else { - sumOffsets(Offset, RResult.Val.getInt(), BinOpKind, RIsInt); + sumOffsets(Offset, RResult, BinOpKind, RIsInt); E = BinOp->getLHS(); goto tryAgain; } @@ -6518,10 +6516,9 @@ checkFormatStringExpr(Sema &S, const Expr *E, ArrayRef<const Expr *> Args, const UnaryOperator *UnaOp = cast<UnaryOperator>(E); auto ASE = dyn_cast<ArraySubscriptExpr>(UnaOp->getSubExpr()); if (UnaOp->getOpcode() == UO_AddrOf && ASE) { - Expr::EvalResult IndexResult; + llvm::APSInt IndexResult; if (ASE->getRHS()->EvaluateAsInt(IndexResult, S.Context)) { - sumOffsets(Offset, IndexResult.Val.getInt(), BO_Add, - /*RHS is int*/ true); + sumOffsets(Offset, IndexResult, BO_Add, /*RHS is int*/ true); E = ASE->getBase(); goto tryAgain; } @@ -10266,8 +10263,8 @@ static bool AnalyzeBitFieldAssignment(Sema &S, FieldDecl *Bitfield, Expr *Init, Expr *OriginalInit = Init->IgnoreParenImpCasts(); unsigned FieldWidth = Bitfield->getBitWidthValue(S.Context); - Expr::EvalResult Result; - if (!OriginalInit->EvaluateAsInt(Result, S.Context, + llvm::APSInt Value; + if (!OriginalInit->EvaluateAsInt(Value, S.Context, Expr::SE_AllowSideEffects)) { // The RHS is not constant. If the RHS has an enum type, make sure the // bitfield is wide enough to hold all the values of the enum without @@ -10323,8 +10320,6 @@ static bool AnalyzeBitFieldAssignment(Sema &S, FieldDecl *Bitfield, Expr *Init, return false; } - llvm::APSInt Value = Result.Val.getInt(); - unsigned OriginalWidth = Value.getBitWidth(); if (!Value.isSigned() || Value.isNegative()) @@ -10937,11 +10932,8 @@ CheckImplicitConversion(Sema &S, Expr *E, QualType T, SourceLocation CC, if (SourceRange.Width > TargetRange.Width) { // If the source is a constant, use a default-on diagnostic. // TODO: this should happen for bitfield stores, too. - Expr::EvalResult Result; - if (E->EvaluateAsInt(Result, S.Context, Expr::SE_AllowSideEffects)) { - llvm::APSInt Value(32); - Value = Result.Val.getInt(); - + llvm::APSInt Value(32); + if (E->EvaluateAsInt(Value, S.Context, Expr::SE_AllowSideEffects)) { if (S.SourceMgr.isInSystemMacro(CC)) return; @@ -10985,10 +10977,9 @@ CheckImplicitConversion(Sema &S, Expr *E, QualType T, SourceLocation CC, // source value is exactly the width of the target type, which will // cause a negative value to be stored. - Expr::EvalResult Result; - if (E->EvaluateAsInt(Result, S.Context, Expr::SE_AllowSideEffects) && + llvm::APSInt Value; + if (E->EvaluateAsInt(Value, S.Context, Expr::SE_AllowSideEffects) && !S.SourceMgr.isInSystemMacro(CC)) { - llvm::APSInt Value = Result.Val.getInt(); if (isSameWidthConstantConversion(S, E, T, CC)) { std::string PrettySourceValue = Value.toString(10); std::string PrettyTargetValue = PrettyPrintInRange(Value, TargetRange); @@ -12275,11 +12266,9 @@ void Sema::CheckArrayAccess(const Expr *BaseExpr, const Expr *IndexExpr, if (!ArrayTy) return; - Expr::EvalResult Result; - if (!IndexExpr->EvaluateAsInt(Result, Context, Expr::SE_AllowSideEffects)) + llvm::APSInt index; + if (!IndexExpr->EvaluateAsInt(index, Context, Expr::SE_AllowSideEffects)) return; - - llvm::APSInt index = Result.Val.getInt(); if (IndexNegated) index = -index; |