aboutsummaryrefslogtreecommitdiff
path: root/lib/AST/ExprConstant.cpp
diff options
context:
space:
mode:
authorArgyrios Kyrtzidis <akyrtzi@gmail.com>2012-02-25 23:21:37 +0000
committerArgyrios Kyrtzidis <akyrtzi@gmail.com>2012-02-25 23:21:37 +0000
commit2fa975c94027c6565cb112ffcf93c05b22922c0e (patch)
treec0e528d69d11f01ba7649a9ddc92ab7c8d899cd0 /lib/AST/ExprConstant.cpp
parentfaf4ef62b6a4f5b0638e4fb7f77c33a8935bd003 (diff)
Revert r151460 as it is not enough to address the issue.
Original log: When evaluating integer expressions handle logical operators outside VisitBinaryOperator() to reduce stack pressure for source with huge number of logical operators. Fixes rdar://10913206. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@151464 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/AST/ExprConstant.cpp')
-rw-r--r--lib/AST/ExprConstant.cpp90
1 files changed, 38 insertions, 52 deletions
diff --git a/lib/AST/ExprConstant.cpp b/lib/AST/ExprConstant.cpp
index 224f88cfc2..0cb8e80871 100644
--- a/lib/AST/ExprConstant.cpp
+++ b/lib/AST/ExprConstant.cpp
@@ -406,7 +406,7 @@ namespace {
/// certain things in certain situations.
struct EvalInfo {
ASTContext &Ctx;
-
+CCValue WVal;
/// EvalStatus - Contains information about the evaluation.
Expr::EvalStatus &EvalStatus;
@@ -1205,10 +1205,10 @@ static bool HandleConversionToBool(const CCValue &Val, bool &Result) {
static bool EvaluateAsBooleanCondition(const Expr *E, bool &Result,
EvalInfo &Info) {
assert(E->isRValue() && "missing lvalue-to-rvalue conv in bool condition");
- CCValue Val;
- if (!Evaluate(Val, Info, E))
+ //CCValue Val;
+ if (!Evaluate(Info.WVal, Info, E))
return false;
- return HandleConversionToBool(Val, Result);
+ return HandleConversionToBool(Info.WVal, Result);
}
template<typename T>
@@ -4095,9 +4095,6 @@ public:
}
bool VisitCallExpr(const CallExpr *E);
- bool VisitBinLAnd(const BinaryOperator *E);
- bool VisitBinLOr(const BinaryOperator *E);
- bool VisitBinLogicalOp(const BinaryOperator *E);
bool VisitBinaryOperator(const BinaryOperator *E);
bool VisitOffsetOfExpr(const OffsetOfExpr *E);
bool VisitUnaryOperator(const UnaryOperator *E);
@@ -4498,50 +4495,6 @@ static APSInt CheckedIntArithmetic(EvalInfo &Info, const Expr *E,
return Result;
}
-// Handle logical operators outside VisitBinaryOperator() to reduce
-// stack pressure for source with huge number of logical operators.
-bool IntExprEvaluator::VisitBinLAnd(const BinaryOperator *E) {
- return VisitBinLogicalOp(E);
-}
-bool IntExprEvaluator::VisitBinLOr(const BinaryOperator *E) {
- return VisitBinLogicalOp(E);
-}
-
-bool IntExprEvaluator::VisitBinLogicalOp(const BinaryOperator *E) {
- // These need to be handled specially because the operands aren't
- // necessarily integral nor evaluated.
- bool lhsResult, rhsResult;
-
- if (EvaluateAsBooleanCondition(E->getLHS(), lhsResult, Info)) {
- // We were able to evaluate the LHS, see if we can get away with not
- // evaluating the RHS: 0 && X -> 0, 1 || X -> 1
- if (lhsResult == (E->getOpcode() == BO_LOr))
- return Success(lhsResult, E);
-
- if (EvaluateAsBooleanCondition(E->getRHS(), rhsResult, Info)) {
- if (E->getOpcode() == BO_LOr)
- return Success(lhsResult || rhsResult, E);
- else
- return Success(lhsResult && rhsResult, E);
- }
- } else {
- // Since we weren't able to evaluate the left hand side, it
- // must have had side effects.
- Info.EvalStatus.HasSideEffects = true;
-
- // Suppress diagnostics from this arm.
- SpeculativeEvaluationRAII Speculative(Info);
- if (EvaluateAsBooleanCondition(E->getRHS(), rhsResult, Info)) {
- // We can't evaluate the LHS; however, sometimes the result
- // is determined by the RHS: X && 0 -> 0, X || 1 -> 1.
- if (rhsResult == (E->getOpcode() == BO_LOr))
- return Success(rhsResult, E);
- }
- }
-
- return false;
-}
-
bool IntExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) {
if (E->isAssignmentOp())
return Error(E);
@@ -4551,7 +4504,40 @@ bool IntExprEvaluator::VisitBinaryOperator(const BinaryOperator *E) {
return Visit(E->getRHS());
}
- assert(!E->isLogicalOp() && "Logical ops not handled separately?");
+ if (E->isLogicalOp()) {
+ // These need to be handled specially because the operands aren't
+ // necessarily integral nor evaluated.
+ bool lhsResult, rhsResult;
+
+ if (EvaluateAsBooleanCondition(E->getLHS(), lhsResult, Info)) {
+ // We were able to evaluate the LHS, see if we can get away with not
+ // evaluating the RHS: 0 && X -> 0, 1 || X -> 1
+ if (lhsResult == (E->getOpcode() == BO_LOr))
+ return Success(lhsResult, E);
+
+ if (EvaluateAsBooleanCondition(E->getRHS(), rhsResult, Info)) {
+ if (E->getOpcode() == BO_LOr)
+ return Success(lhsResult || rhsResult, E);
+ else
+ return Success(lhsResult && rhsResult, E);
+ }
+ } else {
+ // Since we weren't able to evaluate the left hand side, it
+ // must have had side effects.
+ Info.EvalStatus.HasSideEffects = true;
+
+ // Suppress diagnostics from this arm.
+ SpeculativeEvaluationRAII Speculative(Info);
+ if (EvaluateAsBooleanCondition(E->getRHS(), rhsResult, Info)) {
+ // We can't evaluate the LHS; however, sometimes the result
+ // is determined by the RHS: X && 0 -> 0, X || 1 -> 1.
+ if (rhsResult == (E->getOpcode() == BO_LOr))
+ return Success(rhsResult, E);
+ }
+ }
+
+ return false;
+ }
QualType LHSTy = E->getLHS()->getType();
QualType RHSTy = E->getRHS()->getType();