Removed "hasImplicitControlFlow" from class CFG, and moved it to class Stmt
as a member function. This function is no longer needed within the CFG
class, and logically belongs to the Stmt class as a predicate for a
Stmt instance.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@42489 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/AST/CFG.cpp b/AST/CFG.cpp
index e1c1a74..acda71e 100644
--- a/AST/CFG.cpp
+++ b/AST/CFG.cpp
@@ -1237,30 +1237,6 @@
print_block(OS, cfg, *this, &Helper, true);
}
-/// hasImplicitControlFlow - Returns true if a given expression is
-/// is represented within a CFG as having a designated "statement slot"
-bool CFG::hasImplicitControlFlow(const Stmt* S) {
- switch (S->getStmtClass()) {
- default:
- return false;
-
- case Stmt::CallExprClass:
- case Stmt::ConditionalOperatorClass:
- case Stmt::ChooseExprClass:
- case Stmt::StmtExprClass:
- case Stmt::DeclStmtClass:
- return true;
-
- case Stmt::BinaryOperatorClass: {
- const BinaryOperator* B = cast<BinaryOperator>(S);
- if (B->isLogicalOp() || B->getOpcode() == BinaryOperator::Comma)
- return true;
- else
- return false;
- }
- }
-}
-
//===----------------------------------------------------------------------===//
// CFG Graphviz Visualization
//===----------------------------------------------------------------------===//
diff --git a/AST/Stmt.cpp b/AST/Stmt.cpp
index 9b405f1..0f2bb70 100644
--- a/AST/Stmt.cpp
+++ b/AST/Stmt.cpp
@@ -89,6 +89,28 @@
return SourceRange(RetLoc);
}
+bool Stmt::hasImplicitControlFlow() const {
+ switch (sClass) {
+ default:
+ return false;
+
+ case CallExprClass:
+ case ConditionalOperatorClass:
+ case ChooseExprClass:
+ case StmtExprClass:
+ case DeclStmtClass:
+ return true;
+
+ case Stmt::BinaryOperatorClass: {
+ const BinaryOperator* B = cast<BinaryOperator>(this);
+ if (B->isLogicalOp() || B->getOpcode() == BinaryOperator::Comma)
+ return true;
+ else
+ return false;
+ }
+ }
+}
+
//===----------------------------------------------------------------------===//
// Child Iterators for iterating over subexpressions/substatements
//===----------------------------------------------------------------------===//
diff --git a/include/clang/AST/CFG.h b/include/clang/AST/CFG.h
index 5a3bbf2..e50c3cc 100644
--- a/include/clang/AST/CFG.h
+++ b/include/clang/AST/CFG.h
@@ -274,45 +274,6 @@
void dump() const;
//===--------------------------------------------------------------------===//
- // Static Predicates pertaining to CFG-related properties.
- //===--------------------------------------------------------------------===//
-
- /// hasImplicitControlFlow - Returns true if a given expression is
- /// is represented within a CFG as having a designated "statement slot"
- /// within a CFGBlock to represent the execution of that expression. This
- /// is usefull for expressions that contain implicit control flow, such
- /// as &&, ||, and ? operators, as well as commas and statement expressions.
- ///
- /// For example, considering a CFGBlock with the following statement:
- ///
- /// (1) x = ... ? ... ? ...
- ///
- /// When the CFG is built, this logically becomes:
- ///
- /// (1) ... ? ... : ... (a unique statement slot for the ternary ?)
- /// (2) x = [E1] (where E1 is actually the ConditionalOperator*)
- ///
- /// A client of the CFG, when walking the statement at (2), will encounter
- /// E1. In this case, hasImplicitControlFlow(E1) == true, and the client
- /// will know that the expression E1 is explicitly placed into its own
- /// statement slot to capture the implicit control-flow it has.
- ///
- /// Special cases:
- ///
- /// (1) Function calls.
- /// Function calls are placed in their own statement slot so that
- /// that we have a clear identification of "call-return" sites. If
- /// you see a CallExpr nested as a subexpression of E, the CallExpr appears
- /// in a statement slot in the CFG that dominates the location of E.
- ///
- /// (2) DeclStmts
- /// We include DeclStmts because the initializer expressions for Decls
- /// will be separated out into distinct statements in the CFG. These
- /// statements will dominate the Decl.
- ///
- static bool hasImplicitControlFlow(const Stmt* S);
-
- //===--------------------------------------------------------------------===//
// Internal: constructors and data.
//===--------------------------------------------------------------------===//
diff --git a/include/clang/AST/Stmt.h b/include/clang/AST/Stmt.h
index a346fdc..ff93d22 100644
--- a/include/clang/AST/Stmt.h
+++ b/include/clang/AST/Stmt.h
@@ -85,6 +85,13 @@
// Implement isa<T> support.
static bool classof(const Stmt *) { return true; }
+ /// hasImplicitControlFlow - Some statements (e.g. short circuited operations)
+ /// contain implicit control-flow in the order their subexpressions
+ /// are evaluated. This predicate returns true if this statement has
+ /// such implicit control-flow. Such statements are also specially handled
+ /// within CFGs.
+ bool hasImplicitControlFlow() const;
+
/// Child Iterators: All subclasses must implement child_begin and child_end
/// to permit easy iteration over the substatements/subexpessions of an
/// AST node. This permits easy iteration over all nodes in the AST.