Added static method "CFG::hasImplicitControlFlow".

This method is used to determine if an expression contains implicit
control-flow, and thus appears in a distinct statement slot in the CFG.

For example:

  (1) x = ... ? ... ? ...

  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.


git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@41868 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/AST/CFG.cpp b/AST/CFG.cpp
index c1f96ce..268fc06 100644
--- a/AST/CFG.cpp
+++ b/AST/CFG.cpp
@@ -1240,6 +1240,30 @@
   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
 //===----------------------------------------------------------------------===//