Author: Valeriy Savchenko
Date: 2020-05-28T18:54:27+03:00
New Revision: bb2ae74717a25ba268e7bd17a2a572d931ed094e

URL: 
https://github.com/llvm/llvm-project/commit/bb2ae74717a25ba268e7bd17a2a572d931ed094e
DIFF: 
https://github.com/llvm/llvm-project/commit/bb2ae74717a25ba268e7bd17a2a572d931ed094e.diff

LOG: [analyzer] Merge implementations of SymInt, IntSym, and SymSym exprs

Summary:
SymIntExpr, IntSymExpr, and SymSymExpr share a big portion of logic
that used to be duplicated across all three classes.  New
implementation also adds an easy way of introducing another type of
operands into the mix.

Differential Revision: https://reviews.llvm.org/D79156

Added: 
    

Modified: 
    clang/include/clang/StaticAnalyzer/Core/PathSensitive/SymbolManager.h
    clang/lib/StaticAnalyzer/Core/SymbolManager.cpp

Removed: 
    


################################################################################
diff  --git 
a/clang/include/clang/StaticAnalyzer/Core/PathSensitive/SymbolManager.h 
b/clang/include/clang/StaticAnalyzer/Core/PathSensitive/SymbolManager.h
index 2c505995bee0..390ced8c29f8 100644
--- a/clang/include/clang/StaticAnalyzer/Core/PathSensitive/SymbolManager.h
+++ b/clang/include/clang/StaticAnalyzer/Core/PathSensitive/SymbolManager.h
@@ -326,136 +326,83 @@ class BinarySymExpr : public SymExpr {
     Kind k = SE->getKind();
     return k >= BEGIN_BINARYSYMEXPRS && k <= END_BINARYSYMEXPRS;
   }
-};
-
-/// Represents a symbolic expression like 'x' + 3.
-class SymIntExpr : public BinarySymExpr {
-  const SymExpr *LHS;
-  const llvm::APSInt& RHS;
 
-public:
-  SymIntExpr(const SymExpr *lhs, BinaryOperator::Opcode op,
-             const llvm::APSInt &rhs, QualType t)
-      : BinarySymExpr(SymIntExprKind, op, t), LHS(lhs), RHS(rhs) {
-    assert(lhs);
+protected:
+  static unsigned computeOperandComplexity(const SymExpr *Value) {
+    return Value->computeComplexity();
   }
-
-  void dumpToStream(raw_ostream &os) const override;
-
-  const SymExpr *getLHS() const { return LHS; }
-  const llvm::APSInt &getRHS() const { return RHS; }
-
-  unsigned computeComplexity() const override {
-    if (Complexity == 0)
-      Complexity = 1 + LHS->computeComplexity();
-    return Complexity;
+  static unsigned computeOperandComplexity(const llvm::APSInt &Value) {
+    return 1;
   }
 
-  static void Profile(llvm::FoldingSetNodeID& ID, const SymExpr *lhs,
-                      BinaryOperator::Opcode op, const llvm::APSInt& rhs,
-                      QualType t) {
-    ID.AddInteger((unsigned) SymIntExprKind);
-    ID.AddPointer(lhs);
-    ID.AddInteger(op);
-    ID.AddPointer(&rhs);
-    ID.Add(t);
+  static const llvm::APSInt *getPointer(const llvm::APSInt &Value) {
+    return &Value;
   }
+  static const SymExpr *getPointer(const SymExpr *Value) { return Value; }
 
-  void Profile(llvm::FoldingSetNodeID& ID) override {
-    Profile(ID, LHS, getOpcode(), RHS, getType());
-  }
-
-  // Implement isa<T> support.
-  static bool classof(const SymExpr *SE) {
-    return SE->getKind() == SymIntExprKind;
-  }
+  static void dumpToStreamImpl(raw_ostream &os, const SymExpr *Value);
+  static void dumpToStreamImpl(raw_ostream &os, const llvm::APSInt &Value);
+  static void dumpToStreamImpl(raw_ostream &os, BinaryOperator::Opcode op);
 };
 
-/// Represents a symbolic expression like 3 - 'x'.
-class IntSymExpr : public BinarySymExpr {
-  const llvm::APSInt& LHS;
-  const SymExpr *RHS;
+/// Template implementation for all binary symbolic expressions
+template <class LHSTYPE, class RHSTYPE, SymExpr::Kind ClassKind>
+class BinarySymExprImpl : public BinarySymExpr {
+  LHSTYPE LHS;
+  RHSTYPE RHS;
 
 public:
-  IntSymExpr(const llvm::APSInt &lhs, BinaryOperator::Opcode op,
-             const SymExpr *rhs, QualType t)
-      : BinarySymExpr(IntSymExprKind, op, t), LHS(lhs), RHS(rhs) {
-    assert(rhs);
+  BinarySymExprImpl(LHSTYPE lhs, BinaryOperator::Opcode op, RHSTYPE rhs,
+                    QualType t)
+      : BinarySymExpr(ClassKind, op, t), LHS(lhs), RHS(rhs) {
+    assert(getPointer(lhs));
+    assert(getPointer(rhs));
   }
 
-  void dumpToStream(raw_ostream &os) const override;
+  void dumpToStream(raw_ostream &os) const override {
+    dumpToStreamImpl(os, LHS);
+    dumpToStreamImpl(os, getOpcode());
+    dumpToStreamImpl(os, RHS);
+  }
 
-  const SymExpr *getRHS() const { return RHS; }
-  const llvm::APSInt &getLHS() const { return LHS; }
+  LHSTYPE getLHS() const { return LHS; }
+  RHSTYPE getRHS() const { return RHS; }
 
   unsigned computeComplexity() const override {
     if (Complexity == 0)
-      Complexity = 1 + RHS->computeComplexity();
+      Complexity =
+          computeOperandComplexity(RHS) + computeOperandComplexity(LHS);
     return Complexity;
   }
 
-  static void Profile(llvm::FoldingSetNodeID& ID, const llvm::APSInt& lhs,
-                      BinaryOperator::Opcode op, const SymExpr *rhs,
-                      QualType t) {
-    ID.AddInteger((unsigned) IntSymExprKind);
-    ID.AddPointer(&lhs);
+  static void Profile(llvm::FoldingSetNodeID &ID, LHSTYPE lhs,
+                      BinaryOperator::Opcode op, RHSTYPE rhs, QualType t) {
+    ID.AddInteger((unsigned)ClassKind);
+    ID.AddPointer(getPointer(lhs));
     ID.AddInteger(op);
-    ID.AddPointer(rhs);
+    ID.AddPointer(getPointer(rhs));
     ID.Add(t);
   }
 
-  void Profile(llvm::FoldingSetNodeID& ID) override {
+  void Profile(llvm::FoldingSetNodeID &ID) override {
     Profile(ID, LHS, getOpcode(), RHS, getType());
   }
 
   // Implement isa<T> support.
-  static bool classof(const SymExpr *SE) {
-    return SE->getKind() == IntSymExprKind;
-  }
+  static bool classof(const SymExpr *SE) { return SE->getKind() == ClassKind; }
 };
 
-/// Represents a symbolic expression like 'x' + 'y'.
-class SymSymExpr : public BinarySymExpr {
-  const SymExpr *LHS;
-  const SymExpr *RHS;
-
-public:
-  SymSymExpr(const SymExpr *lhs, BinaryOperator::Opcode op, const SymExpr *rhs,
-             QualType t)
-      : BinarySymExpr(SymSymExprKind, op, t), LHS(lhs), RHS(rhs) {
-    assert(lhs);
-    assert(rhs);
-  }
-
-  const SymExpr *getLHS() const { return LHS; }
-  const SymExpr *getRHS() const { return RHS; }
-
-  void dumpToStream(raw_ostream &os) const override;
-
-  unsigned computeComplexity() const override {
-    if (Complexity == 0)
-      Complexity = RHS->computeComplexity() + LHS->computeComplexity();
-    return Complexity;
-  }
-
-  static void Profile(llvm::FoldingSetNodeID& ID, const SymExpr *lhs,
-                    BinaryOperator::Opcode op, const SymExpr *rhs, QualType t) 
{
-    ID.AddInteger((unsigned) SymSymExprKind);
-    ID.AddPointer(lhs);
-    ID.AddInteger(op);
-    ID.AddPointer(rhs);
-    ID.Add(t);
-  }
+/// Represents a symbolic expression like 'x' + 3.
+using SymIntExpr = BinarySymExprImpl<const SymExpr *, const llvm::APSInt &,
+                                     SymExpr::Kind::SymIntExprKind>;
 
-  void Profile(llvm::FoldingSetNodeID& ID) override {
-    Profile(ID, LHS, getOpcode(), RHS, getType());
-  }
+/// Represents a symbolic expression like 3 - 'x'.
+using IntSymExpr = BinarySymExprImpl<const llvm::APSInt &, const SymExpr *,
+                                     SymExpr::Kind::IntSymExprKind>;
 
-  // Implement isa<T> support.
-  static bool classof(const SymExpr *SE) {
-    return SE->getKind() == SymSymExprKind;
-  }
-};
+/// Represents a symbolic expression like 'x' + 'y'.
+using SymSymExpr = BinarySymExprImpl<const SymExpr *, const SymExpr *,
+                                     SymExpr::Kind::SymSymExprKind>;
 
 class SymbolManager {
   using DataSetTy = llvm::FoldingSet<SymExpr>;

diff  --git a/clang/lib/StaticAnalyzer/Core/SymbolManager.cpp 
b/clang/lib/StaticAnalyzer/Core/SymbolManager.cpp
index ff6cd21b09d6..6ca7aec9caec 100644
--- a/clang/lib/StaticAnalyzer/Core/SymbolManager.cpp
+++ b/clang/lib/StaticAnalyzer/Core/SymbolManager.cpp
@@ -34,45 +34,27 @@ using namespace ento;
 
 void SymExpr::anchor() {}
 
-LLVM_DUMP_METHOD void SymExpr::dump() const {
-  dumpToStream(llvm::errs());
-}
+LLVM_DUMP_METHOD void SymExpr::dump() const { dumpToStream(llvm::errs()); }
 
-void SymIntExpr::dumpToStream(raw_ostream &os) const {
-  os << '(';
-  getLHS()->dumpToStream(os);
-  os << ") "
-     << BinaryOperator::getOpcodeStr(getOpcode()) << ' ';
-  if (getRHS().isUnsigned())
-    os << getRHS().getZExtValue();
-  else
-    os << getRHS().getSExtValue();
-  if (getRHS().isUnsigned())
-    os << 'U';
+void BinarySymExpr::dumpToStreamImpl(raw_ostream &OS, const SymExpr *Sym) {
+  OS << '(';
+  Sym->dumpToStream(OS);
+  OS << ')';
 }
 
-void IntSymExpr::dumpToStream(raw_ostream &os) const {
-  if (getLHS().isUnsigned())
-    os << getLHS().getZExtValue();
+void BinarySymExpr::dumpToStreamImpl(raw_ostream &OS,
+                                     const llvm::APSInt &Value) {
+  if (Value.isUnsigned())
+    OS << Value.getZExtValue();
   else
-    os << getLHS().getSExtValue();
-  if (getLHS().isUnsigned())
-    os << 'U';
-  os << ' '
-     << BinaryOperator::getOpcodeStr(getOpcode())
-     << " (";
-  getRHS()->dumpToStream(os);
-  os << ')';
+    OS << Value.getSExtValue();
+  if (Value.isUnsigned())
+    OS << 'U';
 }
 
-void SymSymExpr::dumpToStream(raw_ostream &os) const {
-  os << '(';
-  getLHS()->dumpToStream(os);
-  os << ") "
-     << BinaryOperator::getOpcodeStr(getOpcode())
-     << " (";
-  getRHS()->dumpToStream(os);
-  os << ')';
+void BinarySymExpr::dumpToStreamImpl(raw_ostream &OS,
+                                     BinaryOperator::Opcode Op) {
+  OS << ' ' << BinaryOperator::getOpcodeStr(Op) << ' ';
 }
 
 void SymbolCast::dumpToStream(raw_ostream &os) const {


        
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to