summaryrefslogtreecommitdiffstats
path: root/clang/Analysis/GRSimpleVals.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'clang/Analysis/GRSimpleVals.cpp')
-rw-r--r--clang/Analysis/GRSimpleVals.cpp292
1 files changed, 129 insertions, 163 deletions
diff --git a/clang/Analysis/GRSimpleVals.cpp b/clang/Analysis/GRSimpleVals.cpp
index a76acb3d1f3..675882f42e0 100644
--- a/clang/Analysis/GRSimpleVals.cpp
+++ b/clang/Analysis/GRSimpleVals.cpp
@@ -19,47 +19,46 @@
using namespace clang;
namespace clang {
- unsigned RunGRSimpleVals(CFG& cfg, FunctionDecl& FD, ASTContext& Ctx,
- Diagnostic& Diag, bool Visualize) {
-
- if (Diag.hasErrorOccurred())
- return 0;
-
- GRCoreEngine<GRExprEngine> Engine(cfg, FD, Ctx);
- GRExprEngine* CheckerState = &Engine.getCheckerState();
- GRSimpleVals GRSV;
- CheckerState->setTransferFunctions(GRSV);
+
+unsigned RunGRSimpleVals(CFG& cfg, FunctionDecl& FD, ASTContext& Ctx,
+ Diagnostic& Diag, bool Visualize) {
+
+ if (Diag.hasErrorOccurred())
+ return 0;
+
+ GRCoreEngine<GRExprEngine> Engine(cfg, FD, Ctx);
+ GRExprEngine* CheckerState = &Engine.getCheckerState();
+ GRSimpleVals GRSV;
+ CheckerState->setTransferFunctions(GRSV);
+
+ // Execute the worklist algorithm.
+ Engine.ExecuteWorkList(10000);
+
+ // Look for explicit-Null dereferences and warn about them.
+ for (GRExprEngine::null_iterator I=CheckerState->null_begin(),
+ E=CheckerState->null_end(); I!=E; ++I) {
- // Execute the worklist algorithm.
- Engine.ExecuteWorkList(10000);
+ const PostStmt& L = cast<PostStmt>((*I)->getLocation());
+ Expr* Exp = cast<Expr>(L.getStmt());
- // Look for explicit-Null dereferences and warn about them.
- for (GRExprEngine::null_iterator I=CheckerState->null_begin(),
- E=CheckerState->null_end(); I!=E; ++I) {
-
- const PostStmt& L = cast<PostStmt>((*I)->getLocation());
- Expr* Exp = cast<Expr>(L.getStmt());
+ Diag.Report(FullSourceLoc(Exp->getExprLoc(), Ctx.getSourceManager()),
+ diag::chkr_null_deref_after_check);
+ }
- Diag.Report(FullSourceLoc(Exp->getExprLoc(), Ctx.getSourceManager()),
- diag::chkr_null_deref_after_check);
- }
-
#ifndef NDEBUG
- if (Visualize) CheckerState->ViewGraph();
+ if (Visualize) CheckerState->ViewGraph();
#endif
-
- return Engine.getGraph().size();
- }
+
+ return Engine.getGraph().size();
+}
+
} // end clang namespace
//===----------------------------------------------------------------------===//
// Transfer function for Casts.
//===----------------------------------------------------------------------===//
-RValue GRSimpleVals::EvalCast(ValueManager& ValMgr, NonLValue X,
- Expr* CastExpr) {
-
- assert (!isa<UnknownVal>(X) && !isa<UninitializedVal>(X));
+RVal GRSimpleVals::EvalCast(ValueManager& ValMgr, NonLVal X, Expr* CastExpr) {
if (!isa<nonlval::ConcreteInt>(X))
return UnknownVal();
@@ -77,10 +76,8 @@ RValue GRSimpleVals::EvalCast(ValueManager& ValMgr, NonLValue X,
// Casts.
-RValue GRSimpleVals::EvalCast(ValueManager& ValMgr, LValue X, Expr* CastExpr) {
+RVal GRSimpleVals::EvalCast(ValueManager& ValMgr, LVal X, Expr* CastExpr) {
- assert (!isa<UnknownVal>(X) && !isa<UninitializedVal>(X));
-
if (CastExpr->getType()->isPointerType())
return X;
@@ -99,86 +96,65 @@ RValue GRSimpleVals::EvalCast(ValueManager& ValMgr, LValue X, Expr* CastExpr) {
// Unary operators.
-NonLValue GRSimpleVals::EvalMinus(ValueManager& ValMgr, UnaryOperator* U,
- NonLValue X) {
-
- assert (!isa<UnknownVal>(X) && !isa<UninitializedVal>(X));
+RVal GRSimpleVals::EvalMinus(ValueManager& ValMgr, UnaryOperator* U, NonLVal X){
switch (X.getSubKind()) {
+
case nonlval::ConcreteIntKind:
return cast<nonlval::ConcreteInt>(X).EvalMinus(ValMgr, U);
+
default:
- return cast<NonLValue>(UnknownVal());
- }
-}
-
-NonLValue GRSimpleVals::EvalPlus(ValueManager& ValMgr, UnaryOperator* U,
- NonLValue X) {
-
- assert (!isa<UnknownVal>(X) && !isa<UninitializedVal>(X));
-
- switch (X.getSubKind()) {
- case nonlval::ConcreteIntKind:
- return cast<nonlval::ConcreteInt>(X).EvalPlus(ValMgr, U);
- default:
- return cast<NonLValue>(UnknownVal());
+ return UnknownVal();
}
}
+RVal GRSimpleVals::EvalComplement(ValueManager& ValMgr, NonLVal X) {
-NonLValue GRSimpleVals::EvalComplement(ValueManager& ValMgr, NonLValue X) {
-
- assert (!isa<UnknownVal>(X) && !isa<UninitializedVal>(X));
-
switch (X.getSubKind()) {
+
case nonlval::ConcreteIntKind:
return cast<nonlval::ConcreteInt>(X).EvalComplement(ValMgr);
+
default:
- return cast<NonLValue>(UnknownVal());
+ return UnknownVal();
}
}
// Binary operators.
-NonLValue GRSimpleVals::EvalBinaryOp(ValueManager& ValMgr,
- BinaryOperator::Opcode Op,
- NonLValue LHS, NonLValue RHS) {
-
- assert (!isa<UnknownVal>(LHS) && !isa<UninitializedVal>(LHS));
- assert (!isa<UnknownVal>(RHS) && !isa<UninitializedVal>(RHS));
-
- while(1) {
+RVal GRSimpleVals::EvalBinOp(ValueManager& ValMgr, BinaryOperator::Opcode Op,
+ NonLVal L, NonLVal R) {
+ while (1) {
- switch (LHS.getSubKind()) {
+ switch (L.getSubKind()) {
default:
- return cast<NonLValue>(UnknownVal());
+ return cast<NonLVal>(UnknownVal());
case nonlval::ConcreteIntKind:
- if (isa<nonlval::ConcreteInt>(RHS)) {
- const nonlval::ConcreteInt& LHS_CI = cast<nonlval::ConcreteInt>(LHS);
- const nonlval::ConcreteInt& RHS_CI = cast<nonlval::ConcreteInt>(RHS);
- return LHS_CI.EvalBinaryOp(ValMgr, Op, RHS_CI);
+ if (isa<nonlval::ConcreteInt>(R)) {
+ const nonlval::ConcreteInt& L_CI = cast<nonlval::ConcreteInt>(L);
+ const nonlval::ConcreteInt& R_CI = cast<nonlval::ConcreteInt>(R);
+ return L_CI.EvalBinOp(ValMgr, Op, R_CI);
}
- else if(isa<UnknownVal>(RHS))
- return cast<NonLValue>(UnknownVal());
else {
- NonLValue tmp = RHS;
- RHS = LHS;
- LHS = tmp;
+ NonLVal tmp = R;
+ R = L;
+ L = tmp;
continue;
}
case nonlval::SymbolValKind: {
- if (isa<nonlval::ConcreteInt>(RHS)) {
+
+ if (isa<nonlval::ConcreteInt>(R)) {
const SymIntConstraint& C =
- ValMgr.getConstraint(cast<nonlval::SymbolVal>(LHS).getSymbol(), Op,
- cast<nonlval::ConcreteInt>(RHS).getValue());
+ ValMgr.getConstraint(cast<nonlval::SymbolVal>(L).getSymbol(), Op,
+ cast<nonlval::ConcreteInt>(R).getValue());
return nonlval::SymIntConstraintVal(C);
}
else
- return cast<NonLValue>(UnknownVal());
+ return UnknownVal();
}
}
}
@@ -187,150 +163,140 @@ NonLValue GRSimpleVals::EvalBinaryOp(ValueManager& ValMgr,
// Binary Operators (except assignments and comma).
-RValue GRSimpleVals::EvalBinaryOp(ValueManager& ValMgr,
- BinaryOperator::Opcode Op,
- LValue LHS, LValue RHS) {
-
- assert (!isa<UnknownVal>(LHS) && !isa<UninitializedVal>(LHS));
- assert (!isa<UnknownVal>(RHS) && !isa<UninitializedVal>(RHS));
+RVal GRSimpleVals::EvalBinOp(ValueManager& ValMgr, BinaryOperator::Opcode Op,
+ LVal L, LVal R) {
switch (Op) {
+
default:
return UnknownVal();
case BinaryOperator::EQ:
- return EvalEQ(ValMgr, LHS, RHS);
+ return EvalEQ(ValMgr, L, R);
case BinaryOperator::NE:
- return EvalNE(ValMgr, LHS, RHS);
+ return EvalNE(ValMgr, L, R);
}
}
// Pointer arithmetic.
-LValue GRSimpleVals::EvalBinaryOp(ValueManager& ValMgr,
- BinaryOperator::Opcode Op,
- LValue LHS, NonLValue RHS) {
-
- assert (!isa<UnknownVal>(LHS) && !isa<UninitializedVal>(LHS));
- assert (!isa<UnknownVal>(RHS) && !isa<UninitializedVal>(RHS));
-
- return cast<LValue>(UnknownVal());
+RVal GRSimpleVals::EvalBinOp(ValueManager& ValMgr, BinaryOperator::Opcode Op,
+ LVal L, NonLVal R) {
+ return UnknownVal();
}
-// Equality operators for LValues.
+// Equality operators for LVals.
-
-NonLValue GRSimpleVals::EvalEQ(ValueManager& ValMgr, LValue LHS, LValue RHS) {
-
- assert (!isa<UnknownVal>(LHS) && !isa<UninitializedVal>(LHS));
- assert (!isa<UnknownVal>(RHS) && !isa<UninitializedVal>(RHS));
+RVal GRSimpleVals::EvalEQ(ValueManager& ValMgr, LVal L, LVal R) {
- switch (LHS.getSubKind()) {
+ switch (L.getSubKind()) {
+
default:
- assert(false && "EQ not implemented for this LValue.");
- return cast<NonLValue>(UnknownVal());
+ assert(false && "EQ not implemented for this LVal.");
+ return UnknownVal();
case lval::ConcreteIntKind:
- if (isa<lval::ConcreteInt>(RHS)) {
- bool b = cast<lval::ConcreteInt>(LHS).getValue() ==
- cast<lval::ConcreteInt>(RHS).getValue();
+
+ if (isa<lval::ConcreteInt>(R)) {
+ bool b = cast<lval::ConcreteInt>(L).getValue() ==
+ cast<lval::ConcreteInt>(R).getValue();
- return NonLValue::GetIntTruthValue(ValMgr, b);
+ return NonLVal::MakeIntTruthVal(ValMgr, b);
}
- else if (isa<lval::SymbolVal>(RHS)) {
+ else if (isa<lval::SymbolVal>(R)) {
const SymIntConstraint& C =
- ValMgr.getConstraint(cast<lval::SymbolVal>(RHS).getSymbol(),
+ ValMgr.getConstraint(cast<lval::SymbolVal>(R).getSymbol(),
BinaryOperator::EQ,
- cast<lval::ConcreteInt>(LHS).getValue());
+ cast<lval::ConcreteInt>(L).getValue());
return nonlval::SymIntConstraintVal(C);
}
break;
- case lval::SymbolValKind: {
- if (isa<lval::ConcreteInt>(RHS)) {
- const SymIntConstraint& C =
- ValMgr.getConstraint(cast<lval::SymbolVal>(LHS).getSymbol(),
- BinaryOperator::EQ,
- cast<lval::ConcreteInt>(RHS).getValue());
-
- return nonlval::SymIntConstraintVal(C);
- }
-
- // FIXME: Implement unification
- return cast<NonLValue>(UnknownVal());
- //assert (!isa<lval::SymbolVal>(RHS) && "FIXME: Implement unification.");
+ case lval::SymbolValKind: {
+
+ if (isa<lval::ConcreteInt>(R)) {
+ const SymIntConstraint& C =
+ ValMgr.getConstraint(cast<lval::SymbolVal>(L).getSymbol(),
+ BinaryOperator::EQ,
+ cast<lval::ConcreteInt>(R).getValue());
- break;
+ return nonlval::SymIntConstraintVal(C);
}
- case lval::DeclValKind:
+ // FIXME: Implement unification
+ return cast<NonLVal>(UnknownVal());
+ //assert (!isa<lval::SymbolVal>(R) && "FIXME: Implement unification.");
- if (isa<lval::DeclVal>(RHS)) {
- bool b = cast<lval::DeclVal>(LHS) == cast<lval::DeclVal>(RHS);
- return NonLValue::GetIntTruthValue(ValMgr, b);
- }
+ break;
+ }
- break;
+ case lval::DeclValKind:
+
+ if (isa<lval::DeclVal>(R)) {
+ bool b = cast<lval::DeclVal>(L) == cast<lval::DeclVal>(R);
+ return NonLVal::MakeIntTruthVal(ValMgr, b);
+ }
+
+ break;
}
- return NonLValue::GetIntTruthValue(ValMgr, false);
+ return NonLVal::MakeIntTruthVal(ValMgr, false);
}
-NonLValue GRSimpleVals::EvalNE(ValueManager& ValMgr, LValue LHS, LValue RHS) {
+RVal GRSimpleVals::EvalNE(ValueManager& ValMgr, LVal L, LVal R) {
- assert (!isa<UnknownVal>(LHS) && !isa<UninitializedVal>(LHS));
- assert (!isa<UnknownVal>(RHS) && !isa<UninitializedVal>(RHS));
+ switch (L.getSubKind()) {
- switch (LHS.getSubKind()) {
default:
- assert(false && "NE not implemented for this LValue.");
- return cast<NonLValue>(UnknownVal());
+ assert(false && "NE not implemented for this LVal.");
+ return UnknownVal();
case lval::ConcreteIntKind:
- if (isa<lval::ConcreteInt>(RHS)) {
- bool b = cast<lval::ConcreteInt>(LHS).getValue() !=
- cast<lval::ConcreteInt>(RHS).getValue();
+
+ if (isa<lval::ConcreteInt>(R)) {
+ bool b = cast<lval::ConcreteInt>(L).getValue() !=
+ cast<lval::ConcreteInt>(R).getValue();
- return NonLValue::GetIntTruthValue(ValMgr, b);
+ return NonLVal::MakeIntTruthVal(ValMgr, b);
}
- else if (isa<lval::SymbolVal>(RHS)) {
+ else if (isa<lval::SymbolVal>(R)) {
const SymIntConstraint& C =
- ValMgr.getConstraint(cast<lval::SymbolVal>(RHS).getSymbol(),
+ ValMgr.getConstraint(cast<lval::SymbolVal>(R).getSymbol(),
BinaryOperator::NE,
- cast<lval::ConcreteInt>(LHS).getValue());
+ cast<lval::ConcreteInt>(L).getValue());
return nonlval::SymIntConstraintVal(C);
}
break;
- case lval::SymbolValKind: {
- if (isa<lval::ConcreteInt>(RHS)) {
- const SymIntConstraint& C =
- ValMgr.getConstraint(cast<lval::SymbolVal>(LHS).getSymbol(),
- BinaryOperator::NE,
- cast<lval::ConcreteInt>(RHS).getValue());
-
- return nonlval::SymIntConstraintVal(C);
- }
-
- assert (!isa<lval::SymbolVal>(RHS) && "FIXME: Implement sym !=.");
+ case lval::SymbolValKind: {
+ if (isa<lval::ConcreteInt>(R)) {
+ const SymIntConstraint& C =
+ ValMgr.getConstraint(cast<lval::SymbolVal>(L).getSymbol(),
+ BinaryOperator::NE,
+ cast<lval::ConcreteInt>(R).getValue());
- break;
+ return nonlval::SymIntConstraintVal(C);
}
- case lval::DeclValKind:
- if (isa<lval::DeclVal>(RHS)) {
- bool b = cast<lval::DeclVal>(LHS) == cast<lval::DeclVal>(RHS);
- return NonLValue::GetIntTruthValue(ValMgr, b);
- }
+ assert (!isa<lval::SymbolVal>(R) && "FIXME: Implement sym !=.");
break;
+ }
+
+ case lval::DeclValKind:
+ if (isa<lval::DeclVal>(R)) {
+ bool b = cast<lval::DeclVal>(L) == cast<lval::DeclVal>(R);
+ return NonLVal::MakeIntTruthVal(ValMgr, b);
+ }
+
+ break;
}
- return NonLValue::GetIntTruthValue(ValMgr, true);
+ return NonLVal::MakeIntTruthVal(ValMgr, true);
}
OpenPOWER on IntegriCloud