summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTed Kremenek <kremenek@apple.com>2008-01-16 19:42:59 +0000
committerTed Kremenek <kremenek@apple.com>2008-01-16 19:42:59 +0000
commit47b62c1a5fe78c50ddb645fd53dc6eb306643d0d (patch)
treee7cf028eecc8475a50e6e0dc50492bcb6106e971
parentFixed bug where GRConstants::AddBindings() did not check for values (diff)
downloadllvm-project-47b62c1a5fe78c50ddb645fd53dc6eb306643d0d.tar.gz
llvm-project-47b62c1a5fe78c50ddb645fd53dc6eb306643d0d.tar.bz2
llvm-project-47b62c1a5fe78c50ddb645fd53dc6eb306643d0d.zip
Added support for assignments in GRConstants.
llvm-svn: 46086
-rw-r--r--clang/Analysis/GRConstants.cpp24
1 files changed, 24 insertions, 0 deletions
diff --git a/clang/Analysis/GRConstants.cpp b/clang/Analysis/GRConstants.cpp
index 3eff0e0c8643..1502fd4fb87b 100644
--- a/clang/Analysis/GRConstants.cpp
+++ b/clang/Analysis/GRConstants.cpp
@@ -192,6 +192,8 @@ public:
StateTy RemoveGrandchildrenMappings(Stmt* S, StateTy M);
void AddBinding(Expr* E, ExprVariantTy V, bool isBlkLvl = false);
+ void AddBinding(Decl* D, ExprVariantTy V);
+
ExprVariantTy GetBinding(Expr* E);
void BlockStmt_VisitStmt(Stmt* S) { DoStmt(S); }
@@ -200,6 +202,7 @@ public:
void VisitIntegerLiteral(IntegerLiteral* L);
void VisitBinAdd(BinaryOperator* O);
void VisitBinSub(BinaryOperator* O);
+ void VisitBinAssign(BinaryOperator* D);
};
} // end anonymous namespace
@@ -229,6 +232,13 @@ void GRConstants::AddBinding(Expr* E, ExprVariantTy V, bool isBlkLvl) {
CurrentState = StateMgr.Add(CurrentState, DSPtr(E,isBlkLvl), V.getVal());
}
+void GRConstants::AddBinding(Decl* D, ExprVariantTy V) {
+ if (V)
+ CurrentState = StateMgr.Add(CurrentState, DSPtr(D), V.getVal());
+ else
+ CurrentState = StateMgr.Remove(CurrentState, DSPtr(D));
+}
+
void GRConstants::SwitchNodeSets() {
NodeSetTy* Tmp = OldNodes;
OldNodes = Nodes;
@@ -290,6 +300,20 @@ void GRConstants::VisitBinSub(BinaryOperator* B) {
AddBinding(B, GetBinding(B->getLHS()) - GetBinding(B->getRHS()));
}
+
+static inline Expr* IgnoreParen(Expr* E) {
+ while (ParenExpr* P = dyn_cast<ParenExpr>(E))
+ E = P->getSubExpr();
+
+ return E;
+}
+
+
+void GRConstants::VisitBinAssign(BinaryOperator* B) {
+ if (DeclRefExpr* D = dyn_cast<DeclRefExpr>(IgnoreParen(B->getLHS())))
+ AddBinding(D->getDecl(), GetBinding(B->getRHS()));
+}
+
//===----------------------------------------------------------------------===//
// Driver.
//===----------------------------------------------------------------------===//