aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTed Kremenek <kremenek@apple.com>2008-02-05 23:08:41 +0000
committerTed Kremenek <kremenek@apple.com>2008-02-05 23:08:41 +0000
commit0806acf6a197ac7bd5c87649c0429e64e5d0db06 (patch)
treeb1d85beaeed3b1ae91861121946708b76943dca8
parentdfab34a696d1dba8622248c31aaf605906cb6109 (diff)
Added pretty-printing support for lval::SymIntConstraintVal and
nonlval::SymIntConstraintVal. Reworked transfer function for '==' and '!=' for LValues to return SymIntConstraintVal when comparing a symbol with a constant. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@46778 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--Analysis/RValues.cpp143
-rw-r--r--Analysis/RValues.h19
2 files changed, 133 insertions, 29 deletions
diff --git a/Analysis/RValues.cpp b/Analysis/RValues.cpp
index c5c5bdeaa8..33d9d656a7 100644
--- a/Analysis/RValues.cpp
+++ b/Analysis/RValues.cpp
@@ -223,49 +223,109 @@ NonLValue NonLValue::NE(ValueManager& ValMgr, const NonLValue& RHS) const {
NonLValue LValue::EQ(ValueManager& ValMgr, const LValue& RHS) const {
- if (getSubKind() != RHS.getSubKind())
- return NonLValue::GetIntTruthValue(ValMgr, false);
-
switch (getSubKind()) {
default:
assert(false && "EQ not implemented for this LValue.");
return cast<NonLValue>(InvalidValue());
- case lval::ConcreteIntKind: {
- bool b = cast<lval::ConcreteInt>(this)->getValue() ==
- cast<lval::ConcreteInt>(RHS).getValue();
-
- return NonLValue::GetIntTruthValue(ValMgr, b);
- }
+ case lval::ConcreteIntKind:
+ if (isa<lval::ConcreteInt>(RHS)) {
+ bool b = cast<lval::ConcreteInt>(this)->getValue() ==
+ cast<lval::ConcreteInt>(RHS).getValue();
+
+ return NonLValue::GetIntTruthValue(ValMgr, b);
+ }
+ else if (isa<lval::SymbolVal>(RHS)) {
+
+ const SymIntConstraint& C =
+ ValMgr.getConstraint(cast<lval::SymbolVal>(RHS).getSymbol(),
+ BinaryOperator::EQ,
+ cast<lval::ConcreteInt>(this)->getValue());
+
+ return nonlval::SymIntConstraintVal(C);
+ }
+
+ break;
+
+ case lval::SymbolValKind: {
+ if (isa<lval::ConcreteInt>(RHS)) {
+
+ const SymIntConstraint& C =
+ ValMgr.getConstraint(cast<lval::SymbolVal>(this)->getSymbol(),
+ BinaryOperator::EQ,
+ cast<lval::ConcreteInt>(RHS).getValue());
+
+ return nonlval::SymIntConstraintVal(C);
+ }
+
+ assert (!isa<lval::SymbolVal>(RHS) && "FIXME: Implement unification.");
- case lval::DeclValKind: {
- bool b = cast<lval::DeclVal>(*this) == cast<lval::DeclVal>(RHS);
- return NonLValue::GetIntTruthValue(ValMgr, b);
+ break;
}
+
+ case lval::DeclValKind:
+ if (isa<lval::DeclVal>(RHS)) {
+ bool b = cast<lval::DeclVal>(*this) == cast<lval::DeclVal>(RHS);
+ return NonLValue::GetIntTruthValue(ValMgr, b);
+ }
+
+ break;
}
+
+ return NonLValue::GetIntTruthValue(ValMgr, false);
}
NonLValue LValue::NE(ValueManager& ValMgr, const LValue& RHS) const {
- if (getSubKind() != RHS.getSubKind())
- return NonLValue::GetIntTruthValue(ValMgr, true);
-
switch (getSubKind()) {
default:
- assert(false && "EQ not implemented for this LValue.");
+ assert(false && "NE not implemented for this LValue.");
return cast<NonLValue>(InvalidValue());
- case lval::ConcreteIntKind: {
- bool b = cast<lval::ConcreteInt>(this)->getValue() !=
- cast<lval::ConcreteInt>(RHS).getValue();
+ case lval::ConcreteIntKind:
+ if (isa<lval::ConcreteInt>(RHS)) {
+ bool b = cast<lval::ConcreteInt>(this)->getValue() !=
+ cast<lval::ConcreteInt>(RHS).getValue();
+
+ return NonLValue::GetIntTruthValue(ValMgr, b);
+ }
+ else if (isa<lval::SymbolVal>(RHS)) {
+
+ const SymIntConstraint& C =
+ ValMgr.getConstraint(cast<lval::SymbolVal>(RHS).getSymbol(),
+ BinaryOperator::NE,
+ cast<lval::ConcreteInt>(this)->getValue());
+
+ return nonlval::SymIntConstraintVal(C);
+ }
- return NonLValue::GetIntTruthValue(ValMgr, b);
- }
+ break;
- case lval::DeclValKind: {
- bool b = cast<lval::DeclVal>(*this) != cast<lval::DeclVal>(RHS);
- return NonLValue::GetIntTruthValue(ValMgr, b);
- }
+ case lval::SymbolValKind: {
+ if (isa<lval::ConcreteInt>(RHS)) {
+
+ const SymIntConstraint& C =
+ ValMgr.getConstraint(cast<lval::SymbolVal>(this)->getSymbol(),
+ BinaryOperator::NE,
+ cast<lval::ConcreteInt>(RHS).getValue());
+
+ return nonlval::SymIntConstraintVal(C);
+ }
+
+ assert (!isa<lval::SymbolVal>(RHS) && "FIXME: Implement sym !=.");
+
+ break;
+ }
+
+ case lval::DeclValKind:
+ if (isa<lval::DeclVal>(RHS)) {
+ bool b = cast<lval::DeclVal>(*this) == cast<lval::DeclVal>(RHS);
+ return NonLValue::GetIntTruthValue(ValMgr, b);
+ }
+
+ break;
}
+
+ return NonLValue::GetIntTruthValue(ValMgr, true);
}
@@ -320,6 +380,14 @@ void RValue::print(std::ostream& Out) const {
}
}
+static void printOpcode(std::ostream& Out, BinaryOperator::Opcode Op) {
+ switch (Op) {
+ case BinaryOperator::EQ: Out << "=="; break;
+ case BinaryOperator::NE: Out << "!="; break;
+ default: assert(false && "Not yet implemented.");
+ }
+}
+
void NonLValue::print(std::ostream& Out) const {
switch (getSubKind()) {
case nonlval::ConcreteIntKind:
@@ -327,8 +395,18 @@ void NonLValue::print(std::ostream& Out) const {
break;
case nonlval::SymbolValKind:
- Out << '$' << cast<nonlval::SymbolVal>(this)->getSymbolID();
+ Out << '$' << cast<nonlval::SymbolVal>(this)->getSymbol();
break;
+
+ case nonlval::SymIntConstraintValKind: {
+ const nonlval::SymIntConstraintVal& C =
+ *cast<nonlval::SymIntConstraintVal>(this);
+
+ Out << '$' << C.getConstraint().getSymbol() << ' ';
+ printOpcode(Out, C.getConstraint().getOpcode());
+ Out << ' ' << C.getConstraint().getInt().toString();
+ break;
+ }
default:
assert (false && "Pretty-printed not implemented for this NonLValue.");
@@ -336,6 +414,7 @@ void NonLValue::print(std::ostream& Out) const {
}
}
+
void LValue::print(std::ostream& Out) const {
switch (getSubKind()) {
case lval::ConcreteIntKind:
@@ -344,9 +423,19 @@ void LValue::print(std::ostream& Out) const {
break;
case lval::SymbolValKind:
- Out << '$' << cast<lval::SymbolVal>(this)->getSymbolID();
+ Out << '$' << cast<lval::SymbolVal>(this)->getSymbol();
break;
+ case lval::SymIntConstraintValKind: {
+ const lval::SymIntConstraintVal& C =
+ *cast<lval::SymIntConstraintVal>(this);
+
+ Out << '$' << C.getConstraint().getSymbol() << ' ';
+ printOpcode(Out, C.getConstraint().getOpcode());
+ Out << ' ' << C.getConstraint().getInt().toString();
+ break;
+ }
+
case lval::DeclValKind:
Out << '&'
<< cast<lval::DeclVal>(this)->getDecl()->getIdentifier()->getName();
diff --git a/Analysis/RValues.h b/Analysis/RValues.h
index 1db0a185d4..9c788cac35 100644
--- a/Analysis/RValues.h
+++ b/Analysis/RValues.h
@@ -339,7 +339,7 @@ namespace nonlval {
: NonLValue(SymbolValKind,
reinterpret_cast<void*>((uintptr_t) SymID)) {}
- SymbolID getSymbolID() const {
+ SymbolID getSymbol() const {
return (SymbolID) reinterpret_cast<uintptr_t>(getRawPtr());
}
@@ -442,6 +442,7 @@ namespace nonlval {
namespace lval {
enum Kind { SymbolValKind,
+ SymIntConstraintValKind,
DeclValKind,
ConcreteIntKind,
NumKind };
@@ -451,7 +452,7 @@ namespace lval {
SymbolVal(unsigned SymID)
: LValue(SymbolValKind, reinterpret_cast<void*>((uintptr_t) SymID)) {}
- SymbolID getSymbolID() const {
+ SymbolID getSymbol() const {
return (SymbolID) reinterpret_cast<uintptr_t>(getRawPtr());
}
@@ -459,6 +460,20 @@ namespace lval {
return V->getSubKind() == SymbolValKind;
}
};
+
+ class SymIntConstraintVal : public LValue {
+ public:
+ SymIntConstraintVal(const SymIntConstraint& C)
+ : LValue(SymIntConstraintValKind, reinterpret_cast<const void*>(&C)) {}
+
+ const SymIntConstraint& getConstraint() const {
+ return *reinterpret_cast<SymIntConstraint*>(getRawPtr());
+ }
+
+ static inline bool classof(const RValue* V) {
+ return isa<LValue>(V) && V->getSubKind() == SymIntConstraintValKind;
+ }
+ };
class DeclVal : public LValue {
public: